Kesişim Gözlemcisi v2, sadece kesişimleri hem gözlemleme hem de kesişen öğenin kesişim sırasında görünür olup olmadığını tespit etme özelliğini ekler.
Intersection Observer v1, muhtemelen evrensel olarak sevilen API'lerden biridir ve artık Safari de desteklediği için, nihayet tüm önemli tarayıcılarda evrensel olarak kullanılabilir. API ile ilgili bilgilerinizi hızlıca tazelemek için Surma'nın aşağıya yerleştirilmiş IntersectionObserver v1 ile ilgili Supercharged Microtip başlıklı videosunu izlemenizi öneririz.
Surma'nın ayrıntılı makalesini de okuyabilirsiniz.
Kullanıcılar, resim ve videoların geç yüklenmesi, öğeler position: sticky
değerine ulaştığında bildirim alma, analiz etkinliklerini tetikleme ve daha birçok kullanım alanı için Intersection Observer'dan yararlanıyor.
Tüm ayrıntılar için Intersection Observer docs on MDN (MDN'deki Intersection Observer belgeleri) sayfasına göz atın. Ancak Intersection Observer v1 API'nin en temel durumda nasıl göründüğünü hatırlatmak isteriz:
const onIntersection = (entries) => {
for (const entry of entries) {
if (entry.isIntersecting) {
console.log(entry);
}
}
};
const observer = new IntersectionObserver(onIntersection);
observer.observe(document.querySelector('#some-target'));
Intersection Observer v1'in zorluğu nedir?
Açıkça belirtmek gerekirse Intersection Observer v1 çok iyi bir çözüm ama mükemmel değil. API'nin yetersiz kaldığı bazı durumlar vardır. Daha yakından inceleyelim.
Intersection Observer v1 API'si, bir öğe pencerenin görüntü alanına kaydırıldığında size bilgi verebilir. Ancak, öğenin başka bir sayfa içeriği tarafından kaplanıp kaplanmadığını (yani, öğe kapandığında) veya öğenin görsel görünümünün, etkili bir şekilde görünmez hale getirebilecek transform
, opacity
, filter
gibi görsel efektlerle değiştirilip değiştirilmediğini belirtmez.
Üst düzey belgedeki bir öğede bu bilgiler, DOM'un JavaScript aracılığıyla analiz edilmesi (ör. DocumentOrShadowRoot.elementFromPoint()
aracılığıyla) ve ardından daha ayrıntılı inceleme yapılarak belirlenebilir.
Öte yandan, söz konusu öğe bir üçüncü taraf iframe'inde yer alıyorsa aynı bilgiler elde edilemez.
Gerçek görünürlük neden bu kadar önemli?
Maalesef İnternet, kötü niyetli kişileri kendine çeken bir yerdir.
Örneğin, bir içerik sitesinde tıklama başına ödeme reklamları sunan şüpheli bir yayıncı, yayıncının reklam
ödemesini artırmak amacıyla kullanıcıları kandırarak reklamlarını tıklamaları için teşvik edilebilir (en azından kısa bir süre için (reklam ağı bunları yakalayana kadar)).
Genellikle, bu tür reklamlar iframe'ler içinde sunulur.
Yayıncı, kullanıcıların bu tür reklamları tıklamalarını sağlamak isterse, bir CSS kuralı iframe { opacity: 0; }
uygulayarak ve iframe'leri, kullanıcıların gerçekten tıklamak isteyeceği şirin bir kedi videosu gibi çekici bir şeyin üzerine yerleştirerek reklam iframe'lerini tamamen şeffaf hale getirebilir.
Buna tıklama korsanlığı denir.
Bu tür bir tıklama korsanlığı saldırısını bu demonun üst bölümünde görebilirsiniz (kedi videosunu "izlemeyi" deneyin ve "şaka modunu" etkinleştirin).
iframe'deki reklamın geçerli tıklamalar aldığını "düşündüğünü", (istemsiz şekilde tıkladığınızda) tamamen şeffaf
olduğunu fark edersiniz.
Intersection Observer v2 bu sorunu nasıl düzeltir?
Kesişim Gözlemleyicisi v2, hedef öğenin bir insanın tanımlayacağı şekilde gerçek "görünürlüğünü" izleme kavramını ortaya çıkarır.
IntersectionObserver
oluşturucuda bir seçenek ayarlandığında, IntersectionObserverEntry
örneklerinin kesiştiği isVisible
adlı yeni bir boole alanı içerir.
isVisible
için bir true
değeri, temel uygulamada hedef öğenin başka içeriklerle tamamen kapatılmadığını ve ekrandaki görünümünü değiştirecek veya bozacak görsel efektlerin uygulanmadığını belirten güçlü bir garantidir.
false
değeri ise uygulamanın bu garantiyi veremeyeceği anlamına gelir.
spec önemli bir ayrıntısı, uygulamaya yanlış negatifleri bildirmesine izin verilmesidir (yani, hedef öğe tamamen görünür ve değiştirilmemiş olsa bile isVisible
değerini false
olarak ayarlama).
Performans veya başka nedenlerle, tarayıcılar kendilerini sınırlayıcı kutular ve doğrusal geometriyle çalışmakla sınırlar; border-radius
gibi değişiklikler için mükemmel pikseller elde etmeye çalışmazlar.
Bununla birlikte, yanlış pozitiflere hiçbir koşulda izin verilmez (yani hedef öğe tamamen görünür ve değiştirilmemişken isVisible
değerini true
olarak ayarlayın).
Yeni kod pratikte nasıl görünüyor?
IntersectionObserver
oluşturucu artık iki ek yapılandırma özelliği alır: delay
ve trackVisibility
.
delay
, belirli bir hedef için gözlemciden gelen bildirimler arasındaki milisaniye cinsinden minimum gecikmeyi gösteren bir sayıdır.
trackVisibility
, gözlemcinin hedefin görünürlüğündeki değişiklikleri izleyip izlemeyeceğini gösteren bir boole'dir.
trackVisibility
değeri true
olduğunda delay
değerinin en az 100
(yani 100 ms'de bir en fazla bir bildirim) olması gerektiği unutulmamalıdır.
Daha önce belirtildiği gibi, görünürlüğün hesaplanması pahalıdır ve bu gereklilik, performans düşüşü ve pil tüketimine karşı bir önlemdir. Sorumlu geliştirici gecikme için en büyük tolere edilebilir değeri kullanır.
Görünürlük mevcut spec göre aşağıdaki gibi hesaplanır:
Gözlemcinin
trackVisibility
özelliğifalse
ise hedef görünür olarak kabul edilir. Bu, geçerli v1 davranışına karşılık gelir.Hedefin 2D çeviri veya orantılı 2D büyütme dışında etkili bir dönüşüm matrisi varsa hedef görünmez olarak kabul edilir.
Hedef veya içerdiği blok zincirindeki herhangi bir öğe, 1,0 dışında bir etkili opaklığa sahipse hedef görünmez olarak kabul edilir.
Hedefte veya içerdiği blok zincirindeki herhangi bir öğeye filtre uygulanmışsa hedef görünmez olarak kabul edilir.
Uygulama, hedefin başka sayfa içeriği tarafından tamamen kapatılacağını garanti edemezse hedef görünmez olarak kabul edilir.
Bu, mevcut uygulamaların oldukça konservatif olduğu ve görünürlüğü garanti altına aldığı anlamına gelir.
Örneğin, filter: grayscale(0.01%)
gibi neredeyse fark edilmeyecek bir gri tonlama filtresi uygulamak veya opacity: 0.99
ile neredeyse görünmez bir şeffaflık ayarlamak, öğeyi görünmez hale getirir.
Aşağıda, yeni API özelliklerini gösteren kısa bir kod örneği verilmiştir. Tıklama izleme mantığının nasıl çalıştığını demonun ikinci bölümünde görebilirsiniz (ancak şimdi yavru köpek videosunu "izlemeyi" deneyin). Kendinizi hemen şüpheli bir yayıncıya dönüştürmek ve Intersection Observer v2'nin meşru olmayan reklam tıklamalarının izlenmesini nasıl önlediğini görmek için "numara modu"nu tekrar etkinleştirdiğinizden emin olun. Bu kez Intersection Observer v2'de sizi bekliyor. 🎉
<!DOCTYPE html>
<!-- This is the ad running in the iframe -->
<button id="callToActionButton">Buy now!</button>
// This is code running in the iframe.
// The iframe must be visible for at least 800ms prior to an input event
// for the input event to be considered valid.
const minimumVisibleDuration = 800;
// Keep track of when the button transitioned to a visible state.
let visibleSince = 0;
const button = document.querySelector('#callToActionButton');
button.addEventListener('click', (event) => {
if ((visibleSince > 0) &&
(performance.now() - visibleSince >= minimumVisibleDuration)) {
trackAdClick();
} else {
rejectAdClick();
}
});
const observer = new IntersectionObserver((changes) => {
for (const change of changes) {
// ⚠️ Feature detection
if (typeof change.isVisible === 'undefined') {
// The browser doesn't support Intersection Observer v2, falling back to v1 behavior.
change.isVisible = true;
}
if (change.isIntersecting && change.isVisible) {
visibleSince = change.time;
} else {
visibleSince = 0;
}
}
}, {
threshold: [1.0],
// 🆕 Track the actual visibility of the element
trackVisibility: true,
// 🆕 Set a minimum delay between notifications
delay: 100
}));
// Require that the entire iframe be visible.
observer.observe(document.querySelector('#ad'));
İlgili Bağlantılar
- Kesişim Gözlemci spesifikasyonunun en son Editör Taslağı.
- Chrome Platform Durumu sayfasında Intersection Observer v2.
- Intersection Observer v2 Chromium hatası.
- Yayınlama uygulama amacı bölümünde göz atın.
Teşekkür
Bu makaleyi değerlendirdikleri için Simeon Vincent, Yoav Weiss ve Mathias Bynens'e, ayrıca bu özelliği Chrome'da inceleyip uygulamaya koydukları için Stefan Zager'a teşekkür ederiz. Sergey Semin'in Unsplash'ta çektiği hero resim.