| | |
| | | <span>会员费收入:<label id="fee1">${data.fee1}</label></span> |
| | | <span>玩湃币充值收入:<label id="fee2">${data.fee2}</label></span> |
| | | <span>课程收入:<label id="fee3">${data.fee3}</label></span> |
| | | <span>活动/赛事收入:<label id="fee4">${data.fee4}</label></span> |
| | | <span>赛事收入:<label id="fee4">${data.fee4}</label></span> |
| | | <span>订场收入:<label id="fee5">${data.fee5}</label></span> |
| | | <span>商品收入:<label id="fee7">${data.fee7}</label></span> |
| | | <span>商品/其他收入:<label id="fee7">${data.fee7}</label></span> |
| | | </br> |
| | | </br> |
| | | </br> |
| | |
| | | <script src="${ctxPath}/modular/system/dataStatistics/echarts.min.js"></script> |
| | | <script src="${ctxPath}/static/js/plugins/switchery/switchery.js"></script> |
| | | <script> |
| | | // 仅格式化前端展示,接口返回的原始数值不作改动。 |
| | | function formatStatisticNumber(value) { |
| | | var number = Number(value); |
| | | return isFinite(number) ? number.toFixed(2) : '0.00'; |
| | | } |
| | | // 首次进入页面时,收入类型来自服务端模板变量;同样按两位小数展示。 |
| | | $(function () { |
| | | $('#fee1, #fee2, #fee3, #fee4, #fee5, #fee7').each(function () { |
| | | $(this).text(formatStatisticNumber($(this).text())); |
| | | }); |
| | | }); |
| | | laydate.render({ |
| | | elem: '#beginTime' |
| | | , trigger: 'click' |
| | |
| | | }); |
| | | function search1() { |
| | | var time = $("#beginTime").val(); |
| | | var ajax9 = new $ax(Feng.ctxPath + "/data/type1", function(data){ |
| | | |
| | | loadIncomeTypePieCharts(time); |
| | | // 营收卡片与收入类型卡片使用同一接口、同一时间范围,避免筛选后口径不一致。 |
| | | var incomeAjax = new $ax(Feng.ctxPath + "/data/getIncomeData", function(resp){ |
| | | $("#totalIncome").text(formatStatisticNumber(resp.incomeStatistics.totalIncomeAmount)); |
| | | $("#netIncomeAmount").text(formatStatisticNumber(resp.incomeStatistics.netIncomeAmount)); |
| | | $("#couponDeductionAmount").text(formatStatisticNumber(resp.incomeStatistics.couponDeductionAmount)); |
| | | $("#refundAmount").text(formatStatisticNumber(resp.incomeStatistics.refundAmount)); |
| | | var incomeTypeNet = resp.incomeTypeNet || {}; |
| | | $("#fee1").text(formatStatisticNumber(incomeTypeNet[1])); |
| | | $("#fee2").text(formatStatisticNumber(incomeTypeNet[2])); |
| | | $("#fee3").text(formatStatisticNumber(incomeTypeNet[3])); |
| | | $("#fee4").text(formatStatisticNumber(incomeTypeNet[4])); |
| | | $("#fee5").text(formatStatisticNumber(incomeTypeNet[5])); |
| | | $("#fee7").text(formatStatisticNumber(incomeTypeNet[6])); |
| | | renderTicketIncomeChart(resp.ticketIncome || {}); |
| | | }); |
| | | ajax9.set("time",time); |
| | | ajax9.start(); |
| | | incomeAjax.set("time", time); |
| | | incomeAjax.start(); |
| | | } |
| | | var ans = []; |
| | | var weekX = ["1周","2周","3周","4周"]; |
| | |
| | | var yearX = []; |
| | | var timeX = []; |
| | | var dataX = []; |
| | | |
| | | function renderTicketIncomeChart(ticketIncome) { |
| | | var chartDom = document.getElementById('cookieTicket'); |
| | | var myChart = echarts.getInstanceByDom(chartDom) || echarts.init(chartDom); |
| | | myChart.setOption({ |
| | | title: {text: '门票收入', left: 'center'}, |
| | | tooltip: {trigger: 'item'}, |
| | | series: [{ |
| | | name: '门票收入', type: 'pie', radius: '50%', |
| | | data: [ |
| | | {value: ticketIncome.day || 0, name: '日卡'}, |
| | | {value: ticketIncome.month || 0, name: '月卡'}, |
| | | {value: ticketIncome.quarter || 0, name: '季卡'}, |
| | | {value: ticketIncome.year || 0, name: '年卡'} |
| | | ] |
| | | }] |
| | | }, true); |
| | | } |
| | | |
| | | function renderIncomeTypePieChart(elementId, title, data) { |
| | | var chartDom = document.getElementById(elementId); |
| | | var chart = echarts.getInstanceByDom(chartDom) || echarts.init(chartDom); |
| | | chart.setOption({ |
| | | title: {text: title, left: 'center'}, |
| | | tooltip: {trigger: 'item'}, |
| | | series: [{name: title, type: 'pie', radius: '50%', data: data || []}] |
| | | }, true); |
| | | } |
| | | |
| | | // 使用接口返回的 JSON 分类数据,避免服务端模板字符串解析遗漏最后一个分类。 |
| | | function loadIncomeTypePieCharts(time) { |
| | | var ajax = new $ax(Feng.ctxPath + "/data/type1", function (data) { |
| | | renderIncomeTypePieChart('cookieCourse', '课程收入', data.courseData); |
| | | renderIncomeTypePieChart('cookieBooking', '订场收入', data.siteData); |
| | | }); |
| | | ajax.set('time', time); |
| | | ajax.start(); |
| | | } |
| | | |
| | | $(function () { |
| | | loadIncomeTypePieCharts(''); |
| | | }); |
| | | // 创建一个日期对象 |
| | | var currentDate = new Date(); |
| | | // 获取当前日期的号数 |
| | |
| | | |
| | | function renderIncomeStatistics(elementId, periodName, statistics) { |
| | | document.getElementById(elementId).innerText = periodName + "统计:总营收金额 " |
| | | + statistics.totalIncomeAmount + ",净收入金额 " + statistics.netIncomeAmount |
| | | + ",优惠券抵扣金额 " + statistics.couponDeductionAmount + ",退款金额 " |
| | | + statistics.refundAmount; |
| | | + formatStatisticNumber(statistics.totalIncomeAmount) + ",净收入金额 " + formatStatisticNumber(statistics.netIncomeAmount) |
| | | + ",优惠券抵扣金额 " + formatStatisticNumber(statistics.couponDeductionAmount) + ",退款金额 " |
| | | + formatStatisticNumber(statistics.refundAmount); |
| | | } |
| | | |
| | | function renderIncomeStatisticsList(elementId, title, labels, statistics) { |
| | | var records = labels.map(function (label, index) { |
| | | var item = statistics[index]; |
| | | return '<div class="income-period-record"><strong>' + label + '</strong>:总营收金额 ' |
| | | + item.totalIncomeAmount + ',净收入金额 ' + item.netIncomeAmount |
| | | + ',优惠券抵扣金额 ' + item.couponDeductionAmount |
| | | + ',退款金额 ' + item.refundAmount + '</div>'; |
| | | + formatStatisticNumber(item.totalIncomeAmount) + ',净收入金额 ' + formatStatisticNumber(item.netIncomeAmount) |
| | | + ',优惠券抵扣金额 ' + formatStatisticNumber(item.couponDeductionAmount) |
| | | + ',退款金额 ' + formatStatisticNumber(item.refundAmount) + '</div>'; |
| | | }).join(''); |
| | | document.getElementById(elementId).innerHTML = '<div class="income-period-title">' + title |
| | | + '</div><div class="income-period-records">' + records + '</div>'; |
| | |
| | | formatter: function (params) { |
| | | var item = params[0]; |
| | | var detail = statistics[item.dataIndex]; |
| | | return labels[item.dataIndex] + '<br/>总营收:' + detail.totalIncomeAmount |
| | | + '<br/>净收入:' + detail.netIncomeAmount |
| | | + '<br/>优惠券抵扣:' + detail.couponDeductionAmount |
| | | + '<br/>退款:' + detail.refundAmount; |
| | | return labels[item.dataIndex] + '<br/>总营收:' + formatStatisticNumber(detail.totalIncomeAmount) |
| | | + '<br/>净收入:' + formatStatisticNumber(detail.netIncomeAmount) |
| | | + '<br/>优惠券抵扣:' + formatStatisticNumber(detail.couponDeductionAmount) |
| | | + '<br/>退款:' + formatStatisticNumber(detail.refundAmount); |
| | | } |
| | | }, |
| | | grid: {left: '5%', right: '4%', bottom: '18%', containLabel: true}, |
| | |
| | | }); |
| | | } |
| | | |
| | | // 退费图与营收图使用同一接口返回的退款流水,保证统计口径一致。 |
| | | function renderRefundChart(chart, resp) { |
| | | var labelsByPeriod = { |
| | | '年度退费': resp.yearLabels, |
| | | '月度退费': resp.monthLabels, |
| | | '周度退费': resp.weekLabels, |
| | | '日度退费': resp.dayLabels |
| | | }; |
| | | var statisticsByPeriod = { |
| | | '年度退费': resp.yearIncomeStatistics, |
| | | '月度退费': resp.monthIncomeStatistics, |
| | | '周度退费': resp.weekIncomeStatistics, |
| | | '日度退费': resp.dayIncomeStatistics |
| | | }; |
| | | chart.off('legendselectchanged'); |
| | | chart.setOption({ |
| | | tooltip: {trigger: 'axis'}, |
| | | legend: { |
| | | data: ['年度退费', '月度退费', '周度退费', '日度退费'], |
| | | icon: 'stack', |
| | | selectedMode: 'single', |
| | | selected: {'年度退费': true, '月度退费': false, '周度退费': false, '日度退费': false} |
| | | }, |
| | | grid: {left: '3%', right: '4%', bottom: '12%', containLabel: true}, |
| | | toolbox: {feature: {saveAsImage: {}}}, |
| | | xAxis: {type: 'category', boundaryGap: false, data: labelsByPeriod['年度退费'], axisLabel: {rotate: 35, interval: 0}}, |
| | | yAxis: {type: 'value'}, |
| | | series: Object.keys(statisticsByPeriod).map(function (period) { |
| | | return { |
| | | name: period, |
| | | type: 'line', |
| | | data: statisticsByPeriod[period].map(function (item) { return item.refundAmount; }) |
| | | }; |
| | | }) |
| | | }, true); |
| | | chart.on('legendselectchanged', function (event) { |
| | | var labels = labelsByPeriod[event.name]; |
| | | chart.setOption({xAxis: {data: labels, axisLabel: {rotate: labels.length > 7 ? 35 : 0, interval: 0}}}); |
| | | }); |
| | | } |
| | | |
| | | $(function(){ |
| | | getContent(1); |
| | | getContent1(1); |
| | |
| | | ptCourse(); |
| | | |
| | | |
| | | var myChart1 = echarts.init(document.getElementById('refund')); |
| | | var ajax = new $ax(Feng.ctxPath + "/data/getIncomeData", function(resp){ |
| | | // 运营、教学等其他图表仍复用年度横轴。 |
| | | yearX = resp.year; |
| | |
| | | var netIncomeAmount = document.getElementById("netIncomeAmount"); |
| | | var couponDeductionAmount = document.getElementById("couponDeductionAmount"); |
| | | var refundAmount = document.getElementById("refundAmount"); |
| | | t1.innerText = list[0] || 0; |
| | | netIncomeAmount.innerText = resp.incomeStatistics.netIncomeAmount || 0; |
| | | couponDeductionAmount.innerText = resp.incomeStatistics.couponDeductionAmount || 0; |
| | | refundAmount.innerText = resp.incomeStatistics.refundAmount || 0; |
| | | t1.innerText = formatStatisticNumber(list[0]); |
| | | netIncomeAmount.innerText = formatStatisticNumber(resp.incomeStatistics.netIncomeAmount); |
| | | couponDeductionAmount.innerText = formatStatisticNumber(resp.incomeStatistics.couponDeductionAmount); |
| | | refundAmount.innerText = formatStatisticNumber(resp.incomeStatistics.refundAmount); |
| | | renderIncomeStatisticsList("yearIncomeStatistics", "历年营收明细", resp.yearLabels, resp.yearIncomeStatistics); |
| | | renderIncomeStatisticsList("monthIncomeStatistics", "本年各月营收明细", resp.monthLabels, resp.monthIncomeStatistics); |
| | | renderIncomeStatisticsList("weekIncomeStatistics", "近四周营收明细", resp.weekLabels, resp.weekIncomeStatistics); |
| | |
| | | renderIncomeTrendChart("incomeMonthChart", "本年各月营收趋势", resp.monthLabels, resp.monthIncomeStatistics); |
| | | renderIncomeTrendChart("incomeWeekChart", "近四周营收趋势", resp.weekLabels, resp.weekIncomeStatistics); |
| | | renderIncomeTrendChart("incomeDayChart", "近七日营收趋势", resp.dayLabels, resp.dayIncomeStatistics); |
| | | $("#back1").text(formatStatisticNumber(resp.yearIncomeStatistics[resp.yearIncomeStatistics.length - 1].refundAmount)); |
| | | $("#back2").text(formatStatisticNumber(resp.monthIncomeStatistics[new Date().getMonth()].refundAmount)); |
| | | $("#back3").text(formatStatisticNumber(resp.weekIncomeStatistics[resp.weekIncomeStatistics.length - 1].refundAmount)); |
| | | $("#back4").text(formatStatisticNumber(resp.dayIncomeStatistics[resp.dayIncomeStatistics.length - 1].refundAmount)); |
| | | renderRefundChart(myChart1, resp); |
| | | }); |
| | | ajax.set("type",1); |
| | | ajax.start(); |
| | | |
| | | var myChart1 = echarts.init(document.getElementById('refund')); |
| | | |
| | | var myChart7 = echarts.init(document.getElementById('courseData')); |
| | | var ajax3 = new $ax(Feng.ctxPath + "/data/backPt", function(data){ |
| | | $("#back1").text(data.thisYear); |
| | | $("#back2").text(data.thisMonth); |
| | | $("#back3").text(data.thisWeek); |
| | | $("#back4").text(data.thisDay); |
| | | optionBack = { |
| | | |
| | | tooltip: { |
| | | trigger: 'axis' |
| | | }, |
| | | legend: { |
| | | |
| | | data: ['年度退费', '月度退费','周度退费','日度退费'], |
| | | icon: 'stack', |
| | | selectedMode: 'single', // 单选 |
| | | selected: { |
| | | 年度会员数: true, |
| | | 月度会员数: false, |
| | | 周度会员数: false, |
| | | 日度会员数: false |
| | | } |
| | | }, |
| | | grid: { |
| | | left: '3%', |
| | | right: '4%', |
| | | bottom: '3%', |
| | | containLabel: true |
| | | }, |
| | | toolbox: { |
| | | feature: { |
| | | saveAsImage: {} |
| | | } |
| | | }, |
| | | xAxis: { |
| | | type: 'category', |
| | | boundaryGap: false, |
| | | data: yearX |
| | | }, |
| | | yAxis: { |
| | | type: 'value' |
| | | }, |
| | | series: [ |
| | | { |
| | | name: '年度退费', |
| | | type: 'line', |
| | | stack: 'Total', |
| | | data: data.yearData |
| | | }, |
| | | { |
| | | name: '月度退费', |
| | | type: 'line', |
| | | stack: 'Total', |
| | | data: data.monthData |
| | | }, |
| | | { |
| | | name: '周度退费', |
| | | type: 'line', |
| | | stack: 'Total', |
| | | data: data.weekData |
| | | }, |
| | | { |
| | | name: '日度退费', |
| | | type: 'line', |
| | | stack: 'Total', |
| | | data: data.dayData |
| | | } |
| | | ] |
| | | |
| | | }; |
| | | }); |
| | | ajax3.start(); |
| | | |
| | | |
| | | |
| | | var ajax4 = new $ax(Feng.ctxPath + "/data/userAndVipPt", function(data){ |
| | | option1 = { |
| | | |
| | |
| | | }; |
| | | }); |
| | | ajax4.start(); |
| | | |
| | | myChart1.on('legendselectchanged', obj => { |
| | | var options = myChart1.getOption() |
| | | //这里是选择切换什么样的x轴,那么他会进行对Y值的切换 |
| | | if (obj.name == '年度退费') { |
| | | options.xAxis[0].data = yearX |
| | | } else if (obj.name == '月度退费') { |
| | | options.xAxis[0].data = monthX |
| | | } else if (obj.name == '周度退费') { |
| | | options.xAxis[0].data = ["1周","2周","3周","4周"] |
| | | } else if (obj.name == '日度退费') { |
| | | options.xAxis[0].data = dataX |
| | | } |
| | | myChart1.setOption(options, true) |
| | | }) |
| | | |
| | | |
| | | // 使用刚指定的配置项和数据显示图表。 |
| | | myChart1.setOption(optionBack); |
| | | |
| | | myChart7.setOption(option7); |
| | | }); |