| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405 |
- <template>
- <div class="chartsContainer">
- <div class="chartsContainer-title">协同配合</div>
- <div class="chartsContainer-list">
- <div class="chartsContainer-content">
- <div class="chartsContainer-content-top">
- <div class="chartsContainer-content-name">性格特征</div>
- </div>
- <div class="chartsContainer-content-content" ref="bubblesRef" />
- </div>
- <div class="chartsContainer-content-right">
- <div class="chartsContainer-content-item">
- <div class="chartsContainer-content-top">
- <div class="chartsContainer-content-name">工作风格</div>
- </div>
- <div class="chartsContainer-content-content" ref="pie" />
- </div>
- <div class="chartsContainer-content-item">
- <div class="chartsContainer-content-top">
- <div class="chartsContainer-content-name">性别人数</div>
- </div>
- <div class="chartsContainer-content-content" ref="bar" />
- </div>
- </div>
- </div>
- </div>
- </template>
- <script setup>
- import { getCollaborationProfile } from '@/api/item/items'
- import { useTimeOut } from './useTimeOut';
- import { useECharts } from '@/hooks/useEcharts.js';
- import { ref, computed, inject } from 'vue'
- const personalityData = ref([])
- const params = inject('provideParams')
- const bubblesRef = ref(null)
- const getBubblesOption = computed(() => {
- let maxValue = 1; // 防止数据全都为 0,后面会除以 maxValue,为 0 会出错
- let valueList = personalityData.value.map((item) => item.value);
- maxValue = Math.max(maxValue, ...valueList);
- // 设定尺寸的大小
- let minSymbolSize = 70; // 最小尺寸
- let symbolSize = 80; // 大小
- let repulsion = symbolSize * 1.3; // 斥力 为了防止重叠
- // 可以根据数据的多少,动态调整 symbolSize 的大小
- let valueListLen = valueList.length;
- if (valueListLen < 3) {
- symbolSize = 120;
- } else if (valueListLen < 5) {
- symbolSize = 100;
- }
- // 获取要渲染的数据
- let data = personalityData.value.map((item) => {
- // 根据比例与最小尺寸,算出每个元素的大小
- let size = Math.max(symbolSize * (item.value / maxValue), minSymbolSize);
- return {
- name: item.name,
- value: item.value,
- code: item.code,
- symbolSize: size,
- itemStyle: {
- color: item.type === 'I' ? {
- type: 'radial',
- x: 0.4, y: 0.3, r: 1,
- colorStops: [
- { offset: 0, color: '#FFD700' },
- { offset: 0.6, color: '#FFA500' },
- { offset: 1, color: '#333333' }
- ]
- } : {
- type: 'radial',
- x: 0.4, y: 0.3, r: 1,
- colorStops: [
- { offset: 0, color: '#87CEEB' },
- { offset: 0.6, color: '#1E90FF' },
- { offset: 1, color: '#333333' }
- ]
- }
- }
- };
- });
- return {
- xAxis: {
- show: false,
- },
- yAxis: {
- show: false,
- },
- series: [
- {
- data,
- type: "graph", // 关系图
- layout: "force", // 采用力引导布局
- force: {
- repulsion, // 值越大则斥力越大 每个元素间隔越大
- gravity: 0.11,
- edgeLength: 2,
- },
- roam: false,
- draggable: true,
- emphasis: {
- scale: 1.1,
- focus: 'series'
- },
- // 设置 label
- label: {
- show: true,
- position: "inside",
- formatter: (params) => {
- const data = params.data
- return [ data.code, data.name, `${data.value}人` ].join("\n")
- },
- fontSize: 12,
- color: "#FFF",
- align: "center",
- lineHeight: 14,
- fontWeight: 900
- },
- // 设置元素的样式
- itemStyle: {
- borderWidth: 1
- },
- },
- ],
- };
- })
- useECharts(bubblesRef, getBubblesOption)
- const pie = ref(null)
- const pieData = ref([])
- const pieALLCount = ref(0)
- const pieOption = computed(() => {
- return {
- tooltip: {
- trigger: 'axis',
- axisPointer: {
- type: 'shadow'
- },
- formatter: function (params) {
- return `${params[ 0 ].seriesName}: ${params[ 0 ].name}<br/>${params[ 0 ].marker}人数: ${params[ 0 ].value}人 (${Math.round(params[0].value / pieALLCount.value * 1000) / 10}%)`
- }
- },
- grid: {
- left: '20%',
- right: '10%',
- bottom: '10%',
- top: '5%',
- },
- xAxis: {
- type: 'value',
- show: true,
- axisLabel: {
- color: '#fff',
- },
- axisLine: {
- show: true,
- },
- minInterval: 1,
- },
- yAxis: {
- type: 'category',
- data: pieData.value.map(item => item.name),
- axisLabel: {
- color: '#fff',
- formatter: (value) => {
- return `${value.substring(0, 2)} \n${value.substring(2).replace('(', '(').replace(')', ')')}`
- }
- }
- },
- series: [
- {
- name: '工作风格',
- type: 'bar',
- stack: 'total',
- label: {
- show: true,
- color: '#fff'
- },
- color: '#408CFF',
- emphasis: {
- focus: 'series'
- },
- data: pieData.value.map(item => item.value),
- }
- ]
- }
- })
- useECharts(pie, pieOption)
- const bar = ref(null)
- const sexList = ref([])
- const sexALLCount = ref(0)
- const barOption = computed(() => {
- return {
- tooltip: {
- trigger: 'axis',
- axisPointer: {
- type: 'shadow'
- },
- formatter: function (params) {
- return `${params[ 0 ].name}<br/>${params[ 0 ].marker}人数: ${params[ 0 ].value}人 (${Math.round(params[0].value / sexALLCount.value * 1000) / 10}%)`
- }
- },
- grid: {
- left: '20%',
- right: '10%',
- bottom: '10%',
- top: '5%',
- },
- xAxis: {
- type: 'value',
- show: true,
- axisLabel: {
- color: '#fff'
- },
- axisLine: {
- show: true,
- color: '#fff'
- },
- minInterval: 1,
- },
- yAxis: {
- type: 'category',
- data: sexList.value.map(item => item.name),
- axisLabel: {
- color: '#fff'
- }
- },
- series: [ {
- name: '人数',
- type: 'bar',
- stack: 'total',
- label: {
- show: true,
- color: '#fff'
- },
- color: '#408CFF',
- emphasis: {
- focus: 'series'
- },
- data: sexList.value.map(item => item.value)
- } ]
- }
- })
- useECharts(bar, barOption)
- useTimeOut(() => {
- getCollaborationProfile({ deptId: params.value.deptId }).then(res => {
- let pieALLCountNumber = 0
- let sexALLCountNumber = 0
- pieData.value = (res.data || { workingStyleList: [] }).workingStyleList.map(item => {
- pieALLCountNumber += item.count
- return { value: item.count, name: item.name }
- })
- pieALLCount.value = pieALLCountNumber
- sexList.value = (res.data || { sexList: [] }).sexList.map(item => {
- sexALLCountNumber += item.count
- return { name: item.name, value: item.count }
- })
- sexALLCount.value = sexALLCountNumber
- personalityData.value = (res.data || { characterCharacteristicsList: [] }).characterCharacteristicsList.map(item => {
- return {
- name: item.name.substring(4),
- value: item.count,
- code: item.code,
- type: item.code.substring(0, 1)
- }
- })
- })
- }, [ params ])
- </script>
- <style lang="scss" scoped>
- .chartsContainer {
- width: 100%;
- height: 100%;
- position: relative;
- background: linear-gradient(to bottom, rgba(8, 97, 117, 0) 0%, #13a2d6 200%);
- border-radius: 4px;
- overflow: hidden;
- display: flex;
- flex-direction: column;
- .chartsContainer-title {
- height: 42px;
- width: 100%;
- background: linear-gradient(to right, #004387 0%, #090B18 100%);
- border-left: 1px solid #1892CE;
- line-height: 42px;
- color: #fff;
- font-weight: 900;
- font-size: 20px;
- text-indent: 1em;
- }
- .chartsContainer-list {
- padding: 20px 15px 10px;
- box-sizing: border-box;
- display: flex;
- flex: 1;
- column-gap: 10px;
- overflow: hidden;
- }
- .chartsContainer-content {
- display: flex;
- flex-direction: column;
- row-gap: 10px;
- flex: 1;
- .chartsContainer-content-top {
- display: flex;
- align-items: center;
- color: #78DEF5;
- .chartsContainer-content-name {
- color: #fff;
- font-weight: bold;
- font-size: 16px;
- display: flex;
- align-items: center;
- &::before {
- content: '';
- display: inline-block;
- border-left: 9px solid #1CB6FF;
- border-top: 8px solid transparent;
- border-right: 9px solid transparent;
- border-bottom: 8px solid transparent;
- }
- }
- }
- .chartsContainer-content-describe {
- color: #78DEF5;
- font-size: 12px;
- font-weight: bold;
- display: flex;
- align-items: center;
- }
- .chartsContainer-content-content {
- flex: 1;
- width: 100%;
- }
- }
- .chartsContainer-content-right {
- flex: 1;
- display: flex;
- flex-direction: column;
- row-gap: 15px;
- .chartsContainer-content-item {
- display: flex;
- flex-direction: column;
- row-gap: 10px;
- flex: 1;
- .chartsContainer-content-top {
- display: flex;
- align-items: center;
- color: #78DEF5;
- .chartsContainer-content-name {
- color: #fff;
- font-weight: bold;
- font-size: 16px;
- display: flex;
- align-items: center;
- &::before {
- content: '';
- display: inline-block;
- border-left: 9px solid #1CB6FF;
- border-top: 8px solid transparent;
- border-right: 9px solid transparent;
- border-bottom: 8px solid transparent;
- }
- }
- }
- .chartsContainer-content-describe {
- color: #78DEF5;
- font-size: 12px;
- font-weight: bold;
- display: flex;
- align-items: center;
- }
- .chartsContainer-content-content {
- flex: 1;
- width: 100%;
- }
- }
- }
- }
- </style>
|