使用 translate
、rotate
和 scale
屬性轉換元素
CSS transform
屬性
如要將轉換效果套用至元素,請使用 CSS transform
屬性。這個屬性可接受一或多個 <transform-function>
,並依序套用。
.target {
transform: translateX(50%) rotate(30deg) scale(1.2);
}
指定的元素會在 X 軸上平移 50%,旋轉 30 度,最後縮放至 120%。
雖然 transform
屬性運作正常,但如果您想個別變更其中任何值,就會覺得有些麻煩。
如要變更懸停時的縮放比例,您必須複製轉換屬性中的所有函式,即使這些函式的值保持不變也一樣。
.target:hover {
transform: translateX(50%) rotate(30deg) scale(2); /* Only the value of scale() changed */
}
個別轉換屬性
在 Chrome 104 中推出的 CSS 轉換屬性。這些屬性分別是 scale
、rotate
和 translate
,可用於個別定義轉換作業的各個部分。
這樣一來,Chrome 就會加入 Firefox 和 Safari 的行列,這兩款瀏覽器已支援這些屬性。
使用個別屬性重寫上述 transform
範例,程式碼片段會變成這樣:
.target {
translate: 50% 0;
rotate: 30deg;
scale: 1.2;
}
順序很重要
原始 CSS transform
屬性和新屬性之間的一個主要差異,是宣告的轉換套用順序。
使用 transform
時,系統會依照函式寫入的順序套用轉換函式,也就是從左 (外側) 到右 (內側)。
個別轉換屬性中的順序並非宣告的順序。順序一律相同:先 translate
(外部)、rotate
、scale
(內部)。
也就是說,以下兩個程式碼片段會產生相同的結果:
.transform--individual {
translate: 50% 0;
rotate: 30deg;
scale: 1.2;
}
.transform--individual-alt {
rotate: 30deg;
translate: 50% 0;
scale: 1.2;
}
在兩種情況下,指定的元素會先在 X 軸上以 50%
進行平移,然後以 30deg
旋轉,最後以 1.2
縮放。
如果其中一個個別轉換屬性與 transform
屬性一併宣告,系統會先套用個別轉換 (translate
、rotate
,然後是 scale
),最後再套用 transform
(內部)。如需進一步瞭解如何計算轉換矩陣,請參閱相關規格。
動畫
我們之所以新增這些屬性,主要是為了讓動畫更容易製作。假設您想為元素建立動畫,如下所示:
使用transform
如要使用 transform
實作這項動畫,您必須計算所有定義轉換的所有中間值,並將這些值納入每個主要影格。舉例來說,如要在 10% 處進行旋轉,則必須計算其他轉換的值,因為 transform
屬性需要所有轉換。
產生的 CSS 程式碼如下:
@keyframes anim {
0% { transform: translateX(0%); }
5% { transform: translateX(5%) rotate(90deg) scale(1.2); }
10% { transform: translateX(10%) rotate(180deg) scale(1.2); }
90% { transform: translateX(90%) rotate(180deg) scale(1.2); }
95% { transform: translateX(95%) rotate(270deg) scale(1.2); }
100% { transform: translateX(100%) rotate(360deg); }
}
.target {
animation: anim 2s;
animation-fill-mode: forwards;
}
使用個別轉換屬性
有了個別的轉換屬性,這項作業就變得更容易編寫。您可以個別指定每個轉換,而非將所有轉換從一個主要畫面格拖曳到另一個主要畫面格。您也不必再計算所有中間值。
@keyframes anim {
0% { translate: 0% 0; }
100% { translate: 100% 0; }
0%, 100% { scale: 1; }
5%, 95% { scale: 1.2; }
0% { rotate: 0deg; }
10%, 90% { rotate: 180deg; }
100% { rotate: 360deg; }
}
.target {
animation: anim 2s;
animation-fill-mode: forwards;
}
使用個別轉換屬性和多個關鍵影格
如要將程式碼分割成模組,您可以將每個子動畫分割成各自的一組主要畫面格。
@keyframes move {
0% { translate: 0% 0; }
100% { translate: 100% 0; }
}
@keyframes scale {
0%, 100% { scale: 1; }
5%, 95% { scale: 1.2; }
}
@keyframes rotate {
0% { rotate: 0deg; }
10%, 90% { rotate: 180deg; }
100% { rotate: 360deg; }
}
.target {
animation: move 2s, scale 2s, rotate 2s;
animation-fill-mode: forwards;
}
有了這個分割功能,您可以隨心所欲套用各個獨立的關鍵影格,因為 transform
屬性 (現在已成為個別屬性) 不再互相覆寫。您可以為每個轉換設定不同的時間,而不需要重新編寫整個批次。
成效
使用這些新屬性的動畫,效率與現有 transform
屬性的動畫一樣高。
translate
、rotate
和 scale
的動畫會在合成器上執行,而這與 transform
的動畫執行方式相同,因此與 transform
一樣,這些動畫的效能表現也相當出色。
這些新屬性也適用於 will-change
屬性。一般來說,建議您避免過度使用 will-change
,請在最少數量的元素上使用,並盡可能縮短使用時間。但也建議您盡可能提供具體資訊。舉例來說,如果您使用 will-change
搭配 rotate
和 filter
屬性,來改善動畫效果,則應使用 will-change: rotate, filter
進行宣告。在為 rotate
和 filter
製作動畫時,使用 will-change
比使用 will-change: transform, filter
稍微好一些,因為 Chrome 在使用 will-change
時預先建立的部分資料結構,在 transform
和 rotate
之間有所不同。