6 שלב בניית היכולות

CSS מודרני — היכולות של 2024-2026 שמשנות הכל

בפרק הזה תכירו את 20 הפיצ'רים החדשים של CSS שהופכים קוד מורכב ל-3 שורות — Container Queries במקום media queries, :has() הסלקטור שחיכינו לו 20 שנה, CSS nesting native ללא preprocessor, @layer לסוף מלחמות specificity, subgrid, @scope, Popover API, Anchor Positioning, Native Masonry, color-mix(), oklch() ועוד. תלמדו לסווג כל פיצ'ר ל-4 tiers (יציב / קצה-יציב / מתפתח / ניסיוני), להשתמש ב-Can I Use ב-30 שניות, ולכתוב @supports progressive enhancement שלא ישבור דפדפנים ישנים. בסוף יהיה לכם cheat sheet של 20 פיצ'רים עם סטטוס תמיכה (last verified: אפריל 2026), ו-Modern CSS Prompt ל-AI שמכריח אותו להשתמש בפיצ'רים של 2026 ולא ב-CSS של 2015.

מה יהיה לך בסוף הפרק הזה
מה תוכלו לעשות בסוף הפרק הזה
דרישות קדם
הפרויקט שלך

לאורך הקורס אתם בונים את היכולת להפוך אתר גנרי שAI בנה לאתר שנראה כמו עבודת סטודיו — ה-capstone בפרק 13. בפרק הקודם (5) הוספתם שליטה ב-Layout — CSS Grid, Flexbox, 8px spacing system, whitespace מכוון, ו-bento grid. עכשיו יש לכם "שלד" מקצועי. בפרק הזה (6) מוסיפים את ה-"שרירים": Container Queries שמאפשרים ל-component להיות responsive לבד, :has() שיוצר אינטראקטיביות בלי JS, @layer שמביא סדר לקוד של design system, ו-17 פיצ'רים נוספים. הפרק הזה הוא שער לשני פרקים מרכזיים: בפרק 7 (Scroll-Driven Animations) נשתמש באותו דפוס של @supports שלומדים כאן, ובפרק 8 (View Transitions API) נבנה על אותה הבנה של browser support וprogressive enhancement. בלי פרק 6 — פרקים 7 ו-8 לא יעבדו לכם.

מילון מונחים — 21 מושגים מרכזיים בפרק
מונח (English)תרגוםהגדרה בשורה אחת
Container Queriesשאילתות קונטיינרסטיילינג שמגיב לגודל ה-קונטיינר של האלמנט (לא ה-viewport) — הופך components ל-responsive באמת
@containerבלוק תנאי-קונטיינרה-at-rule שמחליף @media כשרוצים לבדוק רוחב קונטיינר במקום רוחב מסך
:has() selectorסלקטור ה"מכיל"סלקטור CSS שבודק אם לאלמנט יש ילד/צאצא מסוים — ה-"parent selector" שחיכינו לו 20 שנה
CSS Nestingקינון CSSכתיבה מקוננת ב-CSS native (ללא SASS/LESS) עם אופרטור & להתייחסות לסלקטור החיצוני
@layerשכבת CascadeAt-rule שיוצר שכבה של specificity — סטיילים בשכבות מאוחרות גוברים תמיד על מוקדמות, ללא קשר ל-specificity של הסלקטור
Cascade Layersשכבות Cascadeהמנגנון הכללי של @layer — סידור CSS לקבוצות מוגדרות (tokens → base → components → utilities)
Subgridתת-רשתgrid ילדים שיורשים את ה-tracks של ה-grid הורה — מאפשר יישור מושלם בין rows/columns ב-cards שונים
@scopeבלוק מתוחםAt-rule שמגביל סטיילים לאזור ספציפי ב-DOM (@scope (.card) to (.card-content)) — style isolation ללא CSS-in-JS
CSS MasonryMasonry מובנהgrid-template-rows: masonry — layout בסגנון Pinterest/Masonry ב-CSS טהור, ללא JavaScript libraries
CSS Mixinsמיקסינים@mixin ו-@apply native של CSS — בלוק כללים שאפשר לשלב ב-selectors אחרים, כמו SASS אבל ב-browser
sibling-index()אינדקס אחפונקציית CSS שמחזירה את מספר האלמנט בקרב אחיו — sibling-index() בתוך calc() יוצר סטיילינג דינמי לפי מיקום
sibling-count()ספירת אחיםפונקציית CSS שמחזירה את סך האחים — משמשת ליצירת distribution אחיד (למשל opacity שעולה לפי מיקום ב-list)
corner-shapeצורת פינהCSS property שמאפשר צורות פינה שונות מ-border-radius רגיל — concave, notch, scoop, squircle
Superellipse / Squircleסופר-אליפסה / סקווירקלצורה בין עיגול לריבוע — הפינה של Apple iOS: "עגולה יותר מעיגול אבל פחות מרובע"
color-mix()ערבוב צבעיםCSS function שמערבב שני צבעים באחוזים — color-mix(in oklch, red 60%, blue). מחליף מתמטיקה ידנית של RGB
oklch()מרחב צבע OKLCHמרחב צבע perceptually uniform — הבהירות שקופה לעין אנושית (יתרון על HSL שלא אחיד perceptually)
Anchor Positioningמיקום מעוגןמיקום אלמנט ביחס לאלמנט אחר (anchor) — מחליף את Floating UI JS library ל-tooltips/dropdowns
Popover APIAPI פופאוברHTML attribute popover + CSS ::backdrop — modals, tooltips, menus native, עם keyboard trap ו-Esc אוטומטי
Browser Supportתמיכת דפדפןאחוז המשתמשים העולמי שדפדפנם תומך בפיצ'ר — בדיקה ב-Can I Use
Progressive Enhancementשיפור הדרגתיאסטרטגיה: נבנה UX בסיסי שעובד בכל הדפדפנים, ואז מוסיפים שכבה של שיפור לדפדפנים המודרניים באמצעות @supports
Can I Use"אפשר להשתמש?"האתר caniuse.com — מקור האמת לסטטוס תמיכה של פיצ'רי CSS/HTML/JS לפי דפדפן
מתחיל 7 דקות חינם מושג

6.1 למה CSS של 2024-2026 הוא לא ה-CSS שאתם מכירים

ה-CSS ש-AI כותב כברירת-מחדל הוא CSS של 2015. זה לא קוד רע — הוא פשוט ישן. הוא משתמש ב-@media queries לכל responsive, ב-:nth-child() וב-+ sibling selectors במקום :has(), ב-calc() במקום clamp(), ב-RGB במקום oklch(), ובמרבית המקרים — ב-JavaScript לדברים ש-CSS כבר עושה בעצמו.

למה זה קורה? כי ה-training data של ה-AI מכיל כמויות אדירות של קוד ישן. גם ה-AIs המתקדמים ביותר נוטים ל-"ברירת-המחדל הבטוחה" — קוד שעובד בכל מקום, אבל נראה כמו שנכתב לפני 10 שנים. עד שלא תבקשו במפורש פיצ'ר מודרני — לא תקבלו אותו.

המטרה של הפרק הזה היא כפולה: (א) לדעת מה קיים — להכיר את 20 הפיצ'רים החדשים שמשנים הכל. (ב) לדעת איך לבקש — לנסח פרומפט שמכריח את ה-AI להשתמש בהם.

ההבדל ב-3 דוגמאות

דוגמה 1 — responsive card שמגיב לגודל שלו:

CSS של 2015 (AI default): מדידת window.innerWidth ב-JS, או @media (min-width: 768px) — אבל המדיה query לא יודע אם ה-card הוא ב-sidebar צר (250px) או ב-main רחב (1000px). התוצאה: ה-card בסיידבר נראה שבור.

CSS של 2026 (Modern): container-type: inline-size + @container (min-width: 400px) { ... }. ה-card יודע את הגודל של עצמו, בכל מקום.

דוגמה 2 — סטיילינג של form עם שגיאה:

CSS של 2015: הוספת class .error ל-form ב-JavaScript, הקשבה ל-events, state management מורכב — 50+ שורות קוד.

CSS של 2026: .form:has(input:invalid) { border-color: red; }. 2 שורות. אפס JavaScript.

דוגמה 3 — dropdown שמוצג כשלוחצים כפתור:

CSS של 2015: Floating UI library (3KB minified), Event listeners, position: absolute עם calculations של scroll/resize, accessibility manual.

CSS של 2026: <button popovertarget="menu"> + <div popover id="menu"> + anchor-name: --menu-anchor. HTML + 3 שורות CSS. Keyboard trap ו-Esc כבר מובנים.

התובנה הגדולה

ההבדל בין אתר שנראה "AI בנה" לאתר שנראה "סטודיו בנה" הוא לרוב לא באיכות הצבעים או הטיפוגרפיה — הוא במה שהאתר יודע לעשות בלי JavaScript. Container queries שגורמים לרכיבים להתנהג חכם בכל מקום, :has() שיוצר אינטראקטיביות בלי state, @layer שמונע מ-utilities לדרוס את ה-design system — כל אלה הופכים את הקוד לנכון ואת החוויה לחלקה. Vibe Coder שיודע את 20 הפיצ'רים האלה כותב אתרים שרצים מהר יותר, שוברים פחות, ונראים טוב יותר — כי הוא לא משתמש ב-JavaScript לדברים ש-CSS כבר עושה.

עשו עכשיו 3 דקות

פתחו את האתר הגנרי שAI בנה לכם. לחצו F12 ועברו ל-tab Sources/Elements. חפשו @media ב-CSS. ספרו כמה יש. עכשיו חפשו @container. 90% מהסיכויים שיש 0. זה הפער. בסוף הפרק תדעו איך לבקש מ-AI להחליף 70% מה-@media ב-@container, ומה זה יעשה לאתר.

עשו עכשיו 2 דקות

פתחו טאב חדש ב-caniuse.com/css-has. רשמו את ה-"Global" support percentage (אמור להיות 92%+ באפריל 2026). זה נתון הייחוס שלכם — :has() נתמך ב-92%+ מהדפדפנים בעולם, ולמרות זאת AI לא משתמש בו. זה בדיוק הפער שהפרק הזה סוגר.

מתחיל 8 דקות חינם אסטרטגיה

6.2 מערכת ה-4 Tiers — איך לסווג כל פיצ'ר חדש

הבעיה עם "CSS מודרני" היא שהוא לא מוצר אחיד. יש פיצ'רים שתומכים בהם ב-96% מהדפדפנים (אפשר להשתמש בלי מחשבה), ויש כאלה שעדיין רק ב-Chrome Canary (חכו שנה). כדי לא לבלבל, אנחנו מסווגים כל פיצ'ר ל-אחד מ-4 Tiers:

TierשםSupportמה עושים?
Tier 1Stable — השתמשו עכשיו95%+ גלובלי, כל 4 הדפדפנים המרכזייםהשתמשו ללא fallback, ללא @supports, בכל פרויקט
Tier 2Cutting-edge Solid85-95% — Chrome/Edge מלא, Safari/Firefox זמינים אבל עדכנייםהשתמשו עם @supports pattern כ-progressive enhancement — UX בסיסי ל-15% הישנים
Tier 3Emerging50-85% — Chrome 145+ בלבד, שאר הדפדפנים באחורההשתמשו רק אם היתרון משמעותי, חובה fallback מלא, עדיפות לפרויקטים פנימיים
Tier 4Experimental / Meta< 50% או behind a flagלמדו את הקונספט, אבל אל תשתמשו ב-production. בדקו מחדש כל 6 חודשים

הסיווג של 20 הפיצ'רים בפרק (אפריל 2026)

הנה המפה המלאה של הפרק. שימו לב שהסטטוסים האלה משתנים מדי חודש — ה-cheat sheet שלכם חייב לכלול תאריך last-verified:

פיצ'רTierChromeEdgeSafariFirefox
Container Queries (@container)1✓ 105+✓ 105+✓ 16+✓ 110+
:has() selector1✓ 105+✓ 105+✓ 15.4+✓ 121+
CSS Nesting (native)1✓ 112+✓ 112+✓ 16.5+✓ 117+
@layer (Cascade Layers)1✓ 99+✓ 99+✓ 15.4+✓ 97+
color-mix()1✓ 111+✓ 111+✓ 16.2+✓ 113+
oklch()/oklab()1✓ 111+✓ 111+✓ 15.4+✓ 113+
clamp()1✓ 79+✓ 79+✓ 13.1+✓ 75+
Subgrid2✓ 117+✓ 117+✓ 16+✓ 71+
@scope2✓ 118+✓ 118+בבנייהבבנייה
Popover API2✓ 114+✓ 114+✓ 17+✓ 125+
Anchor Positioning2✓ 125+✓ 125+בבנייהבבנייה
Native CSS Masonry3✓ 145+ (flag)✓ 145+ (flag)מתוכנןמתוכנן
CSS Mixins (@mixin, @apply)3✓ 145+ (flag)✓ 145+ (flag)מתוכנןמתוכנן
sibling-index() / sibling-count()3✓ 145+✓ 145+מתוכנןמתוכנן
corner-shape / superellipse3✓ 146+ (flag)✓ 146+ (flag)מתוכנןמתוכנן

Last verified: אפריל 2026. הסטטוסים של שורות Tier 3 ככל הנראה ישתפרו משמעותית עד סוף 2026. בדקו ב-caniuse.com לפני כל פרויקט חדש.

מסגרת החלטה: באיזה Tier להשתמש בפרויקט שלי?

ענו על 4 השאלות הבאות — יתנו לכם תשובה ברורה:

  1. האם כל 4 הדפדפנים המרכזיים תומכים? (Chrome, Edge, Safari, Firefox)
    אם כן → Tier 1 — השתמשו בחופשיות.
    אם לא → המשיכו לשאלה 2.
  2. האם יש fallback טבעי? (למשל: Subgrid חוזר ל-Grid רגיל אם לא נתמך)
    אם כן → Tier 2 — השתמשו עם @supports.
    אם לא → המשיכו לשאלה 3.
  3. מה גודל פלח המשתמשים שייפגעו? (בדקו Analytics או Google market share לפי שוק)
    אם < 5% → Tier 2/3 — השתמשו עם fallback מינימלי.
    אם 5-20% → Tier 3 — בנו fallback מלא שנותן UX טוב.
    אם > 20% → Tier 4 — חכו.
  4. האם הפיצ'ר core או enhancement? (האם בלעדיו האתר לא עובד, או רק לא נראה מדהים?)
    Core → רק Tier 1.
    Enhancement → Tier 1-3.

כלל אצבע: לפרויקט production רגיל (landing page, SaaS, e-commerce) — השתמשו ב-Tier 1 חופשי ו-Tier 2 עם @supports. לפרויקט ניסיוני / internal / portfolio — Tier 3 בסדר.

עשו עכשיו 4 דקות

קחו את הפרויקט הפעיל שלכם. ענו על 4 השאלות למעלה ביחס לפיצ'ר הקרוב בליבכם — למשל :has(). רוב הסיכויים שתגיעו ל-Tier 1 וללא @supports. תיאוריה וחבל — זו החלטה של 30 שניות, ואם לא עשיתם אותה אתם חיים בפחד שווא.

טעות נפוצה: "לבקש מ-AI 'CSS מודרני' בלי לפרט אילו פיצ'רים"

הטעות המספר אחת בפרק הזה: לכתוב בפרומפט "use modern CSS" ולצפות שה-AI יבחר טוב. הוא לא יבחר. ה-default שלו הוא 2015. למה זה קורה: ה-training data שלו מכיל כמויות מסיביות של קוד ישן, ו-"modern" זה מונח מעורפל. מה לעשות במקום: רשמו שמות ספציפיים של פיצ'רים. "Use Container Queries (@container) instead of media queries where possible. Use :has() for parent states. Use @layer with layers: tokens, base, components, utilities. Use color-mix() in oklch color space." ה-AI יבצע. השם הספציפי הוא המפתח — בפרק 6.18 יש template מלא.

בינוני 15 דקות חינם מעשי

6.3 Container Queries — הפיצ'ר שהורס את media queries

אם הייתם צריכים ללמוד רק פיצ'ר אחד מהפרק הזה — זה. Container Queries (שאילתות קונטיינר) הן המהפכה הגדולה ב-responsive design מאז media queries ב-2008. הרעיון: במקום לבדוק את רוחב המסך, אנחנו בודקים את רוחב הקונטיינר שבו האלמנט יושב.

הבעיה שהן פותרות

דמיינו product card. אותו רכיב מופיע ב-3 מקומות באתר: (א) בסיידבר צר של 280px, (ב) ב-main grid של 4 עמודות של 300px כל אחת, (ג) ב-hero של עמוד product שתופס 1200px. עם media queries רגילות, ה-card הזה לא יכול לדעת אם הוא בסיידבר או ב-hero — הוא רק יודע את רוחב המסך. אם המסך רחב (desktop 1440px), הוא "חושב" שיש לו הרבה מקום — אבל בפועל הוא נדחק ל-280px בסיידבר ונשבר.

Container Queries פותרות את זה. ה-card שואל את הקונטיינר שלו: "כמה מקום יש לי?" ומקבל תשובה מדויקת. אותו רכיב, 3 התנהגויות שונות, בלי JavaScript ובלי variants.

ה-Syntax הבסיסי

/* שלב 1: מסמנים את האב כ"container" */
.card-wrapper {
  container-type: inline-size;
  container-name: card;  /* optional — שם לשימוש ב-@container */
}

/* שלב 2: כותבים סטיילים על בסיס רוחב הקונטיינר */
.card {
  display: flex;
  flex-direction: column;
  gap: 1rem;
}

@container card (min-width: 400px) {
  .card {
    flex-direction: row;
    align-items: center;
    gap: 1.5rem;
  }
}

@container card (min-width: 600px) {
  .card {
    gap: 2rem;
  }
  .card img {
    width: 40%;
  }
}

תסתכלו על זה: אותו .card עובד בכל מקום. בסיידבר הוא column. ב-grid רחב הוא row. ב-hero הוא row עם תמונה גדולה. ה-HTML זהה. זה הקסם.

3 שימושים אמיתיים

שימוש 1: Product card ב-E-commerce

ה-card מופיע ב-search results (2 עמודות), recently viewed (4 עמודות), ו-product page (1 עמודה רחבה). Container queries מאפשרות לו לשנות layout מ-stacked (תמונה למעלה, טקסט למטה) ל-horizontal (תמונה בשמאל, טקסט בימין) ל-expanded (תמונה ענקית, טקסט מפורט) — לפי המקום שהוא מקבל.

שימוש 2: Sidebar widget

widget של "Recent articles" שאנשים שמים בסיידבר (200px) או ב-footer (1200px, 4 עמודות). ב-sidebar הוא stacked list. ב-footer הוא 4-column grid. Container query — שורה אחת.

שימוש 3: Embedded component (React/Web Component)

אם אתם בונים component library — למשל widget של לוח זמנים שמוטמע באתרים אחרים — אתם לא יודעים איפה הוא ימוקם. Container queries הם חובה: הרכיב מתאים את עצמו לכל גודל שמקבל, בלי לשאול אף אחד.

Container Query Units — cqw, cqh

בנוסף ל-@container, יש יחידות חדשות שמבוססות על הקונטיינר:

למשל, font-size: clamp(1rem, 3cqi, 2rem) — font שגודלו תלוי ב-container, לא ב-viewport. Genius.

מסגרת החלטה: Container Query או Media Query?

השאלה שתעבוד 95% מהמקרים:

עשו עכשיו 5 דקות

פתחו CodePen חדש. העתיקו את הקוד של .card-wrapper + .card מהדוגמה. הוסיפו 3 wrappers ב-HTML — אחד ברוחב 250px, אחד 500px, אחד 900px. תראו איך אותו HTML של card משנה layout ב-3 המקומות. זה רגע ה-"aha" של הפרק. אם לא הרגשתם אותו — חזרו ועשו שוב. זה קריטי.

טעות נפוצה: "לחשוב ש-Container Queries מחליפים media queries"

לא. הם משלימים זה את זה. Media query למקרו-layout (האם אני במובייל או desktop), Container query למיקרו-layout (איך ה-card הזה מסתדר במקום שקיבל). אם תחליפו את כל ה-@media ב-@container — תקבלו באגים, כי החלטות ברמת הדף (navbar, hero) לא שייכות לקונטיינר ספציפי. מה לעשות במקום: Media query להחלטות דף. Container query להחלטות רכיב. 70% מהרכיבים שלכם מתאימים ל-@container, 30% ל-@media.

בינוני 15 דקות חינם מעשי

6.4 :has() — הסלקטור שחיכינו לו 20 שנה

מ-1996 ועד 2022, ל-CSS היה חור גדול אחד: לא הייתה דרך לבחור אלמנט על בסיס הילדים שלו. יכולת לבחור child שיש לו parent מסוים (.parent .child), אבל לא להפך. ה-parent selector היה הבקשה הכי מבוקשת ב-CSS במשך שני עשורים.

ב-2022 הגיע :has() ופתר את זה. והוא עושה הרבה יותר מ"parent selector" — הוא מאפשר לבדוק כל קשר DOM: האם לאלמנט יש ילד? צאצא? אח (sibling) אחרי? אלמנט עם מצב ספציפי?

ה-Syntax

/* אלמנט X שיש לו ילד/צאצא Y */
X:has(Y) { ... }

/* .card שיש בתוכו img */
.card:has(img) {
  padding-top: 0;  /* בלי padding למעלה כי יש תמונה */
}

/* form שיש בו input לא-תקין */
form:has(input:invalid) {
  border: 2px solid red;
}

/* section שיש אחריו section */
section:has(+ section) {
  border-bottom: 1px solid var(--border);
}

8 שימושים מעשיים

1. Form validation — בלי JavaScript:

.field:has(input:invalid:not(:placeholder-shown)) {
  --field-color: var(--danger);
}
.field:has(input:valid:not(:placeholder-shown)) {
  --field-color: var(--success);
}
.field label { color: var(--field-color, var(--neutral)); }
.field input { border-color: var(--field-color, var(--neutral)); }

השדה משתנה צבע אדום/ירוק על בסיס תקינות הקלט. כולל :not(:placeholder-shown) כדי לא להציג שגיאה לפני שהמשתמש הקליד.

2. Card states — האם יש תמונה:

.card:has(img) .card-text { padding: 1rem; }
.card:not(:has(img)) .card-text { padding: 2rem; text-align: center; }
.card:not(:has(img)) { background: var(--gradient-primary); }

card עם תמונה: תמונה + טקסט רגיל. card בלי תמונה: רקע צבעוני + טקסט מרכזי. אותו HTML template. התנהגות חכמה.

3. Empty states — מצב "אין תוכן":

.list:not(:has(li)) {
  display: block;
  padding: 4rem;
  text-align: center;
  color: var(--muted);
}
.list:not(:has(li))::before {
  content: "אין פריטים עדיין";
}

אם ה-list ריק — מוצג empty state. JS? לא. 5 שורות CSS.

4. Conditional layouts — sidebar אם יש aside:

main { grid-template-columns: 1fr; }
main:has(aside) { grid-template-columns: 1fr 280px; }

עיצוב הדף משתנה על בסיס נוכחות <aside>.

5. Theme switching — על בסיס toggle:

body:has(#dark-mode-toggle:checked) {
  --bg: #0a0a0a;
  --text: #fafafa;
}

toggle של dark mode ללא JavaScript. checkbox + :has() + custom properties.

6. Active nav state — על בסיס URL:

nav:has(a[href="/about"].active) .about-link {
  font-weight: 700;
}

כל nav שמכיל link פעיל של /about — מדגיש אותו. (שילוב עם aria-current="page" נפוץ גם.)

7. Dropdown open state:

.dropdown:has(.menu[aria-expanded="true"]) {
  background: var(--hover-bg);
}
.dropdown:has(.menu[aria-expanded="true"]) .arrow {
  transform: rotate(180deg);
}

כש-dropdown פתוח — החצים והרקע מתעדכנים. בלי לגעת ב-state management.

8. Sibling-aware styling:

article:has(+ article) {
  margin-bottom: 2rem;
  border-bottom: 1px solid var(--border);
}

אם יש article אחריו — הוסף margin+border. אם זה האחרון — לא. זה פותר את הבעיה הקלאסית של "הפרדה בין items בלי הפרדה אחרי האחרון".

Performance — האם :has() איטי?

שאלה נפוצה: האם selector שמסתכל על ילדים לא יהיה לאט? התשובה: לא. המנועים המודרניים (Blink, WebKit, Gecko) אופטימיזו :has() למקרי שימוש פרקטיים — הוא רץ כמו כל selector אחר ברוב המקרים. המקרים היחידים שבהם אפשר לראות איטיות: :has() על עץ עמוק מאוד (1000+ אלמנטים) עם שינויי DOM תכופים. ברוב האתרים — לא תרגישו הבדל.

מסגרת החלטה: מתי :has() ומתי JavaScript?
עשו עכשיו 4 דקות

קחו את דוגמה 1 (Form validation). העתיקו ל-CodePen. בנו form עם 2 שדות (email + טלפון). השאירו את ה-validation לדפדפן (type="email", required). הוסיפו את ה-CSS של :has(input:invalid). הקלידו טקסט לא-תקין בשדה. ראו איך השדה משנה צבע ללא JS. זה ה-moment שאחריו לא תחזרו ל-JS validation.

עשו עכשיו 3 דקות

פתחו את האתר שלכם. חפשו event listeners ב-JavaScript שמשנים classes של אלמנטים על בסיס מצב של ילדים (active, hasImage, isEmpty). רשמו 2-3 מהם. אלה המקרים שאפשר להחליף ב-:has(). שמרו את הרשימה — תגשו אליה בתרגילים.

מתחיל 6 דקות חינם מעשי

6.5 CSS Nesting — SASS בלי SASS

עשרים שנה השתמשו מפתחים ב-SASS/LESS/PostCSS רק בשביל דבר אחד: לכתוב CSS מקונן. נגמר. CSS Nesting native נתמך בכל הדפדפנים מ-2023, ואתם לא צריכים יותר preprocessor בשביל זה.

לפני ואחרי

/* CSS של 2015 — שטוח */
.card { padding: 1rem; border-radius: 0.5rem; }
.card h2 { margin-bottom: 0.5rem; }
.card p { color: var(--muted); }
.card:hover { box-shadow: var(--shadow-md); }
.card.featured { border: 2px solid var(--primary); }
.card.featured h2 { color: var(--primary); }

/* CSS של 2026 — מקונן, native */
.card {
  padding: 1rem;
  border-radius: 0.5rem;

  & h2 { margin-bottom: 0.5rem; }
  & p { color: var(--muted); }

  &:hover { box-shadow: var(--shadow-md); }

  &.featured {
    border: 2px solid var(--primary);

    & h2 { color: var(--primary); }
  }
}

הכלל של ה-&

האופרטור & מייצג את ה-selector החיצוני. &:hover שווה ל-.card:hover. &.featured שווה ל-.card.featured. כדי להימנע מ-ambiguity, הפרשנות של CSS Nesting דורשת & במקרים מסוימים — הכי בטוח להשתמש בו תמיד.

כלל הזהב: לא יותר מ-3 רמות

Nesting הוא נשק דו-פני. אם תקוננו 5 רמות עמוק, תקבלו specificity wars שאתם לא יכולים לפתור. הכלל: עד 3 רמות. אם הגעתם ל-4, תחלקו לקלאסים נפרדים.

עשו עכשיו 3 דקות

קחו קובץ CSS שטוח של הפרויקט שלכם. בחרו רכיב אחד (כרטיס, navbar, footer). המירו את כל ה-selectors שלו ל-nested syntax עם &. תראו איך הקוד מתקצר ב-30-40% והופך קריא יותר.

בינוני 10 דקות חינם אסטרטגיה

6.6 @layer — סוף מלחמות ה-specificity

אם כתבתם CSS עד היום, אתם מכירים את זה: !important שדורס !important אחר. שני .class שדוחים #id. Utility classes של Tailwind שמפסידים ל-component CSS. זה specificity war, והוא אחת הסיבות העיקריות למה CSS "מרגיש שבור".

Cascade Layers (@layer) פותרים את זה אחת ולתמיד. הרעיון פשוט: מה שבשכבה מאוחרת יותר תמיד גובר, ללא קשר ל-specificity של הסלקטור. שכבות נקבעות בסדר מפורש.

הדפוס המומלץ — 4 שכבות

/* הצהרת השכבות — קובעת את הסדר. קריטי! */
@layer tokens, base, components, utilities;

/* שכבה 1: Design Tokens — CSS custom properties */
@layer tokens {
  :root {
    --color-primary: oklch(55% 0.2 250);
    --space-1: 0.5rem;
    --space-2: 1rem;
  }
}

/* שכבה 2: Base — reset ו-defaults */
@layer base {
  * { box-sizing: border-box; }
  body { font-family: Heebo, sans-serif; line-height: 1.6; }
  a { color: var(--color-primary); }
}

/* שכבה 3: Components — רכיבים בנויים */
@layer components {
  .card {
    padding: var(--space-3);
    border-radius: 0.75rem;
    background: var(--bg-card);
  }
  .button-primary {
    background: var(--color-primary);
    color: white;
  }
}

/* שכבה 4: Utilities — דריסות נקודתיות (Tailwind-style) */
@layer utilities {
  .mt-4 { margin-top: var(--space-4); }
  .text-center { text-align: center; }
  .hidden { display: none; }
}

למה זה משנה הכל

עכשיו .mt-4 (utility) תמיד גובר על .card (component), בלי !important. אפילו אם ה-utility הוא סלקטור של 1 קלאס וה-component הוא סלקטור של 3 קלאסים — ה-utility ב-layer מאוחר יותר, ולכן ינצח. זה הופך את ה-CSS לצפוי.

מתי להשתמש ב-@layer

בינוני 10 דקות חינם מעשי

6.7 color-mix() ו-oklch() — הצבעים של 2026

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

1. color-mix() — ערבוב מכני של צבעים

/* ערבוב 60% אדום עם 40% כחול במרחב oklch */
background: color-mix(in oklch, red 60%, blue);

/* ליצור variants של ה-primary color */
--primary-light: color-mix(in oklch, var(--primary) 70%, white);
--primary-dark: color-mix(in oklch, var(--primary) 70%, black);
--primary-muted: color-mix(in oklch, var(--primary) 20%, transparent);

/* hover state — primary עם שכבת שקיפות */
.button:hover {
  background: color-mix(in oklch, var(--primary) 90%, black);
}

זה מחליף חישובי RGB ידניים, ספריות JS של color manipulation, ו-SASS lighten()/darken(). פחות מתמטיקה, יותר שליטה.

2. oklch() — מרחב צבע שהעין רואה נכון

HSL (Hue, Saturation, Lightness) היה הסטנדרט במשך 15 שנה. הבעיה: Lightness ב-HSL לא נתפס אחיד על-ידי העין האנושית. צהוב עם L=50% נראה בהיר בהרבה מסגול עם L=50%. זה הופך design systems לכאב ראש — אם תרצו ליצור גרדאציה אחידה של בהירות, תצטרכו לחשב ידנית.

OKLCH (OK Lightness Chroma Hue) פותר את זה. הבהירות אחידה perceptually. L=50% נראה זהה בבהירות בכל גוון. זה הופך את בניית ה-palette לקלה ועקבית.

/* Palette עם 5 רמות בהירות — כל שורה באותה בהירות חזותית */
--gray-100: oklch(95% 0.005 250);
--gray-300: oklch(85% 0.008 250);
--gray-500: oklch(60% 0.012 250);
--gray-700: oklch(35% 0.015 250);
--gray-900: oklch(15% 0.018 250);

/* Primary, secondary, accent — באותה בהירות */
--primary:   oklch(60% 0.18 250);  /* כחול */
--secondary: oklch(60% 0.18 20);   /* כתום — באותה בהירות */
--accent:    oklch(60% 0.18 140);  /* ירוק — באותה בהירות */

שלושת הפרמטרים של oklch()

טיפ פרקטי

השתמשו ב-oklch.com — כלי אונליין שממיר את הצבע הנוכחי שלכם ל-OKLCH, מראה לכם את ה-palette במרחב הזה, ומאפשר "לסובב" את הגוון בלי לשנות בהירות. זה מה שמעצבים של 2026 משתמשים בו.

בינוני 8 דקות חינם מעשי

6.8 Subgrid — יישור מושלם בין grid items

הבעיה: יש לכם row של 4 cards. בכל card יש: כותרת, תיאור, מחיר, כפתור. הכותרות באורך שונה — חלקן שורה אחת, חלקן שתיים. זה גורם לתיאור ב-card עם כותרת קצרה להתחיל "גבוה יותר" מאשר ב-card עם כותרת ארוכה. ה-cards לא מיושרים.

Subgrid פותר את זה. במקום שכל card יהיה grid עצמאי — הוא יורש את ה-rows מה-grid הורה. כל הכותרות בשורה אחת, כל התיאורים בשורה אחרת, כל המחירים בשורה אחרת, כל הכפתורים בשורה אחרת. יישור מושלם.

הקוד

.card-row {
  display: grid;
  grid-template-columns: repeat(4, 1fr);
  grid-template-rows: auto auto auto auto;  /* title, desc, price, button */
  gap: var(--space-3);
}

.card {
  display: grid;
  /* הקסם: יורש את ה-rows מה-parent */
  grid-template-rows: subgrid;
  grid-row: span 4;  /* התופס 4 שורות של ה-parent */
  gap: 0.5rem;
}

.card h3 { grid-row: 1; }
.card p { grid-row: 2; }
.card .price { grid-row: 3; }
.card button { grid-row: 4; }

התוצאה: יש לכם 4 "שורות וירטואליות" שגולשות על פני כל ה-cards. כל אלמנט עם grid-row: N יהיה באותו גובה באופקי. זה מה שלא היה אפשר בלי subgrid.

מתקדם 7 דקות חינם אסטרטגיה

6.9 @scope — הגבלת סטיילים לאזור ב-DOM

פיצ'ר מתקדם יותר. @scope יוצר "גבול" ל-CSS — הוא חל רק על אלמנטים בתוך אזור מוגדר של ה-DOM. זה פותר את הבעיה של widgets שמשתלבים באתרים אחרים או components עם style isolation.

/* כל ה-CSS הזה חל רק בתוך .shopping-cart */
@scope (.shopping-cart) {
  :scope { padding: 1.5rem; }
  .item { border-bottom: 1px solid var(--border); }
  .price { font-weight: 700; color: var(--primary); }
}

/* Scope עם "Lower boundary" — חל מ-.article עד ל-.comments */
@scope (.article) to (.comments) {
  /* כאן כללים שחלים בתוך article אבל לא נכנסים לאזור תגובות */
  p { font-size: 1.125rem; line-height: 1.75; }
}

זה בעצם CSS Modules ללא build step. שימושי למי שבונה widgets, לא לרוב הפרויקטים.

Tier 2 באפריל 2026 — Chrome/Edge מלא, Safari/Firefox בבנייה. אם זה קריטי — @supports selector(:scope) ל-fallback.

בינוני 10 דקות חינם מעשי

6.10 Popover API — modals ו-tooltips ללא JavaScript

Popover API הוא אחד הפיצ'רים הכי חמים של 2024-2026. הוא מביא modals, tooltips, context menus, ו-dropdowns כ-HTML native — עם keyboard traps, Esc support, ו-click-outside handling מובנים.

דוגמה מינימלית

<!-- כפתור שפותח פופאובר -->
<button popovertarget="user-menu">תפריט משתמש</button>

<!-- הפופאובר עצמו -->
<div id="user-menu" popover>
  <a href="/profile">הפרופיל שלי</a>
  <a href="/settings">הגדרות</a>
  <button popovertarget="user-menu" popovertargetaction="hide">סגור</button>
</div>

זה הכל. אפס JavaScript. הדפדפן מטפל ב:

2 סוגי Popover

Styling עם ::backdrop

[popover] {
  padding: 1.5rem;
  border: none;
  border-radius: 1rem;
  box-shadow: var(--shadow-xl);
}

/* הרקע שמאחורי — כשה-popover פתוח */
[popover]::backdrop {
  background: rgba(0, 0, 0, 0.5);
  backdrop-filter: blur(4px);
}
עשו עכשיו 4 דקות

צרו HTML חדש. הדביקו את ה-code של "דוגמה מינימלית" של Popover. פתחו בדפדפן. לחצו על הכפתור. ראו שהתפריט נפתח. לחצו Esc. ראו שהוא נסגר. לחצו מחוץ. ראו שהוא נסגר. בלי JavaScript. זה הרגע שמרגישים את CSS של 2026.

מתקדם 10 דקות חינם מעשי

6.11 Anchor Positioning — סוף לספריית Floating UI

Floating UI (לשעבר Popper.js) היא ספרייה של ~10KB שכמעט כל אתר מודרני משתמש בה כדי למקם tooltips, dropdowns, popovers ליד כפתורים. Anchor Positioning מחליף אותה. CSS טהור.

/* הכפתור משמש כ-anchor */
button.help-btn {
  anchor-name: --help-anchor;
}

/* ה-tooltip "מתחבר" ל-anchor */
.help-tooltip {
  position: absolute;
  position-anchor: --help-anchor;

  /* ממוקם למעלה של ה-anchor, ממורכז אופקית */
  top: anchor(top);
  left: anchor(center);
  translate: -50% -100%;

  /* מרווח של 8px מה-anchor */
  margin-bottom: 8px;
}

/* Auto fallback — אם אין מקום למעלה, תעבור למטה */
.help-tooltip {
  position-try: flip-block;
}

זה מחליף חישובי JS של getBoundingClientRect, scroll/resize listeners, ו-reposition logic. CSS טהור, יותר מהיר, פחות קוד.

סטטוס אפריל 2026: Tier 2 — Chrome 125+/Edge 125+ מלא. Safari/Firefox בבנייה. @supports (position-anchor: --x) לבדיקה.

מתקדם 6 דקות חינם מעשי

6.12 Native CSS Masonry — Pinterest ב-CSS טהור

Masonry הוא layout שבו אלמנטים בגבהים שונים "נופלים" לעמודות באופן אופטימלי — כמו Pinterest. עד 2025, זה דרש JavaScript (Masonry.js, Isotope). עכשיו CSS עושה את זה לבד.

.gallery {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(250px, 1fr));
  grid-template-rows: masonry;  /* זה הקסם */
  gap: 1rem;
}

שורה אחת. פחות שורה בעצם — שינוי של grid-template-rows ל-masonry. האלמנטים "נופלים" לעמודה הקצרה ביותר בכל פעם. Pinterest layout מלא.

Tier 3 באפריל 2026 — Chrome 145+ מאחורי flag. שאר הדפדפנים מתוכננים. עד שיהיה יציב — השתמשו ב-columns: 3 + column-gap כ-fallback (לא אותו דבר, אבל דומה).

מתקדם 6 דקות חינם אסטרטגיה

6.13 CSS Mixins (@mixin, @apply) — reusable patterns native

עוד פיצ'ר שגוזל את SASS. Mixins הם "פונקציות CSS" — בלוק של כללים שאפשר "להחיל" על selector אחר.

/* הגדרת mixin */
@mixin card-base {
  padding: 1.5rem;
  border-radius: 1rem;
  background: var(--bg-card);
  box-shadow: var(--shadow-sm);
  transition: box-shadow 0.2s;
}

/* שימוש */
.product-card {
  @apply card-base;
  border: 1px solid var(--border);
}

.article-card {
  @apply card-base;
  max-width: 42rem;
}

Tier 3 — Chrome 145+ מאחורי flag. עד שיציב — Tailwind @apply הוא ה-alternative (אבל זה build-step, לא native). --var: paren-value עם @property הוא פתרון ביניים.

מתקדם 6 דקות חינם מעשי

6.14 sibling-index() ו-sibling-count() — סטיילינג דינמי לפי מיקום

עד 2025, אם רציתם לסטייל אלמנטים על בסיס מיקומם במערך אחים, הייתם צריכים :nth-child(1), :nth-child(2) וכו' — מדרגה-מדרגה ידנית. sibling-index() ו-sibling-count() הופכים את זה לחישוב דינמי.

/* כל פריט ב-list — opacity דינמי לפי מיקום */
.list-item {
  opacity: calc(1 - (sibling-index() - 1) / sibling-count() * 0.5);
  /* הפריט הראשון — opacity 1, האחרון — 0.5 */
}

/* animation delay מדורג */
.card {
  animation: slide-in 0.6s ease forwards;
  animation-delay: calc(sibling-index() * 0.1s);
  /* card ראשון — 0ms, שני — 100ms, שלישי — 200ms... */
}

זה הרבה יותר אלגנטי מ-:nth-child(1) { ... } :nth-child(2) { ... } של 10 שורות. Tier 3 — Chrome 145+ באפריל 2026. @supports fallback.

מתקדם 5 דקות חינם מעשי

6.15 corner-shape ו-superellipse — squircles בסגנון Apple

אם הסתכלתם על אייקון iOS אי-פעם — הפינות שלו "מעוגלות יותר מעיגול". זה נקרא squircle (square + circle), או מתמטית — superellipse. הפינה עוברת יותר בחלקות מהצלע לעקומה.

עד 2025, זה דרש SVG או JavaScript. עכשיו:

.ios-icon {
  border-radius: 20%;
  corner-shape: superellipse(2.5);
  /* הערך 2.5 = squircle "עגול יותר מעיגול" */
  /* superellipse(2) = עיגול רגיל */
  /* superellipse(4) = יותר מרובע */
  /* superellipse(infinity) = ריבוע חד */
}

הערך 2-2.5 נותן את ה-look של iOS. Tier 3 — Chrome 146+ מאחורי flag באפריל 2026. fallback — border-radius רגיל נראה "בסדר" גם בלי.

טעות נפוצה: "להשתמש בפיצ'ר חדש בלי fallback"

אתם רואים דוגמה של corner-shape ב-Twitter, מתלהבים, ומוסיפים ל-production. 5-10% מהמשתמשים שלכם רואים ריבוע חד במקום squircle — זה עדיין נראה סביר. אבל אם הפיצ'ר קריטי (Popover API שפותח תפריט, :has() שמציג שגיאה) — 5-10% של משתמשים לא יוכלו להשתמש באתר. מה לעשות במקום: Tier 2-3 תמיד עם @supports. Tier 1 בלי חשש. ההכרעה: האם בלי הפיצ'ר — האתר עובד? אם לא — לא בלי @supports.

מתחיל 5 דקות חינם כלי

6.16 Can I Use — איך לבדוק support ב-30 שניות

האתר caniuse.com הוא מקור האמת של עולם ה-web. לפני כל פיצ'ר חדש — בדקו שם. ה-workflow של 30 שניות:

  1. גשו ל-caniuse.com/<feature-name> (למשל caniuse.com/css-has)
  2. חפשו את "Global" percentage בראש העמוד. זה אחוז המשתמשים העולמי שדפדפנם תומך
  3. סתכלו על טבלת הדפדפנים. ירוק = תומך. אדום = לא. כתום = עם prefix או behind flag
  4. בדקו "Notes & Known issues" למטה — יש תמיד גאצ'ות
  5. קבלו החלטה לפי 4-Tier framework שלכם

דוגמה — :has() באפריל 2026

דוגמה — CSS Masonry

עשו עכשיו 3 דקות

בחרו 3 פיצ'רים מהפרק: :has(), Container Queries, Subgrid. בדקו כל אחד ב-caniuse.com. רשמו את ה-Global percentage והחליטו Tier. זה השריר שאתם בונים — לפני כל שימוש בפיצ'ר חדש, 30 שניות ב-caniuse.

בינוני 10 דקות חינם מעשי

6.17 @supports — Progressive Enhancement שלא שובר כלום

Progressive Enhancement (שיפור הדרגתי) היא אסטרטגיה: בונים קודם UX בסיסי שעובד בכל הדפדפנים, ואז מוסיפים שכבה של שיפור לדפדפנים שתומכים בפיצ'רים חדשים. ה-at-rule @supports הוא הכלי.

ה-Syntax

/* בסיס — עובד בכל הדפדפנים */
.gallery {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(250px, 1fr));
  gap: 1rem;
}

/* שיפור — רק אם הדפדפן תומך ב-masonry */
@supports (grid-template-rows: masonry) {
  .gallery {
    grid-template-rows: masonry;
  }
}

Template מוכן להעתקה

/* ===== PROGRESSIVE ENHANCEMENT TEMPLATE ===== */

/* 1. BASELINE — UX בסיסי לכולם */
.modal {
  /* בסיס עם JavaScript toggle */
  display: none;
  position: fixed; inset: 0;
  background: white; padding: 2rem;
}
.modal.is-open { display: block; }

/* 2. ENHANCED — Popover API לדפדפנים שתומכים */
@supports selector(:popover-open) {
  /* כאן: שימוש ב-popover HTML attribute במקום class toggle */
  .modal[popover] { /* styles */ }
  /* JS יכול להשתמש ב-.showPopover() במקום להוסיף class */
}

/* 3. ENHANCED+ — anchor positioning */
@supports (position-anchor: --x) {
  .tooltip {
    position: absolute;
    position-anchor: --help-anchor;
    top: anchor(top);
  }
}

/* 4. ENHANCED++ — container queries */
@supports (container-type: inline-size) {
  .card-wrapper { container-type: inline-size; }
  @container (min-width: 400px) {
    .card { flex-direction: row; }
  }
}

3 סוגי @supports

עשו עכשיו 4 דקות

קחו רכיב אחד בפרויקט שלכם שיכול להשתפר עם Container Query (למשל product card). כתבו את ה-CSS הבסיסי שעובד בלי. הוסיפו @supports (container-type: inline-size) עם השיפור. פתחו ב-Chrome (יראה שיפור) ואז ב-Safari 14 (לא תומך — יראה fallback). זה progressive enhancement בפועל.

בינוני 15 דקות חינם תרגול

6.18 Modern CSS Prompt — איך לכפות על AI לכתוב CSS של 2026

זה ה-deliverable המרכזי של הפרק. פרומפט מובנה שתוכלו להעתיק-להדביק לתחילת כל פרויקט AI, שמכריח את הכלי להשתמש ב-CSS של 2026 ולא של 2015.

Modern CSS Prompt Template v1.0 (English for AI tools)

MODERN CSS REQUIREMENTS — Use these features by name. Do not substitute with older alternatives:

Layout & Responsiveness:
- For COMPONENT responsiveness (cards, widgets, embeds) use Container Queries with container-type: inline-size and @container (min-width: N) {...}. Do NOT use @media for component-level responsive.
- For PAGE-LEVEL responsiveness (navbar, sidebar, hero), use @media.
- For card rows requiring alignment, use subgrid: grid-template-rows: subgrid.

Selectors & State:
- Use :has() for parent/ancestor state: form validation (.field:has(input:invalid)), card variants (.card:has(img)), empty states (.list:not(:has(li)))), conditional layouts.
- Do NOT use JavaScript for state that can be expressed via HTML (checkbox + :has(), aria-attributes + :has()).

Structure:
- Use CSS Nesting with & operator. Max 3 levels deep.
- Use @layer with this exact order: @layer tokens, base, components, utilities;.
- Wrap design tokens in @layer tokens, components in @layer components, utilities/Tailwind-style helpers in @layer utilities.

Colors:
- Use oklch() color space for all palette definitions. Do NOT use HSL for new palettes.
- Use color-mix(in oklch, X N%, Y) for variants (lighter/darker/muted). Do NOT use manual RGB math.
- Hover/active states: color-mix(in oklch, var(--primary) 90%, black).

UI Components:
- For modals, dropdowns, tooltips, context menus — use Popover API (HTML popover attribute + popovertarget).
- For positioning relative to another element (tooltips, dropdowns) — use Anchor Positioning (anchor-name, position-anchor, anchor()). Do NOT use Floating UI library.
- Use ::backdrop with backdrop-filter: blur() for modal overlays.

Fluid sizing:
- Use clamp(min, fluid, max) for responsive font-sizes and spacing. Do NOT use multiple media queries for this.
- Prefer cqi units in clamp() when sizing inside a container-typed element.

Progressive Enhancement:
- For features beyond baseline (Tier 2-3), use @supports to add enhancements without breaking older browsers.
- For :has(): @supports selector(:has(*)).
- For container queries: @supports (container-type: inline-size).

DO NOT (anti-patterns that AI defaults to):
- Do NOT use @media inside a component — use @container.
- Do NOT use JavaScript to toggle classes when :has() can read HTML state.
- Do NOT use SASS/LESS @import or nesting — use native CSS Nesting.
- Do NOT use HSL for new color palettes — use OKLCH.
- Do NOT use Floating UI, Popper, or manual getBoundingClientRect — use Anchor Positioning.
- Do NOT use position: fixed + manual focus trap for modals — use Popover API.
- Do NOT use !important — use @layer ordering instead.

Browser Support Baseline (last verified: April 2026):
- Target: Chrome 120+, Edge 120+, Safari 17+, Firefox 121+
- All Tier 1 features work. Tier 2-3 need @supports.

QUALITY GATE:
Before delivering, audit the CSS: (1) Is there any @media that should be @container? (2) Is there any JavaScript class-toggle that can be :has()? (3) Are colors in oklch()? (4) Are there @layer declarations? (5) Is there an Anchor Positioning block instead of JS positioning? (6) Are modals using popover attribute? If any answer is "no", check if you should refactor.

4 שלבי ההתאמה האישית

  1. Target browsers: אם הפרויקט צריך לתמוך ב-IE11 (נדיר מאוד ב-2026) — הסירו את Tier 2-3. אחרת — השאירו הכל.
  2. אילו פיצ'רים ב-Tier 2 לאשר? Popover ו-Subgrid — תמיד. Anchor Positioning — רק אם יש ספרייה שעדיין משתמשים בה. @scope — אם יש צורך ב-isolation.
  3. Progressive Enhancement — להשאיר או להסיר: לפרויקט עם 5%+ פלח של משתמשים ישנים — להשאיר. לפרויקט internal/portfolio — אפשר להסיר ולהיות Chrome-first.
  4. Quality gate — תמיד להשאיר: זה מה שמאלץ את ה-AI לבדוק את עצמו בסוף.
עשו עכשיו 8 דקות

העתיקו את ה-Modern CSS Prompt. שלבו אותו עם ה-Layout Spec מפרק 5 + Color Palette מפרק 3 + Typography Spec מפרק 4. זה design brief מלא של 2026. שמרו. תשתמשו בזה בתרגיל האחרון של הפרק.

תרגיל 1: Component Audit — מה ב-@media ומה ב-@container 20 דקות
  1. פתחו פרויקט שלכם. רשמו את 5 הרכיבים המרכזיים (למשל: card, navbar, form, hero, sidebar).
  2. לכל רכיב, רשמו: האם הוא מופיע בכמה מקומות שונים? מה הגדלים השונים?
  3. סיווגו: אם הרכיב מופיע ב-2+ גדלים שונים באותה עמודה של פרויקט — הוא מועמד ל-@container. אחרת @media.
  4. בחרו את הרכיב הראשון שמתאים ל-@container — סביר שזה card.
  5. הוסיפו container-type: inline-size ל-wrapper. העבירו לפחות 2 media queries שלו ל-@container.
  6. בדקו ב-DevTools שהרכיב עובד נכון ב-3 גדלים שונים (הקטינו את ה-wrapper ידנית ב-DevTools).
  7. בדקו שה-wrapper ב-sidebar צר נותן layout אחר מאשר ב-main רחב.

מה צריך להיות בסוף: מסמך של טבלת 5 רכיבים עם סיווג (@media/@container), רכיב אחד שהומר, 3 screenshots של אותו רכיב ב-3 גדלים, ורשימת 2-3 תובנות שהגעתם אליהן.

תרגיל 2: המרת JS ל-:has() 25 דקות
  1. פתחו את קוד ה-JavaScript של הפרויקט שלכם. חפשו: classList.add, classList.toggle, setAttribute — כל מה שמוסיף/מסיר state-class.
  2. רשמו 3 מקרים כאלה. למשל: "add .has-image to card when img exists", "add .error to form when input invalid", "add .open to dropdown on click".
  3. לכל מקרה — בדקו: האם ה-state נובע מ-HTML שאפשר לבטא? (img exists → :has(img), input invalid → :has(input:invalid), dropdown open → אפשר עם :has(.menu[aria-expanded="true"])).
  4. בחרו את המקרה הכי קל מה-3. הסירו את ה-JavaScript שמטפל בו.
  5. כתבו את ה-CSS עם :has().
  6. בדקו שההתנהגות זהה — אבל עם 0 שורות JS.
  7. מדדו את ה-bundle size לפני ואחרי. אמור להיות קטן ב-kilobytes בודדים.

מה צריך להיות בסוף: רשימת 3 מקרים של JS class-toggle, מקרה אחד שהומר ל-:has(), השוואת bundle size, והבנה כמה JS נוסף אפשר להסיר.

תרגיל 3: Refactor ל-@layer Architecture 30 דקות
  1. פתחו את קובץ ה-CSS של הפרויקט שלכם.
  2. בראש הקובץ, הוסיפו: @layer tokens, base, components, utilities;
  3. עברו על ה-CSS וסווגו כל בלוק לאחת מ-4 השכבות:
    • tokens: :root { --color-*, --space-* } וכל custom properties
    • base: reset, defaults של body/html, סטיילינג גלובלי של a, h1-h6
    • components: .card, .button, .nav — רכיבים
    • utilities: .mt-*, .text-center, .hidden — מחלקות helper
  4. עטפו כל קבוצה ב-@layer X { ... }.
  5. הסירו את כל ה-!important — עכשיו ה-layer order מטפל בלוגיקת ה-override.
  6. בדקו שהאתר עדיין עובד נכון. אם יש דבר שלא נראה — בדקו שה-utility שעובר על component נמצא ב-layer מאוחר יותר.
  7. רעננו. אמור להיראות זהה — אבל הקוד הרבה יותר ניתן לתחזוקה.

מה צריך להיות בסוף: קובץ CSS מחולק ל-4 layers, 0 מופעים של !important, רשימה של 3-5 שיפורי תחזוקה שה-layers מאפשרים.

תרגיל 4: Modern CSS Prompt — בנייה מהאפס עם AI 40 דקות
  1. קחו את ה-Modern CSS Prompt מ-section 6.18. התאימו: בחרו target browsers, בחרו אילו Tier 2 לאשר, החליטו על progressive enhancement.
  2. שלבו עם פרומפטים קודמים: Layout Spec (פרק 5) + Color Palette (פרק 3) + Typography Spec (פרק 4).
  3. הריצו בכלי AI. בקשו "build a product card component with image, title, description, price, and a 'Add to cart' button. The card should adapt to its container: in sidebar (280px) — stacked; in grid (400px) — horizontal; in featured area (800px) — expanded with large image".
  4. קבלו את הקוד. בדקו באופן שיטתי (DevTools):
    • (א) האם יש container-type: inline-size?
    • (ב) האם יש @container ולא @media?
    • (ג) האם יש :has()?
    • (ד) האם צבעים ב-oklch()?
    • (ה) האם יש @layer?
    • (ו) האם nesting native עם &?
  5. אם אחת לא עברה — זהו את החלק בפרומפט שצריך חיזוק, והוסיפו ב-v1.1.
  6. בדקו ב-3 דפדפנים: Chrome, Safari 17+, Firefox. כולם צריכים לעבוד.
  7. אם יש Tier 2-3 — בדקו שה-fallback עובד (פתחו Chrome DevTools → Emulation → Safari 15).

מה צריך להיות בסוף: Component של product card עם 3 התנהגויות (sidebar/grid/featured), 6 תשובות לבדיקת DevTools, Modern CSS Prompt v1.1 אישי שלכם עם התיקונים, ו-screenshots של 3 הדפדפנים.

שגרת עבודה: חידוד ה-CSS המודרני
תדירותמה לעשותכמה זמן
יומי בקריאת קוד של פרויקט חדש (שלכם או בפרויקטים אחרים) — זהו מקום אחד שאפשר להחליף @media ל-@container, או מקום אחד של JS class-toggle שאפשר להחליף ל-:has(). לא חובה לבצע — רק לזהות ולכתוב למטה. 3 דקות
שבועי בנוסף לשגרה מפרק 5 (Layout Audit) — בדקו 1 אתר שאתם אוהבים ב-DevTools. חפשו שימוש ב-CSS מודרני. רשמו 2-3 דפוסים שראיתם. אם ראיתם פיצ'ר שלא מכירים — בדקו ב-caniuse.com. 15 דקות
חודשי עדכנו את Modern CSS Cheat Sheet שלכם: בדקו 5 פיצ'רים ב-Tier 3 וראו אם קודמו ל-Tier 2. עדכנו את התאריך last-verified. קראו את הבלוג של Bramus (bram.us/2024) ל-features חדשים. 25 דקות
אם אתם עושים רק דבר אחד מהפרק הזה

הוסיפו את Modern CSS Prompt (section 6.18) לתחילת כל שיחה עם AI לבניית אתר. זו עבודה של העתקה והדבקה — פחות מדקה — והיא תגרום ל-AI להשתמש ב-Container Queries, :has(), @layer, oklch() ו-Popover API כברירת-מחדל במקום ב-CSS של 2015. ההבדל בתוצאה הוא בין אתר שנראה "AI" לאתר שנראה "בנוי ב-2026 על-ידי מישהו שיודע". אם רק תוסיפו את הפרומפט הזה לכל פרויקט — זכיתם בפרק.

בדקו את עצמכם — 5 שאלות
  1. למה Container Queries לא מחליפות media queries, אלא משלימות אותן? תנו דוגמה לכל אחת. (רמז: רמת הדף vs רמת רכיב; navbar vs card)
  2. מה 3 השימושים הכי מעשיים של :has() בפרויקט אמיתי? מדוע כל אחד מהם יותר טוב מ-JavaScript? (רמז: form validation, card states, empty states — state-from-HTML)
  3. איך @layer פותר specificity wars? למה utilities בשכבה מאוחרת גוברים על component בשכבה מוקדמת — גם אם ה-component עם specificity גבוה יותר? (רמז: layer ordering גובר על specificity)
  4. באיזה Tier תשתמשו ב-Anchor Positioning באפריל 2026, ולמה חובה @supports? מה הסיכון בלי? (רמז: Tier 2, Safari/Firefox בבנייה, tooltips שבורים)
  5. למה oklch() עדיף על HSL לבניית design system עם 5 רמות בהירות? תנו את ההבדל התפיסתי המרכזי. (רמז: perceptually uniform, צהוב ב-L=50 vs סגול ב-L=50)
סיכום הפרק

בפרק הזה עברתם דרך שינוי תפיסה מהותי: CSS של 2024-2026 הוא לא CSS שאתם מכירים. הוא כלי הרבה חזק יותר, שיכול להחליף JavaScript ברוב המקרים שבהם השתמשתם בו עד היום. עברתם על 20 פיצ'רים חדשים, מחולקים ל-4 Tiers של תמיכה — Tier 1 (Stable: Container Queries, :has(), Nesting, @layer, color-mix(), oklch()), Tier 2 (Cutting-edge: Subgrid, @scope, Popover API, Anchor Positioning), Tier 3 (Emerging: Masonry, Mixins, sibling functions, corner-shape).

הבנתם ש-Container Queries הן המהפכה הגדולה — רכיבים שמגיבים לגודל הקונטיינר שלהם, לא ל-viewport. זה פותר את הבעיה הכי ישנה ב-responsive design: רכיב שמופיע ב-sidebar ו-main וצריך להתאים לשניהם. למדתם ש-:has() הוא ה-parent selector שחיכינו לו 20 שנה, ושהוא מאפשר להחליף עשרות שורות JavaScript ב-2-3 שורות CSS — form validation, card states, theme switching, empty states. למדתם ש-@layer פותר specificity wars אחת ולתמיד, ושדפוס 4-השכבות (tokens → base → components → utilities) הוא ה-architecture הסטנדרטי של CSS ב-2026.

קיבלתם כלים מעשיים: 4-Tier Decision Framework לבחירה באיזה פיצ'ר להשתמש, workflow של Can I Use ב-30 שניות לפני כל שימוש בפיצ'ר חדש, Template של @supports Progressive Enhancement שמבטיח שהאתר לא ישבר בדפדפנים ישנים, ו-Modern CSS Prompt ל-AI שמכריח אותו להשתמש בפיצ'רים מודרניים בשם ולא ב-"CSS מודרני" מעורפל.

בפרק הבא נבנה על הבסיס הזה. בפרק הבא נעבור ל-Scroll-Driven Animations — פיצ'ר CSS חדש שמאפשר אנימציות מבוססות גלילה (reveal, parallax, progress indicators) בלי JavaScript. הדפוס של @supports ו-progressive enhancement שלמדתם כאן יהיה קריטי שם — scroll-driven animations עדיין Tier 2-3 במרבית הדפדפנים, ואם לא תבנו אותם עם fallback תשברו את האתר ל-20% מהמשתמשים. פרק 6 הוא השער — בלי Container Queries, :has(), ו-@supports, פרק 7 לא יעבוד לכם. עם הכלים האלה — נהיה מוכנים להיכנס לעולם האנימציות של 2026.

צ'קליסט השלמה — 14 פריטים