浏览代码

DragControls: Fully migrate to pointer events. (#21958)

Michael Herzog 4 年之前
父节点
当前提交
25da165501
共有 2 个文件被更改,包括 95 次插入327 次删除
  1. 49 176
      examples/js/controls/DragControls.js
  2. 46 151
      examples/jsm/controls/DragControls.js

+ 49 - 176
examples/js/controls/DragControls.js

@@ -4,7 +4,7 @@
 
 	const _raycaster = new THREE.Raycaster();
 
-	const _mouse = new THREE.Vector2();
+	const _pointer = new THREE.Vector2();
 
 	const _offset = new THREE.Vector3();
 
@@ -35,16 +35,6 @@
 
 				_domElement.addEventListener( 'pointerleave', onPointerCancel );
 
-				_domElement.addEventListener( 'touchmove', onTouchMove, {
-					passive: false
-				} );
-
-				_domElement.addEventListener( 'touchstart', onTouchStart, {
-					passive: false
-				} );
-
-				_domElement.addEventListener( 'touchend', onTouchEnd );
-
 			}
 
 			function deactivate() {
@@ -57,12 +47,6 @@
 
 				_domElement.removeEventListener( 'pointerleave', onPointerCancel );
 
-				_domElement.removeEventListener( 'touchmove', onTouchMove );
-
-				_domElement.removeEventListener( 'touchstart', onTouchStart );
-
-				_domElement.removeEventListener( 'touchend', onTouchEnd );
-
 				_domElement.style.cursor = '';
 
 			}
@@ -81,26 +65,9 @@
 
 			function onPointerMove( event ) {
 
-				switch ( event.pointerType ) {
-
-					case 'mouse':
-					case 'pen':
-						onMouseMove( event );
-						break;
-        // TODO touch
-
-				}
-
-			}
-
-			function onMouseMove( event ) {
-
-				const rect = _domElement.getBoundingClientRect();
-
-				_mouse.x = ( event.clientX - rect.left ) / rect.width * 2 - 1;
-				_mouse.y = - ( ( event.clientY - rect.top ) / rect.height ) * 2 + 1;
+				updatePointer( event );
 
-				_raycaster.setFromCamera( _mouse, _camera );
+				_raycaster.setFromCamera( _pointer, _camera );
 
 				if ( _selected && scope.enabled ) {
 
@@ -116,78 +83,71 @@
 					} );
 					return;
 
-				}
+				} // hover support
 
-				_intersections.length = 0;
 
-				_raycaster.setFromCamera( _mouse, _camera );
+				if ( event.pointerType === 'mouse' || event.pointerType === 'pen' ) {
 
-				_raycaster.intersectObjects( _objects, true, _intersections );
+					_intersections.length = 0;
 
-				if ( _intersections.length > 0 ) {
+					_raycaster.setFromCamera( _pointer, _camera );
 
-					const object = _intersections[ 0 ].object;
+					_raycaster.intersectObjects( _objects, true, _intersections );
 
-					_plane.setFromNormalAndCoplanarPoint( _camera.getWorldDirection( _plane.normal ), _worldPosition.setFromMatrixPosition( object.matrixWorld ) );
+					if ( _intersections.length > 0 ) {
 
-					if ( _hovered !== object && _hovered !== null ) {
+						const object = _intersections[ 0 ].object;
 
-						scope.dispatchEvent( {
-							type: 'hoveroff',
-							object: _hovered
-						} );
-						_domElement.style.cursor = 'auto';
-						_hovered = null;
+						_plane.setFromNormalAndCoplanarPoint( _camera.getWorldDirection( _plane.normal ), _worldPosition.setFromMatrixPosition( object.matrixWorld ) );
 
-					}
+						if ( _hovered !== object && _hovered !== null ) {
 
-					if ( _hovered !== object ) {
+							scope.dispatchEvent( {
+								type: 'hoveroff',
+								object: _hovered
+							} );
+							_domElement.style.cursor = 'auto';
+							_hovered = null;
 
-						scope.dispatchEvent( {
-							type: 'hoveron',
-							object: object
-						} );
-						_domElement.style.cursor = 'pointer';
-						_hovered = object;
+						}
 
-					}
-
-				} else {
-
-					if ( _hovered !== null ) {
+						if ( _hovered !== object ) {
 
-						scope.dispatchEvent( {
-							type: 'hoveroff',
-							object: _hovered
-						} );
-						_domElement.style.cursor = 'auto';
-						_hovered = null;
+							scope.dispatchEvent( {
+								type: 'hoveron',
+								object: object
+							} );
+							_domElement.style.cursor = 'pointer';
+							_hovered = object;
 
-					}
+						}
 
-				}
+					} else {
 
-			}
+						if ( _hovered !== null ) {
 
-			function onPointerDown( event ) {
+							scope.dispatchEvent( {
+								type: 'hoveroff',
+								object: _hovered
+							} );
+							_domElement.style.cursor = 'auto';
+							_hovered = null;
 
-				switch ( event.pointerType ) {
+						}
 
-					case 'mouse':
-					case 'pen':
-						onMouseDown();
-						break;
-        // TODO touch
+					}
 
 				}
 
 			}
 
-			function onMouseDown() {
+			function onPointerDown() {
 
+				_domElement.style.touchAction = 'none';
+				updatePointer( event );
 				_intersections.length = 0;
 
-				_raycaster.setFromCamera( _mouse, _camera );
+				_raycaster.setFromCamera( _pointer, _camera );
 
 				_raycaster.intersectObjects( _objects, true, _intersections );
 
@@ -195,6 +155,8 @@
 
 					_selected = scope.transformGroup === true ? _objects[ 0 ] : _intersections[ 0 ].object;
 
+					_plane.setFromNormalAndCoplanarPoint( _camera.getWorldDirection( _plane.normal ), _worldPosition.setFromMatrixPosition( _selected.matrixWorld ) );
+
 					if ( _raycaster.ray.intersectPlane( _plane, _intersection ) ) {
 
 						_inverseMatrix.copy( _selected.parent.matrixWorld ).invert();
@@ -213,21 +175,7 @@
 
 			}
 
-			function onPointerCancel( event ) {
-
-				switch ( event.pointerType ) {
-
-					case 'mouse':
-					case 'pen':
-						onMouseCancel();
-						break;
-        // TODO touch
-
-				}
-
-			}
-
-			function onMouseCancel() {
+			function onPointerCancel() {
 
 				if ( _selected ) {
 
@@ -240,93 +188,18 @@
 				}
 
 				_domElement.style.cursor = _hovered ? 'pointer' : 'auto';
+				_domElement.style.touchAction = '';
 
 			}
 
-			function onTouchMove( event ) {
+			function updatePointer( event ) {
 
-				event.preventDefault();
-				event = event.changedTouches[ 0 ];
+				const e = event.changedTouches ? event.changedTouches[ 0 ] : event;
 
 				const rect = _domElement.getBoundingClientRect();
 
-				_mouse.x = ( event.clientX - rect.left ) / rect.width * 2 - 1;
-				_mouse.y = - ( ( event.clientY - rect.top ) / rect.height ) * 2 + 1;
-
-				_raycaster.setFromCamera( _mouse, _camera );
-
-				if ( _selected && scope.enabled ) {
-
-					if ( _raycaster.ray.intersectPlane( _plane, _intersection ) ) {
-
-						_selected.position.copy( _intersection.sub( _offset ).applyMatrix4( _inverseMatrix ) );
-
-					}
-
-					scope.dispatchEvent( {
-						type: 'drag',
-						object: _selected
-					} );
-					return;
-
-				}
-
-			}
-
-			function onTouchStart( event ) {
-
-				event.preventDefault();
-				event = event.changedTouches[ 0 ];
-
-				const rect = _domElement.getBoundingClientRect();
-
-				_mouse.x = ( event.clientX - rect.left ) / rect.width * 2 - 1;
-				_mouse.y = - ( ( event.clientY - rect.top ) / rect.height ) * 2 + 1;
-				_intersections.length = 0;
-
-				_raycaster.setFromCamera( _mouse, _camera );
-
-				_raycaster.intersectObjects( _objects, true, _intersections );
-
-				if ( _intersections.length > 0 ) {
-
-					_selected = scope.transformGroup === true ? _objects[ 0 ] : _intersections[ 0 ].object;
-
-					_plane.setFromNormalAndCoplanarPoint( _camera.getWorldDirection( _plane.normal ), _worldPosition.setFromMatrixPosition( _selected.matrixWorld ) );
-
-					if ( _raycaster.ray.intersectPlane( _plane, _intersection ) ) {
-
-						_inverseMatrix.copy( _selected.parent.matrixWorld ).invert();
-
-						_offset.copy( _intersection ).sub( _worldPosition.setFromMatrixPosition( _selected.matrixWorld ) );
-
-					}
-
-					_domElement.style.cursor = 'move';
-					scope.dispatchEvent( {
-						type: 'dragstart',
-						object: _selected
-					} );
-
-				}
-
-			}
-
-			function onTouchEnd( event ) {
-
-				event.preventDefault();
-
-				if ( _selected ) {
-
-					scope.dispatchEvent( {
-						type: 'dragend',
-						object: _selected
-					} );
-					_selected = null;
-
-				}
-
-				_domElement.style.cursor = 'auto';
+				_pointer.x = ( e.clientX - rect.left ) / rect.width * 2 - 1;
+				_pointer.y = - ( e.clientY - rect.top ) / rect.height * 2 + 1;
 
 			}
 

+ 46 - 151
examples/jsm/controls/DragControls.js

@@ -10,7 +10,7 @@ import {
 const _plane = new Plane();
 const _raycaster = new Raycaster();
 
-const _mouse = new Vector2();
+const _pointer = new Vector2();
 const _offset = new Vector3();
 const _intersection = new Vector3();
 const _worldPosition = new Vector3();
@@ -36,9 +36,6 @@ class DragControls extends EventDispatcher {
 			_domElement.addEventListener( 'pointerdown', onPointerDown );
 			_domElement.addEventListener( 'pointerup', onPointerCancel );
 			_domElement.addEventListener( 'pointerleave', onPointerCancel );
-			_domElement.addEventListener( 'touchmove', onTouchMove, { passive: false } );
-			_domElement.addEventListener( 'touchstart', onTouchStart, { passive: false } );
-			_domElement.addEventListener( 'touchend', onTouchEnd );
 
 		}
 
@@ -48,9 +45,6 @@ class DragControls extends EventDispatcher {
 			_domElement.removeEventListener( 'pointerdown', onPointerDown );
 			_domElement.removeEventListener( 'pointerup', onPointerCancel );
 			_domElement.removeEventListener( 'pointerleave', onPointerCancel );
-			_domElement.removeEventListener( 'touchmove', onTouchMove );
-			_domElement.removeEventListener( 'touchstart', onTouchStart );
-			_domElement.removeEventListener( 'touchend', onTouchEnd );
 
 			_domElement.style.cursor = '';
 
@@ -70,29 +64,13 @@ class DragControls extends EventDispatcher {
 
 		function onPointerMove( event ) {
 
-			switch ( event.pointerType ) {
+			if ( scope.enabled === false ) return;
 
-				case 'mouse':
-				case 'pen':
-					onMouseMove( event );
-					break;
+			updatePointer( event );
 
-				// TODO touch
+			_raycaster.setFromCamera( _pointer, _camera );
 
-			}
-
-		}
-
-		function onMouseMove( event ) {
-
-			const rect = _domElement.getBoundingClientRect();
-
-			_mouse.x = ( ( event.clientX - rect.left ) / rect.width ) * 2 - 1;
-			_mouse.y = - ( ( event.clientY - rect.top ) / rect.height ) * 2 + 1;
-
-			_raycaster.setFromCamera( _mouse, _camera );
-
-			if ( _selected && scope.enabled ) {
+			if ( _selected ) {
 
 				if ( _raycaster.ray.intersectPlane( _plane, _intersection ) ) {
 
@@ -106,76 +84,75 @@ class DragControls extends EventDispatcher {
 
 			}
 
-			_intersections.length = 0;
+			// hover support
 
-			_raycaster.setFromCamera( _mouse, _camera );
-			_raycaster.intersectObjects( _objects, true, _intersections );
+			if ( event.pointerType === 'mouse' || event.pointerType === 'pen' ) {
 
-			if ( _intersections.length > 0 ) {
+				_intersections.length = 0;
 
-				const object = _intersections[ 0 ].object;
+				_raycaster.setFromCamera( _pointer, _camera );
+				_raycaster.intersectObjects( _objects, true, _intersections );
 
-				_plane.setFromNormalAndCoplanarPoint( _camera.getWorldDirection( _plane.normal ), _worldPosition.setFromMatrixPosition( object.matrixWorld ) );
+				if ( _intersections.length > 0 ) {
 
-				if ( _hovered !== object && _hovered !== null ) {
+					const object = _intersections[ 0 ].object;
 
-					scope.dispatchEvent( { type: 'hoveroff', object: _hovered } );
+					_plane.setFromNormalAndCoplanarPoint( _camera.getWorldDirection( _plane.normal ), _worldPosition.setFromMatrixPosition( object.matrixWorld ) );
 
-					_domElement.style.cursor = 'auto';
-					_hovered = null;
+					if ( _hovered !== object && _hovered !== null ) {
 
-				}
+						scope.dispatchEvent( { type: 'hoveroff', object: _hovered } );
 
-				if ( _hovered !== object ) {
+						_domElement.style.cursor = 'auto';
+						_hovered = null;
 
-					scope.dispatchEvent( { type: 'hoveron', object: object } );
+					}
 
-					_domElement.style.cursor = 'pointer';
-					_hovered = object;
+					if ( _hovered !== object ) {
 
-				}
+						scope.dispatchEvent( { type: 'hoveron', object: object } );
 
-			} else {
+						_domElement.style.cursor = 'pointer';
+						_hovered = object;
 
-				if ( _hovered !== null ) {
+					}
 
-					scope.dispatchEvent( { type: 'hoveroff', object: _hovered } );
+				} else {
 
-					_domElement.style.cursor = 'auto';
-					_hovered = null;
+					if ( _hovered !== null ) {
 
-				}
+						scope.dispatchEvent( { type: 'hoveroff', object: _hovered } );
 
-			}
+						_domElement.style.cursor = 'auto';
+						_hovered = null;
 
-		}
+					}
 
-		function onPointerDown( event ) {
+				}
 
-			switch ( event.pointerType ) {
+			}
 
-				case 'mouse':
-				case 'pen':
-					onMouseDown();
-					break;
+		}
 
-				// TODO touch
+		function onPointerDown() {
 
-			}
+			if ( scope.enabled === false ) return;
 
-		}
+			_domElement.style.touchAction = 'none';
 
-		function onMouseDown() {
+			updatePointer( event );
 
 			_intersections.length = 0;
 
-			_raycaster.setFromCamera( _mouse, _camera );
+			_raycaster.setFromCamera( _pointer, _camera );
 			_raycaster.intersectObjects( _objects, true, _intersections );
 
 			if ( _intersections.length > 0 ) {
 
 				_selected = ( scope.transformGroup === true ) ? _objects[ 0 ] : _intersections[ 0 ].object;
 
+				_plane.setFromNormalAndCoplanarPoint( _camera.getWorldDirection( _plane.normal ), _worldPosition.setFromMatrixPosition( _selected.matrixWorld ) );
+
 				if ( _raycaster.ray.intersectPlane( _plane, _intersection ) ) {
 
 					_inverseMatrix.copy( _selected.parent.matrixWorld ).invert();
@@ -192,22 +169,9 @@ class DragControls extends EventDispatcher {
 
 		}
 
-		function onPointerCancel( event ) {
-
-			switch ( event.pointerType ) {
+		function onPointerCancel() {
 
-				case 'mouse':
-				case 'pen':
-					onMouseCancel();
-					break;
-
-				// TODO touch
-
-			}
-
-		}
-
-		function onMouseCancel() {
+			if ( scope.enabled === false ) return;
 
 			if ( _selected ) {
 
@@ -218,87 +182,18 @@ class DragControls extends EventDispatcher {
 			}
 
 			_domElement.style.cursor = _hovered ? 'pointer' : 'auto';
+			_domElement.style.touchAction = '';
 
 		}
 
-		function onTouchMove( event ) {
+		function updatePointer( event ) {
 
-			event.preventDefault();
-			event = event.changedTouches[ 0 ];
+			const e = event.changedTouches ? event.changedTouches[ 0 ] : event;
 
 			const rect = _domElement.getBoundingClientRect();
 
-			_mouse.x = ( ( event.clientX - rect.left ) / rect.width ) * 2 - 1;
-			_mouse.y = - ( ( event.clientY - rect.top ) / rect.height ) * 2 + 1;
-
-			_raycaster.setFromCamera( _mouse, _camera );
-
-			if ( _selected && scope.enabled ) {
-
-				if ( _raycaster.ray.intersectPlane( _plane, _intersection ) ) {
-
-					_selected.position.copy( _intersection.sub( _offset ).applyMatrix4( _inverseMatrix ) );
-
-				}
-
-				scope.dispatchEvent( { type: 'drag', object: _selected } );
-
-				return;
-
-			}
-
-		}
-
-		function onTouchStart( event ) {
-
-			event.preventDefault();
-			event = event.changedTouches[ 0 ];
-
-			const rect = _domElement.getBoundingClientRect();
-
-			_mouse.x = ( ( event.clientX - rect.left ) / rect.width ) * 2 - 1;
-			_mouse.y = - ( ( event.clientY - rect.top ) / rect.height ) * 2 + 1;
-
-			_intersections.length = 0;
-
-			_raycaster.setFromCamera( _mouse, _camera );
-			 _raycaster.intersectObjects( _objects, true, _intersections );
-
-			if ( _intersections.length > 0 ) {
-
-				_selected = ( scope.transformGroup === true ) ? _objects[ 0 ] : _intersections[ 0 ].object;
-
-				_plane.setFromNormalAndCoplanarPoint( _camera.getWorldDirection( _plane.normal ), _worldPosition.setFromMatrixPosition( _selected.matrixWorld ) );
-
-				if ( _raycaster.ray.intersectPlane( _plane, _intersection ) ) {
-
-					_inverseMatrix.copy( _selected.parent.matrixWorld ).invert();
-					_offset.copy( _intersection ).sub( _worldPosition.setFromMatrixPosition( _selected.matrixWorld ) );
-
-				}
-
-				_domElement.style.cursor = 'move';
-
-				scope.dispatchEvent( { type: 'dragstart', object: _selected } );
-
-			}
-
-
-		}
-
-		function onTouchEnd( event ) {
-
-			event.preventDefault();
-
-			if ( _selected ) {
-
-				scope.dispatchEvent( { type: 'dragend', object: _selected } );
-
-				_selected = null;
-
-			}
-
-			_domElement.style.cursor = 'auto';
+			_pointer.x = ( e.clientX - rect.left ) / rect.width * 2 - 1;
+			_pointer.y = - ( e.clientY - rect.top ) / rect.height * 2 + 1;
 
 		}