Theming
SEED Design의 테마 시스템을 이해하고 활용하는 방법을 알아봅니다.
개요
SEED Design은 라이트 모드와 다크 모드를 지원하는 테마 시스템을 제공합니다.
테마는 HTML 요소의 data-seed-color-mode와 data-seed-user-color-scheme 속성을 통해 제어됩니다.
두 속성의 역할과 차이점을 이해하고, 전역 테마 설정 방법과 특정 영역에만 테마를 오버라이딩하는 방법을 알아봅니다.
테마 속성 이해하기
SEED Design의 테마 시스템은 두 가지 data-* 속성을 사용합니다.
data-seed-color-mode
애플리케이션의 테마 정책을 설정하는 속성입니다. 세 가지 값을 가질 수 있습니다.
system: 사용자의 시스템 설정에 따라 자동으로 라이트/다크 모드를 전환합니다.light-only: 항상 라이트 모드로 고정합니다.dark-only: 항상 다크 모드로 고정합니다.
<!-- 시스템 설정 따르기 -->
<html data-seed-color-mode="system" />
<!-- 라이트 모드로 고정 -->
<html data-seed-color-mode="light-only" />
<!-- 다크 모드로 고정 -->
<html data-seed-color-mode="dark-only" />data-seed-user-color-scheme
사용자 기기의 실제 컬러 스킴을 나타내는 속성입니다. 두 가지 값을 가집니다.
light: 사용자의 시스템이 라이트 모드로 설정되어 있음dark: 사용자의 시스템이 다크 모드로 설정되어 있음
이 값은 data-seed-color-mode="system"일 때만 의미를 가지며, prefers-color-scheme 미디어 쿼리를 통해 자동으로 업데이트됩니다.
<!-- 시스템 설정을 따르도록 설정했으며, 현재 사용자는 라이트 모드를 사용 중 -->
<html data-seed-color-mode="system" data-seed-user-color-scheme="light"></html>작동 원리
SEED CSS는 두 속성의 조합을 통해 적절한 색상 토큰을 적용합니다:
/* 라이트 모드가 적용되는 경우 */
:root,
:root[data-seed-color-mode="system"][data-seed-user-color-scheme="light"],
:root[data-seed-color-mode="light-only"],
:root [data-seed-color-mode="light-only"] {
/* 라이트 모드 색상 토큰 */
}
/* 다크 모드가 적용되는 경우 */
:root[data-seed-color-mode="system"][data-seed-user-color-scheme="dark"],
:root[data-seed-color-mode="dark-only"],
:root [data-seed-color-mode="dark-only"] {
/* 다크 모드 색상 토큰 */
}전역 테마 적용하기
애플리케이션 전체에 테마를 적용하는 방법은 Installation 문서를 참고하세요.
번들러 플러그인을 사용하거나, HTML에 직접 속성과 스크립트를 추가하는 방법을 확인할 수 있습니다.
일부 요소에만 테마 오버라이드하기
특정 영역이나 컴포넌트에만 다른 테마를 적용하고 싶을 때는 해당 요소에 data-seed-color-mode에 light-only, dark-only 또는 system 값을 설정합니다.
import { ActionButton } from "seed-design/ui/action-button";
import { actionButtonVariantMap } from "@seed-design/css/recipes/action-button";
import { Text, VStack } from "@seed-design/react";
function Demo() {
return (
<>
{actionButtonVariantMap.variant.map((variant) => (
<ActionButton key={variant} variant={variant}>
{variant}
</ActionButton>
))}
</>
);
}
export default function ThemingColorModeOverride() {
return (
<div className="grid grid-cols-2 size-full">
<VStack
data-seed-color-mode="light-only"
bg="bg.layerDefault"
alignItems="center"
justify="center"
gap="spacingY.componentDefault"
p="x6"
>
<Text color="fg.neutral" textStyle="t4Bold">
라이트 모드
</Text>
<Demo />
</VStack>
<VStack
data-seed-color-mode="dark-only"
bg="bg.layerDefault"
alignItems="center"
justify="center"
gap="spacingY.componentDefault"
p="x6"
>
<Text color="fg.neutral" textStyle="t4Bold">
다크 모드
</Text>
<Demo />
</VStack>
</div>
);
}클라이언트에서 현재 테마 정보 감지하기
컴포넌트에서 현재 테마 설정에 따라 다른 동작을 수행해야 할 때가 있습니다.
이런 경우 data-seed-color-mode와 data-seed-user-color-scheme 속성을 감지하여 사용할 수 있습니다.
다음은 커스텀 훅을 만들어 현재 테마 정보를 감지하는 예제입니다:
"use client";
import { useEffect, useState } from "react";
export type ColorMode = "system" | "light-only" | "dark-only";
export type UserColorScheme = "light" | "dark";
export interface ThemeInfo {
colorMode: ColorMode;
userColorScheme: UserColorScheme;
}
function readThemeInfo(): ThemeInfo {
if (typeof document === "undefined") {
return {
colorMode: "system",
userColorScheme: "light",
};
}
const colorMode = document.documentElement.getAttribute(
"data-seed-color-mode"
) as ColorMode;
const userColorScheme = document.documentElement.getAttribute(
"data-seed-user-color-scheme"
);
return {
colorMode: colorMode || "system",
userColorScheme: userColorScheme === "dark" ? "dark" : "light",
};
}
export function useTheme(): ThemeInfo {
const [themeInfo, setThemeInfo] = useState<ThemeInfo>(readThemeInfo);
useEffect(() => {
if (typeof document === "undefined") {
return;
}
const observer = new MutationObserver(() => {
setThemeInfo(readThemeInfo());
});
observer.observe(document.documentElement, {
attributes: true,
attributeFilter: ["data-seed-color-mode", "data-seed-user-color-scheme"],
});
return () => observer.disconnect();
}, []);
return themeInfo;
}이 훅은 다음과 같이 사용할 수 있습니다:
"use client";
function MyComponent() {
const { colorMode, userColorScheme } = useTheme();
return (
<div>
<p>테마 정책: {colorMode}</p>
<p>현재 컬러 스킴: {userColorScheme}</p>
{userColorScheme === "dark" ? (
<DarkModeSpecificComponent />
) : (
<LightModeSpecificComponent />
)}
</div>
);
}작동 원리
MutationObserver를 사용하여data-seed-color-mode와data-seed-user-color-scheme속성의 변경을 감지합니다.colorMode는 애플리케이션의 테마 정책(system,light-only,dark-only)을 나타냅니다.userColorScheme는 현재 적용된 실제 컬러 스킴(light또는dark)을 나타냅니다.- 시스템 설정이 변경되거나 테마가 전환될 때 자동으로 상태가 업데이트됩니다.
Last updated on