unitychan-crs 头发随动脚本
1 // 2 3 //SpringCollider for unity-chan! 4 5 // 6 7 //Original Script is here: 8 9 //ricopin / SpringCollider.cs 10 11 //Rocket Jump : http://rocketjump.skr.jp/unity3d/109/ 12 13 //https://twitter.com/ricopin416 14 15 // 16 17 using UnityEngine; 18 19 using System.Collections; 20 21 22 23 namespace UnityChan 24 25 { 26 27 public class SpringCollider : MonoBehaviour 28 29 { 30 31 //半径 32 33 public float radius = 0.5f; 34 35 36 37 private void OnDrawGizmosSelected () 38 39 { 40 41 Gizmos.color = Color.green; 42 43 Gizmos.DrawWireSphere (transform.position, radius); 44 45 } 46 47 } 48 49 }
1 // 2 3 //SpringBone.cs for unity-chan! 4 5 // 6 7 //Original Script is here: 8 9 //ricopin / SpringBone.cs 10 11 //Rocket Jump : http://rocketjump.skr.jp/unity3d/109/ 12 13 //https://twitter.com/ricopin416 14 15 // 16 17 //Revised by N.Kobayashi 2014/06/20 18 19 // 20 21 using UnityEngine; 22 23 using System.Collections; 24 25 26 27 namespace UnityChan 28 29 { 30 31 public class SpringBone : MonoBehaviour 32 33 { 34 35 //次のボーン 36 37 public Transform child; 38 39 40 41 //ボーンの向き 42 43 public Vector3 boneAxis = new Vector3 (-1.0f, 0.0f, 0.0f); 44 45 public float radius = 0.05f; 46 47 48 49 //各SpringBoneに設定されているstiffnessForceとdragForceを使用するか? 50 51 public bool isUseEachBoneForceSettings = false; 52 53 54 55 //バネが戻る力 56 57 public float stiffnessForce = 0.01f; 58 59 60 61 //力の減衰力 62 63 public float dragForce = 0.4f; 64 65 public Vector3 springForce = new Vector3 (0.0f, -0.0001f, 0.0f); 66 67 public SpringCollider[] colliders; 68 69 public bool debug = true; 70 71 //Kobayashi:Thredshold Starting to activate activeRatio 72 73 public float threshold = 0.01f; 74 75 private float springLength; 76 77 private Quaternion localRotation; 78 79 private Transform trs; 80 81 private Vector3 currTipPos; 82 83 private Vector3 prevTipPos; 84 85 //Kobayashi 86 87 private Transform org; 88 89 //Kobayashi:Reference for "SpringManager" component with unitychan 90 91 private SpringManager managerRef; 92 93 94 95 private void Awake () 96 97 { 98 99 trs = transform; 100 101 localRotation = transform.localRotation; 102 103 //Kobayashi:Reference for "SpringManager" component with unitychan 104 105 // GameObject.Find("unitychan_dynamic").GetComponent<SpringManager>(); 106 107 managerRef = GetParentSpringManager (transform); 108 109 } 110 111 112 113 private SpringManager GetParentSpringManager (Transform t) 114 115 { 116 117 var springManager = t.GetComponent<SpringManager> (); 118 119 120 121 if (springManager != null) 122 123 return springManager; 124 125 126 127 if (t.parent != null) { 128 129 return GetParentSpringManager (t.parent); 130 131 } 132 133 134 135 return null; 136 137 } 138 139 140 141 private void Start () 142 143 { 144 145 springLength = Vector3.Distance (trs.position, child.position); 146 147 currTipPos = child.position; 148 149 prevTipPos = child.position; 150 151 } 152 153 154 155 public void UpdateSpring () 156 157 { 158 159 //Kobayashi 160 161 org = trs; 162 163 //回転をリセット 164 165 trs.localRotation = Quaternion.identity * localRotation; 166 167 168 169 float sqrDt = Time.deltaTime * Time.deltaTime; 170 171 172 173 //stiffness 174 175 Vector3 force = trs.rotation * (boneAxis * stiffnessForce) / sqrDt; 176 177 178 179 //drag 180 181 force += (prevTipPos - currTipPos) * dragForce / sqrDt; 182 183 184 185 force += springForce / sqrDt; 186 187 188 189 //前フレームと値が同じにならないように 190 191 Vector3 temp = currTipPos; 192 193 194 195 //verlet 196 197 currTipPos = (currTipPos - prevTipPos) + currTipPos + (force * sqrDt); 198 199 200 201 //長さを元に戻す 202 203 currTipPos = ((currTipPos - trs.position).normalized * springLength) + trs.position; 204 205 206 207 //衝突判定 208 209 for (int i = 0; i < colliders.Length; i++) { 210 211 if (Vector3.Distance (currTipPos, colliders [i].transform.position) <= (radius + colliders [i].radius)) { 212 213 Vector3 normal = (currTipPos - colliders [i].transform.position).normalized; 214 215 currTipPos = colliders [i].transform.position + (normal * (radius + colliders [i].radius)); 216 217 currTipPos = ((currTipPos - trs.position).normalized * springLength) + trs.position; 218 219 } 220 221 222 223 224 225 } 226 227 228 229 prevTipPos = temp; 230 231 232 233 //回転を適用; 234 235 Vector3 aimVector = trs.TransformDirection (boneAxis); 236 237 Quaternion aimRotation = Quaternion.FromToRotation (aimVector, currTipPos - trs.position); 238 239 //original 240 241 //trs.rotation = aimRotation * trs.rotation; 242 243 //Kobayahsi:Lerp with mixWeight 244 245 Quaternion secondaryRotation = aimRotation * trs.rotation; 246 247 trs.rotation = Quaternion.Lerp (org.rotation, secondaryRotation, managerRef.dynamicRatio); 248 249 } 250 251 252 253 private void OnDrawGizmos () 254 255 { 256 257 if (debug) { 258 259 Gizmos.color = Color.yellow; 260 261 Gizmos.DrawWireSphere (currTipPos, radius); 262 263 } 264 265 } 266 267 } 268 269 }
1 // 2 3 //SpingManager.cs for unity-chan! 4 5 // 6 7 //Original Script is here: 8 9 //ricopin / SpingManager.cs 10 11 //Rocket Jump : http://rocketjump.skr.jp/unity3d/109/ 12 13 //https://twitter.com/ricopin416 14 15 // 16 17 //Revised by N.Kobayashi 2014/06/24 18 19 // Y.Ebata 20 21 // 22 23 using UnityEngine; 24 25 using System.Collections; 26 27 28 29 namespace UnityChan 30 31 { 32 33 public class SpringManager : MonoBehaviour 34 35 { 36 37 //Kobayashi 38 39 // DynamicRatio is paramater for activated level of dynamic animation 40 41 public float dynamicRatio = 1.0f; 42 43 44 45 //Ebata 46 47 public float stiffnessForce; 48 49 public AnimationCurve stiffnessCurve; 50 51 public float dragForce; 52 53 public AnimationCurve dragCurve; 54 55 public SpringBone[] springBones; 56 57 58 59 void Start () 60 61 { 62 63 UpdateParameters (); 64 65 } 66 67 68 69 void Update () 70 71 { 72 73 #if UNITY_EDITOR 74 75 //Kobayashi 76 77 if(dynamicRatio >= 1.0f) 78 79 dynamicRatio = 1.0f; 80 81 else if(dynamicRatio <= 0.0f) 82 83 dynamicRatio = 0.0f; 84 85 //Ebata 86 87 UpdateParameters(); 88 89 #endif 90 91 } 92 93 94 95 private void LateUpdate () 96 97 { 98 99 //Kobayashi 100 101 if (dynamicRatio != 0.0f) { 102 103 for (int i = 0; i < springBones.Length; i++) { 104 105 if (dynamicRatio > springBones [i].threshold) { 106 107 springBones [i].UpdateSpring (); 108 109 } 110 111 } 112 113 } 114 115 } 116 117 118 119 private void UpdateParameters () 120 121 { 122 123 UpdateParameter ("stiffnessForce", stiffnessForce, stiffnessCurve); 124 125 UpdateParameter ("dragForce", dragForce, dragCurve); 126 127 } 128 129 130 131 private void UpdateParameter (string fieldName, float baseValue, AnimationCurve curve) 132 133 { 134 135 var start = curve.keys [0].time; 136 137 var end = curve.keys [curve.length - 1].time; 138 139 //var step = (end - start) / (springBones.Length - 1); 140 141 142 143 var prop = springBones [0].GetType ().GetField (fieldName, System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.Public); 144 145 146 147 for (int i = 0; i < springBones.Length; i++) { 148 149 //Kobayashi 150 151 if (!springBones [i].isUseEachBoneForceSettings) { 152 153 var scale = curve.Evaluate (start + (end - start) * i / (springBones.Length - 1)); 154 155 prop.SetValue (springBones [i], baseValue * scale); 156 157 } 158 159 } 160 161 } 162 163 } 164 165 }