# Scale Feedback URL: /react/components/concepts/scale-feedback Source: https://github.com/daangn/seed-design/blob/dev/docs/content/react/components/concepts/scale-feedback.mdx 커스텀 컴포넌트에 SEED의 Scale Feedback을 적용하는 방법을 알아봅니다. SEED 컴포넌트는 눌렸을 때 요소가 살짝 줄어드는 **Scale Feedback**을 기본으로 제공합니다. 작은 아이콘 버튼과 뷰포트 좌우를 채우는 버튼의 눌린 느낌이 같도록 만들기 위해, 축소 배율을 요소마다 다르게 계산합니다. 직접 만든 컴포넌트에도 같은 효과를 적용할 수 있습니다. ## 배율이 정해지는 방식 축소 배율을 고정값으로 정하는 대신, 요소의 실제 크기에서 배율을 계산합니다. | 요소 | 폭 × 높이 | 계산된 배율 | 실제 축소 | | -------- | -------- | ------ | ------------------ | | 아이콘 버튼 | 32 × 32 | 0.938 | 가로 2px, 세로 2px | | 텍스트 버튼 | 120 × 48 | 0.958 | 가로 5px, 세로 2px | | 가로로 긴 버튼 | 343 × 48 | 0.977 | 가로 8px, 세로 1.1px | | 작은 버튼 | 22 × 22 | 0.917 | 가로 1.8px, 세로 1.8px | 배율은 렌더된 크기에서 계산되므로, 폰트 스케일링, 화면 폭 차이, 줄바꿈 등으로 인해 요소가 예상과 다른 크기로 그려져도 별도로 값을 조정할 필요가 없습니다. ## 적용하기 요소의 크기를 측정하는 일은 `ScaleFeedback`이 담당하고, \**계산된 배율을 언제 어떤 요소에 적용할지는 각 사용처에서 직접 정의합니다.*\* ### 요소 크기 측정하기 축소할 요소를 `ScaleFeedback`으로 감쌉니다. ```tsx title="MyButton.tsx" import { ScaleFeedback } from "@seed-design/react"; function MyButton({ className, ...props }) { return ( {/* [!code highlight] */} ); } ``` ```tsx title="MyRow.tsx" ``` ```css title="MyRow.css" .my-row { display: flex; align-items: center; gap: 12px; padding: 12px 16px; } .my-row:active { background-color: var(--seed-color-bg-transparent-pressed); --seed-content-scale: var(--seed-feedback-scale); /* [!code highlight] */ } ``` `ContentScale`은 요소의 유일한 자식으로 두세요. 요소의 `display`와 flex·grid 레이아웃 값(`flex-direction`, `align-items`, `gap`, `grid-template-columns` 등)을 이어받아 콘텐츠를 배치하므로, 레이아웃과 패딩은 지금처럼 요소에 작성하면 됩니다. 축소 트랜지션도 `ContentScale`에 포함되어 있습니다. `ContentScale`은 기본으로 `span`을 렌더합니다. 콘텐츠를 배치하는 요소가 이미 있다면 `asChild`로 그 요소를 대신 사용할 수 있습니다. ```tsx
{children}
``` ## 자동으로 처리되는 것 아래 두 가지는 별도로 처리할 필요가 없습니다. - **동작 줄이기 설정**: `prefers-reduced-motion: reduce` 환경에서는 `--seed-feedback-scale`이 항상 `1`이 됩니다. - **크기를 알 수 없는 상황**: JavaScript가 실행되지 않았거나 첫 측정 전이라면 `--seed-feedback-scale`이 `1`이 됩니다. 잘못된 배율이 적용되는 대신 효과만 나타나지 않습니다. ## 알아둘 점 ### 중첩된 SEED 컴포넌트 커스텀 컴포넌트가 `Checkmark`, `Radiomark`, `Switchmark` 등을 감싸는 경우, 바깥 요소와 안쪽 요소가 함께 줄어들어 안쪽 요소가 이중으로 축소됩니다. 각 컴포넌트 문서에 끄는 방법이 안내되어 있습니다. - [Checkbox](/react/components/checkbox#scale-feedback) - [RadioGroup](/react/components/radio-group#scale-feedback) - [Switch](/react/components/switch#scale-feedback) ### `position: fixed` 자손 `scale` 값이 있는 요소는 stacking context이자 `position: fixed` 자손의 containing block이 되므로, 이 요소 안에 `position: fixed` 요소가 있다면 뷰포트가 아니라 \**이 요소를 기준으로 배치됩니다.*\* `ScaleFeedback`이 적용된 요소와 그 안의 `ContentScale`은 눌리지 않은 상태에서도 `scale: 1`을 유지하므로, 누르는 동안 자손이 따라 움직이지는 않습니다. 다만 배치 기준 자체가 뷰포트와 달라지므로 `scale`을 적용한 요소 하위에 `position: fixed` 자손이 있다면 의도한 위치에 표시되는지 확인하세요. ## 프로젝트 전체에서 끄기 배율을 `1`로 고정하는 규칙을 [`@layer`](/react/getting-started/styling/cascade-layers) 없이 추가하고 **SEED CSS보다 뒤에 로드**하세요. 배율을 읽는 모든 곳이 이 변수 하나를 거치므로 SEED 컴포넌트와 커스텀 컴포넌트가 함께 꺼집니다. ```css title="scale-feedback-off.css" .seed-scale-feedback { --seed-feedback-scale: 1; } ``` 평상시 `scale: 1`은 그대로 남으므로 [`position: fixed` 자손](#position-fixed-자손)의 배치 기준은 달라지지 않습니다.