{"version":3,"file":"planCanvas.module.mjs","names":[],"sources":["../../../../package/common/planCanvas/planCanvas.module.pcss"],"sourcesContent":["/**\n * Every colour comes from a theme variable. The wall fill/outline pair in particular\n * must stay two distinct surfaces, or the two-pass stroke has nothing to reveal.\n */\n\n.planCanvas {\n  /*\n   * The wall body and its edge, resolved once: the outline pass, the caps and the jamb\n   * faces are the same edge of the same object and must not drift apart. Both mix towards\n   * the canvas rather than sitting at the text colour, so a wall reads as mass on the\n   * floor instead of as ink drawn over it. `--plan-wall-outline` and `--plan-wall-fill`\n   * are still the knobs a consumer sets.\n   */\n  --plan-wall-edge-resolved: var(--plan-wall-outline, color-mix(in oklab, var(--text-color) 38%, var(--background)));\n  --plan-wall-fill-resolved: var(--plan-wall-fill, color-mix(in oklab, var(--text-color) 58%, var(--background)));\n\n  display: block;\n  touch-action: none;\n  user-select: none;\n  background: var(--plan-canvas-background, var(--background));\n\n  &-screen {\n    pointer-events: none;\n  }\n\n  /* The storey below, for lining walls up between floors. Faint and dashed so it reads\n     as a tracing under the drawing rather than as part of it, and never picks up a\n     pointer: it is not this floor's geometry. */\n  &-underlay {\n    pointer-events: none;\n\n    line {\n      stroke: var(--plan-underlay-color, var(--text-dark));\n      opacity: 0.28;\n      stroke-dasharray: 6 5;\n      stroke-linecap: round;\n      vector-effect: non-scaling-stroke;\n    }\n  }\n\n  &-grid {\n    pointer-events: none;\n\n    line {\n      stroke: var(--plan-grid-color, var(--text-color));\n      opacity: 0.1;\n    }\n  }\n\n  /* ── Rooms ── */\n\n  &-rooms {\n    pointer-events: auto;\n  }\n\n  &-roomFill {\n    fill: var(--plan-room-fill, var(--background-accent));\n    stroke: none;\n    transition:\n      fill 0.12s ease-out,\n      opacity 0.12s ease-out;\n\n    &-interactive {\n      cursor: pointer;\n      -webkit-tap-highlight-color: transparent;\n\n      &:focus-visible {\n        outline: none;\n        stroke: var(--focus-border-color, var(--primary-color));\n        stroke-width: 2;\n        vector-effect: non-scaling-stroke;\n      }\n    }\n\n    /* Hover tints the floor, selection colours the walls: two channels, so both can be\n       read at once. A fill answers \"which room\" instantly, where a shared wall is\n       ambiguous between the rooms either side of it. */\n    &-hovered {\n      fill: var(--plan-room-fill-hover, var(--background-accent-light));\n    }\n  }\n\n  &-roomLabel {\n    pointer-events: none;\n  }\n\n  &-roomName {\n    fill: var(--text-color);\n    font-size: 13px;\n    font-weight: 600;\n\n    /* A halo, so a label stays legible over any room colour a consumer sets. */\n    paint-order: stroke;\n    stroke: var(--background);\n    stroke-width: 3px;\n    stroke-linejoin: round;\n  }\n\n  &-roomArea {\n    fill: var(--text-dark);\n    font-size: 11px;\n    paint-order: stroke;\n    stroke: var(--background);\n    stroke-width: 3px;\n    stroke-linejoin: round;\n  }\n\n  /* ── Walls ── */\n\n  &-walls {\n    pointer-events: none;\n  }\n\n  /*\n   * Round joins, so the outer corners of the building come out softened and an acute\n   * corner cannot fire a mitre spike out of the junction at all. `--plan-wall-join: miter`\n   * restores the drafting corner, and `--plan-wall-miter-limit` then caps how far the\n   * spike may run. The selection highlight shares the rule: it is drawn from the same\n   * geometry over the same walls, so a different join would leave crescents showing.\n   */\n  &-wallOutline path,\n  &-wallFill path,\n  &-roomEdgeSelected path {\n    fill: none;\n    stroke-linecap: butt;\n    stroke-linejoin: var(--plan-wall-join, round);\n    stroke-miterlimit: var(--plan-wall-miter-limit, 4);\n  }\n\n  &-wallOutline path {\n    stroke: var(--plan-wall-edge-resolved);\n  }\n\n  /* Must match the outline pass exactly: the two are the same shape, and the visible\n     outline is what is left of the first after this one covers its middle. */\n  &-wallFill path {\n    stroke: var(--plan-wall-fill-resolved);\n  }\n\n  &-wallCaps line {\n    stroke: var(--plan-wall-edge-resolved);\n    stroke-linecap: butt;\n  }\n\n  /* Drawn from the same geometry as the walls, so it inherits their corners and their\n     gaps at doors. */\n  &-roomEdgeCaps line {\n    stroke: var(--plan-room-edge-selected, var(--primary-color));\n    stroke-linecap: butt;\n  }\n\n  /* Edge darker than body, so the wall keeps the crisp outline every other wall has\n     rather than turning into a flat slab, and reads as one highlighted object. */\n  &-roomEdgeSelected {\n    .planCanvas-roomEdgeOutline {\n      stroke: var(--plan-room-edge-selected, var(--primary-color));\n    }\n\n    .planCanvas-roomEdgeFill {\n      stroke: var(--plan-room-edge-selected-fill, var(--primary-lighter));\n    }\n  }\n\n  &-wallSelected {\n    stroke: var(--primary-color);\n    opacity: 0.45;\n    stroke-linecap: butt;\n  }\n\n  &-wallHovered {\n    stroke: var(--primary-lighter);\n    opacity: 0.35;\n    stroke-linecap: butt;\n  }\n\n  /* ── Openings ── */\n\n  &-openings {\n    pointer-events: auto;\n  }\n\n  &-opening {\n    /*\n     * State lives on the group so the whole symbol responds, not just the box drawn round\n     * it by `-outline`: a door reads as selected when its leaf and swing do, the way the\n     * room fill does, rather than by acquiring a rectangle.\n     */\n    &-selected {\n      .planCanvas-doorLeaf,\n      .planCanvas-doorSwing,\n      .planCanvas-windowPane {\n        stroke: var(--primary-color);\n      }\n\n      .planCanvas-doorSwing {\n        opacity: 0.9;\n      }\n    }\n\n    &-hovered {\n      .planCanvas-doorLeaf,\n      .planCanvas-doorSwing,\n      .planCanvas-windowPane {\n        stroke: var(--primary-lighter, var(--primary-color));\n      }\n    }\n\n    &-hit {\n      fill: transparent;\n      stroke: none;\n      pointer-events: none;\n\n      &-interactive {\n        pointer-events: auto;\n        cursor: pointer;\n        -webkit-tap-highlight-color: transparent;\n      }\n    }\n\n    &-outline {\n      fill: none;\n      stroke: var(--primary-color);\n      stroke-width: 2;\n    }\n  }\n\n  /* The wall seen in section, so it takes the body colour rather than the edge one: at a\n     doorway it is the only thing standing for the wall, and the edge tone disappears. */\n  &-jamb {\n    stroke: var(--plan-wall-fill-resolved);\n    stroke-linecap: butt;\n\n    &-highlighted {\n      stroke: var(--plan-room-edge-selected, var(--primary-color));\n    }\n  }\n\n  &-doorLeaf {\n    fill: none;\n    stroke: var(--plan-door-color, var(--text-dark));\n    stroke-linecap: butt;\n  }\n\n  &-doorSwing {\n    fill: none;\n    stroke: var(--plan-door-color, var(--text-dark));\n    stroke-dasharray: 6 4;\n    opacity: 0.6;\n  }\n\n  &-windowPane {\n    stroke: var(--plan-window-color, var(--info-color));\n    stroke-linecap: butt;\n  }\n\n  &-selection {\n    pointer-events: none;\n  }\n}\n"],"mappings":""}