David Catuhe 6 лет назад
Родитель
Сommit
9213faa024
5 измененных файлов с 74 добавлено и 10 удалено
  1. 18 1
      src/Meshes/abstractMesh.ts
  2. 7 2
      src/Meshes/instancedMesh.ts
  3. 32 4
      src/Meshes/mesh.ts
  4. 4 1
      src/Rendering/renderingGroup.ts
  5. 13 2
      src/scene.ts

+ 18 - 1
src/Meshes/abstractMesh.ts

@@ -25,6 +25,7 @@ import { AbstractActionManager } from '../Actions/abstractActionManager';
 declare type Ray = import("../Culling/ray").Ray;
 declare type Collider = import("../Collisions/collider").Collider;
 declare type TrianglePickingPredicate = import("../Culling/ray").TrianglePickingPredicate;
+declare type RenderingGroup = import("../Rendering/renderingGroup").RenderingGroup;
 
 /** @hidden */
 class _FacetDataStorage {
@@ -267,6 +268,11 @@ export class AbstractMesh extends TransformNode implements IDisposable, ICullabl
 
     private _visibility = 1.0;
 
+    /** @hidden */
+    public _isActive = false;
+    /** @hidden */
+    public _renderingGroup: RenderingGroup;
+
     /**
      * Gets or sets mesh visibility between 0 and 1 (default is 1)
      */
@@ -1025,8 +1031,19 @@ export class AbstractMesh extends TransformNode implements IDisposable, ICullabl
     }
 
     /** @hidden */
-    public _activate(renderId: number): void {
+    public _activate(renderId: number): boolean {
         this._renderId = renderId;
+        return true;
+    }
+
+    /** @hidden */
+    public _freeze() {
+        // Do nothing
+    }
+
+    /** @hidden */
+    public _unFreeze() {
+        // Do nothing
     }
 
     /**

+ 7 - 2
src/Meshes/instancedMesh.ts

@@ -259,11 +259,16 @@ export class InstancedMesh extends AbstractMesh {
     }
 
     /** @hidden */
-    public _activate(renderId: number): InstancedMesh {
+    public _activate(renderId: number): boolean {
         if (this._currentLOD) {
             this._currentLOD._registerInstanceForRenderId(this, renderId);
         }
-        return this;
+
+        if (this._edgesRenderer && this._edgesRenderer.isEnabled && this._sourceMesh._renderingGroup) {
+            this._sourceMesh._renderingGroup._edgesRenderers.push(this._edgesRenderer);
+        }
+
+        return !this._sourceMesh._isActive;
     }
 
     /**

+ 32 - 4
src/Meshes/mesh.ts

@@ -82,6 +82,9 @@ class _InstanceDataStorage {
     public instancesBuffer: Nullable<Buffer>;
     public instancesData: Float32Array;
     public overridenInstanceCount: number;
+    public isFrozen: boolean;
+    public _previousBatch: _InstancesBatch;
+    public hardwareInstancedRendering: boolean;
 }
 
 /**
@@ -91,6 +94,7 @@ export class _InstancesBatch {
     public mustReturn = false;
     public visibleInstances = new Array<Nullable<Array<InstancedMesh>>>();
     public renderSelf = new Array<boolean>();
+    public hardwareInstancedRendering = new Array<boolean>();
 }
 
 /**
@@ -437,6 +441,7 @@ export class Mesh extends AbstractMesh implements IGetSetVerticesData {
             this.parent = parent;
         }
 
+        this._instanceDataStorage.hardwareInstancedRendering = this.getEngine().getCaps().instancedArrays;
     }
 
     // Methods
@@ -1363,6 +1368,9 @@ export class Mesh extends AbstractMesh implements IGetSetVerticesData {
 
     /** @hidden */
     public _getInstancesRenderList(subMeshId: number): _InstancesBatch {
+        if (this._instanceDataStorage.isFrozen && this._instanceDataStorage._previousBatch) {
+            return this._instanceDataStorage._previousBatch;
+        }
         var scene = this.getScene();
         let batchCache = this._instanceDataStorage.batchCache;
         batchCache.mustReturn = false;
@@ -1396,7 +1404,8 @@ export class Mesh extends AbstractMesh implements IGetSetVerticesData {
             }
             this._instanceDataStorage.renderIdForInstances[subMeshId] = currentRenderId;
         }
-
+        batchCache.hardwareInstancedRendering[subMeshId] = this._instanceDataStorage.hardwareInstancedRendering && (batchCache.visibleInstances[subMeshId] !== null) && (batchCache.visibleInstances[subMeshId] !== undefined);
+        this._instanceDataStorage._previousBatch = batchCache;
         return batchCache;
     }
 
@@ -1502,6 +1511,25 @@ export class Mesh extends AbstractMesh implements IGetSetVerticesData {
         return this;
     }
 
+    /** @hidden */
+    public _freeze() {
+        this._instanceDataStorage.isFrozen = true;
+
+        if (!this.subMeshes) {
+            return;
+        }
+
+        // Prepare batches
+        for (var index = 0; index < this.subMeshes.length; index++) {
+            this._getInstancesRenderList(index);
+        }
+    }
+
+    /** @hidden */
+    public _unFreeze() {
+        this._instanceDataStorage.isFrozen = false;
+    }
+
     /**
      * Triggers the draw call for the mesh. Usually, you don't need to call this method by your own because the mesh rendering is handled by the scene rendering manager
      * @param subMesh defines the subMesh to render
@@ -1531,7 +1559,7 @@ export class Mesh extends AbstractMesh implements IGetSetVerticesData {
         }
 
         var engine = scene.getEngine();
-        var hardwareInstancedRendering = (engine.getCaps().instancedArrays) && (batch.visibleInstances[subMesh._id] !== null) && (batch.visibleInstances[subMesh._id] !== undefined);
+        var hardwareInstancedRendering = batch.hardwareInstancedRendering[subMesh._id];
 
         // Material
         let material = subMesh.getMaterial();
@@ -2420,7 +2448,7 @@ export class Mesh extends AbstractMesh implements IGetSetVerticesData {
                 for (var j = 0; j < 3; j++) {
                     a = vertexIndex[j];
                     b = vertexIndex[(j + 1) % 3];
-                    if (side[a] === undefined  && side[b] ===  undefined) {
+                    if (side[a] === undefined && side[b] === undefined) {
                         side[a] = new Array();
                         side[b] = new Array();
                     }
@@ -2432,7 +2460,7 @@ export class Mesh extends AbstractMesh implements IGetSetVerticesData {
                             side[b] = new Array();
                         }
                     }
-                    if (side[a][b]  === undefined  && side[b][a] === undefined) {
+                    if (side[a][b] === undefined && side[b][a] === undefined) {
                         side[a][b] = [];
                         deltaPosition.x = (positions[3 * b] - positions[3 * a]) / segments;
                         deltaPosition.y = (positions[3 * b + 1] - positions[3 * a + 1]) / segments;

+ 4 - 1
src/Rendering/renderingGroup.ts

@@ -34,7 +34,8 @@ export class RenderingGroup {
     private _renderAlphaTest: (subMeshes: SmartArray<SubMesh>) => void;
     private _renderTransparent: (subMeshes: SmartArray<SubMesh>) => void;
 
-    private _edgesRenderers = new SmartArray<IEdgesRenderer>(16);
+    /** @hidden */
+    public _edgesRenderers = new SmartArray<IEdgesRenderer>(16);
 
     public onBeforeTransparentRendering: () => void;
 
@@ -363,6 +364,8 @@ export class RenderingGroup {
             this._opaqueSubMeshes.push(subMesh); // Opaque
         }
 
+        mesh._renderingGroup = this;
+
         if (mesh._edgesRenderer && mesh._edgesRenderer.isEnabled) {
             this._edgesRenderers.push(mesh._edgesRenderer);
         }

+ 13 - 2
src/scene.ts

@@ -3869,6 +3869,10 @@ export class Scene extends AbstractScene implements IAnimatable {
 
         this._evaluateActiveMeshes();
         this._activeMeshesFrozen = true;
+
+        for (var mesh of this._activeMeshes.data) {
+            mesh._freeze();
+        }
         return this;
     }
 
@@ -3877,6 +3881,10 @@ export class Scene extends AbstractScene implements IAnimatable {
      * @returns the current scene
      */
     public unfreezeActiveMeshes(): Scene {
+        for (var mesh of this._activeMeshes.data) {
+            mesh._unFreeze();
+        }
+
         this._activeMeshesFrozen = false;
         return this;
     }
@@ -3918,6 +3926,7 @@ export class Scene extends AbstractScene implements IAnimatable {
         const len = meshes.length;
         for (let i = 0; i < len; i++) {
             const mesh = meshes.data[i];
+            mesh._isActive = false;
             if (mesh.isBlocked) {
                 continue;
             }
@@ -3952,12 +3961,14 @@ export class Scene extends AbstractScene implements IAnimatable {
                 this._activeMeshes.push(mesh);
                 this.activeCamera._activeMeshes.push(mesh);
 
-                mesh._activate(this._renderId);
                 if (meshLOD !== mesh) {
                     meshLOD._activate(this._renderId);
                 }
 
-                this._activeMesh(mesh, meshLOD);
+                if (mesh._activate(this._renderId)) {
+                    mesh._isActive = true;
+                    this._activeMesh(mesh, meshLOD);
+                }
             }
         }