import { IdeContext } from 'src/components/IdeToolbarNew'
import { useRef, useState, useEffect, useContext, useMemo } from 'react'
import { Canvas, extend, useFrame, useThree } from 'react-three-fiber'
import { OrbitControls } from 'three/examples/jsm/controls/OrbitControls'
extend({ OrbitControls })
function Controls({ onCameraChange }) {
const controls = useRef()
const { scene, camera, gl } = useThree()
useEffect(() => {
// init camera position
camera.position.x = 12
camera.position.y = 12
// Euler rotation can be problematic since order matters
// We want it to rotate around the z or vertical axis first then the x axis
// in Three Y is the vertical axis (Z for openscad)
camera.rotation._order = 'YXZ'
if (controls.current) {
const callback = ({ target }) => {
const getRotations = () => {
const { x, y, z } = target.object.rotation
const rad2Deg = 180 / Math.PI
const scadX = (x + Math.PI / 2) * rad2Deg
const scadZ = y * rad2Deg
const scadY = z * rad2Deg
return [scadX, scadY, scadZ]
}
const getPositions = () => {
const { x: scadX, y: scadZ, z: negScadY } = target.object.position
const scale = 10 // I'm not sure why this is exactly 10
const scadY = -negScadY
return [scadX * scale, scadY * scale, scadZ * scale]
}
const [rx, ry, rz] = getRotations()
const [x, y, z] = getPositions()
onCameraChange({
position: { x, y, z },
rotation: { x: rx, y: ry, z: rz },
})
}
controls.current.addEventListener('end', callback)
const oldCurrent = controls.current
return () => oldCurrent.removeEventListener('end', callback)
}
}, [])
useFrame(() => controls.current.update())
return (