W CSS nie było do tej pory możliwości bezpośredniego wybrania elementu nadrzędnego na podstawie jego elementów podrzędnych. Deweloperzy od wielu lat prosili o to. Rozwiązaniem jest selektor :has()
, który jest teraz obsługiwany przez wszystkie główne przeglądarki. Przed :has()
często łańcuchowało się długie selektory lub dodawało klasy do stylizacji. Teraz możesz nadawać styl na podstawie relacji elementu z jego potomkami. Więcej informacji o selektorze :has()
znajdziesz w artykule Opakowanie CSS 2023 i 5 fragmentów kodu CSS, które każdy programista frontendu powinien znać.
Chociaż ten selektor wydaje się niewielki, może umożliwić ogromną liczbę zastosowań.
W tym artykule przedstawiamy kilka zastosowań, które firmy e-commerce mogą wykorzystać dzięki selektorowi :has()
.
:has()
jest częścią punktu odniesienia ponownie dostępnego.
Obejrzyj całą serię, do której należy ten artykuł, i dowiedz się, jak firmy e-commerce ulepszyły swoje strony dzięki nowym funkcjom CSS i interfejsu.
Policybazaar
Dzięki selektorowi
:has()
udało nam się wyeliminować walidację wyboru użytkownika opartą na JavaScriptzie i zastąpić ją rozwiązaniem opartym na arkuszu CSS, które działa bez zarzutu i w taki sam sposób jak wcześniej.—Aman Soni, Tech Lead, Policybazaar
Zespół ds. inwestycji w Policybazaar wykorzystał selektor :has()
, aby zapewnić użytkownikom wyraźne wizualne wskazanie porównywanych planów. Na poniższym obrazie widać 2 typy planów w interfejsie porównywania (żółty i niebieski). Każdy abonament można porównać tylko z własnym typem. Gdy użytkownik wybierze jeden typ planu, nie będzie mógł wybrać innego typu planu.:has()
Kod
:has()
zapewnia dostęp do stylów elementów nadrzędnych i ich elementów podrzędnych. Poniższy kod sprawdza, czy kontener nadrzędny ma ustawioną klasę .disabled-group
.
Jeśli tak się stanie, karta zostanie wyszarzona, a przycisk „Dodaj” nie będzie reagować na kliknięcia. Aby tego uniknąć, ustaw wartość pointer-events
na none
.
.plan-group-container:has(.disabled-group) {
opacity: 0.5;
filter: grayscale(100%);
}
.plan-group-container:has(.disabled-section) .button {
pointer-events: none;
border-color: #B5B5B5;
color: var(--text-primary-38-color);
background: var(--input-border-color);
}
Zespół Health Policybazaar wdrożył nieco inny przypadek użycia. Użytkownik ma quiz wbudowany w treści, a Ty możesz użyć pola wyboru :has()
, aby sprawdzić, czy pytanie zostało już przez niego rozwiązane. Jeśli tak, animacja przeniesie Cię do następnego pytania.
Kod
W przykładzie porównania abonamentów użyto :has()
do sprawdzenia obecności klasy. Za pomocą :has(input:checked)
możesz też sprawdzić stan elementu wejściowego, np. pola wyboru. W wizualizacji pokazującej quiz każde pytanie na fioletowym banerze jest oznaczone polem wyboru. Policybazaar sprawdza, czy pytanie zostało już answered za pomocą :has(input:checked)
. Jeśli tak, uruchamia animację za pomocą animation: quesSlideOut 0.3s 0.3s linear forwards
, aby przejść do następnego pytania. Więcej informacji na ten temat znajdziesz w kodzie poniżej.
.segment_banner__wrap__questions {
position: relative;
animation: quesSlideIn 0.3s linear forwards;
}
.segment_banner__wrap__questions:has(input:checked) {
animation: quesSlideOut 0.3s 0.3s linear forwards;
}
@keyframes quesSlideIn {
from {
transform: translateX(50px);
opacity: 0;
}
to {
transform: translateX(0px);
opacity: 1;
}
}
@keyframes quesSlideOut {
from {
transform: translateX(0px);
opacity: 1;
}
to {
transform: translateX(-50px);
opacity: 0;
}
}
Tokopedia
Tokopedia używa :has()
do tworzenia obrazu nakładki, jeśli miniatura produktu zawiera film. Jeśli miniatura produktu zawiera klasę .playIcon
, dodana jest nakładka CSS. W tym przykładzie selektor :has() jest używany razem z selektorem zagnieżdżonym &
w ramach ogólnej klasy .thumbnailWrapper
, która ma zastosowanie do wszystkich miniatur. Dzięki temu kod CSS jest bardziej modułowy i czytelny.
Kod
Ten kod używa selektorów i kombinatorów arkusza CSS (&
i >
) oraz zagnieżdżania za pomocą :has()
, aby nadać miniaturze odpowiedni styl.
W przypadku nieobsługiwanych przeglądarek jako kreacji zastępczej używana jest standardowa reguła dodatkowych klas CSS. Reguła @supports selector(:has(*))
służy też do sprawdzania obsługi przeglądarek.
Dzięki temu wszystkie wersje przeglądarki działają tak samo.
export const thumbnailWrapper = css`
padding: 0;
margin-right: 7px;
border: none;
outline: none;
background: transparent;
> div {
width: 64px;
height: 64px;
overflow: hidden;
cursor: pointer;
border-color: ;
position: relative;
border: 2px solid ${NN0};
border-radius: 8px;
transition: border-color 0.25s;
&.active {
border-color: ${GN500};
}
@supports selector(:has(*)) {
&:has(.playIcon) {
&::after {
content: '';
display: block;
background: rgba(0, 0, 0, 0.2);
position: absolute;
top: 0;
left: 0;
right: 0;
bottom: 0;
}
}
}
& > .playIcon {
position: absolute;
top: 25%;
left: 25%;
width: 50%;
height: 50%;
text-align: center;
z-index: 1;
}
}
`;
Co należy wziąć pod uwagę podczas korzystania z :has()
Aby utworzyć bardziej złożony warunek, połącz :has()
z innymi elementami selektora. Zapoznaj się z przykładami funkcji has() w selektorze rodziny.
Zasoby:
- CSS Wrapped 2023
- :has(): selektor rodziny
- Demos :has()
- Czy chcesz zgłosić błąd lub poprosić o dodanie nowej funkcji? Chętnie poznamy Twoją opinię.
Przeczytaj inne artykuły z tej serii, aby dowiedzieć się, jak firmy e-commerce korzystały z nowych funkcji CSS i interfejsu, takich jak animacje sterowane przewijaniem, przejścia między widokami, popovery i zapytania kontenerowe.