עיצוב אחים על סמך ספירה ואינדקס

בעבר, כדי להחיל סגנונות ייחודיים על כל רכיב אחים ברשימה, היה צריך לולאות :nth-child מורכבות או JavaScript כדי להוסיף סגנונות בתוך השורה. ב-CSS מודרני יש את sibling-index() ו-sibling-count() כדי לבצע את החישובים האלה ישירות בגיליון הסגנונות, וכך לאפשר פריסות דינמיות ומערכות צבעים שמתאימות את עצמן באופן אוטומטי כשמוסיפים או מסירים רכיבים.

מערכות צבעים דינמיות

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

.swatch {
  /* Calculate hue by dividing the full 360deg circle by total siblings */
  /* and multiplying by the current element's 1-based index */
  background-color: hsl(
    calc(360deg / sibling-count() * sibling-index()),
    70%,
    50%
  );
}

פריסה סימטרית ואפקטים של מניפה

כדי ליצור אפקטים סימטריים (כמו "מניפה" או פריטים ממורכזים), השתמשו במספר הכולל כדי למצוא את נקודת האמצע של הרשימה.

.card {
  /* Find the center index (e.g., 3 if there are 5 siblings) */
  --center: calc((sibling-count() + 1) / 2);

  /* Rotate items away from the center: negative for left, positive for right */
  /* center element gets 0deg rotation */
  transform: rotate(calc(10deg * (sibling-index() - var(--center))));
}

מיקום מעגלי ומורכב

בשילוב עם פונקציות טריגונומטריות ב-CSS‏ (sin(), cos()), אפשר למקם רכיבים במעגל מושלם בלי קואורדינטות ידניות.

.orb {
  /* Calculate the angle for this item's position on a 360deg circle */
  --angle: calc(360deg / sibling-count() * sibling-index());
  --radius: 150px;

  /* Set the pre-transformed position for all items to be centered */
  position: absolute;
  place-self: center;


  /* Position each element around the parent center */
  transform: translate(
    calc(cos(var(--angle)) * var(--radius)),
    calc(sin(var(--angle)) * var(--radius))
  );
}

אסטרטגיות חלופיות

אם אין תמיכה ב-sibling-index() וב-sibling-count(), צריך לספק חלופה על ידי הזרקה של מאפייני CSS מותאמים אישית באמצעות JavaScript. חובה: צריך להשתמש בזיהוי תכונות עם CSS.supports() כדי לוודא שהסקריפט פועל רק כשצריך.

/* MANDATORY: Check for native support before applying fallback */
if (!CSS.supports('top: calc(sibling-index() * 1px)')) {
  const items = document.querySelectorAll('.item');
  items.forEach((item, index) => {
    /* MANDATORY: Injected index must be 1-based to match native function */
    item.style.setProperty('--sibling-index', index + 1);
    item.style.setProperty('--sibling-count', items.length);
  });
}

ב-CSS, משתמשים במשתנים האלה כבסיס ומחליפים אותם בפונקציות מקוריות בתוך בלוק @supports. חובה: צריך לעטוף את פונקציות ההחלפה המקוריות ב-@supports כדי לוודא שהמשתנים יישארו תקינים בדפדפנים ישנים יותר.

.item {
  /* 1. Set base values using variables (from JS fallback) */
  --index: var(--sibling-index);
  --count: var(--sibling-count);

  /* 2. Use the computed variables - replace this with your implementation-specific styles */
  background-color: hsl(calc(360deg / var(--count) * var(--index)), 70%, 50%);
}

@supports (top: calc(sibling-index() * 1px)) {
  .item {
    /* 3. Override with native functions ONLY if supported */
    --index: sibling-index();
    --count: sibling-count();
  }
}