Compare commits
No commits in common. "0b2be2b4b1c7a10e5447ea1e71eb573694b99622" and "8b425c35f8722e577913ba51263acbe53b9d6f3b" have entirely different histories.
0b2be2b4b1
...
8b425c35f8
@ -1,5 +1,5 @@
|
|||||||
'use client'
|
'use client'
|
||||||
import { useEffect, useRef } from 'react'
|
import { useEffect } from 'react'
|
||||||
import '@/styles/contents.scss'
|
import '@/styles/contents.scss'
|
||||||
import { useRecoilState, useRecoilValue } from 'recoil'
|
import { useRecoilState, useRecoilValue } from 'recoil'
|
||||||
import { contextMenuListState, contextMenuState } from '@/store/contextMenu'
|
import { contextMenuListState, contextMenuState } from '@/store/contextMenu'
|
||||||
@ -15,13 +15,8 @@ export default function QContextMenu(props) {
|
|||||||
const contextMenuList = useRecoilValue(contextMenuListState)
|
const contextMenuList = useRecoilValue(contextMenuListState)
|
||||||
const currentObject = useRecoilValue(currentObjectState)
|
const currentObject = useRecoilValue(currentObjectState)
|
||||||
const { tempGridMode, setTempGridMode } = useTempGrid()
|
const { tempGridMode, setTempGridMode } = useTempGrid()
|
||||||
const { handleKeyup, triggerDelete } = useContextMenu()
|
const { handleKeyup } = useContextMenu()
|
||||||
const { addDocumentEventListener, removeDocumentEvent } = useEvent()
|
const { addDocumentEventListener, removeDocumentEvent } = useEvent()
|
||||||
// [TMP-DEL 2026-05-07] 객체 선택 시 Del 키 활성화: 항상 최신 함수 참조용 ref
|
|
||||||
const handleKeyupRef = useRef(handleKeyup)
|
|
||||||
handleKeyupRef.current = handleKeyup
|
|
||||||
const triggerDeleteRef = useRef(triggerDelete)
|
|
||||||
triggerDeleteRef.current = triggerDelete
|
|
||||||
// const { addDocumentEventListener, removeDocumentEvent } = useContext(EventContext)
|
// const { addDocumentEventListener, removeDocumentEvent } = useContext(EventContext)
|
||||||
|
|
||||||
const getYPosition = (e) => {
|
const getYPosition = (e) => {
|
||||||
@ -44,7 +39,7 @@ export default function QContextMenu(props) {
|
|||||||
y: window.innerHeight / 2 < e.pageY ? getYPosition(e) : e.pageY,
|
y: window.innerHeight / 2 < e.pageY ? getYPosition(e) : e.pageY,
|
||||||
}
|
}
|
||||||
setContextMenu({ visible: true, ...position, currentMousePos: canvasProps.getPointer(e) })
|
setContextMenu({ visible: true, ...position, currentMousePos: canvasProps.getPointer(e) })
|
||||||
// [TMP-DEL 2026-05-07] keyup 등록은 객체 선택 useEffect 가 담당. 메뉴 오픈 시 별도 등록 불필요.
|
addDocumentEventListener('keyup', document, handleKeyup)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -57,7 +52,7 @@ export default function QContextMenu(props) {
|
|||||||
// e.preventDefault()
|
// e.preventDefault()
|
||||||
if (contextMenu.visible) {
|
if (contextMenu.visible) {
|
||||||
setContextMenu({ ...contextMenu, visible: false })
|
setContextMenu({ ...contextMenu, visible: false })
|
||||||
// [TMP-DEL 2026-05-07] 메뉴 닫혀도 객체 선택 상태면 Del 살려야 하므로 keyup 제거하지 않음
|
removeDocumentEvent('keyup')
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -69,33 +64,13 @@ export default function QContextMenu(props) {
|
|||||||
document.addEventListener('click', handleOutsideClick)
|
document.addEventListener('click', handleOutsideClick)
|
||||||
|
|
||||||
return () => {
|
return () => {
|
||||||
// [TMP-DEL 2026-05-07] keyup 은 객체선택 useEffect 가 lifecycle 관리. 여기서 지우면 wrappedKeyup 이 같이 날아감
|
removeDocumentEvent('keyup')
|
||||||
document.removeEventListener('click', handleClick)
|
document.removeEventListener('click', handleClick)
|
||||||
document.removeEventListener('click', handleOutsideClick)
|
document.removeEventListener('click', handleOutsideClick)
|
||||||
canvasProps?.upperCanvasEl.removeEventListener('contextmenu', handleContextMenu) //한번 노출 후 이벤트 삭제
|
canvasProps?.upperCanvasEl.removeEventListener('contextmenu', handleContextMenu) //한번 노출 후 이벤트 삭제
|
||||||
}
|
}
|
||||||
}, [contextRef, contextMenuList, currentObject])
|
}, [contextRef, contextMenuList, currentObject])
|
||||||
|
|
||||||
// [TMP-DEL 2026-05-07] 객체 선택 시 Del 키로 즉시 삭제. 메뉴 단축키(M/C 등)는 기존 handleKeyup 으로 위임.
|
|
||||||
// input/textarea/contentEditable 포커스 중에는 무시.
|
|
||||||
useEffect(() => {
|
|
||||||
if (!currentObject) {
|
|
||||||
removeDocumentEvent('keyup')
|
|
||||||
return
|
|
||||||
}
|
|
||||||
const wrappedKeyup = (e) => {
|
|
||||||
const el = document.activeElement
|
|
||||||
if (el && (el.tagName === 'INPUT' || el.tagName === 'TEXTAREA' || el.isContentEditable)) return
|
|
||||||
if (e.key === 'Delete' || e.key === 'Backspace') {
|
|
||||||
triggerDeleteRef.current()
|
|
||||||
return
|
|
||||||
}
|
|
||||||
handleKeyupRef.current(e)
|
|
||||||
}
|
|
||||||
addDocumentEventListener('keyup', document, wrappedKeyup)
|
|
||||||
return () => removeDocumentEvent('keyup')
|
|
||||||
}, [currentObject])
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
{contextMenu.visible && (
|
{contextMenu.visible && (
|
||||||
|
|||||||
@ -114,24 +114,6 @@ export function useContextMenu() {
|
|||||||
if (menu) handleClick(null, menu)
|
if (menu) handleClick(null, menu)
|
||||||
}
|
}
|
||||||
|
|
||||||
// [TMP-DEL 2026-05-07] Del 키용: 현재 contextMenu 에서 삭제 메뉴를 찾아 실행
|
|
||||||
// 매칭 규칙: id === 'remove' 또는 id 가 'Remove' 로 끝남 (단, 'wallLineRemove' 제외, 'RemoveAll' 제외)
|
|
||||||
const triggerDelete = () => {
|
|
||||||
let target = null
|
|
||||||
for (const group of contextMenu) {
|
|
||||||
for (const item of group) {
|
|
||||||
const id = item?.id || ''
|
|
||||||
if (id === 'wallLineRemove') continue
|
|
||||||
if (id === 'remove' || id.endsWith('Remove')) {
|
|
||||||
target = item
|
|
||||||
break
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (target) break
|
|
||||||
}
|
|
||||||
if (target?.fn) handleClick(null, target)
|
|
||||||
}
|
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
currentMenuSetting()
|
currentMenuSetting()
|
||||||
}, [gridColor, currentMenu])
|
}, [gridColor, currentMenu])
|
||||||
@ -150,7 +132,8 @@ export function useContextMenu() {
|
|||||||
[
|
[
|
||||||
{
|
{
|
||||||
id: 'dormerRemove',
|
id: 'dormerRemove',
|
||||||
name: getMessage('contextmenu.remove'),
|
shortcut: ['d', 'D'],
|
||||||
|
name: `${getMessage('contextmenu.remove')}(D)`,
|
||||||
fn: () => deleteObject(),
|
fn: () => deleteObject(),
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
@ -223,7 +206,8 @@ export function useContextMenu() {
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
id: 'roofMaterialRemove',
|
id: 'roofMaterialRemove',
|
||||||
name: getMessage('contextmenu.remove'),
|
shortcut: ['d', 'D'],
|
||||||
|
name: `${getMessage('contextmenu.remove')}(D)`,
|
||||||
fn: () => deleteObject(),
|
fn: () => deleteObject(),
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
@ -316,7 +300,8 @@ export function useContextMenu() {
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
id: 'roofMaterialRemove',
|
id: 'roofMaterialRemove',
|
||||||
name: getMessage('contextmenu.remove'),
|
shortcut: ['d', 'D'],
|
||||||
|
name: `${getMessage('contextmenu.remove')}(D)`,
|
||||||
fn: () => deleteObject(),
|
fn: () => deleteObject(),
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
@ -379,7 +364,8 @@ export function useContextMenu() {
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
id: 'auxiliaryRemove',
|
id: 'auxiliaryRemove',
|
||||||
name: getMessage('contextmenu.auxiliary.remove'),
|
shortcut: ['d', 'D'],
|
||||||
|
name: `${getMessage('contextmenu.auxiliary.remove')}(D)`,
|
||||||
fn: () => {
|
fn: () => {
|
||||||
if (!currentObject) return
|
if (!currentObject) return
|
||||||
const roof = canvas.getObjects().filter((obj) => obj.id === currentObject.attributes.roofId)[0]
|
const roof = canvas.getObjects().filter((obj) => obj.id === currentObject.attributes.roofId)[0]
|
||||||
@ -488,7 +474,8 @@ export function useContextMenu() {
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
id: 'openingRemove',
|
id: 'openingRemove',
|
||||||
name: getMessage('contextmenu.remove'),
|
shortcut: ['d', 'D'],
|
||||||
|
name: `${getMessage('contextmenu.remove')}(D)`,
|
||||||
fn: () => deleteObject(),
|
fn: () => deleteObject(),
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
@ -690,7 +677,8 @@ export function useContextMenu() {
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
id: 'remove',
|
id: 'remove',
|
||||||
name: getMessage('contextmenu.remove'),
|
shortcut: ['d', 'D'],
|
||||||
|
name: `${getMessage('contextmenu.remove')}(D)`,
|
||||||
fn: () => deleteObject(),
|
fn: () => deleteObject(),
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
@ -985,6 +973,5 @@ export function useContextMenu() {
|
|||||||
setCurrentContextMenu,
|
setCurrentContextMenu,
|
||||||
handleClick,
|
handleClick,
|
||||||
handleKeyup,
|
handleKeyup,
|
||||||
triggerDelete, // [TMP-DEL 2026-05-07]
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user