容器查詢隆重登場!
令人期待的消息:網頁瀏覽器上開始出現眾所期盼的其中一項開發人員功能!自 Chromium 105 和 Safari 16 推出後,您現在可以在這些瀏覽器中建立以大小為依據的容器查詢,並使用容器查詢單位值。為了更容易使用以大小為依據的容器查詢和 cq
單位,Aurora 團隊不斷努力更新容器查詢 Polyfill,以支援更多瀏覽器和使用情境,讓您可放心立即使用這項強大的功能。
什麼是容器查詢?
容器查詢是 CSS 功能,可讓您編寫樣式邏輯,指定父項元素的地圖項目來設定子項的樣式。您可以查詢父項的大小,建立真正以元件為基礎的回應式設計。這項資訊比媒體查詢更精細且實用,後者只會提供檢視區大小資訊。
透過容器查詢,您可以編寫可重複使用的元件,這些元件的外觀會根據網頁在頁面中的位置而不同。這麼做可讓這些元素在各個網頁和範本中更有彈性,回應速度也更快。
使用容器查詢
假設您具備 HTML:
<!-- card parent -->
<div class=”card-parent”>
<div class=”card>
<!-- card contents -->
…
</div>
</div>
如要使用容器查詢,請先為您要追蹤的父項元素設定包含項目。如要執行這項操作,請設定 container-type
屬性,或是使用 container
速記法來同時設定容器類型和容器名稱。
.card-parent {
/* query the inline-direction size of this parent */
container-type: inline-size;
}
您現在可以使用 @container
規則,根據最近的父項設定樣式。在如上圖這樣的設計中,資訊卡可能從一欄轉換為兩欄,如下所示:
@container (min-width: 300px) {
.card {
/* styles to apply when the card container (.card-parent in this case) is >= 300px */
/* I.e. shift from 1-column to 2-column layout: */
grid-template-columns: 1fr 1fr;
}
}
為了讓內容更整齊明確,請為父項元素容器命名:
.card-parent {
container-type: inline-size;
/* set name here, or write this in one line using the container shorthand */
container-name: card-container;
}
然後將先前的程式碼重新編寫為:
@container card-container (min-width: 300px) {
.card {
grid-template-columns: 1fr 1fr;
}
}
容器查詢單元
如要讓容器查詢更實用,您也可以使用以容器為基礎的單位值。下表列出可能的容器單位值,以及這些值與容器大小對應的方式:
單位 | 相對於 |
---|---|
cqw | 查詢容器寬度的 1% |
cqh | 查詢容器高度的 1% |
cqi | 查詢容器內嵌大小的 1% |
cqb | 查詢容器的 1% 區塊大小 |
cqmin | cqi 或 cqb 的較小值 |
cqmax | cqi 或 cqb 較大的值 |
回應式字體排版就是使用容器式單元的方法之一。以檢視區為基礎的單位 (例如 vh
、vb
、vw
和 vi
) 可用於調整螢幕上任何元素的大小。
.card h2 {
font-size: 15cqi;
}
這段程式碼將使容器內嵌大小 (寬度) 的字型變大 15%,代表文字會隨著內嵌大小 (寬度) 增加或縮小而變大。如要進一步達成這個目的,請使用 clamp()
函式設定字體排版的最小和最大尺寸限制,並根據容器大小進行調整:
.card h2 {
font-size: clamp(1.5rem, 15cqi, 3rem);
}
現在標頭一律不會大於 3rem
或小於 .5rem
,但會在容器之間任何位置佔用 15% 的容器內嵌大小。
這項示範可進一步進一步,將較寬的資訊卡調整為縮小範圍,以 2 欄呈現。
容器查詢 polyfill
容器查詢是一項強大的功能,因此我們希望您能自在將這項查詢整合至專案中,也瞭解到瀏覽器支援是重要的一環。因此,我們一直致力於改善容器查詢填充功能。這個 polyfill 一般支援以下項目:
- Firefox 69 以上版本
- Chrome 79 以上版本
- Edge 79 以上版本
- Safari 13.4 以上版本
壓縮後的檔案大小不到 9 KB,並搭配使用 ResizeObserver 和 MutationObserver,以支援目前在穩定版瀏覽器中提供的完整 @container 查詢語法:
- 離散查詢 (
width: 300px
和min-width: 300px
)。 - 範圍查詢 (
200px < width < 400px
和width < 400px
)。 - 屬性和主要畫面格中的容器相對長度單位 (
cqw
、cqh
、cqi
、cqb
、cqmin
和cqmax
)。
使用容器查詢 polyfill
如要使用 polyfill,請在文件標頭中加入以下指令碼標記:
<script type="module">
if (!("container" in document.documentElement.style)) {
import("https://unpkg.com/container-query-polyfill@^0.2.0");
}
</script>
您也可以使用服務,根據 User-Agent
條件式地提供 polyfill,或在自己的原點上自行代管。
為提供最佳使用者體驗,建議您一開始只對需捲動位置的內容使用 polyfill,並使用 @supports
查詢暫時將其替換為載入指標,直到 polyfill 準備好顯示為止:
@supports not (container-type: inline-size) {
.container,
footer {
display: none;
}
.loader {
display: flex;
}
}
在網路和裝置速度足夠快的情況下,或是裝置原生支援容器查詢時,系統不會顯示這項載入指標。
新的 Polyfill 功能
更新後的 polyfill 可支援:
- 巢狀
@container
規則。 - 支援在
@supports
和@media
查詢下建立巢狀@container
規則,反之亦然。 - 在 polyfill 載入後,
@supports (container-type: inline-size)
等條件 CSS 會通過。 - 完整的 CSS 語法支援 (使用註解放在任何語法皆有效時不再出現問題)。
- 垂直書寫模式 (透過寫入模式)。
- 查詢條件、屬性宣告和動畫主要畫面格內支援容器相對單元 (
cqw
、cqh
等)。 查詢條件支援rem
和em
。 - 展開的容器查詢語法:
- 範圍語法 (例如
(200px < width < 400px)
)。 - 等式查詢 (例如
(width = 200px)
)。
- 範圍語法 (例如
- 虛擬元素,例如
::before
和::after
。 - 透過選用的解決方法,支援沒有
:is(...)
/:where(...)
的瀏覽器 orientation
和aspect-ratio
功能查詢。- 根據功能正確篩選查詢 (例如,在水平書寫模式下,禁止查詢
container: inline-size
上的height
)。 - DOM 異動 (例如,在執行階段移除
<style>
和<link>
元素)。
多重填充限制和警告
如果您使用的是容器查詢 polyfill,其中有幾個功能需要留意:
- 目前尚不支援 Shadow DOM。
@media
查詢條件不支援容器相對單元 (例如cqw
和cqh
)。- Safari:在 15.4 之前的版本中,動畫關鍵影格不支援容器相對單位。
- 查詢條件尚不支援
calc()
、min()
、max()
或其他數學函式。 - 這個 polyfill 僅適用於內嵌和相同來源 CSS。不支援跨來源樣式表和 iframe 中的樣式表 (除非手動載入 polyfill)。
layout
和style
隔離功能需要基礎瀏覽器支援:- Safari 15.4 以上版本
- Firefox 目前不支援樣式包容,但我們正在開發這項功能。
警告
- 為避免影響 FID 和 CLS,即使已同步載入第一個版面配置,Polyfill 也無法保證第一個版面配置的發生時間,但會盡量避免嚴重延遲 LCP。換句話說,您不應將其用於首次繪製。
- 產生
ResizeObserver Loop Errors
。原始的 polyfill 也會執行這項操作,但值得一提的是,這是因為container-type: inline-size
的區塊大小在評估查詢後可能會變更,但ResizeObserver
無法告知系統我們不關心區塊大小變更。 - 這個 polyfill 是根據 Web Platform 測試進行測試,且由於 JavaScript API 等某些功能未經聚合處理,因此傳遞率為 70%,因此傳遞率刻意接近 70%。
- 2.23% 使用舊版瀏覽器的使用者必須採用
:where()
解決方法:- Safari 14
- Chromium 88
- Edge 88
- Samsung Internet 15
- Firefox 78