Web Animasyonları - item.animate() artık Chrome 36'da

Burçin Bilgili
Brendan Kenny

Web'de animasyon, bir zamanlar JavaScript'in alt alanıydı. Ancak dünya mobil cihazlara geçişle birlikte, bildirim temelli söz dizimi ve tarayıcıların bununla yapabildiği optimizasyonlar için animasyonlar CSS'ye taşındı. Hedefiniz her zaman mobil cihazlarda 60 fps olduğundan, tarayıcıların nasıl etkili bir şekilde görüntü alacağını bildiğinin dışına çıkmamak çok mantıklıdır.

JavaScript destekli animasyonları daha verimli hale getirmek için daha fazla araç kullanılıyor. Ancak en büyük izin, bildirici ve zorunlu animasyonların birleştirilmesidir. Bu animasyonların nasıl yazılacağına karar verilirken , bir biçimde mümkün olan ve olmayan kodlar değil, en net kod baz alınır.

Web Animasyonları bu çağrıyı yanıtlar ve ilk bölümü Chrome 36'ya element.animate() biçiminde gelir. Bu yeni işlev, yalnızca JavaScript'te animasyon oluşturmanıza ve animasyonun herhangi bir CSS Animasyonu veya Geçişi kadar verimli çalışmasını sağlamanıza olanak tanır (aslında Chrome 34'ten itibaren tüm bu yöntemlerin aynısı Web Animasyonları motoru çalışmaktadır).

Söz dizimi basittir ve daha önce bir CSS Geçişi veya Animasyon yazdıysanız bunların bölümleri size tanıdık gelecektir:

element.animate([
    {cssProperty: value0},
    {cssProperty: value1},
    {cssProperty: value2},
    //...
], {
    duration: timeInMs,
    iterations: iterationCount,
    delay: delayValue
});

Bu yeni işlevin en büyük avantajı, düzgün ve sorunsuz bir animasyon elde etmek için eskiden üzerinden atlamamız gereken birçok garip çemberin ortadan kaldırılmasıdır.

Örneğin, geçen yılki Santa Tracker için kar yağışının sürekli olmasını istiyorduk. Bu kadar etkili bir şekilde yapılabilmesi için karı CSS aracılığıyla canlandırmaya karar verdik.

Ancak, karın yatay konumunu, ekranda devam eden olaylara ve ekrana göre dinamik olarak seçmek istedik. Kar yağışının yüksekliği (kullanıcının tarayıcı penceresinin yüksekliği) biz gerçekten çalışmaya başlayana kadar bilinmiyor. Bu da CSS Geçişlerini kullanmamız gerektiği anlamına geliyordu. Çalışma zamanında CSS Animasyonu yazmak hızla karmaşıklaşıyor (ve yüzlerce kar tanesi, yüzlerce yeni stil kuralı anlamına geliyor).

Bu nedenle, size tanıdık gelen aşağıdaki yaklaşımı uyguladık:

snowFlake.style.transform = 'translate(' + snowLeft + 'px, -100%)';
// wait a frame
snowFlake.offsetWidth;
snowFlake.style.transitionProperty = 'transform';
snowFlake.style.transitionDuration = '1500ms';
snowFlake.style.transform = 'translate(' + snowLeft + 'px, ' + window.innerHeight + 'px)';

Burada en önemli nokta, "çerçeve bekleyin" yorumudur. Bir geçişi başarılı bir şekilde başlatmak için tarayıcının, öğenin başlangıç konumunda olduğunu onaylaması gerekir. Bunu yapmanın birkaç yolu vardır. En yaygın yollardan biri, tarayıcıyı düzeni hesaplamaya zorlayan öğe özelliklerinden birinden okuma yapmak, böylece öğenin bitiş konumuna geçmeden önce başlangıç konumunun olduğunu bilmesini sağlamaktır. Bu yöntemi kullanmak, her tuş vuruşunda kendinizi kötü hissedirken tarayıcının içindeki üst düzey bilginizi tebrik etmenize olanak tanır.

Buna karşılık, element.animate() çağrısının amacı tam olarak ve daha net bir şekilde ifade edilemez:

snowFlake.animate([
    {transform: 'translate(' + snowLeft + 'px, -100%)'},
    {transform: 'translate(' + snowLeft + 'px, ' + window.innerHeight + 'px)'}
], 1500);

Daha birçok seçenek var. CSS eşdeğerlerinde olduğu gibi Web Animasyonları da geciktirilip yinelenebilir:

snowFlake.animate([
    {transform: 'translate(' + snowLeft + 'px, -100%)'},
    {transform: 'translate(' + snowLeft + 'px, ' + window.innerHeight + 'px)'}
], {
    duration: 1500,
    iterations: 10,
    delay: 300
});

AnimationPlayer

element.animate() aslında bir AnimationPlayer nesnesi döndürüyor. Bu nesne, Web Animasyonları spesifikasyonunun lansmanıyla birlikte giderek önem kazanacak. JavaScript ve CSS tarafından oluşturulan animasyonların ilişkilendirildiği AnimationPlayers özellikleri, kullanışlı ve ilginç şekillerde sorunsuz bir şekilde birleştirilmelerine olanak tanır.

Ancak şimdilik AnimationPlayer'da her ikisi de son derece yararlı olan sadece iki işlev bulunmaktadır. Animasyonları istediğiniz zaman AnimationPlayer.cancel() kullanarak iptal edebilirsiniz:

var player = snowFlake.animate([
    {transform: 'translate(' + snowLeft + 'px, -100%)'},
    {transform: 'translate(' + snowLeft + 'px, ' + window.innerHeight + 'px)'}
], 1500);
// less than 1500ms later...changed my mind
player.cancel();

Ayrıca geçmişte CSS Animasyonları veya Geçişleri çerçevesinde bir animasyon sistemi oluşturmayı denemiş olan herkes için yardımcı olmak üzere, Web Animasyonları, sona erdiğinde her zaman bir etkinlik tetikler:

var player = snowFlake.animate([
    {transform: 'translate(' + snowLeft + 'px, -100%)'},
    {transform: 'translate(' + snowLeft + 'px, ' + window.innerHeight + 'px)'}
], 1500);
player.onfinish = function(e) {
    console.log('per aspera ad terra!');
}

Deneyin

Tüm gönderimler Chrome 36'da yapılır. Hemen beta sürümüne geçiyoruz! Denemek isterseniz Chrome 36'daki yerel uygulamayla çalışmayı deneyin. Ancak, tüm Web Animasyonları spesifikasyonunun önemli ölçüde büyük bir bölümünü modern ve her zaman kullanılabilen tarayıcıların herhangi birine getiren bir Web Animasyonları çoklu dolgusu vardır.

Kar efektinin demosunu hem yerel element.animate() sürümünü hem de polyfill kullanarak deneyebilirsiniz.

Düşüncelerinizi bizimle paylaşın

Bu, yakında olacakların bir önizlemesidir ve geliştiricilerden hemen geri bildirim almak amacıyla yayınlanmaktadır. Tüm kullanım alanlarını ele alıp almadığımızı veya animasyon için mevcut API'lerin tüm en kaba kenarlarını zımparalayıp uygulamadığımızdan emin değiliz. Bizim bunu bilmemizin ve doğru şekilde uygulamanın tek yolu, geliştiricilerin bunu deneyip düşüncelerini bize bildirmeleridir.

Bu yayındaki yorumlar elbette önemlidir. Standardın kendisinde yapılan yorumlar public-fx posta listesi aracılığıyla CSS ve SVG Çalışma Gruplarına gönderilebilir.

Güncelleme, Ekim 2014: Chrome 39, oynatmanın kontrol edilmesiyle ilgili play(), pause() ve reverse() gibi çeşitli ek yöntemler için destek sağlar. currentTime özelliği aracılığıyla bir animasyonun zaman çizelgesinde belirli bir noktaya atlamayı da destekler. Söz konusu işlevin nasıl çalıştığını bu yeni demoda görebilirsiniz.

Bu yayınla ilgili yardımları için Addy Osmani ve Max Heinritz'e teşekkür ederiz.