소스 검색

Fixing issues with shadows and instances

David Catuhe 9 년 전
부모
커밋
cc7affa66f

파일 크기가 너무 크기때문에 변경 상태를 표시하지 않습니다.
+ 19 - 19
dist/preview release/babylon.core.js


+ 136 - 132
dist/preview release/babylon.d.ts

@@ -1704,6 +1704,12 @@ declare module BABYLON {
          * @param {boolean} fullDetails - support for multiple levels of logging within scene loading
          */
         toString(fullDetails?: boolean): string;
+        /**
+        * Get bone's index searching by name
+        * @param {string} name is bone's name to search for
+        * @return {number} Indice of the bone. Returns -1 if not found
+        */
+        getBoneIndexByName(name: string): number;
         createAnimationRange(name: string, from: number, to: number): void;
         deleteAnimationRange(name: string, deleteFrames?: boolean): void;
         getAnimationRange(name: string): AnimationRange;
@@ -2002,8 +2008,6 @@ declare module BABYLON {
         targetScreenOffset: Vector2;
         allowUpsideDown: boolean;
         _viewMatrix: Matrix;
-        _attachedElement: HTMLElement;
-        _noPreventDefault: boolean;
         _useCtrlForPanning: boolean;
         inputs: ArcRotateCameraInputsManager;
         _reset: () => void;
@@ -2175,6 +2179,7 @@ declare module BABYLON {
     class CameraInputsManager<TCamera extends BABYLON.Camera> {
         attached: CameraInputsMap<TCamera>;
         attachedElement: HTMLElement;
+        noPreventDefault: boolean;
         camera: TCamera;
         checkInputs: () => void;
         constructor(camera: TCamera);
@@ -2182,9 +2187,10 @@ declare module BABYLON {
         remove(inputToRemove: ICameraInput<TCamera>): void;
         removeByType(inputType: string): void;
         private _addCheckInputs(fn);
+        attachInput(input: ICameraInput<TCamera>): void;
         attachElement(element: HTMLElement, noPreventDefault?: boolean): void;
         detachElement(element: HTMLElement): void;
-        rebuildInputCheck(element: HTMLElement): void;
+        rebuildInputCheck(): void;
         clear(): void;
         serialize(serializedCamera: any): void;
         parse(parsedCamera: any): void;
@@ -2244,8 +2250,6 @@ declare module BABYLON {
         private _oldPosition;
         private _diffPosition;
         private _newPosition;
-        _attachedElement: HTMLElement;
-        _noPreventDefault: boolean;
         _localDirection: Vector3;
         _transformedDirection: Vector3;
         constructor(name: string, position: Vector3, scene: Scene);
@@ -2391,93 +2395,46 @@ declare module BABYLON {
 }
 
 declare module BABYLON {
-    class BoundingBox {
-        minimum: Vector3;
-        maximum: Vector3;
-        vectors: Vector3[];
-        center: Vector3;
-        extendSize: Vector3;
-        directions: Vector3[];
-        vectorsWorld: Vector3[];
-        minimumWorld: Vector3;
-        maximumWorld: Vector3;
-        private _worldMatrix;
-        constructor(minimum: Vector3, maximum: Vector3);
-        getWorldMatrix(): Matrix;
-        setWorldMatrix(matrix: Matrix): BoundingBox;
-        _update(world: Matrix): void;
-        isInFrustum(frustumPlanes: Plane[]): boolean;
-        isCompletelyInFrustum(frustumPlanes: Plane[]): boolean;
-        intersectsPoint(point: Vector3): boolean;
-        intersectsSphere(sphere: BoundingSphere): boolean;
-        intersectsMinMax(min: Vector3, max: Vector3): boolean;
-        static Intersects(box0: BoundingBox, box1: BoundingBox): boolean;
-        static IntersectsSphere(minPoint: Vector3, maxPoint: Vector3, sphereCenter: Vector3, sphereRadius: number): boolean;
-        static IsCompletelyInFrustum(boundingVectors: Vector3[], frustumPlanes: Plane[]): boolean;
-        static IsInFrustum(boundingVectors: Vector3[], frustumPlanes: Plane[]): boolean;
-    }
-}
-
-declare module BABYLON {
-    class BoundingInfo {
-        minimum: Vector3;
-        maximum: Vector3;
-        boundingBox: BoundingBox;
-        boundingSphere: BoundingSphere;
-        private _isLocked;
-        constructor(minimum: Vector3, maximum: Vector3);
-        isLocked: boolean;
-        update(world: Matrix): void;
-        isInFrustum(frustumPlanes: Plane[]): boolean;
-        isCompletelyInFrustum(frustumPlanes: Plane[]): boolean;
-        _checkCollision(collider: Collider): boolean;
-        intersectsPoint(point: Vector3): boolean;
-        intersects(boundingInfo: BoundingInfo, precise: boolean): boolean;
-    }
-}
-
-declare module BABYLON {
-    class BoundingSphere {
-        minimum: Vector3;
-        maximum: Vector3;
-        center: Vector3;
-        radius: number;
-        centerWorld: Vector3;
-        radiusWorld: number;
-        private _tempRadiusVector;
-        constructor(minimum: Vector3, maximum: Vector3);
-        _update(world: Matrix): void;
-        isInFrustum(frustumPlanes: Plane[]): boolean;
-        intersectsPoint(point: Vector3): boolean;
-        static Intersects(sphere0: BoundingSphere, sphere1: BoundingSphere): boolean;
+    class LensFlare {
+        size: number;
+        position: number;
+        color: Color3;
+        texture: Texture;
+        private _system;
+        constructor(size: number, position: number, color: any, imgUrl: string, system: LensFlareSystem);
+        dispose: () => void;
     }
 }
 
 declare module BABYLON {
-    class Ray {
-        origin: Vector3;
-        direction: Vector3;
-        length: number;
-        private _edge1;
-        private _edge2;
-        private _pvec;
-        private _tvec;
-        private _qvec;
-        constructor(origin: Vector3, direction: Vector3, length?: number);
-        intersectsBoxMinMax(minimum: Vector3, maximum: Vector3): boolean;
-        intersectsBox(box: BoundingBox): boolean;
-        intersectsSphere(sphere: any): boolean;
-        intersectsTriangle(vertex0: Vector3, vertex1: Vector3, vertex2: Vector3): IntersectionInfo;
-        static CreateNew(x: number, y: number, viewportWidth: number, viewportHeight: number, world: Matrix, view: Matrix, projection: Matrix): Ray;
-        /**
-        * Function will create a new transformed ray starting from origin and ending at the end point. Ray's length will be set, and ray will be
-        * transformed to the given world matrix.
-        * @param origin The origin point
-        * @param end The end point
-        * @param world a matrix to transform the ray to. Default is the identity matrix.
-        */
-        static CreateNewFromTo(origin: Vector3, end: Vector3, world?: Matrix): Ray;
-        static Transform(ray: Ray, matrix: Matrix): Ray;
+    class LensFlareSystem {
+        name: string;
+        lensFlares: LensFlare[];
+        borderLimit: number;
+        meshesSelectionPredicate: (mesh: Mesh) => boolean;
+        layerMask: number;
+        private _scene;
+        private _emitter;
+        private _vertexDeclaration;
+        private _vertexStrideSize;
+        private _vertexBuffer;
+        private _indexBuffer;
+        private _effect;
+        private _positionX;
+        private _positionY;
+        private _isEnabled;
+        constructor(name: string, emitter: any, scene: Scene);
+        isEnabled: boolean;
+        getScene(): Scene;
+        getEmitter(): any;
+        setEmitter(newEmitter: any): void;
+        getEmitterPosition(): Vector3;
+        computeEffectivePosition(globalViewport: Viewport): boolean;
+        _isVisible(): boolean;
+        render(): boolean;
+        dispose(): void;
+        static Parse(parsedLensFlareSystem: any, scene: Scene, rootUrl: string): LensFlareSystem;
+        serialize(): any;
     }
 }
 
@@ -2593,46 +2550,93 @@ declare module BABYLON {
 }
 
 declare module BABYLON {
-    class LensFlare {
-        size: number;
-        position: number;
-        color: Color3;
-        texture: Texture;
-        private _system;
-        constructor(size: number, position: number, color: any, imgUrl: string, system: LensFlareSystem);
-        dispose: () => void;
+    class BoundingBox {
+        minimum: Vector3;
+        maximum: Vector3;
+        vectors: Vector3[];
+        center: Vector3;
+        extendSize: Vector3;
+        directions: Vector3[];
+        vectorsWorld: Vector3[];
+        minimumWorld: Vector3;
+        maximumWorld: Vector3;
+        private _worldMatrix;
+        constructor(minimum: Vector3, maximum: Vector3);
+        getWorldMatrix(): Matrix;
+        setWorldMatrix(matrix: Matrix): BoundingBox;
+        _update(world: Matrix): void;
+        isInFrustum(frustumPlanes: Plane[]): boolean;
+        isCompletelyInFrustum(frustumPlanes: Plane[]): boolean;
+        intersectsPoint(point: Vector3): boolean;
+        intersectsSphere(sphere: BoundingSphere): boolean;
+        intersectsMinMax(min: Vector3, max: Vector3): boolean;
+        static Intersects(box0: BoundingBox, box1: BoundingBox): boolean;
+        static IntersectsSphere(minPoint: Vector3, maxPoint: Vector3, sphereCenter: Vector3, sphereRadius: number): boolean;
+        static IsCompletelyInFrustum(boundingVectors: Vector3[], frustumPlanes: Plane[]): boolean;
+        static IsInFrustum(boundingVectors: Vector3[], frustumPlanes: Plane[]): boolean;
     }
 }
 
 declare module BABYLON {
-    class LensFlareSystem {
-        name: string;
-        lensFlares: LensFlare[];
-        borderLimit: number;
-        meshesSelectionPredicate: (mesh: Mesh) => boolean;
-        layerMask: number;
-        private _scene;
-        private _emitter;
-        private _vertexDeclaration;
-        private _vertexStrideSize;
-        private _vertexBuffer;
-        private _indexBuffer;
-        private _effect;
-        private _positionX;
-        private _positionY;
-        private _isEnabled;
-        constructor(name: string, emitter: any, scene: Scene);
-        isEnabled: boolean;
-        getScene(): Scene;
-        getEmitter(): any;
-        setEmitter(newEmitter: any): void;
-        getEmitterPosition(): Vector3;
-        computeEffectivePosition(globalViewport: Viewport): boolean;
-        _isVisible(): boolean;
-        render(): boolean;
-        dispose(): void;
-        static Parse(parsedLensFlareSystem: any, scene: Scene, rootUrl: string): LensFlareSystem;
-        serialize(): any;
+    class BoundingInfo {
+        minimum: Vector3;
+        maximum: Vector3;
+        boundingBox: BoundingBox;
+        boundingSphere: BoundingSphere;
+        private _isLocked;
+        constructor(minimum: Vector3, maximum: Vector3);
+        isLocked: boolean;
+        update(world: Matrix): void;
+        isInFrustum(frustumPlanes: Plane[]): boolean;
+        isCompletelyInFrustum(frustumPlanes: Plane[]): boolean;
+        _checkCollision(collider: Collider): boolean;
+        intersectsPoint(point: Vector3): boolean;
+        intersects(boundingInfo: BoundingInfo, precise: boolean): boolean;
+    }
+}
+
+declare module BABYLON {
+    class BoundingSphere {
+        minimum: Vector3;
+        maximum: Vector3;
+        center: Vector3;
+        radius: number;
+        centerWorld: Vector3;
+        radiusWorld: number;
+        private _tempRadiusVector;
+        constructor(minimum: Vector3, maximum: Vector3);
+        _update(world: Matrix): void;
+        isInFrustum(frustumPlanes: Plane[]): boolean;
+        intersectsPoint(point: Vector3): boolean;
+        static Intersects(sphere0: BoundingSphere, sphere1: BoundingSphere): boolean;
+    }
+}
+
+declare module BABYLON {
+    class Ray {
+        origin: Vector3;
+        direction: Vector3;
+        length: number;
+        private _edge1;
+        private _edge2;
+        private _pvec;
+        private _tvec;
+        private _qvec;
+        constructor(origin: Vector3, direction: Vector3, length?: number);
+        intersectsBoxMinMax(minimum: Vector3, maximum: Vector3): boolean;
+        intersectsBox(box: BoundingBox): boolean;
+        intersectsSphere(sphere: any): boolean;
+        intersectsTriangle(vertex0: Vector3, vertex1: Vector3, vertex2: Vector3): IntersectionInfo;
+        static CreateNew(x: number, y: number, viewportWidth: number, viewportHeight: number, world: Matrix, view: Matrix, projection: Matrix): Ray;
+        /**
+        * Function will create a new transformed ray starting from origin and ending at the end point. Ray's length will be set, and ray will be
+        * transformed to the given world matrix.
+        * @param origin The origin point
+        * @param end The end point
+        * @param world a matrix to transform the ray to. Default is the identity matrix.
+        */
+        static CreateNewFromTo(origin: Vector3, end: Vector3, world?: Matrix): Ray;
+        static Transform(ray: Ray, matrix: Matrix): Ray;
     }
 }
 
@@ -7614,13 +7618,13 @@ declare module BABYLON {
 declare module BABYLON {
     class ArcRotateCameraPointersInput implements ICameraInput<ArcRotateCamera> {
         camera: ArcRotateCamera;
-        private _isRightClick;
-        private _isCtrlPushed;
-        pinchInwards: boolean;
         angularSensibilityX: number;
         angularSensibilityY: number;
         pinchPrecision: number;
         panningSensibility: number;
+        private _isRightClick;
+        private _isCtrlPushed;
+        pinchInwards: boolean;
         private _onKeyDown;
         private _onKeyUp;
         private _onPointerDown;
@@ -8210,11 +8214,11 @@ declare module BABYLON {
         /**
         * Creates a video texture.
         * Sample : https://doc.babylonjs.com/tutorials/01._Advanced_Texturing
-        * @param urlsOrVideo can be used to provide an array of urls or an already setup HTML video element.
-        * @param scene is obviously the current scene.
-        * @param generateMipMaps can be used to turn on mipmaps (Can be expensive for videoTextures because they are often updated).
-        * @param invertY is false by default but can be used to invert video on Y axis
-        * @param samplingMode controls the sampling method and is set to TRILINEAR_SAMPLINGMODE by default
+        * @param {Array} urlsOrVideo can be used to provide an array of urls or an already setup HTML video element.
+        * @param {BABYLON.Scene} scene is obviously the current scene.
+        * @param {boolean} generateMipMaps can be used to turn on mipmaps (Can be expensive for videoTextures because they are often updated).
+        * @param {boolean} invertY is false by default but can be used to invert video on Y axis
+        * @param {number} samplingMode controls the sampling method and is set to TRILINEAR_SAMPLINGMODE by default
         */
         constructor(name: string, urlsOrVideo: string[] | HTMLVideoElement, scene: Scene, generateMipMaps?: boolean, invertY?: boolean, samplingMode?: number);
         update(): boolean;

파일 크기가 너무 크기때문에 변경 상태를 표시하지 않습니다.
+ 28 - 28
dist/preview release/babylon.js


파일 크기가 너무 크기때문에 변경 상태를 표시하지 않습니다.
+ 129 - 77
dist/preview release/babylon.max.js


파일 크기가 너무 크기때문에 변경 상태를 표시하지 않습니다.
+ 28 - 28
dist/preview release/babylon.noworker.js


+ 13 - 0
src/Bones/babylon.skeleton.js

@@ -47,6 +47,19 @@ var BABYLON;
             }
             return ret;
         };
+        /**
+        * Get bone's index searching by name
+        * @param {string} name is bone's name to search for
+        * @return {number} Indice of the bone. Returns -1 if not found
+        */
+        Skeleton.prototype.getBoneIndexByName = function (name) {
+            for (var boneIndex = 0, cache = this.bones.length; boneIndex < cache; boneIndex++) {
+                if (this.bones[boneIndex].name === name) {
+                    return boneIndex;
+                }
+            }
+            return -1;
+        };
         Skeleton.prototype.createAnimationRange = function (name, from, to) {
             // check name not already in use
             if (!this._ranges[name]) {

+ 15 - 14
src/Bones/babylon.skeleton.ts

@@ -37,6 +37,7 @@
         }
 
         // Methods
+
         /**
          * @param {boolean} fullDetails - support for multiple levels of logging within scene loading
          */
@@ -57,6 +58,20 @@
             }
             return ret;
         } 
+
+        /**
+        * Get bone's index searching by name
+        * @param {string} name is bone's name to search for
+        * @return {number} Indice of the bone. Returns -1 if not found
+        */
+        public getBoneIndexByName(name: string): number {
+            for (var boneIndex = 0, cache = this.bones.length; boneIndex < cache; boneIndex++) {
+                if (this.bones[boneIndex].name === name) {
+                    return boneIndex;
+                }
+            }
+            return -1;
+        }
         
         public createAnimationRange(name: string, from: number, to: number): void {
             // check name not already in use
@@ -96,20 +111,6 @@
             }
             return animationRanges;
         }
-        
-        /**
-        * get a index on skeleton by name
-        * @param {string} the bone's name
-        * @return {number} the indice of bone on
-        */
-        public getIndexOnSkeletonByName(name: string): number {
-                for (var boneIndex = 0, cache = this.bones.length; boneIndex < cache; boneIndex++) {
-                    if (this.bones[boneIndex].name === name) {
-                        return boneIndex;
-                    }
-                }
-                return null;
-        }
 
         /** 
          *  note: This is not for a complete retargeting, only between very similar skeleton's with only possible bone length differences

+ 20 - 14
src/Cameras/Inputs/babylon.arcrotatecamera.input.keyboard.js

@@ -63,22 +63,28 @@ var BABYLON;
                 { name: "keyup", handler: this._onKeyUp },
                 { name: "blur", handler: this._onLostFocus }
             ]);
+            this._keys = [];
+            this._onKeyDown = null;
+            this._onKeyUp = null;
+            this._onLostFocus = null;
         };
         ArcRotateCameraKeyboardMoveInput.prototype.checkInputs = function () {
-            var camera = this.camera;
-            for (var index = 0; index < this._keys.length; index++) {
-                var keyCode = this._keys[index];
-                if (this.keysLeft.indexOf(keyCode) !== -1) {
-                    camera.inertialAlphaOffset -= 0.01;
-                }
-                else if (this.keysUp.indexOf(keyCode) !== -1) {
-                    camera.inertialBetaOffset -= 0.01;
-                }
-                else if (this.keysRight.indexOf(keyCode) !== -1) {
-                    camera.inertialAlphaOffset += 0.01;
-                }
-                else if (this.keysDown.indexOf(keyCode) !== -1) {
-                    camera.inertialBetaOffset += 0.01;
+            if (this._onKeyDown) {
+                var camera = this.camera;
+                for (var index = 0; index < this._keys.length; index++) {
+                    var keyCode = this._keys[index];
+                    if (this.keysLeft.indexOf(keyCode) !== -1) {
+                        camera.inertialAlphaOffset -= 0.01;
+                    }
+                    else if (this.keysUp.indexOf(keyCode) !== -1) {
+                        camera.inertialBetaOffset -= 0.01;
+                    }
+                    else if (this.keysRight.indexOf(keyCode) !== -1) {
+                        camera.inertialAlphaOffset += 0.01;
+                    }
+                    else if (this.keysDown.indexOf(keyCode) !== -1) {
+                        camera.inertialBetaOffset += 0.01;
+                    }
                 }
             }
         };

+ 2 - 1
src/Cameras/Inputs/babylon.arcrotatecamera.input.mousewheel.js

@@ -23,7 +23,7 @@ var BABYLON;
                 if (delta)
                     _this.camera.inertialRadiusOffset += delta;
                 if (event.preventDefault) {
-                    if (!_this.camera._noPreventDefault) {
+                    if (!noPreventDefault) {
                         event.preventDefault();
                     }
                 }
@@ -35,6 +35,7 @@ var BABYLON;
             if (this._wheel && element) {
                 element.removeEventListener('mousewheel', this._wheel);
                 element.removeEventListener('DOMMouseScroll', this._wheel);
+                this._wheel = null;
             }
         };
         ArcRotateCameraMouseWheelInput.prototype.getTypeName = function () {

+ 17 - 4
src/Cameras/Inputs/babylon.arcrotatecamera.input.pointers.js

@@ -9,13 +9,13 @@ var BABYLON;
     var eventPrefix = BABYLON.Tools.GetPointerPrefix();
     var ArcRotateCameraPointersInput = (function () {
         function ArcRotateCameraPointersInput() {
-            this._isRightClick = false;
-            this._isCtrlPushed = false;
-            this.pinchInwards = true;
             this.angularSensibilityX = 1000.0;
             this.angularSensibilityY = 1000.0;
             this.pinchPrecision = 6.0;
             this.panningSensibility = 50.0;
+            this._isRightClick = false;
+            this._isCtrlPushed = false;
+            this.pinchInwards = true;
         }
         ArcRotateCameraPointersInput.prototype.attachControl = function (element, noPreventDefault) {
             var _this = this;
@@ -149,7 +149,6 @@ var BABYLON;
             ]);
         };
         ArcRotateCameraPointersInput.prototype.detachControl = function (element) {
-            this._MSGestureHandler = null;
             if (element && this._onPointerDown) {
                 element.removeEventListener("contextmenu", this._onContextMenu);
                 element.removeEventListener(eventPrefix + "down", this._onPointerDown);
@@ -159,6 +158,20 @@ var BABYLON;
                 element.removeEventListener("mousemove", this._onMouseMove);
                 element.removeEventListener("MSPointerDown", this._onGestureStart);
                 element.removeEventListener("MSGestureChange", this._onGesture);
+                this._isRightClick = false;
+                this._isCtrlPushed = false;
+                this.pinchInwards = true;
+                this._onKeyDown = null;
+                this._onKeyUp = null;
+                this._onPointerDown = null;
+                this._onPointerUp = null;
+                this._onPointerMove = null;
+                this._onMouseMove = null;
+                this._onGestureStart = null;
+                this._onGesture = null;
+                this._MSGestureHandler = null;
+                this._onLostFocus = null;
+                this._onContextMenu = null;
             }
             BABYLON.Tools.UnregisterTopRootEvents([
                 { name: "blur", handler: this._onLostFocus }

+ 2 - 0
src/Cameras/Inputs/babylon.freecamera.input.deviceorientation.js

@@ -43,6 +43,8 @@ var BABYLON;
             this._orientationBeta = 0;
             this._initialOrientationGamma = 0;
             this._initialOrientationBeta = 0;
+            this._offsetX = null;
+            this._offsetY = null;
         };
         FreeCameraDeviceOrientationInput.prototype.checkInputs = function () {
             if (!this._offsetX) {

+ 31 - 24
src/Cameras/Inputs/babylon.freecamera.input.keyboard.js

@@ -53,33 +53,40 @@ var BABYLON;
             }
         };
         FreeCameraKeyboardMoveInput.prototype.detachControl = function (element) {
-            BABYLON.Tools.UnregisterTopRootEvents([
-                { name: "keydown", handler: this._onKeyDown },
-                { name: "keyup", handler: this._onKeyUp },
-                { name: "blur", handler: this._onLostFocus }
-            ]);
+            if (this._onKeyDown) {
+                BABYLON.Tools.UnregisterTopRootEvents([
+                    { name: "keydown", handler: this._onKeyDown },
+                    { name: "keyup", handler: this._onKeyUp },
+                    { name: "blur", handler: this._onLostFocus }
+                ]);
+                this._keys = [];
+                this._onKeyDown = null;
+                this._onKeyUp = null;
+            }
         };
         FreeCameraKeyboardMoveInput.prototype.checkInputs = function () {
-            var camera = this.camera;
-            // Keyboard
-            for (var index = 0; index < this._keys.length; index++) {
-                var keyCode = this._keys[index];
-                var speed = camera._computeLocalCameraSpeed();
-                if (this.keysLeft.indexOf(keyCode) !== -1) {
-                    camera._localDirection.copyFromFloats(-speed, 0, 0);
-                }
-                else if (this.keysUp.indexOf(keyCode) !== -1) {
-                    camera._localDirection.copyFromFloats(0, 0, speed);
-                }
-                else if (this.keysRight.indexOf(keyCode) !== -1) {
-                    camera._localDirection.copyFromFloats(speed, 0, 0);
-                }
-                else if (this.keysDown.indexOf(keyCode) !== -1) {
-                    camera._localDirection.copyFromFloats(0, 0, -speed);
+            if (this._onKeyDown) {
+                var camera = this.camera;
+                // Keyboard
+                for (var index = 0; index < this._keys.length; index++) {
+                    var keyCode = this._keys[index];
+                    var speed = camera._computeLocalCameraSpeed();
+                    if (this.keysLeft.indexOf(keyCode) !== -1) {
+                        camera._localDirection.copyFromFloats(-speed, 0, 0);
+                    }
+                    else if (this.keysUp.indexOf(keyCode) !== -1) {
+                        camera._localDirection.copyFromFloats(0, 0, speed);
+                    }
+                    else if (this.keysRight.indexOf(keyCode) !== -1) {
+                        camera._localDirection.copyFromFloats(speed, 0, 0);
+                    }
+                    else if (this.keysDown.indexOf(keyCode) !== -1) {
+                        camera._localDirection.copyFromFloats(0, 0, -speed);
+                    }
+                    camera.getViewMatrix().invertToRef(camera._cameraTransformMatrix);
+                    BABYLON.Vector3.TransformNormalToRef(camera._localDirection, camera._cameraTransformMatrix, camera._transformedDirection);
+                    camera.cameraDirection.addInPlace(camera._transformedDirection);
                 }
-                camera.getViewMatrix().invertToRef(camera._cameraTransformMatrix);
-                BABYLON.Vector3.TransformNormalToRef(camera._localDirection, camera._cameraTransformMatrix, camera._transformedDirection);
-                camera.cameraDirection.addInPlace(camera._transformedDirection);
             }
         };
         FreeCameraKeyboardMoveInput.prototype.getTypeName = function () {

+ 4 - 0
src/Cameras/Inputs/babylon.freecamera.input.mouse.js

@@ -73,6 +73,10 @@ var BABYLON;
                 element.removeEventListener("mouseup", this._onMouseUp);
                 element.removeEventListener("mouseout", this._onMouseOut);
                 element.removeEventListener("mousemove", this._onMouseMove);
+                this._onMouseDown = null;
+                this._onMouseUp = null;
+                this._onMouseOut = null;
+                this._onMouseMove = null;
             }
         };
         FreeCameraMouseInput.prototype.getTypeName = function () {

+ 15 - 5
src/Cameras/Inputs/babylon.freecamera.input.touch.js

@@ -83,11 +83,21 @@ var BABYLON;
             element.addEventListener("pointermove", this._onPointerMove);
         };
         FreeCameraTouchInput.prototype.detachControl = function (element) {
-            element.removeEventListener("blur", this._onLostFocus);
-            element.removeEventListener("pointerdown", this._onPointerDown);
-            element.removeEventListener("pointerup", this._onPointerUp);
-            element.removeEventListener("pointerout", this._onPointerUp);
-            element.removeEventListener("pointermove", this._onPointerMove);
+            if (this._onPointerDown && element) {
+                element.removeEventListener("blur", this._onLostFocus);
+                element.removeEventListener("pointerdown", this._onPointerDown);
+                element.removeEventListener("pointerup", this._onPointerUp);
+                element.removeEventListener("pointerout", this._onPointerUp);
+                element.removeEventListener("pointermove", this._onPointerMove);
+                this._onPointerDown = null;
+                this._onPointerUp = null;
+                this._onPointerMove = null;
+                this._onLostFocus = null;
+                this._pointerPressed = [];
+                this._offsetX = null;
+                this._offsetY = null;
+                this._pointerCount = 0;
+            }
         };
         FreeCameraTouchInput.prototype.checkInputs = function () {
             if (this._offsetX) {

+ 1 - 10
src/Cameras/babylon.arcRotateCamera.js

@@ -258,11 +258,6 @@ var BABYLON;
         ArcRotateCamera.prototype.attachControl = function (element, noPreventDefault, useCtrlForPanning) {
             var _this = this;
             if (useCtrlForPanning === void 0) { useCtrlForPanning = true; }
-            if (this._attachedElement) {
-                return;
-            }
-            this._attachedElement = element;
-            this._noPreventDefault = BABYLON.Camera.ForceAttachControlToAlwaysPreventDefault ? false : noPreventDefault;
             this._useCtrlForPanning = useCtrlForPanning;
             this.inputs.attachElement(element, noPreventDefault);
             this._reset = function () {
@@ -272,11 +267,7 @@ var BABYLON;
             };
         };
         ArcRotateCamera.prototype.detachControl = function (element) {
-            if (this._attachedElement !== element) {
-                return;
-            }
-            this.inputs.detachElement(this._attachedElement);
-            this._attachedElement = null;
+            this.inputs.detachElement(element);
             if (this._reset) {
                 this._reset();
             }

+ 35 - 36
src/Cameras/babylon.arcRotateCamera.ts

@@ -38,7 +38,7 @@
 
         @serialize()
         public upperRadiusLimit = null;
-        
+
         @serialize()
         public inertialPanningX: number = 0;
 
@@ -51,107 +51,107 @@
             if (pointers)
                 return pointers.angularSensibilityX;
         }
-        
+
         public set angularSensibilityX(value) {
             var pointers = <ArcRotateCameraPointersInput>this.inputs.attached["pointers"];
-            if (pointers){
+            if (pointers) {
                 pointers.angularSensibilityX = value;
             }
         }
-        
+
         public get angularSensibilityY() {
             var pointers = <ArcRotateCameraPointersInput>this.inputs.attached["pointers"];
             if (pointers)
                 return pointers.angularSensibilityY;
         }
-        
+
         public set angularSensibilityY(value) {
             var pointers = <ArcRotateCameraPointersInput>this.inputs.attached["pointers"];
-            if (pointers){
+            if (pointers) {
                 pointers.angularSensibilityY = value;
             }
         }
-        
+
         public get pinchPrecision() {
             var pointers = <ArcRotateCameraPointersInput>this.inputs.attached["pointers"];
             if (pointers)
                 return pointers.pinchPrecision;
         }
-        
+
         public set pinchPrecision(value) {
             var pointers = <ArcRotateCameraPointersInput>this.inputs.attached["pointers"];
-            if (pointers){
+            if (pointers) {
                 pointers.pinchPrecision = value;
             }
         }
-        
+
         public get panningSensibility() {
             var pointers = <ArcRotateCameraPointersInput>this.inputs.attached["pointers"];
             if (pointers)
                 return pointers.panningSensibility;
         }
-        
+
         public set panningSensibility(value) {
             var pointers = <ArcRotateCameraPointersInput>this.inputs.attached["pointers"];
-            if (pointers){
+            if (pointers) {
                 pointers.panningSensibility = value;
             }
         }
-        
+
         public get keysUp() {
             var keyboard = <ArcRotateCameraKeyboardMoveInput>this.inputs.attached["keyboard"];
             if (keyboard)
                 return keyboard.keysUp;
         }
-        
+
         public set keysUp(value) {
             var keyboard = <ArcRotateCameraKeyboardMoveInput>this.inputs.attached["keyboard"];
             if (keyboard)
                 keyboard.keysUp = value;
         }
-        
+
         public get keysDown() {
             var keyboard = <ArcRotateCameraKeyboardMoveInput>this.inputs.attached["keyboard"];
             if (keyboard)
                 return keyboard.keysDown;
         }
-        
+
         public set keysDown(value) {
             var keyboard = <ArcRotateCameraKeyboardMoveInput>this.inputs.attached["keyboard"];
             if (keyboard)
                 keyboard.keysDown = value;
         }
-        
+
         public get keysLeft() {
             var keyboard = <ArcRotateCameraKeyboardMoveInput>this.inputs.attached["keyboard"];
             if (keyboard)
                 return keyboard.keysLeft;
         }
-        
+
         public set keysLeft(value) {
             var keyboard = <ArcRotateCameraKeyboardMoveInput>this.inputs.attached["keyboard"];
             if (keyboard)
                 keyboard.keysLeft = value;
         }
-        
+
         public get keysRight() {
             var keyboard = <ArcRotateCameraKeyboardMoveInput>this.inputs.attached["keyboard"];
             if (keyboard)
                 return keyboard.keysRight;
         }
-        
+
         public set keysRight(value) {
             var keyboard = <ArcRotateCameraKeyboardMoveInput>this.inputs.attached["keyboard"];
             if (keyboard)
                 keyboard.keysRight = value;
         }
-        
+
         public get wheelPrecision() {
             var mousewheel = <ArcRotateCameraMouseWheelInput>this.inputs.attached["mousewheel"];
             if (mousewheel)
                 return mousewheel.wheelPrecision;
         }
-        
+
         public set wheelPrecision(value) {
             var mousewheel = <ArcRotateCameraMouseWheelInput>this.inputs.attached["mousewheel"];
             if (mousewheel)
@@ -164,14 +164,14 @@
         public zoomOnFactor = 1;
 
         public targetScreenOffset = Vector2.Zero();
-        
+
         @serialize()
         public allowUpsideDown = true;
 
         public _viewMatrix = new Matrix();
-        public _useCtrlForPanning : boolean;
-        public inputs : ArcRotateCameraInputsManager;
-        
+        public _useCtrlForPanning: boolean;
+        public inputs: ArcRotateCameraInputsManager;
+
         public _reset: () => void;
         
         // Panning
@@ -192,7 +192,7 @@
         private _previousRadius: number;
         //due to async collision inspection
         private _collisionTriggered: boolean;
-        
+
         constructor(name: string, alpha: number, beta: number, radius: number, target: Vector3, scene: Scene) {
             super(name, Vector3.Zero(), scene);
 
@@ -258,18 +258,17 @@
             this._useCtrlForPanning = useCtrlForPanning;
 
             this.inputs.attachElement(element, noPreventDefault);
-            
 
-                this._reset = () => {
-                    this.inertialAlphaOffset = 0;
-                    this.inertialBetaOffset = 0;
-                    this.inertialRadiusOffset = 0;
-                };
+            this._reset = () => {
+                this.inertialAlphaOffset = 0;
+                this.inertialBetaOffset = 0;
+                this.inertialRadiusOffset = 0;
+            };
         }
 
         public detachControl(element: HTMLElement): void {
             this.inputs.detachElement(element);
-            
+
             if (this._reset) {
                 this._reset();
             }
@@ -280,7 +279,7 @@
             if (this._collisionTriggered) {
                 return;
             }
-            
+
             this.inputs.checkInputs();            
 			
             // Inertia
@@ -553,7 +552,7 @@
             this.inputs.clear();
             super.dispose();
         }
-        
+
         public getTypeName(): string {
             return "ArcRotateCamera";
         }

+ 15 - 1
src/Cameras/babylon.cameraInputsManager.js

@@ -30,6 +30,7 @@ var BABYLON;
                 if (input === inputToRemove) {
                     input.detachControl(this.attachedElement);
                     delete this.attached[cam];
+                    this.rebuildInputCheck();
                 }
             }
         };
@@ -39,6 +40,7 @@ var BABYLON;
                 if (input.getTypeName() === inputType) {
                     input.detachControl(this.attachedElement);
                     delete this.attached[cam];
+                    this.rebuildInputCheck();
                 }
             }
         };
@@ -49,20 +51,32 @@ var BABYLON;
                 fn();
             };
         };
+        CameraInputsManager.prototype.attachInput = function (input) {
+            input.attachControl(this.attachedElement, this.noPreventDefault);
+        };
         CameraInputsManager.prototype.attachElement = function (element, noPreventDefault) {
+            if (this.attachedElement) {
+                return;
+            }
+            noPreventDefault = BABYLON.Camera.ForceAttachControlToAlwaysPreventDefault ? false : noPreventDefault;
             this.attachedElement = element;
+            this.noPreventDefault = noPreventDefault;
             for (var cam in this.attached) {
                 var input = this.attached[cam];
                 this.attached[cam].attachControl(element, noPreventDefault);
             }
         };
         CameraInputsManager.prototype.detachElement = function (element) {
+            if (this.attachedElement !== element) {
+                return;
+            }
             for (var cam in this.attached) {
                 var input = this.attached[cam];
                 this.attached[cam].detachControl(element);
             }
+            this.attachedElement = null;
         };
-        CameraInputsManager.prototype.rebuildInputCheck = function (element) {
+        CameraInputsManager.prototype.rebuildInputCheck = function () {
             this.checkInputs = function () { };
             for (var cam in this.attached) {
                 var input = this.attached[cam];

+ 11 - 10
src/Cameras/babylon.cameraInputsManager.ts

@@ -2,11 +2,11 @@ module BABYLON {
     export var CameraInputTypes = {};
 
     export interface ICameraInput<TCamera extends BABYLON.Camera> {
-        camera: TCamera;        
+        camera: TCamera;
         getTypeName(): string;
         getSimpleName(): string;
         attachControl: (element: HTMLElement, noPreventDefault?: boolean) => void;
-        detachControl: (element: HTMLElement) => void;        
+        detachControl: (element: HTMLElement) => void;
         checkInputs?: () => void;
     }
 
@@ -36,7 +36,7 @@ module BABYLON {
             }
 
             this.attached[type] = input;
-            
+
             input.camera = this.camera;
             
             //for checkInputs, we are dynamically creating a function
@@ -44,8 +44,8 @@ module BABYLON {
             if (input.checkInputs) {
                 this.checkInputs = this._addCheckInputs(input.checkInputs.bind(input));
             }
-            
-            if (this.attachedElement){
+
+            if (this.attachedElement) {
                 input.attachControl(this.attachedElement);
             }
         }
@@ -80,18 +80,19 @@ module BABYLON {
             }
         }
 
-        public attachInput(input : ICameraInput<TCamera>){
+        public attachInput(input: ICameraInput<TCamera>) {
             input.attachControl(this.attachedElement, this.noPreventDefault);
         }
-        
+
         public attachElement(element: HTMLElement, noPreventDefault?: boolean) {
             if (this.attachedElement) {
                 return;
             }
+
             noPreventDefault = Camera.ForceAttachControlToAlwaysPreventDefault ? false : noPreventDefault;
             this.attachedElement = element;
             this.noPreventDefault = noPreventDefault;
-            
+
             for (var cam in this.attached) {
                 var input = this.attached[cam];
                 this.attached[cam].attachControl(element, noPreventDefault);
@@ -102,12 +103,12 @@ module BABYLON {
             if (this.attachedElement !== element) {
                 return;
             }
-            
+
             for (var cam in this.attached) {
                 var input = this.attached[cam];
                 this.attached[cam].detachControl(element);
             }
-            
+
             this.attachedElement = null;
         }
 

+ 1 - 11
src/Cameras/babylon.freeCamera.js

@@ -118,20 +118,10 @@ var BABYLON;
         });
         // Controls
         FreeCamera.prototype.attachControl = function (element, noPreventDefault) {
-            if (this._attachedElement) {
-                return;
-            }
-            this._noPreventDefault = noPreventDefault;
-            this._attachedElement = element;
-            noPreventDefault = BABYLON.Camera.ForceAttachControlToAlwaysPreventDefault ? false : noPreventDefault;
             this.inputs.attachElement(element, noPreventDefault);
         };
         FreeCamera.prototype.detachControl = function (element) {
-            if (this._attachedElement !== element) {
-                return;
-            }
-            this.inputs.detachElement(this._attachedElement);
-            this._attachedElement = null;
+            this.inputs.detachElement(element);
             this.cameraDirection = new BABYLON.Vector3(0, 0, 0);
             this.cameraRotation = new BABYLON.Vector2(0, 0);
         };

+ 0 - 2
src/Cameras/babylon.freeCamera.ts

@@ -81,8 +81,6 @@
         private _oldPosition = Vector3.Zero();
         private _diffPosition = Vector3.Zero();
         private _newPosition = Vector3.Zero();
-        //public _attachedElement: HTMLElement;
-        //public _noPreventDefault: boolean;
         
         public _localDirection: Vector3;
         public _transformedDirection: Vector3;        

+ 1 - 0
src/Materials/Textures/babylon.renderTargetTexture.js

@@ -145,6 +145,7 @@ var BABYLON;
                         this.resetRefreshCounter();
                         continue;
                     }
+                    mesh._preActivate();
                     if (mesh.isEnabled() && mesh.isVisible && mesh.subMeshes && ((mesh.layerMask & scene.activeCamera.layerMask) !== 0)) {
                         mesh._activate(scene.getRenderId());
                         for (var subIndex = 0; subIndex < mesh.subMeshes.length; subIndex++) {

+ 2 - 0
src/Materials/Textures/babylon.renderTargetTexture.ts

@@ -160,6 +160,8 @@
                         continue;
                     }
 
+                    mesh._preActivate();
+
                     if (mesh.isEnabled() && mesh.isVisible && mesh.subMeshes && ((mesh.layerMask & scene.activeCamera.layerMask) !== 0)) {
                         mesh._activate(scene.getRenderId());
 

+ 5 - 5
src/Materials/Textures/babylon.videoTexture.js

@@ -10,11 +10,11 @@ var BABYLON;
         /**
         * Creates a video texture.
         * Sample : https://doc.babylonjs.com/tutorials/01._Advanced_Texturing
-        * @param urlsOrVideo can be used to provide an array of urls or an already setup HTML video element.
-        * @param scene is obviously the current scene.
-        * @param generateMipMaps can be used to turn on mipmaps (Can be expensive for videoTextures because they are often updated).
-        * @param invertY is false by default but can be used to invert video on Y axis
-        * @param samplingMode controls the sampling method and is set to TRILINEAR_SAMPLINGMODE by default
+        * @param {Array} urlsOrVideo can be used to provide an array of urls or an already setup HTML video element.
+        * @param {BABYLON.Scene} scene is obviously the current scene.
+        * @param {boolean} generateMipMaps can be used to turn on mipmaps (Can be expensive for videoTextures because they are often updated).
+        * @param {boolean} invertY is false by default but can be used to invert video on Y axis
+        * @param {number} samplingMode controls the sampling method and is set to TRILINEAR_SAMPLINGMODE by default
         */
         function VideoTexture(name, urlsOrVideo, scene, generateMipMaps, invertY, samplingMode) {
             var _this = this;

+ 5 - 5
src/Materials/Textures/babylon.videoTexture.ts

@@ -8,11 +8,11 @@
         /**
         * Creates a video texture.  
         * Sample : https://doc.babylonjs.com/tutorials/01._Advanced_Texturing  
-        * @param urlsOrVideo can be used to provide an array of urls or an already setup HTML video element.
-        * @param scene is obviously the current scene.   
-        * @param generateMipMaps can be used to turn on mipmaps (Can be expensive for videoTextures because they are often updated).
-        * @param invertY is false by default but can be used to invert video on Y axis
-        * @param samplingMode controls the sampling method and is set to TRILINEAR_SAMPLINGMODE by default
+        * @param {Array} urlsOrVideo can be used to provide an array of urls or an already setup HTML video element.
+        * @param {BABYLON.Scene} scene is obviously the current scene.   
+        * @param {boolean} generateMipMaps can be used to turn on mipmaps (Can be expensive for videoTextures because they are often updated).
+        * @param {boolean} invertY is false by default but can be used to invert video on Y axis
+        * @param {number} samplingMode controls the sampling method and is set to TRILINEAR_SAMPLINGMODE by default
         */
         constructor(name: string, urlsOrVideo: string[] | HTMLVideoElement, scene: Scene, generateMipMaps = false, invertY = false, samplingMode: number = Texture.TRILINEAR_SAMPLINGMODE) {
             super(null, scene, !generateMipMaps, invertY);

+ 1 - 1
src/Mesh/babylon.mesh.js

@@ -219,7 +219,7 @@ var BABYLON;
             if (!this._LODLevels || this._LODLevels.length === 0) {
                 return this;
             }
-            var distanceToCamera = (boundingSphere ? boundingSphere : this.getBoundingInfo().boundingSphere).centerWorld.subtract(camera.position).length();
+            var distanceToCamera = (boundingSphere ? boundingSphere : this.getBoundingInfo().boundingSphere).centerWorld.subtract(camera.globalPosition).length();
             if (this._LODLevels[this._LODLevels.length - 1].distance > distanceToCamera) {
                 if (this.onLODLevelSelection) {
                     this.onLODLevelSelection(distanceToCamera, this, this._LODLevels[this._LODLevels.length - 1].mesh);

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

@@ -231,7 +231,7 @@
                 return this;
             }
 
-            var distanceToCamera = (boundingSphere ? boundingSphere : this.getBoundingInfo().boundingSphere).centerWorld.subtract(camera.position).length();
+            var distanceToCamera = (boundingSphere ? boundingSphere : this.getBoundingInfo().boundingSphere).centerWorld.subtract(camera.globalPosition).length();
 
             if (this._LODLevels[this._LODLevels.length - 1].distance > distanceToCamera) {
                 if (this.onLODLevelSelection) {