实现以下效果

image.png
结构
<div class="charts">
<van-tabs v-model="active" @click="onClick" line-height='1px' title-active-color='#009E96' color='#009E96'>
<van-tab title="美元">
<div ref="dollarChart" class="mychart"></div>
</van-tab>
<van-tab title="港币">
<div ref="hkdChart" class="mychart"></div>
</van-tab>
<van-tab title="日元">
<div ref="yenChart" class="mychart"></div>
</van-tab>
<van-tab title="欧元">
<div ref="eurChart" class="mychart"></div>
</van-tab>
</van-tabs>
</div>
一开始,按照以下思路实现会出现各种问题
<script>
export default {
data () {
return {
}
},
created () {
this.updateData();
},
methods: {
// 接口一次性回来全部数据
updateData() {
this.$http.post('/pweb/pweb-transfer.MyForeignQry.do', {}).then(res=>{
if( res._RejCode==='000000' ){
this.dataMap = res.DataMap
// 处理echarts数据
for (let key of Object.keys(this.dataMap)){
if(key === 'UsdMap'){ // 美元
this.dollarCurrencyDate = this.dataMap.UsdMap.UsdList.map(item => {
return item.CurrencyDate
})
this.dollarCurrencyBuyRate = this.dataMap.UsdMap.UsdList.map(item => {
return item.CurrencyBuyRate
})
this.dollarCurrencySaleRate = this.dataMap.UsdMap.UsdList.map(item => {
return item.CurrencySaleRate
})
}else if(key === 'EurMap'){ // 欧元
this.eurCurrencyDate = this.dataMap.EurMap.EurList.map(item => {
return item.CurrencyDate
})
this.eurCurrencyBuyRate = this.dataMap.EurMap.EurList.map(item => {
return item.CurrencyBuyRate
})
this.eurCurrencySaleRate = this.dataMap.EurMap.EurList.map(item => {
return item.CurrencySaleRate
})
}else if(key === 'JpyMap'){ // 日元
this.yenCurrencyDate = this.dataMap.JpyMap.JpyList.map(item => {
return item.CurrencyDate
})
this.yenCurrencyBuyRate = this.dataMap.JpyMap.JpyList.map(item => {
return item.CurrencyBuyRate
})
this.yenCurrencySaleRate = this.dataMap.JpyMap.JpyList.map(item => {
return item.CurrencySaleRate
})
}else if(key === 'HkdMap'){ // 港币
this.hkdCurrencyDate = this.dataMap.HkdMap.HkdList.map(item => {
return item.CurrencyDate
})
this.hkdCurrencyBuyRate = this.dataMap.HkdMap.HkdList.map(item => {
return item.CurrencyBuyRate
})
this.hkdCurrencySaleRate = this.dataMap.HkdMap.HkdList.map(item => {
return item.CurrencySaleRate
})
}
}
// 美元
let Data = this.dollarCurrencyDate
let BuyRate = this.dollarCurrencyBuyRate.map(Number)
let SaleRate = this.dollarCurrencySaleRate.map(Number)
// this.setChart(Data,BuyRate,SaleRate)
this.$nextTick(() => {
this.setChart(Data,BuyRate,SaleRate)
})
}
})
},
setChart(Data,BuyRate,SaleRate) {
let dollarChart = this.$echarts.init(this.$refs.dollarChart)
let eurChart = this.$echarts.init(this.$refs.eurChart)
let yenChart = this.$echarts.init(this.$refs.yenChart)
let hkdChart = this.$echarts.init(this.$refs.hkdChart)
let dollarOption = {
tooltip: {
trigger: 'axis'
},
legend: {
type: 'plain',
left: 'left',
data: ['买入汇率', '卖出汇率']
},
xAxis: {
type: 'category',
axisLabel : {//坐标轴刻度标签的相关设置。
interval:0,
rotate:"45"
},
data: Data
},
yAxis: {
type: 'value',
max : 6.7,
min : 6.0,
splitNumber : 7
},
series: [
{
name: '买入汇率',
data: BuyRate,
type: 'line'
},
{
name: '卖出汇率',
data: SaleRate,
type: 'line'
}
]
}
let eurOption = {
tooltip: {
trigger: 'axis'
},
legend: {
type: 'plain',
left: 'left',
data: ['买入汇率', '卖出汇率']
},
xAxis: {
type: 'category',
axisLabel : {//坐标轴刻度标签的相关设置。
interval:0,
rotate:"45"
},
data: this.eurCurrencyDate
},
yAxis: {
type: 'value',
max : 7.8,
min : 7.4,
splitNumber : 7
},
series: [
{
name: '买入汇率',
data: this.eurCurrencyBuyRate.map(Number),
type: 'line'
},
{
name: '卖出汇率',
data: this.eurCurrencySaleRate.map(Number),
type: 'line'
}
]
}
let yenOption = {
tooltip: {
trigger: 'axis'
},
legend: {
type: 'plain',
left: 'left',
data: ['买入汇率', '卖出汇率']
},
xAxis: {
type: 'category',
axisLabel : {//坐标轴刻度标签的相关设置。
interval:0,
rotate:"45"
},
data: this.yenCurrencyDate
},
yAxis: {
type: 'value',
max : 0.4,
min : 0,
splitNumber : 7
},
series: [
{
name: '买入汇率',
data: this.yenCurrencyBuyRate.map(Number),
type: 'line'
},
{
name: '卖出汇率',
data: this.yenCurrencySaleRate.map(Number),
type: 'line'
}
]
}
let hkdOption = {
tooltip: {
trigger: 'axis'
},
legend: {
type: 'plain',
left: 'left',
data: ['买入汇率', '卖出汇率']
},
xAxis: {
type: 'category',
axisLabel : {//坐标轴刻度标签的相关设置。
interval:0,
rotate:"45"
},
data: this.hkdCurrencyDate
},
yAxis: {
type: 'value',
max : 1.1,
min : 0.7,
splitNumber : 7
},
series: [
{
name: '买入汇率',
data: this.hkdCurrencyBuyRate.map(Number),
type: 'line'
},
{
name: '卖出汇率',
data: this.hkdCurrencySaleRate.map(Number),
type: 'line'
}
]
}
dollarChart.setOption(dollarOption)
eurChart.setOption(eurOption)
yenChart.setOption(yenOption)
hkdChart.setOption(hkdOption)
},
},
}
</script>
上述代码在web端结合element的tab可以实现效果
但在手机端会出现问题
具体如下
一 由于echarts的dom和数据是异步的,如果没有使用nextTick会出现如下报错

image.png
解决办法是使用nextTick让数据回来后,等待下一次dom更新完毕后再渲染页面
具体是在created阶段使用nextTick
上述,将nextTick放在拿数据的方法里,依然报上述错误
二 于是给了nextTick后,则报如下错误

image.png
报错 Error in nextTick: "TypeError: Cannot read property 'children' of undefined"
解决:加一个判断 if (数据存在),再执行this.nextTick()方法
三 在setChart方法中,需要给echarts定义dom,这里由于一开始只拿到了美元的div,其他div取不到,这样会导致美元的图也显示不出来
let dollarChart = this.$echarts.init(this.$refs.dollarChart)
// 下面三个div获取不到,导致后面流程走不了,因此美元也展示不了图
let eurChart = this.$echarts.init(this.$refs.eurChart)
let yenChart = this.$echarts.init(this.$refs.yenChart)
let hkdChart = this.$echarts.init(this.$refs.hkdChart)
一开始,总是觉得nextTick没有用对地方,导致数据回来dom没更新(因为在web端这样做是可行的),但没想到是这里出现了关键的问题,后面通过打印div才发现只拿到了一个div,length为1

image.png
这个关键问题找出后,后面的问题就迎刃而解!
解决思路
通过tab提供的click事件,点击一次,则初始化一次dom元素,之后再拿数据去画图,这个时候还是要用到nextTick,以保证dom更新完毕后再把数据渲染上去(因为数据在created就已经拿到)
直接上代码
// 在created()里使用this.$nextTick()可以等待dom生成以后再来获取dom对象
created () {
this.$nextTick(() => {
this.updateData();
})
},
methods: {
// tab的点击事件
onClick(name, title){
if(title === '港币'){
this.$nextTick(()=>{
let hkdChart = this.$echarts.init(this.$refs.hkdChart)
let hkdOption = {
tooltip: {
trigger: 'axis'
},
legend: {
type: 'plain',
left: 'left',
top:'12px',
data: ['买入汇率', '卖出汇率']
},
xAxis: {
type: 'category',
axisLabel : {//坐标轴刻度标签的相关设置。
interval:0,
rotate:"45"
},
data: this.hkdCurrencyDate
},
yAxis: {
type: 'value',
max : 1.1,
min : 0.7,
splitNumber : 7
},
series: [
{
name: '买入汇率',
data: this.hkdCurrencyBuyRate.map(Number),
type: 'line'
},
{
name: '卖出汇率',
data: this.hkdCurrencySaleRate.map(Number),
type: 'line'
}
]
}
hkdChart.setOption(hkdOption)
})
}else if(title === '日元'){
this.$nextTick(()=>{
let yenChart = this.$echarts.init(this.$refs.yenChart)
let yenOption = {
tooltip: {
trigger: 'axis'
},
legend: {
type: 'plain',
left: 'left',
top:'12px',
data: ['买入汇率', '卖出汇率']
},
xAxis: {
type: 'category',
axisLabel : {//坐标轴刻度标签的相关设置。
interval:0,
rotate:"45"
},
data: this.yenCurrencyDate
},
yAxis: {
type: 'value',
max : 0.4,
min : 0,
splitNumber : 7
},
series: [
{
name: '买入汇率',
data: this.yenCurrencyBuyRate.map(Number),
type: 'line'
},
{
name: '卖出汇率',
data: this.yenCurrencySaleRate.map(Number),
type: 'line'
}
]
}
yenChart.setOption(yenOption)
})
}else if(title === '欧元'){
this.$nextTick(()=>{
let eurChart = this.$echarts.init(this.$refs.eurChart)
let eurOption = {
tooltip: {
trigger: 'axis'
},
legend: {
type: 'plain',
left: 'left',
top:'12px',
data: ['买入汇率', '卖出汇率']
},
xAxis: {
type: 'category',
axisLabel : {//坐标轴刻度标签的相关设置。
interval:0,
rotate:"45"
},
data: this.eurCurrencyDate
},
yAxis: {
type: 'value',
max : 7.8,
min : 7.4,
splitNumber : 7
},
series: [
{
name: '买入汇率',
data: this.eurCurrencyBuyRate.map(Number),
type: 'line'
},
{
name: '卖出汇率',
data: this.eurCurrencySaleRate.map(Number),
type: 'line'
}
]
}
eurChart.setOption(eurOption)
})
}
},
updateData() {
this.$http.post('/pweb/pweb-transfer.MyForeignQry.do', {}).then(res=>{
if( res._RejCode==='000000' ){
this.dataMap = res.DataMap
// 处理echarts数据
for (let key of Object.keys(this.dataMap)){
if(key === 'UsdMap'){ // 美元
this.dollarCurrencyDate = this.dataMap.UsdMap.UsdList.map(item => {
return item.CurrencyDate
})
this.dollarCurrencyBuyRate = this.dataMap.UsdMap.UsdList.map(item => {
return item.CurrencyBuyRate
})
this.dollarCurrencySaleRate = this.dataMap.UsdMap.UsdList.map(item => {
return item.CurrencySaleRate
})
}else if(key === 'EurMap'){ // 欧元
this.eurCurrencyDate = this.dataMap.EurMap.EurList.map(item => {
return item.CurrencyDate
})
this.eurCurrencyBuyRate = this.dataMap.EurMap.EurList.map(item => {
return item.CurrencyBuyRate
})
this.eurCurrencySaleRate = this.dataMap.EurMap.EurList.map(item => {
return item.CurrencySaleRate
})
}else if(key === 'JpyMap'){ // 日元
this.yenCurrencyDate = this.dataMap.JpyMap.JpyList.map(item => {
return item.CurrencyDate
})
this.yenCurrencyBuyRate = this.dataMap.JpyMap.JpyList.map(item => {
return item.CurrencyBuyRate
})
this.yenCurrencySaleRate = this.dataMap.JpyMap.JpyList.map(item => {
return item.CurrencySaleRate
})
}else if(key === 'HkdMap'){ // 港币
this.hkdCurrencyDate = this.dataMap.HkdMap.HkdList.map(item => {
return item.CurrencyDate
})
this.hkdCurrencyBuyRate = this.dataMap.HkdMap.HkdList.map(item => {
return item.CurrencyBuyRate
})
this.hkdCurrencySaleRate = this.dataMap.HkdMap.HkdList.map(item => {
return item.CurrencySaleRate
})
}
}
// 美元
let Data = this.dollarCurrencyDate
let BuyRate = this.dollarCurrencyBuyRate.map(Number)
let SaleRate = this.dollarCurrencySaleRate.map(Number)
let this_ = this
if(Data && BuyRate && SaleRate){ // 先判断一下是否有数据,否则会报nextTick的错误
this_.setChart(Data,BuyRate,SaleRate)
}
}
})
},
setChart(Data,BuyRate,SaleRate) {
let dollarChart = this.$echarts.init(this.$refs.dollarChart)
let dollarOption = {
tooltip: {
trigger: 'axis'
},
legend: {
type: 'plain',
left: 'left',
top:'12px',
data: ['买入汇率', '卖出汇率']
},
xAxis: {
type: 'category',
axisLabel : {//坐标轴刻度标签的相关设置。
interval:0,
rotate:"45"
},
data: Data
},
yAxis: {
type: 'value',
max : 6.7,
min : 6.3,
splitNumber : 7
},
series: [
{
name: '买入汇率',
data: BuyRate,
type: 'line'
},
{
name: '卖出汇率',
data: SaleRate,
type: 'line'
}
]
}
dollarChart.setOption(dollarOption)
},
},