dev-cl
parent
fa39fd8492
commit
0ef7703f7d
@ -0,0 +1,62 @@ |
||||
<template> |
||||
<Echart :options="optionsData" :width="400" :height="200" /> |
||||
</template> |
||||
|
||||
<script setup name="BarSalerClueReport"> |
||||
import { set } from 'lodash-es' |
||||
|
||||
onMounted(() => { |
||||
nextTick(() => { |
||||
getReportData() |
||||
}) |
||||
}) |
||||
|
||||
const optionsData = ref({}) |
||||
|
||||
const getReportData = async () => { |
||||
// const data = await HomeApi.getClueSignSignRate() |
||||
set(optionsData, 'radiusAxis', { |
||||
type: 'category', |
||||
data: ['宝典', '一点通', '抖音', '小红书'], |
||||
z: 10 |
||||
}) |
||||
set(optionsData, 'series', [ |
||||
{ |
||||
type: 'bar', |
||||
data: [1, 2, 3, 4], |
||||
coordinateSystem: 'polar', |
||||
name: '高意向A', |
||||
stack: 'a', |
||||
emphasis: { |
||||
focus: 'series' |
||||
} |
||||
}, |
||||
{ |
||||
type: 'bar', |
||||
data: [2, 4, 6, 8], |
||||
coordinateSystem: 'polar', |
||||
name: '中意向B', |
||||
stack: 'a', |
||||
emphasis: { |
||||
focus: 'series' |
||||
} |
||||
}, |
||||
{ |
||||
type: 'bar', |
||||
data: [1, 2, 3, 4], |
||||
coordinateSystem: 'polar', |
||||
name: '低意向C', |
||||
stack: 'a', |
||||
emphasis: { |
||||
focus: 'series' |
||||
} |
||||
} |
||||
]) |
||||
} |
||||
|
||||
defineExpose({ |
||||
getReportData |
||||
}) |
||||
</script> |
||||
|
||||
<style lang="scss" scoped></style> |
@ -0,0 +1,353 @@ |
||||
<template> |
||||
<Dialog title="详情" v-model="dialogVisible" width="1000px"> |
||||
<el-form :model="searchForm" label-width="0" inline> |
||||
<el-form-item> |
||||
<el-date-picker |
||||
v-model="searchForm.period" |
||||
type="daterange" |
||||
format="YYYY-MM-DD" |
||||
value-format="YYYY-MM-DD" |
||||
start-placeholder="选择日期" |
||||
end-placeholder="选择日期" |
||||
/> |
||||
</el-form-item> |
||||
<el-form-item> |
||||
<el-tree-select |
||||
v-model="searchForm.sourceId" |
||||
:data="props.sourceOptions" |
||||
:props="defaultProps" |
||||
check-strictly |
||||
node-key="sourceId" |
||||
placeholder="请选择渠道" |
||||
/> |
||||
</el-form-item> |
||||
<el-form-item> |
||||
<el-select v-model="searchForm.cartype" placeholder="选择驾照类型" clearable> |
||||
<el-option |
||||
v-for="item in props.cartypeOptions" |
||||
:key="item.value" |
||||
:label="item.label" |
||||
:value="item.value" |
||||
/> |
||||
</el-select> |
||||
</el-form-item> |
||||
|
||||
<el-form-item> |
||||
<el-button @click="handleSearch">查询</el-button> |
||||
<el-button @click="handleReset">重置</el-button> |
||||
</el-form-item> |
||||
</el-form> |
||||
|
||||
<el-tabs v-model="showPane" class="pb-10px"> |
||||
<el-tab-pane label="详细数据" :name="1"> |
||||
<el-table v-loading="loading" :data="tableList" border stripe> |
||||
<el-table-column prop="sourceName" label="渠道名称" width="100" fixed="left" /> |
||||
<el-table-column prop="" label="新线索数" sortable /> |
||||
<el-table-column prop="" label="成交数" sortable /> |
||||
<el-table-column prop="" label="成交率" sortable /> |
||||
<el-table-column prop="" label="成交周期" sortable /> |
||||
<el-table-column prop="" label="毛利/单" sortable /> |
||||
<el-table-column prop="" label="支出/单" sortable /> |
||||
<el-table-column prop="" label="线索成本/条" sortable /> |
||||
<el-table-column prop="" label="净利润/单" sortable /> |
||||
<el-table-column label="总线索成本" prop="" sortable min-width="100" /> |
||||
<el-table-column label="总支出" prop="" sortable min-width="100" /> |
||||
<el-table-column label="总利润" prop="" sortable min-width="100" /> |
||||
</el-table> |
||||
</el-tab-pane> |
||||
<el-tab-pane label="图表展示" :name="2" lazy> |
||||
<el-row :gutter="20"> |
||||
<el-col :span="24" :offset="0"> |
||||
<el-checkbox-group v-model="showChannel" @change="setReportData"> |
||||
<el-checkbox v-for="(item, index) in channelArr" :key="index" :label="item" /> |
||||
</el-checkbox-group> |
||||
</el-col> |
||||
|
||||
<el-col :span="12" :offset="0"> |
||||
<el-skeleton :loading="loading" animated> |
||||
<Echart :options="echart1Option" width="100%" :height="400" /> |
||||
</el-skeleton> |
||||
</el-col> |
||||
<el-col :span="12" :offset="0"> |
||||
<Echart :options="echart2Option" width="100%" :height="400" /> |
||||
</el-col> |
||||
<el-col :span="24" :offset="0"> |
||||
<Echart :options="echart3Option" width="100%" :height="400" /> |
||||
</el-col> |
||||
</el-row> |
||||
</el-tab-pane> |
||||
</el-tabs> |
||||
</Dialog> |
||||
</template> |
||||
|
||||
<script setup name="DialogSalerReportDetail"> |
||||
import { set } from 'lodash-es' |
||||
import * as reportApi from '@/api/home/reportSignRate' |
||||
import { removeNullField } from '@/utils' |
||||
|
||||
const props = defineProps({ |
||||
cartypeOptions: { |
||||
type: Array, |
||||
default: () => [] |
||||
}, |
||||
sourceOptions: { |
||||
type: Array, |
||||
default: () => [] |
||||
} |
||||
}) |
||||
|
||||
const defaultProps = { |
||||
children: 'children', |
||||
label: 'sourceName', |
||||
value: 'sourceId', |
||||
isLeaf: 'leaf' |
||||
} |
||||
|
||||
const dialogVisible = ref(false) // 弹窗的是否展示 |
||||
const dialogTitle = ref('') // 弹窗的标题 |
||||
const loading = ref(false) |
||||
const searchForm = ref({}) |
||||
|
||||
const showPane = ref(1) |
||||
const showChannel = ref([]) |
||||
|
||||
function handleReset() { |
||||
searchForm.value = { |
||||
nickname: undefined, |
||||
period: [] |
||||
} |
||||
} |
||||
|
||||
/** 打开弹窗 */ |
||||
const open = async (info, queryInfo) => { |
||||
showPane.value = 1 |
||||
dialogVisible.value = true |
||||
dialogTitle.value = `销售详情-【${info.nickname}】` |
||||
searchForm.value.period = queryInfo.period |
||||
searchForm.value.cartype = queryInfo.cartype |
||||
showChannel.value = [...channelArr] |
||||
|
||||
handleSearch() |
||||
} |
||||
defineExpose({ open }) // 提供 open 方法,用于打开弹窗 |
||||
|
||||
const tableList = ref([]) |
||||
|
||||
async function handleSearch() { |
||||
loading.value = true |
||||
try { |
||||
setReportData() |
||||
const data = await reportApi.getList(removeNullField(searchForm.value)) |
||||
tableList.value = data.map((item) => { |
||||
const count = item.monthClueSignRateReportList.reduce( |
||||
(pre, cur) => { |
||||
return { |
||||
signCount: pre.signCount + cur.clueSignNum, |
||||
clueCount: pre.clueCount + cur.followClueNum |
||||
} |
||||
}, |
||||
{ signCount: 0, clueCount: 0 } |
||||
) |
||||
const rate = count.clueCount > 0 ? ((count.signCount * 100) / count.clueCount).toFixed(2) : 0 |
||||
return { |
||||
...item, |
||||
totalRate: `${rate}%(${count.signCount}/${count.clueCount})`, |
||||
totalRateNum: rate |
||||
} |
||||
}) |
||||
} finally { |
||||
loading.value = false |
||||
} |
||||
} |
||||
|
||||
const channelArr = ['美团', '高德', '线下渠道', '其他', '一点通', '抖音', '小红书', '宝典'] |
||||
|
||||
const echart1Option = ref({ |
||||
title: { |
||||
text: '线索分布图' |
||||
}, |
||||
radiusAxis: {}, |
||||
angleAxis: {}, |
||||
tooltip: { |
||||
show: true, |
||||
formatter: '{b0}-{a}: {c}' |
||||
}, |
||||
polar: {}, |
||||
legend: { |
||||
show: true |
||||
} |
||||
}) |
||||
|
||||
const echart2Option = ref({ |
||||
title: { |
||||
text: '成交分布图' |
||||
}, |
||||
radiusAxis: {}, |
||||
angleAxis: {}, |
||||
tooltip: { |
||||
show: true, |
||||
formatter: '{b0}-{a}: {c}' |
||||
}, |
||||
polar: {}, |
||||
legend: { |
||||
show: true |
||||
} |
||||
}) |
||||
|
||||
const echart3Option = ref({ |
||||
title: { |
||||
text: '销售雷达图' |
||||
}, |
||||
radar: { |
||||
indicator: [ |
||||
{ name: '成交周期' }, |
||||
{ name: '毛利/单' }, |
||||
{ name: '支出/单' }, |
||||
{ name: '线索成本/条' }, |
||||
{ name: '净利润/单' }, |
||||
{ name: '线索总成本' }, |
||||
{ name: '总支出' }, |
||||
{ name: '总利润' } |
||||
] |
||||
}, |
||||
legend: { |
||||
show: true |
||||
} |
||||
}) |
||||
|
||||
const setReportData = async () => { |
||||
// const data = await HomeApi.getClueSignSignRate() |
||||
|
||||
set(echart1Option.value, 'radiusAxis', { |
||||
type: 'category', |
||||
data: showChannel.value, |
||||
axisLabel: { |
||||
margin: 5, |
||||
fontSize: 10, |
||||
interval: 0 |
||||
} |
||||
}) |
||||
|
||||
set(echart1Option.value, 'series', [ |
||||
{ |
||||
type: 'bar', |
||||
data: [2, 2, 3, 4, 10, 22, 43, 141], |
||||
coordinateSystem: 'polar', |
||||
name: '高意向A', |
||||
stack: 'a', |
||||
emphasis: { |
||||
focus: 'series' |
||||
}, |
||||
label: { |
||||
show: true, |
||||
position: 'middle' |
||||
} |
||||
}, |
||||
{ |
||||
type: 'bar', |
||||
data: [6, 6, 7, 8, 22, 14, 36, 128], |
||||
coordinateSystem: 'polar', |
||||
name: '中意向B', |
||||
stack: 'a', |
||||
emphasis: { |
||||
focus: 'series' |
||||
}, |
||||
label: { |
||||
show: true, |
||||
position: 'middle' |
||||
} |
||||
}, |
||||
{ |
||||
type: 'bar', |
||||
data: [1, 4, 7, 11, 16, 42, 13, 42], |
||||
coordinateSystem: 'polar', |
||||
name: '低意向C', |
||||
stack: 'a', |
||||
emphasis: { |
||||
focus: 'series' |
||||
}, |
||||
label: { |
||||
show: true, |
||||
position: 'middle' |
||||
} |
||||
} |
||||
]) |
||||
|
||||
set(echart2Option.value, 'radiusAxis', { |
||||
type: 'category', |
||||
data: showChannel.value, |
||||
axisLabel: { |
||||
margin: 5, |
||||
fontSize: 10, |
||||
interval: 0 |
||||
} |
||||
}) |
||||
set(echart2Option.value, 'series', [ |
||||
{ |
||||
type: 'bar', |
||||
data: [2, 2, 3, 4, 1, 11, 23, 41], |
||||
coordinateSystem: 'polar', |
||||
name: 'C1', |
||||
stack: 'a', |
||||
emphasis: { |
||||
focus: 'series' |
||||
}, |
||||
label: { |
||||
show: true, |
||||
position: 'middle' |
||||
} |
||||
}, |
||||
{ |
||||
type: 'bar', |
||||
data: [6, 6, 7, 8, 12, 14, 6, 28], |
||||
coordinateSystem: 'polar', |
||||
name: 'C2', |
||||
stack: 'a', |
||||
emphasis: { |
||||
focus: 'series' |
||||
}, |
||||
label: { |
||||
show: true, |
||||
position: 'middle' |
||||
} |
||||
}, |
||||
{ |
||||
type: 'bar', |
||||
data: [1, 4, 7, 1, 6, 2, 23, 14], |
||||
coordinateSystem: 'polar', |
||||
name: 'D/E/F', |
||||
stack: 'a', |
||||
emphasis: { |
||||
focus: 'series' |
||||
}, |
||||
label: { |
||||
show: true, |
||||
position: 'middle' |
||||
} |
||||
} |
||||
]) |
||||
set(echart3Option.value, 'series', [ |
||||
{ |
||||
type: 'radar', |
||||
data: [ |
||||
{ |
||||
value: [5.5, 1000, 200, 51, 666, 12345, 1245, 65478], |
||||
name: '平均', |
||||
label: { |
||||
show: true |
||||
} |
||||
}, |
||||
{ |
||||
value: [15, 800, 300, 66, 551, 23456, 2123, 25698], |
||||
name: '当前', |
||||
label: { |
||||
show: true |
||||
} |
||||
} |
||||
] |
||||
} |
||||
]) |
||||
} |
||||
</script> |
||||
|
||||
<style lang="scss" scoped></style> |
Loading…
Reference in new issue