@use "./utils" as *;

:root {
  --header-height: 52px;
  // Top inset of the device safe area (Dynamic Island / notch / status bar).
  // Resolves to 0 on the web and on non-notched devices; requires the
  // viewport-fit=cover meta (set in index.html) to be non-zero on iOS.
  --safe-area-inset-top: env(safe-area-inset-top, var(--c--globals--spacings--2xs));
  // Bottom inset of the device safe area (home indicator / gesture bar).
  // Floating bottom bars fold it into their padding so they clear the system UI.
  --safe-area-inset-bottom: env(safe-area-inset-bottom, var(--c--globals--spacings--2xs));
  --c--components--forms-checkbox--size: 24px;
  --toastify-z-index: 9999999;
}

@media screen and (max-width: breakpoint(tablet)) {
  :root {
    --header-height: 104px;
  }
}

:root.native {
  // Height of the floating bottom bar (controls + block paddings). Used to keep
  // scrollable content clear of it and to stop the search overlay above it.
  --mobile-bottom-bar-height: calc(64px + var(--safe-area-inset-bottom));
  // The native webview draws edge-to-edge (viewport-fit=cover on iOS,
  // enforced on Android 15+), so the fixed header absorbs the top safe area:
  // fold it into --header-height — panels and the mobile thread view are all
  // laid out from it and follow automatically. The header itself pushes its
  // content below the inset (see main/header/_index.scss).
  --header-height: calc(52px + var(--safe-area-inset-top));
}

@media screen and (max-width: breakpoint(tablet)) {
  :root.native {
    --header-height: calc(104px + var(--safe-area-inset-top));
  }
}

// Reserve room for the floating bottom bar so the last list item / message
// isn't hidden behind it on the native app.
.native .thread-panel__threads_list,
.native .thread-view {
  padding-bottom: var(--mobile-bottom-bar-height);
}

// BlockNote's mobile toolbar pins itself above the keyboard via its own
// --bn-mobile-keyboard-offset (Visual Viewport based). The positioning rule
// lives in @blocknote/react's stylesheet, which we don't load (mantine theme
// only), so we declare it here.
.native .bn-mobile-formatting-toolbar {
  position: fixed;
  left: 0;
  right: 0;
  bottom: var(--bn-mobile-keyboard-offset, 0px);
  z-index: 1100;
  display: flex;
  overflow-x: auto;
  touch-action: pan-x;
  -webkit-overflow-scrolling: touch;
  padding-bottom: var(--safe-area-inset-bottom);
  transition: bottom 0.15s ease-out;
  // Solid bar so the buttons read against the content scrolling behind.
  background-color: var(--c--contextuals--background--surface--secondary);
  border-top: 1px solid var(--c--contextuals--border--surface--primary);

  // Keep all buttons on a single horizontally-scrollable row.
  .bn-formatting-toolbar {
    flex-wrap: nowrap;
    width: max-content;
    box-shadow: none;
    border: none;
    background: transparent;
  }
}

html, body {
  height: 100%;
}

body {
  margin: 0;
  background-color: var(--c--contextuals--background--surface--tertiary);
  color: var(--c--contextuals--content--semantic--neutral--primary);
}

* {
  box-sizing: border-box;
}

// Related to 'react-resizable-panels'
// By default, it sets overflow to 'hidden', this is not compatible
// with our ui mainly because of tooltips.
*[data-panel],
*[data-panel-group],
.c__main-layout__content__center__children {
  overflow: auto !important;
}

// Customize resize handle to add an hover effect to explicit that
// this component is interactive. Orientation is driven by the
// `aria-orientation` attribute set by react-resizable-panels:
// "vertical" → vertical line (horizontal Group, drag left/right)
// "horizontal" → horizontal line (vertical Group, drag up/down)
.panel__resize-handle {
  background-color: var(--c--contextuals--border--surface--primary);
  position: relative;

  &:before {
    content: '';
    background: var(--c--contextuals--border--surface--primary);
    position: absolute;
    opacity: 0;
    transition: opacity 250ms var(--c--globals--transitions--ease-in-out);
    z-index: 10;
  }

  // Expand the hover catch zone.
  &:after {
    content: '';
    position: absolute;
  }

  &:hover:before {
    opacity: 1;
  }

  &[aria-orientation="vertical"] {
    width: 1px;

    &:before {
      width: 3px;
      left: -1px;
      top: 0;
      bottom: 0;
    }

    &:after {
      width: 11px;
      left: -5px;
      top: 0;
      bottom: 0;
    }
  }

  &[aria-orientation="horizontal"] {
    height: 1px;

    &:before {
      height: 3px;
      top: -1px;
      left: 0;
      right: 0;
    }

    &:after {
      height: 11px;
      top: -5px;
      left: 0;
      right: 0;
    }
  }
}


// Cunningham tweaks
.c__datagrid__table__container > table tbody tr:not(:last-child) {
  border-bottom: 1px solid var(--c--contextuals--border--surface--primary);
}

.c__dropdown-menu-trigger .c__button {
  font-size: var(--c--globals--font--sizes--sm);
}

a.c__button.c__button--brand--primary.c__button--disabled {
    background-color: var(--c--contextuals--background--semantic--disabled--primary);
    color: var(--c--contextuals--content--semantic--disabled--primary);
}

// Cunningham: force label up for datetime-local/time inputs
// The browser always renders native placeholder text for these input types,
// which overlaps with Cunningham's floating label in "placeholder" position.
.labelled-box:has(input[type="datetime-local"], input[type="time"]) .labelled-box__label.placeholder {
  top: 8px;
  font-size: 11px;
  line-height: 16.5px;
}

// Cunningham icon sizes tweaks
.material-icons.icon--size-sm {
  font-size: var(--c--globals--font--sizes--sm);
}

// Cunningham modal class utilities
.c__modal__text--centered {
  display: inline-block;
  width: 100%;
  text-align: center;
}

// Fullscreen modals (Cunningham ModalSize.FULL, used on mobile) fill the screen
// edge-to-edge with no padding of their own, so on devices with a notch / home
// indicator the header and footer land under the system UI. Inset them by the
// device safe area; resolves to 0 on desktop and on non-notched devices.
.c__modal--full {
  padding-top: var(--safe-area-inset-top);
  padding-bottom: var(--safe-area-inset-bottom);
}

// On mobile, non-fullscreen modals are nearly full-width, so Cunningham's close
// button (a static flex item, justified to the right) ends up flush in the
// top-right corner. Give it breathing room from the edges.
@media (max-width: breakpoint("mobile")) {
  .c__modal:not(.c__modal--full) .c__modal__close {
    padding-top: var(--c--globals--spacings--sm);
    padding-right: var(--c--globals--spacings--sm);
  }
}


// Hide toast container as we use react-toastify
.c__toast__container {
  display: none;
}

// React Modal tweaks
// Make it always on top of the other modals
.ReactModalPortal {
  position: relative;
  z-index: 999999;
}

// Related to @viselect/react
.selection-area {
  background: rgba(46, 115, 252, 0.11);
  border: 2px solid rgba(98, 155, 255, 0.81);
  border-radius: 0.1em;

  &__container {
    user-select: none;
  }
}

// Class utilities
.flex-row {
  display: flex;
  flex-direction: row;
}

.flex-column {
  display: flex;
  flex-direction: column;
}

.flex-align-center {
  align-items: center;
}

.flex-align-end {
  align-items: flex-end;
}

.flex-justify-center {
  justify-content: center;
}

.flex-justify-end {
  justify-content: flex-end;
}

.flex-justify-space-between {
  justify-content: space-between;
}

.p-0 {
  padding: var(--c--globals--spacings--2xs);
}

.p-2xs {
  padding: var(--c--globals--spacings--2xs);
}

.p-xs {
  padding: var(--c--globals--spacings--xs);
}

.p-sm {
  padding: var(--c--globals--spacings--sm);
}

.p-md {
  padding: var(--c--globals--spacings--md);
}

.p-base {
  padding: var(--c--globals--spacings--base);
}

.m-0 {
  margin: 0;
}

.m-2xs {
  margin: var(--c--globals--spacings--2xs);
}

.m-xs {
  margin: var(--c--globals--spacings--xs);
}

.m-sm {
  margin: var(--c--globals--spacings--sm);
}

.m-md {
  margin: var(--c--globals--spacings--md);
}

.m-base {
  margin: var(--c--globals--spacings--base);
}

.hidden {
  visibility: hidden;
}

.text-nowrap {
  white-space: nowrap;
}
