İşaretçi Olayları Özelliğiyle SVG Etkileşimini Yönetme

Yayınlanan: 2022-03-10
Hızlı özet ↬ Şimdi SVG görüntülerinin etkileşiminin nasıl şekillendirileceğine bir göz atalım - yani, pointer-events özelliğini kullanarak belgenin hangi bölümlerinin tıklama, dokunma veya dokunma alabileceğini kontrol edelim.

Aşağıdaki SVG resmine tıklamayı veya dokunmayı deneyin. İşaretçinizi doğru yere (gölgeli yol) koyarsanız, Smashing Magazine'in ana sayfasını yeni bir tarayıcı sekmesinde açmanız gerekir. Beyaz bir alana tıklamaya çalıştıysanız, bunun yerine gerçekten kafanız karışmış olabilir.

CodePen'de Tiffany Brown (@webinista) tarafından kalem Ametist'e bakın.

CodePen'de Tiffany Brown (@webinista) tarafından kalem Ametist'e bakın.

SVG görüntüleri içindeki bağlantıları içeren yeni bir proje sırasında karşılaştığım ikilem bu. Bazen resme tıkladığımda bağlantı çalıştı. Diğer zamanlarda olmadı. Kafa karıştırıcı, değil mi?

Neler olabileceği ve SVG'nin bir düzeltme sunup sunmadığı hakkında daha fazla bilgi edinmek için SVG spesifikasyonuna döndüm. Cevap: pointer-events .

Atlamadan sonra daha fazlası! Aşağıdan okumaya devam edin ↓

DOM ( Belge Nesne Modeli ) işaretçi olaylarıyla karıştırılmaması için, pointer-events hem bir CSS özelliği hem de bir SVG öğesi niteliğidir. Bununla, bir SVG belgesinin veya öğesinin hangi bölümlerinin fare, izleme dörtgeni veya parmak gibi bir işaretleme aygıtından olayları alabileceğini yönetebiliriz.

Terminoloji hakkında bir not: "işaretçi olayları", aynı zamanda, kullanıcı girişi için cihazdan bağımsız, web platformu özelliğinin adıdır. Ancak, bu makalede - ve pointer-events özelliğinin amaçları doğrultusunda - "işaretçi olayları" ifadesi ayrıca fare ve dokunma olaylarını da içerir.

Kutunun Dışında: SVG'nin “Şekil Modeli”

CSS'yi HTML ile kullanmak, HTML'ye bir kutu düzeni modeli uygular. Kutu yerleşim modelinde, her öğe içeriğinin etrafında bir dikdörtgen oluşturur. Bu dikdörtgen satır içi, satır içi düzey, atomik satır içi düzey veya blok olabilir, ancak yine de dört dik açılı ve dört kenarlı bir dikdörtgendir. Bir öğeye bir bağlantı veya olay dinleyicisi eklediğimizde, etkileşimli alan dikdörtgenin boyutlarıyla eşleşir.

Not : Etkileşimli bir öğeye bir clip-path eklemek, etkileşimli sınırlarını değiştirir. Başka bir deyişle, a öğeye altıgen bir clip-path yolu eklerseniz, yalnızca kırpma yolu içindeki noktalar tıklanabilir olacaktır. Benzer şekilde, bir skew dönüşümü eklemek, dikdörtgenleri eşkenar dörtgenlere dönüştürecektir.

SVG'nin kutu yerleşim modeli yoktur. Görüyorsunuz, bir CSS mizanpajı içinde bir HTML belgesi bir SVG belgesi içerdiğinde, kök SVG öğesi kutu yerleşim modeline yapışır. Alt öğeleri yoktur. Sonuç olarak, CSS mizanpajıyla ilgili çoğu özellik SVG için geçerli değildir.

Bunun yerine, SVG benim 'şekil modeli' diyeceğim şeye sahiptir. Bir SVG belgesine veya öğesine bir bağlantı veya olay dinleyicisi eklediğimizde, etkileşimli alan mutlaka bir dikdörtgen olmayacaktır. SVG öğelerinin bir sınırlayıcı kutusu vardır. Sınırlayıcı kutu şu şekilde tanımlanır: bu öğeyi ve alt öğelerini tamamen çevreleyen kullanıcı koordinat sisteminin eksenleriyle hizalanmış en sıkı oturan dikdörtgen. Ancak başlangıçta, bir SVG belgesinin hangi bölümlerinin etkileşimli olduğu, hangi bölümlerin görünür ve/veya boyalı olduğuna bağlıdır.

Boyalı ve Görünür Öğeler

SVG öğeleri "doldurulabilir" ancak aynı zamanda "konturlanabilir". Dolgu , bir şeklin içini ifade eder. İnme , ana hatlarını ifade eder.

"Doldur" ve "kontur" birlikte, öğeleri ekrana veya sayfaya ( tuval olarak da bilinir) dönüştüren boyama işlemleridir . Boyalı elemanlar hakkında konuştuğumuzda, elemanın dolgusu ve/veya konturu olduğunu kastediyoruz. Genellikle bu, öğenin de görünür olduğu anlamına gelir.

Ancak, bir SVG öğesi görünmeden boyanabilir. Bu, visible öznitelik değeri veya CSS özelliği hidden veya display none ise olabilir. Öğe oradadır ve teorik alanı kaplar. Biz onu göremiyoruz (ve yardımcı teknoloji bunu tespit etmeyebilir).

Belki de daha kafa karıştırıcı bir şekilde, bir öğe boyanmadan da visible - yani hesaplanmış visibility değerine sahip olabilir. Bu, öğelerde hem kontur hem de dolgu olmadığında olur.

Not : Alfa şeffaflığına sahip renk değerleri (örn rgba(0,0,0,0) ) bir elemanın boyanmış veya görünür olmasını etkilemez. Başka bir deyişle, bir öğenin alfa saydam dolgusu veya konturu varsa, görülmese bile boyanır.

Bir öğenin ne zaman boyandığını, görünür olduğunu veya hiçbirinin olmadığını bilmek, her bir pointer-events değerinin etkisini anlamak için çok önemlidir.

Hepsi Veya Hiçbiri Veya Arasında Bir Şey: Değerler

pointer-events , hem bir CSS özelliği hem de bir SVG öğesi niteliğidir. Başlangıç ​​değeri auto ; bu, yalnızca boyanan ve görünen bölümlerin işaretçi olaylarını alacağı anlamına gelir. Diğer değerlerin çoğu iki gruba ayrılabilir:

  1. Bir öğenin görünür olmasını gerektiren değerler; ve
  2. Olmayan değerler.

painted , fill , stroke ve all ikinci kategoriye girer. Görünürlüğe bağlı muadilleri - visiblePainted , visibleFill , visibleStroke ve visible - birincisine girer.

SVG 2.0 spesifikasyonu ayrıca bir bounding-box değeri tanımlar. pointer-events değeri bounding-box olduğunda, öğenin etrafındaki dikdörtgen alan da işaretçi olaylarını alabilir. Bu yazı itibariyle, yalnızca Chrome 65+ bounding-box değerini destekler.

none de geçerli bir değer değildir. Öğenin ve alt öğelerinin herhangi bir işaretçi olayı almasını engeller. pointer-events CSS özelliği, HTML öğeleriyle de kullanılabilir. Ancak HTML ile kullanıldığında yalnızca auto ve none geçerli değerler değildir.

pointer-events değerleri açıklanandan daha iyi gösterildiği için, bazı demolara bakalım.

Burada dolgu ve kontur uygulanmış bir dairemiz var. Hem boyalı hem de görülebilir . Tüm daire işaretçi olaylarını alabilir, ancak dairenin dışındaki alan alamaz.

CodePen'de Tiffany Brown (@webinista) tarafından SVG'de boyanmış Pen Visible'a karşı bakın.

CodePen'de Tiffany Brown (@webinista) tarafından SVG'de boyanmış Pen Visible'a karşı bakın.

Değeri none olacak şekilde dolguyu devre dışı bırakın. Şimdi, dairenin içini gezdirmeye, tıklamaya veya dokunmaya çalışırsanız hiçbir şey olmuyor. Ancak aynısını kontur alanı için yaparsanız, işaretçi olayları yine de gönderilir. fill değerini none olarak değiştirmek, bu alanın görünür olduğu, ancak boyanmadığı anlamına gelir.

İşaretlememizde küçük bir değişiklik yapalım. fill=none öğesini korurken circle pointer-events="visible" ekleyeceğiz.

Kaleme İşaretçi olayları nasıl eklenir: tümü CodePen'de Tiffany Brown (@webinista) tarafından etkileşimi etkiler.

Kaleme İşaretçi olayları nasıl eklenir: tümü CodePen'de Tiffany Brown (@webinista) tarafından etkileşimi etkiler.

Artık kontur tarafından çevrelenen boyanmamış alan işaretçi olaylarını alabilir.

Bir SVG Resminin Tıklanabilir Alanını Büyütme

Bu makalenin başındaki resme dönelim. "Ametistimiz", her biri bir stroke ve fill içeren bir grup çokgenden farklı olarak bir path öğesidir. Bu, yalnızca pointer-events="all" ekleyip buna bir gün diyemeyeceğimiz anlamına gelir.

Bunun yerine, tıklama alanını büyütmemiz gerekiyor. Boyalı ve görünür öğeler hakkında bildiklerimizi kullanalım. Aşağıdaki örnekte, resim işaretlememize bir dikdörtgen ekledim.

CodePen'de Tiffany Brown (@webinista) tarafından hazırlanan bir SVG görüntüsünün tıklama alanını artıran Kalem'e bakın.

CodePen'de Tiffany Brown (@webinista) tarafından hazırlanan bir SVG görüntüsünün tıklama alanını artıran Kalem'e bakın.

Bu dikdörtgen görünmez olsa da, teknik olarak hala görülebilir (yani visibility: visible ). Ancak dolgu olmaması boyanmadığı anlamına gelir. Görüntümüz aynı görünüyor. Aslında hala aynı şekilde çalışıyor - beyaz alana tıklamak hala bir gezinme işlemini tetiklemiyor. Hala a elementimize pointer-events özniteliği eklememiz gerekiyor. visible veya all değerleri kullanmak burada işe yarayacaktır.

CodePen'de Tiffany Brown (@webinista) tarafından hazırlanan bir SVG görüntüsünün tıklama alanını artıran Kalem'e bakın.

CodePen'de Tiffany Brown (@webinista) tarafından hazırlanan bir SVG görüntüsünün tıklama alanını artıran Kalem'e bakın.

Artık görüntünün tamamı işaretçi olaylarını alabilir.

bounding-box kullanmak, bir hayalet öğeye olan ihtiyacı ortadan kaldıracaktır. Sınırlayıcı kutu içindeki tüm noktalar, yolun çevrelediği beyaz boşluk da dahil olmak üzere işaretçi olaylarını alır. Ancak yine: pointer-events="bounding-box" yaygın olarak desteklenmemektedir. Olana kadar boyanmamış elemanları kullanabiliriz.

SVG ve HTML'yi Karıştırırken pointer-events Kullanma

pointer-events yardımcı olabileceği başka bir durum: HTML düğmesinin içinde SVG kullanmak.

CodePen'de Tiffany Brown (@webinista) tarafından kaleme alınan Ovxmmy'ye bakın.

CodePen'de Tiffany Brown (@webinista) tarafından kaleme alınan Ovxmmy'ye bakın.

Çoğu tarayıcıda - Firefox ve Internet Explorer 11 burada istisnadır - event.target değeri HTML düğmemiz yerine bir SVG öğesi olacaktır. Açılış SVG etiketimize pointer-events="none" ekleyelim.

Pen How işaretçi olayları: hiçbiri CodePen'de Tiffany Brown (@webinista) tarafından SVG ve HTML ile kullanılamaz.

Pen How işaretçi olayları: hiçbiri CodePen'de Tiffany Brown (@webinista) tarafından SVG ve HTML ile kullanılamaz.

Artık kullanıcılar düğmemize tıkladığında veya dokunduğunda, event.target button bulunacaktır.

DOM ve JavaScript konusunda deneyimli olanlar, ok işlevi yerine function anahtar sözcüğünü ve event.target yerine this anahtar sözcüğünü kullanmanın bu sorunu çözdüğünü fark edeceklerdir. Bununla birlikte, pointer-events="none" (veya CSS'nizde pointer-events: none; ) kullanmak, o belirli JavaScript tuhaflığını belleğe kaydetmeniz gerekmediği anlamına gelir.

Çözüm

SVG, HTML ile alışık olduğumuz aynı türde etkileşimi destekler. Tıklamalara veya dokunmalara yanıt veren grafikler oluşturmak için kullanabiliriz. CSS ve HTML kutu modeline uymayan bağlantılı alanlar oluşturabiliriz. pointer-events eklenmesiyle, kullanıcı etkileşimine yanıt olarak SVG belgelerimizin davranış biçimini iyileştirebiliriz.

SVG pointer-events için tarayıcı desteği sağlamdır. SVG'yi destekleyen her tarayıcı, SVG belgeleri ve öğeleri için özelliği destekler. HTML öğeleriyle birlikte kullanıldığında, destek biraz daha az sağlamdır. Internet Explorer 10'da veya önceki sürümlerinde veya Opera Mini'nin herhangi bir sürümünde mevcut değildir.

Bu parçada pointer-events yüzeyini henüz çizdik. Daha ayrıntılı bir teknik işlem için SVG Spesifikasyonunu okuyun. MDN (Mozilla Geliştirici Ağı) Web Dokümanları, pointer-events için örneklerle birlikte daha fazla web geliştirici dostu belgeler sunar.