<script lang="ts" setup>
import { ref,onMounted, onBeforeUnmount, Ref, unref, watch, computed } from 'vue'
import * as echarts from 'echarts'
import { spCampaignMetricsEnum } from '/@/views/adManage/utils/enum.js'
import MetricsCards from '/@/components/MetricsCards/index.vue'
import XEUtils from 'xe-utils'
import { buildChartOpt, parseQueryParams } from '/@/views/adManage/utils/tools.js'

defineOptions({
  name: "DataTendencyChart"
})

interface Props {
  fetchCard: Function,
  fetchLine: Function,
  fetchLineMonth?: Function,
  fetchLineWeek?: Function,
  query: {[key: string]: any},
  initMetric?: ShowMetric[],
  metricEnum?: {[key: string]: string}[]
}

const props = withDefaults(defineProps<Props>(), {
  initMetric: () => [
    {metric: 'Impression', color: '#0085ff', 'label': '曝光量'},
    {metric: 'Click', color: '#3fd4cf', 'label': '点击量'},
    {metric: 'Spend', color: '#ff9500', 'label': '花费'},
  ],
  metricEnum: () => spCampaignMetricsEnum
})

const metrics = ref(props.initMetric)
// const shopInfo = useShopInfo()
// const publicData = usePublicData()
// const { dateRange } = storeToRefs(publicData)
const metricsItems: Ref<MetricData[]> = ref([])
let chartObj:any
const chartRef = ref()
const statDim = ref('day')
const option: any = {
  dataset: {
    source: []
  },
  tooltip: {
    trigger: 'axis',
    axisPointer: {
      label: {
        backgroundColor: '#6a7985'
      }
    }
  },
  legend: {
    selected: {},  // 控制显隐
    show: false
  },
  grid: {
    top: 50, right: 150, bottom: 30, left: 65,
  },
  xAxis: {
    type: 'category'
  },
  yAxis: [
    {
      id: 0,
      type: 'value',
      name: '',
      splitLine: {
        show: true // 设置显示分割线
      },
      axisLine: {
        show: true,
				lineStyle: { color: '' }
      },
      show: true
    },
    {
      id: 1,
      type: 'value',
      name: '',
      position: 'right',
      splitLine: {
        show: false
      },
      axisLine: {
        show: true,
				lineStyle: {
					color: ''
				}
      },
      show: true
    },
    {
      id: 2,
      type: 'value',
      position: 'right',
      offset: 90,
      name: '',
      splitLine: {
        show: false
      },
      axisLine: {
        show: true,
				lineStyle: {
					color: ''
				}
      },
      show: true
    }
  ],
  series: [
    {
      id: 0,
      name: '',
      type: 'bar',
      encode: {
        x: 'Name',
        y: ''
      },
      barWidth: '20px',
      yAxisIndex: 0,
      itemStyle: {
        color: '',
        borderRadius: [6, 6, 6, 6],
      }
    },
    {
      id: 1,
      name: '',
      type: 'line',
      encode: {
        x: 'Name',
        y: ''
      },
      symbolSize: 6,
      symbol: 'circle',
      smooth: true,
      yAxisIndex: 1,
      itemStyle: {
        // color: '#ff9500',
        // borderColor: '#ff9500'
      },
      areaStyle: {
        // color: new echarts.graphic.LinearGradient(0, 0, 0, 1, [
        //   { offset: 0, color: '#3fd4cf53' },
        //   { offset: 1, color: '#3fd4cf03' },
        // ]),
      },
      emphasis: {
        focus:'series'
      }
    },
    {
      id: 2,
      name: '',
      type: 'line',
      encode: {
        x: 'Name',
        y: ''
      },
      symbolSize: 6,
      symbol: 'circle',
      smooth: true,
      yAxisIndex: 2,
      itemStyle: {},
      areaStyle: {},
      emphasis: {
        focus:'series'
      }
    }
  ]
}
const loading = ref(true)
const queryParams = computed(() => parseQueryParams(props.query))

onMounted(() => {
  getMetricsItems()
	addResize()
  // initLine()
  setTimeout(() => { initLine() }, 0)
})
onBeforeUnmount(() => {
	if(chartObj) {
		chartObj.dispose()
    chartObj = null
	}
  removeResize()
})

const initLine = async () => {
	chartObj = echarts.init(chartRef.value)
	const items = await getDataset()
	option.dataset.source = items

  XEUtils.arrayEach(option.series, (info:any, index) => {
    const color = metrics.value[index].color
    info.name = metrics.value[index].label
    info.encode.y = metrics.value[index].metric
    if (info.type === 'bar') {
      info.itemStyle.color = color
    } else {
      info.itemStyle = { color: color, borderColor: color }
      info.areaStyle = {
        color: new echarts.graphic.LinearGradient(0, 0, 0, 1, [
          { offset: 0, color: color + '53' },
          { offset: 1, color: color + '03' },
        ])
      }
    }
  })
  XEUtils.arrayEach(option.yAxis, (info:any, index) => {
    info.name = metrics.value[index].label
    info.axisLine.lineStyle.color = metrics.value[index].color
  })

  XEUtils.arrayEach(props.metricEnum, info => {
    option.legend.selected[info.label] = false
  })
  for(const info of metrics.value) {
    option.legend.selected[info.label] = true
  }
  // console.log(option)
	chartObj.setOption(option)
  loading.value = false
}
const getDataset = async () => {
	if (statDim.value === 'week') {
    if (props.fetchLineWeek) {
      const resp = await props.fetchLineWeek(queryParams.value)
      return resp.data
    }
  } else if (statDim.value === 'month') {
    if (props.fetchLineMonth) {
      const resp = await props.fetchLineMonth(queryParams.value)
      return resp.data
    }
  } else {
    const resp = await props.fetchLine(queryParams.value)
    return resp.data
  }
}
const getMetricsItems = async () => {
	const resp = await props.fetchCard(queryParams.value)
	const data = resp.data
  metricsItems.value.length = 0
	XEUtils.arrayEach(props.metricEnum, info => {
		const tmp:MetricData = {
			label: info.label,
			value: info.value,
			metricVal: data[info.value],
			gapVal: data[`gap${info.value}`],
			preVal: data[`prev${info.value}`],
		}
		metricsItems.value.push(tmp)
	})
}

const changeMetric = () => {
  const opt = buildChartOpt(option, metrics.value)
  chartObj.setOption(opt)
}

const changeStatDim = async () => {
  loading.value = true
  let source = await getDataset()
  if (source.length > 0) {
    chartObj.setOption({dataset: {source: source}})
  }
  loading.value = false
}

watch(
  props.query,
  async () => {
    // console.log("------watch-----queryParams", props.query)
    loading.value = true
    await getMetricsItems()
    const items = await getDataset()
    const opt = { dataset: { source: items } }
    chartObj.setOption(opt)
    loading.value = false
  }
)

const resizeChart = () => { chartObj.resize() }
const addResize = () => { window.addEventListener('resize', resizeChart) }
const removeResize = () => { window.removeEventListener('resize', resizeChart) }


</script>

<template>
  <div v-loading="loading">
    <MetricsCards v-model="metrics" :metric-items="metricsItems" @change="changeMetric"></MetricsCards>
    <div style="height: 350px;" ref="chartRef"></div>
</div>
</template>

<style scoped>
.metrics-cards {
  display: flex;
  justify-content: space-between;
  align-items: flex-start;
  gap: 12px;
  width: 100%;
}

.chart-button-group {
  display: flex;
  justify-content: flex-end;
  margin-top: 5px;
}
</style>
