/* ============================================================
   Astra 橋接層
   把父主題的全域色變數接到我們的 Layer 2 語意 token。

   為什麼要這一層：Astra 內建規則大量用 .ast-separate-container 這類
   body class 選擇器（特異性 0,1,0），會贏過我們寫在 body 上的規則（0,0,1）。
   與其逐條加 !important 對抗，不如改寫它取值的來源——
   Astra 自己的規則就會吃我們的色，按鈕、容器、邊框全部一起跟上。

   🔴 這層只做「對應」，不定義新顏色。真正的色值一律在 tokens.css。
   若日後換掉 Astra，刪掉這一個檔案即可。

   🔴 覆寫 Astra／Woo 的樣式時，選擇器要寫得跟它一樣深。
   實際踩過三次：
     .site-below-footer-wrap[data-section="..."]        (0,2,0)
     .woocommerce-js .woocommerce-breadcrumb a          (0,2,0)
     .woocommerce-js form .form-row .required           (0,3,0)
   只寫單一類別（0,1,0）會靜靜地輸掉——而且常常是「背景輸了、前景贏了」，
   結果變成看不見的字。改完一定跑 scripts/qa/contrast-audit.js 驗。
   ============================================================ */

:root,
body {
  --ast-global-color-0: var(--accent);      /* 主色：連結、按鈕底 */
  --ast-global-color-1: var(--accent-hover); /* 主色 hover */
  --ast-global-color-2: var(--text);        /* 標題文字 */
  --ast-global-color-3: var(--text);        /* 內文（不用 text-soft，內文要最高對比） */
  --ast-global-color-4: var(--bg-raised);   /* 內容容器底 */
  --ast-global-color-5: var(--bg);          /* 站台底色 */
  --ast-global-color-6: var(--text);
  --ast-global-color-7: var(--line);        /* 邊框細線 */
  --ast-global-color-8: var(--text);
}

/* Astra 的容器底色改用語意層。
   🔴 兩種容器都要列：文章頁是 .ast-separate-container，
   WooCommerce 封存頁（商店頁）是 .ast-plain-container，Astra 把它指到
   --ast-global-color-4（我們映成浮起色），漏掉就會變成近白而不是米底。 */
.ast-separate-container,
.ast-plain-container {
  background-color: var(--bg);
}

/* 浮起面（內容卡片、標頭）。
   底色與前景色一律成對出現，並在子樹內重定義 Astra 的色變數——
   否則 D 深調把 --bg-raised 翻成米色時，Astra 自己的規則仍會輸出米色文字。 */
.ast-separate-container .ast-article-post,
.ast-separate-container .ast-article-single,
.ast-separate-container .ast-comment-list li.depth-1,
.ast-separate-container .comment-respond,
.site-header,
.ast-primary-header-bar,
.main-header-bar {
  background-color: var(--bg-raised);
  color: var(--text-on-raised);

  /* 🔴 關鍵：在子樹內重新定義「語意層」本身，不只是 Astra 的變數。
     這樣連我們自己寫在 base.css 的 a{color:var(--accent)} 也會自動取到
     浮起面版本——否則深調時它會拿全域的柔沙棕，壓在米色卡片上只有 1.57:1。
     一個變數、靠繼承生效，勝過逐條規則對抗特異性。 */
  --text:      var(--text-on-raised);
  --text-soft: var(--text-soft-on-raised);
  --accent:    var(--accent-on-raised);
  --danger:    var(--danger-on-raised);
  /* --accent 在這裡翻成深棕，配對的前景色必須一起翻 */
  --on-accent:       var(--brand-cream);
  --accent-hover:    var(--brand-ink);
  --on-accent-hover: var(--brand-cream);

  --ast-global-color-0: var(--accent-on-raised);
  --ast-global-color-1: var(--text-on-raised);
  --ast-global-color-2: var(--text-on-raised);
  --ast-global-color-3: var(--text-on-raised);
  --ast-global-color-6: var(--text-on-raised);
  --ast-global-color-8: var(--text-on-raised);
}

/* 頁尾走自己的語意，不跟著容器。
   🔴 必須用 [data-section] 屬性選擇器：Astra 的頁尾建構器輸出的是
   .site-below-footer-wrap[data-section="section-below-footer-builder"]（特異性 0,2,0），
   只寫類別（0,1,0）會被它蓋掉背景——但我們的文字色仍然生效，
   結果就是米色字壓在近白底上（1.06:1，等於隱形）。
   所以底色與文字色一律寫在同一個規則區塊，不讓兩者脫鉤。 */

.site-footer,
.site-primary-footer-wrap[data-section="section-primary-footer-builder"],
.site-below-footer-wrap[data-section="section-below-footer-builder"] {
  background-color: var(--footer-bg);
  color: var(--footer-fg);

  /* 🔴 頁尾內要把 Astra 的色變數重新定義一次。
     上面的全域映射把 --ast-global-color-3 指到 --text（深墨），
     而頁尾底色也是深墨——Astra 的版權列規則吃到那個變數，就變成深壓深（1:1）。
     自訂屬性會繼承，所以在這裡重新定義，整個頁尾子樹自動跟著換。 */
  --ast-global-color-0: var(--footer-fg);
  --ast-global-color-1: var(--brand-sand);
  --ast-global-color-2: var(--footer-fg);
  --ast-global-color-3: var(--footer-fg);
  --ast-global-color-6: var(--footer-fg);
  --ast-global-color-8: var(--footer-fg);
}

.site-footer a,
.site-primary-footer-wrap[data-section="section-primary-footer-builder"] a,
.site-below-footer-wrap[data-section="section-below-footer-builder"] a {
  color: var(--footer-fg);
  text-decoration: underline;
  text-underline-offset: .25em;
}

.site-footer a:hover,
.site-footer a:focus-visible {
  color: var(--brand-sand);
}

/* ---------- WooCommerce ---------- */

/* 麵包屑：Woo／Astra 寫死 #777（壓在米底上只有 3.75:1，不到 AA）。
   🔴 必須寫成 .woocommerce-js .woocommerce-breadcrumb a 才蓋得掉——
   Astra 的 woocommerce-grid.min.css 用的就是這個選擇器（0,2,0），
   只寫 .woocommerce-breadcrumb a（0,1,0）會輸。 */
.woocommerce-breadcrumb,
.woocommerce-js .woocommerce-breadcrumb,
.woocommerce-js .woocommerce-breadcrumb a {
  color: var(--text-soft);
}

.woocommerce-js .woocommerce-breadcrumb a:hover,
.woocommerce-js .woocommerce-breadcrumb a:focus-visible {
  color: var(--accent);
}

/* 必填星號與錯誤訊息：Woo 預設 red，對米底 3.50:1 不合格。
   🔴 Astra 的 woocommerce-grid.min.css 用 .woocommerce-js form .form-row .required（0,3,0），
   要蓋掉就得寫一樣深。這是本檔第三次遇到同一件事，規則寫在檔頭。 */
.required,
abbr.required,
.woocommerce-js form .form-row .required,
.woocommerce-js form .form-row abbr.required,
.woocommerce-error,
.woocommerce-js form .form-row.woocommerce-invalid label {
  color: var(--danger);
}

/* Woo 的提示訊息列（購物車空了、找不到商品）走襯底，不用 Woo 預設的灰藍 */
.woocommerce-info,
.woocommerce-message,
.woocommerce-error {
  background-color: var(--bg-alt);
  color: var(--text);
  border-top-color: var(--accent);
}

.woocommerce-info a,
.woocommerce-message a {
  color: var(--accent);
}

/* 按鈕：Astra 把文字寫死 color:#fff，背景卻走 --ast-global-color-0。
   D 深調把主色翻成柔沙棕（淺）之後，白字壓在淺底上只有 1.8:1。
   🔴 底色與文字色一律一起指定，並對齊 .woocommerce-js a.button（0,2,0）。
   實測：亮版 米底 on #8E5B32 = 4.98:1；深調 深棕字 on 柔沙棕 = 6.53:1。 */
.button,
/* 🔴 這個光禿禿的 button 會打到主題裡每一個 <button>，
   包含漢堡、數量的 −／＋ 這種「不是按鈕外觀」的控制項——被填成主色之後，
   前景與底色同深，控制項等於整個消失（漢堡那次就是這樣，滑過才看得到）。
   排除的方式是一個記號 class .ns-plain，不是逐一列出元件名稱：
   逐一列的話，下一個無外觀按鈕又會踩一次，而且要等到有人滑過才發現。 */
button:not(.ns-plain),
.ast-button,
.ast-custom-button,
input[type="button"],
input[type="submit"],
.wp-block-button__link,
.woocommerce-js a.button,
.woocommerce-js button.button,
.woocommerce-js input.button,
.woocommerce-js a.button.alt,
.woocommerce-js button.button.alt {
  background-color: var(--accent);
  color: var(--on-accent);
  border-color: var(--accent);
}

.button:hover,
button:not(.ns-plain):hover,
.ast-button:hover,
.wp-block-button__link:hover,
.woocommerce-js a.button:hover,
.woocommerce-js button.button:hover,
.woocommerce-js a.button.alt:hover,
.woocommerce-js button.button.alt:hover {
  background-color: var(--accent-hover);
  color: var(--on-accent-hover);
  border-color: var(--accent-hover);
}

/* 字級下限 16px（2026-09-16 指定）
   ─────────────────────────────────────────────────────────
   我們自己的 CSS 已經全部走 --fs-* token，但 WooCommerce 與 Astra
   自己輸出的那幾串字不在我們的規則裡，實測還停在 12.4–14.6px：

     .woocommerce-result-count    14.6px  「顯示所有 2 筆結果」
     .ast-onsale-card             12.7px  「Sale!」
     .ast-woo-product-category    12.4px  「Uncategorized」
     .woocommerce-info            14.6px  「您的購物車裡還沒有任何商品。」

   這四處分別出現在商店頁與空購物車／結帳頁——都是還沒做自訂模板的地方。
   🔴 注意：screen-reader-text（例如「Scroll to Top」15px）刻意不管。
   它是 clip 成 0×0 的無障礙文字，根本不顯示，放大它沒有任何意義。 */
.woocommerce-result-count,
.woocommerce-ordering,
.woocommerce-ordering select,
.ast-woo-product-category,
.woocommerce-info,
.woocommerce-message,
.woocommerce-error,
.woocommerce ul.products li.product .price,
.woocommerce ul.products li.product .price del,
.woocommerce ul.products li.product .price ins {
  font-size: var(--fs-xs);
}

.ast-onsale-card,
.woocommerce span.onsale {
  font-size: var(--fs-2xs);
}

/* 🔴 商品分類標籤要寫到 (0,4,2) 才蓋得過——單寫 .ast-woo-product-category（0,1,0）
   會輸給 Astra 的 loop 選擇器。它同時帶 opacity:.6，合成後只有 3.71:1。
   兩件事一起處理：字級拉到下限、opacity 拿掉改用實色。 */
.woocommerce ul.products li.product .ast-woo-product-category,
.ast-woo-product-category {
  font-size: var(--fs-xs);
  opacity: 1;
  color: var(--text-soft);
}

/* 🔴 手機的根字級是 14.592px，不是 16px。
   ─────────────────────────────────────────────────────────
   Astra 會依斷點縮 <html> 的 font-size（實測 390 寬時是 14.592px），
   而它自己的按鈕規則寫的是 `font-size: 1rem`——於是所有沒有被我們明確
   指定字級的第三方字串，在手機上會比桌機小一階，穿過 16px 的下限。

   我們自己的 CSS 全部走 --fs-* 這組**絕對 px** 的 token，所以不受影響；
   會中槍的只有 Woo／Astra 直接輸出的那些字。下面兩段就是在補這些。

   量法：不要只看 getComputedStyle。這個環境的樣式讀取會落後一次呼叫，
   實測有過「設了 !important 卻讀到舊值」。用 Range 量實際文字寬度交叉驗證：
   「查看購物車」五個中文字寬 75.5px ⇒ 每字 15.1px ⇒ 字級約 14.6px。 */

/* 按鈕類的字級。空購物車的「回到商店」是 .return-to-shop > a.button.wc-backward，
   不在 .woocommerce-info 裡（那是猜的，實測才知道），所以要各自列。
   按鈕字級一律走 --fs-xs，比內文小一階但仍在下限之上。 */
/* 🔴 這一組要寫到 (0,3,1)。上一版寫的是 .woocommerce-message .button（0,2,0），
   照理贏得過 Astra 的 .button（0,1,0），實測在 390 寬卻仍然是 14.592px。
   加一層 .woocommerce 祖先 ＋ 指定元素名之後才真的蓋掉。
   結論照舊：選擇器的深度要用量的，不要用推的。 */
.woocommerce .woocommerce-info a.button,
.woocommerce .woocommerce-message a.button,
.woocommerce .woocommerce-error a.button,
.woocommerce .return-to-shop a.button,
.woocommerce-info .button,
.woocommerce-message .button,
.woocommerce-error .button,
.woocommerce .return-to-shop .button,
.woocommerce .wc-backward,
.woocommerce .wc-forward,
.woocommerce a.button,
.woocommerce button.button,
.woocommerce input.button {
  font-size: var(--fs-xs);
}

/* 通知列本身的字（「已加入您的購物車」）。同樣的理由，同樣的深度。 */
.woocommerce .woocommerce-message,
.woocommerce .woocommerce-info,
.woocommerce .woocommerce-error {
  font-size: var(--fs-xs);
}

/* 🔴 商店頁的刪除線原價實測 2.03:1（Astra 預設把它壓得很淡）。
   首頁與商品頁我們自己那兩條已經修成 6.11:1，這裡補上同樣的處理，
   否則「選購」這個主導覽指過去的第一頁就是全站最不可讀的地方。
   等 archive-product.php 做出來，這一段可以整塊刪掉。 */
.woocommerce ul.products li.product .price del {
  color: var(--text-soft);
  opacity: 1;
}


/* 🔴 Astra 給單篇內容的每一張圖都加了陰影。
   ──────────────────────────────────────────
   它的動態 inline CSS 裡有這一條：

     .ast-article-single figure,
     .ast-article-single img:not(figure img) { box-shadow: 0 0 30px rgba(0,0,0,.15); }

   對一張**去背的 PNG**，陰影是照著元素的**矩形**畫的，不是照著圖形輪廓——
   所以去背圖會長出一個灰白色的方框，看起來就像「圖沒有去背」。
   2026-09-18 煮麵步驟圖示就是這樣：檔案本身透明（實測 hasAlpha yes、
   放在藍底上邊緣乾淨），但頁面上四張都帶著一個方塊。
   查的時候很容易往「圖檔沒去乾淨」的方向鑽，實際上一行 CSS 而已。

   我們自己的區塊從來沒有要過這個陰影（設計稿裡沒有任何一張圖有投影），
   所以把 .ns- 底下的圖一律關掉。Woo 的商品圖走 .ns-slot 的 <figure>，
   本來就被 Astra 自己的 :not(figure img) 排除，不受影響。

   特異性：Astra 是 (0,2,0)。這裡寫 .ast-article-single [class^="ns-"] 也是 (0,2,0)
   但載入較晚，贏得過去；為保險再多一層屬性選擇器。 */
.ast-article-single img[class*="ns-"],
.ast-article-single [class*="ns-"] img {
  box-shadow: none;
}

/* 表單標籤：Woo 寫死 700，而中文字型只載到 500。
   ────────────────────────────────────────────
   `.woocommerce-js form .form-row label` 是 (0,3,1)，我們在 account.css／flow.css
   寫的 `.ns-login__form label`（0,1,1）贏不了它，所以登入頁的標籤一直是 700
   ——而 700 沒有字面，瀏覽器合成偽粗體，中文糊掉。

   這裡用**一模一樣的選擇器**覆寫：特異性相同時後載入的贏，
   而這個檔案排在 Astra 與 Woo 之後。比再堆一層類別乾淨，
   也不必猜對方的 DOM 長怎樣。 */
.woocommerce-js form .form-row label,
.woocommerce form .form-row label {
  font-weight: var(--fw-text);
  /* 🔴 Astra 同一條還寫了 font-size: .9rem。桌機 14.4px、手機 13.1px（見下方 html 那段），
     都破 15px 下限。checkout 的 .ns-fields label 本來就是 --fs-2xs，所以這裡設同一個值
     只會把登入／忘記密碼頁拉上來，不會動到結帳頁。2026-09-25 稽核腳本量出來的。 */
  font-size: var(--fs-2xs);
}

/* 「保持登入」與 .screen-reader-text 走的是 <span>，同樣被 700 掃到。 */
.woocommerce-js form .form-row label span,
.woocommerce-form-login__rememberme span {
  font-weight: inherit;
}

/* 必填星號。Woo 是 `.woocommerce form .form-row .required`（0,3,1），
   忘記密碼頁不在 .ns-acct__content 裡，所以 account.css 那條蓋不到它——
   全站只剩這一個 700 就是它。同樣用相同選擇器覆寫。 */
.woocommerce-js form .form-row .required,
.woocommerce form .form-row .required {
  font-weight: var(--fw-text);
}

/* 密碼欄的顯示／隱藏眼睛。Woo 把它定位在 top:.7em 之類的絕對位置，
   而我們的欄位是 44px 高、標籤在上方——結果圖示騎在輸入框的上邊線上，
   一半在框外（2026-09-19 評審抓到）。改成在 44px 的框裡垂直置中。 */
.password-input { position: relative; display: block; }
/* 🔴 要 (0,4,2)：Woo 自己那條帶 top:22px＋負 margin＋translateY 的置中算式
   特異性高，第一版 (0,2,1) 靜靜輸掉，量出來反而更偏（-22 → -33）。
   這裡不猜對方的數字，直接 50% ＋ translateY(-50%) 對框置中。 */
.woocommerce form .form-row .password-input .show-password-input,
.woocommerce-js form .form-row .password-input .show-password-input {
  /* 🔴 用 bottom:0 不用 top:50%。量出來眼睛的定位祖先不是 span.password-input
     而是外層的 p.form-row（標籤 44 ＋ 輸入框 44 ＝ 88px），50% 會置中到標籤與
     輸入框的交界。而不管祖先是哪一個，它們的**底邊都等於輸入框的底邊**——
     貼底再給 44px 高，就一定落在輸入框裡。 */
  top: auto; bottom: 0; right: 0; margin: 0;
  height: 44px; width: 44px; transform: none;
  /* 🔴 還有一個 translate: 0 -50%——是 CSS 的 translate 屬性，不是 transform，
     getComputedStyle(...).transform 看不到它。量了三輪才抓到。 */
  translate: none;
}

/* placeholder：Astra／Woo 給的是 #9CA3AF（灰藍），在米底上約 2.5:1。
   全站共用的欄位提示字，弱視或強光下看不見。改用次要文字色。 */
input::placeholder, textarea::placeholder,
.woocommerce form .form-row input.input-text::placeholder,
.woocommerce form .form-row textarea::placeholder {
  color: var(--text-soft); opacity: 1;
}

/* 鍵盤焦點：Woo／Astra 對 .button 寫了 outline:none（特異性高過 base.css 的
   button:focus-visible），結果「登入」「加入購物車」「送出訂單」這些最重要的
   按鈕，Tab 到它們時什麼都看不到（2026-09-20 用真的 Tab 鍵量出來的）。
   在這裡用同等深度的選擇器補回全站一致的焦點外框。 */
.woocommerce .button:focus-visible,
.woocommerce-page .button:focus-visible,
.woocommerce button.button:focus-visible,
.woocommerce-button:focus-visible,
.woocommerce #respond input#submit:focus-visible,
.woocommerce a.button:focus-visible,
.woocommerce input.button:focus-visible,
.ns-btn:focus-visible {
  outline: 2px solid var(--accent);
  outline-offset: 2px;
}


/* ───────────────────────────────────────────────
   手機字級被 Astra 從外面縮掉
   ───────────────────────────────────────────────
   Astra 的動態 CSS（<style id="astra-theme-css-inline-css">）在 ≤921px 與 ≤544px
   各寫一條 html{font-size:91.2%}，手機上 html 變 14.592px。
   我們的字級 token 都是絕對 px，所以絕大多數文字沒事——這就是為什麼兩輪評審
   都沒看出來。但**靠繼承的**全部掉下去：Woo 用 .9rem 算的表單標籤（13.1px）、
   忘記密碼頁沒指定字級的 <p>（14.6px）、首頁 .ns-lede（14.6px）。
   09-18 待改清單 A6 那條就是它；那天 87d15e1 改了整組字級階卻沒修到，
   因為根因不在我們的階裡。

   同樣的兩個媒體查詢、同樣的 html 選擇器、這支檔案後載入 → 贏。
   不用 !important。2026-09-25。 */
@media (max-width: 921px) { html { font-size: 100%; } }
@media (max-width: 544px) { html { font-size: 100%; } }
