diff --git a/src/components/Roof2.jsx b/src/components/Roof2.jsx index 5d864c47..ff570d90 100644 --- a/src/components/Roof2.jsx +++ b/src/components/Roof2.jsx @@ -34,6 +34,7 @@ import { degreesToRadians, radiansToDegrees } from '@turf/turf' import InitSettingsModal from './InitSettingsModal' import GridSettingsModal from './GridSettingsModal' +import { SurfaceShapeModal } from '@/components/ui/SurfaceShape' export default function Roof2(props) { const { name, userId, email, isLoggedIn } = props @@ -534,6 +535,44 @@ export default function Roof2(props) { }) } + const setCurrentPattern = (polygon) => { + const { width, height, roofStyle } = roofMaterial + const roofRatio = window.devicePixelRatio || 1 + const patternSourceCanvas = document.createElement('canvas') + + if (roofStyle === 1) { + patternSourceCanvas.width = width * roofRatio + patternSourceCanvas.height = height * roofRatio + } else if (roofStyle === 2) { + patternSourceCanvas.width = width * 2 + patternSourceCanvas.height = height * 2 + } + + const ctx = patternSourceCanvas.getContext('2d') + + ctx.scale(roofRatio, roofRatio) + ctx.strokeStyle = 'green' + ctx.lineWidth = 0.4 + // 벽돌 패턴 그리기 + if (roofStyle === 1) { + ctx.strokeRect(0, 0, 50, 30) + } else if (roofStyle === 2) { + // 지그재그 + ctx.strokeRect(0, 0, 200, 100) + ctx.strokeRect(100, 100, 200, 100) + } + + // 패턴 생성 + const pattern = new fabric.Pattern({ + source: patternSourceCanvas, + repeat: 'repeat', + }) + polygon.set('fill', null) + + polygon.set('fill', pattern) + canvas?.renderAll() + } + /** * canvas 내용 불러오기 */ @@ -576,41 +615,6 @@ export default function Roof2(props) { canvas?.renderAll() } - const createTemplate1 = () => { - const length1 = prompt('1번') - const length2 = prompt('2번') - - let isDrawing = true - canvas?.on('mouse:move', (e) => { - if (!isDrawing) { - return - } - canvas?.remove(...canvas?.getObjects().filter((obj) => obj.name === 'guideTriangle')) - const pointer = canvas?.getPointer(e.e) - const triangle = new QPolygon( - [ - { x: pointer.x, y: pointer.y - parseInt(length2) / 2 }, - { x: pointer.x - parseInt(length1) / 2, y: pointer.y + parseInt(length1) / 2 }, - { x: pointer.x + parseInt(length1) / 2, y: pointer.y + parseInt(length1) / 2 }, - ], - { - fill: 'transparent', - stroke: 'black', - strokeWidth: 2, - selectable: true, - fontSize: fontSize, - name: 'guideTriangle', - }, - ) - - canvas?.add(triangle) - }) - - canvas?.on('mouse:down', (e) => { - isDrawing = false - }) - } - const createPentagon2 = () => { const a = 400 //Number(prompt('a')) const b = 200 //Number(prompt('b')) @@ -671,297 +675,6 @@ export default function Roof2(props) { }) } - const createTemplate2 = () => { - const length1 = prompt('1번') - const length2 = prompt('2번') - - let isDrawing = true - canvas?.on('mouse:move', (e) => { - if (!isDrawing) { - return - } - canvas?.remove(...canvas?.getObjects().filter((obj) => obj.name === 'guideTriangle')) - const pointer = canvas?.getPointer(e.e) - const triangle = new QPolygon( - [ - { x: pointer.x - length1 / 2, y: pointer.y + length2 / 2 }, - { x: pointer.x + length1 / 2, y: pointer.y + length2 / 2 }, - { x: pointer.x + length1 / 2, y: pointer.y - length2 / 2 }, - { x: pointer.x - length1 / 2, y: pointer.y - length2 / 2 }, - ], - { - fill: 'transparent', - stroke: 'black', - strokeWidth: 2, - selectable: true, - fontSize: fontSize, - name: 'guideTriangle', - }, - ) - - canvas?.add(triangle) - }) - - canvas?.on('mouse:down', (e) => { - isDrawing = false - }) - } - - const createTemplate3 = () => { - const length1 = Number(prompt('1번')) - const length2 = Number(prompt('2번')) - const length3 = Number(prompt('3번')) - - let isDrawing = true - canvas?.on('mouse:move', (e) => { - if (!isDrawing) { - return - } - canvas?.remove(...canvas?.getObjects().filter((obj) => obj.name === 'guideTriangle')) - const pointer = canvas?.getPointer(e.e) - const triangle = new QPolygon( - [ - { x: pointer.x - length1 / 2, y: pointer.y + length2 / 2 }, - { x: pointer.x + length1 / 2, y: pointer.y + length2 / 2 }, - { x: pointer.x + length3 / 2, y: pointer.y - length2 / 2 }, - { x: pointer.x - length3 / 2, y: pointer.y - length2 / 2 }, - ], - { - fill: 'transparent', - stroke: 'black', - strokeWidth: 2, - selectable: true, - fontSize: fontSize, - name: 'guideTriangle', - }, - ) - - canvas?.add(triangle) - }) - - canvas?.on('mouse:down', (e) => { - isDrawing = false - }) - } - - const createTemplate4 = () => { - const length1 = Number(prompt('1번')) - const length2 = Number(prompt('2번')) - - let isDrawing = true - canvas?.on('mouse:move', (e) => { - if (!isDrawing) { - return - } - canvas?.remove(...canvas?.getObjects().filter((obj) => obj.name === 'guideTriangle')) - const pointer = canvas?.getPointer(e.e) - const triangle = new QPolygon( - [ - { x: pointer.x - length1 / 2, y: pointer.y + length2 / 2 }, - { x: pointer.x + length1 / 2, y: pointer.y + length2 / 2 }, - { x: pointer.x + length1 / 2, y: pointer.y - length2 / 2 }, - ], - { - fill: 'transparent', - stroke: 'black', - strokeWidth: 2, - selectable: true, - fontSize: fontSize, - name: 'guideTriangle', - }, - ) - - canvas?.add(triangle) - }) - - canvas?.on('mouse:down', (e) => { - isDrawing = false - }) - } - - const createTemplate5 = () => { - const length1 = Number(prompt('1번')) - const length2 = Number(prompt('2번')) - - let isDrawing = true - canvas?.on('mouse:move', (e) => { - if (!isDrawing) { - return - } - canvas?.remove(...canvas?.getObjects().filter((obj) => obj.name === 'guideTriangle')) - const pointer = canvas?.getPointer(e.e) - const triangle = new QPolygon( - [ - { x: pointer.x + length1 / 2, y: pointer.y + length2 / 2 }, - { x: pointer.x - length1 / 2, y: pointer.y + length2 / 2 }, - { x: pointer.x - length1 / 2, y: pointer.y - length2 / 2 }, - ], - { - fill: 'transparent', - stroke: 'black', - strokeWidth: 2, - selectable: true, - fontSize: fontSize, - name: 'guideTriangle', - }, - ) - - canvas?.add(triangle) - }) - - canvas?.on('mouse:down', (e) => { - isDrawing = false - }) - } - - const createTemplate6 = () => { - const length1 = Number(prompt('1번')) - const length2 = Number(prompt('2번')) - const length3 = Number(prompt('3번')) - - let isDrawing = true - canvas?.on('mouse:move', (e) => { - if (!isDrawing) { - return - } - canvas?.remove(...canvas?.getObjects().filter((obj) => obj.name === 'guideTriangle')) - const pointer = canvas?.getPointer(e.e) - const triangle = new QPolygon( - [ - { x: pointer.x - length1 / 2, y: pointer.y - length3 / 2 }, - { x: pointer.x - length1 / 2, y: pointer.y + length3 / 2 }, - { x: pointer.x + length1 / 2, y: pointer.y + length3 / 2 }, - { x: pointer.x + length1 / 2, y: pointer.y + length3 / 2 - length2 }, - ], - { - fill: 'transparent', - stroke: 'black', - strokeWidth: 2, - selectable: true, - fontSize: fontSize, - name: 'guideTriangle', - }, - ) - - canvas?.add(triangle) - }) - - canvas?.on('mouse:down', (e) => { - isDrawing = false - }) - } - const createTemplate7 = () => { - const length1 = Number(prompt('1번')) - const length2 = Number(prompt('2번')) - const length3 = Number(prompt('3번')) - - let isDrawing = true - canvas?.on('mouse:move', (e) => { - if (!isDrawing) { - return - } - canvas?.remove(...canvas?.getObjects().filter((obj) => obj.name === 'guideTriangle')) - const pointer = canvas?.getPointer(e.e) - const triangle = new QPolygon( - [ - { x: pointer.x - length1 / 2, y: pointer.y - length2 / 2 }, - { x: pointer.x - length1 / 2, y: pointer.y + length2 / 2 }, - { x: pointer.x + length1 / 2, y: pointer.y + length2 / 2 }, - { x: pointer.x + length1 / 2, y: pointer.y + length2 / 2 - length3 }, - ], - { - fill: 'transparent', - stroke: 'black', - strokeWidth: 2, - selectable: true, - fontSize: fontSize, - name: 'guideTriangle', - }, - ) - - canvas?.add(triangle) - }) - - canvas?.on('mouse:down', (e) => { - isDrawing = false - }) - } - const createTemplate8 = () => { - const length1 = Number(prompt('1번')) // 밑변 - const length2 = Number(prompt('2번')) // 높이 - const length3 = Number(prompt('3번')) // 빗변 - - const angleInRadians = Math.asin(length2 / length3) - - let isDrawing = true - canvas?.on('mouse:move', (e) => { - if (!isDrawing) { - return - } - canvas?.remove(...canvas?.getObjects().filter((obj) => obj.name === 'guideTriangle')) - const pointer = canvas?.getPointer(e.e) - const triangle = new QPolygon( - [ - { x: pointer.x - length1 / 2, y: pointer.y + length2 / 2 }, - { x: pointer.x - length1 / 2 + length3 * Math.cos(angleInRadians), y: pointer.y + length2 / 2 - length3 * Math.sin(angleInRadians) }, - { x: pointer.x + length1 / 2 + length3 * Math.cos(angleInRadians), y: pointer.y + length2 / 2 - length3 * Math.sin(angleInRadians) }, - { x: pointer.x + length1 / 2, y: pointer.y + length2 / 2 }, - ], - { - fill: 'transparent', - stroke: 'black', - strokeWidth: 2, - selectable: true, - fontSize: fontSize, - name: 'guideTriangle', - }, - ) - - canvas?.add(triangle) - }) - - canvas?.on('mouse:down', (e) => { - isDrawing = false - }) - } - const createTemplate9 = () => { - const length1 = Number(prompt('1번')) // 밑변 - const length2 = Number(prompt('2번')) // 높이 - const length3 = Number(prompt('3번')) // 빗변 - - const angleInRadians = Math.asin(length2 / length3) - - let isDrawing = true - canvas?.on('mouse:move', (e) => { - if (!isDrawing) { - return - } - canvas?.remove(...canvas?.getObjects().filter((obj) => obj.name === 'guideTriangle')) - const pointer = canvas?.getPointer(e.e) - const triangle = new QPolygon( - [ - { x: pointer.x + length1 / 2, y: pointer.y + length2 / 2 }, - { x: pointer.x + length1 / 2 - length3 * Math.cos(angleInRadians), y: pointer.y + length2 / 2 - length3 * Math.sin(angleInRadians) }, - { x: pointer.x - length1 / 2 - length3 * Math.cos(angleInRadians), y: pointer.y + length2 / 2 - length3 * Math.sin(angleInRadians) }, - { x: pointer.x - length1 / 2, y: pointer.y + length2 / 2 }, - ], - { - fill: 'transparent', - stroke: 'black', - strokeWidth: 2, - selectable: true, - fontSize: fontSize, - name: 'guideTriangle', - }, - ) - - canvas?.add(triangle) - }) - - canvas?.on('mouse:down', (e) => { - isDrawing = false - }) - } const createTemplate10 = () => { const length1 = Number(prompt('1번')) const length2 = Number(prompt('2번')) @@ -1858,6 +1571,13 @@ export default function Roof2(props) { + @@ -1947,6 +1667,15 @@ export default function Roof2(props) { + {/**/} @@ -1981,33 +1710,6 @@ export default function Roof2(props) { - - - - - - - - - diff --git a/src/components/ui/SurfaceShape.jsx b/src/components/ui/SurfaceShape.jsx new file mode 100644 index 00000000..b55db429 --- /dev/null +++ b/src/components/ui/SurfaceShape.jsx @@ -0,0 +1,387 @@ +import { Button, Input } from '@nextui-org/react' +import { useCallback, useEffect, useState } from 'react' +import { useRecoilState, useRecoilValue, useSetRecoilState } from 'recoil' +import { modalState } from '@/store/modalAtom' +import { QPolygon } from '@/components/fabric/QPolygon' +import { fontSizeState } from '@/store/canvasAtom' + +/** + * 면형상 배치 모달 + * @returns {JSX.Element} + * @constructor + */ +export const SurfaceShapeModal = ({ canvas }) => { + const [type, setType] = useState(0) + const setOpen = useSetRecoilState(modalState) + const fontSize = useRecoilValue(fontSizeState) + + /** + * 최대 5개의 length + */ + const [length1, setLength1] = useState(0) + const [length2, setLength2] = useState(0) + const [length3, setLength3] = useState(0) + const [length4, setLength4] = useState(0) + const [length5, setLength5] = useState(0) + + /** + * 최대 5개의 length + */ + const onChangeType = (e) => { + setType(Number(e.target.value)) + } + + const closeModal = () => { + setOpen(false) + } + + const onSave = () => { + let isDrawing = true + let obj = null + canvas?.on('mouse:move', (e) => { + if (!isDrawing) { + return + } + switch (type) { + case 1: { + canvas?.remove(...canvas?.getObjects().filter((obj) => obj.name === 'guideTriangle')) + const pointer = canvas?.getPointer(e.e) + obj = new QPolygon( + [ + { x: pointer.x, y: pointer.y - parseInt(length2) / 2 }, + { x: pointer.x - parseInt(length1) / 2, y: pointer.y + parseInt(length1) / 2 }, + { x: pointer.x + parseInt(length1) / 2, y: pointer.y + parseInt(length1) / 2 }, + ], + { + fill: 'transparent', + stroke: 'black', + strokeWidth: 2, + selectable: true, + fontSize: fontSize, + name: 'guideTriangle', + }, + ) + + break + } + case 2: { + canvas?.remove(...canvas?.getObjects().filter((obj) => obj.name === 'guideTriangle')) + const pointer = canvas?.getPointer(e.e) + obj = new QPolygon( + [ + { x: pointer.x - length1 / 2, y: pointer.y + length2 / 2 }, + { x: pointer.x + length1 / 2, y: pointer.y + length2 / 2 }, + { x: pointer.x + length1 / 2, y: pointer.y - length2 / 2 }, + { x: pointer.x - length1 / 2, y: pointer.y - length2 / 2 }, + ], + { + fill: 'transparent', + stroke: 'black', + strokeWidth: 2, + selectable: true, + fontSize: fontSize, + name: 'guideTriangle', + }, + ) + break + } + case 3: { + canvas?.remove(...canvas?.getObjects().filter((obj) => obj.name === 'guideTriangle')) + const pointer = canvas?.getPointer(e.e) + obj = new QPolygon( + [ + { x: pointer.x - length1 / 2, y: pointer.y + length2 / 2 }, + { x: pointer.x + length1 / 2, y: pointer.y + length2 / 2 }, + { x: pointer.x + length3 / 2, y: pointer.y - length2 / 2 }, + { x: pointer.x - length3 / 2, y: pointer.y - length2 / 2 }, + ], + { + fill: 'transparent', + stroke: 'black', + strokeWidth: 2, + selectable: true, + fontSize: fontSize, + name: 'guideTriangle', + }, + ) + break + } + case 4: { + canvas?.remove(...canvas?.getObjects().filter((obj) => obj.name === 'guideTriangle')) + const pointer = canvas?.getPointer(e.e) + obj = new QPolygon( + [ + { x: pointer.x - length1 / 2, y: pointer.y + length2 / 2 }, + { x: pointer.x + length1 / 2, y: pointer.y + length2 / 2 }, + { x: pointer.x + length1 / 2, y: pointer.y - length2 / 2 }, + ], + { + fill: 'transparent', + stroke: 'black', + strokeWidth: 2, + selectable: true, + fontSize: fontSize, + name: 'guideTriangle', + }, + ) + + break + } + case 5: { + canvas?.remove(...canvas?.getObjects().filter((obj) => obj.name === 'guideTriangle')) + const pointer = canvas?.getPointer(e.e) + obj = new QPolygon( + [ + { x: pointer.x + length1 / 2, y: pointer.y + length2 / 2 }, + { x: pointer.x - length1 / 2, y: pointer.y + length2 / 2 }, + { x: pointer.x - length1 / 2, y: pointer.y - length2 / 2 }, + ], + { + fill: 'transparent', + stroke: 'black', + strokeWidth: 2, + selectable: true, + fontSize: fontSize, + name: 'guideTriangle', + }, + ) + break + } + + case 6: { + canvas?.remove(...canvas?.getObjects().filter((obj) => obj.name === 'guideTriangle')) + const pointer = canvas?.getPointer(e.e) + obj = new QPolygon( + [ + { x: pointer.x - length1 / 2, y: pointer.y - length3 / 2 }, + { x: pointer.x - length1 / 2, y: pointer.y + length3 / 2 }, + { x: pointer.x + length1 / 2, y: pointer.y + length3 / 2 }, + { x: pointer.x + length1 / 2, y: pointer.y + length3 / 2 - length2 }, + ], + { + fill: 'transparent', + stroke: 'black', + strokeWidth: 2, + selectable: true, + fontSize: fontSize, + name: 'guideTriangle', + }, + ) + break + } + + case 7: { + canvas?.remove(...canvas?.getObjects().filter((obj) => obj.name === 'guideTriangle')) + const pointer = canvas?.getPointer(e.e) + obj = new QPolygon( + [ + { x: pointer.x - length1 / 2, y: pointer.y - length2 / 2 }, + { x: pointer.x - length1 / 2, y: pointer.y + length2 / 2 }, + { x: pointer.x + length1 / 2, y: pointer.y + length2 / 2 }, + { x: pointer.x + length1 / 2, y: pointer.y + length2 / 2 - length3 }, + ], + { + fill: 'transparent', + stroke: 'black', + strokeWidth: 2, + selectable: true, + fontSize: fontSize, + name: 'guideTriangle', + }, + ) + } + case 8: { + const angleInRadians = Math.asin(length2 / length3) + canvas?.remove(...canvas?.getObjects().filter((obj) => obj.name === 'guideTriangle')) + const pointer = canvas?.getPointer(e.e) + obj = new QPolygon( + [ + { x: pointer.x - length1 / 2, y: pointer.y + length2 / 2 }, + { x: pointer.x - length1 / 2 + length3 * Math.cos(angleInRadians), y: pointer.y + length2 / 2 - length3 * Math.sin(angleInRadians) }, + { x: pointer.x + length1 / 2 + length3 * Math.cos(angleInRadians), y: pointer.y + length2 / 2 - length3 * Math.sin(angleInRadians) }, + { x: pointer.x + length1 / 2, y: pointer.y + length2 / 2 }, + ], + { + fill: 'transparent', + stroke: 'black', + strokeWidth: 2, + selectable: true, + fontSize: fontSize, + name: 'guideTriangle', + }, + ) + } + case 9: { + const angleInRadians = Math.asin(length2 / length3) + const pointer = canvas?.getPointer(e.e) + obj = new QPolygon( + [ + { x: pointer.x + length1 / 2, y: pointer.y + length2 / 2 }, + { x: pointer.x + length1 / 2 - length3 * Math.cos(angleInRadians), y: pointer.y + length2 / 2 - length3 * Math.sin(angleInRadians) }, + { x: pointer.x - length1 / 2 - length3 * Math.cos(angleInRadians), y: pointer.y + length2 / 2 - length3 * Math.sin(angleInRadians) }, + { x: pointer.x - length1 / 2, y: pointer.y + length2 / 2 }, + ], + { + fill: 'transparent', + stroke: 'black', + strokeWidth: 2, + selectable: true, + fontSize: fontSize, + name: 'guideTriangle', + }, + ) + } + } + canvas?.add(obj) + }) + + canvas?.on('mouse:down', (e) => { + isDrawing = false + obj.set('name', 'roof') + }) + setOpen(false) + } + + const setLength = (e) => { + const { name, value } = e.target + switch (name) { + case 'length1': + setLength1(value) + break + case 'length2': + setLength2(value) + break + case 'length3': + setLength3(value) + break + case 'length4': + setLength4(value) + break + case 'length5': + setLength5(value) + break + default: + break + } + } + + return ( + <> +