comparison Orchestland/Assets/LeapMotion/Scripts/Hands/HandModel.cs @ 1:f7675884f2a1

Add Orchestland project
author Daiki OYAKAWA <e135764@ie.u-ryukyu.ac.jp>
date Fri, 17 Jul 2015 23:09:20 +0900
parents
children
comparison
equal deleted inserted replaced
0:347d21cdfc22 1:f7675884f2a1
1 /******************************************************************************\
2 * Copyright (C) Leap Motion, Inc. 2011-2014. *
3 * Leap Motion proprietary. Licensed under Apache 2.0 *
4 * Available at http://www.apache.org/licenses/LICENSE-2.0.html *
5 \******************************************************************************/
6
7 using UnityEngine;
8 using System.Collections;
9 using Leap;
10
11 /**
12 * The base class for all hand models, both graphics and physics.
13 *
14 * This class serves as the interface between the HandController object
15 * and the concrete hand object containing the graphics and physics of a hand.
16 *
17 * Subclasses of HandModel must implement InitHand() and UpdateHand(). The UpdateHand()
18 * function is called in the Unity Update() phase for graphics HandModel instances;
19 * and in the Unity FixedUpdate() phase for physics objects. InitHand() is called once,
20 * when the hand is created and is followed by a call to UpdateHand().
21 */
22 public abstract class HandModel : MonoBehaviour {
23
24 /** The number of fingers on a hand.*/
25 public const int NUM_FINGERS = 5;
26
27 /** The model width of the hand in meters. This value is used with the measured value
28 * of the user's hand to scale the model proportionally.
29 */
30 public float handModelPalmWidth = 0.085f;
31 /** The array of finger objects for this hand. The array is ordered from thumb (element 0) to pinky (element 4).*/
32 public FingerModel[] fingers = new FingerModel[NUM_FINGERS];
33
34 // Unity references
35 public Transform palm;
36 public Transform forearm;
37 public Transform wristJoint;
38 public Transform elbowJoint;
39
40 // Leap references
41 /** The Leap Hand object this hand model represents. */
42 protected Hand hand_;
43 /** The parent HandController object for this hand. */
44 protected HandController controller_;
45
46 /** Whether the parent HandController instance has been set to mirror across the z axis.*/
47 protected bool mirror_z_axis_ = false;
48
49 /**
50 * Calculates the offset between the wrist position and the controller based
51 * on the HandController.handMovementScale property and the Leap hand wrist position.
52 */
53 public Vector3 GetHandOffset() {
54 if (controller_ == null || hand_ == null)
55 return Vector3.zero;
56
57 Vector3 additional_movement = controller_.handMovementScale - Vector3.one;
58 Vector3 scaled_wrist_position = Vector3.Scale(additional_movement, hand_.WristPosition.ToUnityScaled(mirror_z_axis_));
59
60 return controller_.transform.TransformPoint(scaled_wrist_position) -
61 controller_.transform.position;
62 }
63
64 /** Calculates the position of the palm relative to the controller.
65 * @returns A Vector3 containing the Unity coordinates of the palm position.
66 */
67 public Vector3 GetPalmPosition() {
68 if (controller_ != null && hand_ != null) {
69 return controller_.transform.TransformPoint (hand_.PalmPosition.ToUnityScaled (mirror_z_axis_)) + GetHandOffset ();
70 }
71 if (palm) {
72 return palm.position;
73 }
74 return Vector3.zero;
75 }
76
77 /** Calculates the rotation of the hand relative to the controller.
78 * @returns A Quaternion representing the rotation of the hand relative to the controller.
79 */
80 public Quaternion GetPalmRotation() {
81 if (controller_ != null && hand_ != null) {
82 return controller_.transform.rotation * hand_.Basis.Rotation(mirror_z_axis_);
83 }
84 if (palm) {
85 return palm.rotation;
86 }
87 return Quaternion.identity;
88 }
89
90 /** Calculates the direction vector of the hand relative to the controller.
91 * @returns A Vector3 representing the direction of the hand relative to the controller.
92 */
93 public Vector3 GetPalmDirection() {
94 if (controller_ != null && hand_ != null) {
95 return controller_.transform.TransformDirection(hand_.Direction.ToUnity(mirror_z_axis_));
96 }
97 if (palm) {
98 return palm.forward;
99 }
100 return Vector3.forward;
101 }
102
103 /** Calculates the normal vector projecting from the hand relative to the controller.
104 * @returns A Vector3 representing the vector perpendicular to the palm.
105 */
106 public Vector3 GetPalmNormal() {
107 if (controller_ != null && hand_ != null) {
108 return controller_.transform.TransformDirection(hand_.PalmNormal.ToUnity(mirror_z_axis_));
109 }
110 if (palm) {
111 return -palm.up;
112 }
113 return -Vector3.up;
114 }
115
116 /** Calculates the direction vector of the forearm relative to the controller.
117 * @returns A Vector3 representing the direction of the forearm (pointing from elbow to wrist).
118 */
119 public Vector3 GetArmDirection() {
120 if (controller_ != null && hand_ != null) {
121 return controller_.transform.TransformDirection(hand_.Arm.Direction.ToUnity(mirror_z_axis_));
122 }
123 if (forearm) {
124 return forearm.forward;
125 }
126 return Vector3.forward;
127 }
128
129 /** Calculates the center of the forearm relative to the controller.
130 * @returns A Vector3 containing the Unity coordinates of the center of the forearm.
131 */
132 public Vector3 GetArmCenter() {
133 if (controller_ != null && hand_ != null) {
134 Vector leap_center = 0.5f * (hand_.Arm.WristPosition + hand_.Arm.ElbowPosition);
135 return controller_.transform.TransformPoint (leap_center.ToUnityScaled (mirror_z_axis_)) + GetHandOffset ();
136 }
137 if (forearm) {
138 return forearm.position;
139 }
140 return Vector3.zero;
141 }
142
143 /** Returns the measured length of the forearm in meters.*/
144 public float GetArmLength() {
145 return (hand_.Arm.WristPosition - hand_.Arm.ElbowPosition).Magnitude * UnityVectorExtension.INPUT_SCALE;
146 }
147
148 /** Returns the measured width of the forearm in meters.*/
149 public float GetArmWidth() {
150 return hand_.Arm.Width * UnityVectorExtension.INPUT_SCALE;
151 }
152
153 /** Calculates the position of the elbow relative to the controller.
154 * @returns A Vector3 containing the Unity coordinates of the elbow.
155 */
156 public Vector3 GetElbowPosition() {
157 if (controller_ != null && hand_ != null) {
158 Vector3 local_position = hand_.Arm.ElbowPosition.ToUnityScaled (mirror_z_axis_);
159 return controller_.transform.TransformPoint (local_position) + GetHandOffset ();
160 }
161 if (elbowJoint) {
162 return elbowJoint.position;
163 }
164 return Vector3.zero;
165 }
166
167 /** Calculates the position of the wrist relative to the controller.
168 * @returns A Vector3 containing the Unity coordinates of the wrist.
169 */
170 public Vector3 GetWristPosition() {
171 if (controller_ != null && hand_ != null) {
172 Vector3 local_position = hand_.Arm.WristPosition.ToUnityScaled (mirror_z_axis_);
173 return controller_.transform.TransformPoint (local_position) + GetHandOffset ();
174 }
175 if (wristJoint) {
176 return wristJoint.position;
177 }
178 return Vector3.zero;
179 }
180
181 /** Calculates the rotation of the forearm relative to the controller.
182 * @returns A Quaternion representing the rotation of the arm relative to the controller.
183 */
184 public Quaternion GetArmRotation() {
185 if (controller_ != null && hand_ != null) {
186 Quaternion local_rotation = hand_.Arm.Basis.Rotation (mirror_z_axis_);
187 return controller_.transform.rotation * local_rotation;
188 }
189 if (forearm) {
190 return forearm.rotation;
191 }
192 return Quaternion.identity;
193 }
194
195 /**
196 * Returns the Leap Hand object represented by this HandModel.
197 * Note that any physical quantities and directions obtained from the
198 * Leap Hand object are relative to the Leap Motion coordinate system,
199 * which uses a right-handed axes and units of millimeters.
200 */
201 public Hand GetLeapHand() {
202 return hand_;
203 }
204
205 /**
206 * Assigns a Leap Hand object to this hand model.
207 * Note that the Leap Hand objects are recreated every frame. The parent
208 * HandController calls this method to set or update the underlying hand.
209 */
210 public void SetLeapHand(Hand hand) {
211 hand_ = hand;
212 for (int i = 0; i < fingers.Length; ++i) {
213 if (fingers[i] != null) {
214 fingers[i].SetLeapHand(hand_);
215 fingers[i].SetOffset(GetHandOffset());
216 }
217 }
218 }
219
220 /**
221 * Sets the mirror z-axis flag for this Hand Model and its fingers.
222 * Mirroring the z axis reverses the hand so that they face the opposite direction -- as if in a mirror.
223 * @param mirror Set true, the default value to mirror; false for normal rendering.
224 */
225 public void MirrorZAxis(bool mirror = true) {
226 mirror_z_axis_ = mirror;
227 for (int i = 0; i < fingers.Length; ++i) {
228 if (fingers[i] != null)
229 fingers[i].MirrorZAxis(mirror);
230 }
231 }
232
233 /** Whether this hand is currently mirrored.*/
234 public bool IsMirrored() {
235 return mirror_z_axis_;
236 }
237
238 /** The parent HandController object of this hand.*/
239 public HandController GetController() {
240 return controller_;
241 }
242
243 /** Sets the parent HandController object. */
244 public void SetController(HandController controller) {
245 controller_ = controller;
246 for (int i = 0; i < fingers.Length; ++i) {
247 if (fingers[i] != null)
248 fingers[i].SetController(controller_);
249 }
250 }
251
252 /**
253 * Implement this function to initialise this hand after it is created.
254 * This function is called by the HandController during the Unity Update() phase when a new hand is detected
255 * by the Leap Motion device.
256 */
257 public virtual void InitHand() {
258 for (int f = 0; f < fingers.Length; ++f) {
259 if (fingers[f] != null) {
260 fingers[f].fingerType = (Finger.FingerType)f;
261 fingers[f].InitFinger();
262 }
263 }
264
265 UpdateHand ();
266 }
267
268 /**
269 * Implement this function to update this hand once every game loop.
270 * For HandModel instances assigned to the HandController graphics hand list, the HandController calls this
271 * function during the Unity Update() phase. For HandModel instances in the physics hand list, the HandController
272 * calls this function in the FixedUpdate() phase.
273 */
274 public abstract void UpdateHand();
275 }