/* =============================================================================
   dsh-mobile-fix —— DSH Pocket 移动端 UI 补丁层
   -----------------------------------------------------------------------------
   由 proxy.js 注入到 dsh-pocket(3081) 返回的 HTML 中，<style id="dsh-mobile-fix">。
   不修改 dsh-pocket / DSH web 任何包文件。

   覆盖顺序：本文件排在应用样式表之后注入，但应用用 vanilla-extract 在运行时
   追加 <style>，顺序不可靠，因此关键声明统一用 !important（补丁层可接受）。
   选择器全部取自实测 DOM / 运行时 CSSOM，见 report.md 的「选择器来源」一节。

   段落：
     §0 变量
     §1 P0-1 账号菜单被抽屉遮挡
     §2 P0-2 header 标题被后台任务 chip 压成 1~2 字
     §3 P1-1 触控目标 < 44px
     §4 P1-2 底部安全区
     §5 P1-3 软键盘（配合 proxy 注入的 interactive-widget + --kb-inset）
   ============================================================================= */

/* ---------------------------------------------------------------- §0 变量 */
:root {
  /* 层级：抽屉 1200（实测 .pI_x6G_sidebarCol），弹出层原 1100 → 必须更高 */
  --dsh-mf-z-drawer: 1200;
  --dsh-mf-z-popover: 1400;

  --dsh-mf-tap: 44px;          /* iOS HIG / Android 最小触控尺寸 */
  --dsh-mf-tap-sm: 44px;

  /* 安全区。用自定义属性包一层，便于在无刘海环境（桌面 / headless）里
     覆盖 --dsh-mf-safe-bottom 来验证规则确实生效。 */
  --dsh-mf-safe-top: env(safe-area-inset-top, 0px);
  --dsh-mf-safe-bottom: env(safe-area-inset-bottom, 0px);

  --dsh-mf-title-min: 5em;     /* 标题至少 5 个汉字（14px × 5 = 70px） */
}

/* ============================================================
   §1 P0-1 账号菜单被抽屉遮挡
   -----------------------------------------------------------------
   实测（390×844，抽屉打开）：
     菜单面板 div[role=menu]._surface_ri079_1._list_4ub78_7
       rect 144×110 @ (12,676)  z-index 1100  position fixed
     抽屉 .pI_x6G_sidebarCol  z-index 1200
     elementFromPoint(84,697) → div.bhn1Oq_list（抽屉会话列表）
   根因：._portal_4ub78_41 { z-index: 1100 } 低于抽屉的 1200。
   修法：把 portal 层抬到 1400。所有弹出层（菜单 / 子菜单 / 模型选择器）
        一起抬升，语义正确且不会互相打架。
   ============================================================ */
._portal_4ub78_41,
[role="menu"][data-menu-material],
[data-menu-material][class*="_surface_ri079"] {
  z-index: var(--dsh-mf-z-popover) !important;
}

/* ------------------------------------------------------------
   P0-1 的孪生问题：整个浮层带都被抽屉压住
   -----------------------------------------------------------------
   抽屉 .pI_x6G_sidebarCol 的 z-index 是 1200（内联样式，由 dsh-pocket 的
   移动导航脚本写入），而应用里所有 modal / 菜单 / toast 都在 900~1100：
     .VOzbGW_overlay              1000   ← 设置弹窗
     ._44HXVa_overlay             1001
     ._root_o6lrb_6 / ._backdrop_19zw2_2 / .BInVoG_mask   1000
     .tQSFJa_onboardingOverlay     900
     .JObwrW_panel / .ovHEHG_panel / .bRhRbq_panel /
     .JYBKaa_portal / .X_2TxG_registry /
     ._toast_l6cvn_6 / ._bubble_12mhf_1[data-portal] /
     ._7KE1Ra_menu                1100
   后果：抽屉开着的时候点「设置」，设置弹窗会**整个跑到抽屉后面**
   （实测 .VOzbGW_overlay z=1000 < 抽屉 1200，弹窗左侧 280px 被抽屉盖住、
   其余部分被抽屉挡住的遮罩拦截点击）。这是修好账号菜单后才暴露出来的。
   修法：把整条浮层带抬到 1300（抽屉 1200 < 弹层 1300 < 菜单 1400）。
   说明：下面的类名是当前构建的哈希类名，DSH 升级后需要复核一次；
   上面那条 :has() 规则不依赖哈希，覆盖所有含 dialog 的 body 直接子元素。
   ------------------------------------------------------------ */
body > *:has([role="dialog"]),
body > *:has([aria-modal="true"]) {
  z-index: 1300 !important;
}

.VOzbGW_overlay,
._44HXVa_overlay,
._root_o6lrb_6,
._backdrop_19zw2_2,
.BInVoG_mask,
.tQSFJa_onboardingOverlay,
.JObwrW_panel,
.ovHEHG_panel,
.bRhRbq_panel,
.JYBKaa_portal,
.X_2TxG_registry,
._toast_l6cvn_6,
._bubble_12mhf_1[data-portal],
._7KE1Ra_menu {
  z-index: 1300 !important;
}

/* 弹出层抬到抽屉之上后，窄屏把它变成「底部动作面板」：
   彻底避开抽屉的左边缘遮挡，同时天然获得安全区与 44px 行高。
   只作用于 role=menu 的浮层（账号菜单 / 更多操作等），
   不影响 .ZKlsPq_menu 这类模型选择器浮层。
   注：._viewport_4ub78_19 自带 overflow-y:auto，这里只约束外框高度。 */
@media (max-width: 480px) {
  [role="menu"][data-menu-material] {
    position: fixed !important;
    left: 8px !important;
    right: 8px !important;
    top: auto !important;
    bottom: calc(8px + var(--dsh-mf-safe-bottom)) !important;
    width: auto !important;
    min-width: 0 !important;
    max-width: none !important;
    max-height: min(60vh, 480px) !important;
    border-radius: 16px !important;
    padding-bottom: 6px !important;
  }
}

/* ============================================================
   §2 P0-2 header 标题被后台任务 chip 压成 1~2 字
   -----------------------------------------------------------------
   实测（390×844，运行中，见 qa/ux/report.md）：
     .wSkVaW_titleCluster 183~203px
     .wSkVaW_crumbCurrent clientWidth 41.2px / scrollWidth 170px  → 只剩 1~2 字
   运行时 CSSOM 里的根因：
     .wSkVaW_crumbs        { flex: 0 1 auto; min-width: 0; overflow: hidden }
     .wSkVaW_headerActions { flex: 0 0 auto }   ← 永不收缩，chip 独占空间
     .wSkVaW_crumbCurrent  { 没有 min-width 下限 }
   修法：
     1) 标题导航吃满剩余空间（flex-grow）
     2) 标题给硬下限 5em（≈5 个汉字），永远不会缩成 1~2 字
     3) chip 容器改为可收缩并封顶 55%，先让位给标题
   ============================================================ */
.wSkVaW_crumbs.wSkVaW_crumbs {
  flex: 1 1 auto !important;
  min-width: 0 !important;
}

.wSkVaW_crumbCurrent {
  min-width: var(--dsh-mf-title-min) !important;
}

/* chip 容器：**保持原来的 flex: 0 0 auto**（不让 chip 被压扁变形 / 换行），
   只加一个 max-width 封顶，防止 chip 把标题吃光。
   标题的下限由上面 crumbCurrent 的 min-width 保证，所以这里不需要靠压缩 chip 来让位。 */
.wSkVaW_headerActions.wSkVaW_headerActions {
  flex: 0 0 auto !important;
  max-width: 50% !important;
  white-space: nowrap !important;
}

/* 状态 chip 一律单行：被挤压时宁可省略号，也不要折成两行 */
.wSkVaW_headerActions.wSkVaW_headerActions,
.wSkVaW_headerActions.wSkVaW_headerActions * {
  white-space: nowrap !important;
}

.wSkVaW_headerActions.wSkVaW_headerActions span {
  overflow: hidden !important;
  text-overflow: ellipsis !important;
}

/* 腾出空间：右侧工具栏收紧间距，把 12px 让给标题 */
.wSkVaW_headerUtilities {
  margin-left: 8px !important;
  gap: 2px !important;
}

/* ============================================================
   §3 P1-1 触控目标 < 44px
   -----------------------------------------------------------------
   实测（390×844，getBoundingClientRect）：
     发送  button.uV2eYG_primary            34×34
     抽屉开关 button[data-mobile-nav=toggle]  28×28   （首屏 fab 38×38）
     更多  button.nL4_yW_moreButton          28×28
     tab   button.wSkVaW_tab                 26×25
     会话行 div.YDXeBa_sessionRow           256×32
     菜单项 button._item_4ub78_90           136×34
   只在触屏 / 窄屏生效，桌面不受影响。
   ============================================================ */
@media (pointer: coarse), (max-width: 480px) {

  /* --- 发送（34 → 44）--- */
  button.uV2eYG_primary {
    width: var(--dsh-mf-tap) !important;
    height: var(--dsh-mf-tap) !important;
  }

  /* --- 添加文件（28 → 44）--- */
  button.uV2eYG_add {
    width: var(--dsh-mf-tap) !important;
    height: var(--dsh-mf-tap) !important;
  }

  /* --- 抽屉开关：会话页 toggle（28 → 44）、首屏 fab（38 → 44）---
         toggle 是 position:absolute，放大不影响 header 网格，标题不被挤。 */
  [data-mobile-nav="toggle"],
  [data-mobile-nav="files"],
  [data-mobile-nav="fab"] {
    width: var(--dsh-mf-tap) !important;
    height: var(--dsh-mf-tap) !important;
  }

  /* --- header 右侧图标按钮：更多操作 / 打开右侧边栏 ---
         header 右缘本来就溢出（scrollWidth 394 > 390），把盒子直接加到 44 会把
         相邻按钮推出屏幕，所以用「保持视觉尺寸、扩大命中区」的做法。
         两个按钮间距只有 8px，所以命中区做成 **36 宽 × 44 高**（左右各外扩 4px，
         正好到间距中点），避免两块 44×44 命中区互相覆盖导致边界处命中相邻按钮。
         §5 用 elementFromPoint 逐像素扫描实测有效命中区。 */
  .nL4_yW_moreButton,
  header ._button_1rv3m_2._sm_1rv3m_28 {
    position: relative !important;
    touch-action: manipulation;
  }
  .nL4_yW_moreButton::after,
  header ._button_1rv3m_2._sm_1rv3m_28::after {
    content: "" !important;
    position: absolute !important;
    left: 50% !important;
    top: 50% !important;
    width: 36px !important;
    height: var(--dsh-mf-tap) !important;
    transform: translate(-50%, -50%) !important;
    /* 纯命中区，不参与绘制 */
    background: transparent !important;
  }

  /* --- 对话 / 轨迹 tab（26×25 → 44×44 以上）---
         tab 是并排的，只加高度会让宽度仍只有 26px，所以补左右内边距，
         同时把 tab 容器间距 36 → 12 让整体宽度不变。 */
  .wSkVaW_tab {
    box-sizing: border-box !important;
    min-height: var(--dsh-mf-tap) !important;
    min-width: var(--dsh-mf-tap) !important;
    display: inline-flex !important;
    align-items: center !important;
    justify-content: center !important;
    padding: 0 12px !important;
  }
  .wSkVaW_tabs {
    gap: 12px !important;
    padding-left: 0 !important;
  }

  /* --- 抽屉会话行（32 → 44）--- */
  .YDXeBa_sessionRow,
  .YDXeBa_projectRow {
    height: auto !important;
    min-height: var(--dsh-mf-tap) !important;
  }
  .YDXeBa_sessionRow .YDXeBa_title {
    min-width: 0 !important;
  }

  /* --- 菜单项（34 → 44）--- */
  ._item_4ub78_90 {
    min-height: var(--dsh-mf-tap) !important;
  }

  /* --- 抽屉内其它可点元素 --- */
  .hHd-Xa_newSession {
    height: var(--dsh-mf-tap) !important;
  }
  .hHd-Xa_iconButton,
  .bhn1Oq_iconButton,
  .bhn1Oq_searchButton {
    width: var(--dsh-mf-tap) !important;
    height: var(--dsh-mf-tap) !important;
  }
  .VOzbGW_navCell {
    min-height: var(--dsh-mf-tap) !important;
  }
  [data-mobile-nav="session-log"],
  [data-mobile-nav="explorer"] {
    height: var(--dsh-mf-tap) !important;
  }

  /* --- 设置弹窗关闭按钮 ---
     应用在 @media(max-width:1023px) 里用一条 b≈7 的 !important 规则把它钉成
     32×32（[aria-modal="true"]:has(...):not(:has(...)) > :last-child > :first-child
     > :last-child）。要用 !important 盖过去得堆 8 个类，维护性太差，
     所以这里不动视觉尺寸，只补 44×44 命中区（伪元素不受那条规则约束）。 */
  .VOzbGW_close {
    position: relative !important;
  }
  .VOzbGW_close::after {
    content: "" !important;
    position: absolute !important;
    left: 50% !important;
    top: 50% !important;
    width: var(--dsh-mf-tap) !important;
    height: var(--dsh-mf-tap) !important;
    transform: translate(-50%, -50%) !important;
    background: transparent !important;
  }

  /* 触屏去掉 300ms 残留 & 双击缩放 */
  button,
  a,
  [role="button"],
  [role="menuitem"],
  [role="treeitem"] {
    touch-action: manipulation;
  }
}

/* ============================================================
   §4 P1-2 底部安全区
   -----------------------------------------------------------------
   实测：全站 safe-area-inset-bottom 只出现 1 次（FAB），
     [data-composer-seat] bottomGap = 0（输入区紧贴视口底边）
     .hHd-Xa_footArea 底边距视口 6px
   修法：用 --dsh-mf-safe-bottom（默认 env(...)）补底部内边距。
   ============================================================ */
[data-composer-seat] {
  padding-bottom: max(4px, var(--dsh-mf-safe-bottom)) !important;
}

.hHd-Xa_footArea {
  padding-bottom: var(--dsh-mf-safe-bottom) !important;
}

.bhn1Oq_listArea {
  padding-bottom: var(--dsh-mf-safe-bottom) !important;
}

/* 弹出菜单贴底时也要避开 home indicator */
._viewport_4ub78_19 {
  padding-bottom: env(safe-area-inset-bottom, 0px);
}

/* ============================================================
   §5 P1-3 软键盘
   -----------------------------------------------------------------
   proxy.js 已把 viewport 改成 interactive-widget=resizes-content；
   这里再兜底 iOS Safari（不改布局视口的内核）：用注入脚本算出的
   --kb-inset 把输入区抬起来。
   ============================================================ */
[data-composer-seat] {
  margin-bottom: var(--kb-inset, 0px) !important;
}

/* ============================================================
   §6 防横向溢出兜底
   ============================================================ */
html,
body {
  overscroll-behavior-y: none;
}
.wSkVaW_scrollBody {
  overscroll-behavior: contain;
}
