구분선 리사이즈 개선
This commit is contained in:
parent
8d34b73a45
commit
8789b2b864
|
|
@ -310,11 +310,26 @@ export function CanvasComponent({ component }: CanvasComponentProps) {
|
|||
const boundedWidth = Math.min(newWidth, maxWidth);
|
||||
const boundedHeight = Math.min(newHeight, maxHeight);
|
||||
|
||||
// Grid Snap 적용
|
||||
updateComponent(component.id, {
|
||||
width: snapValueToGrid(boundedWidth),
|
||||
height: snapValueToGrid(boundedHeight),
|
||||
});
|
||||
// 구분선은 방향에 따라 한 축만 조절 가능
|
||||
if (component.type === "divider") {
|
||||
if (component.orientation === "vertical") {
|
||||
// 세로 구분선: 높이만 조절
|
||||
updateComponent(component.id, {
|
||||
height: snapValueToGrid(boundedHeight),
|
||||
});
|
||||
} else {
|
||||
// 가로 구분선: 너비만 조절
|
||||
updateComponent(component.id, {
|
||||
width: snapValueToGrid(boundedWidth),
|
||||
});
|
||||
}
|
||||
} else {
|
||||
// Grid Snap 적용
|
||||
updateComponent(component.id, {
|
||||
width: snapValueToGrid(boundedWidth),
|
||||
height: snapValueToGrid(boundedHeight),
|
||||
});
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
|
|
@ -546,21 +561,23 @@ export function CanvasComponent({ component }: CanvasComponentProps) {
|
|||
);
|
||||
|
||||
case "divider":
|
||||
const lineWidth = component.lineWidth || 1;
|
||||
const lineColor = component.lineColor || "#000000";
|
||||
// 구분선 (가로: 너비만 조절, 세로: 높이만 조절)
|
||||
const dividerLineWidth = component.lineWidth || 1;
|
||||
const dividerLineColor = component.lineColor || "#000000";
|
||||
const isHorizontal = component.orientation !== "vertical";
|
||||
|
||||
return (
|
||||
<div className="flex h-full w-full items-center justify-center">
|
||||
<div className={`flex h-full w-full ${isHorizontal ? "items-center" : "justify-center"}`}>
|
||||
<div
|
||||
style={{
|
||||
width: component.orientation === "horizontal" ? "100%" : `${lineWidth}px`,
|
||||
height: component.orientation === "vertical" ? "100%" : `${lineWidth}px`,
|
||||
backgroundColor: lineColor,
|
||||
width: isHorizontal ? "100%" : `${dividerLineWidth}px`,
|
||||
height: isHorizontal ? `${dividerLineWidth}px` : "100%",
|
||||
backgroundColor: dividerLineColor,
|
||||
...(component.lineStyle === "dashed" && {
|
||||
backgroundImage: `repeating-linear-gradient(
|
||||
${component.orientation === "horizontal" ? "90deg" : "0deg"},
|
||||
${lineColor} 0px,
|
||||
${lineColor} 10px,
|
||||
${isHorizontal ? "90deg" : "0deg"},
|
||||
${dividerLineColor} 0px,
|
||||
${dividerLineColor} 10px,
|
||||
transparent 10px,
|
||||
transparent 20px
|
||||
)`,
|
||||
|
|
@ -568,19 +585,18 @@ export function CanvasComponent({ component }: CanvasComponentProps) {
|
|||
}),
|
||||
...(component.lineStyle === "dotted" && {
|
||||
backgroundImage: `repeating-linear-gradient(
|
||||
${component.orientation === "horizontal" ? "90deg" : "0deg"},
|
||||
${lineColor} 0px,
|
||||
${lineColor} 3px,
|
||||
${isHorizontal ? "90deg" : "0deg"},
|
||||
${dividerLineColor} 0px,
|
||||
${dividerLineColor} 3px,
|
||||
transparent 3px,
|
||||
transparent 10px
|
||||
)`,
|
||||
backgroundColor: "transparent",
|
||||
}),
|
||||
...(component.lineStyle === "double" && {
|
||||
boxShadow:
|
||||
component.orientation === "horizontal"
|
||||
? `0 ${lineWidth * 2}px 0 0 ${lineColor}`
|
||||
: `${lineWidth * 2}px 0 0 0 ${lineColor}`,
|
||||
boxShadow: isHorizontal
|
||||
? `0 ${dividerLineWidth * 2}px 0 0 ${dividerLineColor}`
|
||||
: `${dividerLineWidth * 2}px 0 0 0 ${dividerLineColor}`,
|
||||
}),
|
||||
}}
|
||||
/>
|
||||
|
|
@ -1093,7 +1109,7 @@ export function CanvasComponent({ component }: CanvasComponentProps) {
|
|||
return (
|
||||
<div
|
||||
ref={componentRef}
|
||||
className={`absolute p-2 shadow-sm ${isLocked ? "cursor-not-allowed opacity-80" : "cursor-move"} ${
|
||||
className={`absolute ${component.type === "divider" ? "p-0" : "p-2"} shadow-sm ${isLocked ? "cursor-not-allowed opacity-80" : "cursor-move"} ${
|
||||
isSelected
|
||||
? isLocked
|
||||
? "ring-2 ring-red-500"
|
||||
|
|
@ -1132,8 +1148,20 @@ export function CanvasComponent({ component }: CanvasComponentProps) {
|
|||
{/* 리사이즈 핸들 (선택된 경우만, 잠금 안 된 경우만) */}
|
||||
{isSelected && !isLocked && (
|
||||
<div
|
||||
className="resize-handle absolute right-0 bottom-0 h-3 w-3 cursor-se-resize rounded-full bg-blue-500"
|
||||
style={{ transform: "translate(50%, 50%)" }}
|
||||
className={`resize-handle absolute h-3 w-3 rounded-full bg-blue-500 ${
|
||||
component.type === "divider"
|
||||
? component.orientation === "vertical"
|
||||
? "bottom-0 left-1/2 cursor-s-resize" // 세로 구분선: 하단 중앙
|
||||
: "right-0 top-1/2 cursor-e-resize" // 가로 구분선: 우측 중앙
|
||||
: "right-0 bottom-0 cursor-se-resize" // 일반 컴포넌트: 우하단
|
||||
}`}
|
||||
style={{
|
||||
transform: component.type === "divider"
|
||||
? component.orientation === "vertical"
|
||||
? "translate(-50%, 50%)" // 세로 구분선
|
||||
: "translate(50%, -50%)" // 가로 구분선
|
||||
: "translate(50%, 50%)" // 일반 컴포넌트
|
||||
}}
|
||||
onMouseDown={handleResizeStart}
|
||||
/>
|
||||
)}
|
||||
|
|
|
|||
|
|
@ -58,7 +58,7 @@ export function ReportDesignerCanvas() {
|
|||
height = 150;
|
||||
} else if (item.componentType === "divider") {
|
||||
width = 300;
|
||||
height = 2;
|
||||
height = 10; // 선 두께 + 여백 (선택/드래그를 위한 최소 높이)
|
||||
} else if (item.componentType === "signature") {
|
||||
width = 120;
|
||||
height = 70;
|
||||
|
|
|
|||
|
|
@ -562,11 +562,17 @@ export function ReportDesignerRightPanel() {
|
|||
<Label className="text-xs">방향</Label>
|
||||
<Select
|
||||
value={selectedComponent.orientation || "horizontal"}
|
||||
onValueChange={(value) =>
|
||||
onValueChange={(value) => {
|
||||
// 방향 변경 시 너비/높이 스왑
|
||||
const isToVertical = value === "vertical";
|
||||
const currentWidth = selectedComponent.width;
|
||||
const currentHeight = selectedComponent.height;
|
||||
updateComponent(selectedComponent.id, {
|
||||
orientation: value as "horizontal" | "vertical",
|
||||
})
|
||||
}
|
||||
width: isToVertical ? 10 : currentWidth > 50 ? currentWidth : 300,
|
||||
height: isToVertical ? currentWidth > 50 ? currentWidth : 300 : 10,
|
||||
});
|
||||
}}
|
||||
>
|
||||
<SelectTrigger className="h-8">
|
||||
<SelectValue />
|
||||
|
|
|
|||
Loading…
Reference in New Issue