Compare commits
1 Commits
jtran/fix-
...
franknoiro
Author | SHA1 | Date | |
---|---|---|---|
c03357d897 |
@ -34,7 +34,7 @@ const FRAMES_TO_ANIMATE_IN = 30
|
||||
|
||||
const tempQuaternion = new Quaternion() // just used for maths
|
||||
|
||||
type interactionType = 'pan' | 'rotate' | 'zoom'
|
||||
export type CameraInteractionType = 'pan' | 'rotate' | 'zoom'
|
||||
|
||||
interface ThreeCamValues {
|
||||
position: Vector3
|
||||
@ -1219,8 +1219,8 @@ function _getInteractionType(
|
||||
enablePan: boolean,
|
||||
enableRotate: boolean,
|
||||
enableZoom: boolean
|
||||
): interactionType | 'none' {
|
||||
let state: interactionType | 'none' = 'none'
|
||||
): CameraInteractionType | 'none' {
|
||||
let state: CameraInteractionType | 'none' = 'none'
|
||||
if (enablePan && interactionGuards.pan.callback(event)) return 'pan'
|
||||
if (enableRotate && interactionGuards.rotate.callback(event)) return 'rotate'
|
||||
if (enableZoom && interactionGuards.zoom.dragCallback(event)) return 'zoom'
|
||||
|
@ -105,7 +105,7 @@ export const ModelingMachineProvider = ({
|
||||
settings: {
|
||||
context: {
|
||||
app: { theme, enableSSAO },
|
||||
modeling: { defaultUnit, highlightEdges, showScaleGrid },
|
||||
modeling: { defaultUnit, highlightEdges, showScaleGrid, mouseControls },
|
||||
},
|
||||
},
|
||||
} = useSettingsAuthContext()
|
||||
@ -509,6 +509,7 @@ export const ModelingMachineProvider = ({
|
||||
settings: {
|
||||
theme: theme.current,
|
||||
highlightEdges: highlightEdges.current,
|
||||
mouseControls: mouseControls.current,
|
||||
},
|
||||
}).catch(reportRejection)
|
||||
},
|
||||
|
@ -5,7 +5,7 @@ import { isDesktop } from 'lib/isDesktop'
|
||||
import { PATHS } from 'lib/paths'
|
||||
import toast from 'react-hot-toast'
|
||||
import { TextToCad_type } from '@kittycad/lib/dist/types/src/models'
|
||||
import { useCallback, useEffect, useRef, useState } from 'react'
|
||||
import { useCallback, useEffect, useMemo, useRef, useState } from 'react'
|
||||
import {
|
||||
Box3,
|
||||
Color,
|
||||
@ -15,6 +15,7 @@ import {
|
||||
LineSegments,
|
||||
Mesh,
|
||||
MeshBasicMaterial,
|
||||
MOUSE,
|
||||
OrthographicCamera,
|
||||
Scene,
|
||||
Vector3,
|
||||
@ -29,6 +30,15 @@ import { commandBarMachine } from 'machines/commandBarMachine'
|
||||
import { EventFrom } from 'xstate'
|
||||
import { fileMachine } from 'machines/fileMachine'
|
||||
import { reportRejection } from 'lib/trap'
|
||||
import {
|
||||
CameraControls,
|
||||
CameraInteractionType,
|
||||
} from 'clientSideScene/CameraControls'
|
||||
import {
|
||||
cameraMouseDragGuards,
|
||||
CameraSystem,
|
||||
MouseGuard,
|
||||
} from 'lib/cameraControls'
|
||||
|
||||
const CANVAS_SIZE = 128
|
||||
const PROMPT_TRUNCATE_LENGTH = 128
|
||||
@ -118,8 +128,14 @@ export function ToastTextToCadSuccess({
|
||||
settings: {
|
||||
theme: Themes
|
||||
highlightEdges: boolean
|
||||
mouseControls: CameraSystem
|
||||
}
|
||||
}) {
|
||||
const interactionGuards = useMemo(
|
||||
() => cameraMouseDragGuards[settings.mouseControls],
|
||||
[settings.mouseControls]
|
||||
)
|
||||
const controlsRef = useRef<OrbitControls | null>(null)
|
||||
const wrapperRef = useRef<HTMLDivElement | null>(null)
|
||||
const canvasRef = useRef<HTMLCanvasElement | null>(null)
|
||||
const animationRequestRef = useRef<number>()
|
||||
@ -168,8 +184,59 @@ export function ToastTextToCadSuccess({
|
||||
const ambientLight = new DirectionalLight(new Color('white'), 8.0)
|
||||
scene.add(ambientLight)
|
||||
const camera = createCamera()
|
||||
// Because this listener is registered before the OrbitControls are created,
|
||||
// it runs first and can block the OrbitControls from working.
|
||||
renderer.domElement.addEventListener('pointerdown', (e) => {
|
||||
if (!controlsRef.current) return
|
||||
const newInteractionType = getCameraInteractionType({
|
||||
interactionGuards,
|
||||
event: e,
|
||||
})
|
||||
console.log('newInteractionType', newInteractionType)
|
||||
|
||||
if (newInteractionType === 'none') {
|
||||
e.stopImmediatePropagation()
|
||||
}
|
||||
|
||||
/**
|
||||
* Update the OrbitControls to enable only the current interaction type.
|
||||
* This is a hack to override the interaction types of the OrbitControls
|
||||
* to match ours. In the future, we should roll our own class based on OrbitControls,
|
||||
* which can handle interaction guards that are more complex than just mouse buttons.
|
||||
*/
|
||||
if (newInteractionType === 'pan') {
|
||||
controlsRef.current.enablePan = true
|
||||
controlsRef.current.enableZoom = false
|
||||
controlsRef.current.enableRotate = false
|
||||
controlsRef.current.mouseButtons = {
|
||||
LEFT: MOUSE.PAN,
|
||||
MIDDLE: MOUSE.PAN,
|
||||
RIGHT: MOUSE.PAN,
|
||||
}
|
||||
} else if (newInteractionType === 'zoom') {
|
||||
controlsRef.current.enablePan = false
|
||||
controlsRef.current.enableZoom = true
|
||||
controlsRef.current.enableRotate = false
|
||||
controlsRef.current.mouseButtons = {
|
||||
LEFT: MOUSE.DOLLY,
|
||||
MIDDLE: MOUSE.DOLLY,
|
||||
RIGHT: MOUSE.DOLLY,
|
||||
}
|
||||
} else if (newInteractionType === 'rotate') {
|
||||
controlsRef.current.enablePan = false
|
||||
controlsRef.current.enableZoom = false
|
||||
controlsRef.current.enableRotate = true
|
||||
controlsRef.current.mouseButtons = {
|
||||
LEFT: MOUSE.ROTATE,
|
||||
MIDDLE: MOUSE.ROTATE,
|
||||
RIGHT: MOUSE.ROTATE,
|
||||
}
|
||||
}
|
||||
|
||||
controls.update()
|
||||
})
|
||||
const controls = new OrbitControls(camera, renderer.domElement)
|
||||
controls.enableDamping = true
|
||||
controlsRef.current = controls
|
||||
const loader = new GLTFLoader()
|
||||
const dracoLoader = new DRACOLoader()
|
||||
dracoLoader.setDecoderPath('/examples/jsm/libs/draco/')
|
||||
@ -270,7 +337,7 @@ export function ToastTextToCadSuccess({
|
||||
}, [])
|
||||
|
||||
return (
|
||||
<div className="flex gap-4 min-w-80" ref={wrapperRef}>
|
||||
<div className="flex gap-4 min-w-80 user-select-none" ref={wrapperRef}>
|
||||
<div
|
||||
className="flex-none overflow-hidden"
|
||||
style={{ width: CANVAS_SIZE + 'px', height: CANVAS_SIZE + 'px' }}
|
||||
@ -411,3 +478,22 @@ function traverseSceneToStyleObjects({
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
function getCameraInteractionType({
|
||||
interactionGuards,
|
||||
event,
|
||||
}: {
|
||||
interactionGuards: MouseGuard
|
||||
event: MouseEvent
|
||||
}): CameraInteractionType | 'none' {
|
||||
if (interactionGuards.pan.callback(event)) {
|
||||
return 'pan'
|
||||
}
|
||||
if (interactionGuards.zoom.dragCallback(event)) {
|
||||
return 'zoom'
|
||||
}
|
||||
if (interactionGuards.rotate.callback(event)) {
|
||||
return 'rotate'
|
||||
}
|
||||
return 'none'
|
||||
}
|
||||
|
@ -6,7 +6,7 @@ const META =
|
||||
PLATFORM === 'macos' ? 'Cmd' : PLATFORM === 'windows' ? 'Win' : 'Super'
|
||||
const ALT = PLATFORM === 'macos' ? 'Option' : 'Alt'
|
||||
|
||||
const noModifiersPressed = (e: React.MouseEvent) =>
|
||||
const noModifiersPressed = (e: React.MouseEvent | MouseEvent) =>
|
||||
!e.ctrlKey && !e.shiftKey && !e.altKey && !e.metaKey
|
||||
|
||||
export type CameraSystem =
|
||||
@ -53,14 +53,14 @@ export function mouseControlsToCameraSystem(
|
||||
|
||||
interface MouseGuardHandler {
|
||||
description: string
|
||||
callback: (e: React.MouseEvent) => boolean
|
||||
callback: (e: React.MouseEvent | MouseEvent) => boolean
|
||||
lenientDragStartButton?: number
|
||||
}
|
||||
|
||||
interface MouseGuardZoomHandler {
|
||||
description: string
|
||||
dragCallback: (e: React.MouseEvent) => boolean
|
||||
scrollCallback: (e: React.MouseEvent) => boolean
|
||||
dragCallback: (e: React.MouseEvent | MouseEvent) => boolean
|
||||
scrollCallback: (e: React.MouseEvent | MouseEvent) => boolean
|
||||
lenientDragStartButton?: number
|
||||
}
|
||||
|
||||
@ -70,7 +70,7 @@ export interface MouseGuard {
|
||||
rotate: MouseGuardHandler
|
||||
}
|
||||
|
||||
export const btnName = (e: React.MouseEvent) => ({
|
||||
export const btnName = (e: React.MouseEvent | MouseEvent) => ({
|
||||
middle: !!(e.buttons & 4) || e.button === 1,
|
||||
right: !!(e.buttons & 2) || e.button === 2,
|
||||
left: !!(e.buttons & 1) || e.button === 0,
|
||||
|
@ -16,6 +16,7 @@ import { commandBarMachine } from 'machines/commandBarMachine'
|
||||
import { getNextFileName } from './desktopFS'
|
||||
import { reportRejection } from './trap'
|
||||
import { toSync } from './utils'
|
||||
import { CameraSystem } from './cameraControls'
|
||||
|
||||
export async function submitTextToCadPrompt(
|
||||
prompt: string,
|
||||
@ -77,6 +78,7 @@ interface TextToKclProps {
|
||||
settings: {
|
||||
theme: Themes
|
||||
highlightEdges: boolean
|
||||
mouseControls: CameraSystem
|
||||
}
|
||||
}
|
||||
|
||||
|
Reference in New Issue
Block a user