/*
 * gm-ui.css — GMC64 UI stylesheet
 *
 * Include this in every GMC64 editor page for consistent styling.
 *
 * Contains:
 * - C64 font and color palette (reusable for other C64 projects)
 * - GMC64-specific UI components (buttons, popups, file lists, color picker)
 *
 * Pages can add their own overrides in <style> blocks for page-specific items.
 */

/* ==========================================================================
   C64 FONT
   ========================================================================== */

@font-face {
    font-family: C64;
    src: url(fonts/C64_Pro_Mono_Narrow8.woff2);
}

/* Original unscaled font if needed */
@font-face {
    font-family: C64-Wide;
    src: url(fonts/C64_Pro_Mono-STYLE.woff2);
}

/* ==========================================================================
   C64 COLOR PALETTE
   ========================================================================== */

:root {
    /*
     * C64 PALETTE - copied from c64lib.js c64Palette
     * Keep in sync! These are the authoritative VICE RGB values.
     */
    --c64-black:    rgb(0, 0, 0);          /* 0x00 */
    --c64-white:    rgb(255, 255, 255);    /* 0x01 */
    --c64-red:      rgb(169, 71, 100);     /* 0x02 */
    --c64-cyan:     rgb(138, 230, 203);    /* 0x03 */
    --c64-purple:   rgb(154, 88, 185);     /* 0x04 */
    --c64-green:    rgb(114, 189, 103);    /* 0x05 */
    --c64-blue:     rgb(25, 73, 180);      /* 0x06 */
    --c64-yellow:   rgb(255, 248, 141);    /* 0x07 */
    --c64-orange:   rgb(196, 98, 65);      /* 0x08 */
    --c64-brown:    rgb(151, 64, 0);       /* 0x09 */
    --c64-lt-red:   rgb(230, 134, 163);    /* 0x0A */
    --c64-gray1:    rgb(98, 98, 98);       /* 0x0B */
    --c64-gray2:    rgb(148, 148, 148);    /* 0x0C */
    --c64-lt-green: rgb(198, 255, 186);    /* 0x0D */
    --c64-lt-blue:  rgb(98, 145, 251);     /* 0x0E */
    --c64-gray3:    rgb(205, 205, 205);    /* 0x0F */

    /* UI-specific colors */
    --c64-panel-bg:     #2a2a3a;
    --c64-panel-border: #1a1a2a;
    --c64-hover-bg:     #3a3a4a;
    --c64-inactive:     #444444;
    --c64-inactive-text:#888888;
}

/* ==========================================================================
   BASE STYLES
   ========================================================================== */

* {
    box-sizing: border-box;
}

body {
    background: var(--c64-black);
    font-family: C64, monospace;
    font-size: 14px;
    color: var(--c64-gray2);
    -webkit-user-select: none;
    -ms-user-select: none;
    user-select: none;
    cursor: default;
    margin: 0;
    padding: 10px;
}

/* ==========================================================================
   BUTTONS - 3D raised C64 look
   ========================================================================== */

button {
    font-family: inherit;
    font-size: inherit;
    margin: 3px;
    padding: 5px 10px;
    background: var(--c64-gray3);
    color: var(--c64-blue);
    border: 3px solid black;
    border-bottom: 6px solid black;
    border-right: 6px solid black;
    cursor: pointer;
}

button:hover {
    background: var(--c64-white);
}

button:disabled {
    background: var(--c64-gray2);
    color: var(--c64-gray1);
}

button:disabled:hover {
    background: var(--c64-gray2);
}

/* ==========================================================================
   POPUP OVERLAY
   ========================================================================== */

.popup-overlay {
    position: fixed;
    top: 0;
    left: 0;
    width: 100%;
    height: 100%;
    background: rgba(0, 0, 0, 0.7);
    display: flex;
    align-items: center;
    justify-content: center;
    z-index: 1000;
}

/* ==========================================================================
   POPUP DIALOG
   ========================================================================== */

.popup-dialog {
    background: var(--c64-gray1);
    border: 4px solid var(--c64-black);
    padding: 15px;
    min-width: 300px;
    max-width: 500px;
    max-height: 80vh;
    display: flex;
    flex-direction: column;
    position: relative;
}

.gm-disk-dialog {
    width: 600px;
    min-width: 0;
    max-width: 600px;
    /* Let the dialog grow to contain all its children — the parent
       .popup-dialog max-height: 80vh would otherwise clip the file list
       and leave content spilling outside the gray box. */
    max-height: none;
}

.popup-close-x {
    position: absolute;
    top: 4px;
    right: 4px;
    padding: 2px 6px;
    margin: 0;
}

.popup-title {
    color: var(--c64-yellow);
    margin-bottom: 10px;
    text-align: center;
}

.popup-buttons {
    display: flex;
    flex-wrap: wrap;
    margin-bottom: 10px;
}

/* Disk dialog button layout */
.popup-buttons-top,
.popup-buttons-bottom {
    display: flex;
    justify-content: space-between;
    align-items: flex-end;
    margin-bottom: 10px;
}

.popup-buttons-bottom {
    margin-bottom: 0;
    margin-top: 10px;
}

.popup-buttons-left,
.popup-buttons-right {
    display: flex;
    flex-direction: column;
    gap: 2px;
}

.popup-buttons-right {
    align-items: flex-end;
}

/* Horizontal Insert / New / Rename / Eject row at the top of the disk
   dialog. Four buttons compete for limited width — trim per-button
   horizontal padding/margin so labels don't wrap to two lines. */
.gm-disk-disk-row {
    display: flex;
    gap: 4px;
    margin-bottom: 8px;
}
.gm-disk-disk-row button {
    margin: 3px 2px;
    padding: 5px 6px;
}

/* Per-file actions row, sits directly below the file listing. Delete
   anchors the left (destructive — kept away from the constructive
   cluster); Load + filename + Save sit together on the right. */
.gm-disk-file-actions-row {
    display: flex;
    gap: 6px;
    margin-top: 6px;
    margin-bottom: 10px;
}

/* First element of the right cluster — pushes itself + everything after
   to the right edge. */
.gm-disk-actions-right {
    margin-left: auto;
}

/* "Show All File Types" is a secondary list-filter toggle, so it's sized
   a notch smaller than the main popup buttons (font and padding both
   step down) to read as auxiliary rather than primary. */
.gm-disk-show-all {
    font-size: 12px;
    padding: 3px 8px;
}

/* Active state for the show-all toggle — same lt-green fill scene-maker
   uses for its toggleable tool buttons. */
.gm-disk-show-all.active {
    background: var(--c64-lt-green);
}

/* Active state for the top-row prompt buttons (rename / new disk /
   eject) while their prompt is open. White (not lt-green) is
   intentional: these buttons aren't a long-lived toggle state like
   show-all — they're "in this modal mode" indicators that pair with
   the in-message-bar prompt. */
.gm-disk-rename.active,
.gm-disk-blank.active,
.gm-disk-eject.active {
    background: var(--c64-white);
}

/* Non-loadable files shown in "show all" mode — visibly de-emphasised but
   still selectable (so the user can delete them). The Load button stays
   disabled when a dimmed row is selected; only Delete activates. */
.gm-disk-row-dimmed {
    opacity: 0.55;
}

/* Spacer row between type groups in "show all" mode. Just empty vertical
   air — the gap itself is the separator. */
.gm-disk-group-gap {
    height: 8px;
    pointer-events: none;
}
.gm-disk-group-gap td {
    border: none;
    padding: 0;
}

.gm-disk-name-input {
    /* Wider than the 6-char maxlength so the caret and the placeholder
       ("filename") both fit comfortably without clipping. */
    width: 14ch;
    font: inherit;
    text-transform: lowercase;
    padding: 2px 6px;
    background: var(--c64-blue);
    color: var(--c64-white);
    border: 2px solid var(--c64-black);
    outline: none;
}

.gm-disk-name-input::placeholder {
    color: var(--c64-lt-blue);
    opacity: 1;
}

.gm-disk-name-input:focus::placeholder {
    color: transparent;
}

/* Message bar — sits between the save row and the disk-picker info bar.
   Reserves a fixed line of vertical space so prompts/flash messages can
   appear without shifting the layout. */
.gm-disk-message-bar {
    display: flex;
    justify-content: center;
    align-items: center;
    padding: 4px 10px;
    margin-bottom: 8px;
    min-height: 1.4em;
    background: transparent;
    color: var(--c64-black);
}

/* All message-bar prompts share .gm-disk-prompt for layout, color, and
   chip styling. Adding a new prompt is just: drop another <span> with
   .gm-disk-prompt in the message bar — no CSS changes needed. The
   form-style variant (input + actions row stacked) adds the modifier
   class .gm-disk-prompt--form. */
.gm-disk-prompt,
.gm-disk-info-message {
    flex: 1;
    text-align: center;
}
.gm-disk-prompt {
    color: var(--c64-yellow);
}

/* Info messages get a white background pill so error text (red by
   default) reads well against the gray3 popup background. Keeps the
   sibling rule's flex:1 (fills the message bar so the bar's padding
   constrains the pill's width and long messages wrap inside instead of
   running off-screen). */
.gm-disk-info-message:not([hidden]) {
    background: var(--c64-white);
    padding: 2px 6px;
    white-space: normal;
    word-break: break-word;
}
/* When info is visible, let the bar grow vertically for wrapped text
   instead of clipping at the fixed-line min-height. */
.gm-disk-message-bar:has(.gm-disk-info-message:not([hidden])) {
    min-height: 0;
    align-items: stretch;
}

/* Form variant — input on one line, ok/cancel chips below.
   Explicit [hidden] rule because the custom `display: flex` would
   otherwise override hidden's user-agent `display: none`. */
.gm-disk-prompt--form {
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: 6px;
}
.gm-disk-prompt--form[hidden] {
    display: none;
}

/* Inline text input for the name prompt — matches the save-row input
   visually. Filenames are arbitrary user text; case is preserved. */
.gm-disk-name-prompt-input {
    width: 30ch;
    font: inherit;
    padding: 0 4px;
    background: var(--c64-blue);
    color: var(--c64-white);
    border: 2px solid var(--c64-black);
    outline: none;
}

/* Shared yes/no/ok/cancel chip — white on blue with light-blue hover.
   .gm-yes-no covers chips outside the disk popup (e.g. the in-app
   save dialog); .gm-disk-prompt a covers every disk-popup prompt. */
.gm-yes-no,
.gm-disk-prompt a {
    color: var(--c64-white);
    background: var(--c64-blue);
    padding: 0 4px;
    text-decoration: none;
    cursor: pointer;
}
.gm-yes-no:hover,
.gm-disk-prompt a:hover {
    background: var(--c64-lt-blue);
}

/* ==========================================================================
   INFO BAR
   ========================================================================== */

/* Info bar styled as a button — it acts as the disk-picker trigger.
   Matches the standard C64 button look: gray3 bg, blue text, 3D drop-shadow border. */
.info-bar {
    display: flex;
    justify-content: space-between;
    padding: 5px 10px;
    background: var(--c64-gray3);
    color: var(--c64-blue);
    margin-bottom: 10px;
    border: 3px solid var(--c64-black);
    border-bottom: 6px solid var(--c64-black);
    border-right: 6px solid var(--c64-black);
}

.info-bar:hover,
.info-bar:has(.is-interacting) {
    background: var(--c64-white);
}

/* Single-line disk-picker display (resting state) and dropdown items:
   filename on the left, "N blocks free" on the right. */
.gm-disk-name {
    flex: 1;
    display: flex;
    justify-content: space-between;
    cursor: pointer;
}

.gm-disk-filename {
    color: var(--c64-blue);
}

.gm-disk-free {
    color: var(--c64-blue);
}

/* Dropdown items mirror the resting layout */
.gm-disk-item {
    display: flex;
    justify-content: space-between;
    width: 100%;
}

.draggable-dropdown-item .gm-disk-item .gm-disk-filename {
    color: inherit;
}

.draggable-dropdown-item .gm-disk-item .gm-disk-free {
    color: inherit;
    opacity: 0.7;
}

/* ==========================================================================
   DIRECTORY/FILE TABLE
   ========================================================================== */

.file-list-container {
    overflow-y: auto;
    background: var(--c64-blue);
    border: 2px solid var(--c64-black);
    /* Fixed-height listing so popup geometry stays constant regardless of
       file count. 8 row-equivalents tall (header + 7 data rows visible);
       the rest scrolls. Row unit = 3px top + 3px bottom padding + ~1.4em
       line-height. */
    height: calc(8 * (1.4em + 6px));
}

.file-list {
    width: 100%;
    border-collapse: collapse;
    color: var(--c64-lt-blue);
    text-transform: lowercase;
    white-space: pre;
    table-layout: fixed;
}

/* Header row lives INSIDE the scrolling container as a sticky first
   line — uses the same highlight palette as selected rows so the eye
   reads it as part of the listing rather than a separate label.
   Border-bottom (not padding) gives the half-row gap before the first
   data row, so the gap takes the LISTING background color (darker blue)
   rather than extending the header's highlight downward. */
.file-list thead th {
    position: sticky;
    top: 0;
    z-index: 1;
    background: var(--c64-lt-blue);
    color: var(--c64-blue);
    text-align: left;
    font-weight: normal;
    padding: 3px 10px;
    border-bottom: 0.7em solid var(--c64-blue);
}
.file-list .file-list-header-blocks {
    text-align: right;
}

.file-list td {
    padding: 3px 10px;
}

/* Three columns: name 25% / type 25% / blocks 50% right-aligned. Header
   <th> elements share the same widths via the class names below. */
.file-list-header-name,
.file-list td:first-child {
    width: 25%;
}

.file-list-header-type,
.file-list td:nth-child(2) {
    width: 25%;
}

.file-list-header-blocks,
.file-list td:last-child {
    width: 50%;
    text-align: right;
}

.file-list tbody tr {
    cursor: pointer;
}

.file-list tbody tr:hover,
.file-list tbody tr.selected {
    background: var(--c64-lt-blue);
    color: var(--c64-blue);
}

.file-list a {
    color: inherit;
    text-decoration: none;
}

/* Empty state message */
.file-list-empty td {
    text-align: center;
    color: var(--c64-lt-blue);
    padding: 20px 10px;
}

/* ==========================================================================
   COLOR PICKER - 16-color C64 palette picker
   Used by: GMTools.colorPicker (js/gmTools.js)
   Layout: 2 columns x 8 rows (colors 0-7 left, 8-15 right via grid-auto-flow)
   ========================================================================== */

.color-picker-overlay {
    display: none;
    position: fixed;
    top: 0;
    left: 0;
    width: 100%;
    height: 100%;
    background: transparent;
    z-index: 1001;
}

.color-picker-dialog {
    position: absolute;
    background: var(--c64-gray1);
    border: 4px solid var(--c64-black);
    padding: 10px;
}

.color-picker-grid {
    display: grid;
    grid-template-columns: repeat(2, 1fr);
    grid-template-rows: repeat(8, 1fr);
    grid-auto-flow: column;
    gap: 4px;
}

.color-swatch {
    padding: 4px 8px;
    border: 2px solid var(--c64-black);
    cursor: pointer;
    color: var(--c64-black);
    text-align: center;
    white-space: nowrap;
}

.color-swatch:hover {
    border-color: var(--c64-white);
}

/* ==========================================================================
   DRAGGABLE FIELD DROPDOWN
   Used by: GMTools.draggableField (js/gmTools.js)
   Shows when clicking (not dragging) a draggable field
   ========================================================================== */

/* No browser focus ring — we use the .is-interacting class for active feedback */
[data-draggable] { outline: none; }

/* While a draggable is being dragged, suppress hover on the other ones so the
   cursor passing over them during the drag doesn't steal the highlight. */
body.draggable-dragging [data-draggable]:not(.is-interacting) {
    pointer-events: none;
}

.draggable-dropdown-overlay {
    display: none;
    position: fixed;
    top: 0;
    left: 0;
    width: 100%;
    height: 100%;
    background: transparent;
    z-index: 1001;
}

.draggable-dropdown {
    position: absolute;
    background: var(--c64-gray3);
    border: 2px solid var(--c64-black);
    /* Was 80px — bumped to fit color names plus their swatch chip
       comfortably, with one extra ch of right-edge breathing room.
       Item padding alone didn't move the visual edge in practice
       (probably content-width override), so the room is added via
       min-width here. */
    min-width: calc(80px + 3ch);
    max-height: 200px;
    overflow-y: auto;
}

.draggable-dropdown-item {
    padding: 2px 8px;
    color: var(--c64-blue);
    cursor: pointer;
    white-space: nowrap;
}

.draggable-dropdown-item:hover {
    background: var(--c64-gray2);
}

.draggable-dropdown-item.selected {
    background: var(--c64-blue);
    color: var(--c64-white);
}

.draggable-dropdown-item .match-highlight {
    color: var(--c64-black);
}

.draggable-dropdown-item.selected .match-highlight {
    color: var(--c64-yellow);
}

.draggable-dropdown-empty {
    padding: 4px 8px;
    color: var(--c64-red);
    font-style: italic;
}

/* ==========================================================================
   QUIT MENU - Navigation popup for switching between GM tools
   Used by: GMTools.quitMenu (js/gmTools.js)
   ========================================================================== */

.quit-menu-overlay {
    position: fixed;
    top: 0;
    left: 0;
    width: 100%;
    height: 100%;
    background: rgba(0, 0, 0, 0.7);
    display: flex;
    align-items: center;
    justify-content: center;
    z-index: 1001;
}

/* When attached to a tool's #screen container, fit the overlay to that area
   instead of the viewport, and let the layered rings stretch to fill it.
   Opaque black background so nothing underneath bleeds through if the inner
   .quit-menu-outer's layout (flex centering, padding rounding) leaves a
   sliver of the overlay uncovered. The negative inset over-extends by 1px in
   every direction to mask sub-pixel rounding gaps that have shown up at the
   top edge in some layouts. */
.quit-menu-overlay.screen-fit {
    position: absolute;
    background: var(--c64-black);
    z-index: 100;
    top: -1px;
    left: -1px;
    width: calc(100% + 2px);
    height: calc(100% + 2px);
}

.quit-menu-outer {
    background: var(--c64-black);
    padding: 40px;
}

.quit-menu-overlay.screen-fit .quit-menu-outer {
    width: 100%;
    height: 100%;
    box-sizing: border-box;
    padding: 20px;
    display: flex;
    align-items: center;
    justify-content: center;
}

.quit-menu-container {
    background: var(--c64-gray1);
    padding: 100px;
}

.quit-menu-overlay.screen-fit .quit-menu-container {
    width: 100%;
    height: 100%;
    box-sizing: border-box;
    padding: 40px;
    display: flex;
    align-items: center;
    justify-content: center;
}

.quit-menu-box {
    background: var(--c64-gray3);
    border: 3px solid var(--c64-black);
    border-bottom: 6px solid var(--c64-black);
    border-right: 6px solid var(--c64-black);
    padding: 10px 20px;
    display: flex;
    flex-direction: column;
}

.quit-menu-box a {
    color: var(--c64-blue);
    text-decoration: none;
    padding: 3px 8px;
}

.quit-menu-box a:hover {
    color: var(--c64-red);
}
