//////////////////////////////////////////////////////////////////////////////// // // Copyright (C) 2007-2020 , Inc. All Rights Reserved. // //////////////////////////////////////////////////////////////////////////////// using UnityEngine; using UnityEngine.EventSystems; using GCSeries.Core.EventSystems; using GCSeries.Core.Input; namespace GCSeries.Core.Samples { public class DraggableCustomPlane : ZPointerInteractable, IBeginDragHandler, IDragHandler, IEndDragHandler { //////////////////////////////////////////////////////////////////////// // Inspector Fields //////////////////////////////////////////////////////////////////////// /// /// A transform from which to base planar movement on. Forward (Z) is /// normal to the plane, and the object will drag along its X and Y /// coordinates. /// [Tooltip( "A transform from which to base planar movement on. Forward (Z) " + "is normal to the plane, and the object will drag along its X " + "and Y coordinates.")] public Transform PlaneQuadTransform; //////////////////////////////////////////////////////////////////////// // Public Methods //////////////////////////////////////////////////////////////////////// public override ZPointer.DragPolicy GetDragPolicy(ZPointer pointer) { return ZPointer.DragPolicy.LockToCustomPlane; } public override Plane GetDragPlane(ZPointer pointer) { if (PlaneQuadTransform != null) { return new Plane( PlaneQuadTransform.forward, PlaneQuadTransform.position); } return base.GetDragPlane(pointer); } public void OnBeginDrag(PointerEventData eventData) { ZPointerEventData pointerEventData = eventData as ZPointerEventData; if (pointerEventData == null || pointerEventData.button != PointerEventData.InputButton.Left) { return; } Pose pose = pointerEventData.Pointer.EndPointWorldPose; // Cache the initial grab state. this._initialGrabOffset = Quaternion.Inverse(this.transform.rotation) * (this.transform.position - pose.position); // commenting out rotation from the original draggable script // to maintain a fixed orientation relative to the drag plane // //this._initialGrabRotation = // Quaternion.Inverse(pose.rotation) * // this.transform.rotation; // If the grabbable object has a rigidbody component, // mark it as kinematic during the grab. var rigidbody = this.GetComponent(); if (rigidbody != null) { this._isKinematic = rigidbody.isKinematic; rigidbody.isKinematic = true; } // Capture pointer events. pointerEventData.Pointer.CapturePointer(this.gameObject); } public void OnDrag(PointerEventData eventData) { ZPointerEventData pointerEventData = eventData as ZPointerEventData; if (pointerEventData == null || pointerEventData.button != PointerEventData.InputButton.Left) { return; } Pose pose = pointerEventData.Pointer.EndPointWorldPose; // commenting out rotation from the original draggable script // to maintain a fixed orientation relative to the drag plane // // Update the grab object's rotation. //this.transform.rotation = // pose.rotation * this._initialGrabRotation; // Update the grab object's position. this.transform.position = pose.position + (this.transform.rotation * this._initialGrabOffset); } public void OnEndDrag(PointerEventData eventData) { ZPointerEventData pointerEventData = eventData as ZPointerEventData; if (pointerEventData == null || pointerEventData.button != PointerEventData.InputButton.Left) { return; } // Release the pointer. pointerEventData.Pointer.CapturePointer(null); // If the grabbable object has a rigidbody component, // restore its original isKinematic state. var rigidbody = this.GetComponent(); if (rigidbody != null) { rigidbody.isKinematic = this._isKinematic; } } //////////////////////////////////////////////////////////////////////// // Private Members //////////////////////////////////////////////////////////////////////// private Vector3 _initialGrabOffset = Vector3.zero; //private Quaternion _initialGrabRotation = Quaternion.identity; private bool _isKinematic = false; } }