אנימציות של גבולות CSS

תצוגה של כמה דרכים לאנימציה של גבול ב-CSS

הגדרת גבולות

יש כמה שיטות להגדרת גבול על רכיב: border, outline ו-box-shadow. כפי שמפורט ב-The 3 CSS Methods for Add Element Borders מאת סטפני אקלס, לכל גישה יש יתרונות וחסרונות משלה – במיוחד כשמדובר באנימציה של הגבולות. הסיבה העיקרית לכך שאין להשתמש ב-CSS תקין border היא למטרות אנימציה.

אנימציות גבולות עם outline-offset של קווין ג'. פאוול

מאמר שמשך את תשומת לבי לאחרונה הוא אנימציה מדהימה של גבולות CSS, שבה המחבר Coco בחן אפשרויות נוספות. על ידי החדרת תוכן שנוצר באמצעות ::before ו-::after, הן יוצרות גבול מזויף שלאחר מכן מונפשת.

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

אנימציות גבולות עם תוכן שנוצר על ידי Coco

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

שמירת דגם התיבה

אחד החסרונות בשימוש בתוכן שנוצר כדי לחקות גבול הוא שמודל האריזה לא תקין: עכשיו התוכן יכול לטשטש את הגבול המזויף כי הכיתוב "גבול" מופיע מתחתיו. כדי לפתור את הבעיה, יש להחיל את הערך הרצוי בשדה border-width בתור padding.

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

העקרונות הבסיסיים

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

/* Size of the border */
--border-size: 0.5rem;

/* Create a dotted border */
border: var(--border-size) dotted lime;

/* Create two background layers:
   1. A white semi-transparent
   2. A layer with the colored boxes
 */
background-image:
  linear-gradient(to right, rgb(255 255 255 / 0.5), rgb(255 255 255 / 0.5)),

  conic-gradient(
    from 45deg,
    #d53e33 0deg 90deg,
    #fbb300 90deg 180deg,
    #377af5 180deg 270deg,
    #399953 270deg 360deg
  )
;

התאמת גודל הרקעים באמצעות background-origin

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

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

תמיכה בדפדפן

  • 1
  • 12
  • 4
  • 3

מקור

מה אסור לעשות
/* Manually add or offset the size of the border where needed */
background-position: calc(var(--border-size) * -1) calc(var(--border-size) * -1);
background-size: calc(var(--border-size) * 2 + 100%) calc(var(--border-size) * 2 + 100%);
מה מותר לעשות
background-origin: border-box;

התוספת הזו משפרת מאוד את המראה:

כיווץ שכבת הרקע הלבנה עם background-clip

עכשיו הרקעים תופסים את כל השטח, לכן צריך לכווץ שוב את השכבה השקופה למחצה. במקום להתעסק עם background-size שוב, יש דרך קלה יותר לעשות זאת: להשתמש ב-background-clip ולהגדיר אותו ל-padding-box. כך הרקע לא ישורטט יותר מתחת לאזור של הגבול.

תמיכה בדפדפן

  • 1
  • 12
  • 4
  • 5

מקור

background-clip:
  padding-box, /* Clip white semi-transparent to the padding-box */
  border-box /* Clip colored boxes to the border-box (default) */
;

לבסוף, הגדר את הגבול transparent כדי לקבל את האפקט המלא.

border: 0.3rem dotted transparent;

Animation

כדי לשחזר את האנימציה של הגבול, אפשר לשנות את זווית ההתחלה של הconic-gradient.

--angle: 0deg;
conic-gradient(
  from var(--angle),
  #d53e33 0deg 90deg,
  #fbb300 90deg 180deg,
  #377af5 180deg 270deg,
  #399953 270deg 360deg
);

בזכות @property אפשר לעשות זאת בקלות בדפדפנים שתומכים באפשרות הזו:

תמיכה בדפדפן

  • 85
  • 85
  • 16.4

מקור

@property --angle {
  syntax: "<angle>";
  initial-value: 0deg;
  inherits: false;
}

@keyframes rotate {
  to {
    --angle: 360deg;
  }
}

ביחד, הקוד הופך ל:

תוכן הבונוס: border-image

גישה שטופלה בעבר לשרטט גבול הדרגתי היא להשתמש ב-CSS border-image.

תמיכה בדפדפן

  • 16
  • 12
  • 15
  • 6

מקור

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

/* Create a border */
border: 0.5rem solid transparent;

/* Paint an image in the border */
border-image:
  conic-gradient(
    from var(--angle),
    #d53e33 0deg 90deg,
    #fbb300 90deg 180deg,
    #377af5 180deg 270deg,
    #399953 270deg 360deg
  ) 1
;

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

  • ה-border-image לא מופיע אחרי border-radius; הוא תמיד יישאר מלבני.
  • כשמגדירים מילוי של border-image-slice, border-image לא מופיע מתחת לקבוצה background אלא בחלק העליון. זה עלול להיות בעייתי אם רוצים שהרקע יהיה שקוף למחצה.

לקראת סגירה

יש הרבה אפשרויות ליצירת גבולות ב-CSS. בהתאם לתרחיש לדוגמה, תוכלו לבחור באחד מהם.