Magic Flip Cards: Yaygın Bir Boyutlandırma Problemini Çözme
Yayınlanan: 2022-03-10Bir sonraki müşterinizin projesini tanıtırken etkileşimli kelimesini kullanma şansı nedir? Tecrübelerime göre, cevap %100'dür , bu yüzden her zaman bu hedefi tartışırken ortaya çıkan çeşitli özellikleri ve etkileri sunmama yardımcı olacak sağlam CSS teknikleri arıyorum.
Tekrar tekrar uygulamam istenen küçük bir etkileşim parçası, flip kartlardır - üzerine gelindiğinde veya dokunulduğunda dönen içerik blokları, arka taraflarındaki içeriği ortaya çıkarır. Eğlenceli göz atmayı teşvik eden zarif bir efekt ve sayfadan uzaklaşmadan daha fazla bilgi göstermenin başka bir yolu. Ancak, farklı kart içerik uzunluklarını barındırmak söz konusu olduğunda standart yöntemin bir sorunu vardır.
Bu öğreticide, bu sorunu bazı CSS temelleriyle (dönüşümler, esnek ve ızgara) çözen bir çevirmeli kart ızgarası oluşturacağız. Bunlara aşina olmanız gerekecek ve bu, CSS konumlandırma tekniklerini iyi kavramanıza yardımcı olacaktır. Şunları ele alacağız:
- Çevirmeli kartlar genellikle mutlak konumlandırma kullanılarak nasıl uygulanır;
- Mutlak konumlandırmanın getirdiği boyutlandırma problemi; ve
- Üst üste binen içeriğin otomatik olarak boyutlandırılması için genel bir çözüm.
Temel Bir Çevirmeli Kart Oluşturma
Üç boyutlu dönüşümler için iyi modern tarayıcı desteğiyle, temel bir çevirme kartı oluşturmak nispeten basittir. Genel yöntem, ön ve arka kart yüzlerini bir ana kaba yerleştirmek ve arka yüzü kesinlikle ön yüzün boyutuna uyacak şekilde konumlandırmaktır. Ters çevrilmiş görünmesi için arka yüze bir x ekseni dönüşümü ekleyin, üzerine gelindiğinde kartın kendisine bir tane daha ekleyin ve işte başlıyoruz.
.cards { display: grid; } .card { perspective: 40rem; } .card-body { transform-style: preserve-3d; transition: var(--time) transform; .card:hover & { transform: rotateX(-180deg); } } .card-front, .card-back { backface-visibility: hidden; } .card-back { position: absolute; top: 0; right: 0; bottom: 0; left: 0; transform: rotateX(-180deg); }
Ne Yanlış Gidebilir?
Ancak standart çözümümüzün büyük bir sorunu var: Arka yüz, ön yüzün sağladığından daha fazla alana ihtiyaç duyduğunda çalışmaz. Karta büyük, sabit bir boyut vermek bir çözümdür, ancak bu yaklaşımın bazı ekran boyutları için bir noktada başarısız olması da garanti edilir.
Tasarım kompozisyonları, doğal olarak, mükemmel bir şekilde uyan metin içeren düzgün görünümlü kutular içerir. Ancak geliştirmeye başlarken, gerçek içerik için çalışan bir sayfa ve kart düzeni elde etmek zor olabilir. Ve bir CMS'den dinamik içerik görüntülerken bu imkansız olabilir! Kelime veya karakter sınırlamalarına rağmen, genellikle tüm cihazlarda güvenilir bir şekilde çalışan bir çözüm yoktur.
Her zaman çok çeşitli içerik uzunluklarını tolere eden düzen uygulamaları oluşturmaya çalışmalıyız. Ama kolay değil! Zaman kısıtlamaları, yetersiz tarayıcı desteği, zayıf bir referans tasarımı veya sadece kendi deneyimim nedeniyle, sık sık sabit boyutlandırma ve konum kullanmaya geri dönme fırsatım oldu.
Yıllar geçtikçe, tasarımcıyla iyi bir yinelemeli süreç ve sağlıklı bir diyalogun bu sorunları çözerken çok yardımcı olabileceğini öğrendim ve genellikle ortalarda bir yerde buluşarak biraz etkileşimli sağlam bir düzen elde edebilirsiniz. Ama eldeki göreve geri dönelim - yapılabilir mi?
Kutunun Dışında Düşünmek
Aslında kartları hem ön hem de arka içeriğe göre boyutlandırmak mümkün ve ilk bakışta göründüğü kadar zor değil. Sadece metodik ve ısrarcı olmamız gerekiyor!
Problemi Kısıtlamak
Düzenimizin gereksinimlerinin bir listesini yaparak başlayalım. Ne istediğinizi tam olarak yazmaya çalışmak bir angarya gibi görünebilir, ancak bir sorunu çözmek için basitleştirilebilecek kısıtlamaları ortaya çıkarmanın harika bir yoludur. Diyelimki:
- Tek sütunlu veya çok sütunlu bir ızgarada düzenlenmiş bir veya daha fazla dikdörtgen kart görmek istiyoruz;
- Arka yüzdeki ikinci bir içerik grubunu ortaya çıkarmak için kartların üzerine gelindiğinde veya hafifçe vurulduğunda ters çevrilmesini istiyoruz;
- Kartların, içerik uzunluğu veya stili ne olursa olsun, tüm ön ve arka içeriklerini gösterecek kadar büyük olmasını istiyoruz; ve
- Birden fazla sütun olması durumunda, ideal olarak, tüm kartların aynı boyutta olmasını isteriz, böylece satırlar güzel bir şekilde hizalanır.
Bu gereksinimleri düşünerek, sorunu basitleştiren birkaç şeyi fark edebiliriz:
- Kartlar bir ızgarada sunulacaksa, genişlikleri üzerinde bir kısıtlamamız vardır - yani genişlikleri, kendi içeriklerinden ziyade görünüm penceresinin veya ızgara kabının işlevleridir;
- Bir kartın genişliğini (en azından ebeveyninin yüzdesi olarak) bildiğimize göre, yatay boyutu çözdük ve kartın yüksekliğini, ön veya arka yüzünün daha uzun olanına uyacak şekilde genişletmemiz gerekiyor; ve
- Bunu yapabilirsek ve her kart dikey olarak kendi boyutundaysa, tüm kart sıralarını en uzun kart kadar uzun yapmak için CSS Grid'in
grid-auto-rows
kullanabiliriz.
Kart Numarasını Anlamak
Peki, kartları nasıl kendimiz boyutlandıracağız? Şimdi problemimizi basitleştirdik, çözüme yakınız.
Bir an için içeriği diğer içeriğin üzerine koyma fikrini unutun ve yeni gereksinimimize odaklanın: en uzun çocuğu kadar uzun bir ebeveyn. Bu kolay! Sütunları kullanarak, bir ebeveynin en uzun çocuğunun boyuna genişlemesine neden olabiliriz. Ardından, çocukları hizaya getirmek için biraz el çabukluğu kullanmamız yeterli:
- Çocukları ebeveynleriyle aynı genişlikte olacak şekilde ayarlayın
- İkinci çocuğun sağa taşmasına izin verin
- Sola doğru uygun yerine geri dönüştürün
.cards { display: grid; } .card-body { display: flex; } .card-front, .card-back { min-width: 100%; mix-blend-mode: multiply; // Preview both faces } .card-back { transform: translate(-100%, 0); }
Bu yaklaşım bariz görünüyorsa, bunu düşünmeden önce gerçekten korkunç fikirlerle saatlerce uğraştığımdan emin olabilirsiniz. İlk başta, kartı doğru boyuta genişletmek için ön yüzün içine arka yüz metninin gizli bir kopyasını yazdırmayı planlamıştım. Ve sütun taşmasını kullanmayı düşündüğümde, orijinal olarak sağdaki sütunu overflow:hidden
kullanarak kırpıyordum ve onu yalnızca vurgunun başladığı son anda dönüştürüyordum, çünkü henüz fark etmemiştim, sadece dönüştürülmüş tutabileceğimi ve gerektiğinde açıp kapatmak için opacity
veya backface-visibility
gibi başka bir yöntem kullanın.
Başka bir deyişle, bariz çözümler sıkı çalışmanın sonucudur! Bir yerleşim problemiyle başınızı saatlerce masanıza çarpıyormuş gibi hissediyorsanız, bir adım geri atmanız ve müşterinizin zamanını akıllıca harcayıp harcamadığınıza karar vermeniz önemlidir: tasarımı değiştirmelerini önermek isteyip istemediğiniz ve baskı ortadan kalktığında bir öğrenme alıştırması olarak kendi zamanınızda çözümü takip etmek. Ama basit yöntemler bulduğunuzda asla aptal hissetmeyin çünkü uzun zaman aldı . Şimdi tam çözümümüzü gözden geçirelim.
.cards { display: grid; } .card { perspective: 40rem; } .card-body { display: flex; transform-style: preserve-3d; transition: var(--time) transform; .card:hover & { transform: rotateX(-180deg); } } .card-front, .card-back { backface-visibility: hidden; min-width: 100%; } .card-back { transform: rotateX(-180deg) translate(-100%, 0); }
Herhangi Bir Uyarı Var mı?
Çözüm, akılda tutulması gereken birkaç küçük uyarı dışında genel olarak iyi çalışır:
- Kartlar, bir ızgara düzeninde veya genişliklerinin içeriğe bağlı olmadığı başka bir bağlamda bulunmalıdır.
- Kartlar, animasyonlar sırasında fareyle üzerine gelme alanının değişmemesi için bir tür içerik sarmalayıcıya (
card-body
gövdesimiz) ihtiyaç duyar. Kartın kendisi animasyonluysa, animasyon hızla durup yeniden başladığında bazı aksaklıklar görürsünüz. - Arka planlar ve kutu gölgeleri gibi stiller en iyi şekilde doğrudan ön ve arka yüzlere yerleştirilir, çünkü kartın üzerindeki efektler canlandırılmayacaktır. Doğal olarak ters çevrileceklerinden, kart gövdesindeki kutu gölgeleri gibi stillere dikkat edin.
- Kartların ön ve arka yüzleri,
min-width
gereksinimlerinden dolayı, kendi dolguları varsa,box-sizing
özelliklerininborder-box
olarak ayarlanmasına ihtiyaç duyar, aksi takdirde taşarlar. - Safari, satıcı ön ekli biçiminde hala
-webkit-backface-visibility
gerektirir.
Biraz Lehçe Eklemek
Şimdi zor sorunu çözdük, tüm etkileşimin olabildiğince sorunsuz çalışmasını sağlamak için yapabileceğimiz birkaç ince ayara bakalım.
İlk olarak, çevirirken kartların üst üste gelip gelmediğini kontrol edin. Bu, birden çok sütun kullanıp kullanmadığınıza, sütun oluğunun genişliğine, kapağın yönüne ve kartın perspektif değerine bağlı olacaktır, ancak olması muhtemeldir. Olayları daha net görmek için animasyonun süresini artırabilirsiniz. Gezinirken, üzerine gelinen kartın sonraki komşularının altından geçmesi doğal görünmüyor, bu yüzden z-index
kullanarak onu üste koymamız gerekiyor. Yeterince kolay, ama dikkat et! z-index
geri yüklemeden önce giden animasyonun tamamlanmasını beklememiz gerekiyor. transition-delay
girin:
.card { transition: z-index; transition-delay: var(--time); z-index: 0; &:hover { transition-delay: 0s; z-index: 1; } }
Ardından, kartlar için aktif bir durum oluşturmayı düşünün. Genellikle bu gibi kartları alakalı bir yere bağlamaya çalışırım - tasarımcı tarafından belirtilmemiş olsa bile - bunun gibi vurgulu efektlere sahip öğeler çok dokunulabilir hissettirir, bu nedenle şanslarını deneyen okuyucular için bir hedef sağlamak iyidir. Hedef sayfanın yüklenmesiyle animasyonun ikinci yarısının kesilip kesilmediği konusunda oldukça iyi çalıştığı için kısa, ince bir ölçek dönüşümünü seviyorum (tarayıcıların navigasyondan önce uçuş animasyonlarını temiz bir şekilde tamamlamasını isterim). Bunun pratikte uygulanması göründüğünden çok daha zor olacağından eminim).
Bu aynı zamanda kartlarımızın arka içeriğinin ne kadar erişilebilir olduğunu düşünmek için harika bir fırsat. İşaretlememiz kısa ve düzenlidir, bu nedenle ekran okuyucuları ve stili göz ardı eden diğer kullanım durumlarını ele aldık, peki ya klavye kullanıcıları? Kartların kendilerini sabitleyecek olursak, sayfa boyunca klavye kullanıcıları sekmesi olarak odaklanacaklar. Kartın fareyle üzerine gelme durumunu odak durumu olarak yeniden kullanalım ve klavye taraması sırasında arka içerik doğal olarak görünecektir.
.card { transition: z-index, transform calc(var(--time) / 4); transition-delay: var(--time), 0s; z-index: 0; &:hover { transition-delay: 0s; z-index: 1; } &:active { transform: scale(0.975); } } .card-body { .card:hover &, .card:focus & { transform: rotateX(-180deg); } }
Son olarak, kartın içeriğine uyacak şekilde otomatik olarak ölçeklendiğini unutmayın, ön ve arka kapların içinde istediğiniz hizalama ve boşluk tekniklerini hemen hemen kullanabilirsiniz. Başlıkları ortalamak için esnek hizalamayı kullanın, dolgu ekleyin, hatta kartın içine başka bir ızgara yerleştirin. Bu, içeriğiyle ölçeklenen iyi yerleşim çözümlerinin güzelliğidir - çocukların ebeveynlere daha az bağlanması ve her seferinde tek bir şeye odaklanmanıza olanak tanıyan modülerlik.
.card-front, .card-back { display: flex; align-items: center; background-color: white; box-shadow: 0 5px 10px black; border-radius: 0.25rem; padding: 1.5rem; }
Toplama
Umarım bu CSS tekniğini faydalı bulursunuz! Neden ölçek efekti veya basit bir çapraz geçiş gibi animasyon üzerinde bazı varyasyonları denemiyorsunuz? Teknik, kartların form faktörü ile de sınırlı değildir. Dikey boyutlandırma sorumluluğunun birden fazla elemana düştüğü her yerde kullanılabilir. Üst üste bindirilmiş başlıklar içeren büyük fotoğraflar içeren bir dergi web sitesi hayal edin - hem yüksek en boy oranlarına sahip görüntüleri hem de uzun dinamik metinleri barındırmak için kullanabilirsiniz.
Her şeyden önce, yalnızca sabit boyutlandırma ve konumla çalışacakmış gibi görünen bir tasarımı uygulamanın bir yolu olup olmadığını gerçekten düşünmek için biraz zaman ayırmanın faydalarını unutmayın. Çoğu zaman vardır ve sorun ilk bakışta ne kadar zor görünürse görünsün, tüm gereksinimlerinizi yazmak, minimum bir test senaryosu oluşturmak için biraz zaman ayırmak ve yöntemli bir şekilde adım atmak her zaman en iyi seçenektir.