فارسی

انتخابگر :has() در CSS را که تحولی در انتخاب والد است، کاوش کنید. کاربردهای عملی، سازگاری بین مرورگرها و تکنیک‌های پیشرفته برای متحول کردن استایل‌دهی CSS خود را بیاموزید.

تسلط بر انتخابگر :has() در CSS: آزادسازی قدرت انتخاب والد

سال‌ها بود که توسعه‌دهندگان CSS در آرزوی راهی ساده و مؤثر برای انتخاب عناصر والد بر اساس فرزندانشان بودند. انتظار به پایان رسید! شبه‌کلاس (pseudo-class) :has() بالاخره از راه رسید و در حال متحول کردن روش نوشتن CSS ما است. این انتخابگر قدرتمند به شما این امکان را می‌دهد که یک عنصر والد را در صورتی که حاوی یک عنصر فرزند خاص باشد، هدف قرار دهید و دنیایی از امکانات را برای استایل‌دهی پویا و واکنش‌گرا باز می‌کند.

انتخابگر :has() چیست؟

شبه‌کلاس :has() یک شبه‌کلاس رابطه‌ای (relational pseudo-class) در CSS است که لیستی از انتخابگرها را به عنوان آرگومان می‌پذیرد. این انتخابگر، عنصری را انتخاب می‌کند که حداقل یکی از انتخابگرهای موجود در لیست آرگومان، با یکی از نوادگان (descendants) آن عنصر مطابقت داشته باشد. به زبان ساده‌تر، این انتخابگر بررسی می‌کند که آیا یک عنصر والد، فرزند خاصی را دارد یا نه، و اگر داشت، عنصر والد انتخاب می‌شود.

سینتکس پایه آن به این صورت است:

والد:has(فرزند) { /* قوانین CSS */ }

این کد، عنصر والد را تنها در صورتی انتخاب می‌کند که حداقل یک عنصر فرزند در آن وجود داشته باشد.

چرا :has() اینقدر مهم است؟

به طور سنتی، CSS در توانایی خود برای انتخاب عناصر والد بر اساس فرزندانشان محدود بود. این محدودیت اغلب نیازمند راه‌حل‌های پیچیده جاوا اسکریپت یا ترفندهایی برای دستیابی به استایل‌دهی پویا بود. انتخابگر :has() نیاز به این روش‌های دست‌وپاگیر را از بین می‌برد و امکان نوشتن کدهای CSS تمیزتر، قابل نگهداری‌تر و با عملکرد بهتر را فراهم می‌کند.

در اینجا دلایلی که چرا :has() یک تحول بزرگ است، آورده شده است:

مثال‌های پایه از انتخابگر :has()

بیایید با چند مثال ساده شروع کنیم تا قدرت انتخابگر :has() را نشان دهیم.

مثال ۱: استایل‌دهی یک Div والد بر اساس وجود یک تصویر

فرض کنید می‌خواهید به یک عنصر <div> تنها در صورتی که حاوی یک عنصر <img> باشد، یک حاشیه (border) اضافه کنید:

div:has(img) { border: 2px solid blue; }

این قانون CSS یک حاشیه آبی به هر <div> که حداقل یک عنصر <img> داشته باشد، اعمال می‌کند.

مثال ۲: استایل‌دهی یک آیتم لیست بر اساس وجود یک Span

فرض کنید لیستی از آیتم‌ها دارید و می‌خواهید آیتم لیستی را که حاوی یک عنصر <span> با یک کلاس خاص است، برجسته کنید:

li:has(span.highlight) { background-color: yellow; }

این قانون CSS رنگ پس‌زمینه هر <li> که حاوی یک <span> با کلاس "highlight" باشد را به زرد تغییر می‌دهد.

مثال ۳: استایل‌دهی برچسب فرم بر اساس اعتبار ورودی

شما می‌توانید از :has() برای استایل‌دهی برچسب یک فرم بر اساس معتبر یا نامعتبر بودن فیلد ورودی مرتبط با آن (در ترکیب با شبه‌کلاس :invalid) استفاده کنید:

label:has(+ input:invalid) { color: red; font-weight: bold; }

این کد، برچسب را قرمز و ضخیم می‌کند اگر فیلد ورودی که بلافاصله بعد از آن قرار دارد، نامعتبر باشد.

کاربردهای پیشرفته انتخابگر :has()

انتخابگر :has() وقتی با دیگر انتخابگرها و شبه‌کلاس‌های CSS ترکیب شود، حتی قدرتمندتر هم می‌شود. در اینجا چند مورد استفاده پیشرفته آورده شده است:

مثال ۴: هدف قرار دادن عناصر خالی

شما می‌توانید از شبه‌کلاس :not() در کنار :has() برای هدف قرار دادن عناصری که فرزند خاصی را *ندارند* استفاده کنید. برای مثال، برای استایل‌دهی divهایی که تصویر *ندارند*:

div:not(:has(img)) { background-color: #f0f0f0; }

این کد یک پس‌زمینه خاکستری روشن به هر <div> که حاوی عنصر <img> نباشد، اعمال می‌کند.

مثال ۵: ایجاد طرح‌بندی‌های پیچیده

انتخابگر :has() می‌تواند برای ایجاد طرح‌بندی‌های پویا بر اساس محتوای یک کانتینر استفاده شود. برای مثال، شما می‌توانید طرح‌بندی یک گرید (grid) را بر اساس وجود نوع خاصی از عنصر در داخل یک سلول گرید تغییر دهید.

.grid-container { display: grid; grid-template-columns: repeat(3, 1fr); } .grid-item:has(img) { grid-column: span 2; }

این کد باعث می‌شود یک آیتم گرید، در صورتی که حاوی تصویر باشد، دو ستون را اشغال کند.

مثال ۶: استایل‌دهی پویای فرم

شما می‌توانید از :has() برای استایل‌دهی پویای عناصر فرم بر اساس وضعیت آن‌ها (مثلاً اینکه آیا در حالت فوکوس، پر شده یا معتبر هستند) استفاده کنید.

.form-group:has(input:focus) { box-shadow: 0 0 5px rgba(0, 0, 255, 0.5); } .form-group:has(input:valid) { border-color: green; } .form-group:has(input:invalid) { border-color: red; }

این کد یک سایه جعبه‌ای آبی هنگام فوکوس ورودی، یک حاشیه سبز اگر ورودی معتبر باشد، و یک حاشیه قرمز اگر ورودی نامعتبر باشد، اضافه می‌کند.

مثال ۷: استایل‌دهی بر اساس تعداد فرزندان

اگرچه :has() مستقیماً تعداد فرزندان را نمی‌شمارد، اما می‌توانید آن را با دیگر انتخابگرها و ویژگی‌های CSS ترکیب کنید تا به نتایج مشابهی دست یابید. برای مثال، می‌توانید از :only-child برای استایل‌دهی یک والد استفاده کنید اگر فقط یک فرزند از نوع خاصی داشته باشد.

div:has(> p:only-child) { background-color: lightgreen; }

این کد یک <div> را با پس‌زمینه سبز روشن استایل‌دهی می‌کند تنها در صورتی که حاوی یک عنصر <p> به عنوان تنها فرزند مستقیم خود باشد.

سازگاری بین مرورگرها و Fallbackها

تا اواخر سال ۲۰۲۳، انتخابگر :has() از پشتیبانی عالی در مرورگرهای مدرن از جمله کروم، فایرفاکس، سافاری و اج برخوردار است. با این حال، بررسی سازگاری در وب‌سایت Can I use قبل از استفاده در محیط پروداکشن، به ویژه اگر نیاز به پشتیبانی از مرورگرهای قدیمی‌تر دارید، بسیار مهم است.

در اینجا خلاصه‌ای از ملاحظات سازگاری آورده شده است:

فراهم کردن Fallbackها

اگر نیاز به پشتیبانی از مرورگرهای قدیمی‌تر دارید، باید fallback (راه حل جایگزین) فراهم کنید. در اینجا چند استراتژی وجود دارد:

در اینجا مثالی از استفاده از feature query آورده شده است:

.parent { /* استایل‌دهی پایه برای همه مرورگرها */ border: 1px solid black; } @supports selector(:has(img)) { .parent:has(img) { /* استایل‌دهی بهبودیافته برای مرورگرهایی که از :has() پشتیبانی می‌کنند */ border: 3px solid blue; } }

این کد یک حاشیه سیاه به عنصر .parent در همه مرورگرها اعمال می‌کند. در مرورگرهایی که از :has() پشتیبانی می‌کنند، اگر عنصر .parent حاوی یک تصویر باشد، یک حاشیه آبی اعمال خواهد کرد.

ملاحظات عملکرد

در حالی که :has() مزایای قابل توجهی ارائه می‌دهد، توجه به تأثیر بالقوه آن بر عملکرد، به ویژه هنگام استفاده گسترده یا با انتخابگرهای پیچیده، ضروری است. مرورگرها باید انتخابگر را برای هر عنصر در صفحه ارزیابی کنند، که می‌تواند از نظر محاسباتی پرهزینه باشد.

در اینجا چند نکته برای بهینه‌سازی عملکرد :has() آورده شده است:

اشتباهات رایج برای اجتناب

هنگام کار با انتخابگر :has()، به راحتی می‌توان اشتباهاتی مرتکب شد که منجر به نتایج غیرمنتظره می‌شود. در اینجا برخی از اشتباهات رایج برای اجتناب آورده شده است:

بهترین شیوه‌ها برای استفاده از :has()

برای به حداکثر رساندن مزایای انتخابگر :has() و جلوگیری از مشکلات احتمالی، این بهترین شیوه‌ها را دنبال کنید:

مثال‌های دنیای واقعی و موارد استفاده

بیایید چند مثال از دنیای واقعی را بررسی کنیم که چگونه انتخابگر :has() می‌تواند برای حل چالش‌های طراحی رایج استفاده شود.

مثال ۸: ایجاد منوهای ناوبری واکنش‌گرا

شما می‌توانید از :has() برای ایجاد منوهای ناوبری واکنش‌گرا استفاده کنید که بر اساس وجود آیتم‌های منوی خاص، با اندازه‌های مختلف صفحه سازگار می‌شوند.

سناریویی را تصور کنید که می‌خواهید بسته به اینکه کاربر وارد شده است یا نه، یک منوی ناوبری متفاوت نمایش دهید. اگر وارد شده باشند، ممکن است گزینه‌های پروفایل و خروج را نشان دهید، در غیر این صورت ممکن است ورود/ثبت‌نام را نشان دهید.

nav:has(.user-profile) { /* استایل‌ها برای کاربران وارد شده */ } nav:not(:has(.user-profile)) { /* استایل‌ها برای کاربران خارج شده */ }

مثال ۹: استایل‌دهی کامپوننت‌های کارت

انتخابگر :has() می‌تواند برای استایل‌دهی کامپوننت‌های کارت بر اساس محتوای آنها استفاده شود. برای مثال، شما می‌توانید تنها در صورتی که یک کارت حاوی تصویر باشد، به آن سایه اضافه کنید.

.card:has(img) { box-shadow: 0 4px 8px rgba(0, 0, 0, 0.2); }

مثال ۱۰: پیاده‌سازی تم‌های پویا

شما می‌توانید از :has() برای پیاده‌سازی تم‌های پویا بر اساس ترجیحات کاربر یا تنظیمات سیستم استفاده کنید. برای مثال، می‌توانید رنگ پس‌زمینه صفحه را بر اساس اینکه کاربر حالت تاریک (dark mode) را فعال کرده است یا نه، تغییر دهید.

body:has(.dark-mode) { background-color: #333; color: #fff; }

این مثال‌ها تطبیق‌پذیری انتخابگر :has() و توانایی آن در حل طیف گسترده‌ای از چالش‌های طراحی را نشان می‌دهند.

آینده CSS: قدم بعدی چیست؟

معرفی انتخابگر :has() یک گام مهم رو به جلو در تکامل CSS است. این انتخابگر به توسعه‌دهندگان قدرت می‌دهد تا شیوه‌نامه‌های (stylesheets) پویاتر، واکنش‌گراتر و قابل نگهداری‌تری با وابستگی کمتر به جاوا اسکریپت ایجاد کنند. با ادامه رشد پشتیبانی مرورگرها از :has()، می‌توانیم انتظار داشته باشیم که استفاده‌های نوآورانه‌تر و خلاقانه‌تری از این انتخابگر قدرتمند ببینیم.

با نگاه به آینده، کارگروه CSS در حال بررسی سایر ویژگی‌ها و بهبودهای هیجان‌انگیزی است که قابلیت‌های CSS را بیش از پیش گسترش خواهند داد. این موارد عبارتند از:

با به‌روز ماندن با آخرین تحولات CSS و استقبال از ویژگی‌های جدیدی مانند :has()، توسعه‌دهندگان می‌توانند پتانسیل کامل CSS را آزاد کرده و تجربیات وب واقعاً استثنایی ایجاد کنند.

نتیجه‌گیری

انتخابگر :has() یک افزودنی قدرتمند به جعبه ابزار CSS است که امکان انتخاب والد را فراهم کرده و امکانات جدیدی برای استایل‌دهی پویا و واکنش‌گرا باز می‌کند. در حالی که در نظر گرفتن سازگاری مرورگر و پیامدهای عملکردی آن بسیار مهم است، مزایای استفاده از :has() برای داشتن کدهای CSS تمیزتر، قابل نگهداری‌تر و با عملکرد بهتر، غیرقابل انکار است. این انتخابگر متحول‌کننده را بپذیرید و استایل‌دهی CSS خود را امروز متحول کنید!

به یاد داشته باشید که دسترسی‌پذیری را در نظر بگیرید و مکانیزم‌های جایگزین برای مرورگرهای قدیمی‌تر فراهم کنید. با پیروی از بهترین شیوه‌های ذکر شده در این راهنما، می‌توانید از پتانسیل کامل انتخابگر :has() بهره‌مند شوید و تجربیات وب واقعاً استثنایی برای کاربران در سراسر جهان ایجاد کنید.