merchant-web/src/views/modules/datacenter/customer-analysis/index.vue

328 lines
9.3 KiB
Vue
Raw Normal View History

2024-12-03 10:47:55 +00:00
<template>
<div>
<div>
2024-12-17 11:21:19 +00:00
<el-form :inline="true" :model="formInline" class="demo-form-inline">
<el-form-item label="日期类型">
<el-select
style="margin-right: 20px"
v-model="formInline.dateType"
placeholder="请选择"
>
<el-option
v-for="item in [
{ value: '1', label: '日' },
{ value: '2', label: '周' },
{ value: '3', label: '月' },
{ value: '4', label: '年' },
]"
:key="item.value"
:label="item.label"
:value="item.value"
>
</el-option>
</el-select>
</el-form-item>
<el-form-item label="统计类型">
<el-select
style="margin-right: 20px"
v-model="formInline.elementType"
placeholder="请选择统计类型"
>
<el-option
v-for="item in [
{ value: '1', label: '浏览数量' },
{ value: '2', label: '浏览人数' },
{ value: '3', label: '新客数量' },
{ value: '4', label: '支付订单人数' },
]"
:key="item.value"
:label="item.label"
:value="item.value"
>
</el-option>
</el-select>
</el-form-item>
<el-form-item>
<el-button @click="getList" type="primary">查询</el-button>
<el-button @click="batchExport" type="success">导出</el-button>
</el-form-item>
</el-form>
2024-12-03 10:47:55 +00:00
</div>
<div class="stat-list">
<div class="stat-item">
<i style="font-size: 22px" class="el-icon-camera-solid"></i>
<div class="stat-right">
<div class="stat-title">展现量 </div>
<div class="stat-value">
2024-12-06 11:14:50 +00:00
<span style="font-size: 20px">{{
analysis.viewCount ? analysis.viewCount : "0"
}}</span>
2024-12-03 10:47:55 +00:00
<span
2024-12-17 11:21:19 +00:00
v-if="analysis.viewCountRatio < '0%'"
2024-12-06 11:14:50 +00:00
style="font-size: 16px; margin: 0 5px; color: green"
></span
>
<span style="font-size: 16px; margin: 0 5px; color: red" v-else
2024-12-03 10:47:55 +00:00
></span
>
2024-12-17 11:21:19 +00:00
<span style="font-size: 16px">{{ analysis.viewCountRatio }}</span>
2024-12-03 10:47:55 +00:00
</div>
</div>
</div>
<div class="stat-item">
<i style="font-size: 22px" class="el-icon-user-solid"></i>
<div class="stat-right">
<div class="stat-title">浏览人数 </div>
<div class="stat-value">
2024-12-17 11:21:19 +00:00
<span style="font-size: 20px">{{ analysis.peopleCount }}</span>
2024-12-03 10:47:55 +00:00
<span
2024-12-17 11:21:19 +00:00
v-if="analysis.peopleCountRatio < '0%'"
2024-12-03 10:47:55 +00:00
style="font-size: 16px; margin: 0 5px; color: green"
></span
>
2024-12-06 11:14:50 +00:00
<span style="font-size: 16px; margin: 0 5px; color: red" v-else
></span
>
2024-12-17 11:21:19 +00:00
<span style="font-size: 16px">{{ analysis.peopleCountRatio }}</span>
2024-12-03 10:47:55 +00:00
</div>
</div>
</div>
<div class="stat-item">
<i style="font-size: 22px" class="el-icon-user-solid"></i>
<div class="stat-right">
<div class="stat-title">新客数量 </div>
<div class="stat-value">
2024-12-06 11:14:50 +00:00
<span style="font-size: 20px">{{
analysis.newPeopleCount ? analysis.newPeopleCount : "0"
}}</span>
2024-12-03 10:47:55 +00:00
<span
2024-12-17 11:21:19 +00:00
v-if="analysis.newPeopleCountRatio < '0%'"
2024-12-03 10:47:55 +00:00
style="font-size: 16px; margin: 0 5px; color: green"
></span
>
2024-12-06 11:14:50 +00:00
<span style="font-size: 16px; margin: 0 5px; color: red" v-else
></span
>
<span style="font-size: 16px">{{
2024-12-17 11:21:19 +00:00
analysis.newPeopleCountRatio
2024-12-06 11:14:50 +00:00
}}</span>
2024-12-03 10:47:55 +00:00
</div>
</div>
</div>
<div class="stat-item">
<i style="font-size: 22px" class="el-icon-user-solid"></i>
<div class="stat-right">
<div class="stat-title">支付订单人数 </div>
2024-12-06 11:14:50 +00:00
<div style="font-size: 20px" class="stat-value">
2024-12-17 11:21:19 +00:00
{{ analysis.payCount ? analysis.payCount : "0" }}
2024-12-06 11:14:50 +00:00
</div>
2024-12-03 10:47:55 +00:00
</div>
</div>
<div class="stat-item">
<i style="font-size: 22px" class="el-icon-s-order"></i>
<div class="stat-right">
<div class="stat-title">支付订单转化率 %</div>
2024-12-06 11:14:50 +00:00
<div style="font-size: 20px" class="stat-value">
2024-12-17 11:21:19 +00:00
{{ analysis.payConversion ? analysis.payConversion : "0" }}
2024-12-06 11:14:50 +00:00
</div>
2024-12-03 10:47:55 +00:00
</div>
</div>
<div class="stat-item">
<i style="font-size: 22px" class="el-icon-s-order"></i>
<div class="stat-right">
<div class="stat-title">客户复购率 %</div>
2024-12-06 11:14:50 +00:00
<div style="font-size: 20px" class="stat-value">
{{ analysis.repurchaseRate ? analysis.repurchaseRate : "0" }}
</div>
2024-12-03 10:47:55 +00:00
</div>
</div>
</div>
<el-row class="echarts-line">
<div
id="echarts-LineChart"
style="
width: 100%;
height: calc(100vh - 500px);
margin-top: 20px;
border: 1px solid #ccc;
"
/>
</el-row>
</div>
</template>
<script>
2024-12-17 11:21:19 +00:00
import * as XLSX from "xlsx";
import { saveAs } from "file-saver";
2024-12-06 11:14:50 +00:00
import { mapState } from "vuex";
2024-12-03 10:47:55 +00:00
import * as echarts from "echarts";
export default {
data() {
return {
value1: "",
value: "",
2024-12-06 11:14:50 +00:00
formInline: {
2024-12-17 11:21:19 +00:00
dateType: "1",
elementType: "1",
2024-12-06 11:14:50 +00:00
},
analysis: {},
trend: [],
2024-12-03 10:47:55 +00:00
};
},
mounted() {
2024-12-06 11:14:50 +00:00
this.getList();
2024-12-03 10:47:55 +00:00
},
methods: {
2024-12-06 11:14:50 +00:00
getList() {
console.log("1213");
2024-12-17 11:21:19 +00:00
this.$api.dataCenter
.customerAnalysis({ dateType: this.formInline.dateType })
.then((res) => {
this.analysis = res.data.data;
});
2024-12-06 11:14:50 +00:00
this.$api.dataCenter.customerTrend(this.formInline).then((res) => {
2024-12-17 11:21:19 +00:00
this.trend = res.data.data;
this.init(res.data.data);
2024-12-06 11:14:50 +00:00
});
},
2024-12-17 11:21:19 +00:00
init(data) {
2024-12-03 10:47:55 +00:00
this.$nextTick(() => {
// 折线图
const myChat = echarts.init(
document.getElementById("echarts-LineChart")
);
2024-12-17 11:21:19 +00:00
myChat.setOption(this.LineChart(data));
2024-12-03 10:47:55 +00:00
window.addEventListener("resize", () => {
myChat.resize();
});
});
},
2024-12-17 11:21:19 +00:00
LineChart(data) {
2024-12-03 10:47:55 +00:00
return {
title: {
2024-12-17 11:21:19 +00:00
text: "数据趋势分析",
2024-12-03 10:47:55 +00:00
},
tooltip: {
trigger: "axis",
},
legend: {
2024-12-17 11:21:19 +00:00
data: [this.elementTypeName(this.formInline.elementType)],
2024-12-03 10:47:55 +00:00
},
grid: {
left: "3%",
right: "4%",
bottom: "3%",
containLabel: true,
},
toolbox: {
feature: {
saveAsImage: {},
},
},
xAxis: {
type: "category",
boundaryGap: false,
2024-12-17 11:21:19 +00:00
data: data.map((item) => {
return item.countDate;
}),
2024-12-03 10:47:55 +00:00
},
yAxis: {
type: "value",
},
series: [
{
2024-12-17 11:21:19 +00:00
name: this.elementTypeName(this.formInline.elementType),
2024-12-03 10:47:55 +00:00
type: "line",
stack: "Total",
2024-12-17 11:21:19 +00:00
data: data.map((item) => {
return item.value;
}),
2024-12-03 10:47:55 +00:00
},
],
};
},
2024-12-17 11:21:19 +00:00
elementTypeName(row) {
if (row == "1") {
return "浏览数量";
} else if (row == "2") {
return "浏览人数";
} else if (row == "3") {
return "新客数量";
} else if (row == "4") {
return "支付订单人数";
2024-12-06 11:14:50 +00:00
}
2024-12-17 11:21:19 +00:00
},
async batchExport() {
let trendData = this.trend.map((item) => {
return {
日期: item.countDate,
数量: item.value,
};
});
let row = this.analysis;
const analysisData = [
{
展现量: row.viewCount,
浏览人数: row.peopleCount,
新客数量: row.newPeopleCount,
支付订单人数: row.payCount,
支付订单转化率: row.payConversion,
},
];
const workbook = XLSX.utils.book_new();
const worksheet = XLSX.utils.json_to_sheet(analysisData);
const worksheetOne = XLSX.utils.json_to_sheet(trendData);
XLSX.utils.book_append_sheet(workbook, worksheet, "总数据");
XLSX.utils.book_append_sheet(workbook, worksheetOne, "数据趋势");
const excelData = XLSX.write(workbook, {
type: "array",
bookType: "xlsx",
});
const blob = new Blob([excelData], { type: "application/octet-stream" });
saveAs(blob, "客户分析.xlsx");
2024-12-06 11:14:50 +00:00
},
},
computed: {
...mapState("userData", [
"isMerchant",
"marketList",
"storeList",
"marketId",
"shopId",
]),
2024-12-03 10:47:55 +00:00
},
};
</script>
<style lang="scss" scoped>
.stat-list {
display: flex;
align-items: center;
/* justify-content: space-between; */
flex-wrap: wrap;
margin-top: 20px;
padding: 10px;
border: 1px solid #ccc;
}
.stat-item {
width: 25%;
margin: 30px 30px;
display: flex;
align-items: center;
}
.stat-icon {
background: rgb(99 152 252);
width: 60px;
height: 60px;
border-radius: 3px;
}
.stat-right {
margin-left: 12px;
font-size: 18px;
}
.stat-title {
color: #969696;
margin-bottom: 10px;
}
</style>