// Update is called once per frame void Update() { if (!path || !lineRenderer) { return; } _progress = 0; _positionIndex = 0; _positionCount = Mathf.CeilToInt(path.PathLength / minPointDistance); lineRenderer.positionCount = _positionCount + 1; while (_positionIndex < _positionCount) { var pos = path.EvaluatePositionAtUnit(_progress, CinemachinePathBase.PositionUnits.Distance); lineRenderer.SetPosition(_positionIndex, pos); _progress += minPointDistance; _positionIndex++; } // Manually place the last position so it always ends on the same point var finalPos = path.EvaluatePositionAtUnit(1, CinemachinePathBase.PositionUnits.Normalized); lineRenderer.SetPosition(_positionIndex, finalPos); }
void UpdatePosition() { pathPosition += _speedOnPath * Time.deltaTime; if (clampPathPos) { pathPosition = Mathf.Clamp(pathPosition, clampedPathPos.x, clampedPathPos.y); } // Loop the path position so it stays within the bounds of path length. if (path.Looped) { if (pathPosition < 0) { pathPosition += path.PathLength; } else if (pathPosition > path.PathLength) { pathPosition -= path.PathLength; } } else { pathPosition = Mathf.Clamp(pathPosition, 0, path.PathLength); } if (orientToPath) { transform.rotation = path.EvaluateOrientationAtUnit(pathPosition, _units); } // Lerp me to the path point transform.position = Vector3.Lerp(transform.position, path.EvaluatePositionAtUnit(pathPosition, _units), Time.deltaTime * lerpSpeed); }
void UpdateParticles() { if (!path) { return; } // get the count of particles needed to fit on the line int newCount = Mathf.RoundToInt(path.PathLength / spacing); if (newCount != count) { count = newCount; ReInitialize(); } if (particles == null) { ReInitialize(); } int particleCount = particleSystem.GetParticles(particles); for (int i = 0; i < particleCount; i++) { Vector3 pos = path.EvaluatePositionAtUnit(i * spacing, CinemachinePathBase.PositionUnits.Distance); particles[i].position = pos; particles[i].startColor = Color.white; } particleSystem.SetParticles(particles, particles.Length); }
void SetCartPosition(float distanceAlongPath) { if (m_Path != null) { m_Position = m_Path.StandardizeUnit(distanceAlongPath, m_PositionUnits); var newPos = m_Path.EvaluatePositionAtUnit(m_Position, m_PositionUnits); var dir = newPos - transform.position; transform.position = m_Path.EvaluatePositionAtUnit(m_Position, m_PositionUnits); if (dir != Vector3.zero) { transform.transform.rotation = Quaternion.LookRotation(dir); } } }
void SetCartPosition(float distanceAlongPath) { if (m_Path != null) { m_Position = m_Path.NormalizeUnit(distanceAlongPath, m_PositionUnits); transform.position = m_Path.EvaluatePositionAtUnit(m_Position, m_PositionUnits); transform.rotation = m_Path.EvaluateOrientationAtUnit(m_Position, m_PositionUnits); } }
void SetCartPosition(float distanceAlongPath) { if (m_Path != null) { m_Position = m_Path.StandardizeUnit(distanceAlongPath, m_PositionUnits); transform.position = m_Path.EvaluatePositionAtUnit(m_Position, m_PositionUnits); var tangent = m_Path.EvaluateTangentAtUnit(m_Position, m_PositionUnits); tangent.y = 0; // Y方向を無効 transform.rotation = Quaternion.LookRotation(tangent); } }
// Update is called once per frame void Update() { if (!path) { return; } for (int i = 0; i < instances.Count; i++) { Vector3 pos = path.EvaluatePositionAtUnit(i * spacing, CinemachinePathBase.PositionUnits.Distance); instances[i].transform.position = pos; } }
// Update is called once per frame void Update() { if (!path) { return; } transform.position = path.EvaluatePositionAtUnit(position, CinemachinePathBase.PositionUnits.Normalized); if (orientToPath) { Quaternion offsetQuaternion = Quaternion.Euler(offsetRotation); transform.rotation = offsetQuaternion * path.EvaluateOrientationAtUnit(position, CinemachinePathBase.PositionUnits.Normalized); } }
void Spawn() { #if UNITY_EDITOR foreach (var instance in instances) { SafeDestroy(instance); } instances.Clear(); if (!path) { return; } if (prefabsToSpawn.Count < 1) { return; } float progressAlongPath = 0; int iterations = 0; while (iterations < 9999) { // spawn the instance Vector3 spawnPos = path.EvaluatePositionAtUnit(progressAlongPath, CinemachinePathBase.PositionUnits.Distance); GameObject prefabToSpawn = Math.RandomElementOfList(prefabsToSpawn); var newInstance = UnityEditor.PrefabUtility.InstantiatePrefab(prefabToSpawn, transform) as GameObject; instances.Add(newInstance); Vector3 randomCircle = Random.insideUnitSphere * randomRadius; newInstance.transform.position = spawnPos + new Vector3(randomCircle.x, 0, randomCircle.z); float scaleMultiplier = Random.Range(minScale, maxScale); newInstance.transform.localScale *= scaleMultiplier; progressAlongPath += spacing; if (progressAlongPath >= path.PathLength) { break; } iterations++; } #endif }
private static void DrawTrackeDollyGizmos(CinemachineTrackedDolly target, GizmoType selectionType) { if (target.IsValid) { CinemachinePathBase path = target.m_Path; if (path != null) { CinemachinePathEditor.DrawPathGizmo(path, path.m_Appearance.pathColor); Vector3 pos = path.EvaluatePositionAtUnit(target.m_PathPosition, target.m_PositionUnits); Color oldColor = Gizmos.color; Gizmos.color = CinemachineCore.Instance.IsLive(target.VirtualCamera) ? CinemachineSettings.CinemachineCoreSettings.ActiveGizmoColour : CinemachineSettings.CinemachineCoreSettings.InactiveGizmoColour; Gizmos.DrawLine(pos, target.VirtualCamera.State.RawPosition); Gizmos.color = oldColor; } } }
/// <summary>Positions the virtual camera according to the transposer rules.</summary> /// <param name="curState">The current camera state</param> /// <param name="deltaTime">Used for damping. If less that 0, no damping is done.</param> public override void MutateCameraState(ref CameraState curState, float deltaTime) { // Init previous frame state info if (deltaTime < 0) { m_PreviousPathPosition = m_PathPosition; m_PreviousCameraPosition = curState.RawPosition; } if (!IsValid) { return; } //UnityEngine.Profiling.Profiler.BeginSample("CinemachineTrackedDolly.MutateCameraState"); // Get the new ideal path base position if (m_AutoDolly.m_Enabled && FollowTarget != null) { float prevPos = m_PreviousPathPosition; if (m_PositionUnits == CinemachinePathBase.PositionUnits.Distance) { prevPos = m_Path.GetPathPositionFromDistance(prevPos); } // This works in path units m_PathPosition = m_Path.FindClosestPoint( FollowTarget.transform.position, Mathf.FloorToInt(prevPos), (deltaTime < 0 || m_AutoDolly.m_SearchRadius <= 0) ? -1 : m_AutoDolly.m_SearchRadius, m_AutoDolly.m_SearchResolution); if (m_PositionUnits == CinemachinePathBase.PositionUnits.Distance) { m_PathPosition = m_Path.GetPathDistanceFromPosition(m_PathPosition); } // Apply the path position offset m_PathPosition += m_AutoDolly.m_PositionOffset; } float newPathPosition = m_PathPosition; if (deltaTime >= 0) { // Normalize previous position to find the shortest path float maxUnit = m_Path.MaxUnit(m_PositionUnits); if (maxUnit > 0) { float prev = m_Path.NormalizeUnit(m_PreviousPathPosition, m_PositionUnits); float next = m_Path.NormalizeUnit(newPathPosition, m_PositionUnits); if (m_Path.Looped && Mathf.Abs(next - prev) > maxUnit / 2) { if (next > prev) { prev += maxUnit; } else { prev -= maxUnit; } } m_PreviousPathPosition = prev; newPathPosition = next; } // Apply damping along the path direction float offset = m_PreviousPathPosition - newPathPosition; offset = Damper.Damp(offset, m_ZDamping, deltaTime); newPathPosition = m_PreviousPathPosition - offset; } m_PreviousPathPosition = newPathPosition; Quaternion newPathOrientation = m_Path.EvaluateOrientationAtUnit(newPathPosition, m_PositionUnits); // Apply the offset to get the new camera position Vector3 newCameraPos = m_Path.EvaluatePositionAtUnit(newPathPosition, m_PositionUnits); Vector3 offsetX = newPathOrientation * Vector3.right; Vector3 offsetY = newPathOrientation * Vector3.up; Vector3 offsetZ = newPathOrientation * Vector3.forward; newCameraPos += m_PathOffset.x * offsetX; newCameraPos += m_PathOffset.y * offsetY; newCameraPos += m_PathOffset.z * offsetZ; // Apply damping to the remaining directions if (deltaTime >= 0) { Vector3 currentCameraPos = m_PreviousCameraPosition; Vector3 delta = (currentCameraPos - newCameraPos); Vector3 delta1 = Vector3.Dot(delta, offsetY) * offsetY; Vector3 delta0 = delta - delta1; delta0 = Damper.Damp(delta0, m_XDamping, deltaTime); delta1 = Damper.Damp(delta1, m_YDamping, deltaTime); newCameraPos = currentCameraPos - (delta0 + delta1); } curState.RawPosition = m_PreviousCameraPosition = newCameraPos; // Set the orientation and up Quaternion newOrientation = GetTargetOrientationAtPathPoint(newPathOrientation, curState.ReferenceUp); if (deltaTime < 0) { m_PreviousOrientation = newOrientation; } else { if (deltaTime >= 0) { Vector3 relative = (Quaternion.Inverse(m_PreviousOrientation) * newOrientation).eulerAngles; for (int i = 0; i < 3; ++i) { if (relative[i] > 180) { relative[i] -= 360; } } relative = Damper.Damp(relative, AngularDamping, deltaTime); newOrientation = m_PreviousOrientation * Quaternion.Euler(relative); } m_PreviousOrientation = newOrientation; } curState.RawOrientation = newOrientation; curState.ReferenceUp = curState.RawOrientation * Vector3.up; //UnityEngine.Profiling.Profiler.EndSample(); }