열. 단 삽입 추가

This commit is contained in:
김민식 2024-12-30 15:13:11 +09:00
parent 15b4d8f74e
commit 3907624dac
2 changed files with 218 additions and 33 deletions

View File

@ -5,20 +5,22 @@ import { useRecoilValue } from 'recoil'
import { contextPopupPositionState } from '@/store/popupAtom' import { contextPopupPositionState } from '@/store/popupAtom'
import { usePopup } from '@/hooks/usePopup' import { usePopup } from '@/hooks/usePopup'
import { useMessage } from '@/hooks/useMessage' import { useMessage } from '@/hooks/useMessage'
import { MODULE_INSERT_TYPE, useModule } from '@/hooks/module/useModule'
export default function RowInsert(props) { export default function RowInsert(props) {
const contextPopupPosition = useRecoilValue(contextPopupPositionState) const contextPopupPosition = useRecoilValue(contextPopupPositionState)
const { id, pos = contextPopupPosition, apply } = props const { id, pos = contextPopupPosition, apply } = props
const { closePopup } = usePopup() const { closePopup } = usePopup()
const [selectedType, setSelectedType] = useState(1) const [selectedType, setSelectedType] = useState(MODULE_INSERT_TYPE.TOP)
const { getMessage } = useMessage() const { getMessage } = useMessage()
const { muduleRowInsert } = useModule()
const handleApply = () => { const handleApply = () => {
if (apply) apply() muduleRowInsert(selectedType)
closePopup(id) closePopup(id)
} }
const HandleRadioChange = (e) => { const HandleRadioChange = (e) => {
setSelectedType(Number(e.target.value)) setSelectedType(e.target.value)
} }
return ( return (
@ -36,16 +38,30 @@ export default function RowInsert(props) {
<div className="additional-wrap"> <div className="additional-wrap">
<div className="additional-radio-wrap"> <div className="additional-radio-wrap">
<div className="d-check-radio pop"> <div className="d-check-radio pop">
<input type="radio" name="radio01" id="ra01" onChange={HandleRadioChange} value={1} checked={selectedType === 1} /> <input
type="radio"
name="radio01"
id="ra01"
onChange={HandleRadioChange}
value={MODULE_INSERT_TYPE.TOP}
checked={selectedType === MODULE_INSERT_TYPE.TOP}
/>
<label htmlFor="ra01">{getMessage('modal.row.insert.type.up')}</label> <label htmlFor="ra01">{getMessage('modal.row.insert.type.up')}</label>
</div> </div>
<div className="d-check-radio pop"> <div className="d-check-radio pop">
<input type="radio" name="radio01" id="ra02" onChange={HandleRadioChange} value={2} checked={selectedType === 2} /> <input
type="radio"
name="radio01"
id="ra02"
onChange={HandleRadioChange}
value={MODULE_INSERT_TYPE.BOTTOM}
checked={selectedType === MODULE_INSERT_TYPE.BOTTOM}
/>
<label htmlFor="ra02">{getMessage('modal.row.insert.type.down')}</label> <label htmlFor="ra02">{getMessage('modal.row.insert.type.down')}</label>
</div> </div>
</div> </div>
<div className="additional-img-wrap"> <div className="additional-img-wrap">
{selectedType === 1 && ( {selectedType === MODULE_INSERT_TYPE.TOP && (
<Image <Image
src="/static/images/canvas/additional_bundle-edit01.svg" src="/static/images/canvas/additional_bundle-edit01.svg"
alt="react" alt="react"
@ -54,7 +70,7 @@ export default function RowInsert(props) {
style={{ width: 'auto', height: 'auto' }} style={{ width: 'auto', height: 'auto' }}
/> />
)} )}
{selectedType === 2 && ( {selectedType === MODULE_INSERT_TYPE.BOTTOM && (
<Image <Image
src="/static/images/canvas/additional_bundle-edit02.svg" src="/static/images/canvas/additional_bundle-edit02.svg"
alt="react" alt="react"

View File

@ -21,8 +21,8 @@ export const MODULE_REMOVE_TYPE = {
export const MODULE_INSERT_TYPE = { export const MODULE_INSERT_TYPE = {
LEFT: 'left', LEFT: 'left',
RIGHT: 'right', RIGHT: 'right',
TOP: 'top', TOP: 'up',
BOTTOM: 'bottom', BOTTOM: 'down',
} }
export function useModule() { export function useModule() {
@ -264,17 +264,14 @@ export function useModule() {
.filter((obj) => obj.name === POLYGON_TYPE.MODULE_SETUP_SURFACE && obj.id === modules[0].surfaceId)[0] .filter((obj) => obj.name === POLYGON_TYPE.MODULE_SETUP_SURFACE && obj.id === modules[0].surfaceId)[0]
let [isOverlapOtherModules, isOverlapObjects, isOutsideSurface] = [[], [], []] let [isOverlapOtherModules, isOverlapObjects, isOutsideSurface] = [[], [], []]
let moduleLength = 0 let moduleLength = 0
if (type === 'column') { if (['up', 'down'].includes(direction)) {
moduleLength = Number(modules[modules.length - 1].top) + Number(modules[modules.length - 1].height) - Number(modules[0].top) moduleLength = Number(modules[modules.length - 1].top) + Number(modules[modules.length - 1].height) - Number(modules[0].top)
} else if (type === 'row') { } else if (['left', 'right'].includes(direction)) {
moduleLength = Number(modules[modules.length - 1].left) + Number(modules[modules.length - 1].width) - Number(modules[0].left) moduleLength = Number(modules[modules.length - 1].left) + Number(modules[modules.length - 1].width) - Number(modules[0].left)
} }
console.log('🚀 ~ moduleMultiCopy ~ modules:', modules)
console.log('🚀 ~ moduleMultiCopy ~ moduleLength:', moduleLength)
modules.forEach((module) => { modules.forEach((module) => {
const { top, left } = getPosotion(module, direction, Number(length) + Number(moduleLength), false) const { top, left } = getPosotion(module, direction, Number(length) + Number(moduleLength), false)
console.log('🚀 ~ modules.forEach ~ top:', top)
const moduleOptions = { ...module, left, top, id: uuidv4() } const moduleOptions = { ...module, left, top, id: uuidv4() }
const rect = new QPolygon(module.getCurrentPoints(), moduleOptions) const rect = new QPolygon(module.getCurrentPoints(), moduleOptions)
canvas.add(rect) canvas.add(rect)
@ -545,41 +542,212 @@ export function useModule() {
} }
canvas.renderAll() canvas.renderAll()
} }
// 좌우 열 옮기고 current Column 복사하기.
const moduleColumnInsert = (type) => { const moduleColumnInsert = (type) => {
const activeModule = canvas.getObjects().filter((obj) => canvas.getActiveObjects()[0].id === obj.id)[0] const activeModule = canvas.getObjects().filter((obj) => canvas.getActiveObjects()[0].id === obj.id)[0]
const columnModules = getColumnModules(activeModule) const columnModules = getColumnModules(activeModule)
const otherModules = getOtherModules(columnModules) let otherModules = getOtherModules(columnModules)
const targetModules = const targetModules =
type === MODULE_INSERT_TYPE.LEFT type === MODULE_INSERT_TYPE.LEFT
? otherModules.filter((module) => module.left < activeModule.left).sort((a, b) => a.left - b.left) ? otherModules.filter((module) => module.left < activeModule.left).sort((a, b) => a.left - b.left)
: otherModules.filter((module) => module.left > activeModule.left).sort((a, b) => b.left - a.left) : otherModules.filter((module) => module.left > activeModule.left).sort((a, b) => b.left - a.left)
const objects = getObjects() const objects = getObjects()
const copyRects = [] const copyModules = []
const moduleSetupSurface = canvas const moduleSetupSurface = canvas
.getObjects() .getObjects()
.filter((obj) => obj.name === POLYGON_TYPE.MODULE_SETUP_SURFACE && obj.id === activeModule.surfaceId)[0] .filter((obj) => obj.name === POLYGON_TYPE.MODULE_SETUP_SURFACE && obj.id === activeModule.surfaceId)[0]
let width = -1 let width = -1
let [isOverlapOtherModules, isOverlapObjects, isOutsideSurface] = [[], [], []] let [isOverlapOtherModules, isOverlapObjects, isOutsideSurface] = [[], [], []]
if (targetModules.length === 0) {
swalFire({
title: '마지막 모듈입니다.',
icon: 'error',
type: 'alert',
})
return
}
canvas.discardActiveObject()
targetModules.forEach((module) => { targetModules.forEach((module) => {
if (width === -1) width = type === MODULE_INSERT_TYPE.LEFT ? module.left - activeModule.left : activeModule.left - module.left if (width === -1)
const { left } = getPosotion(module, type, width, false) width = type === MODULE_INSERT_TYPE.LEFT ? Number(activeModule.left) - Number(module.left) : Number(module.left) - Number(activeModule.left)
const moduleOptions = { ...module, left, top, id: uuidv4() } const { top, left } = getPosotion(module, type, width, false)
module.set({ left }) module.originPos = {
// const rect = new QPolygon(module.getCurrentPoints(), moduleOptions) left: module.left,
// canvas.add(rect) top: module.top,
// copyRects.push(rect) }
module.set({ left, top })
canvas.renderAll()
if (objects.length > 0) {
isOverlapObjects.push(!checkModuleDisjointObjects(polygonToTurfPolygon(module, true), objects))
}
isOutsideSurface.push(
!turf.booleanContains(polygonToTurfPolygon(moduleSetupSurface, true), polygonToTurfPolygon(module, true)) ||
!turf.booleanWithin(polygonToTurfPolygon(module, true), polygonToTurfPolygon(moduleSetupSurface, true)),
)
module.setCoords() module.setCoords()
}) })
// columnModules.forEach((module) => { otherModules = getOtherModules(columnModules)
// const { top, left } = getPosotion(module, MODULE_INSERT_TYPE.LEFT, module.width, false) columnModules.forEach((module) => {
// const moduleOptions = { ...module, left, top, id: uuidv4() } const { top, left } = getPosotion(module, type, width, false)
// const rect = new QPolygon(module.getCurrentPoints(), moduleOptions) const moduleOptions = { ...module, left, top, id: uuidv4() }
// canvas.add(rect) const copyModule = new QPolygon(module.points, moduleOptions)
// copyRects.push(rect) canvas.add(copyModule)
// module.setCoords() copyModules.push(copyModule)
// }) canvas.renderAll()
if (otherModules.length > 0) {
isOverlapOtherModules.push(
otherModules.some(
(otherModule) =>
turf.booleanOverlap(polygonToTurfPolygon(copyModule, true), polygonToTurfPolygon(otherModule, true)) ||
turf.booleanWithin(polygonToTurfPolygon(copyModule, true), polygonToTurfPolygon(otherModule, true)),
),
)
}
if (objects.length > 0) {
isOverlapObjects.push(!checkModuleDisjointObjects(polygonToTurfPolygon(module, true), objects))
}
isOutsideSurface.push(
!turf.booleanContains(polygonToTurfPolygon(moduleSetupSurface, true), polygonToTurfPolygon(copyModule, true)) ||
!turf.booleanWithin(polygonToTurfPolygon(copyModule, true), polygonToTurfPolygon(moduleSetupSurface, true)),
)
module.setCoords()
})
if (
isOverlapOtherModules.some((isOverlap) => isOverlap) ||
isOverlapObjects.some((isOverlap) => isOverlap) ||
isOutsideSurface.some((isOutside) => isOutside)
) {
swalFire({
title: isOverlapOtherModules.some((isOverlap) => isOverlap)
? '겹치는 모듈이 있습니다.'
: isOverlapObjects.some((isOverlap) => isOverlap)
? '모듈이 오브젝트와 겹칩니다.'
: '영역 밖',
icon: 'error',
type: 'confirm',
confirmFn: () => {
targetModules.forEach((module) => {
module.set({ top: module.originPos.top, left: module.originPos.left })
module.setCoords()
})
canvas.renderAll()
copyModules.forEach((module) => {
canvas.remove(module)
})
canvas.renderAll()
},
})
}
}
const muduleRowInsert = (type) => {
console.log('🚀 ~ muduleRowInsert ~ type:', type)
const activeModule = canvas.getObjects().filter((obj) => canvas.getActiveObjects()[0].id === obj.id)[0]
const rowModules = getRowModules(activeModule)
console.log('🚀 ~ muduleRowInsert ~ rowModules:', rowModules)
let otherModules = getOtherModules(rowModules)
const targetModules =
type === MODULE_INSERT_TYPE.TOP
? otherModules.filter((module) => module.top < activeModule.top).sort((a, b) => b.top - a.top)
: otherModules.filter((module) => module.top > activeModule.top).sort((a, b) => a.top - b.top)
console.log('🚀 ~ muduleRowInsert ~ targetModules:', targetModules)
if (targetModules.length === 0) {
swalFire({
title: '마지막 모듈입니다.',
icon: 'error',
type: 'alert',
})
return
}
const objects = getObjects()
const copyModules = []
const moduleSetupSurface = canvas
.getObjects()
.filter((obj) => obj.name === POLYGON_TYPE.MODULE_SETUP_SURFACE && obj.id === activeModule.surfaceId)[0]
let height = -1
let [isOverlapOtherModules, isOverlapObjects, isOutsideSurface] = [[], [], []]
canvas.discardActiveObject()
targetModules.forEach((module) => {
if (height === -1)
height = type === MODULE_INSERT_TYPE.TOP ? Number(activeModule.top) - Number(module.top) : Number(module.top) - Number(activeModule.top)
const { top, left } = getPosotion(module, type, height, false)
module.originPos = {
left: module.left,
top: module.top,
}
module.set({ left, top })
canvas.renderAll()
if (objects.length > 0) {
isOverlapObjects.push(!checkModuleDisjointObjects(polygonToTurfPolygon(module, true), objects))
}
isOutsideSurface.push(
!turf.booleanContains(polygonToTurfPolygon(moduleSetupSurface, true), polygonToTurfPolygon(module, true)) ||
!turf.booleanWithin(polygonToTurfPolygon(module, true), polygonToTurfPolygon(moduleSetupSurface, true)),
)
module.setCoords()
})
otherModules = getOtherModules(rowModules)
rowModules.forEach((module) => {
const { top, left } = getPosotion(module, type, height, false)
const moduleOptions = { ...module, left, top, id: uuidv4() }
const copyModule = new QPolygon(module.points, moduleOptions)
canvas.add(copyModule)
copyModules.push(copyModule)
canvas.renderAll()
if (otherModules.length > 0) {
isOverlapOtherModules.push(
otherModules.some(
(otherModule) =>
turf.booleanOverlap(polygonToTurfPolygon(copyModule, true), polygonToTurfPolygon(otherModule, true)) ||
turf.booleanWithin(polygonToTurfPolygon(copyModule, true), polygonToTurfPolygon(otherModule, true)),
),
)
}
if (objects.length > 0) {
isOverlapObjects.push(!checkModuleDisjointObjects(polygonToTurfPolygon(module, true), objects))
}
isOutsideSurface.push(
!turf.booleanContains(polygonToTurfPolygon(moduleSetupSurface, true), polygonToTurfPolygon(copyModule, true)) ||
!turf.booleanWithin(polygonToTurfPolygon(copyModule, true), polygonToTurfPolygon(moduleSetupSurface, true)),
)
module.setCoords()
})
if (
isOverlapOtherModules.some((isOverlap) => isOverlap) ||
isOverlapObjects.some((isOverlap) => isOverlap) ||
isOutsideSurface.some((isOutside) => isOutside)
) {
swalFire({
title: isOverlapOtherModules.some((isOverlap) => isOverlap)
? '겹치는 모듈이 있습니다.'
: isOverlapObjects.some((isOverlap) => isOverlap)
? '모듈이 오브젝트와 겹칩니다.'
: '영역 밖',
icon: 'error',
type: 'confirm',
confirmFn: () => {
targetModules.forEach((module) => {
module.set({ top: module.originPos.top, left: module.originPos.left })
module.setCoords()
})
canvas.renderAll()
copyModules.forEach((module) => {
canvas.remove(module)
})
canvas.renderAll()
},
})
}
} }
const getRowModules = (target) => { const getRowModules = (target) => {
@ -660,5 +828,6 @@ export function useModule() {
moduleColumnRemove, moduleColumnRemove,
moduleRowRemove, moduleRowRemove,
moduleColumnInsert, moduleColumnInsert,
muduleRowInsert,
} }
} }