feat: Refactor Roof2 component to remove unused imports and optimize code

This commit is contained in:
yoosangwook 2024-07-17 18:42:45 +09:00
parent fdd52deec8
commit edfa72bf48
3 changed files with 166 additions and 199 deletions

View File

@ -1,6 +1,5 @@
'use client' 'use client'
import Hero from '@/components/Hero'
import Roof2 from '@/components/Roof2' import Roof2 from '@/components/Roof2'
import { textState } from '@/store/canvasAtom' import { textState } from '@/store/canvasAtom'
import { useEffect } from 'react' import { useEffect } from 'react'

View File

@ -7,21 +7,11 @@ import QPolygon from '@/components/fabric/QPolygon'
import RangeSlider from './ui/RangeSlider' import RangeSlider from './ui/RangeSlider'
import { useRecoilState, useRecoilValue } from 'recoil' import { useRecoilState, useRecoilValue } from 'recoil'
import { import { canvasSizeState, fontSizeState, sortedPolygonArray } from '@/store/canvasAtom'
canvasSizeState,
fontSizeState,
sortedPolygonArray,
} from '@/store/canvasAtom'
import { QLine } from '@/components/fabric/QLine' import { QLine } from '@/components/fabric/QLine'
export default function Roof2() { export default function Roof2() {
const { const { canvas, handleRedo, handleUndo, setCanvasBackgroundWithDots, saveImage } = useCanvas('canvas')
canvas,
handleRedo,
handleUndo,
setCanvasBackgroundWithDots,
saveImage,
} = useCanvas('canvas')
//canvas //canvas
const [canvasSize, setCanvasSize] = useRecoilState(canvasSizeState) const [canvasSize, setCanvasSize] = useRecoilState(canvasSizeState)
@ -39,18 +29,8 @@ export default function Roof2() {
const [showControl, setShowControl] = useState(false) const [showControl, setShowControl] = useState(false)
const { const { mode, changeMode, handleClear, fillCellInPolygon, zoomIn, zoomOut, zoom, togglePolygonLine, handleOuterlinesTest2, applyTemplateB } =
mode, useMode()
changeMode,
handleClear,
fillCellInPolygon,
zoomIn,
zoomOut,
zoom,
togglePolygonLine,
handleOuterlinesTest2,
applyTemplateB,
} = useMode()
useEffect(() => { useEffect(() => {
if (!canvas) { if (!canvas) {
@ -251,11 +231,7 @@ export default function Roof2() {
{canvas && ( {canvas && (
<> <>
<div className=" my-8 w-full text:pretty"> <div className=" my-8 w-full text:pretty">
<Button <Button className="m-1 p-2" color={`${mode === Mode.DEFAULT ? 'primary' : 'default'}`} onClick={fillCellInPolygon}>
className="m-1 p-2"
color={`${mode === Mode.DEFAULT ? 'primary' : 'default'}`}
onClick={fillCellInPolygon}
>
모드 DEFAULT 모드 DEFAULT
</Button> </Button>
<Button <Button
@ -265,39 +241,19 @@ export default function Roof2() {
> >
기준선 긋기 모드 기준선 긋기 모드
</Button> </Button>
<Button <Button className="m-1 p-2" color={`${mode === Mode.EDIT ? 'primary' : 'default'}`} onClick={() => changeMode(canvas, Mode.EDIT)}>
className="m-1 p-2"
color={`${mode === Mode.EDIT ? 'primary' : 'default'}`}
onClick={() => changeMode(canvas, Mode.EDIT)}
>
에디팅모드 에디팅모드
</Button> </Button>
<Button <Button className="m-1 p-2" color={`${mode === Mode.TEMPLATE ? 'primary' : 'default'}`} onClick={() => changeMode(canvas, Mode.TEMPLATE)}>
className="m-1 p-2"
color={`${mode === Mode.TEMPLATE ? 'primary' : 'default'}`}
onClick={() => changeMode(canvas, Mode.TEMPLATE)}
>
템플릿(기둥) 템플릿(기둥)
</Button> </Button>
<Button <Button className="m-1 p-2" color={`${mode === Mode.TEMPLATE ? 'primary' : 'default'}`} onClick={() => changeMode(canvas, Mode.PATTERNA)}>
className="m-1 p-2"
color={`${mode === Mode.TEMPLATE ? 'primary' : 'default'}`}
onClick={() => changeMode(canvas, Mode.PATTERNA)}
>
템플릿(A 패턴) 템플릿(A 패턴)
</Button> </Button>
<Button <Button className="m-1 p-2" color={`${mode === Mode.TEMPLATE ? 'primary' : 'default'}`} onClick={() => changeMode(canvas, Mode.PATTERNB)}>
className="m-1 p-2"
color={`${mode === Mode.TEMPLATE ? 'primary' : 'default'}`}
onClick={() => changeMode(canvas, Mode.PATTERNB)}
>
템플릿(B 패턴) 템플릿(B 패턴)
</Button> </Button>
<Button <Button className="m-1 p-2" color={`${mode === Mode.TEXTBOX ? 'primary' : 'default'}`} onClick={() => changeMode(canvas, Mode.TEXTBOX)}>
className="m-1 p-2"
color={`${mode === Mode.TEXTBOX ? 'primary' : 'default'}`}
onClick={() => changeMode(canvas, Mode.TEXTBOX)}
>
텍스트박스 모드 텍스트박스 모드
</Button> </Button>
<Button <Button
@ -363,30 +319,13 @@ export default function Roof2() {
<Button className="m-1 p-2" onClick={PolygonToLine}> <Button className="m-1 p-2" onClick={PolygonToLine}>
PolygonToLine PolygonToLine
</Button> </Button>
<Button <Button className="m-1 p-2" color={`${showControl ? 'primary' : 'default'}`} onClick={handleShowController}>
className="m-1 p-2"
color={`${showControl ? 'primary' : 'default'}`}
onClick={handleShowController}
>
canvas 컨트롤러 {`${showControl ? '숨기기' : '보이기'}`} canvas 컨트롤러 {`${showControl ? '숨기기' : '보이기'}`}
</Button> </Button>
</div> </div>
<div <div className={showControl ? `flex justify-center flex-col items-center` : `hidden`}>
className={
showControl
? `flex justify-center flex-col items-center`
: `hidden`
}
>
<div className="m-2 p-2 w-80"> <div className="m-2 p-2 w-80">
<RangeSlider <RangeSlider title={`각도${angle}`} initValue={angle} min="0" step="1" max="360" onchange={setAngle} />
title={`각도${angle}`}
initValue={angle}
min="0"
step="1"
max="360"
onchange={setAngle}
/>
</div> </div>
<div className="m-2 p-2 w-80"> <div className="m-2 p-2 w-80">
<RangeSlider <RangeSlider
@ -409,11 +348,7 @@ export default function Roof2() {
/> />
</div> </div>
<div className="m-2 p-2 w-80"> <div className="m-2 p-2 w-80">
<RangeSlider <RangeSlider title={`글자 크기${fontSize}`} initValue={fontSize} onchange={setFontSize} />
title={`글자 크기${fontSize}`}
initValue={fontSize}
onchange={setFontSize}
/>
</div> </div>
</div> </div>
</> </>

View File

@ -1,20 +1,9 @@
import { useEffect, useRef, useState } from 'react' import { useEffect, useRef, useState } from 'react'
import QRect from '@/components/fabric/QRect' import QRect from '@/components/fabric/QRect'
import QPolygon from '@/components/fabric/QPolygon' import QPolygon from '@/components/fabric/QPolygon'
import { import { getStartIndex, rearrangeArray, findTopTwoIndexesByDistance, getDirection, getCenterPoint } from '@/util/canvas-util'
getStartIndex,
rearrangeArray,
findTopTwoIndexesByDistance,
getDirection,
getCenterPoint,
} from '@/util/canvas-util'
import { useRecoilState, useSetRecoilState } from 'recoil' import { useRecoilState, useSetRecoilState } from 'recoil'
import { import { fontSizeState, roofState, sortedPolygonArray, wallState } from '@/store/canvasAtom'
fontSizeState,
roofState,
sortedPolygonArray,
wallState,
} from '@/store/canvasAtom'
import { QLine } from '@/components/fabric/QLine' import { QLine } from '@/components/fabric/QLine'
export const Mode = { export const Mode = {
@ -101,8 +90,7 @@ export function useMode() {
if (isNaN(length) || length === 0) { if (isNaN(length) || length === 0) {
//마지막 추가 된 points 제거합니다. //마지막 추가 된 points 제거합니다.
const lastPoint = const lastPoint = historyPoints.current[historyPoints.current.length - 1]
historyPoints.current[historyPoints.current.length - 1]
canvas?.remove(lastPoint) canvas?.remove(lastPoint)
@ -134,12 +122,7 @@ export function useMode() {
} }
const line = new QLine( const line = new QLine(
[ [points.current[0].left, points.current[0].top, points.current[0].left + scaledVector.x, points.current[0].top + scaledVector.y],
points.current[0].left,
points.current[0].top,
points.current[0].left + scaledVector.x,
points.current[0].top + scaledVector.y,
],
{ {
stroke: 'black', stroke: 'black',
strokeWidth: 2, strokeWidth: 2,
@ -180,27 +163,20 @@ export function useMode() {
} }
const pushHistoryLine = (line) => { const pushHistoryLine = (line) => {
if ( if (historyLines.current.length > 0 && historyLines.current[historyLines.current.length - 1].direction === line.direction) {
historyLines.current.length > 0 &&
historyLines.current[historyLines.current.length - 1].direction ===
line.direction
) {
// 같은 방향의 선이 두 번 연속으로 그려지면 이전 선을 제거하고, 새로운 선과 merge한다. // 같은 방향의 선이 두 번 연속으로 그려지면 이전 선을 제거하고, 새로운 선과 merge한다.
const lastLine = historyLines.current.pop() const lastLine = historyLines.current.pop()
canvas?.remove(lastLine) canvas?.remove(lastLine)
const mergedLine = new QLine( const mergedLine = new QLine([lastLine.x1, lastLine.y1, line.x2, line.y2], {
[lastLine.x1, lastLine.y1, line.x2, line.y2],
{
stroke: 'black', stroke: 'black',
strokeWidth: 2, strokeWidth: 2,
selectable: false, selectable: false,
viewLengthText: true, viewLengthText: true,
direction: lastLine.direction, direction: lastLine.direction,
fontSize: fontSize, fontSize: fontSize,
}, })
)
historyLines.current.push(mergedLine) historyLines.current.push(mergedLine)
canvas?.add(mergedLine) canvas?.add(mergedLine)
} else { } else {
@ -460,9 +436,7 @@ export function useMode() {
const newOuterlines = [] const newOuterlines = []
for (let i = 0; i < historyLines.current.length; i++) { for (let i = 0; i < historyLines.current.length; i++) {
const next = historyLines.current[i + 1] const next = historyLines.current[i + 1]
const prev = const prev = historyLines.current[i - 1] ?? historyLines.current[historyLines.current.length - 1]
historyLines.current[i - 1] ??
historyLines.current[historyLines.current.length - 1]
if (next) { if (next) {
if (next.direction === 'right') { if (next.direction === 'right') {
// 다름 라인이 오른쪽으로 이동 // 다름 라인이 오른쪽으로 이동
@ -797,9 +771,7 @@ export function useMode() {
} }
// 평균 법선 벡터를 단위 벡터로 정규화 // 평균 법선 벡터를 단위 벡터로 정규화
var lengthNormal = Math.sqrt( var lengthNormal = Math.sqrt(averageNormal.x * averageNormal.x + averageNormal.y * averageNormal.y)
averageNormal.x * averageNormal.x + averageNormal.y * averageNormal.y,
)
var unitNormal = { var unitNormal = {
x: averageNormal.x / lengthNormal, x: averageNormal.x / lengthNormal,
y: averageNormal.y / lengthNormal, y: averageNormal.y / lengthNormal,
@ -867,9 +839,7 @@ export function useMode() {
} }
// 평균 법선 벡터를 단위 벡터로 정규화 // 평균 법선 벡터를 단위 벡터로 정규화
const lengthNormal = Math.sqrt( const lengthNormal = Math.sqrt(averageNormal.x * averageNormal.x + averageNormal.y * averageNormal.y)
averageNormal.x * averageNormal.x + averageNormal.y * averageNormal.y,
)
const unitNormal = { const unitNormal = {
x: averageNormal.x / lengthNormal, x: averageNormal.x / lengthNormal,
y: averageNormal.y / lengthNormal, y: averageNormal.y / lengthNormal,
@ -933,64 +903,144 @@ export function useMode() {
const applyTemplateB = () => { const applyTemplateB = () => {
changeMode(canvas, Mode.EDIT) changeMode(canvas, Mode.EDIT)
const polygon = drawWallPolygon() const polygon = drawWallPolygon()
handleOuterLineTemplateB(polygon) console.log('polygon', polygon)
const params = {
eaves: 50,
edge: 20,
polygon,
}
handleInnerLineColor(polygon)
handleOuterLineTemplateB(params)
} }
const handleOuterLineTemplateB = (polygon) => { const handleInnerLineColor = (polygon) => {
polygon.lines.forEach((line, index) => {
if (index % 2 === 0) {
line.set('stroke', 'rgb(0, 220, 221)')
} else {
line.set('stroke', 'rgb(0, 224, 61)')
}
const overLine = new QLine([line.x1, line.y1, line.x2, line.y2], {
stroke: line.stroke,
strokeWidth: 2,
selectable: false,
fontSize: fontSize,
})
canvas.add(overLine)
})
canvas.renderAll()
}
const handleOuterLineTemplateB = (params) => {
const { eaves, edge, polygon } = params
polygon.points.forEach((point, index) => { polygon.points.forEach((point, index) => {
let x2 = let x2 = index === polygon.points.length - 1 ? polygon.points[0].x : polygon.points[index + 1].x
index === polygon.points.length - 1 let y2 = index === polygon.points.length - 1 ? polygon.points[0].y : polygon.points[index + 1].y
? polygon.points[0].x
: polygon.points[index + 1].x
let y2 =
index === polygon.points.length - 1
? polygon.points[0].y
: polygon.points[index + 1].y
let x1 = point.x let x1 = point.x
let y1 = point.y let y1 = point.y
if (index % 2 === 0) { if (index % 2 === 0) {
if (polygon.lines[index].direction === 'bottom') { if (polygon.lines[index].direction === 'bottom') {
y1 = y1 - 50 y1 = y1 - eaves
y2 = y2 + 50 y2 = y2 + eaves
x1 = x1 - 20 x1 = x1 - edge
x2 = x2 - 20 x2 = x2 - edge
} else { } else {
y1 = y1 + 50 y1 = y1 + eaves
y2 = y2 - 50 y2 = y2 - eaves
x1 = x1 + 20 x1 = x1 + edge
x2 = x2 + 20 x2 = x2 + edge
} }
} else { } else {
if (polygon.lines[index].direction === 'right') { if (polygon.lines[index].direction === 'right') {
x1 = x1 - 20 x1 = x1 - edge
x2 = x2 + 20 x2 = x2 + edge
y1 = y1 + 50 y1 = y1 + eaves
y2 = y2 + 50 y2 = y2 + eaves
} else { } else {
x1 = x1 + 20 x1 = x1 + edge
x2 = x2 - 20 x2 = x2 - edge
y1 = y1 - 50 y1 = y1 - eaves
y2 = y2 - 50 y2 = y2 - eaves
} }
} }
switch (polygon.shape) { switch (polygon.shape) {
case 1: case 1:
break
case 2:
const centerPoint =
polygon.points[3].y +
(polygon.points[2].y - polygon.points[3].y) / 2
if (index === 0) { if (index === 0) {
const subLine = new QLine( const subLine = new QLine(
[ [
point.x - 20, point.x - edge,
polygon.points[0].y + polygon.points[0].y + (polygon.points[1].y - polygon.points[0].y) / 2,
(polygon.points[1].y - polygon.points[0].y) / 2, polygon.points[2].x,
polygon.points[5].x + 20, polygon.points[0].y + (polygon.points[1].y - polygon.points[0].y) / 2,
polygon.points[0].y + ],
(polygon.points[1].y - polygon.points[0].y) / 2, {
stroke: 'blue',
strokeWidth: 2,
selectable: false,
fontSize: fontSize,
},
)
canvas.add(subLine)
}
if (index === 1) {
x2 = x2 - edge
const subLine = new QLine([x2, y2, x2, polygon.points[0].y + (polygon.points[1].y - polygon.points[0].y) / 2], {
stroke: 'blue',
strokeWidth: 2,
selectable: false,
fontSize: fontSize,
})
canvas.add(subLine)
}
if (index === 2) {
y1 = point.y - (polygon.points[1].y - polygon.points[0].y) / 2
const centeredPoint = getCenterPoint(polygon.points[1].x, point.x)
const subLine = new QLine(
[centeredPoint, point.y + eaves, centeredPoint, polygon.points[0].y + (polygon.points[1].y - polygon.points[0].y) / 2],
{
stroke: 'black',
strokeWidth: 2,
strokeDashArray: [5, 5],
selectable: false,
fontSize: fontSize,
},
)
canvas.add(subLine)
}
if (index === 3) {
const centeredPoint = getCenterPoint(point.x, polygon.points[4].x)
const subLine = new QLine([centeredPoint, point.y + eaves, centeredPoint, polygon.points[5].y - eaves], {
stroke: 'black',
strokeWidth: 2,
strokeDashArray: [5, 5],
selectable: false,
fontSize: fontSize,
})
canvas.add(subLine)
}
if (index === 5) {
const centeredPoint = getCenterPoint(point.y, polygon.points[4].y)
const subLine = new QLine([point.x + edge, centeredPoint, polygon.points[2].x - edge, centeredPoint], {
stroke: 'blue',
strokeWidth: 2,
selectable: false,
fontSize: fontSize,
})
canvas.add(subLine)
}
break
case 2:
const centerPoint = polygon.points[3].y + (polygon.points[2].y - polygon.points[3].y) / 2
if (index === 0) {
const subLine = new QLine(
[
point.x - egde,
polygon.points[0].y + (polygon.points[1].y - polygon.points[0].y) / 2,
polygon.points[5].x + egde,
polygon.points[0].y + (polygon.points[1].y - polygon.points[0].y) / 2,
], ],
{ {
stroke: 'blue', stroke: 'blue',
@ -1002,7 +1052,7 @@ export function useMode() {
canvas.add(subLine) canvas.add(subLine)
} }
if (index === 3) { if (index === 3) {
x2 = x2 + 20 x2 = x2 + egde
const subLine = new QLine([x2, y2, x2, centerPoint], { const subLine = new QLine([x2, y2, x2, centerPoint], {
stroke: 'blue', stroke: 'blue',
@ -1013,26 +1063,20 @@ export function useMode() {
canvas.add(subLine) canvas.add(subLine)
} }
if (index === 4) { if (index === 4) {
y1 = y1 = point.y + (polygon.points[index - 2].y - polygon.points[index - 1].y) / 2
point.y +
(polygon.points[index - 2].y - polygon.points[index - 1].y) / 2
const subLine = new QLine( const subLine = new QLine([point.x, centerPoint, polygon.points[2].x + 20, centerPoint], {
[point.x, centerPoint, polygon.points[2].x + 20, centerPoint],
{
stroke: 'blue', stroke: 'blue',
strokeWidth: 2, strokeWidth: 2,
selectable: false, selectable: false,
fontSize: fontSize, fontSize: fontSize,
}, })
)
canvas.add(subLine)
const subVerticalLine = new QLine( const subVerticalLine = new QLine(
[ [
getCenterPoint(point.x, polygon.points[2].x + 20), getCenterPoint(point.x, polygon.points[2].x + egde),
polygon.points[3].y - 50, polygon.points[3].y - eaves,
getCenterPoint(point.x, polygon.points[2].x + 20), getCenterPoint(point.x, polygon.points[2].x + egde),
centerPoint, centerPoint,
], ],
{ {
@ -1047,25 +1091,14 @@ export function useMode() {
} }
if (index === 5) { if (index === 5) {
const centeredPoint = getCenterPoint( const centeredPoint = getCenterPoint(polygon.points[0].x, polygon.points[5].x)
polygon.points[0].x, const verticalSubLine = new QLine([centeredPoint, polygon.points[0].y - eaves, centeredPoint, polygon.points[1].y + eaves], {
polygon.points[5].x,
)
const verticalSubLine = new QLine(
[
centeredPoint,
polygon.points[0].y - 50,
centeredPoint,
polygon.points[1].y + 50,
],
{
stroke: 'black', stroke: 'black',
strokeWidth: 2, strokeWidth: 2,
strokeDashArray: [5, 5], strokeDashArray: [5, 5],
selectable: false, selectable: false,
fontSize: fontSize, fontSize: fontSize,
}, })
)
canvas.add(verticalSubLine) canvas.add(verticalSubLine)
} }