Svelte Component 라이브러리 - 6일차
포스트
취소

Svelte Component 라이브러리 - 6일차

원하는 UI 구성을 위해 유틸리티 CSS 라이브러리인 Open Props 공부합니다. 웹프레임워크로 SveltKit 을 사용하고 bun 런타임 위에서 실행합니다.

svelte-components 시리즈는 여기까지만 한다. 본래 컴포넌트 만드는 연습을 하기 위해 작성하기 시작한 것인데, css 프레임워크를 한번씩 살펴보는 시리즈가 되어 버렸다. (실패다) 여러 기술들을 살펴보는 것은 좋으나, 깊이 없이 기웃거리기만 하고 있으니 실망스럽다. 어느 분야이든 깊이 파고든다는 것은 중요하다. 기웃거리더라도 넘치면 지식이 된다는데, 그런 방식으로는 굳건한 줄기를 만드는데 너무 많은 시간이 걸릴 것이다. 효율적으로 공부하자.

0. 개요

tailwindcss 는 백엔드 개발자들이 선호하고, open-props 는 프론트엔드 개발자들이 선호하는 경향이 있다고 한다. (순수한 css 이기 때문에)

참고 : 유튜브 - Open Props - CSS Framework

open-props 사용을 위한 vscode extension 추천 (자동완성)

CSS Variable Autocomplete

1. 프로젝트 생성

1) SvelteKit 프로젝트 생성

1
2
3
4
5
6
7
8
bun create svelte@latest bun-openprops-app
  # - Skeleton project
  # - Typescript

cd bun-openprops-app
bun install

bun run dev

2) Open Props 설정

  1. postcss 설치 및 구성 (svelte-add)
  2. postcss-preset-env (autoprefixer, nested 포함)
  3. open-props, postcss-jit-props 설치
  4. heroicon 설치
  5. postcss.config.cjs 설정 (autoprefixer 제거할것)
  6. src/app.pcss 에 open-props 와 font 임포트
  7. +layout.svelte 에 app.pcss 참조 (이미 되어있음)
  8. +page.svelte 에 데모 코드를 넣어 작동 확인
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
bunx svelte-add@latest postcss
bun add -d postcss-preset-env
bun add -d open-props postcss-jit-props
bun add -d svelte-hero-icons

# postcss 는 CommonJS 확장자를 필요로 한다!
cat <<EOF > postcss.config.cjs 
const postcssPresetEnv = require('postcss-preset-env');
const postcssJitProps = require('postcss-jit-props');
const openProps = require('open-props');

module.exports = {
  plugins: [
    postcssJitProps(openProps),
    postcssPresetEnv({
      features: {
        'nesting-rules': {
          noIsPseudoSelector: false
        }
      }
    })
  ]
};
EOF

# 전역 css 에 directives 와 noto 폰트 설정
cat <<EOF > src/app.pcss
/* fonts: Noto Color Emoji, Noto Sans KR, Noto Serif KR */
@import url('https://fonts.googleapis.com/css2?family=Noto+Color+Emoji&family=Noto+Sans+KR:wght@300;400;500;700&family=Noto+Serif+KR:wght@400;700&display=swap');
@import url("//cdn.jsdelivr.net/gh/wan2land/d2coding/d2coding-ligature-full.css");

/* the props */
@import 'open-props/postcss/style';

/* optional imports that use the props */
@import 'open-props/postcss/normalize';
@import 'open-props/postcss/buttons';

/* Reset */
*,
*::before,
*::after {
  padding: var(--size-fluid-0);
  margin: var(--size-fluid-0);
  box-sizing: border-box;
  font-family: 'Noto Sans KR', var(--font-sans);
}
EOF

cat <<EOF > src/routes/+layout.svelte
<script>
  import '../app.pcss';
</script>

<slot />
EOF

cat <<EOF > src/routes/+page.svelte
<script>
  import { Icon, Radio } from 'svelte-hero-icons';
</script>

<section>
  <h1>Welcome to SvelteKit</h1>
  <p>Visit <a href="https://kit.svelte.dev">kit.svelte.dev</a> to read the documentation</p>
  <button class="btn-custom">
    <Icon src={Radio} size="1rem" />
    Icon
  </button>
</section>

<style lang="pcss">
  :global(body) {
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
    gap: var(--size-5);
    padding: var(--size-5);
  }

  section {
    display: grid;
    gap: var(--size-2); /* .5rem */
    text-align: center;

    & > p {
      font-size: var(--font-size-4); /* 1.5rem */
    }
  }

  .btn-custom {
    --_bg: linear-gradient(var(--indigo-5), var(--indigo-7));
    --_border: var(--indigo-6);
    --_text: var(--indigo-0);
    --_ink-shadow: 0 1px 0 var(--indigo-9);
    --_size: var(--font-size-3);
    padding-block: var(--size-2);
  }
</style>
EOF

bun run dev

open-props 개별적인 import 항목들 (선택사항)

1
2
3
4
5
6
7
/* individual imports */
@import 'open-props/postcss/indigo';
@import 'open-props/postcss/easings';
@import 'open-props/postcss/animations';
@import 'open-props/postcss/sizes';
@import 'open-props/postcss/gradients';
/* see PropPacks for the full list */

9. Review

  • 검색을 해봐도 open props 예제를 찾기 어렵다. 순수 CSS 에 능숙한 이들만 쓴다.
    • tailwind 는 프로토타입 개발에 유용하지만, 작성한 코드를 다시 보기 싫다는데
    • 그렇다 하더라도 빠른 개발과 수정에는 tailwind 가 효과적이란 의견이 다수이다.
  • postcss 를 어떻게 써야할지 고민하지 말고 postcss-preset-env 쓰자.

트렌드 - postcss nesting 플러그인 3종 비교

비등한데, 최근에 단촐하게 postcss-nested 플러그인만 사용하는 경향이 많아졌다.

참고 : Nesting in PostCSS — Which Way to Go?

  • postcss-nesting : CSS 스펙 스타일
  • postcss-nested : Sass 스타일
    • nest 기능 외에는 관심이 없다는 사용자는 이것만 설치하는 경향이 있다.
  • postcss-preset-env ← 저자가 추천하는 플러그인? (일반적인 선택)
    • git 리포지토리 이름은 postcss-plugins 이다. (커밋은 활발)
    • 흔히 사용되는 설정들을 다 포함한다. (autoprefixer, nested 포함)
    • css 스펙과 동떨어지는 경향도 없지 않지만 쉬운 css 사용을 위해 노력한다고 소개글에 적혀있다.
    • rgb, color 등등 다양한 함수를 지원하고 있다.

참고 : tailwind 의 postcss 플러그인 사용 예시

1
2
bun add -d postcss-import
bun add -d postcss-preset-env
1
2
3
4
5
6
7
8
9
10
11
// postcss.config.js
module.exports = {
  plugins: {
    'postcss-import': {},
    'tailwindcss/nesting': {},
    tailwindcss: {},
    'postcss-preset-env': {
      features: { 'nesting-rules': false },
    },
  }
}

 
 

끝!   읽어주셔서 감사합니다.

이 기사는 저작권자의 CC BY 4.0 라이센스를 따릅니다.