๐Ÿงฑ ๋‹คํฌ ๋ชจ๋“œ์—์„œ ๊ธ€์ž๊ฐ€ ๋ฐฐ๊ฒฝ์— ๋ฌปํžŒ๋‹ค: ์˜ˆ์™ธ ์„ ํƒ์ž 19๊ฐœ์™€ ์ธ๋ผ์ธ ์Šคํƒ€์ผ 38๊ฐœ๊ฐ€ ์‚ฌ๋ผ์ง„ ํ† ํฐ ์ •๋ฆฌ๊ธฐ

@leekh8 ยท September 22, 2026 ยท 10 min read

์‚ฌ์ด๋“œ ํ”„๋กœ์ ํŠธ ๋„ค ๊ณณ์˜ ํ™”๋ฉด์„ ํ•˜๋ฃจ์— ์†๋ดค๋‹ค. ์ถœ๋ฐœ์ ์€ "๋””์ž์ธ์ด ์ดŒ์Šค๋Ÿฝ๋‹ค"์˜€๋Š”๋ฐ, ์ฝ”๋“œ๋ฅผ ์—ด์ž ์ดŒ์Šค๋Ÿฌ์›€์€ ๊ฒฐ๊ณผ์˜€๊ณ  ์›์ธ์€ ๋”ฐ๋กœ ์žˆ์—ˆ๋‹ค.

๋„ค ๊ณณ์ด ์ „๋ถ€ ๊ฐ™์€ ๋ณ‘์ด์—ˆ๋‹ค. ์ƒ‰๊ณผ ํฌ๊ธฐ๋ฅผ ๊ฐ’์œผ๋กœ ์ง์ ‘ ์“ฐ๋‹ค ๋ณด๋‹ˆ, ํ…Œ๋งˆ๋‚˜ ํ™”๋ฉด ํฌ๊ธฐ๊ฐ€ ๋ฐ”๋€” ๋•Œ๋งˆ๋‹ค ์˜ˆ์™ธ ๊ทœ์น™์„ ๋ง๋ถ™์ด๋Š” ๊ตฌ์กฐ. ์ฆ์ƒ๋งŒ ํ”„๋กœ์ ํŠธ๋งˆ๋‹ค ๋‹ค๋ฅด๊ฒŒ ๋‚˜ํƒ€๋‚ฌ๋‹ค.

ํ”„๋กœ์ ํŠธ ๊ฒ‰์œผ๋กœ ๋“œ๋Ÿฌ๋‚œ ์ฆ์ƒ ์‹ค์ œ ์›์ธ ์ •๋ฆฌ ํ›„
SEO ์ ์ˆ˜ ์—๋””ํ„ฐ ์ธ๋ผ์ธ style={{ }} 38๊ฐœ ์ ์ˆ˜์— ๋”ฐ๋ผ ์ƒ‰์ด ๋ฐ”๋€Œ๋Š” ๋™์  ์Šคํƒ€์ผ 0๊ฐœ
ํฌ๋ชจ๋„๋กœ ํƒ€์ด๋จธ ๋‹คํฌ ๋ชจ๋“œ์—์„œ ๊ธ€์ž๊ฐ€ ๋ฌปํž˜ ๋‹คํฌ ํ† ํฐ์ด 2๊ฐœ๋ฟ ๋ณด์ • ์„ ํƒ์ž 19 โ†’ 0
์ด ๋ธ”๋กœ๊ทธ font-size์— ์†Œ์ˆ˜์  px html์ด 14px๋กœ ๊ณ ์ •๋ผ rem์ด ์–ด๊ธ‹๋‚จ ๊ณ ์œ ๊ฐ’ 34์ข… โ†’ 9๋‹จ๊ณ„
์‚ฌ์ดํŠธ๋งต ์ƒ์„ฑ๊ธฐ ๋ชจ๋ฐ”์ผ์—์„œ ๋ ˆ์ด์•„์›ƒ ๋ถ•๊ดด @media ์ฟผ๋ฆฌ 0๊ฐœ, ํŽ˜์ด์ง€๋งˆ๋‹ค <head> ์ค‘๋ณต breakpoint 0 โ†’ 4

๋„ค ์ฆ์ƒ์„ ํ•˜๋‚˜์”ฉ ๋”ฐ๋ผ๊ฐ€๋ฉด ๊ฐ™์€ ์ž๋ฆฌ์— ๋„์ฐฉํ•œ๋‹ค.

๋‹คํฌ ๋ชจ๋“œ์—์„œ ๊ธ€์ž๊ฐ€ ๋ฐฐ๊ฒฝ์— ๋ฌปํžŒ๋‹ค

๊ฐ€์žฅ ์•Œ์•„๋ณด๊ธฐ ์‰ฌ์šด ์ฆ์ƒ๋ถ€ํ„ฐ ๋ณธ๋‹ค. ๋‹คํฌ ๋ชจ๋“œ๋ฅผ ์ผฐ๋Š”๋ฐ ์ผ๋ถ€ ๊ธ€์ž๊ฐ€ ์–ด๋‘์šด ๋ฐฐ๊ฒฝ์— ์–ด๋‘์šด ์ƒ‰์œผ๋กœ ๋‚จ์•„ ์•ˆ ๋ณด์ธ๋‹ค.

์›์ธ์€ ์ฝ”๋“œ ์ฃผ์„์— ์ด๋ฏธ ์ ํ˜€ ์žˆ์—ˆ๋‹ค.

/* ๋‹คํฌ ๋ชจ๋“œ ๋Œ€๋น„ ๋ณด์ • - text-color(#333) ๋ณ€์ˆ˜๊ฐ€ ๋‹คํฌ์—์„œ ์•ˆ ๋ฐ”๋€Œ์–ด
   ์–ด๋‘์šด ๋ฐฐ๊ฒฝ์— ์–ด๋‘์šด ๊ธ€์”จ๋กœ ๋ฌปํžˆ๋˜ ์š”์†Œ๋“ค */
.App.dark-mode .task-buttons button {
  color: var(--dark-text-color);
  border-color: #444;
}

์ฃผ์„์€ ์ •ํ™•ํ•˜๋‹ค. ๊ทธ๋Ÿฐ๋ฐ ์ฒ˜๋ฐฉ์ด ๋ฐ˜๋Œ€ ๋ฐฉํ–ฅ์ด์—ˆ๋‹ค. ํ† ํฐ ์ •์˜๋ฅผ ๋ณด๋ฉด ์•ˆ๋‹ค.

:root {
  --text-color: #333333;
  --background-color: #ffffff;
  --border-color: #dddddd;
  --shadow-color: rgba(0, 0, 0, 0.1);
  --dark-background-color: #121212;   /* ๋‹คํฌ ์ „์šฉ์€ ์ด ๋‘˜๋ฟ */
  --dark-text-color: #ffffff;
}

body.dark-mode {
  background-color: var(--dark-background-color);
  color: var(--dark-text-color);
}

๋ผ์ดํŠธ์—๋Š” ํ† ํฐ์ด ์—ฌ๋Ÿฌ ๊ฐœ์ธ๋ฐ ๋‹คํฌ์—๋Š” ๋ฐฐ๊ฒฝ๊ณผ ๊ธ€์ž ๋‘˜๋ฟ์ด๋‹ค. ํ…Œ๋‘๋ฆฌ, ๊ทธ๋ฆผ์ž, ์นด๋“œ ํ‘œ๋ฉด, ์ž…๋ ฅ ํ•„๋“œ์— ํ•ด๋‹นํ•˜๋Š” ๋‹คํฌ ๊ฐ’์ด ์—†๋‹ค. ๊ทธ๋Ÿฌ๋‹ˆ ๊ทธ ์ƒ‰์ด ํ•„์š”ํ•œ ์ž๋ฆฌ๋งˆ๋‹ค ์„ ํƒ์ž๋ฅผ ํ•˜๋‚˜์”ฉ ๋งŒ๋“ค์–ด ๋ฎ๋Š” ์ˆ˜๋ฐ–์— ์—†๋‹ค.

๊ทธ๋ ‡๊ฒŒ ๋Š˜์–ด๋‚œ ๊ฒƒ์ด .App.dark-mode ๋ณด์ • ์„ ํƒ์ž 19๊ฐœ์˜€๋‹ค.

.App.dark-mode .timer-container,
.App.dark-mode .task-list,
.App.dark-mode .modal-content,
.App.dark-mode .task-item {
  background-color: #1e1e1e;      /* ์ด๋ฆ„ ์—†๋Š” ๋‹คํฌ ํ‘œ๋ฉด์ƒ‰ */
  color: var(--dark-text-color);
}

.App.dark-mode .task-text,
.App.dark-mode .task-input,
.App.dark-mode .task-input-edit {
  color: var(--dark-text-color);
  background-color: #2a2a2a;      /* ์ด๋ฆ„ ์—†๋Š” ๋‹คํฌ ์ž…๋ ฅ ๋ฐฐ๊ฒฝ */
  border-color: #444;             /* ์ด๋ฆ„ ์—†๋Š” ๋‹คํฌ ํ…Œ๋‘๋ฆฌ */
}

์—ฌ๊ธฐ์„œ ํ•œ ๊ฐ€์ง€๊ฐ€ ๋ณด์ธ๋‹ค. ์˜ˆ์™ธ ์„ ํƒ์ž ์•ˆ์— ์ด๋ฏธ ํ† ํฐ ๊ฐ’์ด ๋“ค์–ด ์žˆ์—ˆ๋‹ค. ์ด๋ฆ„๋งŒ ์—†์—ˆ์„ ๋ฟ์ด๋‹ค. #1e1e1e๋Š” ์นด๋“œ ํ‘œ๋ฉด, #2a2a2a๋Š” ์ž…๋ ฅ ๋ฐฐ๊ฒฝ, #444๋Š” ํ…Œ๋‘๋ฆฌ๋‹ค. ์…‹ ๋‹ค ์—ฌ๋Ÿฌ ์„ ํƒ์ž์— ๋ฐ˜๋ณตํ•ด์„œ ๋‚˜์˜จ๋‹ค.

์ด๋ฆ„์„ ๋ถ™์ด๋ฉด ์˜ˆ์™ธ๊ฐ€ ์‚ฌ๋ผ์ง„๋‹ค.

:root {
  --background-color: #ffffff;   /* ํŽ˜์ด์ง€ ๋ฐ”๋‹ฅ */
  --surface-color: #ffffff;      /* ์นด๋“œ, ํŒจ๋„, ๋ชจ๋‹ฌ */
  --input-background: #ffffff;   /* ์ž…๋ ฅ ํ•„๋“œ */
  --text-color: #333333;
  --border-color: #dddddd;
  --hover-overlay: rgba(0, 0, 0, 0.05);
}

body.dark-mode {
  --background-color: #121212;
  --surface-color: #1e1e1e;
  --input-background: #2a2a2a;
  --text-color: #ffffff;
  --border-color: #444444;
  --hover-overlay: rgba(255, 255, 255, 0.08);
}

ํ•ต์‹ฌ์€ ๋‹คํฌ๊ฐ€ ๋ณ„๋„ ํ† ํฐ ์ด๋ฆ„์„ ๊ฐ–์ง€ ์•Š๋Š”๋‹ค๋Š” ๊ฒƒ์ด๋‹ค. ๊ฐ™์€ ์ด๋ฆ„ ํ•œ ๋ฒŒ์„ ๋‘๊ณ  body.dark-mode ์•ˆ์—์„œ ๊ฐ’๋งŒ ๋‹ค์‹œ ์ •์˜ํ•œ๋‹ค. CSS ์‚ฌ์šฉ์ž ์ •์˜ ์†์„ฑ์€ ์ƒ์†๋˜๋ฏ€๋กœ, --text-color๋ฅผ ์“ฐ๋Š” ๋ชจ๋“  ํ›„์† ์š”์†Œ๊ฐ€ ์ž๋™์œผ๋กœ ๋”ฐ๋ผ์˜จ๋‹ค.mdn-custom-props

ํ† ํฐ์„ ๋ผ์ดํŠธ 19๊ฐœ, ๋‹คํฌ ์žฌ์ •์˜ 9๊ฐœ๋กœ ๋Š˜๋ฆฌ๋‹ˆ ๋ณด์ • ์„ ํƒ์ž๊ฐ€ ์ „๋ถ€ ์‚ฌ๋ผ์กŒ๋‹ค. ํŒŒ์ผ์€ 945์ค„์—์„œ 902์ค„์ด ๋๋‹ค.

์žˆ๋‹ค
์—†๋‹ค
๋Š๋Š” ๋ฐฉ๋ฒ•
์ƒˆ ์ƒ‰์ด ํ•„์š”ํ•˜๋‹ค
๊ทธ ์—ญํ• ์˜ ํ† ํฐ์ด ์žˆ๋Š”๊ฐ€
์—ญํ•  ํ† ํฐ์„ ์“ด๋‹ค. ๋‹คํฌ๋Š” ์ €์ ˆ๋กœ ๋”ฐ๋ผ์˜จ๋‹ค
์˜ˆ์™ธ ์„ ํƒ์ž๋ฅผ ํ•˜๋‚˜ ๋” ๋งŒ๋“ ๋‹ค
๊ฐ™์€ ์ƒํ™ฉ์ด ๋˜ ์˜จ๋‹ค
๊ฐ’์ด ์•„๋‹ˆ๋ผ ์—ญํ• ์— ์ด๋ฆ„์„ ๋ถ™์ธ๋‹ค

์ธ๋ผ์ธ ์Šคํƒ€์ผ 38๊ฐœ๋Š” ๊ฒŒ์œผ๋ฆ„์ด ์•„๋‹ˆ์—ˆ๋‹ค

SEO ์ ์ˆ˜ ์—๋””ํ„ฐ์—๋Š” ์ธ๋ผ์ธ style={{ }}์ด 38๊ฐœ ์žˆ์—ˆ๋‹ค(๋ถ„์„ ํŒจ๋„ 32๊ฐœ, ์—๋””ํ„ฐ 6๊ฐœ). ์ฒ˜์Œ์—” ๊ธ‰ํ•˜๊ฒŒ ์งœ๋‹ค ๋งŒ ํ”์ ์œผ๋กœ ๋ณด์˜€๋‹ค.

์‹ค์ œ ์ด์œ ๋Š” ๋‹ฌ๋ž๋‹ค. ์ ์ˆ˜์— ๋”ฐ๋ผ ์ƒ‰์ด ๋ฐ”๋€Œ์–ด์•ผ ํ–ˆ๊ณ , ์ƒ‰์„ ๊ฐ’์œผ๋กœ๋งŒ ํ‘œํ˜„ํ•  ์ค„ ์•Œ์•˜๊ธฐ ๋•Œ๋ฌธ์ด๋‹ค.

// ํ•จ์ˆ˜๊ฐ€ ์ƒ‰๊ฐ’์„ ๋ฐ˜ํ™˜ํ•œ๋‹ค. ๊ทธ๋Ÿฌ๋‹ˆ ์ด ๊ฐ’์„ ๋ฐ›์„ ๊ณณ์€ ์ธ๋ผ์ธ๋ฐ–์— ์—†๋‹ค.
const getScoreColor = (score) => {
  if (score >= 80) return "#22c55e";
  if (score >= 60) return "#eab308";
  if (score >= 40) return "#f97316";
  return "#ef4444";
};

const color = getScoreColor(score);
<span style={{ color, fontWeight: "bold" }}>{check.passed ? "โœ“" : "โœ—"}</span>

์ƒ‰๊ฐ’์ด ์ปดํฌ๋„ŒํŠธ ์•ˆ์— ์žˆ์œผ๋‹ˆ CSS ํŒŒ์ผ๋กœ ์˜ฎ๊ธธ ๋ฐฉ๋ฒ•์ด ์—†๋‹ค. ๊ทธ๋ž˜์„œ ์ธ๋ผ์ธ์ด ๋‚จ๋Š”๋‹ค. ๊ทธ๋ฆฌ๊ณ  ์ธ๋ผ์ธ์ด ํ•˜๋‚˜ ํ—ˆ์šฉ๋˜๋ฉด ๊ทธ ์˜†์˜ ์ •์  ์Šคํƒ€์ผ๊นŒ์ง€ ๊ฐ™์ด ์ธ๋ผ์ธ์œผ๋กœ ์ ํžˆ๊ธฐ ์‹œ์ž‘ํ•œ๋‹ค. 38๊ฐœ ์ค‘ ์ƒ๋‹น์ˆ˜๋Š” textAlign, marginBottom ๊ฐ™์€ ๊ณ ์ •๊ฐ’์ด์—ˆ๋‹ค.

๊ณ ์นœ ๋ฐฉ๋ฒ•์€ ํ•จ์ˆ˜์˜ ๋ฐ˜ํ™˜๊ฐ’์„ ์ƒ‰์ด ์•„๋‹ˆ๋ผ ํ† ํฐ ์ด๋ฆ„์œผ๋กœ ๋ฐ”๊พธ๋Š” ๊ฒƒ์ด๋‹ค.

/** ์ ์ˆ˜๋ฅผ semantic ํ† ํฐ ์ด๋ฆ„์œผ๋กœ ์˜ฎ๊ธด๋‹ค. ์ƒ‰๊ฐ’์„ ์ปดํฌ๋„ŒํŠธ์— ๋‘์ง€ ์•Š๊ธฐ ์œ„ํ•จ. */
const scoreTone = (score) => {
  if (score >= 80) return "good";
  if (score >= 60) return "fair";
  if (score >= 40) return "warn";
  return "poor";
};

๋ฐ˜ํ™˜ ํƒ€์ž…์ด "#22c55e"์—์„œ "good"์œผ๋กœ ๋ฐ”๋€ ๊ฒƒ๋ฟ์ธ๋ฐ, ์ƒ‰๊ฐ’์ด ์ปดํฌ๋„ŒํŠธ์—์„œ ์™„์ „ํžˆ ๋น ์ง„๋‹ค. ๋ฐ›๋Š” ์ชฝ์€ styled-components์˜ props ํ•จ์ˆ˜๋กœ ํ† ํฐ ์ด๋ฆ„์„ ์กฐ๋ฆฝํ•œ๋‹ค.

const Stripe = styled.div`
  height: 3px;
  background: var(--${(p) => p.$tone});
`;

<Stripe $tone={scoreTone(score)} aria-hidden="true" />

SVG์ฒ˜๋Ÿผ styled๋กœ ๊ฐ์‹ธ๊ธฐ ์• ๋งคํ•œ ๊ณณ๋„ ๊ฐ™์€ ๋ฌธ์ž์—ด์„ ๊ทธ๋Œ€๋กœ ์“ด๋‹ค.

<circle stroke={`var(--${tone})`} ... />

ํ† ํฐ ์ •์˜๋Š” ํ•œ ๊ณณ์—๋งŒ ๋‘”๋‹ค. ์‹œ์Šคํ…œ ํ…Œ๋งˆ๋ฅผ ๋”ฐ๋ฅด๋Š” ๋‹คํฌ ๋Œ€์‘๋„ ์—ฌ๊ธฐ์„œ ๋๋‚œ๋‹ค.mdn-prefers

:root {
  --good: #15794a;  --fair: #8a6300;  --warn: #b8510c;  --poor: #b52a30;
}
@media (prefers-color-scheme: dark) {
  :root {
    --good: #4ec98a;  --fair: #dcb04a;  --warn: #f0894a;  --poor: #f27279;
  }
}

$tone์ฒ˜๋Ÿผ ๋‹ฌ๋Ÿฌ ๊ธฐํ˜ธ๋กœ ์‹œ์ž‘ํ•˜๋Š” prop์€ styled-components v5.1 ์ด์ƒ์—์„œ transient prop์œผ๋กœ ์ทจ๊ธ‰๋ผ ์‹ค์ œ DOM ์š”์†Œ๋กœ ์ „๋‹ฌ๋˜์ง€ ์•Š๋Š”๋‹ค.sc-transient ์ด๊ฑธ ๋นผ๋จน์œผ๋ฉด <div tone="good">์ด ๊ทธ๋Œ€๋กœ ๋ Œ๋”๋ผ React๊ฐ€ ์•Œ ์ˆ˜ ์—†๋Š” ์†์„ฑ ๊ฒฝ๊ณ ๋ฅผ ๋‚ธ๋‹ค.

๋ค์œผ๋กœ ์–ป์€ ๊ฒƒ์ด ํ•˜๋‚˜ ์žˆ๋‹ค. ์ƒ‰์ด ํ† ํฐ ์ด๋ฆ„์œผ๋กœ ์ •๋ฆฌ๋˜์ž, ๊ฒŒ์ด์ง€๋ฅผ ๋ณด์ง€ ์•Š์•„๋„ ์ƒํƒœ๊ฐ€ ์ฝํžˆ๋„๋ก ๋ถ„์„ ํŒจ๋„ ๋จธ๋ฆฌ์— ์ƒํƒœ ๋ ๋ฅผ ๋‘๋ฅด๋Š” ์ผ์ด ์„ธ ์ค„๋กœ ๋๋‚ฌ๋‹ค. ๊ฐ’์œผ๋กœ ํฉ์–ด์ ธ ์žˆ์„ ๋•Œ๋Š” ์†๋Œ€๊ธฐ ์–ด๋ ค์› ๋˜ ๋ณ€๊ฒฝ์ด๋‹ค.

์†Œ์ˆ˜์  px์˜ ์ •์ฒด๋Š” ๋‚˜๋ˆ—์…ˆ ๊ฒฐ๊ณผ์˜€๋‹ค

์ด ๋ธ”๋กœ๊ทธ๋Š” ์ฆ์ƒ์ด ๋” ์ด์ƒํ–ˆ๋‹ค. font-size๊ฐ€ 34์ข…์ด์—ˆ๋Š”๋ฐ ๊ทธ์ค‘์— 14.4px, 15.5px, 17.6px, 44.8px ๊ฐ™์€ ๊ฐ’์ด ์„ž์—ฌ ์žˆ์—ˆ๋‹ค.

์ „์—ญ ์Šคํƒ€์ผ์— ์›์ธ์ด ์žˆ์—ˆ๋‹ค.

html {
  font-size: 14px;
}

rem์€ ๋ฃจํŠธ ์š”์†Œ์˜ ํฐํŠธ ํฌ๊ธฐ๋ฅผ ๊ธฐ์ค€์œผ๋กœ ํ•˜๋Š” ์ƒ๋Œ€ ๋‹จ์œ„๋‹ค.mdn-rem ๋ธŒ๋ผ์šฐ์ € ๊ธฐ๋ณธ๊ฐ’์€ 16px์ธ๋ฐ ์—ฌ๊ธฐ์„œ 14px๋กœ ๊ณ ์ •ํ•ด ๋ฒ„๋ ธ๋‹ค. ๊ทธ๋Ÿฌ๋ฉด 0.9rem์€ 14.4px์ด ์•„๋‹ˆ๋ผ 12.6px์ด ๋œ๋‹ค. 16px ๊ธฐ์ค€์œผ๋กœ ๊ณ„์‚ฐํ•ด ๋‘” ๋””์ž์ธ ๊ฐ’์ด ์ „๋ถ€ ์–ด๊ธ‹๋‚œ๋‹ค.

๊ทธ๋ž˜์„œ rem์„ ํฌ๊ธฐํ•˜๊ณ  px์„ ์ง์ ‘ ์ ๋Š” ์ชฝ์œผ๋กœ ํ˜๋ €๊ณ , ๊ทธ๋•Œ ์ ํžŒ ๊ฐ’์ด 16 ร— 0.9 = 14.4, 16 ร— 2.8 = 44.8 ๊ฐ™์€ ๊ณ„์‚ฐ ๊ฒฐ๊ณผ์˜€๋‹ค. ์†Œ์ˆ˜์  px์€ ์‹ค์ˆ˜๊ฐ€ ์•„๋‹ˆ๋ผ ์šฐํšŒ์˜ ํ”์ ์ด๋‹ค.

๋” ํฐ ๋ฌธ์ œ๋Š” ๊ทธ ๊ฒฐ๊ณผ๋กœ ์ƒ๊ธด ์œ„๊ณ„ ๋ถ•๊ดด์˜€๋‹ค.

์ •๋ฆฌ ์ „ ์ •๋ฆฌ ํ›„
h2 22px --fs-2xl
h3 16.5px --fs-lg
h4 16px --fs-md (bold)
๋ณธ๋ฌธ 15.5px --fs-md

h3, h4, ๋ณธ๋ฌธ์ด ์‚ฌ์‹ค์ƒ ๊ฐ™์€ ํฌ๊ธฐ๋‹ค. ๊ตต๊ธฐ๋งŒ ๋‹ค๋ฅผ ๋ฟ ํฌ๊ธฐ๋กœ๋Š” ๊ตฌ๋ถ„๋˜์ง€ ์•Š๋Š”๋‹ค. ๊ธ€ ์•ˆ์—์„œ ๊ณ„์ธต์ด ๋ณด์ด์ง€ ์•Š๋Š” ์ด์œ ๊ฐ€ ์—ฌ๊ธฐ ์žˆ์—ˆ๋‹ค.

9๋‹จ๊ณ„ ํƒ€์ž… ์Šค์ผ€์ผ์„ ์ •์˜ํ•˜๊ณ  27๊ฐœ ํŒŒ์ผ 74๊ณณ์„ ์น˜ํ™˜ํ–ˆ๋‹ค. ์ปดํฌ๋„ŒํŠธ์—๋Š” var(--fs-*)๋งŒ ๋‚จ๊ธฐ๊ณ  px์„ ์ง์ ‘ ์ ์ง€ ์•Š๋Š” ๊ทœ์น™์„ ์ฃผ์„์œผ๋กœ ๋ฐ•์•„ ๋’€๋‹ค.

<title>Document</title>๊ฐ€ ๋ฐฐํฌ๋ผ ์žˆ์—ˆ๋‹ค

์‚ฌ์ดํŠธ๋งต ์ƒ์„ฑ๊ธฐ๋Š” @media ์ฟผ๋ฆฌ๊ฐ€ ํ•˜๋‚˜๋„ ์—†์–ด ๋ชจ๋ฐ”์ผ์—์„œ 800px ๊ณ ์ •ํญ์ด ๊ทธ๋Œ€๋กœ ๋‚˜์™”๋‹ค. ํŒŒ๋ž‘๋„ ๋„ค ์ข…๋ฅ˜๊ฐ€ ๋Œ์•„๋‹ค๋…”๋‹ค(#0077b6, #007bff, #0056b3, #0d6efd. Bootstrap ๊ธฐ๋ณธ๊ฐ’๊ณผ ์ง์ ‘ ๊ณ ๋ฅธ ๊ฐ’์ด ๋’ค์„ž์ธ ๊ฒฐ๊ณผ๋‹ค).

๊ทผ๋ณธ ์›์ธ์€ ์ƒ‰์ด ์•„๋‹ˆ๋ผ ๊ตฌ์กฐ์˜€๋‹ค. 5๊ฐœ EJS ํŽ˜์ด์ง€๊ฐ€ ๊ฐ์ž <head>๋ฅผ ๊ด€๋ฆฌํ•˜๊ณ  ์žˆ์—ˆ๋‹ค. ํฐํŠธ ๋งํฌ๋Š” 5๊ฐœ ์ค‘ 1๊ฐœ์—๋งŒ ์žˆ์—ˆ๊ณ , ์ƒˆ ํŽ˜์ด์ง€๋ฅผ ๋งŒ๋“ค ๋•Œ๋งˆ๋‹ค ์•ž ํŽ˜์ด์ง€๋ฅผ ๋ณต์‚ฌํ•ด ์˜ค๋‹ค ๋ณด๋‹ˆ ๋น ์ง„ ๊ฒƒ์„ ์•„๋ฌด๋„ ๋ชฐ๋ž๋‹ค.

views/partials/head.ejs ํ•˜๋‚˜๋กœ ๋ฌถ์—ˆ๋‹ค. ๊ทธ ๊ณผ์ •์—์„œ ์ด๊ฒŒ ๋‚˜์™”๋‹ค.

<!-- views/404.ejs -->
<head>
  <meta charset="UTF-8" />
  <title>Document</title>
</head>

์—๋””ํ„ฐ๊ฐ€ HTML ๊ณจ๊ฒฉ์„ ์ž๋™ ์™„์„ฑํ•  ๋•Œ ๋„ฃ์–ด ์ฃผ๋Š” ๊ธฐ๋ณธ ์ œ๋ชฉ์ด๋‹ค. 404 ํŽ˜์ด์ง€๋ผ ๊ฐœ๋ฐœ ์ค‘์— ์—ด์–ด ๋ณผ ์ผ์ด ์—†์—ˆ๊ณ , ๊ทธ๋Œ€๋กœ ๋ฐฐํฌ๋ผ ์žˆ์—ˆ๋‹ค. ์ค‘๋ณต์„ ์—†์• ๋Š” ์ž‘์—…์€ ์ค‘๋ณต ๊ทธ ์ž์ฒด๋ณด๋‹ค ์ค‘๋ณต ๋’ค์— ์ˆจ์–ด ์žˆ๋˜ ๊ฒƒ์„ ๋“œ๋Ÿฌ๋‚ด๋Š” ์ชฝ์ด ๋” ๊ฐ’์ง€๋‹ค.

๊ฒ€์ฆ์€ ์‹ค์ œ ๋ Œ๋”๋กœ ํ–ˆ๋‹ค. ์ด ํ”„๋กœ์ ํŠธ๋Š” node_modules๊ฐ€ ์žˆ์–ด์„œ EJS 5๊ฐœ ํŽ˜์ด์ง€๋ฅผ ์ง์ ‘ ๋ Œ๋”ํ•ด ํ™•์ธํ•  ์ˆ˜ ์žˆ์—ˆ๋‹ค.

ํ† ํฐํ™”๊ฐ€ ์ƒˆ ํ•จ์ • ์…‹์„ ์—ด์—ˆ๋‹ค

์—ฌ๊ธฐ๊นŒ์ง€๊ฐ€ ์ •๋ฆฌ ๋‹น์ผ์˜ ์ด์•ผ๊ธฐ๋‹ค. ๊ทธ๋Ÿฐ๋ฐ ๋„ค ๊ณณ ์ค‘ ๋‘ ๊ณณ์—์„œ 12์ผ, 18์ผ ๋’ค์— ํ›„์† ์ˆ˜์ • ์ปค๋ฐ‹์ด ๋‚˜๊ฐ”๋‹ค. ํ† ํฐํ™”๋Š” ๋์ด ์•„๋‹ˆ๋ผ ์ƒˆ ์‹คํŒจ ๋ชจ๋“œ์˜ ์‹œ์ž‘์ด์—ˆ๋‹ค.

1. ์ž๊ธฐ ์ž์‹ ์„ ์ฐธ์กฐํ•œ CSS ๋ณ€์ˆ˜๋Š” ์กฐ์šฉํžˆ ๋ฌดํšจ๊ฐ€ ๋œ๋‹ค

ํ† ํฐ์„ ์žฌ๋ฐฐ์น˜ํ•˜๋‹ค ์ด๋Ÿฐ ์ค„์ด ๋‚จ์•˜๋‹ค.

:root {
  --reset-color: var(--reset-color);   /* ์ž๊ธฐ ์ž์‹ ์„ ์ฐธ์กฐํ•œ๋‹ค */
  --danger-color: var(--danger-color);
}

CSS๋Š” ์˜ค๋ฅ˜๋ฅผ ๋‚ด์ง€ ์•Š๋Š”๋‹ค. ๋นŒ๋“œ๋„ ํ†ต๊ณผํ•œ๋‹ค. ์‚ฌ์–‘์ƒ ์ˆœํ™˜ ์ฐธ์กฐ๊ฐ€ ์žˆ๋Š” ์‚ฌ์šฉ์ž ์ •์˜ ์†์„ฑ์€ computed-value ์‹œ์ ์— ๋ฌดํšจ(invalid at computed-value time) ๋กœ ์ฒ˜๋ฆฌ๋˜๊ณ , ๊ทธ ์†์„ฑ์€ ์ƒ์†๊ฐ’์ด๋‚˜ ์ดˆ๊ธฐ๊ฐ’์œผ๋กœ ๋–จ์–ด์ง„๋‹ค.w3c-cycles ๊ฒฐ๊ณผ์ ์œผ๋กœ ํ•ด๋‹น ๋ฒ„ํŠผ์˜ ์ƒ‰์ด ํ†ต์งธ๋กœ ์‚ฌ๋ผ์ง„๋‹ค.

์—๋Ÿฌ ๋ฉ”์‹œ์ง€๊ฐ€ ์—†์œผ๋‹ˆ ๊ฒ€์ƒ‰ํ•  ๋ฌธ์ž์—ด๋„ ์—†๋‹ค. ํ™”๋ฉด์„ ๋ˆˆ์œผ๋กœ ๋ด์•ผ๋งŒ ๋ฐœ๊ฒฌ๋œ๋‹ค. ๊ฐ’์œผ๋กœ ๋˜๋Œ๋ ค ๊ณ ์ณค๋‹ค.

--reset-color: #ff9800;
--danger-color: #f44336;

2. ํ•˜๋“œ์ฝ”๋”ฉ์„ ๊ฑท์–ด๋‚ด๋ฉด ๋ธŒ๋ผ์šฐ์ € ๊ธฐ๋ณธ๊ฐ’์ด ๋“œ๋Ÿฌ๋‚œ๋‹ค

์˜ˆ์™ธ ์„ ํƒ์ž๋ฅผ ์ง€์šฐ๋ฉด์„œ .App.dark-mode .task-input { background-color: #2a2a2a }๋„ ๊ฐ™์ด ์ง€์› ๋‹ค. ๊ทธ๋Ÿฐ๋ฐ .task-input ๋ณธ์ฒด์—๋Š” ๋ฐฐ๊ฒฝ ์ง€์ •์ด ์•„์˜ˆ ์—†์—ˆ๋‹ค. ์˜ˆ์™ธ ์„ ํƒ์ž๊ฐ€ ์œ ์ผํ•œ ์ง€์ •์ด์—ˆ๋˜ ๊ฒƒ์ด๋‹ค.

์ง€์šฐ๊ณ  ๋‚˜๋‹ˆ ๋ธŒ๋ผ์šฐ์ € ๊ธฐ๋ณธ ํฐ์ƒ‰์ด ๋“œ๋Ÿฌ๋‚˜, ๋‹คํฌ ๋ชจ๋“œ์—์„œ ์ž…๋ ฅ์ฐฝ๋งŒ ํ•˜์–—๊ฒŒ ํŠ€์—ˆ๋‹ค.

.task-input {
  /* ์ง€์ •ํ•˜์ง€ ์•Š์œผ๋ฉด ๋ธŒ๋ผ์šฐ์ € ๊ธฐ๋ณธ ํฐ์ƒ‰์ด๋ผ ๋‹คํฌ์—์„œ ์ž…๋ ฅ์ฐฝ๋งŒ ํŠ„๋‹ค */
  background-color: var(--input-background);
  color: var(--text-color);
}

์˜ˆ์™ธ๋ฅผ ์ง€์šธ ๋•Œ๋Š” ๊ทธ ์˜ˆ์™ธ๊ฐ€ ๋ฎ๊ณ  ์žˆ๋˜ ๊ฒƒ์ด ๋ฌด์—‡์ธ์ง€๋ถ€ํ„ฐ ํ™•์ธํ•ด์•ผ ํ•œ๋‹ค. ์˜ˆ์™ธ๊ฐ€ ์œ ์ผํ•œ ์ง€์ •์ด์—ˆ๋‹ค๋ฉด ์ง€์šฐ๋Š” ์ˆœ๊ฐ„ ๊ธฐ๋ณธ๊ฐ’์ด ์˜ฌ๋ผ์˜จ๋‹ค.

3. ํ…Œ๋งˆ์™€ ๋ฌด๊ด€ํ•ด์•ผ ํ•˜๋Š” ํ† ํฐ์ด ๋”ฐ๋กœ ์žˆ๋‹ค

ํ† ํฐ์„ ์žฌ์ •์˜ํ•˜๊ธฐ ์ง์ „์— ํšŒ๊ท€ ํ•˜๋‚˜๋ฅผ ๋ฐœ๊ฒฌํ–ˆ๋‹ค.

button {
  color: var(--background-color);   /* ์ปฌ๋Ÿฌ ๋ฒ„ํŠผ ์œ„์˜ ํฐ ๊ธ€์ž๋ฅผ ์˜๋„ํ–ˆ๋‹ค */
}

์˜ˆ์ „์—๋Š” --background-color๊ฐ€ ๋‹คํฌ์—์„œ ์•ˆ ๋ฐ”๋€Œ์—ˆ๋‹ค. ๊ทธ๋ž˜์„œ ์ด ๊ธ€์ž๋Š” ํ•ญ์ƒ ํฐ์ƒ‰์ด์—ˆ๊ณ , ์šฐ์—ฐํžˆ ์˜๋„๋Œ€๋กœ ๋™์ž‘ํ–ˆ๋‹ค. ํ† ํฐ์„ ํ…Œ๋งˆ๋ณ„๋กœ ์žฌ์ •์˜ํ•˜๋Š” ์ˆœ๊ฐ„ ์ด ๊ธ€์ž๋Š” ๊ฒ€์€์ƒ‰์ด ๋œ๋‹ค. ์ดˆ๋ก ๋ฒ„ํŠผ ์œ„์˜ ๊ฒ€์€ ๊ธ€์”จ๋‹ค.

์˜๋„๋Š” "๋ฐฐ๊ฒฝ์ƒ‰"์ด ์•„๋‹ˆ๋ผ "์ปฌ๋Ÿฌ ๋ฒ„ํŠผ ์œ„์— ์–น๋Š” ๊ธ€์ž์ƒ‰"์ด์—ˆ๋‹ค. ์ด๋ฆ„์„ ์ƒˆ๋กœ ๋งŒ๋“ค์–ด 3๊ณณ์„ ์˜ฎ๊ฒผ๋‹ค.

--on-accent: #ffffff;   /* ํ…Œ๋งˆ์™€ ๋ฌด๊ด€. ์ปฌ๋Ÿฌ ๋ฒ„ํŠผ ์œ„์— ์–น๋Š” ๊ธ€์ž */

๊ฐ™์€ ํ† ํฐ์ด ์‚ฌ์ดํŠธ๋งต ์ƒ์„ฑ๊ธฐ์—๋„ ํ•„์š”ํ–ˆ๋‹ค. ๋‹คํฌ ๋ชจ๋“œ์—์„œ ๋ฒ„ํŠผ ๊ธ€์ž๊ฐ€ WCAG AA ๋Œ€๋น„ ๊ธฐ์ค€ 4.5:1์„ ๋ชป ๋„˜๊ธฐ๊ณ  ์žˆ์—ˆ๋‹ค.wcag-contrast

ํ…Œ๋งˆ๋ฅผ ๋”ฐ๋ผ์•ผ ํ•˜๋Š” ํ† ํฐ๊ณผ ๋”ฐ๋ฅด๋ฉด ์•ˆ ๋˜๋Š” ํ† ํฐ์„ ๊ตฌ๋ถ„ํ•˜๋Š” ๊ฒƒ์ด ํ•œ ๋ฒŒ ์šด์˜์˜ ์ „์ œ๋‹ค. ํ‘œ๋ฉด๊ณผ ํ…์ŠคํŠธ๋Š” ๋”ฐ๋ผ์•ผ ํ•˜๊ณ , ๋ธŒ๋žœ๋“œ ์ƒ‰๊ณผ ๊ทธ ์œ„์— ์–น๋Š” ๊ธ€์ž์ƒ‰์€ ๋”ฐ๋ฅด๋ฉด ์•ˆ ๋œ๋‹ค.

์ •๋ฆฌ

  1. ์˜ˆ์™ธ ๊ทœ์น™์˜ ๊ฐœ์ˆ˜๊ฐ€ ํ† ํฐ ๋ถ€์กฑ์˜ ์ง€ํ‘œ๋‹ค. .dark-mode ๋ณด์ • ์„ ํƒ์ž 19๊ฐœ๋Š” ๋‹คํฌ ํ† ํฐ์ด 2๊ฐœ๋ผ๋Š” ์‚ฌ์‹ค์˜ ๋‹ค๋ฅธ ํ‘œํ˜„์ด์—ˆ๋‹ค
  2. ์ธ๋ผ์ธ ์Šคํƒ€์ผ์ด ์•ˆ ์—†์–ด์ง€๋ฉด ๋™์  ์Šคํƒ€์ผ์„ ์˜์‹ฌํ•œ๋‹ค. ํ•จ์ˆ˜๊ฐ€ ์ƒ‰๊ฐ’์„ ๋ฐ˜ํ™˜ํ•˜๋Š” ํ•œ ๊ทธ ๊ฐ’์ด ๊ฐˆ ๊ณณ์€ ์ธ๋ผ์ธ๋ฟ์ด๋‹ค. ๋ฐ˜ํ™˜๊ฐ’์„ ํ† ํฐ ์ด๋ฆ„์œผ๋กœ ๋ฐ”๊พธ๋ฉด ํ’€๋ฆฐ๋‹ค
  3. ์†Œ์ˆ˜์  px์€ ์–ด๋”˜๊ฐ€์—์„œ ๋‚˜๋ˆ—์…ˆ์„ ํ–ˆ๋‹ค๋Š” ๋œป์ด๋‹ค. html { font-size }๋ฅผ ๊ฑด๋“œ๋ ธ๋Š”์ง€ ๋จผ์ € ๋ณธ๋‹ค
  4. ์˜ˆ์™ธ ์„ ํƒ์ž ์•ˆ์— ์ด๋ฏธ ํ† ํฐ ๊ฐ’์ด ์žˆ๋‹ค. ๋ฐ˜๋ณต๋˜๋Š” ํ•˜๋“œ์ฝ”๋”ฉ ์ƒ‰์„ ์„ธ์–ด ๋ณด๋ฉด ํ•„์š”ํ•œ ํ† ํฐ ๋ชฉ๋ก์ด ๊ทธ๋Œ€๋กœ ๋‚˜์˜จ๋‹ค
  5. ํ† ํฐํ™” ์งํ›„๊ฐ€ ๊ฐ€์žฅ ์œ„ํ—˜ํ•˜๋‹ค. ์˜ˆ์™ธ๋ฅผ ์ง€์šฐ๋ฉด ๊ทธ ์˜ˆ์™ธ๊ฐ€ ์œ ์ผํ•œ ์ง€์ •์ด์—ˆ๋˜ ์ž๋ฆฌ์—์„œ ๊ธฐ๋ณธ๊ฐ’์ด ์˜ฌ๋ผ์˜จ๋‹ค

๊ฐ€์žฅ ์ค‘์š”ํ•œ ํ•˜๋‚˜๋ฅผ ๊ณ ๋ฅด๋ผ๋ฉด ์ฒซ ๋ฒˆ์งธ๋‹ค. ์˜ˆ์™ธ๋Š” ๊ฒŒ์œผ๋ฆ„์˜ ๊ฒฐ๊ณผ๊ฐ€ ์•„๋‹ˆ๋ผ ์–ดํœ˜๊ฐ€ ๋ชจ์ž๋ž€ ๊ณณ์—์„œ ์ƒ๊ธฐ๋Š” ์šฐํšŒ๋กœ๋‹ค. ์šฐํšŒ๋กœ๋ฅผ ํ•˜๋‚˜์”ฉ ๋ง‰๋Š” ๋Œ€์‹  ์–ดํœ˜๋ฅผ ๋Š˜๋ฆฌ๋ฉด ์šฐํšŒ๋กœ๊ฐ€ ์Šค์Šค๋กœ ์‚ฌ๋ผ์ง„๋‹ค.

  • .dark-mode, .theme-* ๊ฐ™์€ ๋ณด์ • ์„ ํƒ์ž์˜ ๊ฐœ์ˆ˜๋ฅผ ์„ผ๋‹ค. ๋‹ค์„ฏ ๊ฐœ๋ฅผ ๋„˜์œผ๋ฉด ํ† ํฐ์ด ๋ถ€์กฑํ•œ ๊ฒƒ์ด๋‹ค
  • ๋‹คํฌ ์ „์šฉ ํ† ํฐ ์ด๋ฆ„(--dark-*)์„ ๋งŒ๋“ค์ง€ ์•Š๋Š”๋‹ค. ๊ฐ™์€ ์ด๋ฆ„ ํ•œ ๋ฒŒ์„ ํ…Œ๋งˆ ๋ธ”๋ก์—์„œ ์žฌ์ •์˜ํ•œ๋‹ค
  • ์˜ˆ์™ธ ์„ ํƒ์ž์— ๋ฐ˜๋ณตํ•ด ๋‚˜์˜ค๋Š” ํ•˜๋“œ์ฝ”๋”ฉ ์ƒ‰์„ ๋ฝ‘์•„ ์ด๋ฆ„์„ ๋ถ™์ธ๋‹ค. ๊ทธ๊ฒŒ ๋น ์ง„ ํ† ํฐ ๋ชฉ๋ก์ด๋‹ค
  • ์ƒ‰๊ฐ’์„ ๋ฐ˜ํ™˜ํ•˜๋Š” ํ•จ์ˆ˜๋ฅผ ์ฐพ์•„ ํ† ํฐ ์ด๋ฆ„์„ ๋ฐ˜ํ™˜ํ•˜๋„๋ก ๋ฐ”๊พผ๋‹ค
  • styled-components ๋™์  prop์—๋Š” $ ์ ‘๋‘์‚ฌ๋ฅผ ๋ถ™์ธ๋‹ค
  • html { font-size }๊ฐ€ 16px์ด ์•„๋‹Œ์ง€ ํ™•์ธํ•œ๋‹ค. ์†Œ์ˆ˜์  px์˜ ์ถœ์ฒ˜๋‹ค
  • ์ œ๋ชฉ ๋‹จ๊ณ„๋ณ„ ํฌ๊ธฐ๊ฐ€ ์‹ค์ œ๋กœ ๋‹ค๋ฅธ์ง€ ํ™•์ธํ•œ๋‹ค. h3, h4, ๋ณธ๋ฌธ์ด ๊ฐ™์€ ๊ฐ’์ด๋ฉด ์œ„๊ณ„๊ฐ€ ์—†๋Š” ๊ฒƒ์ด๋‹ค
  • ํ† ํฐ ์ •์˜์— --x: var(--x) ์ž๊ธฐ์ฐธ์กฐ๊ฐ€ ์—†๋Š”์ง€ ํ›‘๋Š”๋‹ค. ๋นŒ๋“œ๋Š” ํ†ต๊ณผํ•˜๊ณ  ์ƒ‰๋งŒ ์‚ฌ๋ผ์ง„๋‹ค
  • ์˜ˆ์™ธ ์„ ํƒ์ž๋ฅผ ์ง€์šฐ๊ธฐ ์ „์—, ๊ทธ ์†์„ฑ์ด ๋ณธ์ฒด์—๋„ ์ง€์ •๋ผ ์žˆ๋Š”์ง€ ํ™•์ธํ•œ๋‹ค
  • ๋ธŒ๋žœ๋“œ ์ƒ‰ ์œ„์— ์–น๋Š” ๊ธ€์ž์ƒ‰์€ ํ…Œ๋งˆ ๋ฌด๊ด€ ํ† ํฐ(--on-accent)์œผ๋กœ ๋ถ„๋ฆฌํ•œ๋‹ค
  • ์—ฌ๋Ÿฌ ํŽ˜์ด์ง€๊ฐ€ ๊ฐ์ž <head>๋ฅผ ๊ด€๋ฆฌํ•˜๊ณ  ์žˆ์œผ๋ฉด partial๋กœ ๋ฌถ๋Š”๋‹ค. ๋น ์ง„ ๋ฉ”ํƒ€ ํƒœ๊ทธ๊ฐ€ ๋“œ๋Ÿฌ๋‚œ๋‹ค

๋‹ค์Œ ๊ธ€์—์„œ๋Š” ๊ฒ€์ƒ‰ ์ชฝ์œผ๋กœ ๊ฐ„๋‹ค. ํ•œ๊ตญ์–ด ๋ฌธ์„œ๋ฅผ SQLite FTS5๋กœ ๊ฒ€์ƒ‰ํ•  ๋•Œ ๊ธฐ๋ณธ ํ† ํฌ๋‚˜์ด์ €๊ฐ€ ๋‘ ๊ธ€์ž ๋‹จ์–ด๋ฅผ ๋ชป ์žก๋Š” ์ด์œ ์™€, ํ‚ค์›Œ๋“œ์™€ ์˜๋ฏธ ๊ฒ€์ƒ‰์„ ์ˆœ์œ„๋กœ๋งŒ ํ•ฉ์น˜๋ฉด ์ •ํ™•ํžˆ ์ผ์น˜ํ•œ ๊ฒฐ๊ณผ๊ฐ€ ์˜คํžˆ๋ ค ๋ฐ€๋ ค๋‚˜๋Š” ๊ตฌ์กฐ๋ฅผ ๋‹ค๋ฃฌ๋‹ค.

์ฐธ๊ณ ๋ฌธํ—Œ


์ด์–ด์„œ ์ฝ๊ธฐ


  1. MDN Web Docs. "Using CSS custom properties (variables)" (์‚ฌ์šฉ์ž ์ •์˜ ์†์„ฑ์˜ ์ƒ์†๊ณผ ์žฌ์ •์˜). https://developer.mozilla.org/en-US/docs/Web/CSS/CSS_cascading_variables/Using_CSS_custom_propertiesโ†ฉ
  2. MDN Web Docs. "prefers-color-scheme" (์‹œ์Šคํ…œ ํ…Œ๋งˆ ์งˆ์˜). https://developer.mozilla.org/en-US/docs/Web/CSS/@media/prefers-color-schemeโ†ฉ
  3. styled-components. "Transient props" ($ ์ ‘๋‘์‚ฌ prop์€ DOM์œผ๋กœ ์ „๋‹ฌ๋˜์ง€ ์•Š๋Š”๋‹ค). https://styled-components.com/docs/api#transient-propsโ†ฉ
  4. MDN Web Docs. "CSS length: rem" (๋ฃจํŠธ ์š”์†Œ ๊ธฐ์ค€ ์ƒ๋Œ€ ๋‹จ์œ„). https://developer.mozilla.org/en-US/docs/Web/CSS/length#remโ†ฉ
  5. W3C. "CSS Custom Properties for Cascading Variables Module Level 1 - Resolving Dependency Cycles" (์ˆœํ™˜ ์ฐธ์กฐ๋Š” invalid at computed-value time). https://www.w3.org/TR/css-variables-1/#cyclesโ†ฉ
  6. W3C. "WCAG 2.1 Success Criterion 1.4.3 Contrast (Minimum)" (๋ณธ๋ฌธ ๋Œ€๋น„ 4.5:1). https://www.w3.org/WAI/WCAG21/Understanding/contrast-minimum.htmlโ†ฉ

@leekh8
๋ณด์•ˆ, ์›น ๊ฐœ๋ฐœ, Python์„ ๋‹ค๋ฃจ๋Š” ๊ธฐ์ˆ  ๋ธ”๋กœ๊ทธ