CSS'de kaydırmaya dayalı animasyonları kullanmaya başlama

1. Başlamadan önce

Kaydırma odaklı animasyonlar, bir animasyonu oynatmayı kaydırma kapsayıcısının kaydırma konumuna göre kontrol etmenize olanak tanır. Bu, siz yukarı veya aşağı kaydırırken animasyonun ileri veya geri sarmalandığı anlamına gelir. Ayrıca, kaydırma odaklı animasyonlarla bir animasyonu, öğenin kaydırma kapsayıcısındaki konumuna göre de kontrol edebilirsiniz. Bu sayede paralaks arka plan resmi, kaydırma ilerleme çubukları ve görüntüye geldikçe ortaya çıkan resimler gibi ilginç efektler oluşturabilirsiniz.

Chrome 115'te, kaydırmayla çalışan beyanlarda animasyonlar oluşturmanıza olanak tanıyan bir dizi JavaScript sınıfı ve CSS özelliği desteği eklendi. Bu yeni API'ler mevcut Web Animasyonları ve CSS Animasyonları API'leriyle birlikte çalışır.

Bu codelab'de, CSS kullanarak kaydırmayla çalışan animasyonlar oluşturmayı öğreneceksiniz. Bu kod laboratuvarını tamamlayarak bu heyecan verici özellik tarafından sunulan scroll-timeline, view-timeline, animation-timeline ve animation-range gibi birçok yeni CSS özelliğiyle tanışabilirsiniz.

Neler öğreneceksiniz?

  • CSS'de kaydırma zaman çizelgesi ile paralaks arka plan efekti oluşturma.
  • CSS'de kaydırma zaman çizelgesi içeren bir ilerleme çubuğu oluşturma.
  • CSS'de görüntü zaman çizelgesi ile resim gösterme efekti oluşturma.
  • CSS'de bir görüntüleme zaman çizelgesinin farklı türdeki aralıklarını hedefleme.

İhtiyacınız olanlar

Aşağıdaki cihaz kombinasyonlarından biri:

  • ChromeOS, macOS veya Windows'ta "Deneysel Web Platformu Özellikleri" işareti etkin olarak ayarlanmış, Chrome'un son sürümlerinden biri (115 veya daha yeni).
  • HTML hakkında temel düzeyde bilgi
  • CSS'yi ve özellikle CSS'deki animasyonları temel düzeyde anlama

2. Hazırlanın

Bu proje için ihtiyacınız olan her şey GitHub deposunda mevcuttur. Başlamak için kodu klonlayın ve favori geliştirme ortamınızda açın.

  1. Yeni bir tarayıcı sekmesi açıp https://github.com/googlechromelabs/io23-scroll-driven-animations-codelab adresine gidin.
  2. Depoyu klonlayın.
  3. Kodu tercih ettiğiniz IDE'de açın.
  4. Bağımlılıkları yüklemek için npm install'ü çalıştırın.
  5. npm start dosyasını çalıştırın ve http://localhost:3000/ adresini ziyaret edin.
  6. Alternatif olarak, npm yüklü değilse Chrome'da src/index.html dosyasını açın.

3. Animasyon zaman çizelgeleri hakkında bilgi

Bir öğeye eklenen animasyon varsayılan olarak belge zaman çizelgesinde çalışır. Yani sayfa yüklendiğinde, zaman ilerledikçe animasyon da ileri doğru ilerler. Bu, varsayılan animasyon zaman çizelgesidir ve şimdiye kadar erişebildiğiniz tek animasyon zaman çizelgesidir.

Kaydırmayla çalışan animasyonlar sayesinde iki yeni zaman çizelgesi türüne erişebilirsiniz:

  • İlerleme zaman çizelgesini kaydırın
  • İlerleme Zaman Çizelgesini Görüntüleme

CSS'de bu zaman çizelgeleri, animation-timeline özelliği kullanılarak bir animasyona eklenebilir. Bu yeni zaman çizelgelerinin ne anlama geldiğine ve birbirlerinden nasıl farklı olduğuna göz atın.

İlerleme zaman çizelgesini kaydırın

Kaydırma ilerleme zaman çizelgesi, belirli bir eksen boyunca kaydırma kapsayıcısının (kaydırma alanı veya kaydırma çubuğu olarak da bilinir) kaydırma konumundaki ilerlemeyle bağlantılı bir animasyon zaman çizelgesidir. Kaydırma aralığındaki bir konumu, zaman çizelgesinde ilerleme yüzdesine dönüştürür.

Başlangıç kaydırma konumu% 0 ilerlemeyi, bitiş kaydırma konumu ise% 100 ilerlemeyi temsil eder. Aşağıdaki görselleştirmede, kaydırma çubuğunu aşağı kaydırdığınızda ilerlemenin% 0'dan% 100'e doğru arttığını görebilirsiniz.

İlerleme Zaman Çizelgesini Görüntüleme

Bu zaman çizelgesi türü, kaydırma kapsayıcısındaki belirli bir öğenin göreceli ilerleme durumuna bağlıdır. Kaydırma ilerleme zaman çizelgesi gibi, kaydırma çubuğunun kaydırma ofseti de izlenir. Kaydırma ilerleme zaman çizelgesinin aksine, ilerlemeyi belirleyen, bir öznenin kaydırma çubuğu içindeki göreli konumudur. Bu, bir öğenin kaydırma çubuğunda ne kadar görünür olduğunu izleyen IntersectionObserver ile benzerdir. Öğe kaydırma çubuğunda görünmüyorsa kesişme yoktur. Kaydırma çubuğunun içinde görünüyorsa (en küçük parçada bile) kesişiyor demektir.

Görüntüleme İlerleme Zaman Çizelgesi, bir öznenin kaydırma çubuğuyla kesişmeye başladığı andan başlar ve öznenin kaydırma çubuğuyla kesişmeyi bıraktığı anda sona erer. Aşağıdaki görselde, özne kaydırma kapsayıcısına girdiğinde ilerlemenin% 0'dan başlayıp kaydırma kapsayıcısından çıktığında% 100'e ulaştığını görebilirsiniz.

Varsayılan olarak, ilerleme durumunu görüntüleme zaman çizelgesine bağlı bir animasyon, zaman çizelgesinin tamamına eklenir. Bu işlem, öznenin kaydırma alanına girdiği andan başlar ve öznenin kaydırma alanından çıktığı anda sona erer.

Ayrıca, ekleneceği aralığı belirterek ilerleme durumunu görüntüleme zaman çizelgesinin belirli bir bölümüne bağlayabilirsiniz. Örneğin, bu durum yalnızca özne kaydırma çubuğuna girerken olabilir. Aşağıdaki görselleştirmede, özne kaydırma kapsayıcısına girdiğinde ilerleme% 0'dan saymaya başlar ancak tamamen kesiştiği andan itibaren% 100'e ulaşır.

Hedefleyebileceğiniz olası Zaman Çizelgesi görüntüleme aralıkları cover, contain, entry, exit, entry-crossing ve exit-crossing'dir. Bu aralıklar bu kod laboratuvarının ilerleyen bölümlerinde açıklanmaktadır ancak öğrenmek için sabırsızlanıyorsanız her bir aralığın neyi temsil ettiğini görmek için https://goo.gle/view-timeline-range-tool adresindeki aracı kullanın.

4. Paralaks arka plan efekti oluşturma

Sayfaya eklenecek ilk efekt, ana arka plan resminde paralaks arka plan efektidir. Sayfayı aşağı kaydırdığınızda arka plan resmi farklı bir hızda hareket eder. Bunun için bir Kaydırma İlerleme Zaman Çizelgesi'ne güvenirsiniz.

Bunu uygulamak için iki adım uygulanmalıdır:

  1. Arka plan resminin konumunu değiştiren bir animasyon oluşturun.
  2. Animasyonu, dokümanın kaydırma ilerleme durumuna bağlayın.

Animasyonu oluşturma

  1. Animasyonu oluşturmak için normal bir animasyon karesi grubu kullanın. Burada, arka plan konumunu dikey olarak% 0'dan %100'e taşıyın:

src/styles.css

@keyframes move-background {
  from {
    background-position: 50% 0%;
  }
  to {
    background-position: 50% 100%;
  }
}
  1. Ardından bu animasyon karelerini body öğesine ekleyin:

src/styles.css

body {
  animation: 1s linear move-background;
}

Bu kodla move-background animasyonu body öğesine eklenir. animation-duration özelliği bir saniyeye ayarlanmış ve linear yumuşatma kullanılmıştır.

Kaydırma ilerleme zaman çizelgesi oluşturmanın en kolay yolu scroll() işlevini kullanmaktır. Bu işlem, animation-timeline mülkünün değeri olarak ayarlayabileceğiniz anonim bir Kaydırma İlerleme Zaman Çizelgesi oluşturur.

scroll() işlevi bir <scroller> ve bir <axis> bağımsız değişkeni kabul eder.

<scroller> bağımsız değişkeni için kabul edilen değerler şunlardır:

  • nearest. En yakın üst öğe kaydırma kapsayıcısını kullanır (varsayılan).
  • root. Kaydırma kapsayıcısı olarak doküman görüntü alanını kullanır.
  • self. Kaydırma kapsayıcısı olarak öğenin kendisini kullanır.

<axis> bağımsız değişkeni için kabul edilen değerler şunlardır:

  • block. Kaydırma kapsayıcının blok ekseni boyunca ilerleme ölçümünü kullanır (varsayılan).
  • inline. Kaydırma kapsayıcının satır içi ekseni boyunca ilerleme ölçümünü kullanır.
  • y. Kaydırma kapsayıcının y ekseni boyunca ilerleme ölçümünü kullanır.
  • x. Kaydırma kapsayıcının x ekseni boyunca ilerleme ölçümünü kullanır.

Animasyonu, blok eksenindeki kök kaydırma çubuğuna bağlamak için scroll() parametresine root ve block değerleri gönderilir. Bu değerlerin toplamı scroll(root block)'tür.

  • Gövdedeki animation-timeline özelliğinin değeri olarak scroll(root block) değerini ayarlayın.
  • Ayrıca, saniye cinsinden ifade edilen bir animation-duration anlamlı olmadığından süreyi auto olarak ayarlayın. animation-duration belirtmezseniz varsayılan olarak auto olur.

src/styles.css

body {
  animation: linear move-background;
  animation-duration: auto;
  animation-timeline: scroll(root block);
}

Kök kaydırma çubuğu, body öğesi için en yakın üst kaydırma çubuğu olduğundan nearest değerini de kullanabilirsiniz:

src/styles.css

body {
  animation: linear move-background;
  animation-duration: auto;
  animation-timeline: scroll(nearest block);
}

nearest ve block varsayılan değerler olduğundan bunları atlamayı bile seçebilirsiniz. Bu durumda kod şu şekilde basitleştirilebilir:

src/styles.css

body {
  animation: linear move-background;
  animation-duration: auto;
  animation-timeline: scroll();
}

Değişikliklerinizi doğrulama

Her şey yolunda gittiyse şuna sahip olursunuz:

Aksi takdirde, kodun solution-step-1 şubesine göz atın.

5. Resim galerisi için ilerleme çubuğu oluşturma

Sayfada, şu anda hangi fotoğrafı görüntülediğinizi gösteren bir ilerleme çubuğuna ihtiyaç duyulan yatay bir bant var.

Bant için işaretleme şu şekilde görünür:

src/index.html

<div class="gallery">
  <div class="gallery__scrollcontainer" style="--num-images: 3;">
    <div class="gallery__progress"></div>
    <div class="gallery__entry">
      ...
    </div>
    <div class="gallery__entry">
      ...
    </div>
    <div class="gallery__entry">
      ...
    </div>
  </div>
</div>

İlerleme çubuğunun ana kareleri zaten mevcuttur ve şu şekilde görünür:

src/styles.css

@keyframes adjust-progress {
  from {
    transform: scaleX(calc(1 / var(--num-images)));
  }
  to {
    transform: scaleX(1);
  }
}

Bu animasyonun .Kaydırma ilerleme zaman çizelgesi içeren bir gallery__progress öğesi. Önceki adımda gösterildiği gibi, scroll() işleviyle anonim bir Kaydırma İlerleme Zaman Çizelgesi oluşturarak bunu yapabilirsiniz:

src/styles.css

.gallery__progress {
  animation: linear adjust-progress;
  animation-duration: auto;
  animation-timeline: scroll(nearest inline);
}

Bu kod parçası işe yarayabilir gibi görünse de nearest kullanan otomatik kaydırma kapsayıcısı aramalarının işleyiş şekli nedeniyle işe yaramaz. Öğe, en yakın kaydırma çubuğunu ararken yalnızca konumunu etkileyebilecek öğeleri dikkate alır. .gallery__progress mutlak olarak konumlandırıldığı için konumunu belirleyecek ilk üst öğe, position: relative uygulandığı için .gallery öğesidir. Bu, hedeflenmesinin gerektiği kaydırma çubuğu olan .gallery__scrollcontainer öğesinin bu otomatik arama sırasında hiç dikkate alınmadığı anlamına gelir.

Bu sorunu gidermek için .gallery__scrollcontainer öğesinde adlandırılmış bir Kaydırma İlerleme Zaman Çizelgesi oluşturun ve .gallery__progress öğesini bu adı kullanarak ona bağlayın.

Bir öğede adlandırılmış bir kaydırma ilerleme zaman çizelgesi oluşturmak için kaydırma kapsayıcısındaki scroll-timeline-name CSS mülkünü istediğiniz bir değere ayarlayın. Değer -- ile başlamalıdır.

Galeri yatay olarak kaydırılacağından scroll-timeline-axis mülkünü de ayarlamanız gerekir. İzin verilen değerler, scroll() işlevinin <axis> bağımsız değişkeniyle aynıdır.

Son olarak, animasyonu Kaydırma İlerleme Zaman Çizelgesi'ne bağlamak için animasyon uygulanması gereken öğedeki animation-timeline mülkünü, scroll-timeline-name için kullanılan tanımlayıcıyla aynı değere ayarlayın.

  • styles.css dosyasını aşağıdakileri içerecek şekilde değiştirin:

src/styles.css

.gallery__scrollcontainer {
  /* Create the gallery-is-scrolling timeline */
  scroll-timeline-name: --gallery-is-scrolling;
  scroll-timeline-axis: inline;
}

.gallery__progress {
  animation: linear adjust-progress;
  animation-duration: auto;
  /* Set gallery-is-scrolling as the timeline */
  animation-timeline: --gallery-is-scrolling;
}

Değişikliklerinizi doğrulama

Her şey yolunda gittiyse şuna sahip olursunuz:

Aksi takdirde, kodun solution-step-2 şubesine göz atın.

6. Kaydırma çubuğuna girip çıkarken galeri resimlerine animasyon ekleme

Anonim görüntüleme ilerleme zaman çizelgesi oluşturma

Galeri resimlerinin görünüme girerken yavaşça belirmesi gibi güzel bir efekt ekleyebilirsiniz. Bunun için İlerleme Zaman Çizelgesi'ni görüntüleyebilirsiniz.

Görüntüleme ilerleme zaman çizelgesi oluşturmak için view() işlevini kullanabilirsiniz. Kabul edilen bağımsız değişkenleri <axis> ve <view-timeline-inset>'dır.

  • <axis>, Kaydırma İlerleme Zaman Çizelgesi'ndekiyle aynıdır ve hangi eksenin izleneceğini tanımlar.
  • <view-timeline-inset> ile, bir öğenin görünümde olup olmadığına göre sınırları ayarlamak için bir ofset (pozitif veya negatif) belirtebilirsiniz.
  • Animasyon kareleri zaten mevcuttur. Bunları eklemeniz yeterlidir. Bunun için her .gallery__entry öğesinde bir Görüntüleme İlerleme Zaman Çizelgesi oluşturun.

src/styles.css

@keyframes animate-in {
  from {
    opacity: 0;
    clip-path: inset(50% 0% 50% 0%);
  }
  to {
    opacity: 1;
    clip-path: inset(0% 0% 0% 0%);
  }
}

.gallery__entry {
  animation: linear animate-in;
  animation-duration: auto;
  animation-timeline: view(inline);
}

Görüntüleme ilerleme zaman çizelgesinin aralığını sınırlama

CSS'yi kaydedip sayfayı yüklerseniz öğelerin belirdiğini görürsünüz ancak bir şeylerin yanlış olduğu anlaşılır. Öğeler tamamen görünmezken 0 saydamlıkta başlar ve tamamen ekrandan çıktığında yalnızca 1 saydamlıkta sona erer.

Bunun nedeni, görüntüleme ilerleme zaman çizelgesi için varsayılan aralığın tam aralığı olmasıdır. Buna cover aralığı denir.

  1. Öznenin yalnızca entry aralığını hedeflemek için animasyonun ne zaman çalışacağını sınırlamak üzere animation-range CSS özelliğini kullanın.

src/styles.css

.gallery__entry {
  animation: linear fade-in;
  animation-duration: auto;
  animation-timeline: view(inline);
  animation-range: entry 0% entry 100%;
}

Animasyon artık entry 0% (konu kaydırma çubuğuna girmek üzere) ile entry 100% (konu kaydırma çubuğuna tamamen girmiş) arasında çalışır.

Olası zaman çizelgesi görünüm aralıkları şunlardır:

  • cover. Görüntüleme ilerleme zaman çizelgesinin tamamını temsil eder.
  • entry. Ana kutunun görüntüleme ilerleme görünürlüğü aralığına girdiği aralığı temsil eder.
  • exit. Ana kutunun, görüntüleme ilerleme görünürlüğü aralığından çıktığı aralığı temsil eder.
  • entry-crossing. Ana kutunun uç kenarlığıyla kesiştiği aralığı temsil eder.
  • exit-crossing. Ana kutunun başlangıç kenarlığı kenarını geçtiği aralığı temsil eder.
  • contain. Ana kutunun, kaydırma alanındaki görüntüleme ilerleme görünürlük aralığının tamamını kapladığı veya bu aralığın tamamını kapladığı aralığı temsil eder. Bu, öznenin kaydırma çubuğundan daha uzun veya daha kısa olmasına bağlıdır.

Her aralığın neyi temsil ettiğini ve yüzdelerin başlangıç ile bitiş konumlarını nasıl etkilediğini görmek için https://goo.gle/view-timeline-range-tool adresindeki aracı kullanın.

  1. Burada başlangıç ve bitiş aralıkları aynı olduğundan ve varsayılan ofsetler kullanıldığı için animation-range değerini tek bir animasyon aralığı adı olacak şekilde basitleştirin:

src/styles.css

.gallery__entry {
  animation: linear animate-in;
  animation-duration: auto;
  animation-timeline: view(inline);
  animation-range: entry;
}
  • Kaydırma çubuğundan çıktıklarında resimleri soluklaştırmak için, animasyonla gösterme animasyonuyla aynı işlemi yapabilir ancak farklı bir aralığı hedefleyebilirsiniz.

src/styles.css

@keyframes animate-out {
  from {
    opacity: 1;
    clip-path: inset(0% 0% 0% 0%);
  }
  to {
    opacity: 0;
    clip-path: inset(50% 0% 50% 0%);
  }
}

.gallery__entry {
  animation: linear animate-in, linear animate-out;
  animation-duration: auto;
  animation-timeline: view(inline);
  animation-range: entry, exit;
}

animate-in animasyon kareleri entry aralığına, animate-out animasyon kareleri ise exit aralığına uygulanır.

Değişikliklerinizi doğrulama

Her şey yolunda gittiyse şuna sahip olursunuz:

Aksi takdirde, kodun solution-step-3 şubesine göz atın.

7. Bir animasyon karesi grubu kullanarak galeri resimlerinin kaydırma bölmesine girip çıkarken animasyonlu hâle getirilmesi

Bir animasyon karesi grubu için durum

Farklı aralıklara iki animasyon eklemek yerine, aralık bilgilerini zaten içeren bir ana kare grubu oluşturabilirsiniz.

Anahtar karelerin şekli aşağıdaki gibidir:

@keyframes keyframes-name {
  range-name range-offset {
    ...
  }
  range-name range-offset {
    ...
  }
}
  1. Görüntüye gelme ve görüntüden kaybolma animasyon karelerini şu şekilde birleştirin:

src/styles.css

@keyframes animate-in-and-out {
  entry 0% {
    opacity: 0;
    clip-path: inset(50% 0% 50% 0%);
  }
  entry 90% {
    opacity: 1;
    clip-path: inset(0% 0% 0% 0%);
  }

  exit 10% {
    opacity: 1;
    clip-path: inset(0% 0% 0% 0%);
  }
  exit 100% {
    opacity: 0;
    clip-path: inset(50% 0% 50% 0%);
  }
}
  1. Aralık bilgileri anahtar karelerde mevcut olduğunda artık animation-range değerini ayrı olarak belirtmeniz gerekmez. Animasyon karelerini animation özelliği olarak ekleyin.

src/styles.css

.gallery__entry {
  animation: linear animate-in-and-out both;
  animation-duration: auto;
  animation-timeline: view(inline);
}

Değişikliklerinizi doğrulama

Her şey yolunda giderse önceki adımdakiyle aynı sonucu elde edersiniz. Aksi takdirde, kodun solution-step-4 şubesine göz atın.

8. Tebrikler!

Bu codelab'i tamamladınız ve artık CSS'de kaydırma ilerleme zaman çizelgelerini ve görüntüleme ilerleme zaman çizelgelerini nasıl oluşturacağınızı biliyorsunuz.

Daha Fazla Bilgi

Kaynaklar: