Commit 5eb4ab13 authored by 潘自豪's avatar 潘自豪

Merge remote-tracking branch 'origin/ld_databoard_fix' into ld_databoard_fix

parents 4594dc67 f1529c01
......@@ -101,6 +101,9 @@ export const getAllTypeBusinessConditionDetailByYear = (cur_day) => fetch('/api/
export const transportTypeOrderFinishPie = (date) => fetch("/api/query/dash_board/action/get_order_finish_data_by_transport_type_day", {aux: {"cur_day": date}}, "POST")
export const customerOrderFinishPie = (date) => fetch("/api/query/dash_board/action/get_order_finish_data_by_customer_day", {aux: {"cur_day": date}}, "POST")
export const getOrderFinishDataByCondition = (aux) => fetch("/api/query/*/action/get_order_finish_data_by_condition", {aux: aux}, "POST")
export const getOrderWeightAndProportionList = (aux) => fetch("/api/query/dash_board/action/get_order_weight_and_proportion_list", {aux: aux}, "POST")
//流失客户 & 新增客户
export const getOrderLoseAddCustomer = (cur_day) => fetch('/api/query/*/action/get_order_loss_add_customer', {
aux: {
......
......@@ -7,7 +7,7 @@
<td class="winner_span" :style="columnsStyle['title']">{{ row.title }}</td>
<td v-for="(col, idz) in row.column" :key="idz" :style="columnsStyle[col.key]">
<p class="key_span">{{ col.key }}</p>
<p class="value_span" :style="col.valStyle">{{ col.value }}</p>
<p class="value_span" :style="col.valStyle">{{colFormatter[''+idz]?colFormatter[''+idz](col.value):col.value }}</p>
</td>
</tr>
</tbody>
......@@ -38,6 +38,12 @@ export default {
{title: '标题列', column: [{key: '字段', value: '0'}]}
];
}
},
colFormatter:{
type: Object,
default: function(){
return {};
}
}
},
data() {
......@@ -52,6 +58,8 @@ export default {
}
.winner_list::-webkit-scrollbar { width: 0 !important }
table {
height: 100%;
font-size: 12px;
......
......@@ -176,7 +176,7 @@ export default {
type: 'line',
color: 'red',
lineStyle:{
width: 6,
width: 3,
},
label: {
show: true,
......@@ -189,13 +189,13 @@ export default {
}
},
formatter:{
type: Function
type: [Function,String]
},
barFormatter:{
type: Function
type: [Function,String]
},
lineFormatter:{
type: Function
type: [Function,String]
}
},
};
......
<template>
<table>
<thead v-if="showHead">
<tr><th :style="eval('title',title)">{{title}}&nbsp;</th></tr>
<tr><th :style="eval('title',title)">{{titleFormatter?titleFormatter(title):title}}&nbsp;</th></tr>
</thead>
<tbody>
<tr v-for="row in data"><td :style="eval('cell',(row[name]?row[name]:''))">{{row[name]?row[name]:''}}</td></tr>
<tr v-for="row in data"><td :style="eval('cell',(row[name]?row[name]:''))">{{valueFormatter?valueFormatter(row[name]?row[name]:''):row[name]?row[name]:''}}</td></tr>
</tbody>
</table>
</template>
......@@ -65,6 +65,12 @@ export default {
titleStyleFunction:{
type: Function
},
titleFormatter:{
type: Function
},
valueFormatter:{
type: Function
}
}
}
......
import { getOrderWeightAndProportionList} from '../../../api/apiList';
import {calc_hb_str, calc_zb_str, conver_amont} from "../../../utils/numUtil";
let choice = {
"01": "transport_type",
"02": "area_name",
"03": "base_name",
"04": "department",
}
export const getDetailData = async (aux,callback) => {
let resList = new Array();
aux[choice[aux.type]] = aux.key;
await getOrderWeightAndProportionList(aux).then(function (res) {
resList = res.data;
});
callback(resList);
return resList
}
import { getOrderFinishDataByCondition} from '../../../api/apiList';
import {calc_hb_str, calc_zb_str, conver_amont} from "../../../utils/numUtil";
let choice = {
day: '昨日',
month: "上月",
year: "去年",
}
export const getHeadData = async (aux,callback) => {
let resList = new Array();
await getOrderFinishDataByCondition(aux).then(function (res) {
resList = dataFormatter(aux,res.data);
});
callback(resList);
return resList
}
function dataFormatter(aux,data){
let res = new Array();
if (aux.group_type === '01'){
formatType01Data(aux,res, data);
}else {
formatNotType01Data(aux,res, data);
}
return res;
}
function formatNotType01Data(aux,res, data){
let sum = {
title: "当日",
data: [
{
title: '订单量',
today: 0,
yesterday: 0,
},
{
title: '营业额',
today: 0,
yesterday: 0,
},
{
title: '成本',
today: 0,
yesterday: 0,
},
{
title: '毛利',
today: 0,
yesterday: 0,
},
]
};
res.push(sum);
for (let key in data) {
let item = {
title: data[key].name?data[key].name:"空",
key: key,
data: [
{
title: "订单量",
today: data[key].cur_unit_weight,
yesterday: data[key].pre_unit_weight
},
{
title: "营业额",
today: data[key].cur_sell_settle_amount,
yesterday: data[key].pre_sell_settle_amount
},
{
title: "成本",
today: data[key].cur_buy_settle_amount,
yesterday: data[key].pre_buy_settle_amount
},
{
title: "毛利",
today: data[key].cur_gross_profit_amount,
yesterday: data[key].pre_gross_profit_amount
},
]
};
for (let i = 0; i < sum.data.length; i++) {
sum.data[i].today += item.data[i].today;
sum.data[i].yesterday += item.data[i].yesterday;
}
res.push(item);
}
}
//转换领域细分数据
function formatType01Data(aux,res, data) {
let sum = {
title: "当日订单量(不含仓库)",
amount: 0,
hb: [
{
title: choice[aux.time_type],
amount: 0,
rate: "0.00%"
}
]
};
res.push(sum);
for (let key in data) {
let item = {
title: data[key].name?data[key].name:"空",
amount: data[key].cur_unit_weight,
key: key,
hb: [
{
title: choice[aux.time_type],
amount: conver_amont(data[key].pre_unit_weight),
rate: calc_hb_str(data[key].cur_unit_weight, data[key].pre_unit_weight)
}
]
};
sum.amount += data[key].cur_unit_weight;
sum.hb[0].amount += data[key].pre_unit_weight;
res.push(item);
}
calcProportion(res);
sum.amount = conver_amont(sum.amount);
sum.hb[0].amount = conver_amont(sum.hb[0].amount);
}
function calcProportion(list) {
let sum = list[0];
for (let i = 1; i < list.length; i++) {
list[i].hb.push({
title: "占比",
amount: calc_zb_str(list[i].amount,sum.amount)
})
list[i].amount = conver_amont(list[i].amount);
}
}
{
"domain":{
"01":{
"day": {
"head": [
{
......@@ -1021,7 +1021,7 @@
}
}
},
"area":{
"02":{
"day": {
"head": [
{
......@@ -2205,7 +2205,7 @@
}
}
},
"base": {
"03": {
"day": {
"head": [
{
......@@ -3857,7 +3857,7 @@
}
}
},
"business": {
"04": {
"day": {
"head": [
{
......
<template>
<div class="turnover-detail">
<div class="order-proportion">
<div class="menu">
<input type="button" :class="{'selectedBtn': currentBtn.subdivide === 'domain'}" value="领域细分" @click="clickBtn('subdivide','domain')">
<input type="button" :class="{'selectedBtn': currentBtn.subdivide === 'area'}" value="区域细分" @click="clickBtn('subdivide','area')">
<input type="button" :class="{'selectedBtn': currentBtn.subdivide === 'base'}" value="基地细分" @click="clickBtn('subdivide','base')">
<input type="button" :class="{'selectedBtn': currentBtn.subdivide === 'business'}" value="事业部细分" @click="clickBtn('subdivide','business')">
<input type="button" :class="{'selectedBtn': currentBtn.subdivide === '01'}" value="领域细分" @click="clickBtn('subdivide','01')">
<input type="button" :class="{'selectedBtn': currentBtn.subdivide === '02'}" value="区域细分" @click="clickBtn('subdivide','02')">
<input type="button" :class="{'selectedBtn': currentBtn.subdivide === '03'}" value="基地细分" @click="clickBtn('subdivide','03')">
<input type="button" :class="{'selectedBtn': currentBtn.subdivide === '04'}" value="事业部细分" @click="clickBtn('subdivide','04')">
</div>
<div class="menu">
<input type="button" :class="{'selectedBtn': currentBtn.date === 'day'}" value="日统计" @click="clickBtn('date','day')">
<input type="button" :class="{'selectedBtn': currentBtn.date === 'month'}" value="月统计" @click="clickBtn('date','month')">
<input type="button" :class="{'selectedBtn': currentBtn.date === 'year'}" value="年统计" @click="clickBtn('date','year')">
</div>
<div class="card-board" v-if="currentBtn.subdivide === 'domain'">
<contrast-card v-for="data in currentData.head" style="height: 100%;width: 18%;" :class="{'selectCard': currentCard === data.title}" @click.native="selectCard(data)">
<title-content-mark style="color: #369afa;float: left;width: 40%;font-size: 18px" :title-style="{'font-weight': 'bold'}" :title="data.title" :content="data.amount" isBold/>
<div class="card-board" v-if="currentBtn.subdivide === '01'">
<contrast-card v-for="data in currentHeadData" style="height: 100%;width: 18%;" :class="{'selectCard': currentCard === data.key}" @click.native="selectCard(data)">
<title-content-mark style="color: #369afa;float: left;width: 40%;font-size: 18px" :title-style="{'font-weight': 'bold'}" :mark-style="{'bottom': '12%'}" :title="data.title" :content="data.amount" mark="万元" isBold/>
<div style="width: 60%; height: 100%; float:left; padding: 2% 2% 0 8%; line-height: 40px; display: flex; align-items: center;font-size: 16px;">
<table-column style="float: left;width: 25%;" :data="data.hb" name="title"/>
<table-column style="float: left;width: 40%;" :data="data.hb" name="amount"/>
<table-column style="float: left;width: 35%;" :data="data.hb" name="rate" cell-style-js="var res = {color: '#5eeef4'}; if(data.indexOf('+') !== -1){res.color = '#fee064'} res;"/>
<table-column style="float: left;width: 35%;" :data="data.hb" name="rate" cell-style-js="var res = {color: 'rgb(255, 51, 0)'}; if(data.indexOf('+') !== -1){res.color = 'rgb(51, 255, 102)'} res;"/>
</div>
</contrast-card>
</div>
<div class="card-board" v-if="currentBtn.subdivide !== 'domain'">
<contrast-card v-for="data in currentData.head" style="height: 100%;width: 18%;" :class="{'selectCard': currentCard === data.title}" @click.native="selectCard(data)" :style="listCardStyle">
<div style="width: 100%; height: 100%; float:left; padding: 2%; line-height: 28px; display: flex; align-items: center; font-size: 14px;">
<table-column style="float: left;width: 35%;" :data="data.data" name="title" :title="data.title" show-head :title-style="{'font-size': '18px','padding-left':'7%','white-space': 'nowrap'}"/>
<table-column style="float: left;width: 45%;font-size: 24px;font-weight: bold;color: #5eeef4;text-align: center;" :data="data.data" name="today" show-head/>
<table-column style="float: left;width: 20%;" :data="data.data" name="yesterday" title="昨日" show-head/>
<div class="card-board" v-if="currentBtn.subdivide !== '01'">
<!-- <contrast-card v-for="data in currentHeadData" style="height: 100%;width: 18%;" :class="{'selectCard': currentCard === data.title}" @click.native="selectCard(data)" :style="listCardStyle">-->
<!-- <div style="width: 100%; height: 100%; float:left; padding: 2%; line-height: 28px; display: flex; align-items: center; font-size: 14px;">-->
<!-- <table-column style="float: left;width: 20%;" :data="data.data" name="title" :title="data.title" :title-formatter="value=> value+'(万元)'" show-head :title-style="{'font-size': '18px','padding-left':'7%','white-space': 'nowrap'}"/>-->
<!-- <table-column style="float: left;width: 60%;font-size: 24px;font-weight: bold;color: #5eeef4;text-align: center;" :data="data.data" name="today" :value-formatter="converAmont" show-head/>-->
<!-- <table-column style="float: left;width: 20%;" :data="data.data" name="yesterday" :value-formatter="converAmont" title="昨日" show-head/>-->
<!-- </div>-->
<!-- </contrast-card>-->
<contrast-card v-for="data in currentHeadData" style="height: 100%;width: 18%;" :class="{'selectCard': currentCard === data.key}" @click.native="selectCard(data)" :style="listCardStyle">
<div style="width: 100%; height: 20%; float:left; padding: 2%; line-height: 28px; display: flex; align-items: center; font-size: 14px;">
<table-column style="float: left;width: 80%;" :data="[]" name="title" :title="data.title" :title-formatter="value=> value+'(万元)'" show-head :title-style="{'font-size': '18px','padding-left':'3%','white-space': 'nowrap',}"/>
<table-column style="float: left;width: 0;font-size: 24px;font-weight: bold;color: #5eeef4;text-align: center;" :data="[]" name="today"/>
<table-column style="float: left;width: 20%;" :data="[]" name="yesterday" :title="dateTimeChoice[currentBtn.date]" show-head/>
</div>
<div style="width: 100%; height: 80%; float:left; padding: 2%;margin-top: 1%; line-height: 28px; display: flex; align-items: center; font-size: 14px;">
<table-column style="float: left;width: 30%;" :data="data.data" name="title" :title-formatter="value=> value+'(万元)'"/>
<table-column style="float: left;width: 50%;font-size: 24px;font-weight: bold;color: #5eeef4;text-align: center;" :data="data.data" name="today" :value-formatter="converAmont"/>
<table-column style="float: left;width: 20%;" :data="data.data" name="yesterday" :value-formatter="converAmont"/>
</div>
</contrast-card>
</div>
<div class="chart">
<display-board class="trade_left" :title="listTitle" title_size="large">
<winners-list style="height: 96%" id="ar_company_list" :rows="currentData[currentCard]?currentData[currentCard].list:[]" :show-icon="false" :columns-style="{'title':{'width':'50%'},'订单量(万吨)':{'width':'30%'}}"/>
<display-board class="trade_left" title="订单量占比" title_size="large">
<winners-list style="height: 96%;overflow: auto;" id="ar_company_list" :rows="currentDetailData" :show-icon="false" :columns-style="{'title':{'width':'50%'},'订单量(万吨)':{'width':'30%'}}" :col-formatter="{'1':(v)=>v+'%'}"/>
</display-board>
<line-bar-chart style="width: 75%;height: 100%;" :data="currentData[currentCard]?currentData[currentCard].detail:[]" x="company" y="value" :title="chartTitle" :formatter="formatter" :line-formatter="lineFormatter"/>
<line-bar-chart style="width: 75%;height: 100%;" :data="currentDetailData" x="company" y="value" :title="chartTitle" :formatter="formatter" :line-formatter="lineFormatter" bar-formatter="{@value}万元"/>
</div>
</div>
</template>
......@@ -44,55 +56,85 @@ import TitleContentMark from "../components/layout/title-content-mark.vue";
import TableColumn from "../components/table/table-column.vue";
import ContrastCard from "../components/card/contrast-card.vue";
import * as echarts from "echarts";
import data from "./mockData/order_proportion.json";
import DisplayBoard from "../components/container/display-board.vue";
import WinnersList from "../components/card/winners-list.vue";
import LineBarChart from "../components/chart/line-bar-chart.vue";
import {getHeadData} from "./js/orderProportionHeadData";
import {conver_amont} from "../../utils/numUtil";
import {getDetailData} from "./js/orderProportionDetailData";
export default {
name:"OrderProportion",
components: {LineBarChart, WinnersList, DisplayBoard, ContrastCard, TableColumn, TitleContentMark},
data() {
return {
currentData: {},
mockData: data,
today: "2022-06-26",
currentHeadData:[],
currentDetailData:[],
chart: null,
currentCard:null,
listTitle: "当日订单量占比",
chartTitle: "当日订单委托单位占比",
listCardStyle:{
width: "18%",
},
currentBtn:{
date: "day",
subdivide: "domain",
subdivide: "01",
},
dateTimeChoice:{
day: '昨日',
month: "上月",
year: "去年",
}
}
},
methods: {
converAmont(value){
return conver_amont(value);
},
back(){
this.$router.push({path: '/'});
},
changeDimension(){
this.currentData = this.mockData[this.currentBtn.subdivide][this.currentBtn.date];
this.currentCard = this.currentData.head[0].title;
changeDimension(type){
this.getHeadData(type);
},
getHeadData(type){
getHeadData({cur_day: this.today,time_type:this.currentBtn.date,group_type:this.currentBtn.subdivide},
(res) => {
this.currentHeadData = res;
if (type !== "date"){
this.currentCard = res[0]?res[0].key:null;
this.chartTitle = res[0]?(res[0].title + '委托单位占比'):null;
}
this.calcCardWidth();
this.getDetailData();
}
);
},
getDetailData(){
getDetailData({cur_day: this.today,date:this.currentBtn.date,type:this.currentBtn.subdivide,key:this.currentCard},
(res) => {
this.currentDetailData = res;
}
);
},
clickBtn(type,dimension){
this.currentBtn[type] = dimension;
this.changeDimension();
this.changeDimension(type);
},
selectCard(data){
this.currentCard = data.title;
this.currentCard = data.key;
this.chartTitle = data.title + '委托单位占比';
this.getDetailData();
},
formatter(param){
return "订单量:<br>" + param[0].marker + param[0].name + ":\t" + param[0].data.value + "<br> " + param[1].marker + "占比:" + param[1].data.proportion + "%";
return "订单量:<br>" + param[0].marker + param[0].name + ":\t" + param[0].data.value + "万元<br> " + param[1].marker + "占比:" + param[1].data.proportion + "%";
},
lineFormatter(param){
return param.data.proportion + '%';
},
calcCardWidth(){
this.listCardStyle.width = "calc((100% - 4rem) / " + this.currentData.head.length + ")";
this.listCardStyle.width = "calc((100% - 4rem) / " + this.currentHeadData.length + ")";
}
},
mounted() {
......@@ -106,7 +148,7 @@ export default {
}
</script>
<style scoped>
.turnover-detail{
.order-proportion{
width: 100%;
height: 100%;
}
......
......@@ -256,7 +256,6 @@ export default {
}
},
selectLegend(title) {
console.log(title)
let name;
this.chart.dispatchAction({
type: 'legendAllSelect'
......@@ -295,7 +294,6 @@ export default {
default:
break;
}
console.log(name)
if (name) {
this.chart.dispatchAction({
type: 'legendInverseSelect'
......
//环比值=(当日营业额-昨日营业额)/昨日营业额*100%计算
export const calc_hb_str = function (cur, pre) {
if (cur == 0 || pre == 0){
return '0.00%'
}
return conver_num_rate(formater((cur - pre) / pre * 100));
};
......@@ -8,6 +11,15 @@ export const calc_tb_str = function (cur, pre) {
return conver_num_rate(formater(cur / pre * 100));
};
//计算占比
export const calc_zb_str = function (item, total) {
if (item == 0 || total == 0){
return '0.00%'
}
return formater(item / total * 100) + '%';
};
//conver amont
export const conver_amont = function (amont) {
return formater(amont / 10000);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment