123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143 |
- using System;
- using System.Collections.Generic;
- using Controller.Bicycle;
- using UnityEngine;
- namespace Animation
- {
- #region Helpers
- public enum WheelRotationDirection
- {
- Forward,
- Backward
- }
- [Serializable]
- public struct WheelAnimationConfig
- {
- public GameObject wheel;
- public Axis rotationAxis;
- public WheelRotationDirection rotationDirection;
- }
- #endregion
- [RequireComponent(typeof(IBicycleController))]
- public class BikeAnimation : MonoBehaviour
- {
- // Start is called before the first frame update
- private void Start()
- {
- bicycleController = GetComponentInParent<IBicycleController>();
- initialPositions[crankSet] = crankSet.gameObject.transform.localPosition;
- initialPositions[fork] = fork.gameObject.transform.localPosition;
- initialRotations[crankSet] = crankSet.gameObject.transform.localRotation;
- initialRotations[fork] = fork.gameObject.transform.localRotation;
- }
- private void Update()
- {
- var cadence = /*BikeSensorData.Instance.PowermeterData?.InstantaneousCadence ??*/
- defaultCadence * bicycleController.CurrentSpeed / 8; //rpm*/
- var cadenceAngle = cadence / 60 * 360 * Time.deltaTime; //rps * 360 deg for one round
- if (!pause)
- {
- RotateWheels();
- RotateAroundDefinedAxis(fork, bicycleController.CurrentSteerAngle);
- //Debug.Log($"Rotate cranks with angle {cadenceAngle}");
- RotateAroundDefinedAxis(crankSet, cadenceAngle, false);
- }
- }
- private void RotateWheels()
- {
- var speed = bicycleController.CurrentSpeed;
- var rps = speed / wheelCircumference;
- var angle = rps * Time.deltaTime * 360f;
- RotateSingleWheel(frontWheel, angle);
- RotateSingleWheel(rearWheel, angle);
- }
- private void RotateSingleWheel(WheelAnimationConfig wheel, float angle)
- {
- var t = wheel.wheel.transform;
- var oldPos = t.localPosition;
- var axis = wheel.rotationAxis;
- var backwards = wheel.rotationDirection == WheelRotationDirection.Backward;
- var directedAngle = backwards ? -angle : angle;
- Vector3 rotateAxis;
- if (axis == Axis.X)
- rotateAxis = t.right;
- else if (axis == Axis.Y)
- rotateAxis = t.up;
- else
- rotateAxis = t.forward;
- t.RotateAround(t.position, rotateAxis, directedAngle);
- t.localPosition = oldPos;
- }
- private void RotateAroundDefinedAxis(Rotatable rotatable, float angle, bool resetBeforeRotate = true)
- {
- if (resetBeforeRotate)
- {
- rotatable.gameObject.transform.localPosition = initialPositions[rotatable];
- rotatable.gameObject.transform.localRotation = initialRotations[rotatable];
- }
- if (Mathf.Abs(angle) <= 0.2f) return;
- Vector3 axis;
- if (rotatable.rotateAxis == RotateAxis.Up)
- axis = rotatable.rotateAround.up;
- else if (rotatable.rotateAxis == RotateAxis.Forward)
- axis = rotatable.rotateAround.forward;
- else
- axis = rotatable.rotateAround.right;
- //Debug.Log($"rotatable.rotateAround.position = {rotatable.rotateAround.position}");
- //Debug.Log($"axis = {axis}");
- //Debug.DrawLine(rotatable.rotateAround.position, rotatable.rotateAround.position+axis*5, Color.yellow);
- rotatable.gameObject.transform.RotateAround(rotatable.rotateAround.position, axis, angle);
- }
- //rotates the meshes
- private void RotateObject(GameObject obj, float multiplier)
- {
- obj.transform.Rotate(
- Time.deltaTime * bicycleController.CurrentSpeed * (360f / 12f) * multiplier, 0,
- 0);
- //obj.transform.Rotate(Time.deltaTime * rotSpeed * (360f / oneRotationSpeed) * multiplier, 0, 0);
- }
- #region Variables
- public bool pause; //TODO: remove, only for debugging purposes
- [Header("Wheels - rotating around center")]
- public WheelAnimationConfig rearWheel;
- public WheelAnimationConfig frontWheel;
- [Header("Other with defined rotation axis")]
- public Rotatable crankSet;
- public Rotatable fork;
- [Header("Parameters")] public float wheelCircumference = 2.096f;
- public float defaultCadence = 80;
- private IBicycleController bicycleController;
- private readonly Dictionary<Rotatable, Vector3> initialPositions = new Dictionary<Rotatable, Vector3>();
- private readonly Dictionary<Rotatable, Quaternion> initialRotations = new Dictionary<Rotatable, Quaternion>();
- #endregion
- }
- }
|