浏览代码

Merge remote-tracking branch 'BabylonJS/master' into viewer-gulp

Raanan Weber 7 年之前
父节点
当前提交
cbbc84b509
共有 55 个文件被更改,包括 15137 次插入14049 次删除
  1. 882 789
      Playground/babylon.d.txt
  2. 1 1
      Playground/js/pbt.js
  3. 2 2
      Tools/Gulp/config.json
  4. 7138 7046
      dist/preview release/babylon.d.ts
  5. 34 34
      dist/preview release/babylon.js
  6. 466 158
      dist/preview release/babylon.max.js
  7. 48 48
      dist/preview release/babylon.worker.js
  8. 5654 5551
      dist/preview release/customConfigurations/minimalGLTFViewer/babylon.d.ts
  9. 52 52
      dist/preview release/customConfigurations/minimalGLTFViewer/babylon.js
  10. 491 163
      dist/preview release/customConfigurations/minimalGLTFViewer/babylon.max.js
  11. 3 3
      dist/preview release/gui/babylon.gui.d.ts
  12. 10 4
      dist/preview release/gui/babylon.gui.js
  13. 3 3
      dist/preview release/gui/babylon.gui.min.js
  14. 3 3
      dist/preview release/gui/babylon.gui.module.d.ts
  15. 1 1
      dist/preview release/gui/package.json
  16. 6 6
      dist/preview release/inspector/babylon.inspector.bundle.js
  17. 7 1
      dist/preview release/inspector/babylon.inspector.js
  18. 4 4
      dist/preview release/inspector/babylon.inspector.min.js
  19. 1 1
      dist/preview release/inspector/package.json
  20. 8 2
      dist/preview release/loaders/babylon.glTF1FileLoader.js
  21. 1 1
      dist/preview release/loaders/babylon.glTF1FileLoader.min.js
  22. 23 4
      dist/preview release/loaders/babylon.glTF2FileLoader.js
  23. 2 2
      dist/preview release/loaders/babylon.glTF2FileLoader.min.js
  24. 24 5
      dist/preview release/loaders/babylon.glTFFileLoader.js
  25. 3 3
      dist/preview release/loaders/babylon.glTFFileLoader.min.js
  26. 24 5
      dist/preview release/loaders/babylonjs.loaders.js
  27. 3 3
      dist/preview release/loaders/babylonjs.loaders.min.js
  28. 1 1
      dist/preview release/loaders/package.json
  29. 1 1
      dist/preview release/materialsLibrary/package.json
  30. 1 1
      dist/preview release/postProcessesLibrary/package.json
  31. 1 1
      dist/preview release/proceduralTexturesLibrary/package.json
  32. 1 1
      dist/preview release/serializers/package.json
  33. 2 0
      gui/src/advancedDynamicTexture.ts
  34. 2 2
      gui/src/controls/control.ts
  35. 7 3
      gui/src/controls/slider.ts
  36. 7 1
      inspector/src/details/PropertyLine.ts
  37. 6 6
      loaders/src/glTF/1.0/babylon.glTFLoader.ts
  38. 17 3
      loaders/src/glTF/2.0/babylon.glTFLoader.ts
  39. 8 1
      loaders/src/glTF/babylon.glTFFileLoader.ts
  40. 3 3
      localDev/index.html
  41. 2 2
      package.json
  42. 6 0
      sandbox/index.js
  43. 81 86
      src/Cameras/VR/babylon.vrExperienceHelper.ts
  44. 5 1
      src/Cameras/VR/babylon.webVRCamera.ts
  45. 1 1
      src/Layer/babylon.highlightlayer.ts
  46. 11 3
      src/Materials/PBR/babylon.pbrBaseMaterial.ts
  47. 24 1
      src/Materials/PBR/babylon.pbrBaseSimpleMaterial.ts
  48. 9 1
      src/Materials/PBR/babylon.pbrMaterial.ts
  49. 1 1
      src/Mesh/babylon.subMesh.ts
  50. 18 9
      src/Mesh/babylon.transformNode.ts
  51. 12 12
      src/Physics/babylon.physicsHelper.ts
  52. 1 1
      src/Physics/babylon.physicsImpostor.ts
  53. 2 1
      src/PostProcess/babylon.imageProcessingPostProcess.ts
  54. 6 1
      src/Shaders/pbr.fragment.fx
  55. 7 10
      src/babylon.scene.ts

文件差异内容过多而无法显示
+ 882 - 789
Playground/babylon.d.txt


+ 1 - 1
Playground/js/pbt.js

@@ -417,7 +417,7 @@ var PBT = function() {
             parent.addControl(header);  
 
             button.onValueChangedObservable.add(function(value) {
-                header.text = "Y-rotation: " + onValueChange(value) + " " + unit;
+                header.text = text + onValueChange(value) + " " + unit;
                 func(value);
             });
             parent.addControl(button);

+ 2 - 2
Tools/Gulp/config.json

@@ -1567,12 +1567,12 @@
                     "../../gui/src/controls/ellipse.ts",
                     "../../gui/src/controls/line.ts",
                     "../../gui/src/controls/slider.ts",
-                    "../../gui/src/controls/checkBox.ts",
+                    "../../gui/src/controls/checkbox.ts",
                     "../../gui/src/controls/radioButton.ts",
                     "../../gui/src/controls/textBlock.ts",
                     "../../gui/src/controls/image.ts",
                     "../../gui/src/controls/button.ts",
-                    "../../gui/src/controls/colorPicker.ts",
+                    "../../gui/src/controls/colorpicker.ts",
                     "../../gui/src/controls/inputText.ts",
                     "../../gui/src/controls/virtualKeyboard.ts"
                 ],

文件差异内容过多而无法显示
+ 7138 - 7046
dist/preview release/babylon.d.ts


文件差异内容过多而无法显示
+ 34 - 34
dist/preview release/babylon.js


文件差异内容过多而无法显示
+ 466 - 158
dist/preview release/babylon.max.js


文件差异内容过多而无法显示
+ 48 - 48
dist/preview release/babylon.worker.js


文件差异内容过多而无法显示
+ 5654 - 5551
dist/preview release/customConfigurations/minimalGLTFViewer/babylon.d.ts


文件差异内容过多而无法显示
+ 52 - 52
dist/preview release/customConfigurations/minimalGLTFViewer/babylon.js


文件差异内容过多而无法显示
+ 491 - 163
dist/preview release/customConfigurations/minimalGLTFViewer/babylon.max.js


+ 3 - 3
dist/preview release/gui/babylon.gui.d.ts

@@ -165,8 +165,8 @@ declare module BABYLON.GUI {
         private _transformCenterX;
         private _transformCenterY;
         private _transformMatrix;
-        private _invertTransformMatrix;
-        private _transformedPosition;
+        protected _invertTransformMatrix: Matrix2D;
+        protected _transformedPosition: Vector2;
         private _isMatrixDirty;
         private _cachedOffsetX;
         private _cachedOffsetY;
@@ -456,7 +456,7 @@ declare module BABYLON.GUI {
         protected _getTypeName(): string;
         _draw(parentMeasure: Measure, context: CanvasRenderingContext2D): void;
         private _pointerIsDown;
-        private _updateValueFromPointer(x);
+        private _updateValueFromPointer(x, y);
         _onPointerDown(target: Control, coordinates: Vector2, buttonIndex: number): boolean;
         _onPointerMove(target: Control, coordinates: Vector2): void;
         _onPointerUp(target: Control, coordinates: Vector2, buttonIndex: number): void;

+ 10 - 4
dist/preview release/gui/babylon.gui.js

@@ -304,6 +304,8 @@ var BABYLON;
                             continue;
                         }
                         control.notRenderable = false;
+                        // Account for RenderScale.
+                        projectedPosition.scaleInPlace(this.renderScale);
                         control._moveToProjectedPosition(projectedPosition);
                     }
                 }
@@ -2831,7 +2833,11 @@ var BABYLON;
                 }
                 context.restore();
             };
-            Slider.prototype._updateValueFromPointer = function (x) {
+            Slider.prototype._updateValueFromPointer = function (x, y) {
+                if (this.rotation != 0) {
+                    this._invertTransformMatrix.transformCoordinates(x, y, this._transformedPosition);
+                    x = this._transformedPosition.x;
+                }
                 this.value = this._minimum + ((x - this._currentMeasure.left) / this._currentMeasure.width) * (this._maximum - this._minimum);
             };
             Slider.prototype._onPointerDown = function (target, coordinates, buttonIndex) {
@@ -2839,13 +2845,13 @@ var BABYLON;
                     return false;
                 }
                 this._pointerIsDown = true;
-                this._updateValueFromPointer(coordinates.x);
+                this._updateValueFromPointer(coordinates.x, coordinates.y);
                 this._host._capturingControl = this;
                 return true;
             };
             Slider.prototype._onPointerMove = function (target, coordinates) {
                 if (this._pointerIsDown) {
-                    this._updateValueFromPointer(coordinates.x);
+                    this._updateValueFromPointer(coordinates.x, coordinates.y);
                 }
                 _super.prototype._onPointerMove.call(this, target, coordinates);
             };
@@ -2987,7 +2993,7 @@ var BABYLON;
     })(GUI = BABYLON.GUI || (BABYLON.GUI = {}));
 })(BABYLON || (BABYLON = {}));
 
-//# sourceMappingURL=checkBox.js.map
+//# sourceMappingURL=checkbox.js.map
 
 /// <reference path="../../../dist/preview release/babylon.d.ts"/>
 

文件差异内容过多而无法显示
+ 3 - 3
dist/preview release/gui/babylon.gui.min.js


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

@@ -170,8 +170,8 @@ declare module BABYLON.GUI {
         private _transformCenterX;
         private _transformCenterY;
         private _transformMatrix;
-        private _invertTransformMatrix;
-        private _transformedPosition;
+        protected _invertTransformMatrix: Matrix2D;
+        protected _transformedPosition: Vector2;
         private _isMatrixDirty;
         private _cachedOffsetX;
         private _cachedOffsetY;
@@ -461,7 +461,7 @@ declare module BABYLON.GUI {
         protected _getTypeName(): string;
         _draw(parentMeasure: Measure, context: CanvasRenderingContext2D): void;
         private _pointerIsDown;
-        private _updateValueFromPointer(x);
+        private _updateValueFromPointer(x, y);
         _onPointerDown(target: Control, coordinates: Vector2, buttonIndex: number): boolean;
         _onPointerMove(target: Control, coordinates: Vector2): void;
         _onPointerUp(target: Control, coordinates: Vector2, buttonIndex: number): void;

+ 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.1.0-beta5",
+    "version": "3.1.0-beta6",
     "repository": {
         "type": "git",
         "url": "https://github.com/BabylonJS/Babylon.js.git"

文件差异内容过多而无法显示
+ 6 - 6
dist/preview release/inspector/babylon.inspector.bundle.js


+ 7 - 1
dist/preview release/inspector/babylon.inspector.js

@@ -1699,7 +1699,13 @@ var INSPECTOR;
                     var objToDetail = this.value;
                     // Display all properties that are not functions
                     var propToDisplay = INSPECTOR.Helpers.GetAllLinesPropertiesAsString(objToDetail);
-                    propToDisplay.sort().reverse();
+                    // special case for color3
+                    if ((propToDisplay.indexOf('r') && propToDisplay.indexOf('g') && propToDisplay.indexOf('b')) == 0) {
+                        propToDisplay.sort();
+                    }
+                    else {
+                        propToDisplay.sort().reverse();
+                    }
                     for (var _b = 0, propToDisplay_1 = propToDisplay; _b < propToDisplay_1.length; _b++) {
                         var prop = propToDisplay_1[_b];
                         var infos = new INSPECTOR.Property(prop, this._property.value);

文件差异内容过多而无法显示
+ 4 - 4
dist/preview release/inspector/babylon.inspector.min.js


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

@@ -4,7 +4,7 @@
     },
     "name": "babylonjs-inspector",
     "description": "The Babylon.js inspector.",
-    "version": "3.1.0-beta5",
+    "version": "3.1.0-beta6",
     "repository": {
         "type": "git",
         "url": "https://github.com/BabylonJS/Babylon.js.git"

+ 8 - 2
dist/preview release/loaders/babylon.glTF1FileLoader.js

@@ -181,7 +181,13 @@ var BABYLON;
             };
         };
         GLTFFileLoader._parseVersion = function (version) {
-            var match = (version + "").match(/^(\d+)\.(\d+)$/);
+            if (version === "1.0" || version === "1.0.1") {
+                return {
+                    major: 1,
+                    minor: 0
+                };
+            }
+            var match = (version + "").match(/^(\d+)\.(\d+)/);
             if (!match) {
                 return null;
             }
@@ -992,7 +998,7 @@ var BABYLON;
                     var skin = gltfRuntime.skins[node.skin];
                     var newMesh = importMesh(gltfRuntime, node, node.meshes, id, node.babylonNode);
                     newMesh.skeleton = gltfRuntime.scene.getLastSkeletonByID(node.skin);
-                    if (newMesh.skeleton === null && skin.babylonSkeleton) {
+                    if (newMesh.skeleton === null) {
                         newMesh.skeleton = importSkeleton(gltfRuntime, skin, newMesh, skin.babylonSkeleton, node.skin);
                         if (!skin.babylonSkeleton) {
                             skin.babylonSkeleton = newMesh.skeleton;

文件差异内容过多而无法显示
+ 1 - 1
dist/preview release/loaders/babylon.glTF1FileLoader.min.js


+ 23 - 4
dist/preview release/loaders/babylon.glTF2FileLoader.js

@@ -181,7 +181,13 @@ var BABYLON;
             };
         };
         GLTFFileLoader._parseVersion = function (version) {
-            var match = (version + "").match(/^(\d+)\.(\d+)$/);
+            if (version === "1.0" || version === "1.0.1") {
+                return {
+                    major: 1,
+                    minor: 0
+                };
+            }
+            var match = (version + "").match(/^(\d+)\.(\d+)/);
             if (!match) {
                 return null;
             }
@@ -999,6 +1005,9 @@ var BABYLON;
             };
             GLTFLoader.prototype._loadSkin = function (context, skin) {
                 var _this = this;
+                if (skin.babylonSkeleton) {
+                    return skin.babylonSkeleton;
+                }
                 var skeletonId = "skeleton" + skin.index;
                 skin.babylonSkeleton = new BABYLON.Skeleton(skin.name || skeletonId, skeletonId, this._babylonScene);
                 if (skin.inverseBindMatrices == null) {
@@ -1206,9 +1215,19 @@ var BABYLON;
                         }
                     }
                     ;
-                    var keys = new Array(inputData.length);
-                    for (var frameIndex = 0; frameIndex < inputData.length; frameIndex++) {
-                        keys[frameIndex] = getNextKey(frameIndex);
+                    var keys;
+                    if (inputData.length === 1) {
+                        var key = getNextKey(0);
+                        keys = [
+                            { frame: key.frame, value: key.value },
+                            { frame: key.frame + 1, value: key.value }
+                        ];
+                    }
+                    else {
+                        keys = new Array(inputData.length);
+                        for (var frameIndex = 0; frameIndex < inputData.length; frameIndex++) {
+                            keys[frameIndex] = getNextKey(frameIndex);
+                        }
                     }
                     if (targetPath === "influence") {
                         var morphTargetManager = targetNode.babylonMesh.morphTargetManager;

文件差异内容过多而无法显示
+ 2 - 2
dist/preview release/loaders/babylon.glTF2FileLoader.min.js


+ 24 - 5
dist/preview release/loaders/babylon.glTFFileLoader.js

@@ -181,7 +181,13 @@ var BABYLON;
             };
         };
         GLTFFileLoader._parseVersion = function (version) {
-            var match = (version + "").match(/^(\d+)\.(\d+)$/);
+            if (version === "1.0" || version === "1.0.1") {
+                return {
+                    major: 1,
+                    minor: 0
+                };
+            }
+            var match = (version + "").match(/^(\d+)\.(\d+)/);
             if (!match) {
                 return null;
             }
@@ -992,7 +998,7 @@ var BABYLON;
                     var skin = gltfRuntime.skins[node.skin];
                     var newMesh = importMesh(gltfRuntime, node, node.meshes, id, node.babylonNode);
                     newMesh.skeleton = gltfRuntime.scene.getLastSkeletonByID(node.skin);
-                    if (newMesh.skeleton === null && skin.babylonSkeleton) {
+                    if (newMesh.skeleton === null) {
                         newMesh.skeleton = importSkeleton(gltfRuntime, skin, newMesh, skin.babylonSkeleton, node.skin);
                         if (!skin.babylonSkeleton) {
                             skin.babylonSkeleton = newMesh.skeleton;
@@ -3144,6 +3150,9 @@ var BABYLON;
             };
             GLTFLoader.prototype._loadSkin = function (context, skin) {
                 var _this = this;
+                if (skin.babylonSkeleton) {
+                    return skin.babylonSkeleton;
+                }
                 var skeletonId = "skeleton" + skin.index;
                 skin.babylonSkeleton = new BABYLON.Skeleton(skin.name || skeletonId, skeletonId, this._babylonScene);
                 if (skin.inverseBindMatrices == null) {
@@ -3351,9 +3360,19 @@ var BABYLON;
                         }
                     }
                     ;
-                    var keys = new Array(inputData.length);
-                    for (var frameIndex = 0; frameIndex < inputData.length; frameIndex++) {
-                        keys[frameIndex] = getNextKey(frameIndex);
+                    var keys;
+                    if (inputData.length === 1) {
+                        var key = getNextKey(0);
+                        keys = [
+                            { frame: key.frame, value: key.value },
+                            { frame: key.frame + 1, value: key.value }
+                        ];
+                    }
+                    else {
+                        keys = new Array(inputData.length);
+                        for (var frameIndex = 0; frameIndex < inputData.length; frameIndex++) {
+                            keys[frameIndex] = getNextKey(frameIndex);
+                        }
                     }
                     if (targetPath === "influence") {
                         var morphTargetManager = targetNode.babylonMesh.morphTargetManager;

文件差异内容过多而无法显示
+ 3 - 3
dist/preview release/loaders/babylon.glTFFileLoader.min.js


+ 24 - 5
dist/preview release/loaders/babylonjs.loaders.js

@@ -1155,7 +1155,13 @@ var BABYLON;
             };
         };
         GLTFFileLoader._parseVersion = function (version) {
-            var match = (version + "").match(/^(\d+)\.(\d+)$/);
+            if (version === "1.0" || version === "1.0.1") {
+                return {
+                    major: 1,
+                    minor: 0
+                };
+            }
+            var match = (version + "").match(/^(\d+)\.(\d+)/);
             if (!match) {
                 return null;
             }
@@ -1966,7 +1972,7 @@ var BABYLON;
                     var skin = gltfRuntime.skins[node.skin];
                     var newMesh = importMesh(gltfRuntime, node, node.meshes, id, node.babylonNode);
                     newMesh.skeleton = gltfRuntime.scene.getLastSkeletonByID(node.skin);
-                    if (newMesh.skeleton === null && skin.babylonSkeleton) {
+                    if (newMesh.skeleton === null) {
                         newMesh.skeleton = importSkeleton(gltfRuntime, skin, newMesh, skin.babylonSkeleton, node.skin);
                         if (!skin.babylonSkeleton) {
                             skin.babylonSkeleton = newMesh.skeleton;
@@ -4100,6 +4106,9 @@ var BABYLON;
             };
             GLTFLoader.prototype._loadSkin = function (context, skin) {
                 var _this = this;
+                if (skin.babylonSkeleton) {
+                    return skin.babylonSkeleton;
+                }
                 var skeletonId = "skeleton" + skin.index;
                 skin.babylonSkeleton = new BABYLON.Skeleton(skin.name || skeletonId, skeletonId, this._babylonScene);
                 if (skin.inverseBindMatrices == null) {
@@ -4307,9 +4316,19 @@ var BABYLON;
                         }
                     }
                     ;
-                    var keys = new Array(inputData.length);
-                    for (var frameIndex = 0; frameIndex < inputData.length; frameIndex++) {
-                        keys[frameIndex] = getNextKey(frameIndex);
+                    var keys;
+                    if (inputData.length === 1) {
+                        var key = getNextKey(0);
+                        keys = [
+                            { frame: key.frame, value: key.value },
+                            { frame: key.frame + 1, value: key.value }
+                        ];
+                    }
+                    else {
+                        keys = new Array(inputData.length);
+                        for (var frameIndex = 0; frameIndex < inputData.length; frameIndex++) {
+                            keys[frameIndex] = getNextKey(frameIndex);
+                        }
                     }
                     if (targetPath === "influence") {
                         var morphTargetManager = targetNode.babylonMesh.morphTargetManager;

文件差异内容过多而无法显示
+ 3 - 3
dist/preview release/loaders/babylonjs.loaders.min.js


+ 1 - 1
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.1.0-beta5",
+    "version": "3.1.0-beta6",
     "repository": {
         "type": "git",
         "url": "https://github.com/BabylonJS/Babylon.js.git"

+ 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.1.0-beta5",
+    "version": "3.1.0-beta6",
     "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.1.0-beta5",
+    "version": "3.1.0-beta6",
     "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.1.0-beta5",
+    "version": "3.1.0-beta6",
     "repository": {
         "type": "git",
         "url": "https://github.com/BabylonJS/Babylon.js.git"

+ 1 - 1
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.1.0-beta5",
+    "version": "3.1.0-beta6",
     "repository": {
         "type": "git",
         "url": "https://github.com/BabylonJS/Babylon.js.git"

+ 2 - 0
gui/src/advancedDynamicTexture.ts

@@ -327,6 +327,8 @@ module BABYLON.GUI {
                         continue;
                     }
                     control.notRenderable = false;
+                    // Account for RenderScale.
+                    projectedPosition.scaleInPlace(this.renderScale);
                     control._moveToProjectedPosition(projectedPosition);
                 }
             }

+ 2 - 2
gui/src/controls/control.ts

@@ -33,8 +33,8 @@ module BABYLON.GUI {
         private _transformCenterX = 0.5;
         private _transformCenterY = 0.5;
         private _transformMatrix = Matrix2D.Identity();
-        private _invertTransformMatrix = Matrix2D.Identity();
-        private _transformedPosition = Vector2.Zero();
+        protected _invertTransformMatrix = Matrix2D.Identity();
+        protected _transformedPosition = Vector2.Zero();
         private _isMatrixDirty = true;
         private _cachedOffsetX: number;
         private _cachedOffsetY: number;

+ 7 - 3
gui/src/controls/slider.ts

@@ -231,7 +231,11 @@ module BABYLON.GUI {
         // Events
         private _pointerIsDown = false;
 
-        private _updateValueFromPointer(x: number): void {
+        private _updateValueFromPointer(x: number, y:number): void {
+            if(this.rotation != 0){
+                this._invertTransformMatrix.transformCoordinates(x, y, this._transformedPosition);
+                x = this._transformedPosition.x;
+            }
             this.value = this._minimum + ((x - this._currentMeasure.left) / this._currentMeasure.width) * (this._maximum - this._minimum);
         }
 
@@ -242,7 +246,7 @@ module BABYLON.GUI {
 
             this._pointerIsDown = true;
 
-            this._updateValueFromPointer(coordinates.x);
+            this._updateValueFromPointer(coordinates.x, coordinates.y);
             this._host._capturingControl = this;
 
             return true;
@@ -250,7 +254,7 @@ module BABYLON.GUI {
 
         public _onPointerMove(target: Control, coordinates: Vector2): void {
             if (this._pointerIsDown) {
-                this._updateValueFromPointer(coordinates.x);
+                this._updateValueFromPointer(coordinates.x, coordinates.y);
             }
 
             super._onPointerMove(target, coordinates);

+ 7 - 1
inspector/src/details/PropertyLine.ts

@@ -388,7 +388,13 @@ module INSPECTOR {
                     let objToDetail = this.value;
                     // Display all properties that are not functions
                     let propToDisplay = Helpers.GetAllLinesPropertiesAsString(objToDetail);
-                    propToDisplay.sort().reverse();
+
+                    // special case for color3
+                    if ((propToDisplay.indexOf('r') && propToDisplay.indexOf('g') && propToDisplay.indexOf('b')) == 0) {
+                        propToDisplay.sort();
+                    } else {
+                        propToDisplay.sort().reverse();
+                    }
 
                     for (let prop of propToDisplay) {
                         let infos = new Property(prop, this._property.value);

+ 6 - 6
loaders/src/glTF/1.0/babylon.glTFLoader.ts

@@ -445,7 +445,7 @@ module BABYLON.GLTF1 {
     /**
     * Imports a skeleton
     */
-    var importSkeleton = (gltfRuntime: IGLTFRuntime, skins: IGLTFSkins, mesh: Mesh, newSkeleton: Skeleton, id: string): Skeleton => {
+    var importSkeleton = (gltfRuntime: IGLTFRuntime, skins: IGLTFSkins, mesh: Mesh, newSkeleton: Skeleton | undefined, id: string): Skeleton => {
 
         if (!newSkeleton) {
             newSkeleton = new Skeleton(skins.name || "", "", gltfRuntime.scene);
@@ -785,7 +785,7 @@ module BABYLON.GLTF1 {
                 var newMesh = importMesh(gltfRuntime, node, node.meshes, id, <Mesh>node.babylonNode);
                 newMesh.skeleton = gltfRuntime.scene.getLastSkeletonByID(node.skin);
 
-                if (newMesh.skeleton === null && skin.babylonSkeleton) {
+                if (newMesh.skeleton === null) {
                     newMesh.skeleton = importSkeleton(gltfRuntime, skin, newMesh, skin.babylonSkeleton, node.skin);
 
                     if (!skin.babylonSkeleton) {
@@ -892,10 +892,10 @@ module BABYLON.GLTF1 {
                         persCamera.minZ = perspectiveCamera.znear;
                     }
 
-                    lastNode = persCamera;
-                }
-            }
-        }
+                     lastNode = persCamera;
+                 }
+             }
+         }
 
         // Empty node
         if (!node.jointName) {

+ 17 - 3
loaders/src/glTF/2.0/babylon.glTFLoader.ts

@@ -808,6 +808,10 @@ module BABYLON.GLTF2 {
         }
 
         private _loadSkin(context: string, skin: IGLTFSkin): Skeleton {
+            if (skin.babylonSkeleton) {
+                return skin.babylonSkeleton;
+            }
+
             const skeletonId = "skeleton" + skin.index;
             skin.babylonSkeleton = new Skeleton(skin.name || skeletonId, skeletonId, this._babylonScene);
 
@@ -1049,9 +1053,19 @@ module BABYLON.GLTF2 {
                     }
                 };
 
-                const keys = new Array(inputData.length);
-                for (let frameIndex = 0; frameIndex < inputData.length; frameIndex++) {
-                    keys[frameIndex] = getNextKey(frameIndex);
+                let keys: Array<any>;
+                if (inputData.length === 1) {
+                    let key = getNextKey(0);
+                    keys = [
+                        { frame: key.frame, value: key.value },
+                        { frame: key.frame + 1, value: key.value }
+                    ];
+                }
+                else {
+                    keys = new Array(inputData.length);
+                    for (let frameIndex = 0; frameIndex < inputData.length; frameIndex++) {
+                        keys[frameIndex] = getNextKey(frameIndex);
+                    }
                 }
 
                 if (targetPath === "influence") {

+ 8 - 1
loaders/src/glTF/babylon.glTFFileLoader.ts

@@ -253,7 +253,14 @@ module BABYLON {
         }
 
         private static _parseVersion(version: string): Nullable<{ major: number, minor: number }> {
-            const match = (version + "").match(/^(\d+)\.(\d+)$/);
+            if (version === "1.0" || version === "1.0.1") {
+                return {
+                    major: 1,
+                    minor: 0
+                };
+            }
+
+            const match = (version + "").match(/^(\d+)\.(\d+)/);
             if (!match) {
                 return null;
             }

+ 3 - 3
localDev/index.html

@@ -7,7 +7,7 @@
 	<script src="https://preview.babylonjs.com/cannon.js"></script>
 	<script src="https://preview.babylonjs.com/Oimo.js"></script>
 	<script src="https://cdnjs.cloudflare.com/ajax/libs/dat-gui/0.6.2/dat.gui.min.js"></script>
-	<script src="../tools/DevLoader/BabylonLoader.js"></script>
+	<script src="../Tools/DevLoader/BabylonLoader.js"></script>
 	<script src="src/webgl-debug.js"></script>
 
 	<style>
@@ -65,7 +65,7 @@
 			.require(indexjs)
 			.load(function() {
 				if (BABYLON.Engine.isSupported()) {
-					engine = new BABYLON.Engine(canvas, true, { stencil: true, disableWebGL2Support: false });
+					engine = new BABYLON.Engine(canvas, true, { stencil: true, disableWebGL2Support: false, preserveDrawingBuffer: true });
 					BABYLONDEVTOOLS.Loader.debugShortcut(engine);
 
 					// call the scene creation from the js.
@@ -108,4 +108,4 @@
 			});
 	</script>
 </body>
-</html>
+</html>

+ 2 - 2
package.json

@@ -8,7 +8,7 @@
     ],
     "name": "babylonjs",
     "description": "Babylon.js is a JavaScript 3D engine based on webgl.",
-    "version": "3.1.0-beta5",
+    "version": "3.1.0-beta6",
     "repository": {
         "type": "git",
         "url": "https://github.com/BabylonJS/Babylon.js.git"
@@ -67,4 +67,4 @@
     "readmeFilename": "README.md",
     "_id": "babylonjs@3.1.0-alpha2",
     "_from": "babylonjs@"
-}
+}

+ 6 - 0
sandbox/index.js

@@ -32,6 +32,7 @@ if (BABYLON.Engine.isSupported()) {
     if (!currentHelpCounter) currentHelpCounter = 0;
 
     // Setting up some GLTF values
+    BABYLON.GLTFFileLoader.IncrementalLoading = false;
     BABYLON.SceneLoader.OnPluginActivatedObservable.add(function(plugin) {
         currentPluginName = plugin.name;
 
@@ -71,6 +72,11 @@ if (BABYLON.Engine.isSupported()) {
         // Fix for IE, otherwise it will change the default filter for files selection after first use
         htmlInput.value = "";
 
+        // removing glTF created camera
+        if (currentScene.activeCamera && currentPluginName === "gltf") {
+            currentScene.activeCamera.dispose();
+            currentScene.activeCamera = null;
+        }
         // Attach camera to canvas inputs
         if (!currentScene.activeCamera || currentScene.lights.length === 0) {
             currentScene.createDefaultCameraOrLight(true);

+ 81 - 86
src/Cameras/VR/babylon.vrExperienceHelper.ts

@@ -31,10 +31,11 @@ module BABYLON {
         private _onVRRequestPresentStart: () => void;
         private _onVRRequestPresentComplete: (success: boolean) => void;
         
-        public onEnteringVR: () => void;
-        public onExitingVR: () => void;
-        public onControllerMeshLoaded: (controller: WebVRController) => void;
+        public onEnteringVR = new Observable(); 
+        public onExitingVR = new Observable();
+        public onControllerMeshLoaded = new Observable<WebVRController>();  
 
+        private _rayLength: number;
         private _useCustomVRButton: boolean = false;
         private _teleportationRequested: boolean = false;
         private _teleportationEnabledOnLeftController: boolean = false;
@@ -61,10 +62,20 @@ module BABYLON {
         private _rightLaserPointer: Nullable<Mesh>;
         private _currentMeshSelected: Nullable<AbstractMesh>;
         public onNewMeshSelected = new Observable<AbstractMesh>();
+        private _circleEase:CircleEase;
 
-        private _meshSelectionPredicate: (mesh: AbstractMesh) => boolean;
-        public meshSelectionPredicate: (mesh: AbstractMesh) => boolean;
+        private _raySelectionPredicate: (mesh: AbstractMesh) => boolean;
+
+        /**
+         * To be optionaly changed by user to define custom ray selection
+         */
+        public raySelectionPredicate: (mesh: AbstractMesh) => boolean;
 
+        /**
+         * To be optionaly changed by user to define custom selection logic (after ray selection)
+         */
+        public meshSelectionPredicate: (mesh: AbstractMesh) => boolean;
+        
         private _currentHit: Nullable<PickingInfo>;
         private _pointerDownOnMeshAsked = false;
         private _isActionableMesh = false;
@@ -103,6 +114,16 @@ module BABYLON {
                 this._deviceOrientationCamera = new BABYLON.DeviceOrientationCamera("deviceOrientationVRHelper", this._position, scene);
                 this._deviceOrientationCamera.minZ = this._scene.activeCamera.minZ;
                 this._deviceOrientationCamera.maxZ = this._scene.activeCamera.maxZ;
+                // Set rotation from previous camera
+                if(this._scene.activeCamera instanceof TargetCamera && this._scene.activeCamera.rotation){
+                    var targetCamera = this._scene.activeCamera;
+                    if(targetCamera.rotationQuaternion){
+                        this._deviceOrientationCamera.rotationQuaternion.copyFrom(targetCamera.rotationQuaternion);
+                    }else{
+                        this._deviceOrientationCamera.rotationQuaternion.copyFrom(Quaternion.RotationYawPitchRoll(targetCamera.rotation.y, targetCamera.rotation.x, targetCamera.rotation.z));
+                    }
+                    this._deviceOrientationCamera.rotation = targetCamera.rotation.clone();
+                }
             }
             this._scene.activeCamera = this._deviceOrientationCamera;
             this._canvas = scene.getEngine().getRenderingCanvas();
@@ -117,6 +138,10 @@ module BABYLON {
                         this._btnVR = webVROptions.customVRButton;
                     }
                 }
+
+                if (webVROptions.rayLength) {
+                    this._rayLength = webVROptions.rayLength
+                }
             }
 
             if (!this._useCustomVRButton) {
@@ -209,6 +234,10 @@ module BABYLON {
             this._webVRCamera.onControllerMeshLoadedObservable.add((webVRController) => this._onDefaultMeshLoaded(webVRController));
         
             this.updateButtonVisibility();
+
+            //create easing functions
+            this._circleEase = new BABYLON.CircleEase();
+            this._circleEase.setEasingMode(BABYLON.EasingFunction.EASINGMODE_EASEINOUT);
         }
 
         // Raised when one of the controller has loaded successfully its associated default mesh
@@ -226,7 +255,7 @@ module BABYLON {
                 }
             }
             if (this.onControllerMeshLoaded) {
-                this.onControllerMeshLoaded(webVRController);
+                this.onControllerMeshLoaded.notifyObservers(webVRController);
             }
         }
 
@@ -302,7 +331,7 @@ module BABYLON {
             }
 
             if (this.onEnteringVR) {
-                this.onEnteringVR();
+                this.onEnteringVR.notifyObservers({});
             }
             if (this._webVRrequesting)
                 return;
@@ -331,7 +360,7 @@ module BABYLON {
          */
         public exitVR() {
             if (this.onExitingVR) {
-                this.onExitingVR();
+                this.onExitingVR.notifyObservers({});
             }
             if (this._webVRpresenting) {
                 this._scene.getEngine().disableVR();
@@ -385,6 +414,7 @@ module BABYLON {
             // (gamma/linear) conflicts.
             const imageProcessingConfiguration = new ImageProcessingConfiguration();
             imageProcessingConfiguration.vignetteColor = new BABYLON.Color4(0, 0, 0, 0);
+            imageProcessingConfiguration.vignetteEnabled = true;
             this._postProcessMove = new BABYLON.ImageProcessingPostProcess("postProcessMove", 
                 1.0, 
                 this._webVRCamera,
@@ -393,28 +423,28 @@ module BABYLON {
                 undefined,
                 undefined,
                 imageProcessingConfiguration);
-            // Force recompilation of the postprocess to be ready before hand and not block the animation.
-            // Simply touching the property forces recompilation of the effect.
-            this._postProcessMove.imageProcessingConfiguration.vignetteEnabled = true;
-            // Go back to default (both variants would be compiled).
-            this._postProcessMove.imageProcessingConfiguration.vignetteEnabled = false;
+            
+            this._webVRCamera.detachPostProcess(this._postProcessMove)
 
             this._passProcessMove = new BABYLON.PassPostProcess("pass", 1.0, this._webVRCamera);
 
             this._createGazeTracker();
             this._createTeleportationCircles();
 
-            // To be optionnaly changed by user to define his custom selection logic
+            this.raySelectionPredicate = (mesh) => {
+                return true;
+            }
+
             this.meshSelectionPredicate = (mesh) => {
                 return true;
             }
 
-            this._meshSelectionPredicate = (mesh) => {
+            this._raySelectionPredicate = (mesh) => {
                 if (mesh.name.indexOf(this._floorMeshName) !== -1 || (mesh.isVisible && mesh.name.indexOf("gazeTracker") === -1 
                         && mesh.name.indexOf("teleportationCircle") === -1
                         && mesh.name.indexOf("torusTeleportation") === -1
                         && mesh.name.indexOf("laserPointer") === -1)) {
-                    return true;
+                    return this.raySelectionPredicate(mesh);
                 }
                 return false;
             }
@@ -709,10 +739,8 @@ module BABYLON {
             });
         
             animationRotation.setKeys(animationRotationKeys);
-        
-            var easingFunction = new BABYLON.CircleEase();
-            easingFunction.setEasingMode(BABYLON.EasingFunction.EASINGMODE_EASEINOUT);
-            animationRotation.setEasingFunction(easingFunction);
+
+            animationRotation.setEasingFunction(this._circleEase);
         
             this.currentVRCamera.animations.push(animationRotation);
         
@@ -736,7 +764,7 @@ module BABYLON {
             });
         
             animationPP.setKeys(vignetteWeightKeys);
-            animationPP.setEasingFunction(easingFunction);
+            animationPP.setEasingFunction(this._circleEase);
             this._postProcessMove.animations.push(animationPP);
         
             var animationPP2 = new BABYLON.Animation("animationPP2", "vignetteStretch", 90, BABYLON.Animation.ANIMATIONTYPE_FLOAT,
@@ -757,15 +785,15 @@ module BABYLON {
             });
         
             animationPP2.setKeys(vignetteStretchKeys);
-            animationPP2.setEasingFunction(easingFunction);
+            animationPP2.setEasingFunction(this._circleEase);
             this._postProcessMove.animations.push(animationPP2);
             
             this._postProcessMove.imageProcessingConfiguration.vignetteWeight = 0;
             this._postProcessMove.imageProcessingConfiguration.vignetteStretch = 0;
-            this._postProcessMove.imageProcessingConfiguration.vignetteEnabled = true;
-        
+
+            this._webVRCamera.attachPostProcess(this._postProcessMove)
             this._scene.beginAnimation(this._postProcessMove, 0, 6, false, 1, () => {
-                this._postProcessMove.imageProcessingConfiguration.vignetteEnabled = false;
+                this._webVRCamera.detachPostProcess(this._postProcessMove)
             });
             this._scene.beginAnimation(this.currentVRCamera, 0, 6, false, 1);
         }
@@ -790,63 +818,30 @@ module BABYLON {
                 this._teleportationCircle.position.y += 0.1;
             }
         }
-
+        private _workingVector = Vector3.Zero();
         private _teleportCamera() {
+            // Teleport the hmd to where the user is looking by moving the anchor to where they are looking minus the
+            // offset of the headset from the anchor. Then add the helper's position to account for user's height offset
+            this.webVRCamera.leftCamera!.globalPosition.subtractToRef(this.webVRCamera.position, this._workingVector);
+            this._haloCenter.subtractToRef(this._workingVector, this._workingVector);
+            this._workingVector.addInPlace(this.position);
+            
+            // Create animation from the camera's position to the new location
             this.currentVRCamera.animations = [];
-        
-            var animationCameraTeleportationX = new BABYLON.Animation("animationCameraTeleportationX", "position.x", 90, BABYLON.Animation.ANIMATIONTYPE_FLOAT,
-                BABYLON.Animation.ANIMATIONLOOPMODE_CONSTANT);
-        
-            var animationCameraTeleportationXKeys = [];
-            animationCameraTeleportationXKeys.push({
-                frame: 0,
-                value: this.currentVRCamera.position.x
-            });
-            animationCameraTeleportationXKeys.push({
-                frame: 11,
-                value: this._haloCenter.x
-            });
-        
-            var easingFunction = new BABYLON.CircleEase();
-            easingFunction.setEasingMode(BABYLON.EasingFunction.EASINGMODE_EASEINOUT);
-
-            animationCameraTeleportationX.setKeys(animationCameraTeleportationXKeys);
-            animationCameraTeleportationX.setEasingFunction(easingFunction);
-            this.currentVRCamera.animations.push(animationCameraTeleportationX);
-
-            var animationCameraTeleportationY = new BABYLON.Animation("animationCameraTeleportationY", "position.y", 90, BABYLON.Animation.ANIMATIONTYPE_FLOAT,
-            BABYLON.Animation.ANIMATIONLOOPMODE_CONSTANT);
-    
-            var animationCameraTeleportationYKeys = [];
-            animationCameraTeleportationYKeys.push({
-                frame: 0,
-                value: this.currentVRCamera.position.y
-            });
-            animationCameraTeleportationYKeys.push({
-                frame: 11,
-                value: this._haloCenter.y+1.7
-            });
-        
-            animationCameraTeleportationY.setKeys(animationCameraTeleportationYKeys);
-            animationCameraTeleportationY.setEasingFunction(easingFunction);
-            this.currentVRCamera.animations.push(animationCameraTeleportationY);
-        
-            var animationCameraTeleportationZ = new BABYLON.Animation("animationCameraTeleportationZ", "position.z", 90, BABYLON.Animation.ANIMATIONTYPE_FLOAT,
-                BABYLON.Animation.ANIMATIONLOOPMODE_CONSTANT);
-        
-            var animationCameraTeleportationZKeys = [];
-            animationCameraTeleportationZKeys.push({
-                frame: 0,
-                value: this.currentVRCamera.position.z
-            });
-            animationCameraTeleportationZKeys.push({
-                frame: 11,
-                value: this._haloCenter.z
-            });
-        
-            animationCameraTeleportationZ.setKeys(animationCameraTeleportationZKeys);
-            animationCameraTeleportationZ.setEasingFunction(easingFunction);
-            this.currentVRCamera.animations.push(animationCameraTeleportationZ);
+            var animationCameraTeleportation = new BABYLON.Animation("animationCameraTeleportation", "position", 90, BABYLON.Animation.ANIMATIONTYPE_VECTOR3, BABYLON.Animation.ANIMATIONLOOPMODE_CONSTANT);
+            var animationCameraTeleportationKeys = [{
+                    frame: 0,
+                    value: this.currentVRCamera.position
+                },
+                {
+                    frame: 11,
+                    value: this._workingVector
+                }
+            ];
+            
+            animationCameraTeleportation.setKeys(animationCameraTeleportationKeys);
+            animationCameraTeleportation.setEasingFunction(this._circleEase);
+            this.currentVRCamera.animations.push(animationCameraTeleportation);
         
             this._postProcessMove.animations = [];
         
@@ -892,10 +887,10 @@ module BABYLON {
         
             this._postProcessMove.imageProcessingConfiguration.vignetteWeight = 8;
             this._postProcessMove.imageProcessingConfiguration.vignetteStretch = 10;
-            this._postProcessMove.imageProcessingConfiguration.vignetteEnabled = true;
             
+            this._webVRCamera.attachPostProcess(this._postProcessMove)
             this._scene.beginAnimation(this._postProcessMove, 0, 11, false, 1, () => {
-                this._postProcessMove.imageProcessingConfiguration.vignetteEnabled = false;
+                this._webVRCamera.detachPostProcess(this._postProcessMove)
             });
             this._scene.beginAnimation(this.currentVRCamera, 0, 11, false, 1);
         }
@@ -906,18 +901,18 @@ module BABYLON {
                 (this._leftLaserPointer && !this._leftLaserPointer.isVisible && !this._rightLaserPointer) || 
                 (this._rightLaserPointer && !this._rightLaserPointer.isVisible && !this._leftLaserPointer) || 
                 (this._rightLaserPointer && this._leftLaserPointer && !this._rightLaserPointer.isVisible && !this._leftLaserPointer.isVisible)) {
-                    ray = this.currentVRCamera.getForwardRay();
+                    ray = this.currentVRCamera.getForwardRay(this._rayLength);
                 
             } else {
                 if (this._leftLaserPointer && this._leftLaserPointer.isVisible) {
-                    ray = (<any>this.currentVRCamera).leftController.getForwardRay();
+                    ray = (<any>this.currentVRCamera).leftController.getForwardRay(this._rayLength);
                 }
                 else {
-                    ray = (<any>this.currentVRCamera).rightController.getForwardRay();
+                    ray = (<any>this.currentVRCamera).rightController.getForwardRay(this._rayLength);
                 }
             }
         
-            var hit = this._scene.pickWithRay(ray, this._meshSelectionPredicate);
+            var hit = this._scene.pickWithRay(ray, this._raySelectionPredicate);
 
             // Moving the gazeTracker on the mesh face targetted
             if (hit && hit.pickedPoint) {

+ 5 - 1
src/Cameras/VR/babylon.webVRCamera.ts

@@ -37,6 +37,7 @@ module BABYLON {
         defaultLightingOnControllers?: boolean; // creating a default HemiLight only on controllers
         useCustomVRButton?: boolean; // if you don't want to use the default VR button of the helper
         customVRButton?: HTMLButtonElement; //if you'd like to provide your own button to the VRHelper
+        rayLength?: number; // to change the length of the ray for gaze/controllers.
     }
 
     export class WebVRFreeCamera extends FreeCamera implements PoseControlled {
@@ -179,9 +180,12 @@ module BABYLON {
             return this._rightController;
         };
 
+
+        
         public getForwardRay(length = 100): Ray {
             if (this.leftCamera) {
-                return super.getForwardRay(length, this.leftCamera.getWorldMatrix(), this.position.add(this.devicePosition)); // Need the actual rendered camera
+                // Use left eye to avoid computation to compute center on every call
+                return super.getForwardRay(length, this.leftCamera.getWorldMatrix(), this.leftCamera.globalPosition); // Need the actual rendered camera
             }
             else {
                 return super.getForwardRay(length);

+ 1 - 1
src/Layer/babylon.highlightlayer.ts

@@ -825,7 +825,7 @@
 
             this._shouldRender = false;
             for (var meshHighlightToCheck in this._meshes) {
-                if (meshHighlightToCheck) {
+                if (this._meshes[meshHighlightToCheck]) {
                     this._shouldRender = true;
                     break;
                 }

+ 11 - 3
src/Materials/PBR/babylon.pbrBaseMaterial.ts

@@ -27,6 +27,7 @@
         public SPECULAROVERALPHA = false;
         public RADIANCEOVERALPHA = false;
         public ALPHAFRESNEL = false;
+        public LINEARALPHAFRESNEL = false;
         public PREMULTIPLYALPHA = false;
 
         public EMISSIVE = false;
@@ -394,11 +395,17 @@
 
         /**
          * A fresnel is applied to the alpha of the model to ensure grazing angles edges are not alpha tested.
-         * And/Or occlude the blended part.
+         * And/Or occlude the blended part. (alpha is converted to gamma to compute the fresnel)
          */
         protected _useAlphaFresnel = false;
 
         /**
+         * A fresnel is applied to the alpha of the model to ensure grazing angles edges are not alpha tested.
+         * And/Or occlude the blended part. (alpha stays linear to compute the fresnel)
+         */
+        protected _useLinearAlphaFresnel = false;
+
+        /**
          * The transparency mode of the material.
          */
         protected _transparencyMode: Nullable<number> = null;
@@ -572,7 +579,7 @@
                 return false;
             }
 
-            return this._albedoTexture != null && this._albedoTexture.hasAlpha && this._transparencyMode === PBRMaterial.PBRMATERIAL_ALPHATEST;
+            return this._albedoTexture != null && this._albedoTexture.hasAlpha && (this._transparencyMode == null || this._transparencyMode === PBRMaterial.PBRMATERIAL_ALPHATEST);
         }
 
         /**
@@ -871,7 +878,8 @@
                 defines.ALPHATESTVALUE = this._alphaCutOff;
                 defines.PREMULTIPLYALPHA = (this.alphaMode === Engine.ALPHA_PREMULTIPLIED || this.alphaMode === Engine.ALPHA_PREMULTIPLIED_PORTERDUFF);
                 defines.ALPHABLEND = this.needAlphaBlendingForMesh(mesh);
-                defines.ALPHAFRESNEL = this._useAlphaFresnel;
+                defines.ALPHAFRESNEL = this._useAlphaFresnel || this._useLinearAlphaFresnel;
+                defines.LINEARALPHAFRESNEL = this._useLinearAlphaFresnel;
             }
 
             if (defines._areImageProcessingDirty) {

+ 24 - 1
src/Materials/PBR/babylon.pbrBaseSimpleMaterial.ts

@@ -103,6 +103,14 @@
             this._markAllSubMeshesAsTexturesDirty();
         }
 
+        @serializeAsTexture()
+        @expandToProperty("_markAllSubMeshesAsTexturesDirty", null)
+        public lightmapTexture: BaseTexture;
+
+        @serialize()
+        @expandToProperty("_markAllSubMeshesAsTexturesDirty")
+        public useLightmapAsShadowmap = false;
+
         /**
          * Return the active textures of the material.
          */
@@ -125,9 +133,25 @@
                 activeTextures.push(this.occlusionTexture);
             }
 
+            if (this.lightmapTexture) {
+                activeTextures.push(this.lightmapTexture);
+            }
+
             return activeTextures;
         }
 
+        public hasTexture(texture: BaseTexture): boolean {
+            if (super.hasTexture(texture)) {
+                return true;
+            }
+
+            if (this.lightmapTexture === texture) {
+                return true;
+            }
+
+            return false;
+        }
+
         /**
          * Instantiates a new PBRMaterial instance.
          * 
@@ -137,7 +161,6 @@
         constructor(name: string, scene: Scene) {
             super(name, scene);
 
-            this._transparencyMode = PBRMaterial.PBRMATERIAL_OPAQUE;
             this._useAlphaFromAlbedoTexture = true;
             this._useAmbientInGrayScale = true;
         }

+ 9 - 1
src/Materials/PBR/babylon.pbrMaterial.ts

@@ -382,7 +382,7 @@
 
         /**
          * A fresnel is applied to the alpha of the model to ensure grazing angles edges are not alpha tested.
-         * And/Or occlude the blended part.
+         * And/Or occlude the blended part. (alpha is converted to gamma to compute the fresnel)
          */
         @serialize()
         @expandToProperty("_markAllSubMeshesAsTexturesDirty")
@@ -390,6 +390,14 @@
 
         /**
          * A fresnel is applied to the alpha of the model to ensure grazing angles edges are not alpha tested.
+         * And/Or occlude the blended part. (alpha stays linear to compute the fresnel)
+         */
+        @serialize()
+        @expandToProperty("_markAllSubMeshesAsTexturesDirty")
+        public useLinearAlphaFresnel = false;
+
+        /**
+         * A fresnel is applied to the alpha of the model to ensure grazing angles edges are not alpha tested.
          * And/Or occlude the blended part.
          */
         @serializeAsTexture()

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

@@ -250,7 +250,7 @@
             var intersectInfo: Nullable<IntersectionInfo> = null;
 
             // LineMesh first as it's also a Mesh...
-            if (this._mesh instanceof LinesMesh) {
+            if (BABYLON.LinesMesh && this._mesh instanceof LinesMesh) {
                 var lineMesh = <LinesMesh>this._mesh;
 
                 // Line test

+ 18 - 9
src/Mesh/babylon.transformNode.ts

@@ -331,22 +331,31 @@ module BABYLON {
         }
 
         private static _lookAtVectorCache = new Vector3(0, 0, 0);
-        public lookAt(targetPoint: Vector3, yawCor: number = 0, pitchCor: number = 0, rollCor: number = 0, space: Space = Space.LOCAL): TransformNode {
-            /// <summary>Orients a mesh towards a target point. Mesh must be drawn facing user.</summary>
-            /// <param name="targetPoint" type="Vector3">The position (must be in same space as current mesh) to look at</param>
-            /// <param name="yawCor" type="Number">optional yaw (y-axis) correction in radians</param>
-            /// <param name="pitchCor" type="Number">optional pitch (x-axis) correction in radians</param>
-            /// <param name="rollCor" type="Number">optional roll (z-axis) correction in radians</param>
-            /// <returns>Mesh oriented towards targetMesh</returns>
 
+        /**
+         * Orients a mesh towards a target point. Mesh must be drawn facing user.
+         * @param targetPoint the position (must be in same space as current mesh) to look at
+         * @param yawCor optional yaw (y-axis) correction in radians
+         * @param pitchCor optional pitch (x-axis) correction in radians
+         * @param rollCor optional roll (z-axis) correction in radians
+         * @param space the choosen space of the target
+         * @returns the TransformNode. 
+         */
+        public lookAt(targetPoint: Vector3, yawCor: number = 0, pitchCor: number = 0, rollCor: number = 0, space: Space = Space.LOCAL): TransformNode {
             var dv = AbstractMesh._lookAtVectorCache;
             var pos = space === Space.LOCAL ? this.position : this.getAbsolutePosition();
             targetPoint.subtractToRef(pos, dv);
             var yaw = -Math.atan2(dv.z, dv.x) - Math.PI / 2;
             var len = Math.sqrt(dv.x * dv.x + dv.z * dv.z);
             var pitch = Math.atan2(dv.y, len);
-            this.rotationQuaternion = this.rotationQuaternion || new Quaternion();
-            Quaternion.RotationYawPitchRollToRef(yaw + yawCor, pitch + pitchCor, rollCor, this.rotationQuaternion);
+            if (this.rotationQuaternion) {
+                Quaternion.RotationYawPitchRollToRef(yaw + yawCor, pitch + pitchCor, rollCor, this.rotationQuaternion);
+            }
+            else {
+                this.rotation.x = pitch + pitchCor;
+                this.rotation.y = yaw + yawCor;
+                this.rotation.z = rollCor;
+            }
             return this;
         }
 

+ 12 - 12
src/Physics/babylon.physicsHelper.ts

@@ -3,7 +3,7 @@ module BABYLON {
     /**
      * The strenght of the force in correspondence to the distance of the affected object
      */
-    export enum PhysicsRadialImpulseFallof {
+    export enum PhysicsRadialImpulseFalloff {
         Constant, // impulse is constant in strength across it's whole radius
         Linear // impulse gets weaker if it's further from the origin
     }
@@ -34,9 +34,9 @@ module BABYLON {
          * @param {Vector3} origin the origin of the explosion
          * @param {number} radius the explosion radius
          * @param {number} strength the explosion strength
-         * @param {PhysicsRadialImpulseFallof} falloff possible options: Constant & Linear. Defaults to Constant
+         * @param {PhysicsRadialImpulseFalloff} falloff possible options: Constant & Linear. Defaults to Constant
          */
-        public applyRadialExplosionImpulse(origin: Vector3, radius: number, strength: number, falloff: PhysicsRadialImpulseFallof = PhysicsRadialImpulseFallof.Constant): Nullable<PhysicsRadialExplosionEvent> {
+        public applyRadialExplosionImpulse(origin: Vector3, radius: number, strength: number, falloff: PhysicsRadialImpulseFalloff = PhysicsRadialImpulseFalloff.Constant): Nullable<PhysicsRadialExplosionEvent> {
             if (!this._physicsEngine) {
                 Tools.Warn('Physics engine not enabled. Please enable the physics before you call this method.');
                 return null;
@@ -67,9 +67,9 @@ module BABYLON {
          * @param {Vector3} origin the origin of the explosion
          * @param {number} radius the explosion radius
          * @param {number} strength the explosion strength
-         * @param {PhysicsRadialImpulseFallof} falloff possible options: Constant & Linear. Defaults to Constant
+         * @param {PhysicsRadialImpulseFalloff} falloff possible options: Constant & Linear. Defaults to Constant
          */
-        public applyRadialExplosionForce(origin: Vector3, radius: number, strength: number, falloff: PhysicsRadialImpulseFallof = PhysicsRadialImpulseFallof.Constant): Nullable<PhysicsRadialExplosionEvent> {
+        public applyRadialExplosionForce(origin: Vector3, radius: number, strength: number, falloff: PhysicsRadialImpulseFalloff = PhysicsRadialImpulseFalloff.Constant): Nullable<PhysicsRadialExplosionEvent> {
             if (!this._physicsEngine) {
                 Tools.Warn('Physics engine not enabled. Please enable the physics before you call the PhysicsHelper.');
                 return null;
@@ -100,9 +100,9 @@ module BABYLON {
          * @param {Vector3} origin the origin of the explosion
          * @param {number} radius the explosion radius
          * @param {number} strength the explosion strength
-         * @param {PhysicsRadialImpulseFallof} falloff possible options: Constant & Linear. Defaults to Constant
+         * @param {PhysicsRadialImpulseFalloff} falloff possible options: Constant & Linear. Defaults to Constant
          */
-        public gravitationalField(origin: Vector3, radius: number, strength: number, falloff: PhysicsRadialImpulseFallof = PhysicsRadialImpulseFallof.Constant): Nullable<PhysicsGravitationalFieldEvent> {
+        public gravitationalField(origin: Vector3, radius: number, strength: number, falloff: PhysicsRadialImpulseFalloff = PhysicsRadialImpulseFalloff.Constant): Nullable<PhysicsGravitationalFieldEvent> {
             if (!this._physicsEngine) {
                 Tools.Warn('Physics engine not enabled. Please enable the physics before you call the PhysicsHelper.');
                 return null;
@@ -177,10 +177,10 @@ module BABYLON {
          * @param {Vector3} origin the origin of the explosion
          * @param {number} radius the explosion radius
          * @param {number} strength the explosion strength
-         * @param {PhysicsRadialImpulseFallof} falloff possible options: Constant & Linear
+         * @param {PhysicsRadialImpulseFalloff} falloff possible options: Constant & Linear
          * @returns {Nullable<PhysicsForceAndContactPoint>}
          */
-        public getImpostorForceAndContactPoint(impostor: PhysicsImpostor, origin: Vector3, radius: number, strength: number, falloff: PhysicsRadialImpulseFallof): Nullable<PhysicsForceAndContactPoint> {
+        public getImpostorForceAndContactPoint(impostor: PhysicsImpostor, origin: Vector3, radius: number, strength: number, falloff: PhysicsRadialImpulseFalloff): Nullable<PhysicsForceAndContactPoint> {
             if (impostor.mass === 0) {
                 return null;
             }
@@ -207,7 +207,7 @@ module BABYLON {
                 return null;
             }
 
-            var multiplier = falloff === PhysicsRadialImpulseFallof.Constant
+            var multiplier = falloff === PhysicsRadialImpulseFalloff.Constant
                 ? strength
                 : strength * (1 - (distanceFromOrigin / radius));
 
@@ -265,12 +265,12 @@ module BABYLON {
         private _origin: Vector3;
         private _radius: number;
         private _strength: number;
-        private _falloff: PhysicsRadialImpulseFallof;
+        private _falloff: PhysicsRadialImpulseFalloff;
         private _tickCallback: any;
         private _sphere: Mesh;
         private _dataFetched: boolean = false; // check if the has been fetched the data. If not, do cleanup
 
-        constructor(physicsHelper: PhysicsHelper, scene: Scene, origin: Vector3, radius: number, strength: number, falloff: PhysicsRadialImpulseFallof = PhysicsRadialImpulseFallof.Constant) {
+        constructor(physicsHelper: PhysicsHelper, scene: Scene, origin: Vector3, radius: number, strength: number, falloff: PhysicsRadialImpulseFalloff = PhysicsRadialImpulseFalloff.Constant) {
             this._physicsHelper = physicsHelper;
             this._scene = scene;
             this._origin = origin;

+ 1 - 1
src/Physics/babylon.physicsImpostor.ts

@@ -157,7 +157,7 @@ module BABYLON {
             this._physicsEngine.removeImpostor(this);
             this.physicsBody = null;
             this._parent = this._parent || this._getPhysicsParent();
-            if (!this.parent || this._options.ignoreParent) {
+            if (!this._isDisposed && (!this.parent || this._options.ignoreParent)) {
                 this._physicsEngine.addImpostor(this);
             }
         }

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

@@ -319,8 +319,9 @@
             // Setup the configuration as forced by the constructor. This would then not force the 
             // scene materials output in linear space and let untouched the default forward pass.
             if (imageProcessingConfiguration) {
+                imageProcessingConfiguration.applyByPostProcess = true;
                 this._attachImageProcessingConfiguration(imageProcessingConfiguration, true);
-                this.imageProcessingConfiguration.applyByPostProcess = false;
+                // This will cause the shader to be compiled
                 this.fromLinearSpace = false;
             }
             // Setup the default processing configuration to the scene.

+ 6 - 1
src/Shaders/pbr.fragment.fx

@@ -388,7 +388,12 @@ void main(void) {
 		// for use with the linear HDR render target. The final composition will be converted back to gamma encoded values for eventual display.
 		// Uses power 2.0 rather than 2.2 for simplicity/efficiency, and because the mapping does not need to map the gamma applied to RGB.
 		float opacityPerceptual = alpha;
-		float opacity0 = opacityPerceptual * opacityPerceptual;
+
+		#ifdef LINEARALPHAFRESNEL
+			float opacity0 = opacityPerceptual;
+		#else
+			float opacity0 = opacityPerceptual * opacityPerceptual;
+		#endif
 		float opacity90 = fresnelGrazingReflectance(opacity0);
 
 		vec3 normalForward = faceforward(normalW, -viewDirectionW, normalW);

+ 7 - 10
src/babylon.scene.ts

@@ -4154,7 +4154,7 @@
             return pickingInfo || new PickingInfo();
         }
 
-        private _tempPickingRay: Ray;
+        private _tempPickingRay: Nullable<Ray> = BABYLON.Ray ? Ray.Zero() : null;
 
         /** Launch a ray to try to pick a mesh in the scene
          * @param x position on screen
@@ -4164,13 +4164,13 @@
          * @param camera to use for computing the picking ray. Can be set to null. In this case, the scene.activeCamera will be used
          */
         public pick(x: number, y: number, predicate?: (mesh: AbstractMesh) => boolean, fastCheck?: boolean, camera?: Nullable<Camera>): Nullable<PickingInfo> {
-            if (!this._tempPickingRay) {
-                this._tempPickingRay = Ray.Zero();
+            if (!BABYLON.PickingInfo) {
+                return null;
             }
 
             return this._internalPick(world => {
-                this.createPickingRayToRef(x, y, world, this._tempPickingRay, camera || null);
-                return this._tempPickingRay;
+                this.createPickingRayToRef(x, y, world, this._tempPickingRay!, camera || null);
+                return this._tempPickingRay!;
             }, predicate, fastCheck);
         }
 
@@ -4182,12 +4182,9 @@
          * @param camera camera to use for computing the picking ray. Can be set to null. In this case, the scene.activeCamera will be used
          */
         public pickSprite(x: number, y: number, predicate?: (sprite: Sprite) => boolean, fastCheck?: boolean, camera?: Camera): Nullable<PickingInfo> {
-            if (!this._tempPickingRay) {
-                this._tempPickingRay = Ray.Zero();
-            }
-            this.createPickingRayInCameraSpaceToRef(x, y, this._tempPickingRay, camera);
+            this.createPickingRayInCameraSpaceToRef(x, y, this._tempPickingRay!, camera);
 
-            return this._internalPickSprites(this._tempPickingRay, predicate, fastCheck, camera);
+            return this._internalPickSprites(this._tempPickingRay!, predicate, fastCheck, camera);
         }
 
         private _cachedRayForTransform: Ray;