텍스트/버튼/이미지/섹션 블록 타입 확장 및 에디터 UI 연동
This commit is contained in:
@@ -1,8 +1,8 @@
|
||||
import { createStore } from "zustand";
|
||||
import { create } from "zustand";
|
||||
|
||||
// 블록 타입 정의: 1단계에서는 텍스트 블록만 사용
|
||||
export type BlockType = "text"; // 이후 image/button/section 으로 확장 예정
|
||||
// 블록 타입 정의: 텍스트/버튼/이미지/섹션 블록
|
||||
export type BlockType = "text" | "button" | "image" | "section";
|
||||
|
||||
// 텍스트 블록 속성
|
||||
export interface TextBlockProps {
|
||||
@@ -13,11 +13,30 @@ export interface TextBlockProps {
|
||||
size: "sm" | "base" | "lg";
|
||||
}
|
||||
|
||||
// 버튼 블록 속성
|
||||
export interface ButtonBlockProps {
|
||||
label: string;
|
||||
href: string;
|
||||
// TODO: variant, size 등은 추후 확장
|
||||
}
|
||||
|
||||
// 이미지 블록 속성
|
||||
export interface ImageBlockProps {
|
||||
src: string;
|
||||
alt: string;
|
||||
}
|
||||
|
||||
// 섹션 블록 속성
|
||||
export interface SectionBlockProps {
|
||||
background: "default" | "muted" | "primary";
|
||||
paddingY: "sm" | "md" | "lg";
|
||||
}
|
||||
|
||||
// 공통 블록 모델
|
||||
export interface Block {
|
||||
id: string;
|
||||
type: BlockType;
|
||||
props: TextBlockProps;
|
||||
props: TextBlockProps | ButtonBlockProps | ImageBlockProps | SectionBlockProps;
|
||||
}
|
||||
|
||||
// 에디터 상태 인터페이스
|
||||
@@ -25,7 +44,10 @@ export interface EditorState {
|
||||
blocks: Block[];
|
||||
selectedBlockId: string | null;
|
||||
addTextBlock: () => void;
|
||||
updateBlock: (id: string, partial: Partial<TextBlockProps>) => void;
|
||||
addButtonBlock: () => void;
|
||||
addImageBlock: () => void;
|
||||
addSectionBlock: () => void;
|
||||
updateBlock: (id: string, partial: Partial<TextBlockProps & ButtonBlockProps>) => void;
|
||||
selectBlock: (id: string | null) => void;
|
||||
replaceBlocks: (blocks: Block[]) => void;
|
||||
reorderBlocks: (activeId: string, overId: string) => void;
|
||||
@@ -60,7 +82,61 @@ const createEditorState = (set: any, get: any): EditorState => ({
|
||||
}));
|
||||
},
|
||||
|
||||
// 특정 블록의 텍스트 속성을 부분 업데이트
|
||||
// 이미지 블록 추가: 기본 플레이스홀더와 함께 생성 후 선택 상태로 만든다
|
||||
addImageBlock: () => {
|
||||
const id = createId();
|
||||
const newBlock: Block = {
|
||||
id,
|
||||
type: "image",
|
||||
props: {
|
||||
src: "",
|
||||
alt: "이미지 설명",
|
||||
},
|
||||
};
|
||||
|
||||
set((state: EditorState) => ({
|
||||
blocks: [...state.blocks, newBlock],
|
||||
selectedBlockId: id,
|
||||
}));
|
||||
},
|
||||
|
||||
// 섹션 블록 추가: 배경/패딩 기본값과 함께 생성 후 선택 상태로 만든다
|
||||
addSectionBlock: () => {
|
||||
const id = createId();
|
||||
const newBlock: Block = {
|
||||
id,
|
||||
type: "section",
|
||||
props: {
|
||||
background: "default",
|
||||
paddingY: "md",
|
||||
},
|
||||
};
|
||||
|
||||
set((state: EditorState) => ({
|
||||
blocks: [...state.blocks, newBlock],
|
||||
selectedBlockId: id,
|
||||
}));
|
||||
},
|
||||
|
||||
// 버튼 블록 추가: 기본 라벨/링크와 함께 생성 후 선택 상태로 만든다
|
||||
addButtonBlock: () => {
|
||||
const id = createId();
|
||||
const newBlock: Block = {
|
||||
id,
|
||||
type: "button",
|
||||
props: {
|
||||
label: "버튼",
|
||||
href: "#",
|
||||
},
|
||||
};
|
||||
|
||||
set((state: EditorState) => ({
|
||||
blocks: [...state.blocks, newBlock],
|
||||
selectedBlockId: id,
|
||||
}));
|
||||
},
|
||||
|
||||
// 특정 블록의 속성을 부분 업데이트 (텍스트/버튼 공통 사용)
|
||||
updateBlock: (id, partial) => {
|
||||
set((state: EditorState) => ({
|
||||
blocks: state.blocks.map((block: Block) =>
|
||||
|
||||
Reference in New Issue
Block a user