מאפיין CSS חדש עם יחס גובה-רוחב נתמך ב-Chromium, בתצוגה המקדימה של הטכנולוגיה של Safari וב-Firefox ללילה

מאפיין ה-CSS החדש שעוזר לשמור על ריווח בפריסות רספונסיביות.

יחס גובה-רוחב

תמיכה בדפדפן

  • 88
  • 88
  • 89
  • 15

מקור

יחס הגובה-רוחב מתבטא בדרך כלל כשני מספרים שלמים ונקודתיים במימדים הבאים: width:height או x:y. יחסי הגובה-רוחב הנפוצים ביותר לצילום תמונות הם 4:3 ו-3:2, ואילו ביחסי הווידאו, ובמצלמות מודרניות יותר, יש בדרך כלל יחס גובה-רוחב של 16:9.

שתי תמונות עם אותו יחס גובה-רוחב. גודל אחד הוא 634 x 951 פיקסלים והשני הוא 200 x 300 פיקסלים. יחס הגובה-רוחב של שניהם הוא 2:3.
שתי תמונות עם אותו יחס גובה-רוחב. גודל אחד הוא 634 x 951 פיקסלים והשני הוא 200 x 300 פיקסלים. שניהם הם ביחס גובה-רוחב של 2:3.

עם ההתפתחות של עיצוב רספונסיבי, שמירה על יחס הגובה-רוחב הולכת וגדלה בקרב מפתחי אתרים, במיוחד לאור העובדה שמידות התמונה שונות וגודל הרכיבים משתנה בהתאם לשטח הזמין.

הנה כמה דוגמאות לחשיבות השמירה על יחס הגובה-רוחב:

  • יצירת מסגרות iframe רספונסיביות, שהן 100% מרוחב ההורה והגובה צריך להישאר ביחס של אזור תצוגה ספציפי
  • יצירת קונטיינרים פנימיים של placeholder עבור תמונות, סרטונים והטמעות, כדי למנוע פריסה מחדש כשהפריטים נטענים ותופסים מקום
  • יצירת שטח רספונסיבי ואחיד להמחשות נתונים אינטראקטיביות או לאנימציות SVG
  • יצירת מרחב רספונסיבי ואחיד לרכיבים שמכילים כמה רכיבים כמו כרטיסים או תאריכים ביומן
  • יצירת שטח רספונסיבי ואחיד למספר תמונות במידות שונות (אפשר להשתמש בו לצד object-fit)

התאמת אובייקט

הגדרה של יחס גובה-רוחב מאפשרת לנו לשנות את גודל המדיה בהקשר רספונסיבי. כלי נוסף בקטגוריה הזו הוא המאפיין object-fit, שמאפשר למשתמשים לתאר איך אובייקט (כמו תמונה) בתוך בלוק צריך למלא את הבלוק הזה:

הדגמה של התאמת אובייקט להמחשה
מוצגים ערכים שונים של object-fit. ראו הדגמה ב-Codepen.

הערכים initial ו-fill מתאימים מחדש את התמונה כך שתמלא את המקום. בדוגמה הזו, התמונה נדחית ומטושטשת בזמן שהיא מכווננת מחדש את הפיקסלים. לא אידיאלי. object-fit: cover משתמש בממד הקטן ביותר של התמונה כדי למלא את השטח, וחותך את התמונה כדי שתתאים אליה על סמך הממד הזה. הוא "מתקרב" אל הגבול הנמוך ביותר שלו. object-fit: contain מבטיח שתמיד תהיה תמונה גלויה, וכך ההפך מ-cover, שבו הוא לוקח את גודל הגבול הגדול ביותר (בדוגמה שלנו למעלה (בדוגמה למעלה זה הרוחב), ומשנה את גודל התמונה כדי לשמור על יחס הגובה-רוחב הפנימי שלה תוך כדי התאמה לשטח. באותיות object-fit: none התמונה נחתכה במרכז שלה (מיקום האובייקט המוגדר כברירת מחדל) בגודלה הטבעי.

לרוב, השיטה object-fit: cover פועלת ברוב המצבים כדי להבטיח ממשק אחיד ונעים להתמודדות עם תמונות במידות שונות, אבל המידע יאבד (התמונה תיחתך בקצוות הארוכים ביותר).

אם הפרטים האלה חשובים (למשל, כשעובדים עם שכבת-על של מוצרי טיפוח), לא ניתן לחתוך תוכן חשוב. התרחיש האידיאלי הוא תמונות רספונסיביות בגדלים שונים, שמתאימות לשטח של ממשק המשתמש בלי לחתוך.

הפריצה הישנה: שמירה על יחס גובה-רוחב עם padding-top

שימוש במרווח פנימי-למעלה כדי להגדיר יחס גובה-רוחב 1:1 בתמונות בתצוגה המקדימה של הפוסט בתוך קרוסלה.
באמצעות padding-top כדי להגדיר יחס גובה-רוחב של 1:1 בתמונות בתצוגה מקדימה של הפוסט בתוך קרוסלה.

כדי לשפר את הרספונסיביות של המודעות, אפשר להשתמש ביחס גובה-רוחב. כך אנחנו יכולים להגדיר יחס ספציפי ולבסס את שאר המדיה על ציר נפרד (גובה או רוחב).

פתרון מקובל היטב בדפדפנים שונים לשמירה על יחס גובה-רוחב על סמך רוחב התמונה, נקרא "Padding-Top Hack". בפתרון הזה נדרש קונטיינר הורה ומאגר צאצא במיקום מוחלט. לאחר מכן, יחס הגובה-רוחב יחושב כאחוז כדי להגדיר אותו כ-padding-top. למשל:

  • יחס גובה-רוחב של 1:1 = 1 / 1 = padding-top: 100%
  • יחס גובה-רוחב של 4:3 = padding-top: 75% / 4 = 0.75
  • יחס גובה-רוחב של 3:2 = padding-top: 66.67% / 3 = 0.66666
  • יחס גובה-רוחב של 16:9 = 9 / 16 = 0.5625 = padding-top: 56.25%

עכשיו, אחרי שזיהינו את הערך של יחס הגובה-רוחב, אפשר להחיל אותו על מאגר ההורה שלנו. לדוגמה:

<div class="container">
  <img class="media" src="..." alt="...">
</div>

אחרי זה נוכל לכתוב את ה-CSS הבא:

.container {
  position: relative;
  width: 100%;
  padding-top: 56.25%; /* 16:9 Aspect Ratio */
}

.media {
  position: absolute;
  top: 0;
}

שמירה על יחס גובה-רוחב עם aspect-ratio

שימוש ביחס גובה-רוחב להגדרת יחס גובה-רוחב של 1:1 בתמונות בתצוגה מקדימה של פוסט בתוך קרוסלה.
באמצעות aspect-ratio להגדרת יחס גובה-רוחב של 1:1 בתמונות בתצוגה מקדימה של פוסט בתוך קרוסלה.

לצערנו, חישוב הערכים של padding-top לא מאוד אינטואיטיבי ומחייב תקורה ומיקום נוספים. באמצעות מאפיין ה-CSS המהותי aspect-ratio החדש, הניסוח של שמירת יחס גובה-רוחב הרבה יותר ברור.

עם אותם תגי עיצוב, נוכל להחליף את: padding-top: 56.25% ב-aspect-ratio: 16 / 9, ולהגדיר את aspect-ratio ליחס שצוין של width ל-height.

שימוש במרווח פנימי-למעלה
.container {
  width: 100%;
  padding-top: 56.25%;
}
שימוש ביחס גובה-רוחב
.container {
  width: 100%;
  aspect-ratio: 16 / 9;
}

השימוש ב-aspect-ratio במקום ב-padding-top הרבה יותר ברור, ולא מחליף את מאפיין המרווח הפנימי כדי לבצע פעולות שחורגות מההיקף הרגיל שלו.

המאפיין החדש גם מוסיף את האפשרות להגדיר יחס גובה-רוחב של auto, כאשר "רכיבים שהוחלפו עם יחס גובה-רוחב פנימי משתמשים באותו יחס גובה-רוחב, אחרת אין לתיבה הזו יחס גובה-רוחב מועדף". אם גם auto וגם <ratio> מצוינים יחד, יחס הגובה-רוחב המועדף הוא היחס שצוין, width לחלק ל-height, אלא אם מדובר באלמנט שהוחלף עם יחס גובה-רוחב פנימי. במקרה כזה, המערכת תשתמש ביחס הגובה-רוחב הזה.

דוגמה: עקביות בתצוגת רשת

זה עובד ממש טוב גם עם מנגנוני פריסה של CSS כמו CSS Grid ו-Flexbox. כדאי לשקול רשימה של ילדים שרוצים לשמור על יחס גובה-רוחב של 1:1, כמו רשת של סמלים של נותני חסות:

<ul class="sponsor-grid">
  <li class="sponsor">
    <img src="..." alt="..."/>
  </li>
  <li class="sponsor">
    <img src="..." alt="..."/>
  </li>
</ul>
.sponsor-grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(120px, 1fr));
}

.sponsor img {
  aspect-ratio: 1 / 1;
  width: 100%;
  object-fit: contain;
}
התמונות בתצוגת רשת עם רכיב הורה במידות שונות של יחס גובה-רוחב. לצפייה בהדגמה ב-Codepen

דוגמה: מניעה של שינוי הפריסה

תכונה נהדרת נוספת של aspect-ratio היא היכולת ליצור placeholder של רווחים כדי למנוע Cumulative Layout Shift ולאפשר הצגה טובה יותר של Web Vitals. בדוגמה הראשונה הזו, טעינת נכס מ-API כמו UnFlood יוצרת שינוי פריסה כשמסתיימת הטעינה של המדיה.

סרטון של שינויים מצטברים בפריסה שמתרחשים כאשר לא הוגדר יחס גובה-רוחב בנכס שנטען. הסרטון הזה מוקלט באמצעות אמולציה של רשת 3G.

לעומת זאת, באמצעות aspect-ratio נוצר placeholder כדי למנוע את שינוי הפריסה הזה:

img {
  width: 100%;
  aspect-ratio: 8 / 6;
}
סרטון עם יחס גובה-רוחב קבוע מוגדר בנכס שנטען. הסרטון הזה מוקלט באמצעות אמולציה של רשת 3G. לצפייה בהדגמה ב-Codepen

טיפ בונוס: מאפייני תמונה ליחס גובה-רוחב

דרך נוספת להגדיר יחס גובה-רוחב של תמונה היא באמצעות מאפייני תמונה. אם מידות התמונה ידועות לכם מראש, מומלץ להגדיר את המידות האלה בתור width ו-height.

בדוגמה שלמעלה, אם המידות הן 800 על 600 פיקסלים, תגי העיצוב של התמונה ייראו כך: <img src="image.jpg" alt="..." width="800" height="600">. גם אם לתמונה שנשלחה יש יחס גובה-רוחב זהה, אבל לא בהכרח ערכי הפיקסלים המדויקים, עדיין נוכל להשתמש בערכים של מאפייני התמונה כדי להגדיר את היחס, בשילוב עם סגנון של width: 100%, כך שהתמונה תתפוס את השטח המתאים. כולם ביחד ייראו כך:

<!-- Markup -->
<img src="image.jpg" alt="..." width="8" height="6">
/* CSS */
img {
  width: 100%;
}

בסוף, התוצאה זהה להגדרת aspect-ratio בתמונה באמצעות CSS, ונמנעים שינויים מצטברים בפריסה (ראו הדגמה ב-Codepen).

סיכום

עם השקת מאפיין ה-CSS החדש aspect-ratio במספר דפדפנים מודרניים, קל יותר לשמור על יחסי גובה-רוחב מתאימים בקונטיינרים של מדיה ופריסה.

תמונות של איימי שמבלן וליאונל גוסטב דרך UnFlood.