Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
100 commits
Select commit Hold shift + click to select a range
e41c7cc
style: 추가된 컬러 토큰 구현
woneeeee Jul 1, 2026
7f38d09
feat: 마이페이지용 아이콘 에셋 추가
woneeeee Jul 1, 2026
4e95755
fix: 버튼 primarySoft variants 추가 및 disabled 스타일 보정
woneeeee Jul 1, 2026
93f3eee
fix: 아바타 스타일 및 표시 로직 보정
woneeeee Jul 1, 2026
bf28551
refactor: 게시판 카테고리 선택 미 사용하는 변수 삭제
woneeeee Jul 1, 2026
1e8bfbf
feat: 마이페이지 공통 레이아웃 구현
woneeeee Jul 1, 2026
d6ff651
feat: 마이페이지 공통 네비게이션 구현
woneeeee Jul 1, 2026
412fed0
feat: 마이페이지 활동정보 페이지 추가
woneeeee Jul 1, 2026
730a471
feat: 마이페이지 내가 쓴 글 페이지 추가
woneeeee Jul 1, 2026
9e423a4
feat: 마이페이지 출석 세션 페이지 추가
woneeeee Jul 1, 2026
ff3e834
feat: 마이페이지 서비스 설정 페이지 추가
woneeeee Jul 1, 2026
0ab980f
feat: 마이페이지 프로필 관리 페이지 추가
woneeeee Jul 1, 2026
9707f25
feat: 마이페이지 카드 컴포넌트 구현
woneeeee Jul 1, 2026
67f4a3a
feat: 마이페이지 프로필 선택 모달 구현
woneeeee Jul 1, 2026
7e5e22b
feat: 프로필 추가 모달 구현
woneeeee Jul 1, 2026
9eeab5a
feat: 프로필 추가 헤더 모달 컴포넌트 분리
woneeeee Jul 1, 2026
5adb936
feat: 프로필 추가 모달 step 1 컴포넌트 분리
woneeeee Jul 1, 2026
ea34f0f
feat: 프로필 추가 모달 step 2 컴포넌트 분리
woneeeee Jul 1, 2026
83f94c8
fix: CharacterCountRow 컴포넌트 분리
woneeeee Jul 1, 2026
0ab3d1e
feat: CharacterCountRow 컴포넌트 구현
woneeeee Jul 1, 2026
064b6c9
fix: 내가 쓴 글 목록에서 게시글 재사용 구조 추가
woneeeee Jul 1, 2026
bf25670
feat: 프로필 수정 모달 구현
woneeeee Jul 1, 2026
430de43
feat: 프로필 배경 이미지 편집 컴포넌트 추가
woneeeee Jul 1, 2026
5b233e0
feat: 프로필 이미지 편집 컴포넌트 추가
woneeeee Jul 1, 2026
ea9b49e
fix: 개인정보 수정 페이지에서 안쓰는 컴포넌트 제거
woneeeee Jul 1, 2026
26d5a8c
remove: 개인정보 수정 필드에서 이름, 소개글 및 CharacterCountRow 컴포넌트 제거
woneeeee Jul 1, 2026
a2ffe88
feat: 화면 모드 선택 이미지 추가
woneeeee Jul 1, 2026
cc57869
feat: 마이페이지 활동 동아리 컴포넌트 추가
woneeeee Jul 1, 2026
dd1baa5
feat: 화면 모드 선택 모달 구현
woneeeee Jul 1, 2026
05026b1
feat: 탈퇴 확인 모달 컴포넌트 분리
woneeeee Jul 1, 2026
053f330
feat: 로그아웃 확인 모달 컴포넌트 분리
woneeeee Jul 1, 2026
21316a7
feat: 활동정보 스켈레톤 추가
woneeeee Jul 1, 2026
6bda710
feat: 마이페이지 스켈레톤 최신 화면에 맞게 수정
woneeeee Jul 1, 2026
b889a55
feat: 마이페이지 기존 콘텐츠 구조 정리
woneeeee Jul 1, 2026
cdb4709
feat: 프로필 관리 스켈레톤 추가
woneeeee Jul 1, 2026
5912780
feat: 출석 세션 스켈레톤 추가
woneeeee Jul 1, 2026
7bc9197
feat: 서비스 설정 스켈레톤 추가
woneeeee Jul 1, 2026
99cc6b6
feat: 마이페이지 스켈레톤 export 정리
woneeeee Jul 1, 2026
f964045
refactor: 출석 세션 날짜 포맷 유틸 분리
woneeeee Jul 1, 2026
a7a7991
feat: 활동 동아리 카드 UI 구현
woneeeee Jul 1, 2026
b2f715d
feat: 새로운 프로필 관련 데이터 타입 분리
woneeeee Jul 1, 2026
77b4811
feat: 서비스 설정용 고객지원 리스트 컴포넌트 스타일 수정
woneeeee Jul 1, 2026
6f83c34
feat: 서비스 설정용 고객지원 리스트 UI 구현
woneeeee Jul 1, 2026
6111ef2
feat: 설정 화면에 공용 확인 모달 적용
woneeeee Jul 1, 2026
8c11d7e
fix: 프로필 수정 스켈레톤을 최신 편집 화면에 맞게 수정
woneeeee Jul 1, 2026
6f63160
fix: 기수 설정 모달 제목 수정
woneeeee Jul 1, 2026
3d43eb6
fix: 마이페이지 개인정보수정 모달 미사용 컴포넌트 제거
woneeeee Jul 1, 2026
3035865
refactor: 프로필 수정 화면에 이미지 편집 컴포넌트 적용
woneeeee Jul 1, 2026
b5c791b
feat: 화면 모드 선택 공용 셀렉터 구현
woneeeee Jul 1, 2026
7e371e9
feat: 모바일 전용 화면 모드 페이지 구현
woneeeee Jul 1, 2026
41ff31e
feat: 서비스 설정에서 모바일 화면 모드 페이지 분기 처리
woneeeee Jul 1, 2026
5160c70
refactor: 화면 모드 모달에 공용 셀렉터 적용
woneeeee Jul 1, 2026
efa905f
fix: 마이페이지 네비게이션에 화면 모드 하위 경로 활성화 처리
woneeeee Jul 1, 2026
0cc7efc
refactor: 마이페이지 컴포넌트 export 정리
woneeeee Jul 1, 2026
6f0354d
refactor: 프로필 수정 모달 모바일 반응형 구현
woneeeee Jul 1, 2026
288aea3
fix: 서비스 설정 복사하기 버튼 공통 컴포넌트로 교체
woneeeee Jul 1, 2026
3570c3a
fix: 마이페이지 전체 레이아웃 반응형에 맞게 수정
woneeeee Jul 1, 2026
867795d
fix: 활동 동아리 카드 모바일 가로 스크롤 레이아웃 적용
woneeeee Jul 1, 2026
08a39cf
refactor: 활동정보 반응형 카드 열 계산 로직 훅으로 분리
woneeeee Jul 1, 2026
01b8779
fix: 활동정보 UI 확인용 목업 제거
woneeeee Jul 1, 2026
5e1a00f
feat: 클럽 정보 카드 컴포넌트에서 동아리 입장하기 버튼 추가
woneeeee Jul 1, 2026
96d130d
fix: 서비스 설정 인포 관련 타이포 수정
woneeeee Jul 1, 2026
597711a
fix: 동아리 탈퇴 드롭다운 아이콘 색상 수정
woneeeee Jul 1, 2026
224a4dc
feat: 마이페이지 모바일 반응형 구현
woneeeee Jul 1, 2026
6c08078
feat: 마이페이지 프로필 컴포넌트 반응형 구현
woneeeee Jul 1, 2026
255c609
feat: 마이페이지 내가 쓴 글 반응형 구현
woneeeee Jul 1, 2026
bf95af4
feat: 마이페이지 출석 세션 반응형 구현
woneeeee Jul 1, 2026
f8a4791
feat: 마이페이지 프로필 카드 반응형 구현
woneeeee Jul 1, 2026
3d7e2f9
feat: 마이페이지 프로필 관리 컴포넌트 반응형 구현
woneeeee Jul 1, 2026
56cdc89
Merge branch 'develop' into feat/WTH-421-마이페이지-개선뷰-UI-구현
woneeeee Jul 1, 2026
ebdd0ea
fix: 모바일에서만 보이는 화면에서 헤더에 패딩값 추가
woneeeee Jul 2, 2026
1f6c8c3
fix: 사용 중인 프로필 컴포넌트에서 프로필 관리 컴포넌트 태블릿 뷰 이상에서 보이도록 수정
woneeeee Jul 2, 2026
d56c1e4
feat: 마이페이지에서 기존 헤더 안보이는 경로 분리 및 적용
woneeeee Jul 2, 2026
cb6ea3e
feat: 프로필 수정 모바일 페이지 구현
woneeeee Jul 2, 2026
fdcc68c
feat: 프로필 수정 폼 컨텐츠 컴포넌트 분리
woneeeee Jul 2, 2026
25ee0b0
feat: 프로필 수정 모달 분리한 컴포넌트 적용 및 훅 분리
woneeeee Jul 2, 2026
c416d27
feat: 프로필 추가하기 모바일 페이지 구현
woneeeee Jul 2, 2026
fc9af0b
fix: 폼 필드에서 label 선택사항으로 변경
woneeeee Jul 2, 2026
72aaa81
fix: 프로필 추가 모달에서 훅 분리
woneeeee Jul 2, 2026
08748f7
feat: 프로필 삭제 dialog 컴포넌트 분리
woneeeee Jul 2, 2026
405fd16
feat: 프로필 수정 폼 훅 분리
woneeeee Jul 2, 2026
8042385
feat: 프로필 관리 페이지에서 모바일과 태블릿 이상 페이지 분리
woneeeee Jul 2, 2026
65a4118
feat: 마이페이지 훅 export 정리
woneeeee Jul 2, 2026
800d606
fix: 훅 import문 경로 수정
woneeeee Jul 2, 2026
cc9515e
feat: 마이페이지 텍스트 필드 최대 길이 상수 분리
woneeeee Jul 2, 2026
e7745bd
feat: 프로필 추가 2단계 모바일 페이지에서 버튼 하단으로 이동
woneeeee Jul 2, 2026
9462cfd
feat: 프로필 추가 1단계에서 버튼 하단으로 이동 및 텍스트 필드 최대 높이 상수 적용
woneeeee Jul 2, 2026
1e59f4d
feat: 프로필 수정 페이지 모바일과 태블릿 이상 페이지 뷰 분리
woneeeee Jul 2, 2026
34673b6
fix: 마이페이지 네비에서 subPath 상수 분리
woneeeee Jul 2, 2026
370938e
feat: 추가된 마이페이지 컴포넌트 export문 정리
woneeeee Jul 2, 2026
b0fd980
refactor: 고객지원 리스트 액션 렌더링 분기 함수로 정리
woneeeee Jul 6, 2026
76bb576
refactor: 프로필 섹션 활동 버튼 목록 map 렌더링으로 정리
woneeeee Jul 6, 2026
7d22fb6
refactor: 프로필 이미지 미리보기 로직 useImagePreview 훅으로 분리
woneeeee Jul 6, 2026
f9ee955
refactor: 테마 모드 타입 공통 타입으로 분리
woneeeee Jul 6, 2026
f2850fa
fix: 프로필 관리 버튼 호버 색상 추가
woneeeee Jul 6, 2026
76a7abd
fix: 동아리 탈퇴 드롭다운 함수명 변경
woneeeee Jul 6, 2026
df93ac7
fix: 분리한 테마 타입 import
woneeeee Jul 6, 2026
5e38b11
fix: button 태그에 커서 포인터 추가
woneeeee Jul 6, 2026
8a2ab7e
Merge branch 'develop' into feat/WTH-421-마이페이지-개선뷰-UI-구현
woneeeee Jul 6, 2026
133c931
fix: 코드리뷰 수정사항 반영
woneeeee Jul 6, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions src/app/(private)/[clubId]/(main)/mypage/activity/loading.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
import { MyPageActivitySkeleton } from '@/components/mypage/skeleton';

export default function Loading() {
return <MyPageActivitySkeleton />;
}
7 changes: 7 additions & 0 deletions src/app/(private)/[clubId]/(main)/mypage/activity/page.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
import { MyPageActivityContent } from '@/components/mypage/MyPageActivityContent';

export const dynamic = 'force-dynamic';

export default function MyPageActivityPage() {
return <MyPageActivityContent />;
}
16 changes: 16 additions & 0 deletions src/app/(private)/[clubId]/(main)/mypage/layout.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
import { MyPageNav } from '@/components/mypage/MyPageNav';

interface MyPageLayoutProps {
children: React.ReactNode;
}

export default function MyPageLayout({ children }: MyPageLayoutProps) {
return (
<div className="desktop:px-16 tablet:pt-450 mx-auto flex w-full items-start gap-500 px-450 pb-[80px]">
<aside className="tablet:flex hidden shrink-0">
<MyPageNav />
</aside>
<div className="flex min-w-0 flex-1">{children}</div>
</div>
);
}
7 changes: 7 additions & 0 deletions src/app/(private)/[clubId]/(main)/mypage/posts/page.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
import { MyPagePostsContent } from '@/components/mypage/MyPagePostsContent';

export const dynamic = 'force-dynamic';

export default function MyPagePostsPage() {
return <MyPagePostsContent />;
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
import { EditProfilePageContent } from '@/components/mypage/EditProfilePageContent';

export const dynamic = 'force-dynamic';

export default function EditProfilePage() {
return <EditProfilePageContent />;
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
import { AddProfilePageContent } from '@/components/mypage/AddProfilePageContent';

export const dynamic = 'force-dynamic';

export default function AddProfilePage() {
return <AddProfilePageContent />;
}
5 changes: 5 additions & 0 deletions src/app/(private)/[clubId]/(main)/mypage/profiles/loading.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
import { ProfileManagementSkeleton } from '@/components/mypage/skeleton/ProfileManagementSkeleton';

export default function Loading() {
return <ProfileManagementSkeleton />;
}
7 changes: 7 additions & 0 deletions src/app/(private)/[clubId]/(main)/mypage/profiles/page.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
import { ProfileManagementContent } from '@/components/mypage';

export const dynamic = 'force-dynamic';

export default function ProfilesPage() {
return <ProfileManagementContent />;
}
5 changes: 5 additions & 0 deletions src/app/(private)/[clubId]/(main)/mypage/sessions/loading.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
import { MyPageSessionsSkeleton } from '@/components/mypage/skeleton/MyPageSessionsSkeleton';

export default function Loading() {
return <MyPageSessionsSkeleton />;
}
25 changes: 25 additions & 0 deletions src/app/(private)/[clubId]/(main)/mypage/sessions/page.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
import { MyPageSessionsContent } from '@/components/mypage/MyPageSessionsContent';
import { attendanceServerApi } from '@/lib/apis/attendance.server';
import type { AttendanceSummary } from '@/types/attendance';

interface MyPageSessionsPageProps {
params: Promise<{ clubId: string }>;
}

export const dynamic = 'force-dynamic';

export default async function MyPageSessionsPage({ params }: MyPageSessionsPageProps) {
const { clubId } = await params;

let summary: AttendanceSummary | undefined;
let errorMessage: string | undefined;

try {
const response = await attendanceServerApi.getDetail(clubId);
summary = response.data;
} catch {
errorMessage = '출석 기록을 불러오지 못했습니다.';
}

return <MyPageSessionsContent summary={summary} errorMessage={errorMessage} />;
}
5 changes: 5 additions & 0 deletions src/app/(private)/[clubId]/(main)/mypage/settings/loading.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
import { MyPageSettingsSkeleton } from '@/components/mypage/skeleton';

export default function Loading() {
return <MyPageSettingsSkeleton />;
}
7 changes: 7 additions & 0 deletions src/app/(private)/[clubId]/(main)/mypage/settings/page.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
import { MyPageSettingsContent } from '@/components/mypage/MyPageSettingsContent';

export const dynamic = 'force-dynamic';

export default function MyPageSettingsPage() {
return <MyPageSettingsContent />;
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
import { ThemeModePageContent } from '@/components/mypage/ThemeModePageContent';

export const dynamic = 'force-dynamic';

export default function ThemeModePage() {
return <ThemeModePageContent />;
}
25 changes: 24 additions & 1 deletion src/app/globals.css
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,10 @@
--pink-700: #8e448a;
--pink-900: #280526;

--opacity-60: #ffffff99;
--opacity-100: #00c8aa1f;
--opacity-200: #00c8aa4d;

--background: var(--neutral-200);
--background-2: var(--neutral-300);
--foreground: var(--text-normal);
Expand All @@ -66,8 +70,9 @@
--text-alternative: var(--neutral-600);
--text-disabled: var(--neutral-500);
--text-inverse: var(--neutral-0);
--container-code: var(--neutral-400);
--text-brand: var(--primary-500);

--container-code: var(--neutral-400);
--code-keyword: #d73a49;
--code-string: #032f62;
--code-comment: #6a737d;
Expand All @@ -85,11 +90,15 @@
--container-secondary: var(--secondary-500);
--container-secondary-interaction: var(--secondary-700);
--container-secondary-alternative: var(--secondary-100);
--container-opacity: var(--opacity-60);

--button-neutral: var(--neutral-400);
--button-neutral-interaction: var(--neutral-500);
--button-primary: var(--primary-500);
--button-primary-interaction: var(--primary-600);
--button-primary-subtle: var(--opacity-100);
--button-primary-subtle-interaction: var(--opacity-200);
--button-disabled: var(--neutral-400);

--icon-normal: var(--neutral-800);
--icon-strong: var(--neutral-900);
Expand Down Expand Up @@ -279,6 +288,15 @@
--pink-700: #f3a7f0;
--pink-900: #faddf9;

--opacity-60: #1e202199;
--opacity-100: #355d5a80;
--opacity-200: #00c8aa66;

--button-primary-subtle: var(--opacity-100);
--button-primary-subtle-interaction: var(--opacity-200);

--container-opacity: var(--opacity-60);

--card: oklch(0.205 0 0);
--card-foreground: oklch(0.985 0 0);
--popover: oklch(0.205 0 0);
Expand Down Expand Up @@ -338,6 +356,11 @@
--color-button-neutral-interaction: var(--button-neutral-interaction);
--color-button-primary: var(--button-primary);
--color-button-primary-interaction: var(--button-primary-interaction);
--color-button-primary-subtle: var(--button-primary-subtle);
--color-button-primary-subtle-interaction: var(--button-primary-subtle-interaction);
--color-button-disabled: var(--button-disabled);

--color-container-opacity: var(--container-opacity);

--color-icon-normal: var(--icon-normal);
--color-icon-strong: var(--icon-strong);
Expand Down
3 changes: 3 additions & 0 deletions src/assets/icons/add_round.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions src/assets/icons/calendar.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
5 changes: 5 additions & 0 deletions src/assets/icons/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -64,3 +64,8 @@ export { default as RushIcon } from './rush.svg';
export { default as QuestionCircleIcon } from './question_circle.svg';
export { default as DotIcon } from './dot.svg';
export { default as EmptyListIcon } from './empty_list.svg';
export { default as PhoneIcon } from './phone.svg';
export { default as MailIcon } from './mail.svg';
export { default as SettingIcon } from './setting.svg';
export { default as AddRoundIcon } from './add_round.svg';
export { default as CalendarIcon } from './calendar.svg';
3 changes: 3 additions & 0 deletions src/assets/icons/mail.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions src/assets/icons/phone.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions src/assets/icons/setting.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added src/assets/image/theme/theme_auto.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added src/assets/image/theme/theme_dark.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added src/assets/image/theme/theme_light.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
2 changes: 1 addition & 1 deletion src/components/auth/hub/FormFieldWrapper.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ function FieldError({ message }: { message?: string }) {
}

interface FormFieldWrapperProps {
label: string;
label?: string;
error?: string;
children: React.ReactNode;
}
Expand Down
18 changes: 14 additions & 4 deletions src/components/board/BoardContent.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -24,9 +24,15 @@ function toDisplayImages(files: FileItem[]) {

interface BoardContentProps {
boardId: number | null;
onlyCurrentUser?: boolean;
emptyMessage?: string;
}

function BoardContent({ boardId }: BoardContentProps) {
function BoardContent({
boardId,
onlyCurrentUser = false,
emptyMessage = '아직 게시글이 없습니다.',
}: BoardContentProps) {
const router = useRouter();
const { clubId } = useParams<{ clubId: string }>();
const currentUserId = useUserId();
Expand All @@ -43,6 +49,10 @@ function BoardContent({ boardId }: BoardContentProps) {
const { ref: sentinelRef, isIntersecting } = useIntersectionObserver({
rootMargin: '200px',
});
const filteredPosts =
onlyCurrentUser && currentUserId != null
? posts?.filter((post) => post.author.id === currentUserId)
: posts;

useEffect(() => {
if (!isError || !error) return;
Expand Down Expand Up @@ -72,16 +82,16 @@ function BoardContent({ boardId }: BoardContentProps) {
</main>
);

if (!posts || posts.length === 0)
if (!filteredPosts || filteredPosts.length === 0)
return (
<main className="flex min-w-0 flex-1 flex-col items-center justify-center py-800">
<p className="typo-body1 text-text-alternative">아직 게시글이 없습니다.</p>
<p className="typo-body1 text-text-alternative">{emptyMessage}</p>
</main>
);

return (
<main className="flex min-w-0 flex-1 flex-col gap-400">
{posts.map((post) => (
{filteredPosts.map((post) => (
<PostCard.Root key={post.id} className="relative">
<PostCard.Header>
<PostCard.Author
Expand Down
4 changes: 0 additions & 4 deletions src/components/board/CategorySelector.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,6 @@ import {
Icon,
} from '@/components/ui';
import { ChannelList } from '@/components/board/ChannelList';
import { useClubName } from '@/stores';
import type { BoardNavItem } from '@/types/board';

interface CategorySelectorProps {
Expand All @@ -38,9 +37,6 @@ function CategorySelector({
}: CategorySelectorProps) {
const [open, setOpen] = useState(false);
const activeItem = items.find((item) => item.id === activeId);
const clubName = useClubName();

const boardName = clubName ?? '게시판';
const channelName = activeItem?.label ?? '';

// 아이템 선택 후 드롭다운 닫기
Expand Down
Loading
Loading