.page-wrap {
  width: 80%;
  margin: 0 auto;
}

@media (max-width: 640px) {
  .page-wrap {
    width: 95%;
  }
}
.ctn-table-wrap {
    --ctn-ink:        #1F2937;
    --ctn-ink-soft:   #4B5563;
    --ctn-ink-faint:  #9CA3AF;
    --ctn-paper:      #FFFFFF;
    --ctn-bg:         #FAFAF9;
    --ctn-stripe:     #F3F5F7;
    --ctn-hairline:   #E4E7EB;
    --ctn-accent:     #0F4B70;
    --ctn-accent-tint:#C4F8FF;
    --ctn-tag:        #8A93A1;
    --ctn-font-sans:  'IBM Plex Sans', -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif;
    --ctn-font-mono:  'IBM Plex Mono', ui-monospace, SFMono-Regular, Menlo, monospace;
    --ctn-radius:     8px;

    background: var(--ctn-bg);
    border: 1px solid var(--ctn-hairline);
    border-radius: 10px;
    overflow: hidden; /* clips table corners */
  }

  /* -------------------------------------------------------------------
     SCROLLABLE TABLE MODIFIER
     Add  ctn-table-wrap--scroll  alongside  ctn-table-wrap  to enable
     a fixed-height, sticky-header table that fills the available window.

     Usage:
       <div class="ctn-table-wrap ctn-table-wrap--scroll">
         <div class="ctn-table-header">…</div>
         <div class="ctn-table-scroll-body">          document.getElementById("toggleRows") new inner wrapper
           <table class="ctn-table">…</table>
         </div>
         <div class="ctn-table-footer">…</div>
       </div>

     --ctn-scroll-offset controls how much vertical space to reserve for
     chrome above/below the table (toolbar, page header, footer, etc.).
     Override it on the element or in your page styles as needed.
  ------------------------------------------------------------------- */

  .ctn-table-wrap--scroll {
    --ctn-scroll-offset: 180px; /* adjust to match your page's surrounding chrome */
    display: flex;
    flex-direction: column;
    max-height: calc(100vh - var(--ctn-scroll-offset));
    overflow: hidden; /* the inner scroll body handles overflow */
  }

  /* Shrinks to fill remaining height between header and footer */
  .ctn-table-scroll-body {
    flex: 1 1 auto;
    overflow-y: auto;
    overflow-x: auto;
    /* Thin, themed scrollbar on WebKit browsers */
    scrollbar-width: thin;
    scrollbar-color: var(--ctn-hairline) transparent;
  }

  .ctn-table-scroll-body::-webkit-scrollbar {
    width: 6px;
    height: 6px;
  }

  .ctn-table-scroll-body::-webkit-scrollbar-track {
    background: transparent;
  }

  .ctn-table-scroll-body::-webkit-scrollbar-thumb {
    background: var(--ctn-hairline);
    border-radius: 3px;
  }

  .ctn-table-scroll-body::-webkit-scrollbar-thumb:hover {
    background: var(--ctn-tag);
  }

  /* Sticky thead — only meaningful inside a scrollable body */
  .ctn-table-wrap--scroll .ctn-table thead th {
    position: sticky;
    top: 0;
    z-index: 1;
    /* Solid bg so rows don't bleed through on scroll */
    box-shadow: 0 1px 0 var(--ctn-hairline);
  }

  /* Remove the bottom border from thead (box-shadow handles it) */
  .ctn-table-wrap--scroll .ctn-table thead th {
    border-bottom: none;
  }

  /* Sticky footer row — pin a summary/total row to the bottom of the scroll area */
  .ctn-table-wrap--scroll .ctn-table tfoot td {
    position: sticky;
    bottom: 0;
    background: var(--ctn-bg);
    font-family: var(--ctn-font-mono);
    font-size: 11px;
    font-weight: 500;
    color: var(--ctn-ink-soft);
    padding: 9px 14px;
    border-top: 1px solid var(--ctn-hairline);
    box-shadow: 0 -1px 0 var(--ctn-hairline);
  }

  /* --- Header bar above the table --- */
  .ctn-table-header {
    display: flex;
    align-items: center;
    justify-content: space-between;
    padding: 12px 16px;
    border-bottom: 1px solid var(--ctn-hairline);
    gap: 12px;
  }

  .ctn-table-title {
    font-family: var(--ctn-font-sans);
    font-size: 13px;
    font-weight: 600;
    color: var(--ctn-ink);
    letter-spacing: .01em;
    margin: 0;
  }

  .ctn-row-count {
    font-family: var(--ctn-font-mono);
    font-size: 11px;
    color: var(--ctn-tag);
    letter-spacing: .06em;
  }

  /* --- Search field --- */
  .ctn-table-search {
    position: relative;
    display: flex;
    align-items: center;
    flex: 0 1 240px;
  }

  .ctn-table-search input {
    width: 100%;
    font-family: var(--ctn-font-sans);
    font-size: 12px;
    color: var(--ctn-ink);
    background: var(--ctn-paper);
    border: 1px solid var(--ctn-hairline);
    border-radius: 6px;
    padding: 6px 10px 6px 28px;
    outline: none;
    transition: border-color .15s ease, box-shadow .15s ease;
  }

  .ctn-table-search input::placeholder {
    color: var(--ctn-tag);
  }

  .ctn-table-search input:focus {
    border-color: var(--ctn-accent);
    box-shadow: 0 0 0 3px var(--ctn-accent-tint);
  }

  .ctn-table-search svg {
    position: absolute;
    left: 9px;
    width: 13px;
    height: 13px;
    stroke: var(--ctn-tag);
    pointer-events: none;
  }

  /* Row hidden by search filter */
  .ctn-table tbody tr[hidden] {
    display: none;
  }

  /* Shown when search yields zero matches */
  .ctn-table-empty {
    display: none;
    padding: 28px 14px;
    text-align: center;
    font-family: var(--ctn-font-sans);
    font-size: 13px;
    color: var(--ctn-ink-faint);
  }

  .ctn-table-empty.ctn-table-empty--visible {
    display: block;
  }

  /* --- Table itself --- */
  .ctn-table {
    width: 100%;
    border-collapse: collapse;
    font-family: var(--ctn-font-sans);
    font-size: 13px;
  }

  .ctn-table thead th {
    padding: 9px 14px;
    text-align: left;
    font-family: var(--ctn-font-mono);
    font-size: 10px;
    font-weight: 500;
    letter-spacing: .08em;
    text-transform: uppercase;
    color: var(--ctn-tag);
    background: var(--ctn-bg);
    border-bottom: 1px solid var(--ctn-hairline);
    white-space: nowrap;
    user-select: none;
  }

  .ctn-table tbody tr {
    background: var(--ctn-paper);
    border-bottom: 1px solid var(--ctn-hairline);
    transition: background-color .1s ease;
  }

  /* Striped rows */
  .ctn-table tbody tr:nth-child(even) {
    background: var(--ctn-stripe);
  }

  .ctn-table tbody tr:last-child {
    border-bottom: none;
  }

  .ctn-table tbody tr:hover {
    background: var(--ctn-accent-tint);
  }

  .ctn-table tbody td {
    padding: 10px 14px;
    color: var(--ctn-ink-soft);
    vertical-align: middle;
    white-space: nowrap;
  }

  /* Primary cell — name, slightly bolder */
  .ctn-cell-primary {
    color: var(--ctn-ink);
    font-weight: 500;
  }

  /* Monospaced cells — IDs, phone numbers */
  .ctn-cell-mono {
    font-family: var(--ctn-font-mono);
    font-size: 12px;
    color: var(--ctn-ink-soft);
  }

  /* Faint / secondary text inside a cell */
  .ctn-cell-faint {
    color: var(--ctn-ink-faint);
    font-size: 12px;
  }

  /* --- Footer bar --- */
  .ctn-table-footer {
    display: flex;
    align-items: center;
    justify-content: flex-end;
    padding: 10px 16px;
    border-top: 1px solid var(--ctn-hairline);
    background: var(--ctn-bg);
  }

  .ctn-table-footer span {
    font-family: var(--ctn-font-mono);
    font-size: 11px;
    color: var(--ctn-tag);
    letter-spacing: .06em;
  }

  @media (prefers-reduced-motion: reduce) {
    .ctn-table tbody tr { transition: none; }
  }

  @media (max-width: 640px) {
    .ctn-table-wrap { border-radius: 8px; }
    .ctn-table thead th,
    .ctn-table tbody td { padding: 8px 10px; }
  }

  /* ===================================================================
     MOBILE: HORIZONTAL SCROLL
     On small screens the table scrolls horizontally inside the wrap
     rather than overflowing the page. A subtle fade on the right edge
     hints that more columns exist.

     No extra markup needed — this applies automatically below 640px.
     The wrap itself stays full-width; only the table interior scrolls.
  =================================================================== */

  @media (max-width: 640px) {

    /* Turn the wrap into a scroll container */
    .ctn-table-wrap {
      overflow-x: auto;
      -webkit-overflow-scrolling: touch;
      /* Thin themed scrollbar (same as the vertical scroll body) */
      scrollbar-width: thin;
      scrollbar-color: var(--ctn-hairline) transparent;
    }

    .ctn-table-wrap::-webkit-scrollbar {
      height: 4px;
    }

    .ctn-table-wrap::-webkit-scrollbar-track {
      background: transparent;
    }

    .ctn-table-wrap::-webkit-scrollbar-thumb {
      background: var(--ctn-hairline);
      border-radius: 3px;
    }

    /* Prevent the table from collapsing narrower than its content */
    .ctn-table {
      min-width: max-content;
    }

    /* Fade on the right edge — hints that the table scrolls.
       Removed once the wrap is scrolled to the end via JS (optional). */
    .ctn-table-wrap::after {
      content: '';
      position: sticky;
      right: 0;
      top: 0;
      display: block;
      width: 28px;
      pointer-events: none;
    }

  }

  /* ===================================================================
     COLUMN VISIBILITY UTILITIES
     Add these classes to BOTH the <th> and every <td> in that column.
     Mix and match per table — no global change required.

     Classes:
       ctn-col-hide-sm   — hidden below 640px  (small/mobile)
       ctn-col-hide-md   — hidden below 900px  (tablet + below)
       ctn-col-show-sm   — visible only below 640px (rarely needed)

     PHP example — hide the Phone column on mobile:
       <th class="ctn-col-hide-sm">Phone</th>
       …
       <td class="ctn-cell-mono ctn-col-hide-sm">…</td>
  =================================================================== */

  /* Hidden on mobile (< 640px) */
  @media (max-width: 640px) {
    .ctn-col-hide-sm {
      display: none;
    }
  }

  /* Hidden on tablet and below (< 900px) */
  @media (max-width: 900px) {
    .ctn-col-hide-md {
      display: none;
    }
  }

  /* Visible ONLY on mobile — useful for a compact combined cell
     (e.g. "Name + Role" in one cell) that replaces two columns */
  @media (min-width: 641px) {
    .ctn-col-show-sm {
      display: none;
    }
  }

.gp-select {
    appearance: none;
    -webkit-appearance: none;
    -moz-appearance: none;

    width: 100%;
    max-width: 260px;

    padding: 8px 14px;
    font-size: 14px;
    font-weight: 500;

    border-radius: 12px;
    border: 1px solid #dee2e6;
    background-color: #ffffff;

    text-align: center;
    text-align-last: center; /* centers selected value */

    cursor: pointer;
    transition: all 0.2s ease;
}

.gp-select:focus {
    outline: none;
    border-color: #212529;
    box-shadow: 0 0 0 2px rgba(33,37,41,0.08);
}

.gp-select-wrapper {
    display: flex;
    justify-content: center;
    margin: 16px 0 20px 0;
}

.gp-select-form {
    display: flex;
    justify-content: center;
    width: 100%;
}

/* ===================================================================
   DIV TABLE
   .ctn-div-table        ? outer wrapper (shares ctn-table-wrap tokens)
   .ctn-div-head         ? header row (hidden on mobile)
   .ctn-div-head-cell    ? individual header cell
   .ctn-div-body         ? contains all data rows
   .ctn-div-row          ? a single data row
   .ctn-div-cell         ? a single data cell
   .ctn-div-cell-label   ? the column label injected inside each cell
                           (hidden on desktop, visible on mobile)

   Column width control:
     Add  style="--col-w: 200px"  on a header cell AND its matching
     data cells, or use the  .ctn-col-*  width helpers below.
=================================================================== */

.ctn-div-table {
  /* Inherits all --ctn-* tokens from ctn-table-wrap */
  background: var(--ctn-bg);
  border: 1px solid var(--ctn-hairline);
  border-radius: 10px;
  overflow: hidden;
  font-family: var(--ctn-font-sans);
  font-size: 13px;
}

/* ---- Header row ---- */
.ctn-div-head {
  display: flex;
  border-bottom: 1px solid var(--ctn-hairline);
  background: var(--ctn-bg);
}

.ctn-div-head-cell {
  flex: 1 1 var(--col-w, 0);
  min-width: 0;
  padding: 9px 14px;
  font-family: var(--ctn-font-mono);
  font-size: 10px;
  font-weight: 500;
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--ctn-tag);
  white-space: nowrap;
  user-select: none;
}

/* ---- Body ---- */
.ctn-div-body .ctn-div-row {
  display: flex;
  align-items: stretch;
  border-bottom: 1px solid var(--ctn-hairline);
  background: var(--ctn-paper);
  transition: background-color .1s ease;
}

.ctn-div-body .ctn-div-row:nth-child(even) {
  background: var(--ctn-stripe);
}

.ctn-div-body .ctn-div-row:last-child {
  border-bottom: none;
}

.ctn-div-body .ctn-div-row:hover {
  background: var(--ctn-accent-tint);
}

/* ---- Data cell ---- */
.ctn-div-cell {
  flex: 1 1 var(--col-w, 0);
  min-width: 0;
  padding: 10px 14px;
  color: var(--ctn-ink-soft);
  display: flex;
  flex-direction: column;
  justify-content: center;
  gap: 2px;
}

/* The label inside each cell ? hidden on desktop */
.ctn-div-cell-label {
  display: none;
  font-family: var(--ctn-font-mono);
  font-size: 9px;
  font-weight: 500;
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--ctn-tag);
  margin-bottom: 2px;
}

/* ---- Footer ---- */
.ctn-div-footer {
  display: flex;
  align-items: center;
  justify-content: flex-end;
  padding: 10px 16px;
  border-top: 1px solid var(--ctn-hairline);
  background: var(--ctn-bg);
  font-family: var(--ctn-font-mono);
  font-size: 11px;
  color: var(--ctn-tag);
  letter-spacing: .06em;
}

/* ===================================================================
   MOBILE: CARD COLLAPSE
   Below 640px each .ctn-div-row becomes a stacked card.
   The header row hides. Each cell shows its own label above its value.
=================================================================== */
@media (max-width: 640px) {

  /* Hide the desktop header row entirely */
  .ctn-div-head { display: none; }

  /* Each row becomes a card */
  .ctn-div-body .ctn-div-row {
    flex-direction: column;
    padding: 12px 14px;
    gap: 10px;
    border-bottom: none;
    border-radius: 8px;
    margin: 8px 8px 0;
    /* Lift the card slightly */
    box-shadow: 0 1px 3px rgba(0,0,0,.06);
  }

  /* Gap between cards instead of border-bottom */
  .ctn-div-body .ctn-div-row:last-child {
    margin-bottom: 8px;
  }

  /* Even rows keep their stripe as a card tint */
  .ctn-div-body .ctn-div-row:nth-child(even) {
    background: var(--ctn-stripe);
  }

  /* Cells stack vertically, full width */
  .ctn-div-cell {
    flex: none;
    width: 100%;
    padding: 0;
  }

  /* Show the inline label above the value */
  .ctn-div-cell-label {
    display: block;
  }

  /* Footer stays the same */
  .ctn-div-footer {
    border-top: 1px solid var(--ctn-hairline);
    margin-top: 8px;
  }

}

@media (prefers-reduced-motion: reduce) {
  .ctn-div-body .ctn-div-row { transition: none; }
}