fix level window tools
This commit is contained in:
@@ -1,6 +1,7 @@
|
||||
import {
|
||||
type AnyNodeId,
|
||||
emitter,
|
||||
sceneRegistry,
|
||||
useScene,
|
||||
type WallEvent,
|
||||
WindowNode,
|
||||
@@ -77,6 +78,11 @@ export const MoveWindowTool: React.FC<{ node: WindowNode }> = ({ node: movingWin
|
||||
if (wallId) useScene.getState().dirtyNodes.add(wallId as AnyNodeId)
|
||||
}
|
||||
|
||||
const getLevelYOffset = () => {
|
||||
const id = useViewer.getState().selection.levelId
|
||||
return id ? (sceneRegistry.nodes.get(id as AnyNodeId)?.position.y ?? 0) : 0
|
||||
}
|
||||
|
||||
const hideCursor = () => {
|
||||
if (cursorGroupRef.current) cursorGroupRef.current.visible = false
|
||||
}
|
||||
@@ -128,7 +134,7 @@ export const MoveWindowTool: React.FC<{ node: WindowNode }> = ({ node: movingWin
|
||||
movingWindowNode.id,
|
||||
)
|
||||
|
||||
updateCursor(wallLocalToWorld(event.node, clampedX, clampedY), cursorRotation, valid)
|
||||
updateCursor(wallLocalToWorld(event.node, clampedX, clampedY, getLevelYOffset()), cursorRotation, valid)
|
||||
event.stopPropagation()
|
||||
}
|
||||
|
||||
@@ -166,7 +172,7 @@ export const MoveWindowTool: React.FC<{ node: WindowNode }> = ({ node: movingWin
|
||||
movingWindowNode.id,
|
||||
)
|
||||
|
||||
updateCursor(wallLocalToWorld(event.node, clampedX, clampedY), cursorRotation, valid)
|
||||
updateCursor(wallLocalToWorld(event.node, clampedX, clampedY, getLevelYOffset()), cursorRotation, valid)
|
||||
event.stopPropagation()
|
||||
}
|
||||
|
||||
|
||||
@@ -1,13 +1,16 @@
|
||||
import { type AnyNodeId, type ItemNode, useScene, type WallNode, type WindowNode } from '@pascal-app/core'
|
||||
|
||||
/**
|
||||
* Converts wall-local (X along wall, Y = height) to world XYZ.
|
||||
* Wall-local Y maps directly to world Y; X maps along the wall direction.
|
||||
* Converts wall-local (X along wall, Y = height above level floor) to world XYZ.
|
||||
* Wall XZ uses level-local coordinates (levels only offset in Y, not XZ).
|
||||
* Pass levelYOffset (the level group's current world Y) so the cursor lands at the
|
||||
* correct world height when the cursor group is at the scene root.
|
||||
*/
|
||||
export function wallLocalToWorld(
|
||||
wallNode: WallNode,
|
||||
localX: number,
|
||||
localY: number,
|
||||
levelYOffset = 0,
|
||||
): [number, number, number] {
|
||||
const wallAngle = Math.atan2(
|
||||
wallNode.end[1] - wallNode.start[1],
|
||||
@@ -15,7 +18,7 @@ export function wallLocalToWorld(
|
||||
)
|
||||
return [
|
||||
wallNode.start[0] + localX * Math.cos(wallAngle),
|
||||
localY,
|
||||
localY + levelYOffset,
|
||||
wallNode.start[1] + localX * Math.sin(wallAngle),
|
||||
]
|
||||
}
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
import {
|
||||
type AnyNodeId,
|
||||
emitter,
|
||||
sceneRegistry,
|
||||
useScene,
|
||||
type WallEvent,
|
||||
WindowNode,
|
||||
@@ -39,6 +40,10 @@ export const WindowTool: React.FC = () => {
|
||||
useScene.temporal.getState().pause()
|
||||
|
||||
const getLevelId = () => useViewer.getState().selection.levelId
|
||||
const getLevelYOffset = () => {
|
||||
const id = getLevelId()
|
||||
return id ? (sceneRegistry.nodes.get(id as AnyNodeId)?.position.y ?? 0) : 0
|
||||
}
|
||||
|
||||
const markWallDirty = (wallId: string) => {
|
||||
useScene.getState().dirtyNodes.add(wallId as AnyNodeId)
|
||||
@@ -103,7 +108,7 @@ export const WindowTool: React.FC = () => {
|
||||
|
||||
const valid = !hasWallChildOverlap(event.node.id, clampedX, clampedY, width, height, node.id)
|
||||
|
||||
updateCursor(wallLocalToWorld(event.node, clampedX, clampedY), cursorRotation, valid)
|
||||
updateCursor(wallLocalToWorld(event.node, clampedX, clampedY, getLevelYOffset()), cursorRotation, valid)
|
||||
event.stopPropagation()
|
||||
}
|
||||
|
||||
@@ -137,7 +142,7 @@ export const WindowTool: React.FC = () => {
|
||||
draftRef.current?.id,
|
||||
)
|
||||
|
||||
updateCursor(wallLocalToWorld(event.node, clampedX, clampedY), cursorRotation, valid)
|
||||
updateCursor(wallLocalToWorld(event.node, clampedX, clampedY, getLevelYOffset()), cursorRotation, valid)
|
||||
event.stopPropagation()
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user