import {
  colorDelta,
  getInterpolatedDomainRange,
  removeOutliers
} from "./chunk-SA7APTJR.js";
import {
  copyMerge
} from "./chunk-M3J4MINX.js";
import {
  dtcnv
} from "./chunk-4UWS5Y3N.js";
import {
  Blues_default,
  Reds_default
} from "./chunk-KSGA62R2.js";
import {
  axisBottom,
  axisLeft,
  axisRight,
  axisTop
} from "./chunk-LOZEKOES.js";
import {
  linear
} from "./chunk-OAWQ6LOO.js";
import {
  roundValueAuto
} from "./chunk-TLT4YIG3.js";
import {
  __export
} from "./chunk-HFNDKYVF.js";

// plots/matrix/matrix.layout.js
var matrix_layout_exports = {};
__export(matrix_layout_exports, {
  getMaxGrpLabelWidth: () => getMaxGrpLabelWidth,
  setAutoDimensions: () => setAutoDimensions,
  setLabelsAndScales: () => setLabelsAndScales,
  setLayout: () => setLayout
});
var MINCOLWSPACED = 7;
function setAutoDimensions(xOffset) {
  const m = this.state.config.settings.matrix;
  if (!this.autoDimensions) this.autoDimensions = /* @__PURE__ */ new Set();
  if (!m.colw) this.autoDimensions.add("colw");
  else this.autoDimensions.delete("colw");
  if (!m.rowh) this.autoDimensions.add("rowh");
  else this.autoDimensions.delete("rowh");
  const s = this.settings.matrix;
  this.computedSettings = {
    useCanvas: this.sampleOrder.length > m.svgCanvasSwitch
  };
  if (s.availContentWidth) {
    this.availContentWidth = s.availContentWidth;
  } else {
    let boundingWidth = this.dom.contentNode.getBoundingClientRect().width;
    if (boundingWidth < 600) {
      boundingWidth = window.document.body.clientWidth;
    }
    const maxGrpLabelWidth = this.getMaxGrpLabelWidth();
    const padding = Math.max(65, maxGrpLabelWidth);
    const hcw = this.state.config.settings.hierCluster?.xDendrogramHeight || 0;
    this.availContentWidth = boundingWidth - padding - s.margin.right - xOffset - hcw;
  }
  let colwSpaced, colwNoSpace;
  if (this.autoDimensions.has("colw")) {
    const totalColgspace = s.colgspace * Math.max(0, this.visibleSampleGrps.size - 1);
    const tentativeGaps = this.sampleOrder.length * s.colspace + totalColgspace;
    const spacedColw = (this.availContentWidth - tentativeGaps) / this.sampleOrder.length;
    const constrainedMINCOLWSPACED = Math.max(s.colwMin, Math.min(MINCOLWSPACED, s.colwMax));
    colwSpaced = Math.max(constrainedMINCOLWSPACED, Math.min(spacedColw, s.colwMax));
    const noSpacedColw = (this.availContentWidth - totalColgspace) / this.sampleOrder.length;
    colwNoSpace = Math.max(s.colwMin, Math.min(noSpacedColw, s.colwMax));
    this.computedSettings.colw = colwSpaced <= MINCOLWSPACED ? colwNoSpace : colwSpaced;
    this.computedSettings.zoomMin = s.colwMin / this.computedSettings.colw;
    this.computedSettings.zoomMax = s.colwMax / this.computedSettings.colw;
  } else {
    colwSpaced = m.colw;
    colNoSpace = m.colw;
    this.computedSettings.colw = m.colw;
    this.computedSettings.zoomMin = s.colwMin / m.colw;
    this.computedSettings.zoomMax = s.colwMax / m.colw;
  }
  const { colw } = this.computedSettings;
  this.computedSettings.colspace = colw === colwNoSpace && colwSpaced < colwNoSpace || colw * s.zoomLevel < MINCOLWSPACED ? 0 : s.colspace;
  const hch = this.state.config.settings.hierCluster?.yDendrogramHeight || 0;
  const availHeight = s.availContentHeight || screen.availHeight - hch;
  this.computedSettings.clusterRowh = Math.min(
    s.rowhMax,
    Math.max(s.rowhMin, Math.floor(availHeight / this.numClusterTerms))
  );
  copyMerge(this.settings.matrix, this.computedSettings);
}
function getMaxGrpLabelWidth() {
  const s = this.settings.matrix;
  const g = this.dom.svg.append("g").attr("opacity", 0.01);
  let maxWidth = 0;
  for (const grp of this.termGroups) {
    const grpLabel = !grp.name ? "" : grp.name.length <= s.termGrpLabelMaxChars ? grp.name : grp.name.slice(0, s.termGrpLabelMaxChars) + "\u2026";
    const text = g.append("text").text(grpLabel).attr("font-size", 12);
    const box = text.node().getBBox();
    if (maxWidth < box.width) maxWidth = box.width;
  }
  g.remove();
  return maxWidth;
}
function setLabelsAndScales() {
  const s = this.settings.matrix;
  this.cnvValues = [];
  const ht = s.transpose ? s.colw : s.rowh;
  const grpTotals = {};
  const processedLabels = { sampleGrpByName: {}, termGrpByName: {} };
  let totalHtAdjustments = 0;
  for (const t of this.termOrder) {
    const countedSamples = /* @__PURE__ */ new Set();
    t.counts = { samples: 0, hits: 0 };
    const renderedContinuousVs = [];
    let hasMixedValues = false;
    if (t.tw.term.type == "termCollection") {
      t.counts.minval = 0;
      t.counts.maxval = 0;
    }
    t.counts.subGroupCounts = {};
    for (const group of this.sampleGroups) {
      t.counts.subGroupCounts[group.name] = {
        samplesTotal: 0,
        // number of counted (not Blank or WT) samples
        classes: {}
        // number of each class
      };
      if (t.tw.term.type == "geneVariant") {
        t.counts.subGroupCounts[group.name].samplesNotTested = 0;
      }
    }
    if (!processedLabels.termGrpByName[t.grp.name || ""]) {
      const name = t.grp.name || "";
      t.grp.label = name.length <= s.termGrpLabelMaxChars ? name : name.slice(0, s.termGrpLabelMaxChars) + "\u2026";
      processedLabels.termGrpByName[name] = t.grp.label;
    }
    for (const sample of this.sampleOrder) {
      if (countedSamples.has(sample.row.sample)) continue;
      const name = sample.grp.name || "";
      if (!(name in processedLabels.sampleGrpByName)) {
        sample.grp.label = name.length <= s.sampleGrpLabelMaxChars ? name : name.slice(0, s.sampleGrpLabelMaxChars) + "\u2026";
        if (this.config.divideBy) sample.grp.label += ` (${sample.grp.lst.length})`;
        processedLabels.sampleGrpByName[name] = sample.grp.label;
      }
      const sampleName = sample.row._ref_.label || "";
      sample.label = sampleName.length <= s.collabelmaxchars ? sampleName : sampleName.slice(0, s.collabelmaxchars) + "\u2026";
      const anno = sample.row[t.tw.$id];
      if (!anno) continue;
      if (t.tw.term.type == "termCollection" && anno.hasMixedValues) {
        hasMixedValues = true;
      }
      if (t.tw.term.type == "termCollection" && anno.values) {
        for (const val of anno.values) {
          const pct = val.value;
          if (pct > 0) {
            const cumSum = val.pre_val_sum + pct;
            if (!("maxval" in t.counts) || t.counts.maxval < cumSum) {
              t.counts.maxval = cumSum;
            }
          } else if (pct < 0) {
            const cumSum = val.pre_val_sum + pct;
            if (!("minval" in t.counts) || t.counts.minval > cumSum) {
              t.counts.minval = cumSum;
            }
          }
        }
      }
      const { filteredValues, countedValues, renderedValues } = this.classifyValues(
        anno,
        t.tw,
        t.grp,
        this.settings.matrix,
        sample.row
      );
      anno.filteredValues = filteredValues;
      anno.countedValues = countedValues;
      anno.renderedValues = renderedValues;
      if (anno.countedValues?.length) {
        t.counts.samples += 1;
        t.counts.hits += anno.countedValues.length;
        if (t.tw.q?.mode == "continuous") {
          const v = anno.value;
          if (!t.tw.term.values?.[v]?.uncomputable) {
            if (!("minval" in t.counts) || t.counts.minval > v) t.counts.minval = v;
            if (!("maxval" in t.counts) || t.counts.maxval < v) t.counts.maxval = v;
          }
        }
        if (t.tw.term.type == "geneVariant" && anno.values) {
          for (const val of anno.values) {
            if (val.dt == dtcnv && "value" in val && !s.ignoreCnvValues) {
              const v = val.value;
              this.cnvValues.push(v);
            }
          }
        }
      }
      if (t.tw.q?.mode == "continuous" && renderedValues?.length && t.grp.type != "hierCluster") {
        renderedContinuousVs.push(
          t.tw.term.valueConversion ? t.tw.term.valueConversion.scaleFactor * (renderedValues[0].value || renderedValues[0]) : renderedValues[0].value || renderedValues[0]
        );
      }
      const subGroup = t.counts.subGroupCounts?.[sample.grp.name];
      const countedValuesNoSkip = anno.filteredValues.filter((v) => {
        if (t.tw.term.type == "geneVariant") {
          if (v.class == "WT" || v.class == "Blank") return false;
        }
        return true;
      });
      if (countedValuesNoSkip.length) {
        if (t.tw.term.type == "geneVariant") {
          let sampleCounted = false;
          for (const countedValue of countedValuesNoSkip) {
            if (s.geneVariantCountSamplesSkipMclass.includes(countedValue.class)) {
              if (!subGroup.notTestedClasses) subGroup.notTestedClasses = {};
              if (!(countedValue.class in subGroup.notTestedClasses)) subGroup.notTestedClasses[countedValue.class] = 1;
              else subGroup.notTestedClasses[countedValue.class] += 1;
            } else if (!(countedValue.class in subGroup.classes)) {
              if (!sampleCounted) {
                subGroup.samplesTotal += 1;
                sampleCounted = true;
              }
              subGroup.classes[countedValue.class] = 1;
            } else {
              if (!sampleCounted) {
                subGroup.samplesTotal += 1;
                sampleCounted = true;
              }
              subGroup.classes[countedValue.class] += 1;
            }
          }
        } else {
          subGroup.samplesTotal += 1;
          for (const countedValue of countedValuesNoSkip) {
            if (!(countedValue in subGroup.classes)) subGroup.classes[countedValue] = 1;
            else subGroup.classes[countedValue] += 1;
          }
        }
      }
      if (anno.filteredValues?.length && t.tw.term.type == "geneVariant") {
        const notTested = anno.filteredValues.every((v) => v.class == "Blank");
        if (notTested) {
          subGroup.samplesNotTested += 1;
        }
      }
    }
    if (t.tw.label) {
      t.label = t.tw.label;
    } else if (t.grp.type == "hierCluster") {
      t.label = t.tw.term.gene || t.tw.term.name;
    } else {
      t.label = t.tw.term.name;
    }
    if (t.label.length > s.rowlabelmaxchars) t.label = t.label.slice(0, s.rowlabelmaxchars - 1) + "\u2026";
    const termGroupName = this.config?.settings.hierCluster?.termGroupName;
    if (s.samplecount4gene && t.tw.term.type.startsWith("gene") && (!termGroupName || t.grp.name !== termGroupName)) {
      const count = s.samplecount4gene === "abs" ? t.counts.samples : (100 * t.counts.samples / this.sampleOrder.length).toFixed(1) + "%";
      t.label = `${t.label} (${count})`;
    }
    const twSpecificSettings = this.config.settings.matrix.twSpecificSettings;
    if (!twSpecificSettings[t.tw.$id]) twSpecificSettings[t.tw.$id] = {};
    const twSettings = twSpecificSettings[t.tw.$id];
    if (t.grp.type !== "hierCluster" && t.tw.q?.mode == "continuous") {
      const vc = t.tw.term.valueConversion;
      if (vc) {
        t.counts.minval *= vc.scaleFactor;
        t.counts.maxval *= vc.scaleFactor;
      }
      if (renderedContinuousVs.length && t.tw.q.convert2ZScore) {
        const mean = renderedContinuousVs.reduce((acc, val) => acc + val, 0) / renderedContinuousVs.length;
        const std = Math.sqrt(
          renderedContinuousVs.reduce((acc, val) => acc + Math.pow(val - mean, 2), 0) / renderedContinuousVs.length
        );
        t.mean = mean;
        t.std = std;
        t.counts.minval = (t.counts.minval - mean) / std;
        t.counts.maxval = (t.counts.maxval - mean) / std;
      }
      if (!twSettings.contBarH) twSettings.contBarH = t.tw.term.type == "termCollection" ? 150 : s.barh;
      if (!("gap" in twSettings)) twSettings.contBarGap = 4;
      const barh = twSettings.contBarH;
      if (t.tw.term.type == "termCollection") {
        if (!("minval" in t.counts)) t.counts.minval = 0;
        if (!("maxval" in t.counts)) t.counts.maxval = 0;
      }
      const absMin = Math.abs(t.counts.minval);
      const rangeSpansZero = t.counts.minval < 0 && t.counts.maxval > 0;
      const ratio = t.counts.minval >= 0 ? 1 : t.counts.maxval / (absMin + t.counts.maxval);
      t.counts.posMaxHt = ratio * barh;
      const tickValues = [t.counts.maxval, t.counts.minval];
      t.scales = {
        tickValues,
        full: linear().domain(tickValues).range([1, barh])
      };
      if (t.counts.maxval >= 0) {
        const domainMin = rangeSpansZero ? 0 : t.counts.minval;
        t.scales.pos = linear().domain([domainMin, t.counts.maxval]).range([1, t.counts.posMaxHt]);
      }
      if (t.counts.minval < 0) {
        const domainMax = rangeSpansZero ? 0 : t.counts.maxval;
        t.scales.neg = linear().domain([domainMax, t.counts.minval]).range([1, barh - t.counts.posMaxHt]);
      }
    }
    t.totalHtAdjustments = totalHtAdjustments;
    t.rowHt = t.grp.type == "hierCluster" ? s.clusterRowh : twSettings.contBarH && t.tw.q?.mode == "continuous" ? twSettings.contBarH + 2 * twSettings.contBarGap : ht;
    const adjustment = t.rowHt - ht - (t.grp.type == "hierCluster" ? s.rowspace : 0);
    totalHtAdjustments += adjustment;
    t.cumulativeAdjustment = totalHtAdjustments;
    if (!(t.visibleGrpIndex in grpTotals)) grpTotals[t.visibleGrpIndex] = { htAdjustment: 0 };
    grpTotals[t.visibleGrpIndex].htAdjustment += adjustment;
    t.grpTotals = grpTotals[t.visibleGrpIndex];
  }
  let cnvLegendDomainRange;
  if (this.cnvValues.length) {
    if (s.cnvValues.cutoffMode == "fixed") {
      this.cnvValues = this.cnvValues.filter((v) => v >= s.cnvValues.min && v <= s.cnvValues.max).sort((a, b) => a - b);
      if (this.cnvValues[0] != s.cnvValues.min) this.cnvValues.unshift(s.cnvValues.min);
      if (this.cnvValues[this.cnvValues.length - 1] != s.cnvValues.max) this.cnvValues.push(s.cnvValues.max);
    } else if (s.cnvValues.cutoffMode == "percentile" || s.cnvValues.cutoffMode == "auto") {
      let maxPercentile = s.cnvValues.cutoffMode == "auto" ? s.cnvValues.defaultPercentile : s.cnvValues.percentile;
      maxPercentile = maxPercentile / 100;
      const minPercentile = roundValueAuto(1 - maxPercentile);
      this.cnvValues = removeOutliers(this.cnvValues, { minPercentile, maxPercentile, baseValue: 0 });
    } else throw new Error(`Invalid cnvValues cutoffMode: ${s.cnvValues.cutoffMode}`);
    const minLoss = this.cnvValues[0] <= 0 ? this.cnvValues[0] : void 0;
    const maxGain = this.cnvValues[this.cnvValues.length - 1] >= 0 ? this.cnvValues[this.cnvValues.length - 1] : void 0;
    let maxLoss, minGain, absMax;
    for (const n of this.cnvValues) {
      if (n < 0) maxLoss = n;
      if (!minGain && n > 0) {
        minGain = n;
        break;
      }
    }
    for (const t of this.termOrder) {
      if (t.tw.term.type == "geneVariant") {
        if (!cnvLegendDomainRange) {
          const loss0color = Blues_default(0);
          const gain0color = Reds_default(0);
          const colorDiff = colorDelta(loss0color, gain0color);
          if (minLoss !== void 0 && maxGain !== void 0 && colorDiff > 25)
            console.warn(
              `CNV loss and gain do not have the same middle color for value=0'${loss0color}' vs '${gain0color}', color difference=${colorDiff}`
            );
          absMax = minLoss !== void 0 && maxGain !== void 0 ? Math.max(Math.abs(minLoss), maxGain) : minLoss !== void 0 ? Math.abs(minLoss) : maxGain;
          cnvLegendDomainRange = getInterpolatedDomainRange({
            absMin: 0,
            absMax,
            totalNumSteps: 10,
            negInterpolator: minLoss !== void 0 && Blues_default,
            posInterpolator: maxGain !== void 0 && Reds_default,
            // force this middleColor to white, knowing that interpolateBlues and interpolateReds,
            // as hardcoded above and below, share similar white colors for their minimum abs values
            middleColor: "white"
          });
        }
        t.scales = {
          loss: Blues_default,
          gain: Reds_default,
          maxLoss,
          maxGain,
          minLoss,
          minGain,
          absMax,
          legend: cnvLegendDomainRange
        };
      }
    }
  }
}
function setLayout() {
  const s = this.settings.matrix;
  const [col, row] = !s.transpose ? ["sample", "term"] : ["term", "sample"];
  const [_t_, _b_] = s.collabelpos == "top" ? ["", "Grp"] : ["Grp", ""];
  const [_l_, _r_] = s.rowlabelpos == "left" ? ["", "Grp"] : ["Grp", ""];
  const top = col + _t_;
  const btm = col + _b_;
  const left = row + _l_;
  const right = row + _r_;
  this.samples = this.sampleOrder;
  this.sampleGrps = this.sampleOrder.filter((s2) => s2.index === 0);
  this.terms = this.termOrder;
  this.termGrps = this.termOrder.filter((t) => t.index === 0);
  const layout = {};
  const sides = { top, btm, left, right };
  for (const direction in sides) {
    const d = sides[direction];
    const Direction = direction[0].toUpperCase() + direction.slice(1);
    layout[direction] = {
      prefix: d,
      data: this[`${d}s`],
      offset: s[`${d}LabelOffset`],
      box: this.dom[`${d}LabelG`],
      key: this[`${d}Key`],
      label: this[`${d}Label`],
      render: this[`render${Direction}Label`],
      isGroup: sides[direction].includes("Grp")
    };
  }
  const yOffset = layout.top.offset + s.margin.top + s.scrollHeight;
  const xOffset = layout.left.offset + s.margin.left;
  this.setAutoDimensions(xOffset);
  this.setLabelsAndScales();
  const colw = Math.max(s.colwMin, Math.min(s.colwMax, s.colw * s.zoomLevel));
  const dx = colw + s.colspace;
  const nx = this[`${col}s`].length;
  const dy = s.rowh + s.rowspace;
  const ny = this[`${row}s`].length;
  const mainwByColDimensions = nx * (colw + s.colspace) + this[`${col}Grps`].length * s.colgspace + (this[`${col}s`].slice(-1)[0]?.totalHtAdjustments || 0);
  const mainw = Math.min(mainwByColDimensions, this.availContentWidth);
  const lastRow = this[`${row}s`].slice(-1)[0];
  const mainh = ny * dy + (this[`${row}Grps`].length - 1) * s.rowgspace + (lastRow?.cumulativeAdjustment || 0);
  const colLabelFontSize = Math.min(
    Math.max(colw + s.colspace - 2 * s.collabelpad - s.colspace, s.minLabelFontSize),
    s.maxLabelFontSize
  );
  const topFontSize = _t_ == "Grp" ? s.grpLabelFontSize : colLabelFontSize;
  layout.top.attr = {
    boxTransform: `translate(${xOffset}, ${yOffset - s.collabelgap})`,
    adjustBoxTransform: (dx2) => layout.top.box.attr("transform", `translate(${xOffset + dx2}, ${yOffset - s.collabelgap})`),
    labelTransform: "rotate(-90)",
    labelAnchor: "start",
    labelGY: 0,
    labelGTransform: this[`col${_t_}LabelGTransform`],
    fontSize: topFontSize,
    textpos: { coord: "y", factor: -1 },
    axisFxn: axisTop
  };
  if (layout.top.prefix == "sample")
    layout.top.display = s.sampleLabelsToggle !== "hide" && colw >= s.minLabelFontSize ? "" : "none";
  const btmFontSize = _b_ == "Grp" ? s.grpLabelFontSize : colLabelFontSize;
  layout.btm.attr = {
    boxTransform: `translate(${xOffset}, ${yOffset + mainh + s.collabelgap})`,
    adjustBoxTransform: (dx2) => layout.btm.box.attr("transform", `translate(${xOffset + dx2}, ${yOffset + mainh + s.collabelgap})`),
    labelTransform: "rotate(-90)",
    labelAnchor: "end",
    labelGY: 0,
    labelGTransform: this[`col${_b_}LabelGTransform`],
    fontSize: btmFontSize,
    textpos: { coord: "y", factor: 1 },
    axisFxn: axisBottom
  };
  if (layout.btm.prefix == "sample")
    layout.btm.display = s.sampleLabelsToggle !== "hide" && colw >= s.minLabelFontSize ? "" : "none";
  const leftFontSize = _l_ == "Grp" ? s.grpLabelFontSize : Math.max(s.rowh + s.rowspace - 2 * s.rowlabelpad - s.rowspace, s.minLabelFontSize);
  layout.left.attr = {
    boxTransform: `translate(${xOffset - s.rowlabelgap}, ${yOffset})`,
    labelTransform: "",
    labelAnchor: "end",
    labelGX: 0,
    labelGTransform: this[`row${_l_}LabelGTransform`],
    fontSize: leftFontSize,
    textpos: { coord: "x", factor: -1 },
    axisFxn: axisLeft
  };
  const rtFontSize = _r_ == "Grp" ? s.grpLabelFontSize : Math.max(s.rowh + s.rowspace - 2 * s.rowlabelpad, s.minLabelFontSize);
  layout.right.attr = {
    boxTransform: `translate(${xOffset + mainw + s.rowlabelgap}, ${yOffset})`,
    labelTransform: "",
    labelAnchor: "start",
    labelGX: 0,
    labelGTransform: this[`row${_r_}LabelGTransform`],
    fontSize: rtFontSize,
    textpos: { coord: "x", factor: 1 },
    axisFxn: axisRight
  };
  this.dom.sampleLabelsPG.attr("clip-path", s.transpose ? "" : `url(#${this.seriesClipId})`);
  this.dom.termLabelsPG.attr("clip-path", s.transpose ? `url(#${this.seriesClipId})` : "");
  this.layout = layout;
  if (!s.zoomCenterPct) {
    s.zoomCenterPct = 0.5;
    s.zoomIndex = Math.round(s.zoomCenterPct * mainw / dx);
    s.zoomGrpIndex = this.sampleOrder[s.zoomIndex]?.grpIndex || 0;
  }
  const zoomCenter = s.zoomCenterPct * mainw;
  const centerCellX = s.zoomIndex * dx + s.zoomGrpIndex * s.colgspace;
  const zoomedMainW = Math.max(0, nx * dx + (this[`${col}Grps`].length - 1) * s.colgspace);
  const seriesXoffset = s.zoomLevel <= 1 && mainw >= zoomedMainW ? 0 : Math.max(zoomCenter - centerCellX, mainw - zoomedMainW);
  const imgW = (s.imgWMax > zoomedMainW ? zoomedMainW : s.imgWMax) - 1e-7;
  const halfImgW = 0.5 * imgW;
  const unwantedRightOvershoot = Math.max(0, centerCellX + halfImgW - zoomedMainW);
  const imgLeftMin = Math.max(0, centerCellX - Math.min(halfImgW, imgW) - unwantedRightOvershoot);
  const xMin = s.zoomLevel <= 1 && mainw >= zoomedMainW ? 0 : imgLeftMin;
  const xMax = imgW + xMin;
  this.dimensions = {
    xMin,
    xMax,
    dx,
    dy,
    xOffset,
    yOffset,
    mainw,
    mainh,
    colw,
    zoomedMainW,
    seriesXoffset: seriesXoffset > 0 ? 0 : seriesXoffset,
    maxMainW: Math.max(mainwByColDimensions, this.availContentWidth),
    imgW,
    // recompute the resolvable "pixel width", in case the pixel ratio changes
    // when moving the browser window to a different monitor,
    // will be used to sharpen canvas shapes that are smaller than this pixel width
    pxw: 1 / window.devicePixelRatio
  };
}

export {
  setAutoDimensions,
  getMaxGrpLabelWidth,
  setLabelsAndScales,
  setLayout,
  matrix_layout_exports
};
//# sourceMappingURL=chunk-36EHIPV4.js.map
