chartjs-chart-treemap
Advanced tools
Comparing version 1.0.0-beta.4 to 1.0.0
/*! | ||
* chartjs-chart-treemap v1.0.0-beta.4 | ||
* https://github.com/kurkle/chartjs-chart-treemap#readme | ||
* chartjs-chart-treemap v1.0.0 | ||
* https://chartjs-chart-treemap.pages.dev/ | ||
* (c) 2021 Jukka Kurkela | ||
* Released under the MIT license | ||
*/ | ||
import { DatasetController, Element } from 'chart.js'; | ||
import { DatasetController, registry, Element } from 'chart.js'; | ||
import { toFont, valueOrDefault } from 'chart.js/helpers'; | ||
@@ -112,2 +112,3 @@ | ||
function round(v, n) { | ||
// @ts-ignore | ||
return (+(Math.round(v + 'e+' + n) + 'e-' + n)) || 0; | ||
@@ -330,3 +331,3 @@ } | ||
for (i = 0; i < n; ++i) { | ||
o = {value: val(i), groupSum: gsum, _data: values[tmp[i]._idx]}; | ||
o = {value: val(i), groupSum: gsum, _data: values[tmp[i]._idx], level: undefined, group: undefined}; | ||
if (grp) { | ||
@@ -350,2 +351,4 @@ o.level = lvl; | ||
var version = "1.0.0"; | ||
function rectNotEqual(r1, r2) { | ||
@@ -475,2 +478,10 @@ return !r1 || !r2 | ||
class TreemapController extends DatasetController { | ||
constructor(chart, datasetIndex) { | ||
super(chart, datasetIndex); | ||
this._rect = undefined; | ||
this._key = undefined; | ||
this._groups = undefined; | ||
} | ||
initialize() { | ||
@@ -486,3 +497,3 @@ this.enableOptionSharing = true; | ||
const groups = dataset.groups || (dataset.groups = []); | ||
const font = toFont(dataset.font, me.chart.options.font); | ||
const font = toFont(dataset.font); | ||
const area = me.chart.chartArea; | ||
@@ -499,3 +510,5 @@ const key = dataset.key || ''; | ||
dataset.data = buildData(dataset, mainRect, font); | ||
// @ts-ignore using private stuff | ||
me._dataCheck(); | ||
// @ts-ignore using private stuff | ||
me._resyncElements(); | ||
@@ -510,3 +523,3 @@ } | ||
const result = Object.isFrozen(options) ? Object.assign({}, options) : options; | ||
result.font = toFont(options.font, this.chart.options.font); | ||
result.font = toFont(options.font); | ||
return result; | ||
@@ -588,2 +601,4 @@ } | ||
TreemapController.version = version; | ||
TreemapController.defaults = { | ||
@@ -599,2 +614,3 @@ dataElementType: 'treemap', | ||
}; | ||
TreemapController.overrides = { | ||
@@ -641,2 +657,25 @@ interaction: { | ||
TreemapController.afterRegister = function() { | ||
const tooltipPlugin = registry.plugins.get('tooltip'); | ||
if (tooltipPlugin) { | ||
tooltipPlugin.positioners.treemap = function(active) { | ||
if (!active.length) { | ||
return false; | ||
} | ||
const item = active[active.length - 1]; | ||
const el = item.element; | ||
return el.tooltipPosition(); | ||
}; | ||
} | ||
}; | ||
TreemapController.afterUnregister = function() { | ||
const tooltipPlugin = registry.plugins.get('tooltip'); | ||
if (tooltipPlugin) { | ||
delete tooltipPlugin.positioners.treemap; | ||
} | ||
}; | ||
/** | ||
@@ -800,2 +839,2 @@ * Helper function to get the bounds of the rect | ||
export { Rect, TreemapElement as Rectangle, StatArray, TreemapController, flatten, group, index, isObject, sort, squarify, sum }; | ||
export { TreemapController, TreemapElement }; |
/*! | ||
* chartjs-chart-treemap v1.0.0-beta.4 | ||
* https://github.com/kurkle/chartjs-chart-treemap#readme | ||
* chartjs-chart-treemap v1.0.0 | ||
* https://chartjs-chart-treemap.pages.dev/ | ||
* (c) 2021 Jukka Kurkela | ||
@@ -115,2 +115,3 @@ * Released under the MIT license | ||
function round(v, n) { | ||
// @ts-ignore | ||
return (+(Math.round(v + 'e+' + n) + 'e-' + n)) || 0; | ||
@@ -333,3 +334,3 @@ } | ||
for (i = 0; i < n; ++i) { | ||
o = {value: val(i), groupSum: gsum, _data: values[tmp[i]._idx]}; | ||
o = {value: val(i), groupSum: gsum, _data: values[tmp[i]._idx], level: undefined, group: undefined}; | ||
if (grp) { | ||
@@ -353,2 +354,4 @@ o.level = lvl; | ||
var version = "1.0.0"; | ||
function rectNotEqual(r1, r2) { | ||
@@ -478,2 +481,10 @@ return !r1 || !r2 | ||
class TreemapController extends chart_js.DatasetController { | ||
constructor(chart, datasetIndex) { | ||
super(chart, datasetIndex); | ||
this._rect = undefined; | ||
this._key = undefined; | ||
this._groups = undefined; | ||
} | ||
initialize() { | ||
@@ -489,3 +500,3 @@ this.enableOptionSharing = true; | ||
const groups = dataset.groups || (dataset.groups = []); | ||
const font = helpers.toFont(dataset.font, me.chart.options.font); | ||
const font = helpers.toFont(dataset.font); | ||
const area = me.chart.chartArea; | ||
@@ -502,3 +513,5 @@ const key = dataset.key || ''; | ||
dataset.data = buildData(dataset, mainRect, font); | ||
// @ts-ignore using private stuff | ||
me._dataCheck(); | ||
// @ts-ignore using private stuff | ||
me._resyncElements(); | ||
@@ -513,3 +526,3 @@ } | ||
const result = Object.isFrozen(options) ? Object.assign({}, options) : options; | ||
result.font = helpers.toFont(options.font, this.chart.options.font); | ||
result.font = helpers.toFont(options.font); | ||
return result; | ||
@@ -591,2 +604,4 @@ } | ||
TreemapController.version = version; | ||
TreemapController.defaults = { | ||
@@ -602,2 +617,3 @@ dataElementType: 'treemap', | ||
}; | ||
TreemapController.overrides = { | ||
@@ -644,2 +660,25 @@ interaction: { | ||
TreemapController.afterRegister = function() { | ||
const tooltipPlugin = chart_js.registry.plugins.get('tooltip'); | ||
if (tooltipPlugin) { | ||
tooltipPlugin.positioners.treemap = function(active) { | ||
if (!active.length) { | ||
return false; | ||
} | ||
const item = active[active.length - 1]; | ||
const el = item.element; | ||
return el.tooltipPosition(); | ||
}; | ||
} | ||
}; | ||
TreemapController.afterUnregister = function() { | ||
const tooltipPlugin = chart_js.registry.plugins.get('tooltip'); | ||
if (tooltipPlugin) { | ||
delete tooltipPlugin.positioners.treemap; | ||
} | ||
}; | ||
/** | ||
@@ -805,14 +844,2 @@ * Helper function to get the bounds of the rect | ||
const tooltipPlugin = chart_js.Chart.registry.plugins.get('tooltip'); | ||
tooltipPlugin.positioners.treemap = function(active) { | ||
if (!active.length) { | ||
return false; | ||
} | ||
const item = active[active.length - 1]; | ||
const el = item.element; | ||
return el.tooltipPosition(); | ||
}; | ||
exports.flatten = flatten; | ||
@@ -819,0 +846,0 @@ exports.group = group; |
/*! | ||
* chartjs-chart-treemap v1.0.0-beta.4 | ||
* https://github.com/kurkle/chartjs-chart-treemap#readme | ||
* chartjs-chart-treemap v1.0.0 | ||
* https://chartjs-chart-treemap.pages.dev/ | ||
* (c) 2021 Jukka Kurkela | ||
* Released under the MIT license | ||
*/ | ||
!function(t,e){"object"==typeof exports&&"undefined"!=typeof module?e(exports,require("chart.js"),require("chart.js/helpers")):"function"==typeof define&&define.amd?define(["exports","chart.js","chart.js/helpers"],e):e((t="undefined"!=typeof globalThis?globalThis:t||self)["chartjs-chart-treemap"]={},t.Chart,t.Chart.helpers)}(this,(function(t,e,n){"use strict";function i(t){const e=[...t],n=[];for(;e.length;){const t=e.pop();Array.isArray(t)?e.push(...t):n.push(t)}return n.reverse()}function r(t,e,n,i,r){const o=Object.create(null),s=Object.create(null),a=[];let h,l,u,d;for(l=0,u=t.length;l<u;++l)d=t[l],i&&d[i]!==r||(h=d[e]||"",h in o||(o[h]=0,s[h]=[]),o[h]+=+d[n],s[h].push(d));return Object.keys(o).forEach((t=>{d={children:s[t]},d[n]=+o[t],d[e]=t,i&&(d[i]=r),a.push(d)})),a}function o(t){const e=typeof t;return"function"===e||"object"===e&&!!t}function s(t,e){let n,i=t.length;if(!i)return e;const r=o(t[0]);for(e=r?e:"v",n=0,i=t.length;n<i;++n)r?t[n]._idx=n:t[n]={v:t[n],_idx:n};return e}function a(t,e){e?t.sort(((t,n)=>+n[e]-+t[e])):t.sort(((t,e)=>+e-+t))}function h(t,e){let n,i,r;for(n=0,i=0,r=t.length;i<r;++i)n+=e?+t[i][e]:+t[i];return n}function l(t,e){return+(Math.round(t+"e+"+e)+"e-"+e)||0}function u(t,e,n,i){const r=t._normalized,o=e*r/n,s=Math.sqrt(r*o),a=r/s;return{d1:s,d2:a,w:"_ix"===i?s:a,h:"_ix"===i?a:s}}const d=(t,e)=>l(t.rtl?t.x+t.w-t._ix-e:t.x+t._ix,4);function c(t,e,n,i){const r={x:d(t,n.w),y:l(t.y+t._iy,4),w:l(n.w,4),h:l(n.h,4),a:l(e._normalized,4),v:e.value,s:i,_data:e._data};return e.group&&(r.g=e.group,r.l=e.level,r.gs=e.groupSum),r}class g{constructor(t){const e=this;t=t||{w:1,h:1},e.rtl=!!t.rtl,e.x=t.x||t.left||0,e.y=t.y||t.top||0,e._ix=0,e._iy=0,e.w=t.w||t.width||t.right-t.left,e.h=t.h||t.height||t.bottom-t.top}get area(){return this.w*this.h}get iw(){return this.w-this._ix}get ih(){return this.h-this._iy}get dir(){const t=this.ih;return t<=this.iw&&t>0?"y":"x"}get side(){return"x"===this.dir?this.iw:this.ih}map(t){const e=this,n=[],i=t.nsum,r=t.get(),o=e.dir,s=e.side,a=s*s,h="x"===o?"_ix":"_iy",l=i*i;let d=0,g=0;for(const i of r){const r=u(i,a,l,h);g+=r.d1,d=Math.max(d,r.d2),n.push(c(e,i,r,t.sum)),e[h]+=r.d1}return e["y"===o?"_ix":"_iy"]+=d,e[h]-=g,n}}const p=Math.min,f=Math.max;function m(t,e){const n=+e[t.key],i=n*t.ratio;return e._normalized=i,{min:p(t.min,n),max:f(t.max,n),sum:t.sum+n,nmin:p(t.nmin,i),nmax:f(t.nmax,i),nsum:t.nsum+i}}function x(t,e,n){t._arr.push(e),function(t,e){Object.assign(t,e)}(t,n)}class y{constructor(t,e){const n=this;n.key=t,n.ratio=e,n.reset()}get length(){return this._arr.length}reset(){const t=this;t._arr=[],t._hist=[],t.sum=0,t.nsum=0,t.min=1/0,t.max=-1/0,t.nmin=1/0,t.nmax=-1/0}push(t){x(this,t,m(this,t))}pushIf(t,e,...n){const i=m(this,t);if(!e((r=this,{min:r.min,max:r.max,sum:r.sum,nmin:r.nmin,nmax:r.nmax,nsum:r.nsum}),i,n))return t;var r;x(this,t,i)}get(){return this._arr}}function v(t,e,n){if(0===t.sum)return!0;const[i]=n,r=t.nsum*t.nsum,o=e.nsum*e.nsum,s=i*i,a=Math.max(s*t.nmax/r,r/(s*t.nmin));return Math.max(s*e.nmax/o,o/(s*e.nmin))<=a}function b(t,e,n,r,o,l){t=t||[];const u=[],d=new g(e),c=new y("value",d.area/h(t,n));let p=d.side;const f=t.length;let m,x;if(!f)return u;const b=t.slice();n=s(b,n),a(b,n);const w=t=>r&&b[t][r];for(m=0;m<f;++m)x={value:(_=m,n?+b[_][n]:+b[_]),groupSum:l,_data:t[b[m]._idx]},r&&(x.level=o,x.group=w(m)),x=c.pushIf(x,v,p),x&&(u.push(d.map(c)),p=d.side,c.reset(),c.push(x));var _;return c.length&&u.push(d.map(c)),i(u)}function w(t,e){if(!e)return!1;const n=t.width||t.w,i=t.height||t.h,r=2*e.lineHeight;return n>r&&i>r}function _(t,e,n,i,r){if(t.save(),t.fillStyle=i.color,t.font=i.font.string,t.beginPath(),t.rect(e.x,e.y,e.width,e.height),t.clip(),"l"in n&&n.l!==r){if(i.groupLabels){t.textAlign=i.rtl?"end":"start",t.textBaseline="top";const r=i.rtl?e.x+e.width-i.borderWidth-3:e.x+i.borderWidth+3;t.fillText(n.g,r,e.y+i.borderWidth+3)}}else t.textAlign="center",t.textBaseline="middle",function(t,e,n){const i=n.options,r=i.font.lineHeight,o=(i.label||e.g+"\n"+e.v).split("\n"),s=n.y+n.height/2-o.length*r/4;o.forEach(((e,i)=>t.fillText(e,n.x+n.width/2,s+i*r)))}(t,n,e);t.restore()}function D(t,e){const n=e.options,i=e.width||e.w,r=e.height||e.h;if(t.save(),t.strokeStyle=n.dividerColor||"black",t.lineCap=n.dividerCapStyle,t.setLineDash(n.dividerDash||[]),t.lineDashOffset=n.dividerDashOffset,t.lineWidth=n.dividerWidth,t.beginPath(),i>r){const n=i/2;t.moveTo(e.x+n,e.y),t.lineTo(e.x+n,e.y+r)}else{const n=r/2;t.moveTo(e.x,e.y+n),t.lineTo(e.x+i,e.y+n)}t.stroke(),t.restore()}class O extends e.DatasetController{initialize(){this.enableOptionSharing=!0,super.initialize()}update(t){const e=this,i=e.getMeta(),o=e.getDataset(),s=o.groups||(o.groups=[]),a=n.toFont(o.font,e.chart.options.font),h=e.chart.chartArea,l=o.key||"",u=!!o.rtl,d={x:h.left,y:h.top,w:h.right-h.left,h:h.bottom-h.top,rtl:u};var c,g;"reset"!==t&&(c=e._rect,g=d,c&&g&&c.x===g.x&&c.y===g.y&&c.w===g.w&&c.h===g.h)&&e._key===l&&!function(t,e){let n,i;if(t.lenght!==e.length)return!0;for(n=0,i=t.length;n<i;++n)if(t[n]!==e[n])return!0;return!1}(e._groups,s)||(e._rect=d,e._groups=s.slice(),e._key=l,o.data=function(t,e,i){const o=t.key||"";let s=t.tree||[];const a=t.groups||[],h=a.length,l=(t.spacing||0)+(t.borderWidth||0);return!s.length&&t.data.length&&(s=t.tree=t.data),h?function e(u,d,c,g){const p=a[u],f=u>0&&a[u-1],m=b(r(s,p,o,f,c),d,o,p,u,g),x=m.slice();let y;return u<h-1&&m.forEach((r=>{y={x:r.x+l,y:r.y+l,w:r.w-2*l,h:r.h-2*l},n.valueOrDefault(t.groupLabels,!0)&&w(r,i)&&(y.y+=i.lineHeight,y.h-=i.lineHeight),x.push(...e(u+1,y,r.g,r.s))})),x}(0,e):b(s,e,o)}(o,d,a),e._dataCheck(),e._resyncElements()),e.updateElements(i.data,0,i.data.length,t)}resolveDataElementOptions(t,e){const i=super.resolveDataElementOptions(t,e),r=Object.isFrozen(i)?Object.assign({},i):i;return r.font=n.toFont(i.font,this.chart.options.font),r}updateElements(t,e,n,i){const r=this,o="reset"===i,s=r.getDataset(),a=r._rect.options=r.resolveDataElementOptions(e,i),h=r.getSharedOptions(a),l=r.includeOptions(i,h);for(let a=e;a<e+n;a++){const e=s.data[a],n=h||r.resolveDataElementOptions(a,i),u=o?0:e.h-2*n.spacing,d=o?0:e.w-2*n.spacing,c={x:e.x+n.spacing,y:e.y+n.spacing,width:d,height:u};l&&(c.options=n),r.updateElement(t[a],a,c,i)}r.updateSharedOptions(h,i,a)}_drawDividers(t,e,n){for(let i=0,r=n.length;i<r;++i){const r=n[i],o=e[i];r.options.groupDividers&&o._data.children.length>1&&D(t,r)}this.getDataset().groupDividers&&D(t,this._rect)}_drawRects(t,e,n,i){for(let r=0,o=n.length;r<o;++r){const o=n[r],s=e[r];if(!o.hidden){o.draw(t);const e=o.options;w(o,e.font)&&s.g&&_(t,o,s,e,i)}}}draw(){const t=this,e=t.chart.ctx,n=t.getMeta().data||[],i=t.getDataset(),r=(i.groups||[]).length-1,o=i.data||[];t._drawRects(e,o,n,r),t._drawDividers(e,o,n)}}function C(t,e){const{x:n,y:i,width:r,height:o}=t.getProps(["x","y","width","height"],e);return{left:n,top:i,right:n+r,bottom:i+o}}function k(t,e,n){return Math.max(Math.min(t,n),e)}function j(t){const e=C(t),n=e.right-e.left,i=e.bottom-e.top,r=function(t,e,n){let i,r,s,a;return o(t)?(i=+t.top||0,r=+t.right||0,s=+t.bottom||0,a=+t.left||0):i=r=s=a=+t||0,{t:k(i,0,n),r:k(r,0,e),b:k(s,0,n),l:k(a,0,e)}}(t.options.borderWidth,n/2,i/2);return{outer:{x:e.left,y:e.top,w:n,h:i},inner:{x:e.left+r.l,y:e.top+r.t,w:n-r.l-r.r,h:i-r.t-r.b}}}function E(t,e,n,i){const r=null===e,o=null===n,s=!(!t||r&&o)&&C(t,i);return s&&(r||e>=s.left&&e<=s.right)&&(o||n>=s.top&&n<=s.bottom)}O.id="treemap",O.defaults={dataElementType:"treemap",groupLabels:!0,borderWidth:0,spacing:.5,groupDividers:!1,dividerWidth:1},O.overrides={interaction:{mode:"point",intersect:!0},hover:{},plugins:{tooltip:{position:"treemap",intersect:!0,callbacks:{title(t){if(t.length){return t[0].dataset.key||""}return""},label(t){const e=t.dataset,n=e.data[t.dataIndex],i=n.g||e.label;return(i?i+": ":"")+n.v}}}},scales:{x:{type:"linear",display:!1},y:{type:"linear",display:!1}}};class S extends e.Element{constructor(t){super(),this.options=void 0,this.width=void 0,this.height=void 0,t&&Object.assign(this,t)}draw(t){const e=this.options,{inner:n,outer:i}=j(this);t.save(),i.w!==n.w||i.h!==n.h?(t.beginPath(),t.rect(i.x,i.y,i.w,i.h),t.clip(),t.rect(n.x,n.y,n.w,n.h),t.fillStyle=e.backgroundColor,t.fill(),t.fillStyle=e.borderColor,t.fill("evenodd")):(t.fillStyle=e.backgroundColor,t.fillRect(n.x,n.y,n.w,n.h)),t.restore()}inRange(t,e,n){return E(this,t,e,n)}inXRange(t,e){return E(this,t,null,e)}inYRange(t,e){return E(this,null,t,e)}getCenterPoint(t){const{x:e,y:n,width:i,height:r}=this.getProps(["x","y","width","height"],t);return{x:e+i/2,y:n+r/2}}tooltipPosition(){return this.getCenterPoint()}getRange(t){return"x"===t?this.width/2:this.height/2}}S.id="treemap",S.defaults={borderSkipped:void 0,borderWidth:void 0,color:void 0,dividerCapStyle:"butt",dividerColor:"black",dividerDash:void 0,dividerDashOffset:0,dividerWidth:0,font:{},groupDividers:!1,groupLabels:void 0,spacing:void 0,label:void 0,rtl:void 0},S.defaultRoutes={backgroundColor:"backgroundColor",borderColor:"borderColor"},e.Chart.register(O,S);e.Chart.registry.plugins.get("tooltip").positioners.treemap=function(t){if(!t.length)return!1;return t[t.length-1].element.tooltipPosition()},t.flatten=i,t.group=r,t.index=s,t.isObject=o,t.sort=a,t.sum=h,Object.defineProperty(t,"__esModule",{value:!0})})); | ||
!function(t,e){"object"==typeof exports&&"undefined"!=typeof module?e(exports,require("chart.js"),require("chart.js/helpers")):"function"==typeof define&&define.amd?define(["exports","chart.js","chart.js/helpers"],e):e((t="undefined"!=typeof globalThis?globalThis:t||self)["chartjs-chart-treemap"]={},t.Chart,t.Chart.helpers)}(this,(function(t,e,i){"use strict";function n(t){const e=[...t],i=[];for(;e.length;){const t=e.pop();Array.isArray(t)?e.push(...t):i.push(t)}return i.reverse()}function r(t,e,i,n,r){const o=Object.create(null),s=Object.create(null),a=[];let l,h,u,d;for(h=0,u=t.length;h<u;++h)d=t[h],n&&d[n]!==r||(l=d[e]||"",l in o||(o[l]=0,s[l]=[]),o[l]+=+d[i],s[l].push(d));return Object.keys(o).forEach((t=>{d={children:s[t]},d[i]=+o[t],d[e]=t,n&&(d[n]=r),a.push(d)})),a}function o(t){const e=typeof t;return"function"===e||"object"===e&&!!t}function s(t,e){let i,n=t.length;if(!n)return e;const r=o(t[0]);for(e=r?e:"v",i=0,n=t.length;i<n;++i)r?t[i]._idx=i:t[i]={v:t[i],_idx:i};return e}function a(t,e){e?t.sort(((t,i)=>+i[e]-+t[e])):t.sort(((t,e)=>+e-+t))}function l(t,e){let i,n,r;for(i=0,n=0,r=t.length;n<r;++n)i+=e?+t[n][e]:+t[n];return i}function h(t,e){return+(Math.round(t+"e+"+e)+"e-"+e)||0}function u(t,e,i,n){const r=t._normalized,o=e*r/i,s=Math.sqrt(r*o),a=r/s;return{d1:s,d2:a,w:"_ix"===n?s:a,h:"_ix"===n?a:s}}const d=(t,e)=>h(t.rtl?t.x+t.w-t._ix-e:t.x+t._ix,4);function c(t,e,i,n){const r={x:d(t,i.w),y:h(t.y+t._iy,4),w:h(i.w,4),h:h(i.h,4),a:h(e._normalized,4),v:e.value,s:n,_data:e._data};return e.group&&(r.g=e.group,r.l=e.level,r.gs=e.groupSum),r}class g{constructor(t){const e=this;t=t||{w:1,h:1},e.rtl=!!t.rtl,e.x=t.x||t.left||0,e.y=t.y||t.top||0,e._ix=0,e._iy=0,e.w=t.w||t.width||t.right-t.left,e.h=t.h||t.height||t.bottom-t.top}get area(){return this.w*this.h}get iw(){return this.w-this._ix}get ih(){return this.h-this._iy}get dir(){const t=this.ih;return t<=this.iw&&t>0?"y":"x"}get side(){return"x"===this.dir?this.iw:this.ih}map(t){const e=this,i=[],n=t.nsum,r=t.get(),o=e.dir,s=e.side,a=s*s,l="x"===o?"_ix":"_iy",h=n*n;let d=0,g=0;for(const n of r){const r=u(n,a,h,l);g+=r.d1,d=Math.max(d,r.d2),i.push(c(e,n,r,t.sum)),e[l]+=r.d1}return e["y"===o?"_ix":"_iy"]+=d,e[l]-=g,i}}const p=Math.min,f=Math.max;function m(t,e){const i=+e[t.key],n=i*t.ratio;return e._normalized=n,{min:p(t.min,i),max:f(t.max,i),sum:t.sum+i,nmin:p(t.nmin,n),nmax:f(t.nmax,n),nsum:t.nsum+n}}function x(t,e,i){t._arr.push(e),function(t,e){Object.assign(t,e)}(t,i)}class y{constructor(t,e){const i=this;i.key=t,i.ratio=e,i.reset()}get length(){return this._arr.length}reset(){const t=this;t._arr=[],t._hist=[],t.sum=0,t.nsum=0,t.min=1/0,t.max=-1/0,t.nmin=1/0,t.nmax=-1/0}push(t){x(this,t,m(this,t))}pushIf(t,e,...i){const n=m(this,t);if(!e((r=this,{min:r.min,max:r.max,sum:r.sum,nmin:r.nmin,nmax:r.nmax,nsum:r.nsum}),n,i))return t;var r;x(this,t,n)}get(){return this._arr}}function v(t,e,i){if(0===t.sum)return!0;const[n]=i,r=t.nsum*t.nsum,o=e.nsum*e.nsum,s=n*n,a=Math.max(s*t.nmax/r,r/(s*t.nmin));return Math.max(s*e.nmax/o,o/(s*e.nmin))<=a}function b(t,e,i,r,o,h){t=t||[];const u=[],d=new g(e),c=new y("value",d.area/l(t,i));let p=d.side;const f=t.length;let m,x;if(!f)return u;const b=t.slice();i=s(b,i),a(b,i);const w=t=>r&&b[t][r];for(m=0;m<f;++m)x={value:(_=m,i?+b[_][i]:+b[_]),groupSum:h,_data:t[b[m]._idx],level:void 0,group:void 0},r&&(x.level=o,x.group=w(m)),x=c.pushIf(x,v,p),x&&(u.push(d.map(c)),p=d.side,c.reset(),c.push(x));var _;return c.length&&u.push(d.map(c)),n(u)}function w(t,e){if(!e)return!1;const i=t.width||t.w,n=t.height||t.h,r=2*e.lineHeight;return i>r&&n>r}function _(t,e,i,n,r){if(t.save(),t.fillStyle=n.color,t.font=n.font.string,t.beginPath(),t.rect(e.x,e.y,e.width,e.height),t.clip(),"l"in i&&i.l!==r){if(n.groupLabels){t.textAlign=n.rtl?"end":"start",t.textBaseline="top";const r=n.rtl?e.x+e.width-n.borderWidth-3:e.x+n.borderWidth+3;t.fillText(i.g,r,e.y+n.borderWidth+3)}}else t.textAlign="center",t.textBaseline="middle",function(t,e,i){const n=i.options,r=n.font.lineHeight,o=(n.label||e.g+"\n"+e.v).split("\n"),s=i.y+i.height/2-o.length*r/4;o.forEach(((e,n)=>t.fillText(e,i.x+i.width/2,s+n*r)))}(t,i,e);t.restore()}function D(t,e){const i=e.options,n=e.width||e.w,r=e.height||e.h;if(t.save(),t.strokeStyle=i.dividerColor||"black",t.lineCap=i.dividerCapStyle,t.setLineDash(i.dividerDash||[]),t.lineDashOffset=i.dividerDashOffset,t.lineWidth=i.dividerWidth,t.beginPath(),n>r){const i=n/2;t.moveTo(e.x+i,e.y),t.lineTo(e.x+i,e.y+r)}else{const i=r/2;t.moveTo(e.x,e.y+i),t.lineTo(e.x+n,e.y+i)}t.stroke(),t.restore()}class O extends e.DatasetController{constructor(t,e){super(t,e),this._rect=void 0,this._key=void 0,this._groups=void 0}initialize(){this.enableOptionSharing=!0,super.initialize()}update(t){const e=this,n=e.getMeta(),o=e.getDataset(),s=o.groups||(o.groups=[]),a=i.toFont(o.font),l=e.chart.chartArea,h=o.key||"",u=!!o.rtl,d={x:l.left,y:l.top,w:l.right-l.left,h:l.bottom-l.top,rtl:u};var c,g;"reset"!==t&&(c=e._rect,g=d,c&&g&&c.x===g.x&&c.y===g.y&&c.w===g.w&&c.h===g.h)&&e._key===h&&!function(t,e){let i,n;if(t.lenght!==e.length)return!0;for(i=0,n=t.length;i<n;++i)if(t[i]!==e[i])return!0;return!1}(e._groups,s)||(e._rect=d,e._groups=s.slice(),e._key=h,o.data=function(t,e,n){const o=t.key||"";let s=t.tree||[];const a=t.groups||[],l=a.length,h=(t.spacing||0)+(t.borderWidth||0);return!s.length&&t.data.length&&(s=t.tree=t.data),l?function e(u,d,c,g){const p=a[u],f=u>0&&a[u-1],m=b(r(s,p,o,f,c),d,o,p,u,g),x=m.slice();let y;return u<l-1&&m.forEach((r=>{y={x:r.x+h,y:r.y+h,w:r.w-2*h,h:r.h-2*h},i.valueOrDefault(t.groupLabels,!0)&&w(r,n)&&(y.y+=n.lineHeight,y.h-=n.lineHeight),x.push(...e(u+1,y,r.g,r.s))})),x}(0,e):b(s,e,o)}(o,d,a),e._dataCheck(),e._resyncElements()),e.updateElements(n.data,0,n.data.length,t)}resolveDataElementOptions(t,e){const n=super.resolveDataElementOptions(t,e),r=Object.isFrozen(n)?Object.assign({},n):n;return r.font=i.toFont(n.font),r}updateElements(t,e,i,n){const r=this,o="reset"===n,s=r.getDataset(),a=r._rect.options=r.resolveDataElementOptions(e,n),l=r.getSharedOptions(a),h=r.includeOptions(n,l);for(let a=e;a<e+i;a++){const e=s.data[a],i=l||r.resolveDataElementOptions(a,n),u=o?0:e.h-2*i.spacing,d=o?0:e.w-2*i.spacing,c={x:e.x+i.spacing,y:e.y+i.spacing,width:d,height:u};h&&(c.options=i),r.updateElement(t[a],a,c,n)}r.updateSharedOptions(l,n,a)}_drawDividers(t,e,i){for(let n=0,r=i.length;n<r;++n){const r=i[n],o=e[n];r.options.groupDividers&&o._data.children.length>1&&D(t,r)}this.getDataset().groupDividers&&D(t,this._rect)}_drawRects(t,e,i,n){for(let r=0,o=i.length;r<o;++r){const o=i[r],s=e[r];if(!o.hidden){o.draw(t);const e=o.options;w(o,e.font)&&s.g&&_(t,o,s,e,n)}}}draw(){const t=this,e=t.chart.ctx,i=t.getMeta().data||[],n=t.getDataset(),r=(n.groups||[]).length-1,o=n.data||[];t._drawRects(e,o,i,r),t._drawDividers(e,o,i)}}function k(t,e){const{x:i,y:n,width:r,height:o}=t.getProps(["x","y","width","height"],e);return{left:i,top:n,right:i+r,bottom:n+o}}function C(t,e,i){return Math.max(Math.min(t,i),e)}function j(t){const e=k(t),i=e.right-e.left,n=e.bottom-e.top,r=function(t,e,i){let n,r,s,a;return o(t)?(n=+t.top||0,r=+t.right||0,s=+t.bottom||0,a=+t.left||0):n=r=s=a=+t||0,{t:C(n,0,i),r:C(r,0,e),b:C(s,0,i),l:C(a,0,e)}}(t.options.borderWidth,i/2,n/2);return{outer:{x:e.left,y:e.top,w:i,h:n},inner:{x:e.left+r.l,y:e.top+r.t,w:i-r.l-r.r,h:n-r.t-r.b}}}function E(t,e,i,n){const r=null===e,o=null===i,s=!(!t||r&&o)&&k(t,n);return s&&(r||e>=s.left&&e<=s.right)&&(o||i>=s.top&&i<=s.bottom)}O.id="treemap",O.version="1.0.0",O.defaults={dataElementType:"treemap",groupLabels:!0,borderWidth:0,spacing:.5,groupDividers:!1,dividerWidth:1},O.overrides={interaction:{mode:"point",intersect:!0},hover:{},plugins:{tooltip:{position:"treemap",intersect:!0,callbacks:{title(t){if(t.length){return t[0].dataset.key||""}return""},label(t){const e=t.dataset,i=e.data[t.dataIndex],n=i.g||e.label;return(n?n+": ":"")+i.v}}}},scales:{x:{type:"linear",display:!1},y:{type:"linear",display:!1}}},O.afterRegister=function(){const t=e.registry.plugins.get("tooltip");t&&(t.positioners.treemap=function(t){if(!t.length)return!1;return t[t.length-1].element.tooltipPosition()})},O.afterUnregister=function(){const t=e.registry.plugins.get("tooltip");t&&delete t.positioners.treemap};class S extends e.Element{constructor(t){super(),this.options=void 0,this.width=void 0,this.height=void 0,t&&Object.assign(this,t)}draw(t){const e=this.options,{inner:i,outer:n}=j(this);t.save(),n.w!==i.w||n.h!==i.h?(t.beginPath(),t.rect(n.x,n.y,n.w,n.h),t.clip(),t.rect(i.x,i.y,i.w,i.h),t.fillStyle=e.backgroundColor,t.fill(),t.fillStyle=e.borderColor,t.fill("evenodd")):(t.fillStyle=e.backgroundColor,t.fillRect(i.x,i.y,i.w,i.h)),t.restore()}inRange(t,e,i){return E(this,t,e,i)}inXRange(t,e){return E(this,t,null,e)}inYRange(t,e){return E(this,null,t,e)}getCenterPoint(t){const{x:e,y:i,width:n,height:r}=this.getProps(["x","y","width","height"],t);return{x:e+n/2,y:i+r/2}}tooltipPosition(){return this.getCenterPoint()}getRange(t){return"x"===t?this.width/2:this.height/2}}S.id="treemap",S.defaults={borderSkipped:void 0,borderWidth:void 0,color:void 0,dividerCapStyle:"butt",dividerColor:"black",dividerDash:void 0,dividerDashOffset:0,dividerWidth:0,font:{},groupDividers:!1,groupLabels:void 0,spacing:void 0,label:void 0,rtl:void 0},S.defaultRoutes={backgroundColor:"backgroundColor",borderColor:"borderColor"},e.Chart.register(O,S),t.flatten=n,t.group=r,t.index=s,t.isObject=o,t.sort=a,t.sum=l,Object.defineProperty(t,"__esModule",{value:!0})})); |
{ | ||
"name": "chartjs-chart-treemap", | ||
"version": "1.0.0-beta.4", | ||
"homepage": "https://chartjs-chart-treemap.pages.dev/", | ||
"version": "1.0.0", | ||
"description": "Chart.js module for creating treemap charts", | ||
"main": "dist/chartjs-chart-treemap.js", | ||
"module": "dist/chartjs-chart-treemap.esm.js", | ||
"types": "types/index.esm.d.ts", | ||
"scripts": { | ||
@@ -11,4 +13,8 @@ "autobuild": "rollup -c -w", | ||
"dev": "karma start --no-signle-run --auto-watch --browsers chrome", | ||
"lint": "eslint --ignore-path .gitignore .", | ||
"lint-fix": "eslint --ignore-path .gitignore --fix .", | ||
"docs": "npm run build && vuepress build docs --no-cache", | ||
"docs:dev": "npm run build && vuepress dev docs --no-cache", | ||
"lint": "concurrently -r \"npm:lint-*\"", | ||
"lint-js": "eslint \"src/**/*.js\" \"test/**/*.js\" \"docs/**/*.js\"", | ||
"lint-md": "eslint \"**/*.md\"", | ||
"lint-types": "eslint \"types/**/*.ts\" && tsc -p types/tests/", | ||
"test": "cross-env NODE_ENV=test concurrently \"npm:test-*\"", | ||
@@ -35,18 +41,21 @@ "test-lint": "npm run lint", | ||
}, | ||
"homepage": "https://github.com/kurkle/chartjs-chart-treemap#readme", | ||
"devDependencies": { | ||
"@rollup/plugin-commonjs": "^17.1.0", | ||
"@rollup/plugin-node-resolve": "^11.2.0", | ||
"chart.js": "^3.0.0-rc.2", | ||
"chartjs-adapter-date-fns": "^1.1.0-beta.1", | ||
"@rollup/plugin-commonjs": "^18.0.0", | ||
"@rollup/plugin-json": "^4.1.0", | ||
"@rollup/plugin-node-resolve": "^11.2.1", | ||
"@typescript-eslint/eslint-plugin": "^4.22.0", | ||
"@typescript-eslint/parser": "^4.22.0", | ||
"chart.js": "^3.1.0", | ||
"chartjs-adapter-date-fns": "^2.0.0", | ||
"chartjs-test-utils": "^0.2.2", | ||
"concurrently": "^6.0.0", | ||
"concurrently": "^6.0.1", | ||
"cross-env": "^7.0.3", | ||
"date-fns": "^2.19.0", | ||
"eslint": "^7.22.0", | ||
"date-fns": "^2.20.2", | ||
"eslint": "^7.24.0", | ||
"eslint-config-chartjs": "^0.3.0", | ||
"eslint-plugin-es": "^4.1.0", | ||
"eslint-plugin-html": "^6.1.2", | ||
"eslint-plugin-markdown": "^2.0.1", | ||
"jasmine-core": "^3.7.1", | ||
"karma": "^6.2.0", | ||
"karma": "^6.3.2", | ||
"karma-chrome-launcher": "^3.1.0", | ||
@@ -61,10 +70,16 @@ "karma-coverage": "^2.0.3", | ||
"pixelmatch": "^5.2.1", | ||
"rollup": "^2.42.1", | ||
"rollup": "^2.45.1", | ||
"rollup-plugin-analyzer": "^4.0.0", | ||
"rollup-plugin-istanbul": "^3.0.0", | ||
"rollup-plugin-terser": "^7.0.2" | ||
"rollup-plugin-terser": "^7.0.2", | ||
"typescript": "^4.2.4", | ||
"vuepress": "^1.8.2", | ||
"vuepress-plugin-flexsearch": "^0.1.0", | ||
"vuepress-plugin-redirect": "^1.2.5", | ||
"vuepress-theme-chartjs": "^0.2.0" | ||
}, | ||
"peerDependencies": { | ||
"chart.js": "^3.0.0-beta.10" | ||
"chart.js": "^3.0.0" | ||
}, | ||
"dependencies": {} | ||
} |
# chartjs-chart-treemap | ||
[Chart.js](https://www.chartjs.org/) **v3.0.0-beta.10** module for creating treemap charts. Implementation for Chart.js v2 is in [2.x branch](https://github.com/kurkle/chartjs-chart-treemap/tree/2.x) | ||
[Chart.js](https://www.chartjs.org/) **v3.0.0** module for creating treemap charts. Implementation for Chart.js v2 is in [2.x branch](https://github.com/kurkle/chartjs-chart-treemap/tree/2.x) | ||
@@ -8,67 +8,5 @@ [![npm](https://img.shields.io/npm/v/chartjs-chart-treemap.svg)](https://www.npmjs.com/package/chartjs-chart-matrix) | ||
![npm bundle size](https://img.shields.io/bundlephobia/min/chartjs-chart-treemap.svg) | ||
[![documentation](https://img.shields.io/static/v1?message=Documentation&color=informational)](https://chartjs-chart-treemap.pages.dev) | ||
![GitHub](https://img.shields.io/github/license/kurkle/chartjs-chart-treemap.svg) | ||
## Documentation | ||
To create a treemap chart, include chartjs-chart-treemap.js after chart.js and then create the chart by setting the `type` attribute to `'treemap'` | ||
```js | ||
new Chart(ctx, { | ||
type: 'treemap', | ||
tree: dataObject, | ||
key: 'value', | ||
groups: ['main', 'sub'] | ||
}); | ||
``` | ||
## Configuration | ||
Tree data should be provided in `tree` property of dataset. `data` is then automatically build. `key` defines the key name in data objects to use for value. `groups` array can be provided to display multiple levels of hierarchy. | ||
Data is summarized to groups internally. | ||
```js | ||
new Chart(ctx, { | ||
type: 'treemap', | ||
data: { | ||
datasets: [{ | ||
label: 'Basic treemap', | ||
tree: [6,6,5,4,3,2,2,1], | ||
font: { | ||
color: '#000', | ||
family: 'serif', | ||
size: 12, | ||
style: 'normal', | ||
}, | ||
backgroundColor: function(ctx) { | ||
var value = ctx.dataset.data[ctx.dataIndex]; | ||
var alpha = (value + 3) / 10; | ||
return Color('blue').alpha(alpha).rgbString(); | ||
}, | ||
rtl: false // control in which direction the squares are positioned | ||
}] | ||
}, | ||
}); | ||
``` | ||
### Note about chartjs-plugin-datalabels | ||
Treemap is not using any scales currently and thats why [chartjs-plugin-datalabels](https://chartjs-plugin-datalabels.netlify.app/) plugin does not work with it. | ||
When other charts are using datalables on the same page, you'll need to disable the plugin for treemap charts: | ||
```js | ||
new Chart(ctx, { | ||
type: 'treemap', | ||
data: (...), | ||
options: { | ||
plugins: { | ||
datalabels: false | ||
} | ||
} | ||
}); | ||
``` | ||
## Example | ||
[Live examples @codepen.io](https://codepen.io/kurkle/full/oNjXJwe) | ||
![TreeMap Example Image](treemap.png) | ||
@@ -75,0 +13,0 @@ |
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
No v1
QualityPackage is not semver >=1. This means it is not stable and does not support ^ ranges.
Found 1 instance in 1 package
53808
1484
1
36
34