feat: 调整首页图表

This commit is contained in:
caiyuchao
2025-09-29 17:39:08 +08:00
parent acda6051ef
commit c3eee10f3a
6 changed files with 121 additions and 122 deletions

View File

@@ -25,6 +25,7 @@ export namespace CustomerApi {
contractCount: number; contractCount: number;
signingRate: number; signingRate: number;
completionRate: number; completionRate: number;
permanentCount: number;
} }
} }

View File

@@ -28,7 +28,7 @@ function renderChart() {
series: [ series: [
{ {
// //
name: '授权License数', name: 'License数',
type: 'bar', type: 'bar',
data: [props.dashboardValue.licenseCount], data: [props.dashboardValue.licenseCount],
barWidth: 20, barWidth: 20,
@@ -41,16 +41,16 @@ function renderChart() {
}, },
{ {
// //
name: '已签合同数', name: '永久license数',
type: 'bar', type: 'bar',
data: [props.dashboardValue.contractCount], data: [props.dashboardValue.permanentCount],
barWidth: 20, barWidth: 20,
itemStyle: { color: '#91c7ae' }, itemStyle: { color: '#91c7ae' },
z: 2, z: 2,
label: { label: {
show: true, show: true,
position: 'right', position: 'right',
formatter: `{c}/${props.dashboardValue.licenseCount} (${props.dashboardValue.completionRate}%)`, formatter: `{c}/${props.dashboardValue.licenseCount}`,
rich: { per: { color: '#333', fontWeight: 'bold' } }, rich: { per: { color: '#333', fontWeight: 'bold' } },
}, },
}, },
@@ -74,5 +74,5 @@ watch(
</script> </script>
<template> <template>
<EchartsUI ref="chartRef" /> <EchartsUI ref="chartRef" style="height: 150px" />
</template> </template>

View File

@@ -19,22 +19,26 @@ function renderChart() {
{ {
type: 'pie', type: 'pie',
roseType: 'radius', roseType: 'radius',
radius: [20, 100], radius: [15, 60],
label: { show: true, fontSize: 14 }, label: {
data: [ show: true,
{ fontSize: 14,
value: props.dashboardValue.userCount, formatter: '{b}{c}',
name: '员工',
itemStyle: { color: '#4F81BD' },
}, },
data: [
// {
// value: props.dashboardValue.userCount,
// name: '',
// itemStyle: { color: '#4F81BD' },
// },
{ {
value: props.dashboardValue.customerCount, value: props.dashboardValue.customerCount,
name: '客户', name: '客户',
itemStyle: { color: '#9BBB59' }, itemStyle: { color: '#9BBB59' },
}, },
{ {
value: props.dashboardValue.projectCount, value: props.dashboardValue.projectCount,
name: '项目', name: '项目',
itemStyle: { color: '#C0504D' }, itemStyle: { color: '#C0504D' },
}, },
], ],
@@ -60,5 +64,5 @@ watch(
</script> </script>
<template> <template>
<EchartsUI ref="chartRef" /> <EchartsUI ref="chartRef" style="height: 150px" />
</template> </template>

View File

@@ -1,54 +0,0 @@
<script lang="ts" setup>
import type { EchartsUIType } from '@vben/plugins/echarts';
import { onMounted, ref, watch } from 'vue';
import { EchartsUI, useEcharts } from '@vben/plugins/echarts';
const props = withDefaults(defineProps<{ signingRate?: number }>(), {
signingRate: 0,
});
const chartRef = ref<EchartsUIType>();
const { renderEcharts } = useEcharts(chartRef);
function renderChart() {
renderEcharts({
// title: { text: '签单率', left: 'center' },
series: [
{
type: 'gauge',
startAngle: 225,
endAngle: -45,
progress: { show: true, width: 18 },
axisLine: { lineStyle: { width: 18 } },
pointer: { width: 6 },
detail: { fontSize: 24, formatter: '{value}%' },
data: [{ value: props.signingRate }],
},
],
tooltip: {
trigger: 'item',
},
});
}
onMounted(() => {
renderChart();
});
watch(
() => props.signingRate,
(newVal) => {
if (newVal) {
renderChart();
}
},
{ deep: true },
);
</script>
<template>
<EchartsUI ref="chartRef" />
</template>

View File

@@ -0,0 +1,71 @@
<script lang="ts" setup>
import type { EchartsUIType } from '@vben/plugins/echarts';
import type { CustomerApi } from '#/api/license/customer';
import { onMounted, ref, watch } from 'vue';
import { EchartsUI, useEcharts } from '@vben/plugins/echarts';
const props = defineProps<{ dashboardValue: CustomerApi.Dashboard }>();
const chartRef = ref<EchartsUIType>();
const { renderEcharts } = useEcharts(chartRef);
function renderChart() {
renderEcharts({
// title: { text: '签单率', left: 'center' },
series: [
{
name: '签单率(已签合同数/项目数)',
type: 'gauge',
startAngle: 225,
endAngle: -45,
radius: '100%',
progress: { show: true },
// axisLine: { lineStyle: { width: 11 } },
axisLabel: {
fontSize: 10,
},
axisTick: {
length: 2,
distance: 3,
// show: false,
},
splitLine: {
length: 5,
distance: 3,
lineStyle: {
width: 2,
// color: '#999',
},
},
// pointer: { width: 6 },
detail: { fontSize: 18, formatter: '{value}%' },
data: [{ value: props.dashboardValue.signingRate ?? 0 }],
},
],
tooltip: {
// trigger: 'item',
formatter: `{a} <br/>${props.dashboardValue.contractCount}/${props.dashboardValue.projectCount}={c}%`,
},
});
}
onMounted(() => {
renderChart();
});
watch(
() => props.dashboardValue,
(newVal) => {
if (newVal) {
renderChart();
}
},
{ deep: true },
);
</script>
<template>
<EchartsUI ref="chartRef" style="height: 150px" />
</template>

View File

@@ -5,7 +5,11 @@ import type { CustomerApi } from '#/api/license/customer';
import { onMounted, ref, shallowRef } from 'vue'; import { onMounted, ref, shallowRef } from 'vue';
import { AnalysisChartCard, WorkbenchTrends } from '@vben/common-ui'; import {
AnalysisChartCard,
AnalysisOverviewCard,
WorkbenchTrends,
} from '@vben/common-ui';
import dayjs from 'dayjs'; import dayjs from 'dayjs';
import relativeTime from 'dayjs/plugin/relativeTime'; import relativeTime from 'dayjs/plugin/relativeTime';
@@ -16,11 +20,11 @@ import { getLicenseExpiry } from '#/api/license/license';
// import { DictTag } from '#/components/dict-tag'; // import { DictTag } from '#/components/dict-tag';
import { DICT_TYPE, getDictObj } from '#/utils'; import { DICT_TYPE, getDictObj } from '#/utils';
import AnalyticsVisitsData from './analytics-visits-data.vue'; import AnalyticsVisitsData from './analytics-visits-lic.vue';
import AnalyticsVisitsSales from './analytics-visits-sales.vue'; import AnalyticsVisitsSource from './analytics-visits-pie.vue';
import AnalyticsVisitsSource from './analytics-visits-source.vue'; import AnalyticsVisitsSales from './analytics-visits-sign.vue';
const overviewItems = shallowRef<AnalysisOverviewItem[]>([]); const overviewItems = shallowRef<AnalysisOverviewItem>();
const trendItems = shallowRef<WorkbenchTrendItem[]>([]); const trendItems = shallowRef<WorkbenchTrendItem[]>([]);
const projectProgressItems = shallowRef<WorkbenchTrendItem[]>([]); const projectProgressItems = shallowRef<WorkbenchTrendItem[]>([]);
dayjs.extend(relativeTime); dayjs.extend(relativeTime);
@@ -32,50 +36,13 @@ onMounted(async () => {
dashboardValue.value = data; dashboardValue.value = data;
overviewItems.value = [ overviewItems.value = {
{ icon: 'icon-[streamline-plump-color--user-pin-flat] size-9 flex-shrink-0',
icon: 'icon-[streamline-plump-color--user-pin-flat] size-8 flex-shrink-0', title: '员工数',
title: '员工总数',
totalTitle: '总用户量', totalTitle: '总用户量',
totalValue: data.userCount || 0, totalValue: data.userCount || 0,
value: data.userCount || 0, value: data.userCount || 0,
}, };
{
icon: 'icon-[streamline-color--key-flat] size-8 flex-shrink-0',
title: '授权License数',
totalTitle: '总License量',
totalValue: data?.licenseCount || 0,
value: data?.licenseCount || 0,
},
{
icon: 'icon-[streamline-sharp-color--laptop-project-screen-flat] size-8 flex-shrink-0',
title: '项目总数',
totalTitle: '总项目量',
totalValue: data?.projectCount || 0,
value: data?.projectCount || 0,
},
{
icon: 'icon-[material-icon-theme--folder-contract-open] size-8 flex-shrink-0',
title: '已签合同数',
totalTitle: '总合同量',
totalValue: data?.contractCount || 0,
value: data?.contractCount || 0,
},
{
icon: 'icon-[streamline-color--information-desk-customer] size-8 flex-shrink-0',
title: '客户总数',
totalTitle: '总客户量',
totalValue: data?.customerCount || 0,
value: data?.customerCount || 0,
},
{
icon: 'icon-[streamline-plump-color--fill-and-sign-flat] size-8 flex-shrink-0',
title: '签单率',
totalTitle: '总签单率',
totalValue: data?.signingRate || 0,
value: data?.signingRate || 0,
},
];
const licenses = await getLicenseExpiry(); const licenses = await getLicenseExpiry();
trendItems.value = licenses.map((item) => { trendItems.value = licenses.map((item) => {
@@ -140,14 +107,24 @@ onMounted(async () => {
<!-- <AnalysisOverview :items="overviewItems" /> --> <!-- <AnalysisOverview :items="overviewItems" /> -->
<div class="w-full md:flex"> <div class="w-full md:flex">
<AnalysisChartCard class="mt-5 md:mr-4 md:mt-0 md:w-1/3" title="概览"> <AnalysisOverviewCard
:item="overviewItems"
class="mt-5 md:mr-4 md:mt-0 md:w-1/4"
/>
<AnalysisChartCard
class="mt-5 md:mr-4 md:mt-0 md:w-1/4"
title="项目与客户数"
>
<AnalyticsVisitsSource :dashboard-value="dashboardValue" /> <AnalyticsVisitsSource :dashboard-value="dashboardValue" />
</AnalysisChartCard> </AnalysisChartCard>
<AnalysisChartCard class="mt-5 md:mr-4 md:mt-0 md:w-1/3" title="完成度"> <AnalysisChartCard
class="mt-5 md:mr-4 md:mt-0 md:w-1/4"
title="交付完成率"
>
<AnalyticsVisitsData :dashboard-value="dashboardValue" /> <AnalyticsVisitsData :dashboard-value="dashboardValue" />
</AnalysisChartCard> </AnalysisChartCard>
<AnalysisChartCard class="mt-5 md:mt-0 md:w-1/3" title="签单率"> <AnalysisChartCard class="mt-5 md:mt-0 md:w-1/4" title="签单率">
<AnalyticsVisitsSales :signing-rate="dashboardValue.signingRate" /> <AnalyticsVisitsSales :dashboard-value="dashboardValue" />
</AnalysisChartCard> </AnalysisChartCard>
</div> </div>