CSS秘密花園: 動畫狀態
《 CSS Secrets 》是 @Lea Verou 最新著作,這本書講解了有關于CSS中一些小秘密。是一本CSSer值得一讀的一本書,經過一段時間的閱讀,我、@南北和@彥子一起將在W3cplus發布一系列相關的讀后感,與大家一起分享。
問題
動畫并不總是頁面加載的時候就開始。往往,我們都想通過用戶的操作來觸發動畫,比如鼠標的懸浮( :hover )或者鼠標按下時( :active )。在這種情況之下,我們可能沒辦法控制動畫播放的實妹次數,用戶可能會迫使動畫停止。例如,用戶有通過懸浮( :hover )觸發動畫:鼠標移出元素之前動畫結束。在這樣的例子中會發生什么呢?
如果你的回答是“動畫應該會呆其當前狀態”或者“動畫會順利的過渡到前置狀態”。默認情況下,動畫就會停下來,突然跳到最初始狀態。有時候可能會接受這種非常微妙的動畫。但在大多數情況下它直接影響用戶的體驗。那么我們可以改變這種行為嗎?
我決定拿一個 簡單的頁面 來說明這個問題(這個頁面是我當作禮物送給我朋友Julian的)。注意右邊圓形中的圖片,當用戶鼠標懸停在圓形上時,圓形中的圖片慢慢開始向左滾動,顯示被隱藏的那部分。默認情況,當用戶鼠標移出圓形圖片時,圖片會立即回到原來的位置,這給人感覺體驗不好。因為這是一個小網站,而這張圖片又是該網站核心部分,我不能睜一眼閉一眼,必須得把這個問題給解決。
解決方案
假設我們一個很長的景觀照片,如下圖所示:
但我們要顯示的空間只有 150px X 150px 的正方形。解決這個問題的一個方法就需要使用動畫:默認顯示圖像的從圖像的左邊緣開始,當用戶有交互行為時,圖片慢慢向左滾動(例如,鼠標懸浮在圖片上時)。我們使用單個元素,并且給他設置一個背景圖片,通過動畫修改 background-position 值來實現。
<div class="panoramic"></div>
.panoramic {
width: 150px;
height: 150px;
background: url("img/naxos-greece.jpg");
background-size: auto 100%;
}
目前,它看起來如下圖所示:
沒有動畫和任何交互效果。我們來實戰一回,我們可以看到,原來是手動的修改 background-position 從 0 0 到 0 100% 來修改整個背景圖像。下面我們來嘗試使用 keyframes 來做:
@keyframes panoramic {
to {
background-position: 100% 0;
}
}
.panoramic {
width: 150px;
height: 150px;
background: url("img/naxos-greece.jpg");
background-size: auto 100%;
animation: panoramic 10s linear infinite alternate;
}
它能正常的運行。效果看起來就像一個全景,從左向右看。然而,而面加載動畫就被觸發,這樣一來可能會分散用戶的集中力,例如,旅游網頁,用戶可能會試著只專注于閱讀有關于納克索斯島(Naxos)相關文本,而不是看著美麗的全景照片。當用戶鼠標懸浮在圖片上時,才觸發動畫,這樣看起來更形象。所以,我們首先想的方案就是這樣的。
.panoramic {
width: 150px;
height: 150px;
background: url("img/naxos-greece.jpg");
background-size: auto 100%;
}
.panoramic:hover,
.panoramic:focus {
animation: panoramic 10s linear infinite alternate;
}
當鼠標懸浮在圖片上時動畫被觸發:初始狀態顯示圖像的最左邊的部分,慢慢滾動顯示圖像的其他部分。然而,當我們的鼠標移出圖像時,圖像又突然跳到圖像的最左邊,如下圖所示:
我也是無意之中發現這個問題。
為了解決這個問題,我們要想個辦法來解決。我們需要的是不應用動畫,這意味著 :hover 無法記憶動畫的當前位置。我們需要的是鼠標懸浮在圖片是有動畫,圖片從左向右移動,鼠標移出圖片時,動畫暫停。值得慶幸的是,動畫有一個屬性 animation-play-state 可以實現這樣的效果。
因此,我們把動畫的暫停狀態運用在 .panoramic 上,而鼠標懸浮狀態( :hover )時又播放動畫。因為它不再是播放和取消一個動畫,只是暫停和恢復現有的動畫,這樣動畫不會有突然跳躍。最后的代碼和效果如下:
.panoramic {
width: 150px;
height: 150px;
background: url("http://www.w3cplus.com/sites/default/files/blogs/2015/1507/naxos-greece-big.jpg");
background-size: auto 100%;
animation: panoramic 10s linear infinite alternate;
animation-play-state: paused;
}
.panoramic:hover,
.panoramic:focus {
animation-play-state: running;
}
@keyframes panoramic {
to {
background-position: 100% 0;
}
}
來自: http://www.w3cplus.com/css3/css-secrets/smooth-state-animations.html