Files
Cielonos/Assets/Scripts/SLSUtilities/Feedback/Editor/ShakeCurvePresetDrawer.cs
2026-04-18 13:57:19 -04:00

68 lines
2.3 KiB
C#

#if UNITY_EDITOR
using Sirenix.OdinInspector.Editor;
using UnityEditor;
using UnityEngine;
namespace SLSUtilities.Feedback.Editor
{
/// <summary>
/// 为标记了 [ShakeCurvePreset] 的 AnimationCurve 字段绘制预设按钮组。
/// 按钮紧凑排列在曲线编辑器下方。
/// </summary>
public sealed class ShakeCurvePresetDrawer : OdinAttributeDrawer<ShakeCurvePresetAttribute, AnimationCurve>
{
private const float BUTTON_HEIGHT = 18f;
private const float BUTTON_SPACING = 2f;
protected override void DrawPropertyLayout(GUIContent label)
{
// 先绘制默认的曲线字段
CallNextDrawer(label);
// 绘制预设按钮行
DrawPresetButtons();
}
private void DrawPresetButtons()
{
var presets = ShakeCurvePresets.All;
if (presets == null || presets.Length == 0) return;
Rect totalRect = EditorGUILayout.GetControlRect(false, BUTTON_HEIGHT);
// 计算每个按钮的宽度
float totalSpacing = BUTTON_SPACING * (presets.Length - 1);
float buttonWidth = (totalRect.width - totalSpacing) / presets.Length;
GUIStyle buttonStyle = new GUIStyle(EditorStyles.miniButton)
{
fontSize = 8,
padding = new RectOffset(1, 1, 1, 1),
fixedHeight = BUTTON_HEIGHT
};
for (int i = 0; i < presets.Length; i++)
{
float x = totalRect.x + i * (buttonWidth + BUTTON_SPACING);
Rect buttonRect = new Rect(x, totalRect.y, buttonWidth, BUTTON_HEIGHT);
if (GUI.Button(buttonRect, presets[i].name, buttonStyle))
{
// 记录 Undo 以便撤销
if (Property.Tree.UnitySerializedObject != null)
{
Undo.RecordObject(
Property.Tree.UnitySerializedObject.targetObject,
$"Apply Shake Curve Preset: {presets[i].name}"
);
}
ValueEntry.SmartValue = presets[i].factory();
ValueEntry.ApplyChanges();
}
}
}
}
}
#endif