דגם קופסה

הפודקאסט של CSS – 001: The Box Model

נניח שיש לכם את קטע ה-HTML הבא:

<p>I am a paragraph of text that has a few words in it.</p>

לאחר מכן, כותבים עבורו את ה-CSS הבא:

p {
  width: 100px;
  height: 50px;
  padding: 20px;
  border: 1px solid;
}

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

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

אם תבינו את מודל התיבה של CSS, תוכלו להבין למה התוכן שלכם לא מתאים לאלמנט.

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

תוכן ומידה

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

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

הנה הדגמה בסיסית שמסבירה את ההבדל:

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

ההדגמה כוללת את המילים "CSS is a Awesome", בתיבה עם מידות קבועות ושוליים עבים. לתיבה יש רוחב מוגדר, לכן היא בגודל חיצוני. המשמעות היא שהיא קובעת את הגודל של התוכן הצאצא. עם זאת, המילה "awesome" גדולה מדי לתיבה, ולכן היא גובלת מחוץ לתיבת הגבול של תיבת ההורה (נרחיב על כך בהמשך). דרך אחת למנוע את החריגה הזו היא לאפשר את גודל התיבה באופן פנימי על ידי אי-הגדרת הרוחב, או במקרה הזה, הגדרת הערך של width ל-min-content. מילת המפתח min-content מורה שהתיבה תחול רק ברוחב המינימלי הפנימי של התוכן שלה (המילה "מדהים"). כך התיבה תתאים את הטקסט בצורה מושלמת.

דוגמה מורכבת יותר, שמראה את ההשפעה של מידות שונות על תוכן אמיתי:

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

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

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

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

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

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

האזורים של מודל התיבה

תיבות מורכבות מאזורים שונים של דגם ארגזים, שכולם עושים עבודה מסוימת.

תרשים שמוצגים בו ארבעת האזורים העיקריים של מודל התיבה – תיבת תוכן, תיבת מרווח, תיבת שוליים ותיבת שוליים
ארבעת האזורים העיקריים במודל התיבה: תיבת תוכן, תיבת מרווח, תיבת שוליים ותיבת שוליים.

תיבת התוכן היא האזור שבו נמצא התוכן. התוכן יכול לשלוט בגודל ההורה שלו, לכן בדרך כלל זה האזור בעל הגודל המשתנה ביותר.

התיבה בתוך המרווח מקיפה את תיבת התוכן, והיא המרחב שנוצר על ידי המאפיין padding. מכיוון שהמרווח הפנימי נמצא בתוך התיבה, הרקע של התיבה גלוי במרחב שהיא יוצרת. אם מוגדרים בתיבה כללי אפשרויות נוספות, כמו overflow: auto או overflow: scroll, גם פסי הגלילה תופסים את השטח הזה.

סרגלי הגלילה מופיעים בתיבת המרווח הפנימי.

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

האזור האחרון, תיבת השוליים, הוא הרווח שמסביב לתיבה, שמוגדר על ידי הכלל margin של התיבה. גם מאפיינים כמו outline ו-box-shadow תופסים את השטח הזה, כי הם צבועים על גבי הרכיב ולא משפיעים על גודל התיבה. שינוי השדה outline-width של 200px בתיבה לא משנה דבר בתוך קצה הגבול.

קו מתאר רחב לא משפיע על הגודל של שאר הרכיב.

אנלוגיה שימושית

מודל התיבה מורכב להבנה, ולכן הנה אנלוגיה למה שלמדת עד כה.

שלוש מסגרות לתמונות.
מודל הקופסה מאויר באמצעות מסגרות לתמונות פיזיות.

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

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

ניפוי באגים במודל התיבה

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

כדאי לנסות זאת בדפדפן שלכם:

  1. פותחים את כלי הפיתוח.
  2. בחירת רכיב.
  3. הצגת הכלי לניפוי באגים של דגם תיבה.
כלי לניפוי באגים של מודל התיבות בהדגמה של Outline.

שליטה במודל הקופסה

כדי להבין איך לשלוט במודל התיבה, קודם כל צריך להבין מה קורה בדפדפן.

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

מאפיין אחד, גיליון הסגנונות של סוכן המשתמש מגדיר את display ברירת המחדל של תיבה. לדוגמה, בתהליך רגיל, ערך ברירת המחדל של display של רכיב <div> הוא block, ל-<li> יש ערך ברירת מחדל display של list-item ול-<span> ערך ברירת המחדל display הוא inline.

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

גיליון הסגנונות של סוכן המשתמש גם מגדיר את box-sizing, שמציין בתיבה איך לחשב את גודל התיבה. כברירת מחדל, לכל הרכיבים יש את הסגנון הבא של סוכן משתמש: box-sizing: content-box;. המשמעות היא שכשמגדירים מאפיינים כמו width ו-height, המאפיינים האלה חלים על תיבת התוכן. אם מגדירים את padding ו-border, הערכים האלה מתווספים לגודל תיבת התוכן.

בחינת ההבנה

בוחנים את הידע שלכם לגבי מאפיינים של גודל מודל קופסה שמשפיעים על המאפיינים.

.my-box {
  width: 200px;
  border: 10px solid;
  padding: 20px;
}

מה הרוחב לדעתך של .my-box?

200 פיקסלים
ערך ברירת המחדל של גודל התיבה הוא תיבת תוכן, ולכן מרווח פנימי וגבולות נוספים לרוחב. הערך 200px מתאים אם בתיבה היה box-sizing: border-box.
260 פיקסלים
הגודל של התיבה שמוגדרת כברירת מחדל הוא "תיבת תוכן", והמשמעות היא שהמרווח הפנימי והגבולות מתווספים לתיבה הכוללת.

הרוחב בפועל של התיבה הזו הוא 260 פיקסלים. מכיוון שה-CSS משתמש בברירת המחדל box-sizing: content-box, הרוחב המוחל הוא רוחב התוכן, ו-padding ו-border בשני הצדדים מתווספים אליו. 200 פיקסלים לתוכן + 40 פיקסלים של מרווח פנימי + 20 פיקסלים של גבול יוצרים רוחב גלוי כולל של 260 פיקסלים.

כדי לשנות את זה, אפשר לציין את המידה של border-box:

.my-box {
  box-sizing: border-box;
    width: 200px;
    border: 10px solid;
    padding: 20px;
}

מודל התיבה החלופי מורה ל-CSS להחיל את width על תיבת הגבולות במקום על תיבת התוכן. פירוש הדבר הוא שה-border וה-padding שלנו נדחים פנימה, כך שכאשר מגדירים את .my-box לרוחב 200px, הוא למעשה מוצג ברוחב 200px.

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

השוואה בין ההשפעות של התאמת גודל תיבת התוכן וקופסת הגבולות.
*,
*::before,
*::after {
  box-sizing: border-box;
}

כלל ה-CSS הזה בוחר את כל הרכיב במסמך ואת כל פסאודו רכיב ::before ו-::after, ומחיל את box-sizing: border-box. המשמעות היא שבכל רכיב נעשה עכשיו שימוש במודל התיבה החלופי הזה.

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

משאבים

גיליונות סגנונות של סוכן משתמש