浏览代码

More meshes for preview - #6012

David Catuhe 6 年之前
父节点
当前提交
b40335c2f6

+ 41 - 7
nodeEditor/src/previewManager.ts

@@ -1,4 +1,4 @@
-import { GlobalState } from './globalState';
+import { GlobalState } from '../../globalState';
 import { NodeMaterial } from 'babylonjs/Materials/Node/nodeMaterial';
 import { Nullable } from 'babylonjs/types';
 import { Observer } from 'babylonjs/Misc/observable';
@@ -8,37 +8,48 @@ import { Mesh } from 'babylonjs/Meshes/mesh';
 import { Vector3 } from 'babylonjs/Maths/math.vector';
 import { HemisphericLight } from 'babylonjs/Lights/hemisphericLight';
 import { ArcRotateCamera } from 'babylonjs/Cameras/arcRotateCamera';
+import { PreviewMeshType } from './previewMeshType';
 
 export class PreviewManager {
     private _nodeMaterial: NodeMaterial;
-    private _onBuildObserver: Nullable<Observer<NodeMaterial>>;
+    private _onBuildObserver: Nullable<Observer<NodeMaterial>>;    
+    private _onPreviewMeshTypeChangedObserver: Nullable<Observer<void>>;
     private _engine: Engine;
     private _scene: Scene;
     private _light: HemisphericLight;
-    private _dummySphere: Mesh;
+    private _dummy: Mesh;
     private _camera: ArcRotateCamera;
     private _material: NodeMaterial;
+    private _globalState: GlobalState;    
 
     public constructor(targetCanvas: HTMLCanvasElement, globalState: GlobalState) {
         this._nodeMaterial = globalState.nodeMaterial;
+        this._globalState = globalState;
 
         this._onBuildObserver = this._nodeMaterial.onBuildObservable.add((nodeMaterial) => {
             let serializationObject = nodeMaterial.serialize();
             this._updatePreview(serializationObject);
         });
 
+        this._onPreviewMeshTypeChangedObserver = globalState.onPreviewMeshTypeChanged.add(() => {
+            this._refreshPreviewMesh();
+        });
+
         this._engine = new Engine(targetCanvas, true);
         this._scene = new Scene(this._engine);
         this._camera = new ArcRotateCamera("Camera", 0, 0.8, 4, Vector3.Zero(), this._scene);
         this._light = new HemisphericLight("light", new Vector3(0, 1, 0), this._scene);
 
-        this._dummySphere = Mesh.CreateSphere("sphere", 32, 2, this._scene);
 
-        this._camera.lowerRadiusLimit = 2.5;
+        this._camera.lowerRadiusLimit = 3;
         this._camera.upperRadiusLimit = 10;
+        this._camera.wheelPrecision = 10;
         this._camera.attachControl(targetCanvas, false);
 
+        this._refreshPreviewMesh();
+
         this._engine.runRenderLoop(() => {
+            this._engine.resize();
             this._scene.render();
         });
 
@@ -46,6 +57,28 @@ export class PreviewManager {
         this._updatePreview(serializationObject);
     }
 
+    private _refreshPreviewMesh() {    
+        if (this._dummy) {
+            this._dummy.dispose();
+        }
+        
+        switch (this._globalState.previewMeshType) {
+            case PreviewMeshType.Box:
+                this._dummy = Mesh.CreateBox("dummy", 2, this._scene);
+                break;
+            case PreviewMeshType.Sphere:
+                this._dummy = Mesh.CreateSphere("dummy", 32, 2, this._scene);
+                break;
+            case PreviewMeshType.Torus:
+                this._dummy = Mesh.CreateTorus("dummy", 2, 0.5, 32, this._scene);
+                break;
+                case PreviewMeshType.Cylinder:
+                this._dummy = Mesh.CreateCylinder("dummy", 2, 1, 1.2, 32, 1, this._scene);
+                break;                
+        }
+        this._dummy.material = this._material;
+    }
+
     private _updatePreview(serializationObject: any) {
         if (this._material) {
             this._material.dispose();
@@ -53,18 +86,19 @@ export class PreviewManager {
 
         this._material = NodeMaterial.Parse(serializationObject, this._scene);
         this._material.build(true);
-        this._dummySphere.material = this._material;
+        this._dummy.material = this._material;
     }
 
     public dispose() {
         this._nodeMaterial.onBuildObservable.remove(this._onBuildObserver);
+        this._globalState.onPreviewMeshTypeChanged.remove(this._onPreviewMeshTypeChangedObserver);
 
         if (this._material) {
             this._material.dispose();
         }
 
         this._camera.dispose();
-        this._dummySphere.dispose();
+        this._dummy.dispose();
         this._light.dispose();
         this._engine.dispose();
     }

+ 47 - 0
nodeEditor/src/components/preview/previewMeshControlComponent.tsx

@@ -0,0 +1,47 @@
+
+import * as React from "react";
+import { GlobalState } from '../../globalState';
+import { FontAwesomeIcon } from '@fortawesome/react-fontawesome';
+import { faCircle, faRing, faCube, faHockeyPuck } from '@fortawesome/free-solid-svg-icons';
+import { PreviewMeshType } from './previewMeshType';
+import { DataStorage } from '../../dataStorage';
+
+interface IPreviewMeshControlComponent {
+    globalState: GlobalState;
+}
+
+export class PreviewMeshControlComponent extends React.Component<IPreviewMeshControlComponent> {
+
+    changeMeshType(newOne: PreviewMeshType) {
+        if (this.props.globalState.previewMeshType === newOne) {
+            return;
+        }
+
+        this.props.globalState.previewMeshType = newOne;
+        this.props.globalState.onPreviewMeshTypeChanged.notifyObservers();
+
+        DataStorage.StoreNumber("PreviewMeshType", newOne);
+
+        this.forceUpdate();
+    }
+
+    render() {
+        return (
+            <div id="preview-mesh-bar">
+                <div onClick={() => this.changeMeshType(PreviewMeshType.Box)} className={"button" + (this.props.globalState.previewMeshType === PreviewMeshType.Box ? " selected" : "")}>
+                    <FontAwesomeIcon icon={faCube} />
+                </div>
+                <div onClick={() => this.changeMeshType(PreviewMeshType.Sphere)} className={"button" + (this.props.globalState.previewMeshType === PreviewMeshType.Sphere ? " selected" : "")}>
+                    <FontAwesomeIcon icon={faCircle} />
+                </div>
+                <div onClick={() => this.changeMeshType(PreviewMeshType.Torus)} className={"button" + (this.props.globalState.previewMeshType === PreviewMeshType.Torus ? " selected" : "")}>
+                    <FontAwesomeIcon icon={faRing} />
+                </div>
+                <div onClick={() => this.changeMeshType(PreviewMeshType.Cylinder)} className={"button" + (this.props.globalState.previewMeshType === PreviewMeshType.Cylinder ? " selected" : "")}>
+                    <FontAwesomeIcon icon={faHockeyPuck} />
+                </div>
+            </div>
+        );
+
+    }
+}

+ 6 - 0
nodeEditor/src/components/preview/previewMeshType.ts

@@ -0,0 +1,6 @@
+export enum PreviewMeshType {
+    Sphere,
+    Box, 
+    Torus,
+    Cylinder
+}

+ 8 - 0
nodeEditor/src/globalState.ts

@@ -6,6 +6,8 @@ import { LogEntry } from './components/log/logComponent';
 import { NodeModel } from 'storm-react-diagrams';
 import { INodeLocationInfo } from './nodeLocationInfo';
 import { NodeMaterialBlock } from 'babylonjs/Materials/Node/nodeMaterialBlock';
+import { PreviewMeshType } from './components/preview/previewMeshType';
+import { DataStorage } from './dataStorage';
 
 export class GlobalState {
     nodeMaterial: NodeMaterial;
@@ -19,5 +21,11 @@ export class GlobalState {
     onReOrganizedRequiredObservable = new Observable<void>();
     onLogRequiredObservable = new Observable<LogEntry>();
     onErrorMessageDialogRequiredObservable = new Observable<string>();
+    onPreviewMeshTypeChanged = new Observable<void>();
     onGetNodeFromBlock: (block: NodeMaterialBlock) => NodeModel;
+    previewMeshType: PreviewMeshType;
+
+    public constructor() {
+        this.previewMeshType = DataStorage.ReadNumber("PreviewMeshType", PreviewMeshType.Box);
+    }
 }

+ 3 - 1
nodeEditor/src/graphEditor.tsx

@@ -37,8 +37,9 @@ import { RemapNodeFactory } from './components/diagram/remap/remapNodeFactory';
 import { RemapNodeModel } from './components/diagram/remap/remapNodeModel';
 import { RemapBlock } from 'babylonjs/Materials/Node/Blocks/remapBlock';
 import { GraphHelper } from './graphHelper';
-import { PreviewManager } from './previewManager';
+import { PreviewManager } from './components/preview/previewManager';
 import { INodeLocationInfo } from './nodeLocationInfo';
+import { PreviewMeshControlComponent } from './components/preview/previewMeshControlComponent';
 
 require("storm-react-diagrams/dist/style.min.css");
 require("./main.scss");
@@ -501,6 +502,7 @@ export class GraphEditor extends React.Component<IGraphEditorProps> {
                     {/* Property tab */}
                     <div className="right-panel">
                         <PropertyTabComponent globalState={this.props.globalState} />
+                        <PreviewMeshControlComponent globalState={this.props.globalState} />
                         <div id="preview" style={{height: this._rightWidth + "px"}}>
                             <canvas id="preview-canvas"/>
                         </div>

+ 32 - 3
nodeEditor/src/main.scss

@@ -41,7 +41,7 @@
     grid-row: 1 / span 2;
     grid-column: 5;
     display: grid;
-    grid-template-rows: 1fr auto;
+    grid-template-rows: 1fr 30px auto;
     grid-template-columns: 100%;
 
     #propertyTab {
@@ -49,14 +49,43 @@
         grid-column: 1;
     }
 
+    #preview-mesh-bar {
+        grid-row: 2;
+        grid-column: 1;
+        display: flex;
+        color: white;
+        align-items: center;
+        font-size: 18px;
+
+        .button {
+            display: grid;
+            justify-content: center;
+            align-content: center;
+            height: 30px;
+            width: calc(100% / 4);
+            cursor: pointer;
+
+            &:hover {
+                background: rgb(51, 122, 183);
+                color: white;
+                opacity: 0.8;
+            }
+
+            &.selected {
+                background: rgb(51, 122, 183);
+                color: white;
+            }
+        }        
+    }
+    
     #preview {
         border-top: 1px solid rgb(85, 85, 85);
-        grid-row: 2;
+        grid-row: 3;
         grid-column: 1;
         width: 100%;
         display: grid;
         outline: 0 !important;
-        
+
         #preview-canvas {
             width: 100%;
             height: 100%;