Files
2026-07-13 13:13:17 +08:00

141 lines
5.6 KiB
C#

using ImGuiNET;
using T3.Editor.Gui.Styling;
using T3.Editor.UiModel.InputsAndTypes;
namespace T3.Editor.Gui.Interaction;
internal static class VectorValueEdit
{
// Float control
internal static InputEditStateFlags Draw(float[] components, float min, float max, float scale, bool clampMin, bool clampMax, float rightPadding = 0,
string format = null)
{
// Editors fill the content region, so the snapshot control view's reserved space for
// per-row revert buttons has to be subtracted here - SetNextItemWidth has no effect.
var width = (ImGui.GetContentRegionAvail().X - rightPadding - InputArea.ValueEditRightMargin) / components.Length - 1;
var size = new Vector2(width, 0);
var resultingEditState = InputEditStateFlags.Nothing;
var hasButtons = components.Length == 1 && format?.EndsWith("°") == true;
// Calculate sizes for float buttons
var buttonSize = hasButtons ? Vector2.One * ImGui.GetFrameHeight() : Vector2.Zero;
var fieldWidth = hasButtons ? width - buttonSize.X * 2 : width;
var fieldSize = new Vector2(fieldWidth, 0);
for (var index = 0; index < components.Length; index++)
{
if (index > 0)
ImGui.SameLine();
ImGui.PushID(index);
if (hasButtons)
{
// Draw the input field with adjusted size for buttons
resultingEditState |= SingleValueEdit.Draw(ref components[index], fieldSize, min, max, clampMin, clampMax, scale, format ??= "{0:0.000}");
// Draw +/- buttons for single float component with ° format
var increment = ImGui.GetIO().KeyShift ? ShiftIncrementFloat : DefaultIncrementFloat;
ImGui.SameLine();
ImGui.PushFont(Icons.IconFont);
if (DrawButton((char)Icon.RotateCounterClockwise+"", buttonSize, !clampMin || components[index] > min))
{
components[index] -= increment;
if (clampMin)
components[index] = Math.Max(min, components[index]);
resultingEditState |= InputEditStateFlags.ModifiedAndFinished;
}
ImGui.SameLine();
if (DrawButton((char)Icon.RotateClockwise + "", buttonSize, !clampMax || components[index] < max))
{
components[index] += increment;
if (clampMax)
components[index] = Math.Min(max, components[index]);
resultingEditState |= InputEditStateFlags.ModifiedAndFinished;
}
ImGui.PopFont();
}
else
{
// Draw without buttons
resultingEditState |= SingleValueEdit.Draw(ref components[index], size, min, max, clampMin, clampMax, scale, format ??= "{0:0.000}");
}
ImGui.PopID();
}
return resultingEditState;
}
/// <summary>
/// Integer control, with optional +/- buttons if only one component
/// </summary>
internal static InputEditStateFlags Draw(int[] components, int min, int max, float scale, bool clampMin, bool clampMax)
{
var resultingEditState = InputEditStateFlags.Nothing;
var hasButtons = components.Length == 1;
// Calculate sizes
var width = (ImGui.GetContentRegionAvail().X - InputArea.ValueEditRightMargin) / components.Length - 1;
var buttonSize = hasButtons ? Vector2.One * ImGui.GetFrameHeight() : Vector2.Zero;
var fieldWidth = hasButtons ? width - buttonSize.X * 2 : width;
var size = new Vector2(fieldWidth, 0);
for (var index = 0; index < components.Length; index++)
{
if (index > 0)
ImGui.SameLine();
ImGui.PushID(index);
// Draw the input field
resultingEditState |= SingleValueEdit.Draw(ref components[index], size, min, max, clampMin, clampMax);
// Draw +/- buttons for single component
if (hasButtons)
{
var increment = ImGui.GetIO().KeyShift ? ShiftIncrement : 1;
ImGui.SameLine();
if (DrawButton("-", buttonSize, !clampMin || components[index] > min))
{
components[index] -= increment;
if (clampMin)
components[index] = Math.Max(min, components[index]);
resultingEditState |= InputEditStateFlags.ModifiedAndFinished;
}
ImGui.SameLine();
if (DrawButton("+", buttonSize, !clampMax || components[index] < max))
{
components[index] += increment;
if (clampMax)
components[index] = Math.Min(max, components[index]);
resultingEditState |= InputEditStateFlags.ModifiedAndFinished;
}
}
ImGui.PopID();
}
return resultingEditState;
}
private static bool DrawButton(string label, Vector2 size, bool enabled)
{
if (!enabled)
ImGui.BeginDisabled();
var result = ImGui.Button(label, size);
if (!enabled)
ImGui.EndDisabled();
return result;
}
private const int ShiftIncrement = 10;
private const float DefaultIncrementFloat = -45.0f;
private const float ShiftIncrementFloat = -5.0f;
}