/* Custex editor — shared layout repeat markup (live preview + AI render). */
const { useMemo: uM } = React;

const {
  buildTileMotifsForLayout,
  layoutGroundColor,
  previewVesselPxFromCustomSize,
  layoutNodeIdForAiRender,
} = window.CxMotifPipeline;

function layoutPatternModel(graph, layoutId) {
  const lid = layoutId || 'layout';
  const layout = graph?.nodes?.[lid]?.data || { tile: 'grid', scale: 60, rotate: 0 };
  const tilePlan = (window.CxLayoutTiles?.plan || (() => ({
    cols: 3,
    rows: 3,
    count: 9,
    cellStyle: () => ({}),
  })))(layout.tile || 'grid');
  const tileMotifs = buildTileMotifsForLayout(graph, lid);
  const ground = layoutGroundColor(graph);
  const vesselPx = previewVesselPxFromCustomSize(graph?.nodes?.product?.data?.customSize);
  return { layout, tilePlan, tileMotifs, ground, vesselPx, layoutId: lid };
}

function CxLayoutPatternGrid({ model }) {
  const { layout, tilePlan, tileMotifs } = model;
  const tileMode = (window.CxLayoutTiles?.normalizeTile || ((t) => t))(layout.tile || 'grid');
  return (
    <div
      className={`cx-prev-tile-grid cx-prev-tile-${tileMode}`}
      style={{
        gridTemplateColumns: `repeat(${tilePlan.cols}, 1fr)`,
        gridTemplateRows: `repeat(${tilePlan.rows}, 1fr)`,
        transform: `rotate(${layout.rotate || 0}deg) scale(${(layout.scale || 100) / 100})`,
      }}
    >
      {Array.from({ length: tilePlan.count }).map((_, i) => {
        const col = i % tilePlan.cols;
        const row = Math.floor(i / tilePlan.cols);
        const cellShift = tilePlan.cellStyle(col, row) || {};
        return (
          <div key={i} className="cx-prev-tile" style={cellShift}>
            {tileMotifs.map((tm, j) => (
              <svg
                key={`${i}-${tm.motif.id}-${j}`}
                viewBox="0 0 80 80"
                className="cx-prev-motif"
                preserveAspectRatio="xMidYMid meet"
                dangerouslySetInnerHTML={{ __html: tm.motif?.svg || '' }}
                style={{
                  color: 'rgba(58,47,38,0.72)',
                  transform: `translate(calc(-50% + ${tm.ctl.ox}%), calc(-50% + ${tm.ctl.oy}%)) rotate(${tm.ctl.rotate}deg) scale(${tm.ctl.scale / 100})`,
                }}
              />
            ))}
          </div>
        );
      })}
    </div>
  );
}

function CxLayoutPatternVessel({ graph, layoutId, vesselStyle, className, weaveOverlay, emptyMessage }) {
  const lid = layoutId || 'layout';
  const model = uM(
    () => layoutPatternModel(graph, lid),
    [
      graph,
      lid,
      graph?.nodes?.[lid]?.data?.tile,
      graph?.nodes?.[lid]?.data?.scale,
      graph?.nodes?.[lid]?.data?.rotate,
      JSON.stringify(graph?.nodes?.[lid]?.data?.motifControls || {}),
      graph?.nodes?.product?.data?.customSize?.w,
      graph?.nodes?.product?.data?.customSize?.h,
      graph?.nodes?.product?.data?.customSize?.unit,
      graph?.nodes?.motif?.data?.motifId,
      graph?.nodes?.motif?.data?.generatedImageDataUrl,
      graph?.nodes?.motif?.data?.generatedSvg,
    ]
  );

  if (!model.tileMotifs.length) {
    return emptyMessage ? (
      <div className={`cx-prev-vessel cx-prev-vessel-empty ${className || ''}`} style={vesselStyle}>
        <span className="cx-airender-preview-placeholder">{emptyMessage}</span>
      </div>
    ) : null;
  }

  return (
    <div
      className={`cx-prev-vessel ${className || ''}`}
      style={{ background: model.ground, ...vesselStyle }}
    >
      {weaveOverlay || null}
      <CxLayoutPatternGrid model={model} />
    </div>
  );
}

window.CxLayoutPattern = {
  layoutPatternModel,
  CxLayoutPatternGrid,
  CxLayoutPatternVessel,
  layoutNodeIdForAiRender,
};
