This commit is contained in:
2025-07-13 18:27:36 +08:00
52 changed files with 33692 additions and 16288 deletions

View File

@@ -32,13 +32,10 @@ namespace Ichni.RhythmGame
look.lookAtObject = lookAtTarget;
look.enabling = enabling;
look.animationReturnType = FlexibleReturnType.Before;
look.targetTransformSubmodule = (animatedObject as IHaveTransformSubmodule).transformSubmodule;
//look.timeDurationSubmodule.SetDuration(-999f, 999f); //TODO: 换为(-delay, songLength)
look.targetTransformSubmodule.lookAt = look;
return look;
}
@@ -46,43 +43,19 @@ namespace Ichni.RhythmGame
{
timeDurationSubmodule = new TimeDurationSubmodule(this);
}
// protected override void Update()
// {
// }
// void LateUpdate()
// {
// if (timeDurationSubmodule.CheckTimeInDuration(EditorManager.instance.songInformation.songTime))
// {
// UpdateAnimation(EditorManager.instance.songInformation.songTime);
// }
// }
protected override void UpdateAnimation(float songTime)
{
if (lookAtObject is null) return;
enabling.UpdateFlexibleBool(songTime);
targetTransformSubmodule.eulerAnglesOffsetLock = enabling.value;
if (enabling.value)
{
animationReturnType = FlexibleReturnType.MiddleExecuting;
Vector3 lookingDirection = (lookAtObject.transform.position - animatedObject.transform.position).normalized;
Vector3 eulerAnglesOffset = Quaternion.LookRotation(lookingDirection).eulerAngles;
targetTransformSubmodule.eulerAnglesOffset.Add(eulerAnglesOffset);
targetTransformSubmodule.eulerAnglesDirtyMark = true;
// targetTransformSubmodule.eulerAnglesOffsetLock = true;
// targetTransformSubmodule.currentEulerAngles = eulerAnglesOffset;
}
else if (animationReturnType != FlexibleReturnType.MiddleInterval)
{
targetTransformSubmodule.eulerAnglesOffset.Add(Vector3.zero);
targetTransformSubmodule.eulerAnglesDirtyMark = true;
animationReturnType = FlexibleReturnType.MiddleInterval;
}
// targetTransformSubmodule.eulerAnglesOffsetLock = false;
}
public override void SaveBM()

View File

@@ -1,58 +0,0 @@
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
namespace Ichni
{
/// <summary>
/// 自定义曲线预设
/// </summary>
public static class CustomCurvePresets
{
/// <summary>
/// 瞬间完成
/// </summary>
/// <returns></returns>
public static AnimationCurve Instant()
{
Keyframe[] keys = new Keyframe[2];
keys[0] = new Keyframe(0, 1, 0, 0);
keys[1] = new Keyframe(1, 1, 0, 0);
return new AnimationCurve(keys);
}
/// <summary>
/// 抛物线曲线,在中间达到最大值,两端为起始值
/// </summary>
/// <param name="totalTime">总时间</param>
/// <param name="startValue">起始(和结束)值</param>
/// <param name="peakValue">中点最大值</param>
public static AnimationCurve Parabolic(float totalTime, float startValue, float peakValue)
{
Keyframe[] keys = new Keyframe[3];
keys[0] = new Keyframe(0, startValue, 0, 0);
keys[1] = new Keyframe(totalTime / 2, peakValue, 0, 0);
keys[2] = new Keyframe(totalTime, startValue, 0, 0);
return new AnimationCurve(keys);
}
/// <summary>
/// 自定义峰值点位置的抛物线曲线,在指定时间点达到最大值,两端为起始值
/// </summary>
/// <param name="totalTime">总时间</param>
/// <param name="startValue">起始(和结束)值</param>
/// <param name="peakValue">最大值</param>
/// <param name="peakTimePercent">最大值的比例点</param>
/// <returns></returns>
public static AnimationCurve CustomPeakTimeParabolic(float totalTime, float startValue, float peakValue, float peakTimePercent)
{
Keyframe[] keys = new Keyframe[3];
keys[0] = new Keyframe(0, startValue, 0, 0);
keys[1] = new Keyframe(totalTime * peakTimePercent, peakValue, 0, 0);
keys[2] = new Keyframe(totalTime, startValue, 0, 0);
return new AnimationCurve(keys);
}
}
}

View File

@@ -1,11 +0,0 @@
fileFormatVersion: 2
guid: ac4cc158ed88d48af9a350196b874508
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -24,11 +24,12 @@ namespace Ichni.RhythmGame
public Vector3 currentPosition;
public Vector3 currentEulerAngles;
public Vector3 currentScale;
public bool positionDirtyMark;
public bool eulerAnglesDirtyMark;
public bool scaleDirtyMark;
public LookAt lookAt;
public bool eulerAnglesOffsetLock;
public TransformSubmodule(GameElement attachedGameElement) : base(attachedGameElement)
@@ -157,55 +158,39 @@ namespace Ichni.RhythmGame
if (transformSubmodule.scaleDirtyMark)
{
Vector3 offset = Vector3.zero;
foreach (Vector3 scaleOffset in transformSubmodule.scaleOffset)
{
offset += scaleOffset;
}
Vector3 offset = transformSubmodule.scaleOffset.Sum();
transformSubmodule.currentScale = transformSubmodule.originalScale + offset;
attachedGameElement.transform.localScale = transformSubmodule.currentScale;
transformSubmodule.scaleDirtyMark = false;
willRefresh = true;
transformSubmodule.scaleOffset.Clear();
}
if (transformSubmodule.eulerAnglesDirtyMark)
{
Vector3 offset = Vector3.zero;
foreach (Vector3 eulerOffset in transformSubmodule.eulerAnglesOffset)
{
offset += eulerOffset;
}
Vector3 offset = transformSubmodule.eulerAnglesOffset.Sum();
transformSubmodule.currentEulerAngles = transformSubmodule.originalEulerAngles + offset;
attachedGameElement.transform.localEulerAngles = transformSubmodule.currentEulerAngles;
transformSubmodule.eulerAnglesDirtyMark = false;
willRefresh = true;
transformSubmodule.eulerAnglesOffset.Clear();
}
if (transformSubmodule.positionDirtyMark)
{
Vector3 offset = Vector3.zero;
foreach (Vector3 posOffset in transformSubmodule.positionOffset)
{
offset += posOffset;
}
Vector3 offset = transformSubmodule.positionOffset.Sum();
transformSubmodule.currentPosition = transformSubmodule.originalPosition + offset;
attachedGameElement.transform.localPosition = transformSubmodule.currentPosition;
transformSubmodule.positionDirtyMark = false;
willRefresh = true;
transformSubmodule.positionOffset.Clear();
}
if(willRefresh)
{
attachedGameElement.Refresh();
}
transformSubmodule.scaleOffset.Clear();
transformSubmodule.eulerAnglesOffset.Clear();
transformSubmodule.positionOffset.Clear();
}).AddTo(attachedGameElement);
}
}

View File

@@ -101,7 +101,7 @@ namespace Ichni.RhythmGame
Debug.LogError("Null element detected in elementList. Skipping execution.");
return;
}
Debug.Log(element.GetType());
//Debug.Log(element.GetType());
if (LowPriorityGameElementTypes.Contains(element.GetType()))
{
return;

View File

@@ -15,7 +15,8 @@ namespace Ichni.RhythmGame
{
public partial class GameCamera : GameElement, IHaveTransformSubmodule, IHaveTimeDurationSubmodule
{
[FormerlySerializedAs("camera")] public Camera gameCamera;
[FormerlySerializedAs("camera")]
public Camera gameCamera;
public Transform rotationPoint;
public Transform positionPoint;
public Transform cameraTransform;
@@ -92,22 +93,23 @@ namespace Ichni.RhythmGame
public partial class GameCamera
{
private Vector3 GetWorldEulerAngles()
private void LateUpdate() // 处理LookAt
{
Vector3 output = transformSubmodule.originalEulerAngles;
GameElement element = this;
while (element != null)
if (transformSubmodule?.lookAt is not null &&
transformSubmodule.eulerAnglesOffsetLock &&
transformSubmodule.eulerAnglesDirtyMark)
{
if (element is IHaveTransformSubmodule)
{
output += ((TransformSubmodule)element.submoduleList.Where(r => r is TransformSubmodule).First()).currentEulerAngles;
}
element = element.parentElement;
Vector3 offset = transformSubmodule.eulerAnglesOffset.Sum();
transformSubmodule.currentEulerAngles = transformSubmodule.originalEulerAngles + offset;
transform.LookAt(transformSubmodule.lookAt.lookAtObject.transform);
transform.localEulerAngles += transformSubmodule.currentEulerAngles;
transformSubmodule.eulerAnglesDirtyMark = false;
transformSubmodule.eulerAnglesOffset.Clear();
}
return output;
}
public void SetTransformObserver()
{
Observable.EveryLateUpdate().Subscribe(_ =>
@@ -118,47 +120,32 @@ namespace Ichni.RhythmGame
}
bool willRefresh = false;
if (transformSubmodule.eulerAnglesOffsetLock)
if (!transformSubmodule.eulerAnglesOffsetLock && transformSubmodule.eulerAnglesDirtyMark)
{
transform.localEulerAngles = transformSubmodule.originalEulerAngles;
}
else if (transformSubmodule.eulerAnglesDirtyMark)
{
Vector3 offset = Vector3.zero;
foreach (Vector3 eulerOffset in transformSubmodule.eulerAnglesOffset)
{
offset += eulerOffset;
}
Vector3 offset = transformSubmodule.eulerAnglesOffset.Sum();
transformSubmodule.currentEulerAngles = transformSubmodule.originalEulerAngles + offset;
transform.localEulerAngles = transformSubmodule.currentEulerAngles;
transformSubmodule.eulerAnglesDirtyMark = false;
willRefresh = true;
transformSubmodule.eulerAnglesOffset.Clear();
}
if (transformSubmodule.positionDirtyMark)
{
Vector3 offset = Vector3.zero;
foreach (Vector3 posOffset in transformSubmodule.positionOffset)
{
offset += posOffset;
}
Vector3 offset = transformSubmodule.positionOffset.Sum();
transformSubmodule.currentPosition = transformSubmodule.originalPosition + offset;
transform.localPosition = transformSubmodule.currentPosition;
transformSubmodule.positionDirtyMark = false;
willRefresh = true;
transformSubmodule.positionOffset.Clear();
}
if (willRefresh)
{
this.Refresh();
Refresh();
}
transformSubmodule.eulerAnglesOffset.Clear();
transformSubmodule.positionOffset.Clear();
}).AddTo(gameObject);
}
}

View File

@@ -17,7 +17,7 @@ namespace Ichni.RhythmGame
public string backgroundSpriteName;
public Sprite backgroundSprite;
[FormerlySerializedAs("skyboxController")] public SkyboxSubsetter skyboxSubsetter;
public SkyboxSubsetter skyboxSubsetter;
public static BackgroundSetter GenerateElement(string elementName, Guid id, List<string> tags,
bool isFirstGenerated, GameElement parentElement, bool useSkybox, string skyboxThemeBundleName,