선택기 및 @-규칙 조합

문제

선택기 + 미디어 쿼리, 미디어 쿼리 + 컨테이너 쿼리 등 다양한 유형의 필터링 기준을 결합해야 하는 경우가 많습니다.

예를 들어 (prefers-color-scheme: dark)를 색 구성표 재정의를 타겟팅하는 선택기 (예: :root:has(> head > meta[name="color-scheme"][content="dark"]) 또는 :root.dark)와 결합하여 색 구성표가 설정된 방식과 관계없이 밝은 모드/어두운 모드에서 특정 스타일을 적용할 수 있습니다.

단순한 접근 방식은 코드 중복으로 이어집니다.

/* Light mode styles */
.card.featured {
  font-weight: 400;
}

#logo-dark {
  display: none;
}

@media (prefers-color-scheme: dark) {
  /* Dark mode styles */
  :root:not(.light) {
    .card.featured {
      font-weight: 300;
    }

    #logo-dark {
      display: inline;
    }

    #logo {
      display: none;
    }
  }
}

/* Dark mode styles, again */
:root.dark {
  .card.featured {
    font-weight: 300;
  }

  #logo-dark {
    display: inline;
  }

  #logo {
    display: none;
  }
}

대신 해야 할 일

결합된 필터의 결과를 맞춤 속성에 저장한 다음 컨테이너 스타일 쿼리를 사용하여 해당 속성을 기반으로 규칙을 설정합니다.

중요: 컨테이너 쿼리의 작동 방식 때문에 이 기법은 일치해야 하는 규칙의 상위 요소에 맞춤 속성을 설정할 수 있는 경우에만 작동합니다.

1. 적용된 규칙에서 선택 로직 분리

:root {
  --color-scheme: light;

  @media (prefers-color-scheme: dark) {
    --color-scheme: dark;
  }

  &:has(> head > meta[name="color-scheme"][content="dark"]) {
    --color-scheme: dark;
  }

  &:has(> head > meta[name="color-scheme"][content="light"]) {
    --color-scheme: light;
  }
}

2. 적용된 규칙의 맞춤 속성 키

@container not style(--color-scheme: dark) {
  .card.featured {
    font-weight: 400;
  }

  #logo-dark {
    display: none;
  }
}

@container style(--color-scheme: dark) {
  .card.featured {
    font-weight: 300;
  }

  #logo {
    display: none;
  }
}

3. 선택사항: 공개 상태 전환을 위한 유틸리티 클래스

매우 일반적인 사례는 기준이 일치하는지 여부에 따라 공개 상태를 전환하는 것입니다. 유틸리티 클래스는 임의의 구성요소 스타일 (따라서 !important)보다 우선해야 하며 표시되는 display를 알 수 없으므로 재정의를 사용할 수 없습니다. not style(...)로 제어하세요.

@container not style(--color-scheme: dark) {
  .if-dark {
    display: none !important;
  }
}

@container not style(--color-scheme: light) {
  .if-light {
    display: none !important;
  }
}

대체 값

대체에는 분기의 중요도와 허용 가능한 대체 구성에 따라 두 가지 유형이 있습니다.

  1. 스타일 쿼리가 지원되지 않더라도 모든 상태가 올바르게 작동해야 하는 중요한 분기의 경우 스타일 쿼리를 사용할 수 없습니다. 대신 위의 단순한 접근 방식을 사용하여 각 상태의 규칙을 복제합니다. 유틸리티 클래스도 이와 같이 정의되어 있다면 계속 사용할 수 있습니다.
  2. 기본 상태가 허용되는 중요하지 않은 분기의 경우 @container 규칙 외부에 기본 스타일을 정의하고 스타일 쿼리만 재정의로 사용할 수 있습니다. 이렇게 하면 이 접근 방식의 핵심을 대부분 유지할 수 있지만, 재정의로 인해 값이 결합된다는 주요 단점이 있습니다.
#logo-dark {
  display: none;
}

@container style(--color-scheme: dark) {
  #logo-dark {
    display: inline; /* override */
  }

  #logo {
    display: none;
  }
}