Browse Source

Merged latest and updated whatsnew

andi smithers 7 years ago
parent
commit
eec8890ee4
59 changed files with 32511 additions and 31159 deletions
  1. 18129 17849
      Playground/babylon.d.txt
  2. 12444 12168
      dist/preview release/babylon.d.ts
  3. 1 1
      dist/preview release/babylon.js
  4. 455 121
      dist/preview release/babylon.max.js
  5. 455 121
      dist/preview release/babylon.no-module.max.js
  6. 1 1
      dist/preview release/babylon.worker.js
  7. 455 121
      dist/preview release/es6.js
  8. 1 1
      dist/preview release/glTF2Interface/package.json
  9. 5 1
      dist/preview release/gui/babylon.gui.d.ts
  10. 1 1
      dist/preview release/gui/babylon.gui.js
  11. 1 1
      dist/preview release/gui/babylon.gui.min.js
  12. 1 1
      dist/preview release/gui/babylon.gui.min.js.map
  13. 10 2
      dist/preview release/gui/babylon.gui.module.d.ts
  14. 1 1
      dist/preview release/gui/package.json
  15. 6 4
      dist/preview release/inspector/package.json
  16. 2 2
      dist/preview release/loaders/package.json
  17. 1 1
      dist/preview release/materialsLibrary/package.json
  18. 1 1
      dist/preview release/postProcessesLibrary/package.json
  19. 1 1
      dist/preview release/proceduralTexturesLibrary/package.json
  20. 2 2
      dist/preview release/serializers/package.json
  21. 2 574
      dist/preview release/typedocValidationBaseline.json
  22. 15 1
      dist/preview release/viewer/babylon.viewer.d.ts
  23. 1 1
      dist/preview release/viewer/babylon.viewer.js
  24. 1 1
      dist/preview release/viewer/babylon.viewer.max.js
  25. 18 1
      dist/preview release/viewer/babylon.viewer.module.d.ts
  26. 3 1
      dist/preview release/what's new.md
  27. 10 3
      gui/src/2D/controls/control.ts
  28. 1 1
      package.json
  29. 67 1
      src/Culling/Octrees/babylon.octree.ts
  30. 40 52
      src/Culling/babylon.boundingBox.ts
  31. 20 14
      src/Culling/babylon.boundingInfo.ts
  32. 12 15
      src/Culling/babylon.boundingSphere.ts
  33. 1 1
      src/Engine/babylon.engine.ts
  34. 29 7
      src/Math/babylon.math.ts
  35. 8 8
      src/Mesh/babylon.abstractMesh.ts
  36. 8 4
      src/Mesh/babylon.geometry.ts
  37. 1 0
      src/Mesh/babylon.mesh.ts
  38. 17 19
      src/Mesh/babylon.meshBuilder.ts
  39. 1 1
      src/Mesh/babylon.subMesh.ts
  40. 1 0
      src/Particles/babylon.particle.ts
  41. 2 1
      src/Particles/babylon.particleHelper.ts
  42. 16 11
      src/Particles/babylon.particleSystem.ts
  43. 2 0
      src/PostProcess/RenderPipeline/Pipelines/babylon.defaultRenderingPipeline.ts
  44. 6 0
      src/PostProcess/RenderPipeline/Pipelines/babylon.standardRenderingPipeline.ts
  45. 29 0
      src/PostProcess/RenderPipeline/babylon.postProcessRenderPipeline.ts
  46. 45 12
      src/PostProcess/RenderPipeline/babylon.postProcessRenderPipelineManager.ts
  47. 16 0
      src/PostProcess/babylon.blackAndWhitePostProcess.ts
  48. 13 0
      src/PostProcess/babylon.displayPassPostProcess.ts
  49. 22 1
      src/PostProcess/babylon.filterPostProcess.ts
  50. 15 0
      src/PostProcess/babylon.highlightsPostProcess.ts
  51. 8 1
      src/PostProcess/babylon.imageProcessingPostProcess.ts
  52. 3 0
      src/PostProcess/babylon.postProcess.ts
  53. 38 2
      src/PostProcess/babylon.refractionPostProcess.ts
  54. 12 0
      src/PostProcess/babylon.stereoscopicInterlacePostProcess.ts
  55. 10 0
      src/PostProcess/babylon.vrDistortionCorrectionPostProcess.ts
  56. 13 10
      src/Tools/babylon.tools.ts
  57. 26 15
      src/babylon.node.ts
  58. BIN
      tests/validation/ReferenceImages/ribbon morphing.png
  59. 6 0
      tests/validation/config.json

File diff suppressed because it is too large
+ 18129 - 17849
Playground/babylon.d.txt


File diff suppressed because it is too large
+ 12444 - 12168
dist/preview release/babylon.d.ts


File diff suppressed because it is too large
+ 1 - 1
dist/preview release/babylon.js


File diff suppressed because it is too large
+ 455 - 121
dist/preview release/babylon.max.js


File diff suppressed because it is too large
+ 455 - 121
dist/preview release/babylon.no-module.max.js


File diff suppressed because it is too large
+ 1 - 1
dist/preview release/babylon.worker.js


File diff suppressed because it is too large
+ 455 - 121
dist/preview release/es6.js


+ 1 - 1
dist/preview release/glTF2Interface/package.json

@@ -1,7 +1,7 @@
 {
     "name": "babylonjs-gltf2interface",
     "description": "A typescript declaration of babylon's gltf2 inteface.",
-    "version": "3.3.0-rc.2",
+    "version": "3.3.0-rc.3",
     "repository": {
         "type": "git",
         "url": "https://github.com/BabylonJS/Babylon.js.git"

+ 5 - 1
dist/preview release/gui/babylon.gui.d.ts

@@ -984,6 +984,10 @@ declare module BABYLON.GUI {
             /** Gets a boolean indicating that the control needs to update its rendering */
             readonly isDirty: boolean;
             /**
+                * Gets the current linked mesh (or null if none)
+                */
+            readonly linkedMesh: BABYLON.Nullable<BABYLON.AbstractMesh>;
+            /**
                 * Gets or sets a value indicating the padding to use on the left of the control
                 * @see http://doc.babylonjs.com/how_to/gui#position-and-size
                 */
@@ -1124,7 +1128,7 @@ declare module BABYLON.GUI {
             /** @hidden */
             _markMatrixAsDirty(): void;
             /** @hidden */
-            _markAsDirty(): void;
+            _markAsDirty(force?: boolean): void;
             /** @hidden */
             _markAllAsDirty(): void;
             /** @hidden */

File diff suppressed because it is too large
+ 1 - 1
dist/preview release/gui/babylon.gui.js


File diff suppressed because it is too large
+ 1 - 1
dist/preview release/gui/babylon.gui.min.js


File diff suppressed because it is too large
+ 1 - 1
dist/preview release/gui/babylon.gui.min.js.map


+ 10 - 2
dist/preview release/gui/babylon.gui.module.d.ts

@@ -1087,6 +1087,10 @@ declare module 'babylonjs-gui/2D/controls/control' {
             /** Gets a boolean indicating that the control needs to update its rendering */
             readonly isDirty: boolean;
             /**
+                * Gets the current linked mesh (or null if none)
+                */
+            readonly linkedMesh: Nullable<AbstractMesh>;
+            /**
                 * Gets or sets a value indicating the padding to use on the left of the control
                 * @see http://doc.babylonjs.com/how_to/gui#position-and-size
                 */
@@ -1227,7 +1231,7 @@ declare module 'babylonjs-gui/2D/controls/control' {
             /** @hidden */
             _markMatrixAsDirty(): void;
             /** @hidden */
-            _markAsDirty(): void;
+            _markAsDirty(force?: boolean): void;
             /** @hidden */
             _markAllAsDirty(): void;
             /** @hidden */
@@ -3806,6 +3810,10 @@ declare module BABYLON.GUI {
             /** Gets a boolean indicating that the control needs to update its rendering */
             readonly isDirty: boolean;
             /**
+                * Gets the current linked mesh (or null if none)
+                */
+            readonly linkedMesh: BABYLON.Nullable<BABYLON.AbstractMesh>;
+            /**
                 * Gets or sets a value indicating the padding to use on the left of the control
                 * @see http://doc.babylonjs.com/how_to/gui#position-and-size
                 */
@@ -3946,7 +3954,7 @@ declare module BABYLON.GUI {
             /** @hidden */
             _markMatrixAsDirty(): void;
             /** @hidden */
-            _markAsDirty(): void;
+            _markAsDirty(force?: boolean): void;
             /** @hidden */
             _markAllAsDirty(): void;
             /** @hidden */

+ 1 - 1
dist/preview release/gui/package.json

@@ -4,7 +4,7 @@
     },
     "name": "babylonjs-gui",
     "description": "The Babylon.js GUI library is an extension you can use to generate interactive user interface. It is build on top of the DynamicTexture.",
-    "version": "3.3.0-rc.2",
+    "version": "3.3.0-rc.3",
     "repository": {
         "type": "git",
         "url": "https://github.com/BabylonJS/Babylon.js.git"

+ 6 - 4
dist/preview release/inspector/package.json

@@ -4,7 +4,7 @@
     },
     "name": "babylonjs-inspector",
     "description": "The Babylon.js inspector.",
-    "version": "3.3.0-rc.2",
+    "version": "3.3.0-rc.3",
     "repository": {
         "type": "git",
         "url": "https://github.com/BabylonJS/Babylon.js.git"
@@ -27,10 +27,12 @@
         "inspector"
     ],
     "license": "Apache-2.0",
-    "peerDependencies": {
-        "babylonjs": ">=3.2.0-alpha"
+    "dependencies": {
+        "babylonjs": ">3.2.0",
+        "babylonjs-gui": ">3.2.0",
+        "babylonjs-loaders": ">3.2.0"
     },
     "engines": {
         "node": "*"
     }
-}
+}

+ 2 - 2
dist/preview release/loaders/package.json

@@ -4,7 +4,7 @@
     },
     "name": "babylonjs-loaders",
     "description": "The Babylon.js file loaders library is an extension you can use to load different 3D file types into a Babylon scene.",
-    "version": "3.3.0-rc.2",
+    "version": "3.3.0-rc.3",
     "repository": {
         "type": "git",
         "url": "https://github.com/BabylonJS/Babylon.js.git"
@@ -27,7 +27,7 @@
     ],
     "license": "Apache-2.0",
     "dependencies": {
-        "babylonjs-gltf2interface": "3.3.0-rc.2"
+        "babylonjs-gltf2interface": "3.3.0-rc.3"
     },
     "peerDependencies": {
         "babylonjs": ">=3.2.0-alpha"

+ 1 - 1
dist/preview release/materialsLibrary/package.json

@@ -4,7 +4,7 @@
     },
     "name": "babylonjs-materials",
     "description": "The Babylon.js materials library is a collection of advanced materials to be used in a Babylon.js scene.",
-    "version": "3.3.0-rc.2",
+    "version": "3.3.0-rc.3",
     "repository": {
         "type": "git",
         "url": "https://github.com/BabylonJS/Babylon.js.git"

+ 1 - 1
dist/preview release/postProcessesLibrary/package.json

@@ -4,7 +4,7 @@
     },
     "name": "babylonjs-post-process",
     "description": "The Babylon.js materials library is a collection of advanced materials to be used in a Babylon.js scene.",
-    "version": "3.3.0-rc.2",
+    "version": "3.3.0-rc.3",
     "repository": {
         "type": "git",
         "url": "https://github.com/BabylonJS/Babylon.js.git"

+ 1 - 1
dist/preview release/proceduralTexturesLibrary/package.json

@@ -4,7 +4,7 @@
     },
     "name": "babylonjs-procedural-textures",
     "description": "The Babylon.js materials library is a collection of advanced materials to be used in a Babylon.js scene.",
-    "version": "3.3.0-rc.2",
+    "version": "3.3.0-rc.3",
     "repository": {
         "type": "git",
         "url": "https://github.com/BabylonJS/Babylon.js.git"

+ 2 - 2
dist/preview release/serializers/package.json

@@ -4,7 +4,7 @@
     },
     "name": "babylonjs-serializers",
     "description": "The Babylon.js serializers library is an extension you can use to serialize Babylon scenes.",
-    "version": "3.3.0-rc.2",
+    "version": "3.3.0-rc.3",
     "repository": {
         "type": "git",
         "url": "https://github.com/BabylonJS/Babylon.js.git"
@@ -27,7 +27,7 @@
     ],
     "license": "Apache-2.0",
     "dependencies": {
-        "babylonjs-gltf2interface": "3.3.0-rc.2"
+        "babylonjs-gltf2interface": "3.3.0-rc.3"
     },
     "peerDependencies": {
         "babylonjs": ">=3.2.0-alpha"

+ 2 - 574
dist/preview release/typedocValidationBaseline.json

@@ -1,21 +1,7 @@
 {
-  "errors": 878,
+  "errors": 766,
   "babylon.typedoc.json": {
-    "errors": 878,
-    "BlackAndWhitePostProcess": {
-      "Class": {
-        "Comments": {
-          "MissingText": true
-        }
-      },
-      "Property": {
-        "degree": {
-          "Comments": {
-            "MissingText": true
-          }
-        }
-      }
-    },
+    "errors": 766,
     "DefaultLoadingScreen": {
       "Class": {
         "Comments": {
@@ -80,27 +66,6 @@
         }
       }
     },
-    "DefaultRenderingPipeline": {
-      "Property": {
-        "FxaaPostProcessId": {
-          "Naming": {
-            "NotCamelCase": true
-          }
-        },
-        "ImageProcessingPostProcessId": {
-          "Naming": {
-            "NotCamelCase": true
-          }
-        }
-      }
-    },
-    "DisplayPassPostProcess": {
-      "Class": {
-        "Comments": {
-          "MissingText": true
-        }
-      }
-    },
     "DistanceJoint": {
       "Method": {
         "updateDistance": {
@@ -119,20 +84,6 @@
         }
       }
     },
-    "FilterPostProcess": {
-      "Class": {
-        "Comments": {
-          "MissingText": true
-        }
-      },
-      "Property": {
-        "kernelMatrix": {
-          "Comments": {
-            "MissingText": true
-          }
-        }
-      }
-    },
     "FreeCameraInputsManager": {
       "Method": {
         "addGamepad": {
@@ -279,27 +230,6 @@
         }
       }
     },
-    "HighlightsPostProcess": {
-      "Class": {
-        "Comments": {
-          "MissingText": true
-        }
-      }
-    },
-    "ImageProcessingPostProcess": {
-      "Class": {
-        "Comments": {
-          "MissingText": true
-        }
-      },
-      "Method": {
-        "getClassName": {
-          "Comments": {
-            "MissingText": true
-          }
-        }
-      }
-    },
     "InstancedMesh": {
       "Property": {
         "sourceMesh": {
@@ -605,198 +535,6 @@
         }
       }
     },
-    "Octree": {
-      "Class": {
-        "Comments": {
-          "MissingText": true
-        }
-      },
-      "Constructor": {
-        "new Octree": {
-          "Comments": {
-            "MissingText": true
-          },
-          "Parameter": {
-            "creationFunc": {
-              "Comments": {
-                "MissingText": true
-              }
-            },
-            "maxBlockCapacity": {
-              "Comments": {
-                "MissingText": true
-              }
-            },
-            "maxDepth": {
-              "Comments": {
-                "MissingText": true
-              }
-            }
-          }
-        }
-      },
-      "Property": {
-        "blocks": {
-          "Comments": {
-            "MissingText": true
-          }
-        },
-        "dynamicContent": {
-          "Comments": {
-            "MissingText": true
-          }
-        },
-        "maxDepth": {
-          "Comments": {
-            "MissingText": true
-          }
-        },
-        "CreationFuncForMeshes": {
-          "Comments": {
-            "MissingText": true
-          }
-        },
-        "CreationFuncForSubMeshes": {
-          "Comments": {
-            "MissingText": true
-          }
-        }
-      },
-      "Method": {
-        "addMesh": {
-          "Comments": {
-            "MissingText": true
-          },
-          "Parameter": {
-            "entry": {
-              "Comments": {
-                "MissingText": true
-              }
-            }
-          }
-        },
-        "intersects": {
-          "Comments": {
-            "MissingText": true
-          },
-          "Parameter": {
-            "sphereCenter": {
-              "Comments": {
-                "MissingText": true
-              }
-            },
-            "sphereRadius": {
-              "Comments": {
-                "MissingText": true
-              }
-            },
-            "allowDuplicate": {
-              "Comments": {
-                "MissingText": true
-              }
-            }
-          }
-        },
-        "intersectsRay": {
-          "Comments": {
-            "MissingText": true
-          },
-          "Parameter": {
-            "ray": {
-              "Comments": {
-                "MissingText": true
-              }
-            }
-          }
-        },
-        "select": {
-          "Comments": {
-            "MissingText": true
-          },
-          "Parameter": {
-            "frustumPlanes": {
-              "Comments": {
-                "MissingText": true
-              }
-            },
-            "allowDuplicate": {
-              "Comments": {
-                "MissingText": true
-              }
-            }
-          }
-        },
-        "update": {
-          "Comments": {
-            "MissingText": true
-          },
-          "Parameter": {
-            "worldMin": {
-              "Comments": {
-                "MissingText": true
-              }
-            },
-            "worldMax": {
-              "Comments": {
-                "MissingText": true
-              }
-            },
-            "entries": {
-              "Comments": {
-                "MissingText": true
-              }
-            }
-          }
-        },
-        "_CreateBlocks": {
-          "Comments": {
-            "MissingText": true
-          },
-          "Parameter": {
-            "worldMin": {
-              "Comments": {
-                "MissingText": true
-              }
-            },
-            "worldMax": {
-              "Comments": {
-                "MissingText": true
-              }
-            },
-            "entries": {
-              "Comments": {
-                "MissingText": true
-              }
-            },
-            "maxBlockCapacity": {
-              "Comments": {
-                "MissingText": true
-              }
-            },
-            "currentDepth": {
-              "Comments": {
-                "MissingText": true
-              }
-            },
-            "maxDepth": {
-              "Comments": {
-                "MissingText": true
-              }
-            },
-            "target": {
-              "Comments": {
-                "MissingText": true
-              }
-            },
-            "creationFunc": {
-              "Comments": {
-                "MissingText": true
-              }
-            }
-          }
-        }
-      }
-    },
     "PanoramaToCubeMapTools": {
       "Method": {
         "ConvertPanoramaToCubemap": {
@@ -810,57 +548,6 @@
         }
       }
     },
-    "Particle": {
-      "Property": {
-        "_initialEndSpriteCellID": {
-          "Comments": {
-            "MissingText": true
-          }
-        }
-      }
-    },
-    "ParticleHelper": {
-      "Method": {
-        "ExportSet": {
-          "Comments": {
-            "MissingReturn": true
-          },
-          "Parameter": {
-            "systems": {
-              "Comments": {
-                "MissingText": true
-              }
-            }
-          }
-        }
-      }
-    },
-    "ParticleSystem": {
-      "Method": {
-        "addColorGradient": {
-          "Comments": {
-            "MissingReturn": true
-          }
-        },
-        "removeColorGradient": {
-          "Comments": {
-            "MissingReturn": true
-          }
-        },
-        "_GetEffectCreationOptions": {
-          "Comments": {
-            "MissingText": true
-          },
-          "Parameter": {
-            "isAnimationSheetEnabled": {
-              "Comments": {
-                "MissingText": true
-              }
-            }
-          }
-        }
-      }
-    },
     "PassPostProcess": {
       "Class": {
         "Comments": {
@@ -1821,201 +1508,6 @@
         }
       }
     },
-    "PostProcessRenderPipeline": {
-      "Class": {
-        "Comments": {
-          "MissingText": true
-        }
-      },
-      "Constructor": {
-        "new PostProcessRenderPipeline": {
-          "Comments": {
-            "MissingText": true
-          },
-          "Parameter": {
-            "engine": {
-              "Comments": {
-                "MissingText": true
-              }
-            },
-            "name": {
-              "Comments": {
-                "MissingText": true
-              }
-            }
-          }
-        }
-      },
-      "Property": {
-        "isSupported": {
-          "Comments": {
-            "MissingText": true
-          }
-        }
-      },
-      "Method": {
-        "_disableEffect": {
-          "Comments": {
-            "MissingText": true
-          },
-          "Parameter": {
-            "renderEffectName": {
-              "Comments": {
-                "MissingText": true
-              }
-            },
-            "cameras": {
-              "Comments": {
-                "MissingText": true
-              }
-            }
-          }
-        },
-        "addEffect": {
-          "Comments": {
-            "MissingText": true
-          },
-          "Parameter": {
-            "renderEffect": {
-              "Comments": {
-                "MissingText": true
-              }
-            }
-          }
-        },
-        "dispose": {
-          "Comments": {
-            "MissingText": true
-          }
-        },
-        "getClassName": {
-          "Comments": {
-            "MissingText": true
-          }
-        }
-      }
-    },
-    "PostProcessRenderPipelineManager": {
-      "Class": {
-        "Comments": {
-          "MissingText": true
-        }
-      },
-      "Constructor": {
-        "new PostProcessRenderPipelineManager": {
-          "Comments": {
-            "MissingText": true
-          }
-        }
-      },
-      "Method": {
-        "addPipeline": {
-          "Comments": {
-            "MissingText": true
-          },
-          "Parameter": {
-            "renderPipeline": {
-              "Comments": {
-                "MissingText": true
-              }
-            }
-          }
-        },
-        "attachCamerasToRenderPipeline": {
-          "Comments": {
-            "MissingText": true
-          },
-          "Parameter": {
-            "renderPipelineName": {
-              "Comments": {
-                "MissingText": true
-              }
-            },
-            "cameras": {
-              "Comments": {
-                "MissingText": true
-              }
-            },
-            "unique": {
-              "Comments": {
-                "MissingText": true
-              }
-            }
-          }
-        },
-        "detachCamerasFromRenderPipeline": {
-          "Comments": {
-            "MissingText": true
-          },
-          "Parameter": {
-            "renderPipelineName": {
-              "Comments": {
-                "MissingText": true
-              }
-            },
-            "cameras": {
-              "Comments": {
-                "MissingText": true
-              }
-            }
-          }
-        },
-        "disableEffectInPipeline": {
-          "Comments": {
-            "MissingText": true
-          },
-          "Parameter": {
-            "renderPipelineName": {
-              "Comments": {
-                "MissingText": true
-              }
-            },
-            "renderEffectName": {
-              "Comments": {
-                "MissingText": true
-              }
-            },
-            "cameras": {
-              "Comments": {
-                "MissingText": true
-              }
-            }
-          }
-        },
-        "dispose": {
-          "Comments": {
-            "MissingText": true
-          }
-        },
-        "enableEffectInPipeline": {
-          "Comments": {
-            "MissingText": true
-          },
-          "Parameter": {
-            "renderPipelineName": {
-              "Comments": {
-                "MissingText": true
-              }
-            },
-            "renderEffectName": {
-              "Comments": {
-                "MissingText": true
-              }
-            },
-            "cameras": {
-              "Comments": {
-                "MissingText": true
-              }
-            }
-          }
-        },
-        "update": {
-          "Comments": {
-            "MissingText": true
-          }
-        }
-      }
-    },
     "RawTexture": {
       "Property": {
         "format": {
@@ -2351,30 +1843,6 @@
         }
       }
     },
-    "RefractionPostProcess": {
-      "Class": {
-        "Comments": {
-          "MissingText": true
-        }
-      },
-      "Property": {
-        "color": {
-          "Comments": {
-            "MissingText": true
-          }
-        },
-        "colorLevel": {
-          "Comments": {
-            "MissingText": true
-          }
-        },
-        "depth": {
-          "Comments": {
-            "MissingText": true
-          }
-        }
-      }
-    },
     "RenderTargetTexture": {
       "Class": {
         "Comments": {
@@ -3577,11 +3045,6 @@
       }
     },
     "StandardRenderingPipeline": {
-      "Class": {
-        "Comments": {
-          "MissingText": true
-        }
-      },
       "Property": {
         "BloomEnabled": {
           "Naming": {
@@ -3629,13 +3092,6 @@
         }
       }
     },
-    "StereoscopicInterlacePostProcess": {
-      "Class": {
-        "Comments": {
-          "MissingText": true
-        }
-      }
-    },
     "StringDictionary": {
       "Property": {
         "count": {
@@ -4411,13 +3867,6 @@
         }
       }
     },
-    "VRDistortionCorrectionPostProcess": {
-      "Class": {
-        "Comments": {
-          "MissingText": true
-        }
-      }
-    },
     "ILoadingScreen": {
       "Interface": {
         "Comments": {
@@ -4507,20 +3956,6 @@
         }
       }
     },
-    "IOctreeContainer": {
-      "Interface": {
-        "Comments": {
-          "MissingText": true
-        }
-      },
-      "Property": {
-        "blocks": {
-          "Comments": {
-            "MissingText": true
-          }
-        }
-      }
-    },
     "IPhysicsEnabledObject": {
       "Interface": {
         "Comments": {
@@ -4884,13 +4319,6 @@
         }
       }
     },
-    "PostProcessOptions": {
-      "Type alias": {
-        "Comments": {
-          "MissingText": true
-        }
-      }
-    },
     "CameraInputTypes": {
       "Variable": {
         "Naming": {

+ 15 - 1
dist/preview release/viewer/babylon.viewer.d.ts

@@ -924,7 +924,7 @@ declare module BabylonViewer {
       * @param name the name of the custom optimizer configuration
       * @param upgrade set to true if you want to upgrade optimizer and false if you want to degrade
       */
-    export function getCustomOptimizerByName(name: string, upgrade?: boolean): (sceneManager: SceneManager) => boolean;
+    export function getCustomOptimizerByName(name: string, upgrade?: boolean): typeof extendedUpgrade;
     export function registerCustomOptimizer(name: string, optimizer: (sceneManager: SceneManager) => boolean): void;
 }
 declare module BabylonViewer {
@@ -1558,6 +1558,20 @@ declare module BabylonViewer {
     export function addLoaderPlugin(name: string, plugin: ILoaderPlugin): void;
 }
 declare module BabylonViewer {
+    /**
+        * A custom upgrade-oriented function configuration for the scene optimizer.
+        *
+        * @param viewer the viewer to optimize
+        */
+    export function extendedUpgrade(sceneManager: SceneManager): boolean;
+    /**
+        * A custom degrade-oriented function configuration for the scene optimizer.
+        *
+        * @param viewer the viewer to optimize
+        */
+    export function extendedDegrade(sceneManager: SceneManager): boolean;
+}
+declare module BabylonViewer {
 }
 declare module BabylonViewer {
     export interface IEnvironmentMapConfiguration {

File diff suppressed because it is too large
+ 1 - 1
dist/preview release/viewer/babylon.viewer.js


File diff suppressed because it is too large
+ 1 - 1
dist/preview release/viewer/babylon.viewer.max.js


+ 18 - 1
dist/preview release/viewer/babylon.viewer.module.d.ts

@@ -985,13 +985,14 @@ declare module 'babylonjs-viewer/templating/viewerTemplatePlugin' {
 }
 
 declare module 'babylonjs-viewer/optimizer/custom' {
+    import { extendedUpgrade } from "babylonjs-viewer/optimizer/custom/extended";
     import { SceneManager } from "babylonjs-viewer/managers/sceneManager";
     /**
       *
       * @param name the name of the custom optimizer configuration
       * @param upgrade set to true if you want to upgrade optimizer and false if you want to degrade
       */
-    export function getCustomOptimizerByName(name: string, upgrade?: boolean): (sceneManager: SceneManager) => boolean;
+    export function getCustomOptimizerByName(name: string, upgrade?: boolean): typeof extendedUpgrade;
     export function registerCustomOptimizer(name: string, optimizer: (sceneManager: SceneManager) => boolean): void;
 }
 
@@ -1662,6 +1663,22 @@ declare module 'babylonjs-viewer/loader/plugins' {
     export function addLoaderPlugin(name: string, plugin: ILoaderPlugin): void;
 }
 
+declare module 'babylonjs-viewer/optimizer/custom/extended' {
+    import { SceneManager } from 'babylonjs-viewer/managers/sceneManager';
+    /**
+        * A custom upgrade-oriented function configuration for the scene optimizer.
+        *
+        * @param viewer the viewer to optimize
+        */
+    export function extendedUpgrade(sceneManager: SceneManager): boolean;
+    /**
+        * A custom degrade-oriented function configuration for the scene optimizer.
+        *
+        * @param viewer the viewer to optimize
+        */
+    export function extendedDegrade(sceneManager: SceneManager): boolean;
+}
+
 declare module 'babylonjs-viewer/configuration/interfaces' {
     export * from 'babylonjs-viewer/configuration/interfaces/cameraConfiguration';
     export * from 'babylonjs-viewer/configuration/interfaces/colorGradingConfiguration';

+ 3 - 1
dist/preview release/what's new.md

@@ -128,7 +128,8 @@
 - Added FXAA and MSAA support to the StandardRenderingPipeline ([julien-moreau](https://github.com/julien-moreau))
 - Make teleportCamera public in VR experience helper ([TrevorDev](https://github.com/TrevorDev))
 - Added optional alphaFilter parameter to ```CreateGroundFromHeightMap``` to allow for heightmaps to be created that ignore any transparent data ([Postman-nz](https://github.com/Postman-nz))
-- Added renormalization of mesh weights to babylon.mesh. Also added a validationSkin function to report out any errors on skinned meshes. ([Bolloxim](https://github.com/Bolloxim))
+- Fixed renormalization of mesh weights to in cleanMatrixWeights function. ([Bolloxim](https://github.com/Bolloxim))
+- Added a validationSkin function to report out any errors on skinned meshes. ([Bolloxim](https://github.com/Bolloxim))
 
 
 ### glTF Loader
@@ -203,6 +204,7 @@
 - trackPosition:false not working in webVRCamera/controllers ([TrevorDev](https://github.com/TrevorDev))
 - Spring Joint could not be removed ([TrevorDev](https://github.com/TrevorDev))
 - Sometimes duplicate controller models are loaded in VR ([TrevorDev](https://github.com/TrevorDev))
+- Particle emit rate over time does not reset on every particle system start ([TrevorDev](https://github.com/TrevorDev))
 
 ### Core Engine
 

+ 10 - 3
gui/src/2D/controls/control.ts

@@ -503,7 +503,7 @@ export class Control {
         }
 
         this._isVisible = value;
-        this._markAsDirty();
+        this._markAsDirty(true);
     }
 
     /** Gets a boolean indicating that the control needs to update its rendering */
@@ -512,6 +512,13 @@ export class Control {
     }
 
     /**
+     * Gets the current linked mesh (or null if none)
+     */
+    public get linkedMesh(): Nullable<AbstractMesh> {
+        return this._linkedMesh;
+    }
+
+    /**
      * Gets or sets a value indicating the padding to use on the left of the control
      * @see http://doc.babylonjs.com/how_to/gui#position-and-size
      */
@@ -890,8 +897,8 @@ export class Control {
     }
 
     /** @hidden */
-    public _markAsDirty(): void {
-        if (!this._isVisible) {
+    public _markAsDirty(force = false): void {
+        if (!this._isVisible && !force) {
             return;
         }
 

+ 1 - 1
package.json

@@ -9,7 +9,7 @@
     ],
     "name": "babylonjs",
     "description": "Babylon.js is a JavaScript 3D engine based on webgl.",
-    "version": "3.3.0-rc.2",
+    "version": "3.3.0-rc.3",
     "repository": {
         "type": "git",
         "url": "https://github.com/BabylonJS/Babylon.js.git"

+ 67 - 1
src/Culling/Octrees/babylon.octree.ts

@@ -1,27 +1,66 @@
 module BABYLON {
+    /**
+     * Contains an array of blocks representing the octree
+     */
     export interface IOctreeContainer<T> {
+        /**
+         * Blocks within the octree
+         */
         blocks: Array<OctreeBlock<T>>;
     }
 
+    /**
+     * Octrees are a really powerful data structure that can quickly select entities based on space coordinates.
+     * @see https://doc.babylonjs.com/how_to/optimizing_your_scene_with_octrees
+     */
     export class Octree<T> {
+        /**
+         * Blocks within the octree containing objects
+         */
         public blocks: Array<OctreeBlock<T>>;
+        /**
+         * Content stored in the octree
+         */
         public dynamicContent = new Array<T>();
 
         private _maxBlockCapacity: number;
         private _selectionContent: SmartArrayNoDuplicate<T>;       
         private _creationFunc: (entry: T, block: OctreeBlock<T>) => void;
 
-        constructor(creationFunc: (entry: T, block: OctreeBlock<T>) => void, maxBlockCapacity?: number, public maxDepth = 2) {
+        /**
+         * Creates a octree
+         * @see https://doc.babylonjs.com/how_to/optimizing_your_scene_with_octrees
+         * @param creationFunc function to be used to instatiate the octree
+         * @param maxBlockCapacity defines the maximum number of meshes you want on your octree's leaves (default: 64)
+         * @param maxDepth defines the maximum depth (sub-levels) for your octree. Default value is 2, which means 8 8 8 = 512 blocks :) (This parameter takes precedence over capacity.)
+         */
+        constructor(creationFunc: (
+            entry: T,
+            block: OctreeBlock<T>) => void,
+            maxBlockCapacity?: number, 
+            /** Defines the maximum depth (sub-levels) for your octree. Default value is 2, which means 8 8 8 = 512 blocks :) (This parameter takes precedence over capacity.) */
+            public maxDepth = 2
+        ) {
             this._maxBlockCapacity = maxBlockCapacity || 64;
             this._selectionContent = new SmartArrayNoDuplicate<T>(1024);
             this._creationFunc = creationFunc;
         }
 
         // Methods
+        /**
+         * Updates the octree by adding blocks for the passed in meshes within the min and max world parameters
+         * @param worldMin worldMin for the octree blocks var blockSize = new Vector3((worldMax.x - worldMin.x) / 2, (worldMax.y - worldMin.y) / 2, (worldMax.z - worldMin.z) / 2);
+         * @param worldMax worldMax for the octree blocks var blockSize = new Vector3((worldMax.x - worldMin.x) / 2, (worldMax.y - worldMin.y) / 2, (worldMax.z - worldMin.z) / 2);
+         * @param entries meshes to be added to the octree blocks
+         */
         public update(worldMin: Vector3, worldMax: Vector3, entries: T[]): void {
             Octree._CreateBlocks(worldMin, worldMax, entries, this._maxBlockCapacity, 0, this.maxDepth, this, this._creationFunc);
         }
 
+        /**
+         * Adds a mesh to the octree
+         * @param entry Mesh to add to the octree
+         */
         public addMesh(entry: T): void {
             for (var index = 0; index < this.blocks.length; index++) {
                 var block = this.blocks[index];
@@ -29,6 +68,12 @@
             }
         }
 
+        /**
+         * Selects an array of meshes within the frustum
+         * @param frustumPlanes The frustum planes to use which will select all meshes within it
+         * @param allowDuplicate If duplicate objects are allowed in the resulting object array
+         * @returns array of meshes within the frustum
+         */
         public select(frustumPlanes: Plane[], allowDuplicate?: boolean): SmartArray<T> {
             this._selectionContent.reset();
 
@@ -46,6 +91,13 @@
             return this._selectionContent;
         }
 
+        /**
+         * Test if the octree intersect with the given bounding sphere and if yes, then add its content to the selection array
+         * @param sphereCenter defines the bounding sphere center
+         * @param sphereRadius defines the bounding sphere radius
+         * @param allowDuplicate defines if the selection array can contains duplicated entries
+         * @returns an array of objects that intersect the sphere
+         */
         public intersects(sphereCenter: Vector3, sphereRadius: number, allowDuplicate?: boolean): SmartArray<T> {
             this._selectionContent.reset();
 
@@ -63,6 +115,11 @@
             return this._selectionContent;
         }
 
+        /**
+        * Test if the octree intersect with the given ray and if yes, then add its content to resulting array
+         * @param ray defines the ray to test with
+         * @returns array of intersected objects
+         */
         public intersectsRay(ray: Ray): SmartArray<T> {
             this._selectionContent.reset();
 
@@ -76,6 +133,9 @@
             return this._selectionContent;
         }
 
+        /**
+         * @hidden
+         */
         public static _CreateBlocks<T>(worldMin: Vector3, worldMax: Vector3, entries: T[], maxBlockCapacity: number, currentDepth: number, maxDepth: number, target: IOctreeContainer<T>, creationFunc: (entry: T, block: OctreeBlock<T>) => void): void {
             target.blocks = new Array<OctreeBlock<T>>();
             var blockSize = new Vector3((worldMax.x - worldMin.x) / 2, (worldMax.y - worldMin.y) / 2, (worldMax.z - worldMin.z) / 2);
@@ -95,6 +155,9 @@
             }
         }
 
+        /**
+         * Adds a mesh into the octree block if it intersects the block
+         */
         public static CreationFuncForMeshes = (entry: AbstractMesh, block: OctreeBlock<AbstractMesh>): void => {
             let boundingInfo = entry.getBoundingInfo();
             if (!entry.isBlocked && boundingInfo.boundingBox.intersectsMinMax(block.minPoint, block.maxPoint)) {
@@ -102,6 +165,9 @@
             }
         }
 
+        /**
+         * Adds a submesh into the octree block if it intersects the block
+         */
         public static CreationFuncForSubMeshes = (entry: SubMesh, block: OctreeBlock<SubMesh>): void => {
             let boundingInfo = entry.getBoundingInfo();
             if (boundingInfo.boundingBox.intersectsMinMax(block.minPoint, block.maxPoint)) {

+ 40 - 52
src/Culling/babylon.boundingBox.ts

@@ -6,47 +6,47 @@
         /**
          * Gets the 8 vectors representing the bounding box in local space
          */
-        public vectors: Vector3[];
+        public vectors: Vector3[] = [Vector3.Zero(), Vector3.Zero(), Vector3.Zero(), Vector3.Zero(), Vector3.Zero(), Vector3.Zero(), Vector3.Zero(), Vector3.Zero()];
         /**
          * Gets the center of the bounding box in local space
          */
-        public center: Vector3;
+        public center: Vector3 = Vector3.Zero();
         /**
          * Gets the center of the bounding box in world space
          */
-        public centerWorld: Vector3;
+        public centerWorld: Vector3 = Vector3.Zero();
         /**
          * Gets the extend size in local space
          */
-        public extendSize: Vector3;
+        public extendSize: Vector3 = Vector3.Zero();
         /**
          * Gets the extend size in world space
          */
-        public extendSizeWorld: Vector3;
+        public extendSizeWorld: Vector3 = Vector3.Zero();
         /**
          * Gets the OBB (object bounding box) directions
          */
-        public directions: Vector3[];
+        public directions: Vector3[] = [Vector3.Zero(), Vector3.Zero(), Vector3.Zero()];
         /**
          * Gets the 8 vectors representing the bounding box in world space
-         */        
-        public vectorsWorld: Vector3[] = new Array<Vector3>();
+         */
+        public vectorsWorld: Vector3[] = [Vector3.Zero(), Vector3.Zero(), Vector3.Zero(), Vector3.Zero(), Vector3.Zero(), Vector3.Zero(), Vector3.Zero(), Vector3.Zero()];;
         /**
          * Gets the minimum vector in world space
          */
-        public minimumWorld: Vector3;
+        public minimumWorld: Vector3 = Vector3.Zero();
         /**
          * Gets the maximum vector in world space
          */
-        public maximumWorld: Vector3;
+        public maximumWorld: Vector3 = Vector3.Zero();
         /**
          * Gets the minimum vector in local space
          */
-        public minimum: Vector3;
+        public minimum: Vector3 = Vector3.Zero();
         /**
          * Gets the maximum vector in local space
          */
-        public maximum: Vector3;
+        public maximum: Vector3 = Vector3.Zero();
 
         private _worldMatrix: Matrix;
 
@@ -72,20 +72,18 @@
          * @param max defines the new maximum vector (in local space) 
          */
         public reConstruct(min: Vector3, max: Vector3) {
-            this.minimum = min.clone();
-            this.maximum = max.clone()
+            this.minimum.copyFrom(min);
+            this.maximum.copyFrom(max);
 
             // Bounding vectors
-            this.vectors = [
-                this.minimum.clone(),
-                this.maximum.clone(),
-                this.minimum.clone(),
-                this.minimum.clone(),
-                this.minimum.clone(),
-                this.maximum.clone(),
-                this.maximum.clone(),
-                this.maximum.clone()
-            ];
+            this.vectors[0].copyFrom(this.minimum);
+            this.vectors[1].copyFrom(this.maximum);
+            this.vectors[2].copyFrom(this.minimum);
+            this.vectors[3].copyFrom(this.minimum);
+            this.vectors[4].copyFrom(this.minimum);
+            this.vectors[5].copyFrom(this.maximum);
+            this.vectors[6].copyFrom(this.maximum);
+            this.vectors[7].copyFrom(this.maximum);
 
             this.vectors[2].x = this.maximum.x;
             this.vectors[3].y = this.maximum.y;
@@ -95,19 +93,21 @@
             this.vectors[7].y = this.minimum.y;
 
             // OBB
-            this.center = this.maximum.add(this.minimum).scale(0.5);
-            this.extendSize = this.maximum.subtract(this.minimum).scale(0.5);
-            this.directions = [Vector3.Zero(), Vector3.Zero(), Vector3.Zero()];
+            this.center.copyFrom(this.maximum).addInPlace(this.minimum).scaleInPlace(0.5);
+            this.extendSize.copyFrom(this.maximum).subtractInPlace(this.minimum).scaleInPlace(0.5);
+            for (var index = 0; index < 3; index++) {
+                this.directions[index].copyFromFloats(0,0,0);
+            }
 
             // World
-            for (var index = 0; index < this.vectors.length; index++) {
-                this.vectorsWorld[index] = Vector3.Zero();
+            for (var index = 0; index < 8; index++) {
+                this.vectorsWorld[index].copyFromFloats(0,0,0);
             }
 
-            this.minimumWorld = Vector3.Zero();
-            this.maximumWorld = Vector3.Zero();
-            this.centerWorld = Vector3.Zero();
-            this.extendSizeWorld = Vector3.Zero();
+            this.minimumWorld.copyFromFloats(0,0,0);
+            this.maximumWorld.copyFromFloats(0,0,0);
+            this.centerWorld.copyFromFloats(0,0,0);
+            this.extendSizeWorld.copyFromFloats(0,0,0);
 
             this._update(this._worldMatrix || Matrix.Identity());
         }
@@ -118,13 +118,13 @@
          * @returns the current bounding box
          */
         public scale(factor: number): BoundingBox {
-            let diff = this.maximum.subtract(this.minimum);
+            const diff = Tmp.Vector3[0].copyFrom(this.maximum).subtractInPlace(this.minimum);
             let distance = diff.length() * factor;
             diff.normalize();
-            let newRadius = diff.scale(distance / 2);
+            let newRadius = diff.scaleInPlace(distance * 0.5);
 
-            let min = this.center.subtract(newRadius);
-            let max = this.center.add(newRadius);
+            const min = Tmp.Vector3[1].copyFrom(this.center).subtractInPlace(newRadius);
+            const max = Tmp.Vector3[2].copyFrom(this.center).addInPlace(newRadius);
 
             this.reConstruct(min, max);
 
@@ -154,23 +154,11 @@
             Vector3.FromFloatsToRef(Number.MAX_VALUE, Number.MAX_VALUE, Number.MAX_VALUE, this.minimumWorld);
             Vector3.FromFloatsToRef(-Number.MAX_VALUE, -Number.MAX_VALUE, -Number.MAX_VALUE, this.maximumWorld);
 
-            for (var index = 0; index < this.vectors.length; index++) {
+            for (var index = 0; index < 8; index++) {
                 var v = this.vectorsWorld[index];
                 Vector3.TransformCoordinatesToRef(this.vectors[index], world, v);
-
-                if (v.x < this.minimumWorld.x)
-                    this.minimumWorld.x = v.x;
-                if (v.y < this.minimumWorld.y)
-                    this.minimumWorld.y = v.y;
-                if (v.z < this.minimumWorld.z)
-                    this.minimumWorld.z = v.z;
-
-                if (v.x > this.maximumWorld.x)
-                    this.maximumWorld.x = v.x;
-                if (v.y > this.maximumWorld.y)
-                    this.maximumWorld.y = v.y;
-                if (v.z > this.maximumWorld.z)
-                    this.maximumWorld.z = v.z;
+                this.minimumWorld.minimizeInPlace(v);
+                this.maximumWorld.maximizeInPlace(v);
             }
 
             // Extend

+ 20 - 14
src/Culling/babylon.boundingInfo.ts

@@ -61,21 +61,26 @@
          * @param minimum min vector of the bounding box/sphere
          * @param maximum max vector of the bounding box/sphere
          */
-        constructor(
-            /**
-             * min vector of the bounding box/sphere
-             */
-            public minimum: Vector3, 
-            /**
-             * max vector of the bounding box/sphere
-             */
-            public maximum: Vector3
-        ) {
+        constructor(minimum: Vector3, maximum: Vector3) {
             this.boundingBox = new BoundingBox(minimum, maximum);
             this.boundingSphere = new BoundingSphere(minimum, maximum);
         }
 
         /**
+         * min vector of the bounding box/sphere
+         */
+        public get minimum(): Vector3 {
+            return this.boundingBox.minimum;
+        }
+
+        /**
+         * max vector of the bounding box/sphere
+         */
+        public get maximum(): Vector3 {
+           return this.boundingBox.maximum;
+        }
+
+        /**
          * If the info is locked and won't be updated to avoid perf overhead
          */
         public get isLocked(): boolean {
@@ -106,11 +111,12 @@
          * @returns the current bounding info
          */
         public centerOn(center: Vector3, extend: Vector3): BoundingInfo {
-            this.minimum = center.subtract(extend);
-            this.maximum = center.add(extend);
 
-            this.boundingBox = new BoundingBox(this.minimum, this.maximum);
-            this.boundingSphere = new BoundingSphere(this.minimum, this.maximum);
+            const minimum = Tmp.Vector3[0].copyFrom(center).subtractInPlace(extend);
+            const maximum = Tmp.Vector3[1].copyFrom(center).addInPlace(extend);
+
+            this.boundingBox.reConstruct(minimum, maximum);
+            this.boundingSphere.reConstruct(minimum, maximum);
 
             return this;
         }

+ 12 - 15
src/Culling/babylon.boundingSphere.ts

@@ -1,7 +1,6 @@
 module BABYLON {
     // This matrix is used as a value to reset the bounding box.
     const _identityMatrix = Matrix.Identity();
-    const _tempRadiusVector = new Vector3(0, 0, 0);
 
     /**
      * Class used to store bounding sphere information
@@ -10,7 +9,7 @@
         /**
          * Gets the center of the bounding sphere in local space
          */
-        public center: Vector3;
+        public center = Vector3.Zero();
         /**
          * Radius of the bounding sphere in local space
          */
@@ -18,7 +17,7 @@
         /**
          * Gets the center of the bounding sphere in world space
          */
-        public centerWorld: Vector3;
+        public centerWorld = Vector3.Zero();
         /**
          * Radius of the bounding sphere in world space
          */
@@ -26,11 +25,11 @@
         /**
          * Gets the minimum vector in local space
          */
-        public minimum: Vector3;
+        public minimum = Vector3.Zero();
         /**
          * Gets the maximum vector in local space
          */
-        public maximum: Vector3;
+        public maximum = Vector3.Zero();
 
         /**
          * Creates a new bounding sphere
@@ -38,8 +37,6 @@
          * @param max defines the maximum vector (in local space)
          */
         constructor(min: Vector3, max: Vector3) {
-            this.center = Vector3.Zero();
-            this.centerWorld = Vector3.Zero();
             this.reConstruct(min, max);
         }
 
@@ -49,8 +46,8 @@
          * @param max defines the new maximum vector (in local space) 
          */
         public reConstruct(min: Vector3, max: Vector3) {
-            this.minimum = min.clone();
-            this.maximum = max.clone()
+            this.minimum.copyFrom(min);
+            this.maximum.copyFrom(max);
 
             var distance = Vector3.Distance(min, max);
 
@@ -68,10 +65,9 @@
          */
         public scale(factor: number): BoundingSphere {
             let newRadius = this.radius * factor;
-            _tempRadiusVector.set(newRadius, newRadius, newRadius)
-
-            let min = this.center.subtract(_tempRadiusVector);
-            let max = this.center.add(_tempRadiusVector);
+            const tempRadiusVector = Tmp.Vector3[0].set(newRadius, newRadius, newRadius);
+            let min = Tmp.Vector3[1].copyFrom(this.center).subtractInPlace(tempRadiusVector);
+            let max = Tmp.Vector3[2].copyFrom(this.center).addInPlace(tempRadiusVector);
 
             this.reConstruct(min, max);
 
@@ -82,8 +78,9 @@
         /** @hidden */
         public _update(world: Matrix): void {
             Vector3.TransformCoordinatesToRef(this.center, world, this.centerWorld);
-            Vector3.TransformNormalFromFloatsToRef(1.0, 1.0, 1.0, world, _tempRadiusVector);
-            this.radiusWorld = Math.max(Math.abs(_tempRadiusVector.x), Math.abs(_tempRadiusVector.y), Math.abs(_tempRadiusVector.z)) * this.radius;
+            const tempVector = Tmp.Vector3[0];
+            Vector3.TransformNormalFromFloatsToRef(1.0, 1.0, 1.0, world, tempVector);
+            this.radiusWorld = Math.max(Math.abs(tempVector.x), Math.abs(tempVector.y), Math.abs(tempVector.z)) * this.radius;
         }
 
         /**

+ 1 - 1
src/Engine/babylon.engine.ts

@@ -475,7 +475,7 @@
          * Returns the current version of the framework
          */
         public static get Version(): string {
-            return "3.3.0-rc.2";
+            return "3.3.0-rc.3";
         }
 
         // Updatable statics so stick with vars here

+ 29 - 7
src/Math/babylon.math.ts

@@ -1880,10 +1880,7 @@
          * @returns the current updated Vector3  
          */
         public minimizeInPlace(other: Vector3): Vector3 {
-            if (other.x < this.x) this.x = other.x;
-            if (other.y < this.y) this.y = other.y;
-            if (other.z < this.z) this.z = other.z;
-            return this;
+            return this.minimizeInPlaceFromFloats(other.x, other.y, other.z);
         }
 
         /**
@@ -1892,9 +1889,34 @@
          * @returns the current updated Vector3
          */
         public maximizeInPlace(other: Vector3): Vector3 {
-            if (other.x > this.x) this.x = other.x;
-            if (other.y > this.y) this.y = other.y;
-            if (other.z > this.z) this.z = other.z;
+            return this.maximizeInPlaceFromFloats(other.x, other.y, other.z);
+        }
+
+        /**
+         * Updates the current Vector3 with the minimal coordinate values between its and the given coordinates
+         * @param x defines the x coordinate of the operand
+         * @param y defines the y coordinate of the operand
+         * @param z defines the z coordinate of the operand
+         * @returns the current updated Vector3  
+         */
+        public minimizeInPlaceFromFloats(x: number, y: number, z: number): Vector3 {
+            this.x = Math.min(this.x, x);
+            this.y = Math.min(this.y, y);
+            this.z = Math.min(this.z, z);
+            return this;
+        }
+
+        /**
+         * Updates the current Vector3 with the maximal coordinate values between its and the given coordinates.
+         * @param x defines the x coordinate of the operand
+         * @param y defines the y coordinate of the operand
+         * @param z defines the z coordinate of the operand
+         * @returns the current updated Vector3
+         */
+        public maximizeInPlaceFromFloats(x: number, y: number, z: number): Vector3 {
+            this.x = Math.max(this.x, x);
+            this.y = Math.max(this.y, y);
+            this.z = Math.max(this.z, z);
             return this;
         }
 

+ 8 - 8
src/Mesh/babylon.abstractMesh.ts

@@ -474,9 +474,6 @@
         /** @hidden */
         public _edgesRenderer: Nullable<IEdgesRenderer>;
 
-        // Cache
-        private _collisionsTransformMatrix = Matrix.Zero();
-        private _collisionsScalingMatrix = Matrix.Zero();
         /** @hidden */
         public _masterMesh: Nullable<AbstractMesh>;
         /** @hidden */
@@ -1045,9 +1042,10 @@
             if (!this.subMeshes) {
                 return this;
             }
-            for (var subIndex = 0; subIndex < this.subMeshes.length; subIndex++) {
+            let count = this.subMeshes.length;
+            for (var subIndex = 0; subIndex < count; subIndex++) {
                 var subMesh = this.subMeshes[subIndex];
-                if (!subMesh.IsGlobal) {
+                if (count > 1 || !subMesh.IsGlobal) {
                     subMesh.updateBoundingInfo(matrix);
                 }
             }
@@ -1261,9 +1259,11 @@
                 return this;
 
             // Transformation matrix
-            Matrix.ScalingToRef(1.0 / collider._radius.x, 1.0 / collider._radius.y, 1.0 / collider._radius.z, this._collisionsScalingMatrix);
-            this.worldMatrixFromCache.multiplyToRef(this._collisionsScalingMatrix, this._collisionsTransformMatrix);
-            this._processCollisionsForSubMeshes(collider, this._collisionsTransformMatrix);
+            const collisionsScalingMatrix = Tmp.Matrix[0];
+            const collisionsTransformMatrix = Tmp.Matrix[1];
+            Matrix.ScalingToRef(1.0 / collider._radius.x, 1.0 / collider._radius.y, 1.0 / collider._radius.z, collisionsScalingMatrix);
+            this.worldMatrixFromCache.multiplyToRef(collisionsScalingMatrix, collisionsTransformMatrix);
+            this._processCollisionsForSubMeshes(collider, collisionsTransformMatrix);
             return this;
         }
 

+ 8 - 4
src/Mesh/babylon.geometry.ts

@@ -61,11 +61,15 @@
          *  Gets or sets the Bias Vector to apply on the bounding elements (box/sphere), the max extend is computed as v += v * bias.x + bias.y, the min is computed as v -= v * bias.x + bias.y
          */
         public set boundingBias(value: Vector2) {
-            if (this._boundingBias && this._boundingBias.equals(value)) {
-                return;
+            if (this._boundingBias) {
+                if (this._boundingBias.equals(value)) {
+                    return;
+                }
+                this._boundingBias.copyFrom(value);
+            }
+            else {
+                this._boundingBias = value.clone();
             }
-
-            this._boundingBias = value.clone();
 
             this._updateBoundingInfo(true, null);
         }

+ 1 - 0
src/Mesh/babylon.mesh.ts

@@ -5,6 +5,7 @@
      **/
     export class _CreationDataStorage {
         public closePath?: boolean;
+        public closeArray?: boolean;
         public idx: number[];
         public dashSize: number;
         public gapSize: number;

+ 17 - 19
src/Mesh/babylon.meshBuilder.ts

@@ -211,7 +211,7 @@
                 };
                 var positions = <FloatArray>instance.getVerticesData(VertexBuffer.PositionKind);
                 positionFunction(positions);
-                instance._boundingInfo = new BoundingInfo(Tmp.Vector3[0], Tmp.Vector3[1]);
+                instance._boundingInfo = new BoundingInfo(Tmp.Vector3[2], Tmp.Vector3[3]);
                 instance._boundingInfo.update(instance._worldMatrix);
                 instance.updateVerticesData(VertexBuffer.PositionKind, positions, false, false);
                 if (options.colors) {
@@ -275,7 +275,7 @@
                     ribbon._creationDataStorage.idx = (<any>vertexData)._idx;
                 }
                 ribbon._creationDataStorage.closePath = closePath;
-                (<any>ribbon)._closeArray = closeArray;
+                ribbon._creationDataStorage.closeArray = closeArray;
 
                 vertexData.applyToMesh(ribbon, updatable);
 
@@ -1027,16 +1027,16 @@
             var path3D;
             var pathArray;
             if (instance) { // tube update
-                var arc = options.arc || (<any>instance).arc;
                 let storage = instance._creationDataStorage!;
+                var arc = options.arc || storage.arc;
                 path3D =  storage.path3D.update(path);
                 pathArray = tubePathArray(path, path3D, storage.pathArray, radius, storage.tessellation, radiusFunction, storage.cap, arc);
                 instance = MeshBuilder.CreateRibbon("", { pathArray: pathArray, instance: instance });
-                instance._creationDataStorage = new _CreationDataStorage();
-                instance._creationDataStorage.path3D = path3D;
-                instance._creationDataStorage.pathArray = pathArray;
-                instance._creationDataStorage.arc = arc;
-                instance._creationDataStorage.radius = radius;
+                // Update mode, no need to recreate the storage.
+                storage.path3D = path3D;
+                storage.pathArray = pathArray;
+                storage.arc = arc;
+                storage.radius = radius;
 
                 return instance;
             }
@@ -1047,13 +1047,12 @@
             cap = (cap < 0 || cap > 3) ? 0 : cap;
             pathArray = tubePathArray(path, path3D, newPathArray, radius, tessellation, radiusFunction, cap, options.arc);
             var tube = MeshBuilder.CreateRibbon(name, { pathArray: pathArray, closePath: true, closeArray: false, updatable: updatable, sideOrientation: sideOrientation, invertUV: invertUV, frontUVs: options.frontUVs, backUVs: options.backUVs }, scene);
-            tube._creationDataStorage = new _CreationDataStorage();
-            tube._creationDataStorage.pathArray = pathArray;
-            tube._creationDataStorage.path3D = path3D;
-            tube._creationDataStorage.tessellation = tessellation;
-            tube._creationDataStorage.cap = cap;
-            tube._creationDataStorage.arc = options.arc;
-            tube._creationDataStorage.radius = radius;
+            tube._creationDataStorage!.pathArray = pathArray;
+            tube._creationDataStorage!.path3D = path3D;
+            tube._creationDataStorage!.tessellation = tessellation;
+            tube._creationDataStorage!.cap = cap;
+            tube._creationDataStorage!.arc = options.arc;
+            tube._creationDataStorage!.radius = radius;
 
             return tube;
         }
@@ -1407,10 +1406,9 @@
             cap = (cap < 0 || cap > 3) ? 0 : cap;
             pathArray = extrusionPathArray(shape, curve, path3D, newShapePaths, scale, rotation, scaleFunction, rotateFunction, cap, custom);
             var extrudedGeneric = MeshBuilder.CreateRibbon(name, { pathArray: pathArray, closeArray: rbCA, closePath: rbCP, updatable: updtbl, sideOrientation: side, invertUV: invertUV, frontUVs: frontUVs || undefined, backUVs: backUVs || undefined }, scene);
-            extrudedGeneric._creationDataStorage = new _CreationDataStorage();
-            extrudedGeneric._creationDataStorage.pathArray = pathArray;
-            extrudedGeneric._creationDataStorage.path3D = path3D;
-            extrudedGeneric._creationDataStorage.cap = cap;
+            extrudedGeneric._creationDataStorage!.pathArray = pathArray;
+            extrudedGeneric._creationDataStorage!.path3D = path3D;
+            extrudedGeneric._creationDataStorage!.cap = cap;
 
             return extrudedGeneric;
         }

+ 1 - 1
src/Mesh/babylon.subMesh.ts

@@ -252,7 +252,7 @@
             if (!boundingInfo) {
                 return false;
             }
-            return boundingInfo.isInFrustum(frustumPlanes);
+            return boundingInfo.isInFrustum(frustumPlanes, this._mesh.cullingStrategy);
         }
 
         /**

+ 1 - 0
src/Particles/babylon.particle.ts

@@ -81,6 +81,7 @@
 
         /** @hidden */
         public _initialStartSpriteCellID: number;
+        /** @hidden */
         public _initialEndSpriteCellID: number;
 
         /** @hidden */

+ 2 - 1
src/Particles/babylon.particleHelper.ts

@@ -88,7 +88,8 @@ module BABYLON {
         /**
          * Static function used to export a particle system to a ParticleSystemSet variable.
          * Please note that the emitter shape is not exported
-         * @param system defines the particle systems to export
+         * @param systems defines the particle systems to export
+         * @returns the created particle system set
          */
         public static ExportSet(systems: IParticleSystem[]): ParticleSystemSet {
             var set = new ParticleSystemSet();

+ 16 - 11
src/Particles/babylon.particleSystem.ts

@@ -655,17 +655,6 @@
             }
 
             this._addFactorGradient(this._emitRateGradients, gradient, factor, factor2);
-
-            if (!this._currentEmitRateGradient) {
-                this._currentEmitRateGradient = this._emitRateGradients[0];
-                this._currentEmitRate1 = this._currentEmitRateGradient.getFactor();
-                this._currentEmitRate2 = this._currentEmitRate1;
-            }
-
-            if (this._emitRateGradients.length === 2) {
-                this._currentEmitRate2 = this._emitRateGradients[1].getFactor();
-            }
-
             return this;
         }
 
@@ -809,6 +798,7 @@
          * @param gradient defines the gradient to use (between 0 and 1)
          * @param color1 defines the color to affect to the specified gradient
          * @param color2 defines an additional color used to define a range ([color, color2]) with main color to pick the final color from
+         * @returns this particle system
          */
         public addColorGradient(gradient: number, color1: Color4, color2?: Color4): IParticleSystem {
             if (!this._colorGradients) {
@@ -837,6 +827,7 @@
         /**
          * Remove a specific color gradient
          * @param gradient defines the gradient to remove
+         * @returns this particle system
          */
         public removeColorGradient(gradient: number): IParticleSystem {
             if (!this._colorGradients) {
@@ -1033,6 +1024,18 @@
                 this.activeSubSystems = new Array<ParticleSystem>();
             }
 
+            // Reset emit gradient so it acts the same on every start
+            if(this._emitRateGradients){
+                if(this._emitRateGradients.length > 0){
+                    this._currentEmitRateGradient = this._emitRateGradients[0];
+                    this._currentEmitRate1 = this._currentEmitRateGradient.getFactor();
+                    this._currentEmitRate2 = this._currentEmitRate1;
+                }
+                if(this._emitRateGradients.length > 1){
+                    this._currentEmitRate2 = this._emitRateGradients[1].getFactor();
+                }
+            }
+
             if (this.preWarmCycles) {
                 if (this.emitter instanceof AbstractMesh) {
                     this.emitter.computeWorldMatrix(true);
@@ -1451,6 +1454,7 @@
             return attributeNamesOrOptions;
         }
 
+        /** @hidden */
         public static _GetEffectCreationOptions(isAnimationSheetEnabled = false): string[] {
             var effectCreationOption = ["invView", "view", "projection", "vClipPlane", "vClipPlane2", "vClipPlane3", "vClipPlane4", "textureMask", "translationPivot", "eyePosition"];
 
@@ -1461,6 +1465,7 @@
             return effectCreationOption;
         }
 
+        /** @hidden */
         private _getEffect(blendMode: number): Effect {
             if (this._customEffect) {
                 return this._customEffect;

+ 2 - 0
src/PostProcess/RenderPipeline/Pipelines/babylon.defaultRenderingPipeline.ts

@@ -11,10 +11,12 @@
 		 */
         private readonly SharpenPostProcessId: string = "SharpenPostProcessEffect";
         /**
+         * @ignore
 		 * ID of the image processing post process;
 		 */
         readonly ImageProcessingPostProcessId: string = "ImageProcessingPostProcessEffect";
         /**
+         * @ignore
 		 * ID of the Fast Approximate Anti-Aliasing post process;
 		 */
         readonly FxaaPostProcessId: string = "FxaaPostProcessEffect";

+ 6 - 0
src/PostProcess/RenderPipeline/Pipelines/babylon.standardRenderingPipeline.ts

@@ -1,4 +1,9 @@
 module BABYLON {
+    /**
+     * Standard rendering pipeline
+     * Default pipeline should be used going forward but the standard pipeline will be kept for backwards compatibility.
+     * @see https://doc.babylonjs.com/how_to/using_standard_rendering_pipeline
+     */
     export class StandardRenderingPipeline extends PostProcessRenderPipeline implements IDisposable, IAnimatable {
         /**
         * Public members
@@ -433,6 +438,7 @@
         }
 
         /**
+         * Default pipeline should be used going forward but the standard pipeline will be kept for backwards compatibility.
          * @constructor
          * @param {string} name - The rendering pipeline name
          * @param {BABYLON.Scene} scene - The scene linked to this pipeline

+ 29 - 0
src/PostProcess/RenderPipeline/babylon.postProcessRenderPipeline.ts

@@ -1,15 +1,27 @@
 module BABYLON {
+    /**
+     * PostProcessRenderPipeline
+     * @see https://doc.babylonjs.com/how_to/how_to_use_postprocessrenderpipeline
+     */
     export class PostProcessRenderPipeline {
 
         private _renderEffects: { [key: string]: PostProcessRenderEffect };
         private _renderEffectsForIsolatedPass: PostProcessRenderEffect[];
 
+        /**
+         * @hidden
+         */
         protected _cameras: Camera[];
 
         /** @hidden */
         @serialize()
         public _name: string;
 
+        /**
+         * Initializes a PostProcessRenderPipeline
+         * @param engine engine to add the pipeline to
+         * @param name name of the pipeline
+         */
         constructor(private engine: Engine, name: string) {
             this._name = name;
 
@@ -19,10 +31,17 @@ module BABYLON {
             this._cameras = [];
         }
 
+        /**
+         * "PostProcessRenderPipeline"
+         * @returns "PostProcessRenderPipeline"
+         */
         public getClassName(): string {
             return "PostProcessRenderPipeline";
         }
 
+        /**
+         * If all the render effects in the pipeline are support
+         */
         public get isSupported(): boolean {
             for (var renderEffectName in this._renderEffects) {
                 if (this._renderEffects.hasOwnProperty(renderEffectName)) {
@@ -35,6 +54,10 @@ module BABYLON {
             return true;
         }
 
+        /**
+         * Adds an effect to the pipeline
+         * @param renderEffect the effect to add
+         */
         public addEffect(renderEffect: PostProcessRenderEffect): void {
             (<any>this._renderEffects)[renderEffect._name] = renderEffect;
         }
@@ -61,8 +84,11 @@ module BABYLON {
             renderEffects._enable(Tools.MakeArray(cameras || this._cameras));
         }
 
+        /** @hidden */
         public _disableEffect(renderEffectName: string, cameras: Nullable<Camera[]>): void;
+        /** @hidden */
         public _disableEffect(renderEffectName: string, cameras: Nullable<Camera[]>): void;
+        /** @hidden */
         public _disableEffect(renderEffectName: string, cameras: Nullable<Camera[]>): void {
             var renderEffects: PostProcessRenderEffect = (<any>this._renderEffects)[renderEffectName];
 
@@ -168,6 +194,9 @@ module BABYLON {
             return false;
         }
 
+        /**
+         * Disposes of the pipeline
+         */
         public dispose() {
             // Must be implemented by children 
         }

+ 45 - 12
src/PostProcess/RenderPipeline/babylon.postProcessRenderPipelineManager.ts

@@ -1,18 +1,34 @@
 module BABYLON {
+    /**
+     * PostProcessRenderPipelineManager class
+     * @see https://doc.babylonjs.com/how_to/how_to_use_postprocessrenderpipeline
+     */
     export class PostProcessRenderPipelineManager {
         private _renderPipelines: { [Key: string]: PostProcessRenderPipeline };
 
+        /**
+         * Initializes a PostProcessRenderPipelineManager
+         * @see https://doc.babylonjs.com/how_to/how_to_use_postprocessrenderpipeline
+         */
         constructor() {
             this._renderPipelines = {};
         }
 
+        /**
+         * Adds a pipeline to the manager
+         * @param renderPipeline The pipeline to add
+         */
         public addPipeline(renderPipeline: PostProcessRenderPipeline): void {
             this._renderPipelines[renderPipeline._name] = renderPipeline;
         }
 
-        public attachCamerasToRenderPipeline(renderPipelineName: string, cameras: Camera, unique?: boolean): void;
-        public attachCamerasToRenderPipeline(renderPipelineName: string, cameras: Camera[], unique?: boolean): void;
-        public attachCamerasToRenderPipeline(renderPipelineName: string, cameras: any, unique: boolean = false): void {
+        /**
+         * Attaches a camera to the pipeline
+         * @param renderPipelineName The name of the pipeline to attach to
+         * @param cameras the camera to attach
+         * @param unique if the camera can be attached multiple times to the pipeline
+         */
+        public attachCamerasToRenderPipeline(renderPipelineName: string, cameras: any | Camera[] | Camera, unique: boolean = false): void {
             var renderPipeline: PostProcessRenderPipeline = this._renderPipelines[renderPipelineName];
 
             if (!renderPipeline) {
@@ -22,9 +38,12 @@ module BABYLON {
             renderPipeline._attachCameras(cameras, unique);
         }
 
-        public detachCamerasFromRenderPipeline(renderPipelineName: string, cameras: Camera): void;
-        public detachCamerasFromRenderPipeline(renderPipelineName: string, cameras: Camera[]): void;
-        public detachCamerasFromRenderPipeline(renderPipelineName: string, cameras: any): void {
+        /**
+         * Detaches a camera from the pipeline
+         * @param renderPipelineName The name of the pipeline to detach from
+         * @param cameras the camera to detach
+         */
+        public detachCamerasFromRenderPipeline(renderPipelineName: string, cameras: any | Camera[] | Camera): void {
             var renderPipeline: PostProcessRenderPipeline = this._renderPipelines[renderPipelineName];
 
             if (!renderPipeline) {
@@ -34,9 +53,13 @@ module BABYLON {
             renderPipeline._detachCameras(cameras);
         }
 
-        public enableEffectInPipeline(renderPipelineName: string, renderEffectName: string, cameras: Camera): void;
-        public enableEffectInPipeline(renderPipelineName: string, renderEffectName: string, cameras: Camera[]): void;
-        public enableEffectInPipeline(renderPipelineName: string, renderEffectName: string, cameras: any): void {
+        /**
+         * Enables an effect by name on a pipeline
+         * @param renderPipelineName the name of the pipeline to enable the effect in
+         * @param renderEffectName the name of the effect to enable
+         * @param cameras the cameras that the effect should be enabled on
+         */
+        public enableEffectInPipeline(renderPipelineName: string, renderEffectName: string, cameras: any | Camera[] | Camera): void {
             var renderPipeline: PostProcessRenderPipeline = this._renderPipelines[renderPipelineName];
 
             if (!renderPipeline) {
@@ -46,9 +69,13 @@ module BABYLON {
             renderPipeline._enableEffect(renderEffectName, cameras);
         }
 
-        public disableEffectInPipeline(renderPipelineName: string, renderEffectName: string, cameras: Camera): void;
-        public disableEffectInPipeline(renderPipelineName: string, renderEffectName: string, cameras: Camera[]): void;
-        public disableEffectInPipeline(renderPipelineName: string, renderEffectName: string, cameras: any): void {
+        /**
+         * Disables an effect by name on a pipeline
+         * @param renderPipelineName the name of the pipeline to disable the effect in
+         * @param renderEffectName the name of the effect to disable
+         * @param cameras the cameras that the effect should be disabled on
+         */
+        public disableEffectInPipeline(renderPipelineName: string, renderEffectName: string, cameras: any | Camera[] | Camera): void {
             var renderPipeline: PostProcessRenderPipeline = this._renderPipelines[renderPipelineName];
 
             if (!renderPipeline) {
@@ -58,6 +85,9 @@ module BABYLON {
             renderPipeline._disableEffect(renderEffectName, cameras);
         }
 
+        /**
+         * Updates the state of all contained render pipelines and disposes of any non supported pipelines
+         */
         public update(): void {
             for (var renderPipelineName in this._renderPipelines) {
                 if (this._renderPipelines.hasOwnProperty(renderPipelineName)) {
@@ -82,6 +112,9 @@ module BABYLON {
             }
         }
 
+        /**
+         * Disposes of the manager and pipelines
+         */
         public dispose(): void {
             for (var renderPipelineName in this._renderPipelines) {
                 if (this._renderPipelines.hasOwnProperty(renderPipelineName)) {

+ 16 - 0
src/PostProcess/babylon.blackAndWhitePostProcess.ts

@@ -1,8 +1,24 @@
 module BABYLON {
 
+    /**
+     * Post process used to render in black and white
+     */
     export class BlackAndWhitePostProcess extends PostProcess {
+        /**
+         * Linear about to convert he result to black and white (default: 1)
+         */
         public degree = 1;
     
+        /**
+         * Creates a black and white post process
+         * @see https://doc.babylonjs.com/how_to/how_to_use_postprocesses#black-and-white
+         * @param name The name of the effect.
+         * @param options The required width/height ratio to downsize to before computing the render pass.
+         * @param camera The camera to apply the render pass to.
+         * @param samplingMode The sampling mode to be used when computing the pass. (default: 0)
+         * @param engine The engine which the post process will be applied. (default: current engine)
+         * @param reusable If the post process can be reused on the same frame. (default: false)
+         */
         constructor(name: string, options: number | PostProcessOptions, camera: Camera, samplingMode?: number, engine?: Engine, reusable?: boolean) {
             super(name, "blackAndWhite", ["degree"], null, options, camera, samplingMode, engine, reusable);
 

+ 13 - 0
src/PostProcess/babylon.displayPassPostProcess.ts

@@ -1,5 +1,18 @@
 module BABYLON {
+
+    /**
+     * DisplayPassPostProcess which produces an output the same as it's input
+     */
     export class DisplayPassPostProcess extends PostProcess {
+        /**
+         * Creates the DisplayPassPostProcess
+         * @param name The name of the effect.
+         * @param options The required width/height ratio to downsize to before computing the render pass.
+         * @param camera The camera to apply the render pass to.
+         * @param samplingMode The sampling mode to be used when computing the pass. (default: 0)
+         * @param engine The engine which the post process will be applied. (default: current engine)
+         * @param reusable If the post process can be reused on the same frame. (default: false)
+         */
         constructor(name: string, options: number | PostProcessOptions, camera: Nullable<Camera>, samplingMode?: number, engine?: Engine, reusable?: boolean) {
             super(name, "displayPass", ["passSampler"], ["passSampler"], options, camera, samplingMode, engine, reusable);
         }

+ 22 - 1
src/PostProcess/babylon.filterPostProcess.ts

@@ -1,6 +1,27 @@
 module BABYLON {
+    /**
+     * Applies a kernel filter to the image
+     */
     export class FilterPostProcess extends PostProcess {
-        constructor(name: string, public kernelMatrix: Matrix, options: number | PostProcessOptions, camera: Nullable<Camera>, samplingMode?: number, engine?: Engine, reusable?: boolean) {
+        /**
+         * 
+         * @param name The name of the effect.
+         * @param kernelMatrix The matrix to be applied to the image
+         * @param options The required width/height ratio to downsize to before computing the render pass.
+         * @param camera The camera to apply the render pass to.
+         * @param samplingMode The sampling mode to be used when computing the pass. (default: 0)
+         * @param engine The engine which the post process will be applied. (default: current engine)
+         * @param reusable If the post process can be reused on the same frame. (default: false)
+         */
+        constructor(name: string,
+            /** The matrix to be applied to the image */
+            public kernelMatrix: Matrix, 
+            options: number | PostProcessOptions, 
+            camera: Nullable<Camera>, 
+            samplingMode?: number, 
+            engine?: Engine, 
+            reusable?: boolean
+        ) {
             super(name, "filter", ["kernelMatrix"], null, options, camera, samplingMode, engine, reusable);
 
             this.onApply = (effect: Effect) => {

+ 15 - 0
src/PostProcess/babylon.highlightsPostProcess.ts

@@ -1,5 +1,20 @@
 module BABYLON {
+    /**
+     * Extracts highlights from the image
+     * @see https://doc.babylonjs.com/how_to/how_to_use_postprocesses
+     */
     export class HighlightsPostProcess extends PostProcess {
+        /**
+         * Extracts highlights from the image
+         * @see https://doc.babylonjs.com/how_to/how_to_use_postprocesses 
+         * @param name The name of the effect.
+         * @param options The required width/height ratio to downsize to before computing the render pass.
+         * @param camera The camera to apply the render pass to.
+         * @param samplingMode The sampling mode to be used when computing the pass. (default: 0)
+         * @param engine The engine which the post process will be applied. (default: current engine)
+         * @param reusable If the post process can be reused on the same frame. (default: false)
+         * @param textureType Type of texture for the post process (default: Engine.TEXTURETYPE_UNSIGNED_INT)
+         */
         constructor(name: string, options: number | PostProcessOptions, camera: Nullable<Camera>, samplingMode?: number, engine?: Engine, reusable?: boolean, textureType: number = Engine.TEXTURETYPE_UNSIGNED_INT) {
             super(name, "highlights", null, null, options, camera, samplingMode, engine, reusable, null, textureType);
         }

+ 8 - 1
src/PostProcess/babylon.imageProcessingPostProcess.ts

@@ -1,4 +1,8 @@
 module BABYLON {
+    /**
+     * ImageProcessingPostProcess
+     * @see https://doc.babylonjs.com/how_to/how_to_use_postprocesses#imageprocessing
+     */
     export class ImageProcessingPostProcess extends PostProcess {
 
         /**
@@ -337,7 +341,10 @@
                 this.imageProcessingConfiguration.bind(effect, this.aspectRatio);
             };
         }
-
+        /**
+         *  "ImageProcessingPostProcess"
+         * @returns "ImageProcessingPostProcess"
+         */
         public getClassName(): string {
             return "ImageProcessingPostProcess";
         }

+ 3 - 0
src/PostProcess/babylon.postProcess.ts

@@ -1,4 +1,7 @@
 module BABYLON {
+    /**
+     * Size options for a post process
+     */
     export type PostProcessOptions = { width: number, height: number };
 
     /**

+ 38 - 2
src/PostProcess/babylon.refractionPostProcess.ts

@@ -1,4 +1,8 @@
 module BABYLON {
+    /**
+     * Post process which applies a refractin texture
+     * @see https://doc.babylonjs.com/how_to/how_to_use_postprocesses#refraction
+     */
     export class RefractionPostProcess extends PostProcess {
         private _refTexture: Texture;
         private _ownRefractionTexture = true;
@@ -19,8 +23,36 @@
             this._refTexture = value;
             this._ownRefractionTexture = false;
         }
-
-        constructor(name: string, refractionTextureUrl: string, public color: Color3, public depth: number, public colorLevel: number, options: number | PostProcessOptions, camera: Camera, samplingMode?: number, engine?: Engine, reusable?: boolean) {
+        
+        /**
+         * Initializes the RefractionPostProcess
+         * @see https://doc.babylonjs.com/how_to/how_to_use_postprocesses#refraction
+         * @param name The name of the effect.
+         * @param refractionTextureUrl Url of the refraction texture to use
+         * @param color the base color of the refraction (used to taint the rendering)
+         * @param depth simulated refraction depth
+         * @param colorLevel the coefficient of the base color (0 to remove base color tainting)
+         * @param camera The camera to apply the render pass to.
+         * @param options The required width/height ratio to downsize to before computing the render pass.
+         * @param samplingMode The sampling mode to be used when computing the pass. (default: 0)
+         * @param engine The engine which the post process will be applied. (default: current engine)
+         * @param reusable If the post process can be reused on the same frame. (default: false)
+         */
+        constructor(
+            name: string, 
+            refractionTextureUrl: string, 
+            /** the base color of the refraction (used to taint the rendering) */
+            public color: Color3, 
+            /** simulated refraction depth */
+            public depth: number, 
+            /** the coefficient of the base color (0 to remove base color tainting) */
+            public colorLevel: number, 
+            options: number | PostProcessOptions, 
+            camera: Camera, 
+            samplingMode?: number, 
+            engine?: Engine, 
+            reusable?: boolean
+        ) {
             super(name, "refraction", ["baseColor", "depth", "colorLevel"], ["refractionSampler"], options, camera, samplingMode, engine, reusable);
 
             this.onActivateObservable.add((cam: Camera) => {
@@ -37,6 +69,10 @@
         }
 
         // Methods
+        /**
+         * Disposes of the post process
+         * @param camera Camera to dispose post process on
+         */
         public dispose(camera: Camera): void {
             if (this._refTexture && this._ownRefractionTexture) {
                 this._refTexture.dispose();

+ 12 - 0
src/PostProcess/babylon.stereoscopicInterlacePostProcess.ts

@@ -1,8 +1,20 @@
 module BABYLON {
+    /**
+     * StereoscopicInterlacePostProcess used to render stereo views from a rigged camera
+     */
     export class StereoscopicInterlacePostProcess extends PostProcess {
         private _stepSize : Vector2;
         private _passedProcess : Nullable<PostProcess>;
 
+        /**
+         * Initializes a StereoscopicInterlacePostProcess
+         * @param name The name of the effect.
+         * @param rigCameras The rig cameras to be appled to the post process
+         * @param isStereoscopicHoriz If the rendered results are horizontal or verticle
+         * @param samplingMode The sampling mode to be used when computing the pass. (default: 0)
+         * @param engine The engine which the post process will be applied. (default: current engine)
+         * @param reusable If the post process can be reused on the same frame. (default: false)
+         */
         constructor(name: string, rigCameras: Camera[], isStereoscopicHoriz: boolean, samplingMode?: number, engine?: Engine, reusable?: boolean) {
             super(name, "stereoscopicInterlace", ['stepSize'], ['camASampler'], 1, rigCameras[1], samplingMode, engine, reusable, isStereoscopicHoriz ? "#define IS_STEREOSCOPIC_HORIZ 1" : undefined);
             

+ 10 - 0
src/PostProcess/babylon.vrDistortionCorrectionPostProcess.ts

@@ -1,4 +1,7 @@
 module BABYLON {
+    /**
+     * VRDistortionCorrectionPostProcess used for mobile VR 
+     */
     export class VRDistortionCorrectionPostProcess extends PostProcess {
         private _isRightEye: boolean;
         private _distortionFactors: number[];
@@ -8,6 +11,13 @@
         private _scaleFactor: Vector2;
         private _lensCenter: Vector2;
 
+        /**
+         * Initializes the VRDistortionCorrectionPostProcess
+         * @param name The name of the effect.
+         * @param camera The camera to apply the render pass to.
+         * @param isRightEye If this is for the right eye distortion
+         * @param vrMetrics All the required metrics for the VR camera
+         */
         constructor(name: string, camera: Camera, isRightEye: boolean, vrMetrics: VRCameraMetrics) {
             super(name, "vrDistortionCorrection", [
                 'LensCenter',

+ 13 - 10
src/Tools/babylon.tools.ts

@@ -503,10 +503,12 @@
             var maximum = new Vector3(-Number.MAX_VALUE, -Number.MAX_VALUE, -Number.MAX_VALUE);
 
             for (var index = indexStart; index < indexStart + indexCount; index++) {
-                var current = new Vector3(positions[indices[index] * 3], positions[indices[index] * 3 + 1], positions[indices[index] * 3 + 2]);
-
-                minimum = Vector3.Minimize(current, minimum);
-                maximum = Vector3.Maximize(current, maximum);
+                const offset = indices[index] * 3;
+                const x = positions[offset];
+                const y = positions[offset + 1];
+                const z = positions[offset + 2];
+                minimum.minimizeInPlaceFromFloats(x, y, z);
+                maximum.maximizeInPlaceFromFloats(x, y, z);
             }
 
             if (bias) {
@@ -541,12 +543,13 @@
                 stride = 3;
             }
 
-            for (var index = start; index < start + count; index++) {
-                var current = new Vector3(positions[index * stride], positions[index * stride + 1], positions[index * stride + 2]);
-
-                minimum = Vector3.Minimize(current, minimum);
-                maximum = Vector3.Maximize(current, maximum);
-            }
+            for (var index = start, offset = start*stride; index < start + count; index++, offset+=stride) {
+                const x = positions[offset];
+                const y = positions[offset + 1];
+                const z = positions[offset + 2];
+                minimum.minimizeInPlaceFromFloats(x, y, z);
+                maximum.maximizeInPlaceFromFloats(x, y, z);
+              }
 
             if (bias) {
                 minimum.x -= minimum.x * bias.x + bias.y;

+ 26 - 15
src/babylon.node.ts

@@ -110,6 +110,9 @@
         /** @hidden */
         public _worldMatrixDeterminant = 0;        
 
+        /** @hidden */
+        private _sceneRootNodesIndex = -1;
+
         /**
          * Gets a boolean indicating if the node has been disposed
          * @returns true if the node was disposed
@@ -136,8 +139,7 @@
                 }
 
                 if (!parent) {
-                    // Need to add this node to the rootNodes
-                    this._scene.rootNodes.push(this);
+                    this.addToSceneRootNodes();
                 }
             }
 
@@ -152,12 +154,7 @@
                 this._parentNode._children.push(this);
 
                 if (!previousParentNode) {
-                    // Need to remove from rootNodes
-                    const rootNodeIndex = this._scene.rootNodes.indexOf(this);
-
-                    if (rootNodeIndex > -1) {
-                        this._scene.rootNodes.splice(rootNodeIndex, 1);
-                    }
+                    this.removeFromSceneRootNodes();
                 }
             }
 
@@ -168,7 +165,25 @@
         public get parent(): Nullable<Node> {
             return this._parentNode;
         }
-        
+
+        private addToSceneRootNodes() {
+            if (this._sceneRootNodesIndex === -1) {
+                this._sceneRootNodesIndex = this._scene.rootNodes.length;
+                this._scene.rootNodes.push(this);
+            }
+        }
+
+        private removeFromSceneRootNodes() {
+            if (this._sceneRootNodesIndex !== -1) {
+                const rootNodes = this._scene.rootNodes;
+                const lastIdx = rootNodes.length - 1;
+                rootNodes[this._sceneRootNodesIndex] = rootNodes[lastIdx];
+                rootNodes[this._sceneRootNodesIndex]._sceneRootNodesIndex = this._sceneRootNodesIndex;
+                this._scene.rootNodes.pop();
+                this._sceneRootNodesIndex = -1;
+            }
+        }
+
         private _animationPropertiesOverride: Nullable<AnimationPropertiesOverride> = null;
 
         /**
@@ -221,7 +236,7 @@
             this.uniqueId = this._scene.getUniqueId();
             this._initCache();
 
-            this._scene.rootNodes.push(this);
+            this.addToSceneRootNodes();
         }
 
         /**
@@ -684,11 +699,7 @@
             }
 
             if (!this.parent) {
-                const rootNodeIndex = this._scene.rootNodes.indexOf(this);
-
-                if (rootNodeIndex > -1) {
-                    this._scene.rootNodes.splice(rootNodeIndex, 1);
-                }
+                this.removeFromSceneRootNodes();
             } else {
                 this.parent = null;
             }

BIN
tests/validation/ReferenceImages/ribbon morphing.png


+ 6 - 0
tests/validation/config.json

@@ -2,6 +2,12 @@
   "root": "https://rawgit.com/BabylonJS/Website/master",
   "tests": [
     {
+      "title": "Ribbon morphing",
+      "playgroundId": "#ACKC2#1",
+      "renderCount": 50,
+      "referenceImage": "ribbon morphing.png"
+    },    
+    {
       "title": "Clip planes",
       "playgroundId": "#Y6W087#0",
       "referenceImage": "clipplanes.png"