@@ -93,23 +93,37 @@ const svg = computed(() => {
9393 }
9494});
9595
96- const immutableDataset = ref (props .dataset .map (ds => {
97- return {
98- ... ds,
99- id: createUid ()
96+ function addIdsToTree (tree ) {
97+ tree .forEach ((node , i ) => {
98+ node .id = createUid ();
99+ node .color = convertColorToHex (node .color ) || palette[i] || palette[i % palette .length ];
100+ if (node .children ) {
101+ node .children .forEach (c => {
102+ c .parentId = node .id ,
103+ c .color = node .color
104+ })
105+ addIdsToTree (node .children );
100106 }
101- }));
107+ });
108+ }
109+
110+ const immutableDataset = ref (props .dataset );
111+ onMounted (() => {
112+ addIdsToTree (immutableDataset .value )
113+ })
114+
115+ const currentSet = ref (immutableDataset .value )
102116
103117const datasetCopy = computed (() => {
104- return immutableDataset .value .map ((ds , i ) => {
118+ return currentSet .value .map ((ds , i ) => {
105119 return {
106120 ... ds,
107121 color: convertColorToHex (ds .color ) || palette[i] || palette[i % palette .length ],
108122 }
109123 }).filter ((ds ) => ! segregated .value .includes (ds .id ))
110124});
111125
112- const total = computed (() => datasetCopy .value .map (d => d .value ).reduce ((a , b ) => a + b, 0 ));
126+ const total = computed (() => immutableDataset .value .filter (( ds ) => ! segregated . value . includes ( ds . id )). map (d => d .value || 0 ).reduce ((a , b ) => a + b, 0 ));
113127
114128const orderedDataset = computed ({
115129 get () {
@@ -146,7 +160,6 @@ function mapChildren(children, parentColor, parentName, totalValue) {
146160 color,
147161 proportion,
148162 parentName,
149- id: createUid (),
150163 children: item .children ? mapChildren (item .children , color, item .name , totalValue) : undefined
151164 };
152165 });
@@ -234,11 +247,29 @@ const viewBox = ref({
234247})
235248const isZoom = ref (false );
236249
250+ function findNodeById (id , nodes = immutableDataset .value ) {
251+ for (const node of nodes) {
252+ if (node .id === id) {
253+ return node;
254+ }
255+ if (node .children ) {
256+ const foundNode = findNodeById (id, node .children );
257+ if (foundNode) {
258+ return foundNode;
259+ }
260+ }
261+ }
262+ return null ;
263+ };
264+
265+
237266function zoom (rect ) {
238267 if (isZoom .value ) {
239268 emit (' selectDatapoint' , undefined );
269+ currentSet .value = immutableDataset .value ;
240270 } else {
241271 emit (' selectDatapoint' , rect);
272+ currentSet .value = [findNodeById (rect .parentId )];
242273 }
243274 isZoom .value = ! isZoom .value ;
244275}
@@ -487,7 +518,7 @@ defineExpose({
487518 datapoint: rect,
488519 seriesIndex: i,
489520 })"
490- @mouseleave =" !isZoom ? selectedRect = null : '' ; isTooltip = false"
521+ @mouseleave =" selectedRect = null; isTooltip = false"
491522 :style =" `opacity:${selectedRect ? selectedRect.id === rect.id ? 1 : treemapConfig.style.chart.layout.rects.selected.unselectedOpacity : 1}`"
492523 class =" vue-ui-treemap-rect"
493524 />
@@ -498,7 +529,6 @@ defineExpose({
498529 :height =" getHeight(rect)"
499530 :width =" getWidth(rect)"
500531 class =" vue-ui-treemap-cell-foreignObject"
501- v-if =" !isZoom"
502532 >
503533 <div style =" width : 100% ; height : 100% " class =" vue-ui-treemap-cell" >
504534 <div
@@ -529,56 +559,6 @@ defineExpose({
529559 </div >
530560 </foreignObject >
531561 </g >
532-
533-
534- <g v-if =" isZoom" >
535- <rect
536- :x =" treemapConfig.style.chart.padding.left * 2"
537- :y =" treemapConfig.style.chart.padding.top * 2"
538- :width =" svg.vbWidth - (treemapConfig.style.chart.padding.left * 2) - (treemapConfig.style.chart.padding.right * 2)"
539- :height =" svg.vbHeight - treemapConfig.style.chart.padding.top - treemapConfig.style.chart.padding.bottom"
540- :fill =" treemapConfig.style.chart.layout.rects.gradient.show ? `url(#tgrad_${selectedRect.id})` : selectedRect.color"
541- :rx =" treemapConfig.style.chart.layout.rects.borderRadius"
542- :stroke =" treemapConfig.style.chart.layout.rects.selected.stroke"
543- @click =" zoom(selectedRect)"
544- class =" vue-ui-treemap-cell-zoom"
545- />
546- <foreignObject
547- :x =" treemapConfig.style.chart.padding.left * 2"
548- :y =" treemapConfig.style.chart.padding.top * 2"
549- :width =" svg.vbWidth - (treemapConfig.style.chart.padding.left * 2) - (treemapConfig.style.chart.padding.right * 2)"
550- :height =" svg.vbHeight - treemapConfig.style.chart.padding.top - treemapConfig.style.chart.padding.bottom"
551- class =" vue-ui-treemap-cell-foreignObject"
552- >
553- <div style =" width : 100% ; height : 100% " class =" vue-ui-treemap-cell" >
554- <div
555- class =" vue-ui-treemap-cell-default"
556- v-if =" treemapConfig.style.chart.layout.labels.showDefaultLabels" :style =" `width:calc(100% - ${treemapConfig.style.chart.layout.labels.fontSize/ 1.5}px);text-align:left;padding:${treemapConfig.style.chart.layout.labels.fontSize / 3}px; color:${adaptColorToBackground(selectedRect.color)}`"
557- >
558- <span :style =" `width:100%;`" >
559- {{ selectedRect.name }}
560- </span ><br >
561- <span :style =" `width:100%;`" >
562- {{ dataLabel({
563- p: treemapConfig.style.chart.layout.labels.prefix,
564- v: selectedRect.value,
565- s: treemapConfig.style.chart.layout.labels.suffix,
566- r: treemapConfig.style.chart.layout.labels.rounding
567- }) }}
568- </span >
569- </div >
570- <slot
571- name =" rect"
572- v-bind =" {
573- rect: selectedRect,
574- shouldShow: selectedRect.proportion > treemapConfig.style.chart.layout.labels.hideUnderProportion || isZoom,
575- fontSize: calcFontSize(selectedRect),
576- isZoom,
577- textColor: adaptColorToBackground(selectedRect.color)
578- }" />
579- </div >
580- </foreignObject >
581- </g >
582562 <slot name =" svg" v-bind =" { svg, isZoom, rect: selectedRect, config: treemapConfig }" />
583563 </svg >
584564
@@ -677,7 +657,7 @@ defineExpose({
677657}
678658
679659.vue-ui-treemap-rect {
680- transition : opacity 0.2s ease-in-out ;
660+ transition : all 0.2s ease-in-out ;
681661}
682662
683663.vue-ui-treemap-zoom-info {
0 commit comments