효뚜르팝의 Dev log
디자인 시스템 구축을 위해 Shadcn UI와 Radix Theme PoC 진행해보기 본문
최근에 회사에서 새롭게 디지털 교과서 제작 프로젝트를 시작하게 되면서, 기존에 사용하지 않았던 기술을 도입하기 위해 여러 PoC를 진행하고자 하였다. 그 중 디자인 시스템도 새로 빠르게 구축을 해야해서, 기존의 디자인 시스템을 대체할 만한 라이브러리나 디자인 컴포넌트 들로 PoC를 하게 되었다.
🙋♀️ 디자인 시스템을 새로 구축해야 했던 이유?
회사에서 기존에 사용하던 디자인 시스템이 radix와 stitches의 조합인 CSS in JS로 구성이 되어있었는데 런타임 오버헤드와 번들 크기 확장, 컴포넌트 라이브러리와의 호환성 문제 등 성능상의 이슈를 해결하기 위해, 정적으로 생성되는 방식으로 전환이 필요했다.
참고)
CSS-in-JS의 잠재적 문제에 관련한 글은 아래의 글을 읽어보면 도움이 될 것 같다. https://junghan92.medium.com/%EB%B2%88%EC%97%AD-%EC%9A%B0%EB%A6%AC%EA%B0%80-css-in-js%EC%99%80-%ED%97%A4%EC%96%B4%EC%A7%80%EB%8A%94-%EC%9D%B4%EC%9C%A0-a2e726d6ace6
(번역) 우리가 CSS-in-JS와 헤어지는 이유
원문: https://dev.to/srmagura/why-were-breaking-up-wiht-css-in-js-4g9b
junghan92.medium.com
🙋♀️ 새로운 디자인 시스템 선택지 조건?
우선 제한된 기간 내에 디지털 교과서를 빠르게 구축해야하기 때문에 빠르게 실무에 적용할 수 있는 디자인 시스템이 필요했다.
또한 다른 팀들과 함께 진행하는 프로젝트여서, 통일된 디자인을 위해서 디자인 토큰을 커스텀하고, 커스텀된 컴포넌트로 확장을 할 수 있는지에 대한 확인이 필요했다.
🙋♀️ PoC 진행 방식과 PoC를 진행한 디자인 컴포넌트?
기존에 존재하던 레포에서 해당 디자인 컴포넌트 관련한 패키지를 설치하고, 디자인 컴포넌트를 import해보고 커스텀한 컴포넌트로 확장이 가능한지 등을 확인하는 방식으로 PoC를 진행했다.
두 가지 디자인 컴포넌트로 PoC를 진행하였다.
- Shadcn UI + TailwindCSS
- Radix Theme + TailwindCSS
둘다 최근에 많이 사용되고 있기도 하고, TailwindCSS와 함께 사용이 되어 정적으로 CSS 구현이 가능하다. 또한 기존에 회사에서 사용하던 Radix Primitives를 기반으로 커스텀화하여 만들어진 컴포넌트를 제공하고 있어서, 쉽게 실무에 적용하다는 장점이 보여서 위 두 기술들을 사용해보게 되었다.
🙋♀️ Shadcn UI + TailwindCSS
Shadcn UI는 Radix UI 및 TailwindCSS를 사용하여 구축된 재사용 가능한 컴포넌트이다. 즉, 컴포넌트 라이브러리가 아닌, 앱에 복사하여 붙혀넣을 수 있는 재사용 가능한 컴포넌트 모음이다.
Shadcn UI 사용 방법
- 프로젝트 내에 tailwind 기본 세팅 참고
- cli 또는 수동으로 shadcn ui 초기 세팅
cli로 세팅해야 따로 컴포넌트를 일일히 복사하지 않아도 되어 사용하는 데에 수월함 cli로 기본 세팅 하는 방법 - shadcn ui 초기 세팅에서 만들어진 shadcn ui의 css 파일을 최상위 컴포넌트(App.tsx)에서 import
- 원하는 shadcn 컴포넌트를 import 해서 프로젝트 내에서 사용한다.
npx shadcn-ui@latest add button
Shadcn UI 커스텀해서 사용하기
자동 생성된 `button.tsx` 내에서 토큰 등을 추가하여 커스텀하여 사용할 수 있다.
// button.tsx
const buttonVariants = cva(
{
variants: {
// 따로 추가한 속성
font: {
default: 'text-sm',
xs: 'text-xs',
},
},
defaultVariants: {
font: "default",
},
}
);
// 추가 속성을 props에 전달
const Button = React.forwardRef<HTMLButtonElement, ButtonProps>(
({ className, variant, font, asChild = false, ...props }, ref) => {
const Comp = asChild ? Slot : "button";
return (
<Comp
className={cn(buttonVariants({ variant, font, className }))}
ref={ref}
{...props}
/>
);
}
);
import { Button } from "components/ui/button";
function Test() {
return (
<div>
<Button variant="outline" size="sm" font="xs">Button</Button>
</div>
);
}
export default Test;
Shadcn UI 사용해보고 느낀 점
결론적으로 Radix UI 기반이고 완성된 UI 컴포넌트를 제공하고 있고, Shadcn UI 가 Radix UI의 커스텀 된 버전이라고 보면 될 것 같다.
Shadcn UI는 라이브러리가 아닌 컴포넌트 설치형으로, 기존에 완성된 디자인 컴포넌트를 copy and paste로 간편하게 사용이 가능하다.
다만 컴포넌트를 커스텀하고 싶을 시에, import를 한 컴포넌트 파일에서 직접 토큰을 추가하는 방식으로 수정을 해주어야해서, 디자인 통일성을 위해 다른 팀들 간에 커스텀해서 생성한 토큰과 컴포넌트 파일을 잘 공유해야할 것으로 보인다.
추가로,
- cli 로 shadcn ui 를 초기 세팅 할 때, shadcn UI 관련 `components.json` 이 자동으로 생성이 되는데 이 때 pathname을 정확하게 입력해주는 것이 중요하다.
(tsconfig.json에서 설정한 baseUrl 기준에 맞추어서 적어주어야 함) - tailwind 관련 설정 내용을 담고있는 `tailwind.config.js` 내의 content에서도 어떤 경로의 파일 유형에서 tailwindCSS를 적용할 것인지 정확하게 적어주는 것이 중요하다. https://stackoverflow.com/questions/71070781/tailwind-css-classes-is-not-working-in-my-project
// tailwind.config.js
/** @type {import('tailwindcss').Config} */
module.exports = {
content: [
'./pages/**/*.{ts,tsx}',
'./components/**/*.{ts,tsx}',
'./app/**/*.{ts,tsx}',
'./src/**/*.{ts,tsx}',
],
}
- Shadcn UI 공식 문서 : https://ui.shadcn.com/docs
- shadcn/ui 를 만든 Shadcn이 리트윗한 글..! : https://manupa.dev/blog/anatomy-of-shadcn-ui
- 2023년에 JS기준으로 shadcn/ui가 랭킹 1위였다...! https://risingstars.js.org/2023/en
Introduction
Beautifully designed components that you can copy and paste into your apps. Accessible. Customizable. Open Source.
ui.shadcn.com
Tailwind CSS classes is not working in my project
Here is my HTML link https://play.tailwindcss.com/fbB4GCL0ht Visual Studio Code setup pictures Tailwind.Config.js All files warn - No utility classes were detected in your source files. If this is
stackoverflow.com
🙋♀️ Radix Theme + TailwindCSS
Radix Theme은 특정한 시각적 디자인을 갖춘 Radix 기반의 완성된 UI 테마를 제공하고 있고, 디자인 요소, 색상 팔레트, 폰트 등이 이미 구성되어 있어서, 이를 사용한다면 빠르게 디자인 시스템을 구축할 수 있다는 장점이 있다.
Radix Theme 사용 방법
radix theme은 아래 두가지 방식으로 컴포넌트를 커스텀 할 수 있다.
- 컴포넌트에 props를 내려주는 방식 (Radix UI에서 기본으로 제공하는 props와 Tailwind CSS 문법을 적용)
- style.css에서 디자인 토큰을 정의하거나 radix ui에서 기본으로 제공하는 토큰을 컴포넌트 style로 적용하는 방식
radix theme component 사용 예시는 다음과 같다.
radix theme component에 tailwind CSS 문법을 적용한다.
import { Box, Text, Heading, Container } from '@radix-ui/themes';
const TestComponent = () => {
return(
<Box
style={{ background: 'var(--gray-a2)', borderRadius: 'var(--radius-3)' }}
>
<Container size="1">
<Heading as="h1" align="center">제목입니다.</Heading>
<Text as="p" size="8" weight="bold" mb="7">
본문입니다.
</Text>
<Box py="9" />
</Container>
</Box>
)
};
export default TestComponent;
직접 style.css에서 디자인 토큰을 커스텀하는 방식은 다음과 같다.
style.css 에서 원하는 변수 및 스타일을 선언하고 해당 변수를 컴포넌트에 스타일로 적용한다.
혹은 theme-config.css로 따로 파일을 분리하여 디자인 토큰을 정의하고, global js에서 import를 하는 방식으로도 적용 가능하다. 디자인 토큰 커스텀하는 방법
Token reference – Radix Themes
Tokens provide direct access to theme values and give you flexibility to build and customize your own themed components.
www.radix-ui.com
// style.css
.radix-themes {
--primary-color: var(--ruby-1);
--red-2: var(--ruby-2);
--red-3: var(--ruby-3);
--default-font-size: 18px;
}
그리고 컴포넌트에서 정의한 디자인 토큰을 사용한다.
<Button style={{ cursor: 'pointer', backgroundColor: 'var(--primary-color)', fontSize: 'var(--default-font-size)' }} size="3" >
새로운 클래스 시작하기</Button>
Radix Theme 사용해보고 느낀 점
이미 완성된 ui와 커스텀한 디자인 토큰을 조합해서 사용하면 빠르게 디자인 시스템을 구축하기 용이할 것으로 보인다. 기존의 개발 경험과 유사하다는 점에서 무리없이 바로 사용할 수 있다는 장점이 있다. (하루 사용해보았는데, 별다른 학습 없이 공식문서만 참고하여 바로 적용해 볼 수 있었다.)
- Radix Theme 공식 문서 : radix-ui.com/themes/docs/overview/getting-started
Getting started – Radix Themes
Install Radix Themes and start building your project in minutes
www.radix-ui.com
🙋♀️ 결론
아직 어떤 디자인 시스템을 사용할 지 결정이 된 상황은 아니지만 Radix Theme을 사용할 가능성이 높아보인다. 우선 Radix Theme은 Figma to Code 기능을 사용할 수 있다고 한다. 또한 팀 내 디자이너 분께서 디자인 측면에서 radix 피그마 파일이 다른 시스템에 비해 정리가 잘 되어있어 디자인 작업에 효율이 높다는 의견을 주셨다.
개발 측면에서는 Shadcn UI, Radix Theme 둘 다 Radix UI 기반이고 완성된 UI 컴포넌트를 제공하고 있고, UI와 사용하는 방식에서만 차이가 있고, 두 방식 다 쉽게 사용할 수 있어서 어떤 UI/UX 를 사용할 지에 맞추어 결정을 하면 될 것 같다.
-> 수정된 사항 (2/4)
Shadcn UI를 사용하는 것으로 결정이 되었다. Radix Theme과 같은 경우 토큰을 커스텀할 수 있지만, 컴포넌트의 props를 추가하거나, radix에서 제공하는 색상 이외의 색상을 추가하는 것이 불가능하는 것으로 확인이 되어, 프로젝트에 도입하는 것이 적합하지 않은 것으로 판단이 되었다.
😀 글을 마치며
프로젝트 초기에 수행되는 PoC는 특히 가치 있는 경험이라고 생각한다. 기술을 직접 구현해보지 않은 새로운 기술들을 사용해 보는 것은 듣기만 하던 것을 실제로 체험하는 흥미로운 경험으로 다가왔다. 또한, 해당 기술을 신규 프로젝트에 도입할 때의 사용성 측면에서의 문제를 고려하는 과정은 개발자로서의 성장과 고민을 더욱 촉진시킬 수 있는 기회로 느껴진다.
'TIL' 카테고리의 다른 글
| [React 공식문서로 공부하기] Describe the UI (0) | 2024.02.18 |
|---|---|
| PoC를 진행할 때 유의할 점에 대해서 (3) | 2024.02.04 |
| github workflow를 통해 ci cd 개발 환경 구축하기 (2) | 2024.01.02 |
| 실수에 대해 부검하는, 포스트 모템(Postmortem)에 대해 아시나요? (1) | 2023.12.10 |
| renderHook을 사용한 hook 테스트 코드 작성 하기 (1) | 2023.10.18 |