Components
ReactionBar
하나 또는 여러 개를 켜는 반응 버튼 줄.
import { ReactionBar } from '@coldsurfers/surf-ui/primitives'import { ReactionBar } from '@coldsurfers/surf-ui/primitives'import { useState } from 'react'const BASE = [ { id: 'go', label: '🔥 갈래', count: 22 }, { id: 'hmm', label: '🤔 고민', count: 9 }, { id: 'pricey', label: '💸 비싸', count: 4 },]export default function Example() { const [mine, setMine] = useState<string | null>('go') const items = BASE.map((r) => ({ ...r, count: r.count + (r.id === mine ? 1 : 0) })) return ( <ReactionBar aria-label="이 공연 어때요" items={items} value={mine} onChange={setMine} style={{ width: '100%', maxWidth: 360 }} /> )}같은 폭 버튼 N개에 라벨과 개수를 붙입니다(Figma 1028:400). 기본은 하나만 켜지고, 켠 것을 다시 누르면 onChange(null) 입니다.
여러 개
multiple 이면 칸마다 따로 켜고 끕니다(🔥 갈래 + 💸 비싸 = 가고 싶은데 비싸). value 는 켠 id 배열, onChange(id, on) 은 누른 칸과 켜질지를 넘깁니다 — 서버에 칸 하나씩 켜고 끄는 요청을 보내기 좋은 모양입니다.
import { ReactionBar } from '@coldsurfers/surf-ui/primitives'import { useState } from 'react'const BASE = [ { id: 'go', label: '🔥 갈래', count: 22 }, { id: 'hmm', label: '🤔 고민', count: 9 }, { id: 'pricey', label: '💸 비싸', count: 4 },]export default function Example() { const [mine, setMine] = useState<string[]>(['go', 'pricey']) const items = BASE.map((r) => ({ ...r, count: r.count + (mine.includes(r.id) ? 1 : 0) })) return ( <ReactionBar multiple aria-label="이 공연 어때요" items={items} value={mine} onChange={(id, on) => setMine((prev) => (on ? [...prev, id] : prev.filter((k) => k !== id)))} style={{ width: '100%', maxWidth: 360 }} /> )}숫자를 올리는 일(낙관적 갱신)은 소비처가 items 로 넘깁니다. fieldset 이라 disabled 하나로 안의 버튼이 함께 꺼지고, 이름은 aria-label 로 붙입니다.
Props
Prop
Type