Files
dvcp_v2_webapp/project/sass/apps/Announce/AppAnnounceStatistics/AppAnnounceStatistics.vue

673 lines
20 KiB
Vue
Raw Normal View History

2022-07-13 09:13:31 +08:00
<template>
2022-07-13 16:06:10 +08:00
<ai-list class="AppAnnounceStatistics">
<template slot="content">
<div class="statistics-content">
<ai-title title="宣发日历"></ai-title>
<div class="flex-content">
<div class="flex-left">
2022-07-14 17:10:58 +08:00
<div class="date-header">
<p>{{chooseYear}}{{chooseMonth}}</p>
<div>
<el-date-picker size="small"
v-model="searchMonth"
type="month" value-format="yyyy-MM"
placeholder="选择日期" @change="searchMonthChange">
</el-date-picker>
</div>
</div>
<el-calendar v-model="calendarDate">
2022-07-13 16:06:10 +08:00
<template
slot="dateCell"
slot-scope="{date, data}" >
<div class="flex-date">
2022-07-14 17:10:58 +08:00
<span>{{Number(data.day.substring(8, 10))}}</span>
<span class="tips" v-if="data.day.substring(5, 7) == chooseMonth && dateList[Number(data.day.substring(8, 10))] && dateList[Number(data.day.substring(8, 10))].taskList.length">{{dateList[Number(data.day.substring(8, 10))].taskList.length}}</span>
2022-07-13 16:06:10 +08:00
</div>
</template>
</el-calendar>
</div>
<div class="flex-right">
2022-07-14 17:10:58 +08:00
<div class="title">{{chooseMonth}}{{chooseDay}}日宣发内容</div>
2022-07-13 16:06:10 +08:00
<div class="list-content">
<el-timeline>
2022-07-14 17:10:58 +08:00
<el-timeline-item v-for="(item, index) in taskList" :key="index">
2022-07-13 16:06:10 +08:00
<el-card>
<div class="flex-between">
2022-07-14 17:10:58 +08:00
<p class="item-title">{{item.taskTitle}}</p>
<span class="item-time" v-if="item.createTime">{{item.createTime.substring(10, 16)}}</span>
2022-07-13 16:06:10 +08:00
</div>
2022-07-14 17:10:58 +08:00
<div class="item-info item-created">创建人<span class="name">{{item.createUserId}}</span></div>
<div class="item-info">创建部门<span>{{item.createUserDept}}</span></div>
2022-07-13 16:06:10 +08:00
<div class="flex-between">
2022-07-14 17:10:58 +08:00
<div class="item-info">群发类型<span>{{$dict.getLabel('mstSendType', item.sendType)}}</span></div>
2022-07-13 16:06:10 +08:00
<span class="item-btn">详情</span>
</div>
</el-card>
</el-timeline-item>
</el-timeline>
2022-07-14 17:10:58 +08:00
<ai-empty v-if="!taskList.length" />
2022-07-13 16:06:10 +08:00
</div>
</div>
</div>
</div>
<div class="statistics-content">
<div class="flex-between mar-b16">
<ai-title title="宣发效果"></ai-title>
<div class="right-search">
2022-07-14 17:10:58 +08:00
<div class="time-select" :class="effectType == index ? 'active' : ''" v-for="(item, index) in dateTypeList" :key="index" @click="changeEffectType(index)">{{item}}</div>
2022-07-19 15:24:23 +08:00
<ai-picker :instance="instance" v-model="deptList" style="display:inlie=block;">
<template>
<!-- <ai-select size="medium" clearable placeholder="宣发部门"/> -->
</template>
</ai-picker>
2022-07-13 16:06:10 +08:00
</div>
</div>
<div class="line-content">
<div class="flex1">
<div class="header">
<p>累计创建宣发任务数</p>
2022-07-14 17:10:58 +08:00
<h2>{{effectData.createCount}}</h2>
2022-07-13 16:06:10 +08:00
</div>
<div class="chart-content">
<div class="chart-title">宣发任务数</div>
2022-07-14 17:10:58 +08:00
<div class="chart-box" id="createChart"></div>
2022-07-13 16:06:10 +08:00
</div>
</div>
<div class="flex1">
<div class="header">
<p>累计执行宣发次数</p>
2022-07-14 17:10:58 +08:00
<h2>{{effectData.executeCount}}</h2>
2022-07-13 16:06:10 +08:00
</div>
<div class="chart-content">
<div class="chart-title">宣发次数</div>
2022-07-14 17:10:58 +08:00
<div class="chart-box" id="executeChart"></div>
2022-07-13 16:06:10 +08:00
</div>
</div>
<div class="flex1 mar-r0">
<div class="header">
<p>累计触达人次</p>
2022-07-14 17:10:58 +08:00
<h2>{{effectData.receiveCount}}</h2>
2022-07-13 16:06:10 +08:00
</div>
<div class="chart-content">
<div class="chart-title">触达人次</div>
2022-07-14 17:10:58 +08:00
<div class="chart-box" id="receiveChart"></div>
2022-07-13 16:06:10 +08:00
</div>
</div>
</div>
</div>
<div class="statistics-content">
<div class="flex-between mar-b16">
<ai-title title="宣发明细"></ai-title>
<div class="right-search">
2022-07-14 17:10:58 +08:00
<div class="time-select" :class="departType == index ? 'active' : ''" v-for="(item, index) in dateTypeList" :key="index" @click="changeDepartType(index)">{{item}}</div>
2022-07-13 16:06:10 +08:00
</div>
</div>
2022-07-14 17:10:58 +08:00
<div id="departBarChart"></div>
2022-07-13 16:06:10 +08:00
</div>
2022-07-19 09:43:11 +08:00
<ai-dialog :visible.sync="dialogDate" title="选择时间" width="500px" customFooter :show-close="false">
<el-date-picker v-model="timeList" size="small" type="daterange" value-format="yyyy-MM-dd"
range-separator="至" start-placeholder="开始日期" end-placeholder="结束日期">
</el-date-picker>
<el-button slot="footer" @click="selectDete" type="primary">确认</el-button>
</ai-dialog>
2022-07-13 16:06:10 +08:00
</template>
</ai-list>
2022-07-13 09:13:31 +08:00
</template>
<script>
2022-07-14 17:10:58 +08:00
import * as echarts from "echarts";
2022-07-13 09:13:31 +08:00
export default {
name: 'AppAnnounceStatistics',
label: '协同宣发统计',
2022-07-13 16:06:10 +08:00
props: {
instance: Function,
dict: Object,
permissions: Function
},
2022-07-13 09:13:31 +08:00
data () {
return {
2022-07-14 17:10:58 +08:00
calendarDate: new Date(),
dateList: {},
chooseYear: '',
chooseMonth: '',
chooseDay: '',
searchMonth: '',
taskList: [],
effectType: 0, // 宣发效果类型 0近七天、1近30天、2近一年、3自定义
effectData: {},
createChart: null,
executeChart: null,
receiveChart: null,
departType: 0, // 宣发明细类型 0近七天、1近30天、2近一年、3自定义
dateTypeList: ['近7天', '近30天', '近1年', '自定义'],
departData: {},
departBarChart: null,
2022-07-19 09:43:11 +08:00
dialogDate: false,
timeList: '',
2022-07-19 15:24:23 +08:00
deptList: [],
2022-07-14 17:10:58 +08:00
type: '',
2022-07-13 09:13:31 +08:00
}
},
2022-07-13 16:06:10 +08:00
watch: {
2022-07-14 17:10:58 +08:00
calendarDate: function() {
var year = '' , month = '', date = ''
if(this.calendarDate.length == 9) { // 月份选择器触发
year = this.calendarDate.substring(0, 4)
month = this.calendarDate.substring(5, 7)
date = this.calendarDate.substring(8, 10)
}else { // 日历点击
year = this.calendarDate.getFullYear();
month = this.calendarDate.getMonth() + 1;
date = this.calendarDate.getDate()
if (month >= 1 && month <= 9) {
month = "0" + month;
}
if(this.chooseMonth != month) { // 日历点击不同月
this.searchMonth = ''
}
2022-07-13 16:06:10 +08:00
}
2022-07-14 17:10:58 +08:00
this.chooseDay = date
if(this.chooseMonth != month || this.chooseYear != year) { // 不同年/不同月重新请求日历列表
this.getCalendarList(year, month)
} else {
this.getTaskList(date)
2022-07-13 16:06:10 +08:00
}
2022-07-14 17:10:58 +08:00
this.chooseMonth = month
this.chooseYear = year
2022-07-13 16:06:10 +08:00
}
},
created() {
2022-07-15 17:39:36 +08:00
this.$initWxOpenData()
2022-07-14 17:10:58 +08:00
var year = this.calendarDate.getFullYear();
var month = this.calendarDate.getMonth() + 1;
var date = this.calendarDate.getDate()
if (month >= 1 && month <= 9) {
month = "0" + month;
}
this.chooseMonth = month
this.chooseYear = year
this.chooseDay = date
this.getCalendarList(year, month)
this.getEffect()
this.getDepart()
this.dict.load("mstSendType")
2022-07-13 16:06:10 +08:00
},
2022-07-13 09:13:31 +08:00
methods: {
2022-07-19 09:43:11 +08:00
selectDete() {
console.log(this.timeList)
if(!this.timeList || !this.timeList.length) {
return this.$message.error('请选择自定义时间');
}
if(this.effectType == 3) { //宣发效果
this.getEffect()
}
if(this.departType == 3) { //宣发明细
this.getDepart()
}
this.dialogDate = false
},
2022-07-14 17:10:58 +08:00
searchMonthChange() {
this.calendarDate = this.searchMonth + '-1'
},
getCalendarList(year, month){
this.instance.post(`/app/appmasssendingtask/statisticsCalendar?yyyyMM=${year}${month}`).then(res => {
if (res.code == 0) {
this.dateList = res.data
this.getTaskList(this.chooseDay)
}
})
},
getTaskList(day) {
this.taskList = this.dateList[day].taskList
},
changeEffectType(type) {
this.effectType = type
2022-07-19 09:43:11 +08:00
if(type == 3) {
this.dialogDate = true
this.timeList = []
}else {
this.getEffect()
}
2022-07-14 17:10:58 +08:00
},
getEffect() {
2022-07-19 09:43:11 +08:00
var startTime = this.timeList[0] || '' , endTime = this.timeList[1] || ''
this.instance.post(`/app/appmasssendingtask/statisticsEffect?type=${this.effectType}&startTime=${startTime}&endTime=${endTime}`).then(res => {
2022-07-14 17:10:58 +08:00
if (res.code == 0) {
this.effectData = res.data
var xData = [], createData = [], executeData = [], receiveData = []
res.data.trend.map(e => {
xData.push(e.ymd)
createData.push(e.createCount)
executeData.push(e.executeCount)
receiveData.push(e.receiveCount)
})
this.setLineChart(xData, createData, 'createChart', ['#2891FF'])
this.setLineChart(xData, executeData, 'executeChart', ['#FFB865'])
this.setLineChart(xData, receiveData, 'receiveChart', ['#26D52B'])
}
})
},
setLineChart(xData, yData, id, colorList) {
this[id] = echarts.init(document.querySelector(`#${id}`))
var option = {
xAxis: {
type: 'category',
data: xData
},
yAxis: {
type: 'value'
},
grid: {
left: '10px',
right: '28px',
bottom: '14px',
top: '30px',
containLabel: true
},
2022-07-15 17:39:36 +08:00
tooltip: {
trigger: 'axis'
},
legend: {
type: "plain"
},
2022-07-14 17:10:58 +08:00
color: colorList,
series: [
{
data: yData,
type: 'line'
}
]
}
this[id].setOption(option)
},
changeDepartType(type) {
this.departType = type
2022-07-19 09:43:11 +08:00
if(type == 3) {
this.dialogDate = true
this.timeList = []
}else {
this.getDepart()
}
2022-07-14 17:10:58 +08:00
},
2022-07-19 09:43:11 +08:00
getDepart() {
var startTime = this.timeList[0] || '' , endTime = this.timeList[1] || ''
this.instance.post(`/app/appmasssendingtask/statisticsDepart?type=${this.departType}&startTime=${startTime}&endTime=${endTime}`).then(res => {
2022-07-14 17:10:58 +08:00
if (res.code == 0) {
// this.dateList = res.data
// this.getTaskList(this.chooseDay)
2022-07-15 17:39:36 +08:00
this.setBarChart()
2022-07-14 17:10:58 +08:00
}
})
2022-07-15 17:39:36 +08:00
// var items = [{type: 'departmentName', id: '10', corpid: 'ww596787bb70f08288'}]
// WWOpenData.prefetch({ items }, (err, data) => {
// if (err) {
// console.log(err)
// }
// console.log(data)
// })
2022-07-14 17:10:58 +08:00
},
setBarChart() {
2022-07-15 17:39:36 +08:00
this.departBarChart = echarts.init(document.querySelector(`#departBarChart`))
2022-07-14 17:10:58 +08:00
var option = {
2022-07-15 17:39:36 +08:00
color: ['#2891FF'],
grid: {
top: '10%',
left: '2%',
right: '2%',
bottom: 90,
containLabel: true
},
2022-07-19 09:43:11 +08:00
// toolbox: {
// feature: {
// dataZoom: {
// yAxisIndex: false
// },
// saveAsImage: {
// pixelRatio: 2
// }
// }
// },
2022-07-15 17:39:36 +08:00
tooltip: {
trigger: 'axis',
axisPointer: {
type: 'shadow'
}
},
dataZoom: [
{
type: 'inside'
},
{
type: 'slider'
}
],
2022-07-14 17:10:58 +08:00
xAxis: {
2022-07-15 17:39:36 +08:00
data: ['Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat', 'Sun'],
silent: false,
splitLine: {
show: false
},
splitArea: {
show: false
}
2022-07-14 17:10:58 +08:00
},
yAxis: {
2022-07-15 17:39:36 +08:00
splitArea: {
show: false
}
2022-07-14 17:10:58 +08:00
},
series: [
{
2022-07-15 17:39:36 +08:00
type: 'bar',
data:[120, 200, 150, 80, 70, 110, 130],
barWidth: 20,
barGap: '250%',
large: true
2022-07-14 17:10:58 +08:00
}
]
};
2022-07-15 17:39:36 +08:00
// {
// tooltip: {
// trigger: 'axis',
// axisPointer: {
// type: 'shadow'
// }
// },
// grid: {
// top: '10%',
// left: '2%',
// right: '2%',
// bottom: '2%',
// containLabel: true
// },
// color: ['#2891FF'],
// xAxis: {
// type: 'category',
// data: ['Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat', 'Sun']
// },
// yAxis: {
// type: 'value'
// },
// series: [
// {
// data: [120, 200, 150, 80, 70, 110, 130],
// type: 'bar',
// barWidth: 20,
// barGap: '250%',
// }
// ]
// };
this.departBarChart.setOption(option)
2022-07-13 16:06:10 +08:00
}
2022-07-14 17:10:58 +08:00
2022-07-13 09:13:31 +08:00
}
}
</script>
<style lang="scss" scoped>
.AppAnnounceStatistics {
height: 100%;
2022-07-13 16:06:10 +08:00
.flex-between{
display: flex;
justify-content: space-between;
}
.mar-b16{
margin-bottom: 16px;
}
.mar-r0{
margin-right: 0!important;
}
.statistics-content{
padding: 0 24px 24px;
background-color: #fff;
box-shadow: 0px 4px 6px -2px rgba(15,15,21,0.1500);
border-radius: 4px;
margin-bottom: 20px;
.flex-content{
width: 100%;
display: flex;
margin-top: 16px;
.flex-left{
width: 50%;
2022-07-14 17:10:58 +08:00
.date-header{
padding: 12px 16px;
border: 1px solid #eee;
display: flex;
justify-content: space-between;
p{
line-height: 32px;
}
}
2022-07-13 16:06:10 +08:00
.flex-date{
display: flex;
justify-content: space-between;
}
.tips{
display: inline-block;
padding: 0 4px;
height: 16px;
line-height: 16px;
border-radius: 8px;
background: #2891FF;
font-size: 12px;
font-family: ArialMT;
color: #FFF;
margin-top: 8px;
}
}
.flex-right{
width: 50%;
margin-left: 16px;
border: 1px solid #eee;
.title{
line-height: 56px;
border-bottom: 1px solid #EEE;
padding-left: 16px;
font-size: 16px;
font-family: MicrosoftYaHeiSemibold;
color: #333;
}
.list-content{
padding: 16px;
height: 339px;
box-sizing: border-box;
overflow-y: scroll;
background-color: #F9F9F9;
.item-title{
width: calc(100% - 100px);
word-break: break-all;
margin-bottom: 8px;
font-size: 16px;
font-family: MicrosoftYaHeiSemibold;
color: #222;
line-height: 24px;
}
.item-time{
width: 100px;
text-align: right;
font-size: 16px;
font-family: ArialMT;
color: #888;
line-height: 24px;
}
.item-info{
display: inline-block;
font-size: 14px;
font-family: MicrosoftYaHei;
color: #888;
line-height: 22px;
span{
color: #222;
}
}
.item-created{
width: 152px;
margin-bottom: 4px;
}
.item-btn{
color: #26f;
cursor: pointer;
}
}
}
}
.right-search{
margin-top: 10px;
div{
display: inline-block;
}
.time-select{
font-size: 14px;
font-family: MicrosoftYaHei;
color: #222;
line-height: 22px;
padding: 6px 12px;
border-radius: 2px;
border: 1px solid #D0D4DC;
margin-right: 8px;
box-sizing: border-box;
2022-07-19 09:43:11 +08:00
cursor: pointer;
2022-07-13 16:06:10 +08:00
}
.active{
border: 1px solid #26f;
color: #26f;
}
}
.line-content{
display: flex;
.flex1{
flex: 1;
margin-right: 16px;
.header{
padding: 16px;
width: 100%;
height: 90px;
background: #F9F9F9;
border-radius: 2px;
box-sizing: border-box;
margin-bottom: 16px;
p{
font-size: 14px;
font-family: MicrosoftYaHeiSemibold;
color: #222;
line-height: 22px;
margin-bottom: 4px;
}
h2{
font-size: 24px;
font-family: DINAlternate-Bold, DINAlternate;
font-weight: bold;
color: #26F;
line-height: 32px;
}
}
.chart-content{
width: 100%;
padding: 16px;
background: #F9F9F9;
border-radius: 2px;
box-sizing: border-box;
.chart-title{
font-size: 16px;
font-family: MicrosoftYaHeiSemibold;
color: #333;
line-height: 24px;
}
2022-07-14 17:10:58 +08:00
.chart-box{
width: 100%;
height: 280px;
}
2022-07-13 16:06:10 +08:00
}
}
}
2022-07-14 17:10:58 +08:00
#departBarChart{
width: 100%;
height: 300px;
}
2022-07-13 16:06:10 +08:00
}
::v-deep .el-calendar-table:not(.is-range) td.next,
::v-deep .el-calendar-table:not(.is-range) td.prev {
color: #ccc;
}
::v-deep .el-calendar-table .el-calendar-day{
height: 48px;
line-height: 32px;
padding-left: 12px;
font-size: 14px;
font-family: ArialMT;
}
.el-calendar-table:not(.is-range) td .current{
color: #888;
}
::v-deep .el-calendar__header{
2022-07-14 17:10:58 +08:00
display: none;
2022-07-13 16:06:10 +08:00
}
::v-deep .el-calendar__body{
padding: 0;
}
::v-deep .el-calendar-table thead th:nth-of-type(1){
border-left: 1px solid #eee;
}
::v-deep .el-calendar-table thead th:nth-of-type(7){
border-right: 1px solid #eee;
}
::v-deep .el-calendar-table tr td:first-child {
border-left: 1px solid #eee;
}
::v-deep .el-calendar-table tr:first-child td {
border-top: 1px solid #eee;
}
::v-deep .el-calendar-table td {
border-bottom: 1px solid #eee;
border-right: 1px solid #eee;
}
::v-deep .el-timeline-item__timestamp.is-top{
margin-bottom: 0;
padding-top: 0;
}
::v-deep .el-timeline-item__node{
background-color: #26F;
width: 8px;
height: 8px;
border-radius: 50%;
left: 1px;
}
::v-deep .el-card{
border: none;
}
::v-deep .el-card__body{
padding: 8px;
}
}
::v-deep .ai-list__content {
padding: 0!important;
.ai-list__content--right-wrapper {
background: transparent!important;
box-shadow: none!important;
margin: 0!important;
padding: 0 0 0!important;
}
2022-07-13 09:13:31 +08:00
}
</style>