New: Store the editorOpen state in Theatre
This commit is contained in:
parent
08759e2d5c
commit
6ac6aa87d7
4 changed files with 56 additions and 94 deletions
|
@ -1,4 +1,5 @@
|
|||
import type {VFC} from 'react'
|
||||
import {useLayoutEffect} from 'react'
|
||||
import React, {useEffect, useRef, Suspense} from 'react'
|
||||
import {Canvas} from '@react-three/fiber'
|
||||
import {useEditorStore} from '../store'
|
||||
|
@ -8,8 +9,9 @@ import root from 'react-shadow'
|
|||
import styles from '../bundle.css.txt'
|
||||
import UI from './UI'
|
||||
import ProxyManager from './ProxyManager'
|
||||
import {Button, Heading, Code, PortalManager, IdProvider} from './elements'
|
||||
import {Button, PortalManager, IdProvider} from './elements'
|
||||
import studio from '@theatre/studio'
|
||||
import {useVal} from '@theatre/dataverse-react'
|
||||
|
||||
const EditorScene = () => {
|
||||
const orbitControlsRef = useRef<typeof OrbitControls>()
|
||||
|
@ -60,24 +62,25 @@ const EditorScene = () => {
|
|||
}
|
||||
|
||||
const Editor: VFC = () => {
|
||||
const [
|
||||
sceneSnapshot,
|
||||
editorOpen,
|
||||
initialState,
|
||||
initialEditorCamera,
|
||||
setEditorOpen,
|
||||
createSnapshot,
|
||||
] = useEditorStore(
|
||||
(state) => [
|
||||
state.sceneSnapshot,
|
||||
state.editorOpen,
|
||||
state.initialState,
|
||||
state.initialEditorCamera,
|
||||
state.setEditorOpen,
|
||||
state.createSnapshot,
|
||||
],
|
||||
shallow,
|
||||
)
|
||||
const [editorObject, sceneSnapshot, initialEditorCamera, createSnapshot] =
|
||||
useEditorStore(
|
||||
(state) => [
|
||||
state.editorObject,
|
||||
state.sceneSnapshot,
|
||||
state.initialEditorCamera,
|
||||
state.createSnapshot,
|
||||
],
|
||||
shallow,
|
||||
)
|
||||
|
||||
const editorOpen = !!useVal(editorObject?.props._isOpen)
|
||||
useLayoutEffect(() => {
|
||||
if (editorOpen) {
|
||||
createSnapshot()
|
||||
}
|
||||
}, [editorOpen])
|
||||
|
||||
if (!editorObject) return <></>
|
||||
|
||||
return (
|
||||
<root.div>
|
||||
|
@ -110,67 +113,15 @@ const Editor: VFC = () => {
|
|||
|
||||
<UI />
|
||||
</>
|
||||
) : (
|
||||
<div className="flex justify-center items-center bg-white h-screen">
|
||||
<div className="flex flex-col gap-5 items-center ">
|
||||
<Heading className="text-2xl mb-4">
|
||||
No canvas connected
|
||||
</Heading>
|
||||
<div>
|
||||
Please use <Code>configure()</Code> and{' '}
|
||||
<Code>bind()</Code> to connect a canvas to React Three
|
||||
Editable.
|
||||
</div>
|
||||
<Code block>
|
||||
{`import React from 'react';
|
||||
import { Canvas } from '@react-three/fiber';
|
||||
import { configure, editable as e } from 'react-three-editable';
|
||||
|
||||
const bind = configure({
|
||||
localStorageNamespace: "MyProject"
|
||||
});
|
||||
|
||||
const MyComponent = () => (
|
||||
<Canvas onCreated={bind()}>
|
||||
<e.mesh uniqueName="My First Editable Object">
|
||||
<sphereBufferGeometry />
|
||||
<meshStandardMaterial color="rebeccapurple" />
|
||||
</e.mesh>
|
||||
</Canvas>
|
||||
);`}
|
||||
</Code>
|
||||
<div>
|
||||
For more details, please consult the{' '}
|
||||
<a
|
||||
className="rounded-md font-medium text-green-600 hover:text-green-500"
|
||||
href="https://github.com/AndrewPrifer/react-three-editable"
|
||||
rel="noreferrer"
|
||||
target="_blank"
|
||||
>
|
||||
documentation
|
||||
</a>
|
||||
.
|
||||
</div>
|
||||
<Button
|
||||
className=""
|
||||
onClick={() => {
|
||||
setEditorOpen(false)
|
||||
}}
|
||||
>
|
||||
Close
|
||||
</Button>
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
) : null}
|
||||
</div>
|
||||
{editorOpen || (
|
||||
<Button
|
||||
className="fixed bottom-5 left-5"
|
||||
onClick={() => {
|
||||
if (!sceneSnapshot) {
|
||||
createSnapshot()
|
||||
}
|
||||
setEditorOpen(true)
|
||||
studio.transaction(({set}) => {
|
||||
set(editorObject.props._isOpen, 1)
|
||||
})
|
||||
}}
|
||||
>
|
||||
Editor
|
||||
|
|
|
@ -145,10 +145,11 @@ const ProxyManager: VFC<ProxyManagerProps> = ({orbitControlsRef}) => {
|
|||
setRenderMaterials(renderMaterials)
|
||||
|
||||
return () => {
|
||||
Object.entries(renderMaterials).forEach(([id, material]) => {
|
||||
;(sceneProxy.getObjectById(Number.parseInt(id)) as Mesh).material =
|
||||
material
|
||||
})
|
||||
// @todo do we need this cleanup?
|
||||
// Object.entries(renderMaterials).forEach(([id, material]) => {
|
||||
// ;(sceneProxy.getObjectById(Number.parseInt(id)) as Mesh).material =
|
||||
// material
|
||||
// })
|
||||
}
|
||||
}, [sceneProxy])
|
||||
|
||||
|
|
|
@ -11,9 +11,11 @@ import {Vector3} from 'three'
|
|||
import {IconButton, Button, SettingsButton} from './elements'
|
||||
import ViewportSettings from './ViewportSettings'
|
||||
import type {$FixMe} from '@theatre/shared/utils/types'
|
||||
import studio from '@theatre/studio'
|
||||
|
||||
const UI: VFC = () => {
|
||||
const [
|
||||
editorObject,
|
||||
transformControlsMode,
|
||||
transformControlsSpace,
|
||||
viewportShading,
|
||||
|
@ -21,9 +23,9 @@ const UI: VFC = () => {
|
|||
setTransformControlsMode,
|
||||
setTransformControlsSpace,
|
||||
setViewportShading,
|
||||
setEditorOpen,
|
||||
] = useEditorStore(
|
||||
(state) => [
|
||||
state.editorObject,
|
||||
state.transformControlsMode,
|
||||
state.transformControlsSpace,
|
||||
state.viewportShading,
|
||||
|
@ -31,11 +33,12 @@ const UI: VFC = () => {
|
|||
state.setTransformControlsMode,
|
||||
state.setTransformControlsSpace,
|
||||
state.setViewportShading,
|
||||
state.setEditorOpen,
|
||||
],
|
||||
shallow,
|
||||
)
|
||||
|
||||
if (!editorObject) return <></>
|
||||
|
||||
return (
|
||||
<div className="absolute inset-0 z-50 pointer-events-none">
|
||||
<div className="flex h-full">
|
||||
|
@ -134,7 +137,11 @@ const UI: VFC = () => {
|
|||
{/* Bottom-left corner*/}
|
||||
<Button
|
||||
className="absolute left-0 bottom-0 pointer-events-auto"
|
||||
onClick={() => setEditorOpen(false)}
|
||||
onClick={() =>
|
||||
studio.transaction(({set}) => {
|
||||
set(editorObject.props._isOpen, 0)
|
||||
})
|
||||
}
|
||||
>
|
||||
Close
|
||||
</Button>
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue