Compare commits

..

No commits in common. "main" and "1.4.0.0" have entirely different histories.

137 changed files with 449 additions and 1415 deletions

View file

@ -9,20 +9,18 @@ jobs:
build: build:
runs-on: windows-latest runs-on: windows-latest
steps: steps:
- uses: actions/checkout@v5 - uses: actions/checkout@v2
with: with:
submodules: recursive submodules: recursive
- name: Setup .NET - name: Setup .NET
uses: actions/setup-dotnet@v5 uses: actions/setup-dotnet@v1
with: with:
dotnet-version: | dotnet-version: '9.x.x'
10.x.x
9.x.x
- name: Restore dependencies - name: Restore dependencies
run: dotnet restore run: dotnet restore
- name: Download Dalamud - name: Download Dalamud
run: | run: |
Invoke-WebRequest -Uri https://goatcorp.github.io/dalamud-distrib/stg/latest.zip -OutFile latest.zip Invoke-WebRequest -Uri https://goatcorp.github.io/dalamud-distrib/latest.zip -OutFile latest.zip
Expand-Archive -Force latest.zip "$env:AppData\XIVLauncher\addon\Hooks\dev" Expand-Archive -Force latest.zip "$env:AppData\XIVLauncher\addon\Hooks\dev"
- name: Build - name: Build
run: | run: |

View file

@ -9,15 +9,13 @@ jobs:
build: build:
runs-on: windows-latest runs-on: windows-latest
steps: steps:
- uses: actions/checkout@v5 - uses: actions/checkout@v2
with: with:
submodules: recursive submodules: recursive
- name: Setup .NET - name: Setup .NET
uses: actions/setup-dotnet@v5 uses: actions/setup-dotnet@v1
with: with:
dotnet-version: | dotnet-version: '9.x.x'
10.x.x
9.x.x
- name: Restore dependencies - name: Restore dependencies
run: dotnet restore run: dotnet restore
- name: Download Dalamud - name: Download Dalamud

@ -1 +1 @@
Subproject commit 5b6730d46f17bdd02a441e23e2141576cf7acf53 Subproject commit 64897c069d3b6c3fe027b3ae0e832828728b9108

View file

@ -1,13 +1,13 @@
using Glamourer.Api.Enums; using Glamourer.Api.Enums;
using Glamourer.Designs; using Glamourer.Designs;
using Glamourer.State; using Glamourer.State;
using OtterGui;
using OtterGui.Extensions; using OtterGui.Extensions;
using OtterGui.Log; using OtterGui.Log;
using OtterGui.Services; using OtterGui.Services;
using Penumbra.GameData.Actors; using Penumbra.GameData.Actors;
using Penumbra.GameData.Enums; using Penumbra.GameData.Enums;
using Penumbra.GameData.Interop; using Penumbra.GameData.Interop;
using Penumbra.GameData.Structs;
using Penumbra.String; using Penumbra.String;
namespace Glamourer.Api; namespace Glamourer.Api;
@ -15,24 +15,15 @@ namespace Glamourer.Api;
public class ApiHelpers(ActorObjectManager objects, StateManager stateManager, ActorManager actors) : IApiService public class ApiHelpers(ActorObjectManager objects, StateManager stateManager, ActorManager actors) : IApiService
{ {
[MethodImpl(MethodImplOptions.AggressiveInlining | MethodImplOptions.AggressiveOptimization)] [MethodImpl(MethodImplOptions.AggressiveInlining | MethodImplOptions.AggressiveOptimization)]
internal IEnumerable<ActorState> FindExistingStates(string actorName, ushort worldId = ushort.MaxValue) internal IEnumerable<ActorState> FindExistingStates(string actorName)
{ {
if (actorName.Length == 0 || !ByteString.FromString(actorName, out var byteString)) if (actorName.Length == 0 || !ByteString.FromString(actorName, out var byteString))
yield break; yield break;
if (worldId == WorldId.AnyWorld.Id)
{
foreach (var state in stateManager.Values.Where(state foreach (var state in stateManager.Values.Where(state
=> state.Identifier.Type is IdentifierType.Player && state.Identifier.PlayerName == byteString)) => state.Identifier.Type is IdentifierType.Player && state.Identifier.PlayerName == byteString))
yield return state; yield return state;
} }
else
{
var identifier = actors.CreatePlayer(byteString, worldId);
if (stateManager.TryGetValue(identifier, out var state))
yield return state;
}
}
[MethodImpl(MethodImplOptions.AggressiveInlining | MethodImplOptions.AggressiveOptimization)] [MethodImpl(MethodImplOptions.AggressiveInlining | MethodImplOptions.AggressiveOptimization)]
internal GlamourerApiEc FindExistingState(int objectIndex, out ActorState? state) internal GlamourerApiEc FindExistingState(int objectIndex, out ActorState? state)

View file

@ -20,12 +20,12 @@ public class DesignsApi(
=> designs.Designs.ToDictionary(d => d.Identifier, d => d.Name.Text); => designs.Designs.ToDictionary(d => d.Identifier, d => d.Name.Text);
public Dictionary<Guid, (string DisplayName, string FullPath, uint DisplayColor, bool ShownInQdb)> GetDesignListExtended() public Dictionary<Guid, (string DisplayName, string FullPath, uint DisplayColor, bool ShownInQdb)> GetDesignListExtended()
=> fileSystem.ToDictionary(kvp => kvp.Key.Identifier, => designs.Designs.ToDictionary(d => d.Identifier,
kvp => (kvp.Key.Name.Text, kvp.Value.FullName(), color.GetColor(kvp.Key), kvp.Key.QuickDesign)); d => (d.Name.Text, fileSystem.FindLeaf(d, out var leaf) ? leaf.FullName() : d.Name.Text, color.GetColor(d), d.QuickDesign));
public (string DisplayName, string FullPath, uint DisplayColor, bool ShowInQdb) GetExtendedDesignData(Guid designId) public (string DisplayName, string FullPath, uint DisplayColor, bool ShowInQdb) GetExtendedDesignData(Guid designId)
=> designs.Designs.ByIdentifier(designId) is { } d => designs.Designs.ByIdentifier(designId) is { } d
? (d.Name.Text, fileSystem.TryGetValue(d, out var leaf) ? leaf.FullName() : d.Name.Text, color.GetColor(d), d.QuickDesign) ? (d.Name.Text, fileSystem.FindLeaf(d, out var leaf) ? leaf.FullName() : d.Name.Text, color.GetColor(d), d.QuickDesign)
: (string.Empty, string.Empty, 0, false); : (string.Empty, string.Empty, 0, false);
public GlamourerApiEc ApplyDesign(Guid designId, int objectIndex, uint key, ApplyFlag flags) public GlamourerApiEc ApplyDesign(Guid designId, int objectIndex, uint key, ApplyFlag flags)

View file

@ -3,17 +3,14 @@ using OtterGui.Services;
namespace Glamourer.Api; namespace Glamourer.Api;
public class GlamourerApi(Configuration config, DesignsApi designs, StateApi state, ItemsApi items) : IGlamourerApi, IApiService public class GlamourerApi(DesignsApi designs, StateApi state, ItemsApi items) : IGlamourerApi, IApiService
{ {
public const int CurrentApiVersionMajor = 1; public const int CurrentApiVersionMajor = 1;
public const int CurrentApiVersionMinor = 7; public const int CurrentApiVersionMinor = 6;
public (int Major, int Minor) ApiVersion public (int Major, int Minor) ApiVersion
=> (CurrentApiVersionMajor, CurrentApiVersionMinor); => (CurrentApiVersionMajor, CurrentApiVersionMinor);
public bool AutoReloadGearEnabled
=> config.AutoRedrawEquipOnChanges;
public IGlamourerApiDesigns Designs public IGlamourerApiDesigns Designs
=> designs; => designs;

View file

@ -22,7 +22,6 @@ public sealed class IpcProviders : IDisposable, IApiService
new FuncProvider<(int Major, int Minor)>(pi, "Glamourer.ApiVersions", () => api.ApiVersion), // backward compatibility new FuncProvider<(int Major, int Minor)>(pi, "Glamourer.ApiVersions", () => api.ApiVersion), // backward compatibility
new FuncProvider<int>(pi, "Glamourer.ApiVersion", () => api.ApiVersion.Major), // backward compatibility new FuncProvider<int>(pi, "Glamourer.ApiVersion", () => api.ApiVersion.Major), // backward compatibility
IpcSubscribers.ApiVersion.Provider(pi, api), IpcSubscribers.ApiVersion.Provider(pi, api),
IpcSubscribers.AutoReloadGearEnabled.Provider(pi, api),
IpcSubscribers.GetDesignList.Provider(pi, api.Designs), IpcSubscribers.GetDesignList.Provider(pi, api.Designs),
IpcSubscribers.GetDesignListExtended.Provider(pi, api.Designs), IpcSubscribers.GetDesignListExtended.Provider(pi, api.Designs),
@ -51,18 +50,13 @@ public sealed class IpcProviders : IDisposable, IApiService
IpcSubscribers.GetStateBase64Name.Provider(pi, api.State), IpcSubscribers.GetStateBase64Name.Provider(pi, api.State),
IpcSubscribers.ApplyState.Provider(pi, api.State), IpcSubscribers.ApplyState.Provider(pi, api.State),
IpcSubscribers.ApplyStateName.Provider(pi, api.State), IpcSubscribers.ApplyStateName.Provider(pi, api.State),
IpcSubscribers.ReapplyState.Provider(pi, api.State),
IpcSubscribers.ReapplyStateName.Provider(pi, api.State),
IpcSubscribers.RevertState.Provider(pi, api.State), IpcSubscribers.RevertState.Provider(pi, api.State),
IpcSubscribers.RevertStateName.Provider(pi, api.State), IpcSubscribers.RevertStateName.Provider(pi, api.State),
IpcSubscribers.UnlockState.Provider(pi, api.State), IpcSubscribers.UnlockState.Provider(pi, api.State),
IpcSubscribers.CanUnlock.Provider(pi, api.State),
IpcSubscribers.UnlockStateName.Provider(pi, api.State), IpcSubscribers.UnlockStateName.Provider(pi, api.State),
IpcSubscribers.DeletePlayerState.Provider(pi, api.State),
IpcSubscribers.UnlockAll.Provider(pi, api.State), IpcSubscribers.UnlockAll.Provider(pi, api.State),
IpcSubscribers.RevertToAutomation.Provider(pi, api.State), IpcSubscribers.RevertToAutomation.Provider(pi, api.State),
IpcSubscribers.RevertToAutomationName.Provider(pi, api.State), IpcSubscribers.RevertToAutomationName.Provider(pi, api.State),
IpcSubscribers.AutoReloadGearChanged.Provider(pi, api.State),
IpcSubscribers.StateChanged.Provider(pi, api.State), IpcSubscribers.StateChanged.Provider(pi, api.State),
IpcSubscribers.StateChangedWithType.Provider(pi, api.State), IpcSubscribers.StateChangedWithType.Provider(pi, api.State),
IpcSubscribers.StateFinalized.Provider(pi, api.State), IpcSubscribers.StateFinalized.Provider(pi, api.State),
@ -81,5 +75,3 @@ public sealed class IpcProviders : IDisposable, IApiService
_disposedProvider.Dispose(); _disposedProvider.Dispose();
} }
} }

View file

@ -8,7 +8,6 @@ using Glamourer.State;
using Newtonsoft.Json.Linq; using Newtonsoft.Json.Linq;
using OtterGui.Services; using OtterGui.Services;
using Penumbra.GameData.Interop; using Penumbra.GameData.Interop;
using Penumbra.GameData.Structs;
using StateChanged = Glamourer.Events.StateChanged; using StateChanged = Glamourer.Events.StateChanged;
namespace Glamourer.Api; namespace Glamourer.Api;
@ -18,9 +17,9 @@ public sealed class StateApi : IGlamourerApiState, IApiService, IDisposable
private readonly ApiHelpers _helpers; private readonly ApiHelpers _helpers;
private readonly StateManager _stateManager; private readonly StateManager _stateManager;
private readonly DesignConverter _converter; private readonly DesignConverter _converter;
private readonly Configuration _config;
private readonly AutoDesignApplier _autoDesigns; private readonly AutoDesignApplier _autoDesigns;
private readonly ActorObjectManager _objects; private readonly ActorObjectManager _objects;
private readonly AutoRedrawChanged _autoRedraw;
private readonly StateChanged _stateChanged; private readonly StateChanged _stateChanged;
private readonly StateFinalized _stateFinalized; private readonly StateFinalized _stateFinalized;
private readonly GPoseService _gPose; private readonly GPoseService _gPose;
@ -28,9 +27,9 @@ public sealed class StateApi : IGlamourerApiState, IApiService, IDisposable
public StateApi(ApiHelpers helpers, public StateApi(ApiHelpers helpers,
StateManager stateManager, StateManager stateManager,
DesignConverter converter, DesignConverter converter,
Configuration config,
AutoDesignApplier autoDesigns, AutoDesignApplier autoDesigns,
ActorObjectManager objects, ActorObjectManager objects,
AutoRedrawChanged autoRedraw,
StateChanged stateChanged, StateChanged stateChanged,
StateFinalized stateFinalized, StateFinalized stateFinalized,
GPoseService gPose) GPoseService gPose)
@ -38,13 +37,12 @@ public sealed class StateApi : IGlamourerApiState, IApiService, IDisposable
_helpers = helpers; _helpers = helpers;
_stateManager = stateManager; _stateManager = stateManager;
_converter = converter; _converter = converter;
_config = config;
_autoDesigns = autoDesigns; _autoDesigns = autoDesigns;
_objects = objects; _objects = objects;
_autoRedraw = autoRedraw;
_stateChanged = stateChanged; _stateChanged = stateChanged;
_stateFinalized = stateFinalized; _stateFinalized = stateFinalized;
_gPose = gPose; _gPose = gPose;
_autoRedraw.Subscribe(OnAutoRedrawChange, AutoRedrawChanged.Priority.StateApi);
_stateChanged.Subscribe(OnStateChanged, Events.StateChanged.Priority.GlamourerIpc); _stateChanged.Subscribe(OnStateChanged, Events.StateChanged.Priority.GlamourerIpc);
_stateFinalized.Subscribe(OnStateFinalized, Events.StateFinalized.Priority.StateApi); _stateFinalized.Subscribe(OnStateFinalized, Events.StateFinalized.Priority.StateApi);
_gPose.Subscribe(OnGPoseChange, GPoseService.Priority.StateApi); _gPose.Subscribe(OnGPoseChange, GPoseService.Priority.StateApi);
@ -52,7 +50,6 @@ public sealed class StateApi : IGlamourerApiState, IApiService, IDisposable
public void Dispose() public void Dispose()
{ {
_autoRedraw.Unsubscribe(OnAutoRedrawChange);
_stateChanged.Unsubscribe(OnStateChanged); _stateChanged.Unsubscribe(OnStateChanged);
_stateFinalized.Unsubscribe(OnStateFinalized); _stateFinalized.Unsubscribe(OnStateFinalized);
_gPose.Unsubscribe(OnGPoseChange); _gPose.Unsubscribe(OnGPoseChange);
@ -126,48 +123,6 @@ public sealed class StateApi : IGlamourerApiState, IApiService, IDisposable
return ApiHelpers.Return(GlamourerApiEc.Success, args); return ApiHelpers.Return(GlamourerApiEc.Success, args);
} }
public GlamourerApiEc ReapplyState(int objectIndex, uint key, ApplyFlag flags)
{
var args = ApiHelpers.Args("Index", objectIndex, "Key", key, "Flags", flags);
if (_helpers.FindExistingState(objectIndex, out var state) is not GlamourerApiEc.Success)
return ApiHelpers.Return(GlamourerApiEc.ActorNotFound, args);
if (state is null)
return ApiHelpers.Return(GlamourerApiEc.NothingDone, args);
if (!state.CanUnlock(key))
return ApiHelpers.Return(GlamourerApiEc.InvalidKey, args);
Reapply(_objects.Objects[objectIndex], state, key, flags);
return ApiHelpers.Return(GlamourerApiEc.Success, args);
}
public GlamourerApiEc ReapplyStateName(string playerName, uint key, ApplyFlag flags)
{
var args = ApiHelpers.Args("Name", playerName, "Key", key, "Flags", flags);
var states = _helpers.FindExistingStates(playerName);
var any = false;
var anyReapplied = false;
foreach (var state in states)
{
any = true;
if (!state.CanUnlock(key))
continue;
anyReapplied = true;
anyReapplied |= Reapply(state, key, flags) is GlamourerApiEc.Success;
}
if (any)
ApiHelpers.Return(GlamourerApiEc.NothingDone, args);
if (!anyReapplied)
return ApiHelpers.Return(GlamourerApiEc.InvalidKey, args);
return ApiHelpers.Return(GlamourerApiEc.Success, args);
}
public GlamourerApiEc RevertState(int objectIndex, uint key, ApplyFlag flags) public GlamourerApiEc RevertState(int objectIndex, uint key, ApplyFlag flags)
{ {
var args = ApiHelpers.Args("Index", objectIndex, "Key", key, "Flags", flags); var args = ApiHelpers.Args("Index", objectIndex, "Key", key, "Flags", flags);
@ -225,20 +180,6 @@ public sealed class StateApi : IGlamourerApiState, IApiService, IDisposable
return ApiHelpers.Return(GlamourerApiEc.Success, args); return ApiHelpers.Return(GlamourerApiEc.Success, args);
} }
public GlamourerApiEc CanUnlock(int objectIndex, uint key, out bool isLocked, out bool canUnlock)
{
var args = ApiHelpers.Args("Index", objectIndex, "Key", key);
isLocked = false;
canUnlock = true;
if (_helpers.FindExistingState(objectIndex, out var state) is not GlamourerApiEc.Success)
return ApiHelpers.Return(GlamourerApiEc.ActorNotFound, args);
if (state is null)
return ApiHelpers.Return(GlamourerApiEc.Success, args);
isLocked = state.IsLocked;
canUnlock = state.CanUnlock(key);
return ApiHelpers.Return(GlamourerApiEc.Success, args);
}
public GlamourerApiEc UnlockStateName(string playerName, uint key) public GlamourerApiEc UnlockStateName(string playerName, uint key)
{ {
var args = ApiHelpers.Args("Name", playerName, "Key", key); var args = ApiHelpers.Args("Name", playerName, "Key", key);
@ -261,27 +202,6 @@ public sealed class StateApi : IGlamourerApiState, IApiService, IDisposable
return ApiHelpers.Return(GlamourerApiEc.Success, args); return ApiHelpers.Return(GlamourerApiEc.Success, args);
} }
public GlamourerApiEc DeletePlayerState(string playerName, ushort worldId, uint key)
{
var args = ApiHelpers.Args("Name", playerName, "World", worldId, "Key", key);
var states = _helpers.FindExistingStates(playerName).ToList();
if (states.Count is 0)
return ApiHelpers.Return(GlamourerApiEc.NothingDone, args);
var anyLocked = false;
foreach (var state in states)
{
if (state.CanUnlock(key))
_stateManager.DeleteState(state.Identifier);
else
anyLocked = true;
}
return ApiHelpers.Return(anyLocked
? GlamourerApiEc.InvalidKey
: GlamourerApiEc.Success, args);
}
public int UnlockAll(uint key) public int UnlockAll(uint key)
=> _stateManager.Values.Count(state => state.Unlock(key)); => _stateManager.Values.Count(state => state.Unlock(key));
@ -331,7 +251,6 @@ public sealed class StateApi : IGlamourerApiState, IApiService, IDisposable
return ApiHelpers.Return(GlamourerApiEc.Success, args); return ApiHelpers.Return(GlamourerApiEc.Success, args);
} }
public event Action<bool>? AutoReloadGearChanged;
public event Action<nint>? StateChanged; public event Action<nint>? StateChanged;
public event Action<IntPtr, StateChangeType>? StateChangedWithType; public event Action<IntPtr, StateChangeType>? StateChangedWithType;
public event Action<IntPtr, StateFinalizationType>? StateFinalized; public event Action<IntPtr, StateFinalizationType>? StateFinalized;
@ -346,32 +265,14 @@ public sealed class StateApi : IGlamourerApiState, IApiService, IDisposable
ApiHelpers.Lock(state, key, flags); ApiHelpers.Lock(state, key, flags);
} }
private GlamourerApiEc Reapply(ActorState state, uint key, ApplyFlag flags)
{
if (!_objects.TryGetValue(state.Identifier, out var actors) || !actors.Valid)
return GlamourerApiEc.ActorNotFound;
foreach (var actor in actors.Objects)
Reapply(actor, state, key, flags);
return GlamourerApiEc.Success;
}
private void Reapply(Actor actor, ActorState state, uint key, ApplyFlag flags)
{
var source = flags.HasFlag(ApplyFlag.Once) ? StateSource.IpcFixed : StateSource.IpcManual;
_stateManager.ReapplyState(actor, state, false, source, true);
ApiHelpers.Lock(state, key, flags);
}
private void Revert(ActorState state, uint key, ApplyFlag flags) private void Revert(ActorState state, uint key, ApplyFlag flags)
{ {
var source = flags.HasFlag(ApplyFlag.Once) ? StateSource.IpcFixed : StateSource.IpcManual; var source = (flags & ApplyFlag.Once) != 0 ? StateSource.IpcManual : StateSource.IpcFixed;
switch (flags & (ApplyFlag.Equipment | ApplyFlag.Customization)) switch (flags & (ApplyFlag.Equipment | ApplyFlag.Customization))
{ {
case ApplyFlag.Equipment: _stateManager.ResetEquip(state, source, key); break; case ApplyFlag.Equipment: _stateManager.ResetEquip(state, source, key); break;
case ApplyFlag.Customization: _stateManager.ResetCustomize(state, source, key); break; case ApplyFlag.Customization: _stateManager.ResetCustomize(state, source, key); break;
case ApplyFlag.Equipment | ApplyFlag.Customization: _stateManager.ResetState(state, source, key, true); break; case ApplyFlag.Equipment | ApplyFlag.Customization: _stateManager.ResetState(state, source, key); break;
} }
ApiHelpers.Lock(state, key, flags); ApiHelpers.Lock(state, key, flags);
@ -424,8 +325,8 @@ public sealed class StateApi : IGlamourerApiState, IApiService, IDisposable
}; };
} }
private void OnAutoRedrawChange(bool autoReload) private void OnGPoseChange(bool gPose)
=> AutoReloadGearChanged?.Invoke(autoReload); => GPoseChanged?.Invoke(gPose);
private void OnStateChanged(StateChangeType type, StateSource _2, ActorState _3, ActorData actors, ITransaction? _5) private void OnStateChanged(StateChangeType type, StateSource _2, ActorState _3, ActorData actors, ITransaction? _5)
{ {
@ -446,7 +347,4 @@ public sealed class StateApi : IGlamourerApiState, IApiService, IDisposable
foreach (var actor in actors.Objects) foreach (var actor in actors.Objects)
StateFinalized.Invoke(actor.Address, type); StateFinalized.Invoke(actor.Address, type);
} }
private void OnGPoseChange(bool gPose)
=> GPoseChanged?.Invoke(gPose);
} }

View file

@ -38,7 +38,7 @@ public static class ApplicationTypeExtensions
var customizeFlags = type.HasFlag(ApplicationType.Customizations) ? CustomizeFlagExtensions.All : 0; var customizeFlags = type.HasFlag(ApplicationType.Customizations) ? CustomizeFlagExtensions.All : 0;
var parameterFlags = type.HasFlag(ApplicationType.Customizations) ? CustomizeParameterExtensions.All : 0; var parameterFlags = type.HasFlag(ApplicationType.Customizations) ? CustomizeParameterExtensions.All : 0;
var crestFlags = type.HasFlag(ApplicationType.GearCustomization) ? CrestExtensions.AllRelevant : 0; var crestFlags = type.HasFlag(ApplicationType.GearCustomization) ? CrestExtensions.AllRelevant : 0;
var metaFlags = (type.HasFlag(ApplicationType.Armor) ? MetaFlag.HatState | MetaFlag.VisorState | MetaFlag.EarState : 0) var metaFlags = (type.HasFlag(ApplicationType.Armor) ? MetaFlag.HatState | MetaFlag.VisorState : 0)
| (type.HasFlag(ApplicationType.Weapons) ? MetaFlag.WeaponState : 0) | (type.HasFlag(ApplicationType.Weapons) ? MetaFlag.WeaponState : 0)
| (type.HasFlag(ApplicationType.Customizations) ? MetaFlag.Wetness : 0); | (type.HasFlag(ApplicationType.Customizations) ? MetaFlag.Wetness : 0);
var bonusFlags = type.HasFlag(ApplicationType.Armor) ? BonusExtensions.All : 0; var bonusFlags = type.HasFlag(ApplicationType.Armor) ? BonusExtensions.All : 0;

View file

@ -32,7 +32,6 @@ public class DefaultDesignSettings
public bool ResetAdvancedDyes = false; public bool ResetAdvancedDyes = false;
public bool ShowQuickDesignBar = true; public bool ShowQuickDesignBar = true;
public bool ResetTemporarySettings = false; public bool ResetTemporarySettings = false;
public bool Locked = false;
} }
public class Configuration : IPluginConfiguration, ISavable public class Configuration : IPluginConfiguration, ISavable
@ -40,7 +39,6 @@ public class Configuration : IPluginConfiguration, ISavable
[JsonIgnore] [JsonIgnore]
public readonly EphemeralConfig Ephemeral; public readonly EphemeralConfig Ephemeral;
public bool AttachToPcp { get; set; } = true;
public bool UseRestrictedGearProtection { get; set; } = false; public bool UseRestrictedGearProtection { get; set; } = false;
public bool OpenFoldersByDefault { get; set; } = false; public bool OpenFoldersByDefault { get; set; } = false;
public bool AutoRedrawEquipOnChanges { get; set; } = false; public bool AutoRedrawEquipOnChanges { get; set; } = false;
@ -64,13 +62,11 @@ public class Configuration : IPluginConfiguration, ISavable
public bool UseRgbForColors { get; set; } = true; public bool UseRgbForColors { get; set; } = true;
public bool ShowColorConfig { get; set; } = true; public bool ShowColorConfig { get; set; } = true;
public bool ChangeEntireItem { get; set; } = false; public bool ChangeEntireItem { get; set; } = false;
public bool AlwaysApplyAssociatedMods { get; set; } = true; public bool AlwaysApplyAssociatedMods { get; set; } = false;
public bool UseTemporarySettings { get; set; } = true; public bool UseTemporarySettings { get; set; } = true;
public bool AllowDoubleClickToApply { get; set; } = false; public bool AllowDoubleClickToApply { get; set; } = false;
public bool RespectManualOnAutomationUpdate { get; set; } = false; public bool RespectManualOnAutomationUpdate { get; set; } = false;
public bool PreventRandomRepeats { get; set; } = false; public bool PreventRandomRepeats { get; set; } = false;
public string PcpFolder { get; set; } = "PCP";
public string PcpColor { get; set; } = "";
public DesignPanelFlag HideDesignPanel { get; set; } = 0; public DesignPanelFlag HideDesignPanel { get; set; } = 0;
public DesignPanelFlag AutoExpandDesignPanel { get; set; } = 0; public DesignPanelFlag AutoExpandDesignPanel { get; set; } = 0;

View file

@ -1,5 +1,5 @@
using Glamourer.Designs; using Glamourer.Designs;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui.Text; using OtterGui.Text;
using OtterGui.Text.EndObjects; using OtterGui.Text.EndObjects;

View file

@ -1,6 +1,6 @@
using Glamourer.Api.Enums; using Glamourer.Api.Enums;
using Glamourer.GameData; using Glamourer.GameData;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using Penumbra.GameData.Enums; using Penumbra.GameData.Enums;
namespace Glamourer.Designs; namespace Glamourer.Designs;
@ -19,13 +19,13 @@ public record struct ApplicationCollection(
public static readonly ApplicationCollection None = new(0, 0, CustomizeFlag.BodyType, 0, 0, 0); public static readonly ApplicationCollection None = new(0, 0, CustomizeFlag.BodyType, 0, 0, 0);
public static readonly ApplicationCollection Equipment = new(EquipFlagExtensions.All, BonusExtensions.All, public static readonly ApplicationCollection Equipment = new(EquipFlagExtensions.All, BonusExtensions.All,
CustomizeFlag.BodyType, CrestExtensions.AllRelevant, 0, MetaFlag.HatState | MetaFlag.WeaponState | MetaFlag.VisorState | MetaFlag.EarState); CustomizeFlag.BodyType, CrestExtensions.AllRelevant, 0, MetaFlag.HatState | MetaFlag.WeaponState | MetaFlag.VisorState);
public static readonly ApplicationCollection Customizations = new(0, 0, CustomizeFlagExtensions.AllRelevant, 0, public static readonly ApplicationCollection Customizations = new(0, 0, CustomizeFlagExtensions.AllRelevant, 0,
CustomizeParameterExtensions.All, MetaFlag.Wetness); CustomizeParameterExtensions.All, MetaFlag.Wetness);
public static readonly ApplicationCollection Default = new(EquipFlagExtensions.All, BonusExtensions.All, public static readonly ApplicationCollection Default = new(EquipFlagExtensions.All, BonusExtensions.All,
CustomizeFlagExtensions.AllRelevant, CrestExtensions.AllRelevant, 0, MetaFlag.HatState | MetaFlag.VisorState | MetaFlag.WeaponState | MetaFlag.EarState); CustomizeFlagExtensions.AllRelevant, CrestExtensions.AllRelevant, 0, MetaFlag.HatState | MetaFlag.VisorState | MetaFlag.WeaponState);
public static ApplicationCollection FromKeys() public static ApplicationCollection FromKeys()
=> (ImGui.GetIO().KeyCtrl, ImGui.GetIO().KeyShift) switch => (ImGui.GetIO().KeyCtrl, ImGui.GetIO().KeyShift) switch
@ -47,7 +47,7 @@ public record struct ApplicationCollection(
Equip = 0; Equip = 0;
BonusItem = 0; BonusItem = 0;
Crest = 0; Crest = 0;
Meta &= ~(MetaFlag.HatState | MetaFlag.VisorState | MetaFlag.WeaponState | MetaFlag.EarState); Meta &= ~(MetaFlag.HatState | MetaFlag.VisorState | MetaFlag.WeaponState);
} }
public void RemoveCustomize() public void RemoveCustomize()

View file

@ -1,7 +1,7 @@
using Glamourer.Api.Enums; using Glamourer.Api.Enums;
using Glamourer.GameData; using Glamourer.GameData;
using Glamourer.State; using Glamourer.State;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using Penumbra.GameData.Enums; using Penumbra.GameData.Enums;
namespace Glamourer.Designs; namespace Glamourer.Designs;

View file

@ -100,7 +100,7 @@ public sealed class Design : DesignBase, ISavable, IDesignStandIn
public new JObject JsonSerialize() public new JObject JsonSerialize()
{ {
var ret = new JObject var ret = new JObject()
{ {
["FileVersion"] = FileVersion, ["FileVersion"] = FileVersion,
["Identifier"] = Identifier, ["Identifier"] = Identifier,
@ -131,17 +131,12 @@ public sealed class Design : DesignBase, ISavable, IDesignStandIn
var ret = new JArray(); var ret = new JArray();
foreach (var (mod, settings) in AssociatedMods) foreach (var (mod, settings) in AssociatedMods)
{ {
var obj = new JObject var obj = new JObject()
{ {
["Name"] = mod.Name, ["Name"] = mod.Name,
["Directory"] = mod.DirectoryName, ["Directory"] = mod.DirectoryName,
["Enabled"] = settings.Enabled,
}; };
if (settings.Remove)
obj["Remove"] = true;
else if (settings.ForceInherit)
obj["Inherit"] = true;
else
obj["Enabled"] = settings.Enabled;
if (settings.Enabled) if (settings.Enabled)
{ {
obj["Priority"] = settings.Priority; obj["Priority"] = settings.Priority;

View file

@ -40,8 +40,7 @@ public class DesignBase
} }
/// <summary> Used when importing .cma or .chara files. </summary> /// <summary> Used when importing .cma or .chara files. </summary>
internal DesignBase(CustomizeService customize, in DesignData designData, EquipFlag equipFlags, CustomizeFlag customizeFlags, internal DesignBase(CustomizeService customize, in DesignData designData, EquipFlag equipFlags, CustomizeFlag customizeFlags, BonusItemFlag bonusFlags)
BonusItemFlag bonusFlags)
{ {
_designData = designData; _designData = designData;
ApplyCustomize = customizeFlags & CustomizeFlagExtensions.AllRelevant; ApplyCustomize = customizeFlags & CustomizeFlagExtensions.AllRelevant;
@ -256,7 +255,6 @@ public class DesignBase
} }
ret["Hat"] = new QuadBool(_designData.IsHatVisible(), DoApplyMeta(MetaIndex.HatState)).ToJObject("Show", "Apply"); ret["Hat"] = new QuadBool(_designData.IsHatVisible(), DoApplyMeta(MetaIndex.HatState)).ToJObject("Show", "Apply");
ret["VieraEars"] = new QuadBool(_designData.AreEarsVisible(), DoApplyMeta(MetaIndex.EarState)).ToJObject("Show", "Apply");
ret["Visor"] = new QuadBool(_designData.IsVisorToggled(), DoApplyMeta(MetaIndex.VisorState)).ToJObject("IsToggled", "Apply"); ret["Visor"] = new QuadBool(_designData.IsVisorToggled(), DoApplyMeta(MetaIndex.VisorState)).ToJObject("IsToggled", "Apply");
ret["Weapon"] = new QuadBool(_designData.IsWeaponVisible(), DoApplyMeta(MetaIndex.WeaponState)).ToJObject("Show", "Apply"); ret["Weapon"] = new QuadBool(_designData.IsWeaponVisible(), DoApplyMeta(MetaIndex.WeaponState)).ToJObject("Show", "Apply");
} }
@ -605,10 +603,6 @@ public class DesignBase
metaValue = QuadBool.FromJObject(equip["Visor"], "IsToggled", "Apply", QuadBool.NullFalse); metaValue = QuadBool.FromJObject(equip["Visor"], "IsToggled", "Apply", QuadBool.NullFalse);
design.SetApplyMeta(MetaIndex.VisorState, metaValue.Enabled); design.SetApplyMeta(MetaIndex.VisorState, metaValue.Enabled);
design._designData.SetVisor(metaValue.ForcedValue); design._designData.SetVisor(metaValue.ForcedValue);
metaValue = QuadBool.FromJObject(equip["VieraEars"], "Show", "Apply", QuadBool.NullTrue);
design.SetApplyMeta(MetaIndex.EarState, metaValue.Enabled);
design._designData.SetEarsVisible(metaValue.ForcedValue);
return; return;
void PrintWarning(string msg) void PrintWarning(string msg)

View file

@ -3,7 +3,7 @@ using Dalamud.Interface.ImGuiNotification;
using Dalamud.Interface.Utility.Raii; using Dalamud.Interface.Utility.Raii;
using Glamourer.Gui; using Glamourer.Gui;
using Glamourer.Services; using Glamourer.Services;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using Newtonsoft.Json; using Newtonsoft.Json;
using Newtonsoft.Json.Linq; using Newtonsoft.Json.Linq;
using OtterGui; using OtterGui;

View file

@ -287,7 +287,6 @@ public unsafe struct DesignData
MetaIndex.HatState => IsHatVisible(), MetaIndex.HatState => IsHatVisible(),
MetaIndex.VisorState => IsVisorToggled(), MetaIndex.VisorState => IsVisorToggled(),
MetaIndex.WeaponState => IsWeaponVisible(), MetaIndex.WeaponState => IsWeaponVisible(),
MetaIndex.EarState => AreEarsVisible(),
_ => false, _ => false,
}; };
@ -298,7 +297,6 @@ public unsafe struct DesignData
MetaIndex.HatState => SetHatVisible(value), MetaIndex.HatState => SetHatVisible(value),
MetaIndex.VisorState => SetVisor(value), MetaIndex.VisorState => SetVisor(value),
MetaIndex.WeaponState => SetWeaponVisible(value), MetaIndex.WeaponState => SetWeaponVisible(value),
MetaIndex.EarState => SetEarsVisible(value),
_ => false, _ => false,
}; };
@ -342,9 +340,6 @@ public unsafe struct DesignData
public readonly bool IsWeaponVisible() public readonly bool IsWeaponVisible()
=> (_states & 0x08) == 0x08; => (_states & 0x08) == 0x08;
public readonly bool AreEarsVisible()
=> (_states & 0x10) == 0x00;
public bool SetWeaponVisible(bool value) public bool SetWeaponVisible(bool value)
{ {
if (value == IsWeaponVisible()) if (value == IsWeaponVisible())
@ -354,15 +349,6 @@ public unsafe struct DesignData
return true; return true;
} }
public bool SetEarsVisible(bool value)
{
if (value == AreEarsVisible())
return false;
_states = (byte)(value ? _states & ~0x10 : _states | 0x10);
return true;
}
public void SetDefaultEquipment(ItemManager items) public void SetDefaultEquipment(ItemManager items)
{ {
foreach (var slot in EquipSlotExtensions.EqdpSlots) foreach (var slot in EquipSlotExtensions.EqdpSlots)
@ -400,7 +386,6 @@ public unsafe struct DesignData
SetHatVisible(true); SetHatVisible(true);
SetWeaponVisible(true); SetWeaponVisible(true);
SetEarsVisible(true);
SetVisor(false); SetVisor(false);
fixed (uint* ptr = _itemIds) fixed (uint* ptr = _itemIds)
{ {

View file

@ -41,11 +41,11 @@ public sealed class DesignFileSystem : FileSystem<Design>, IDisposable, ISavable
public struct CreationDate : ISortMode<Design> public struct CreationDate : ISortMode<Design>
{ {
public ReadOnlySpan<byte> Name public string Name
=> "Creation Date (Older First)"u8; => "Creation Date (Older First)";
public ReadOnlySpan<byte> Description public string Description
=> "In each folder, sort all subfolders lexicographically, then sort all leaves using their creation date."u8; => "In each folder, sort all subfolders lexicographically, then sort all leaves using their creation date.";
public IEnumerable<IPath> GetChildren(Folder f) public IEnumerable<IPath> GetChildren(Folder f)
=> f.GetSubFolders().Cast<IPath>().Concat(f.GetLeaves().OrderBy(l => l.Value.CreationDate)); => f.GetSubFolders().Cast<IPath>().Concat(f.GetLeaves().OrderBy(l => l.Value.CreationDate));
@ -53,11 +53,11 @@ public sealed class DesignFileSystem : FileSystem<Design>, IDisposable, ISavable
public struct UpdateDate : ISortMode<Design> public struct UpdateDate : ISortMode<Design>
{ {
public ReadOnlySpan<byte> Name public string Name
=> "Update Date (Older First)"u8; => "Update Date (Older First)";
public ReadOnlySpan<byte> Description public string Description
=> "In each folder, sort all subfolders lexicographically, then sort all leaves using their last update date."u8; => "In each folder, sort all subfolders lexicographically, then sort all leaves using their last update date.";
public IEnumerable<IPath> GetChildren(Folder f) public IEnumerable<IPath> GetChildren(Folder f)
=> f.GetSubFolders().Cast<IPath>().Concat(f.GetLeaves().OrderBy(l => l.Value.LastEdit)); => f.GetSubFolders().Cast<IPath>().Concat(f.GetLeaves().OrderBy(l => l.Value.LastEdit));
@ -65,11 +65,11 @@ public sealed class DesignFileSystem : FileSystem<Design>, IDisposable, ISavable
public struct InverseCreationDate : ISortMode<Design> public struct InverseCreationDate : ISortMode<Design>
{ {
public ReadOnlySpan<byte> Name public string Name
=> "Creation Date (Newer First)"u8; => "Creation Date (Newer First)";
public ReadOnlySpan<byte> Description public string Description
=> "In each folder, sort all subfolders lexicographically, then sort all leaves using their inverse creation date."u8; => "In each folder, sort all subfolders lexicographically, then sort all leaves using their inverse creation date.";
public IEnumerable<IPath> GetChildren(Folder f) public IEnumerable<IPath> GetChildren(Folder f)
=> f.GetSubFolders().Cast<IPath>().Concat(f.GetLeaves().OrderByDescending(l => l.Value.CreationDate)); => f.GetSubFolders().Cast<IPath>().Concat(f.GetLeaves().OrderByDescending(l => l.Value.CreationDate));
@ -77,11 +77,11 @@ public sealed class DesignFileSystem : FileSystem<Design>, IDisposable, ISavable
public struct InverseUpdateDate : ISortMode<Design> public struct InverseUpdateDate : ISortMode<Design>
{ {
public ReadOnlySpan<byte> Name public string Name
=> "Update Date (Newer First)"u8; => "Update Date (Newer First)";
public ReadOnlySpan<byte> Description public string Description
=> "In each folder, sort all subfolders lexicographically, then sort all leaves using their inverse last update date."u8; => "In each folder, sort all subfolders lexicographically, then sort all leaves using their inverse last update date.";
public IEnumerable<IPath> GetChildren(Folder f) public IEnumerable<IPath> GetChildren(Folder f)
=> f.GetSubFolders().Cast<IPath>().Concat(f.GetLeaves().OrderByDescending(l => l.Value.LastEdit)); => f.GetSubFolders().Cast<IPath>().Concat(f.GetLeaves().OrderByDescending(l => l.Value.LastEdit));
@ -114,14 +114,14 @@ public sealed class DesignFileSystem : FileSystem<Design>, IDisposable, ISavable
return; return;
case DesignChanged.Type.Deleted: case DesignChanged.Type.Deleted:
if (TryGetValue(design, out var leaf1)) if (FindLeaf(design, out var leaf1))
Delete(leaf1); Delete(leaf1);
return; return;
case DesignChanged.Type.ReloadedAll: case DesignChanged.Type.ReloadedAll:
Reload(); Reload();
return; return;
case DesignChanged.Type.Renamed when (data as RenameTransaction?)?.Old is { } oldName: case DesignChanged.Type.Renamed when (data as RenameTransaction?)?.Old is { } oldName:
if (!TryGetValue(design, out var leaf2)) if (!FindLeaf(design, out var leaf2))
return; return;
var old = oldName.FixName(); var old = oldName.FixName();
@ -150,6 +150,15 @@ public sealed class DesignFileSystem : FileSystem<Design>, IDisposable, ISavable
? (string.Empty, false) ? (string.Empty, false)
: (DesignToIdentifier(design), true); : (DesignToIdentifier(design), true);
// Search the entire filesystem for the leaf corresponding to a design.
public bool FindLeaf(Design design, [NotNullWhen(true)] out Leaf? leaf)
{
leaf = Root.GetAllDescendants(ISortMode<Design>.Lexicographical)
.OfType<Leaf>()
.FirstOrDefault(l => l.Value == design);
return leaf != null;
}
internal static void MigrateOldPaths(SaveService saveService, Dictionary<string, string> oldPaths) internal static void MigrateOldPaths(SaveService saveService, Dictionary<string, string> oldPaths)
{ {
if (oldPaths.Count == 0) if (oldPaths.Count == 0)

View file

@ -6,13 +6,12 @@ using Glamourer.GameData;
using Glamourer.Interop.Material; using Glamourer.Interop.Material;
using Glamourer.Interop.Penumbra; using Glamourer.Interop.Penumbra;
using Glamourer.Services; using Glamourer.Services;
using OtterGui.Extensions;
using Newtonsoft.Json; using Newtonsoft.Json;
using Newtonsoft.Json.Linq; using Newtonsoft.Json.Linq;
using OtterGui.Extensions;
using Penumbra.GameData.DataContainers; using Penumbra.GameData.DataContainers;
using Penumbra.GameData.Enums; using Penumbra.GameData.Enums;
namespace Glamourer.Designs; namespace Glamourer.Designs;
public sealed class DesignManager : DesignEditor public sealed class DesignManager : DesignEditor
@ -111,7 +110,6 @@ public sealed class DesignManager : DesignEditor
QuickDesign = Config.DefaultDesignSettings.ShowQuickDesignBar, QuickDesign = Config.DefaultDesignSettings.ShowQuickDesignBar,
ResetTemporarySettings = Config.DefaultDesignSettings.ResetTemporarySettings, ResetTemporarySettings = Config.DefaultDesignSettings.ResetTemporarySettings,
}; };
design.SetWriteProtected(Config.DefaultDesignSettings.Locked);
Designs.Add(design); Designs.Add(design);
Glamourer.Log.Debug($"Added new design {design.Identifier}."); Glamourer.Log.Debug($"Added new design {design.Identifier}.");
SaveService.ImmediateSave(design); SaveService.ImmediateSave(design);
@ -136,7 +134,6 @@ public sealed class DesignManager : DesignEditor
ResetTemporarySettings = Config.DefaultDesignSettings.ResetTemporarySettings, ResetTemporarySettings = Config.DefaultDesignSettings.ResetTemporarySettings,
}; };
design.SetWriteProtected(Config.DefaultDesignSettings.Locked);
Designs.Add(design); Designs.Add(design);
Glamourer.Log.Debug($"Added new design {design.Identifier} by cloning Temporary Design."); Glamourer.Log.Debug($"Added new design {design.Identifier} by cloning Temporary Design.");
SaveService.ImmediateSave(design); SaveService.ImmediateSave(design);
@ -156,7 +153,6 @@ public sealed class DesignManager : DesignEditor
Name = actualName, Name = actualName,
Index = Designs.Count, Index = Designs.Count,
}; };
design.SetWriteProtected(Config.DefaultDesignSettings.Locked);
Designs.Add(design); Designs.Add(design);
Glamourer.Log.Debug( Glamourer.Log.Debug(
$"Added new design {design.Identifier} by cloning {clone.Identifier.ToString()}."); $"Added new design {design.Identifier} by cloning {clone.Identifier.ToString()}.");
@ -229,7 +225,7 @@ public sealed class DesignManager : DesignEditor
design.Tags = design.Tags.Append(tag).OrderBy(t => t).ToArray(); design.Tags = design.Tags.Append(tag).OrderBy(t => t).ToArray();
design.LastEdit = DateTimeOffset.UtcNow; design.LastEdit = DateTimeOffset.UtcNow;
var idx = design.Tags.AsEnumerable().IndexOf(tag); var idx = design.Tags.IndexOf(tag);
SaveService.QueueSave(design); SaveService.QueueSave(design);
Glamourer.Log.Debug($"Added tag {tag} at {idx} to design {design.Identifier}."); Glamourer.Log.Debug($"Added tag {tag} at {idx} to design {design.Identifier}.");
DesignChanged.Invoke(DesignChanged.Type.AddedTag, design, new TagAddedTransaction(tag, idx)); DesignChanged.Invoke(DesignChanged.Type.AddedTag, design, new TagAddedTransaction(tag, idx));
@ -262,7 +258,7 @@ public sealed class DesignManager : DesignEditor
SaveService.QueueSave(design); SaveService.QueueSave(design);
Glamourer.Log.Debug($"Renamed tag {oldTag} at {tagIdx} to {newTag} in design {design.Identifier} and reordered tags."); Glamourer.Log.Debug($"Renamed tag {oldTag} at {tagIdx} to {newTag} in design {design.Identifier} and reordered tags.");
DesignChanged.Invoke(DesignChanged.Type.ChangedTag, design, DesignChanged.Invoke(DesignChanged.Type.ChangedTag, design,
new TagChangedTransaction(oldTag, newTag, tagIdx, design.Tags.AsEnumerable().IndexOf(newTag))); new TagChangedTransaction(oldTag, newTag, tagIdx, design.Tags.IndexOf(newTag)));
} }
/// <summary> Add an associated mod to a design. </summary> /// <summary> Add an associated mod to a design. </summary>
@ -557,7 +553,7 @@ public sealed class DesignManager : DesignEditor
try try
{ {
File.Move(SaveService.FileNames.MigrationDesignFile, File.Move(SaveService.FileNames.MigrationDesignFile,
Path.ChangeExtension(SaveService.FileNames.MigrationDesignFile, ".json.bak"), true); Path.ChangeExtension(SaveService.FileNames.MigrationDesignFile, ".json.bak"));
Glamourer.Log.Information($"Moved migrated design file {SaveService.FileNames.MigrationDesignFile} to backup file."); Glamourer.Log.Information($"Moved migrated design file {SaveService.FileNames.MigrationDesignFile} to backup file.");
} }
catch (Exception ex) catch (Exception ex)

View file

@ -1,7 +1,6 @@
using Glamourer.GameData; using Glamourer.GameData;
using Glamourer.Interop.Material; using Glamourer.Interop.Material;
using Glamourer.Interop.Penumbra; using Glamourer.Interop.Penumbra;
using Glamourer.State;
using Penumbra.GameData.Enums; using Penumbra.GameData.Enums;
namespace Glamourer.Designs.History; namespace Glamourer.Designs.History;
@ -126,10 +125,7 @@ public readonly record struct MaterialTransaction(MaterialValueIndex Index, Colo
=> older is MaterialTransaction other && Index == other.Index ? new MaterialTransaction(Index, other.Old, New) : null; => older is MaterialTransaction other && Index == other.Index ? new MaterialTransaction(Index, other.Old, New) : null;
public void Revert(IDesignEditor editor, object data) public void Revert(IDesignEditor editor, object data)
{ => ((DesignManager)editor).ChangeMaterialValue((Design)data, Index, Old);
if (editor is DesignManager e)
e.ChangeMaterialValue((Design)data, Index, Old);
}
} }
/// <remarks> Only Designs. </remarks> /// <remarks> Only Designs. </remarks>

View file

@ -10,15 +10,14 @@ public enum MetaIndex
VisorState = StateIndex.MetaVisorState, VisorState = StateIndex.MetaVisorState,
WeaponState = StateIndex.MetaWeaponState, WeaponState = StateIndex.MetaWeaponState,
ModelId = StateIndex.MetaModelId, ModelId = StateIndex.MetaModelId,
EarState = StateIndex.MetaEarState,
} }
public static class MetaExtensions public static class MetaExtensions
{ {
public static readonly IReadOnlyList<MetaIndex> AllRelevant = public static readonly IReadOnlyList<MetaIndex> AllRelevant =
[MetaIndex.Wetness, MetaIndex.HatState, MetaIndex.VisorState, MetaIndex.WeaponState, MetaIndex.EarState]; [MetaIndex.Wetness, MetaIndex.HatState, MetaIndex.VisorState, MetaIndex.WeaponState];
public const MetaFlag All = MetaFlag.Wetness | MetaFlag.HatState | MetaFlag.VisorState | MetaFlag.WeaponState | MetaFlag.EarState; public const MetaFlag All = MetaFlag.Wetness | MetaFlag.HatState | MetaFlag.VisorState | MetaFlag.WeaponState;
public static MetaFlag ToFlag(this MetaIndex index) public static MetaFlag ToFlag(this MetaIndex index)
=> index switch => index switch
@ -27,7 +26,6 @@ public static class MetaExtensions
MetaIndex.HatState => MetaFlag.HatState, MetaIndex.HatState => MetaFlag.HatState,
MetaIndex.VisorState => MetaFlag.VisorState, MetaIndex.VisorState => MetaFlag.VisorState,
MetaIndex.WeaponState => MetaFlag.WeaponState, MetaIndex.WeaponState => MetaFlag.WeaponState,
MetaIndex.EarState => MetaFlag.EarState,
_ => (MetaFlag)byte.MaxValue, _ => (MetaFlag)byte.MaxValue,
}; };
@ -38,7 +36,6 @@ public static class MetaExtensions
MetaFlag.HatState => MetaIndex.HatState, MetaFlag.HatState => MetaIndex.HatState,
MetaFlag.VisorState => MetaIndex.VisorState, MetaFlag.VisorState => MetaIndex.VisorState,
MetaFlag.WeaponState => MetaIndex.WeaponState, MetaFlag.WeaponState => MetaIndex.WeaponState,
MetaFlag.EarState => MetaIndex.EarState,
_ => (MetaIndex)byte.MaxValue, _ => (MetaIndex)byte.MaxValue,
}; };
@ -52,8 +49,6 @@ public static class MetaExtensions
yield return MetaIndex.VisorState; yield return MetaIndex.VisorState;
if (index.HasFlag(MetaFlag.WeaponState)) if (index.HasFlag(MetaFlag.WeaponState))
yield return MetaIndex.WeaponState; yield return MetaIndex.WeaponState;
if (index.HasFlag(MetaFlag.EarState))
yield return MetaIndex.EarState;
} }
public static string ToName(this MetaIndex index) public static string ToName(this MetaIndex index)
@ -63,7 +58,6 @@ public static class MetaExtensions
MetaIndex.VisorState => "Visor Toggled", MetaIndex.VisorState => "Visor Toggled",
MetaIndex.WeaponState => "Weapon Visible", MetaIndex.WeaponState => "Weapon Visible",
MetaIndex.Wetness => "Force Wetness", MetaIndex.Wetness => "Force Wetness",
MetaIndex.EarState => "Ears Visible",
_ => "Unknown Meta", _ => "Unknown Meta",
}; };
@ -74,7 +68,6 @@ public static class MetaExtensions
MetaIndex.VisorState => "Toggle the visor state of the characters head gear.", MetaIndex.VisorState => "Toggle the visor state of the characters head gear.",
MetaIndex.WeaponState => "Hide or show the characters weapons when not drawn.", MetaIndex.WeaponState => "Hide or show the characters weapons when not drawn.",
MetaIndex.Wetness => "Force the character to be wet or not.", MetaIndex.Wetness => "Force the character to be wet or not.",
MetaIndex.EarState => "Hide or show the characters ears through the head gear. (Viera only)",
_ => string.Empty, _ => string.Empty,
}; };
} }

View file

@ -22,7 +22,7 @@ public interface IDesignPredicate
: designs; : designs;
private static (Design Design, string LowerName, string Identifier, string LowerPath) Transform(Design d, DesignFileSystem fs) private static (Design Design, string LowerName, string Identifier, string LowerPath) Transform(Design d, DesignFileSystem fs)
=> (d, d.Name.Lower, d.Identifier.ToString(), fs.TryGetValue(d, out var l) ? l.FullName().ToLowerInvariant() : string.Empty); => (d, d.Name.Lower, d.Identifier.ToString(), fs.FindLeaf(d, out var l) ? l.FullName().ToLowerInvariant() : string.Empty);
} }
public static class RandomPredicate public static class RandomPredicate

View file

@ -1,16 +0,0 @@
using OtterGui.Classes;
namespace Glamourer.Events;
/// <summary>
/// Triggered when the auto-reload gear setting is changed in glamourer configuration.
/// </summary>
public sealed class AutoRedrawChanged()
: EventWrapper<bool, AutoRedrawChanged.Priority>(nameof(AutoRedrawChanged))
{
public enum Priority
{
/// <seealso cref="Api.StateApi.OnGPoseChange"/>
StateApi = int.MinValue,
}
}

View file

@ -15,8 +15,5 @@ public sealed class PenumbraReloaded()
/// <seealso cref="Interop.VisorService.Restore"/> /// <seealso cref="Interop.VisorService.Restore"/>
VisorService = 0, VisorService = 0,
/// <seealso cref="Interop.VieraEarService.Restore"/>
VieraEarService = 0,
} }
} }

View file

@ -1,22 +0,0 @@
using OtterGui.Classes;
using Penumbra.GameData.Interop;
namespace Glamourer.Events;
/// <summary>
/// Triggered when the state of viera ear visibility for any draw object is changed.
/// <list type="number">
/// <item>Parameter is the model with a changed viera ear visibility state. </item>
/// <item>Parameter is the new state. </item>
/// <item>Parameter is whether to call the original function. </item>
/// </list>
/// </summary>
public sealed class VieraEarStateChanged()
: EventWrapperRef2<Actor, bool, VieraEarStateChanged.Priority>(nameof(VieraEarStateChanged))
{
public enum Priority
{
/// <seealso cref="State.StateListener.OnVieraEarChange"/>
StateListener = 0,
}
}

View file

@ -71,7 +71,6 @@ public class Glamourer : IDalamudPlugin
sb.Append($"> **`Festival Easter-Eggs: `** {config.DisableFestivals}\n"); sb.Append($"> **`Festival Easter-Eggs: `** {config.DisableFestivals}\n");
sb.Append($"> **`Apply Entire Weapon: `** {config.ChangeEntireItem}\n"); sb.Append($"> **`Apply Entire Weapon: `** {config.ChangeEntireItem}\n");
sb.Append($"> **`Apply Associated Mods:`** {config.AlwaysApplyAssociatedMods}\n"); sb.Append($"> **`Apply Associated Mods:`** {config.AlwaysApplyAssociatedMods}\n");
sb.Append($"> **`Attach to PCP: `** {config.AttachToPcp}\n");
sb.Append($"> **`Hidden Panels: `** {config.HideDesignPanel}\n"); sb.Append($"> **`Hidden Panels: `** {config.HideDesignPanel}\n");
sb.Append($"> **`Show QDB: `** {config.Ephemeral.ShowDesignQuickBar}\n"); sb.Append($"> **`Show QDB: `** {config.Ephemeral.ShowDesignQuickBar}\n");
sb.Append($"> **`QDB Hotkey: `** {config.ToggleQuickDesignBar}\n"); sb.Append($"> **`QDB Hotkey: `** {config.ToggleQuickDesignBar}\n");

View file

@ -1,4 +1,4 @@
<Project Sdk="Dalamud.NET.Sdk/14.0.1"> <Project Sdk="Dalamud.NET.Sdk/12.0.2">
<PropertyGroup> <PropertyGroup>
<RootNamespace>Glamourer</RootNamespace> <RootNamespace>Glamourer</RootNamespace>
<AssemblyName>Glamourer</AssemblyName> <AssemblyName>Glamourer</AssemblyName>

View file

@ -8,7 +8,7 @@
"AssemblyVersion": "9.0.0.1", "AssemblyVersion": "9.0.0.1",
"RepoUrl": "https://github.com/Ottermandias/Glamourer", "RepoUrl": "https://github.com/Ottermandias/Glamourer",
"ApplicableVersion": "any", "ApplicableVersion": "any",
"DalamudApiLevel": 14, "DalamudApiLevel": 12,
"ImageUrls": null, "ImageUrls": null,
"IconUrl": "https://raw.githubusercontent.com/Ottermandias/Glamourer/master/images/icon.png" "IconUrl": "https://raw.githubusercontent.com/Ottermandias/Glamourer/master/images/icon.png"
} }

View file

@ -1,4 +1,4 @@
using Dalamud.Bindings.ImGui; using ImGuiNET;
namespace Glamourer.Gui; namespace Glamourer.Gui;

View file

@ -1,7 +1,7 @@
using Dalamud.Interface; using Dalamud.Interface;
using Dalamud.Interface.Utility; using Dalamud.Interface.Utility;
using Glamourer.GameData; using Glamourer.GameData;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Raii; using OtterGui.Raii;
using OtterGui.Text; using OtterGui.Text;

View file

@ -1,5 +1,5 @@
using Dalamud.Interface; using Dalamud.Interface;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Raii; using OtterGui.Raii;
using Penumbra.GameData.Enums; using Penumbra.GameData.Enums;

View file

@ -1,7 +1,7 @@
using Dalamud.Interface.Textures.TextureWraps; using Dalamud.Interface.Textures.TextureWraps;
using Glamourer.GameData; using Glamourer.GameData;
using Glamourer.Unlocks; using Glamourer.Unlocks;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Extensions; using OtterGui.Extensions;
using OtterGui.Raii; using OtterGui.Raii;
@ -35,7 +35,7 @@ public partial class CustomizationDrawer
var hasIcon = icon.TryGetWrap(out var wrap, out _); var hasIcon = icon.TryGetWrap(out var wrap, out _);
using (_ = ImRaii.Disabled(_locked || _currentIndex is CustomizeIndex.Face && _lockedRedraw)) using (_ = ImRaii.Disabled(_locked || _currentIndex is CustomizeIndex.Face && _lockedRedraw))
{ {
if (ImGui.ImageButton(wrap?.Handle ?? icon.GetWrapOrEmpty().Handle, _iconSize)) if (ImGui.ImageButton(wrap?.ImGuiHandle ?? icon.GetWrapOrEmpty().ImGuiHandle, _iconSize))
{ {
ImGui.OpenPopup(IconSelectorPopup); ImGui.OpenPopup(IconSelectorPopup);
} }
@ -89,7 +89,7 @@ public partial class CustomizationDrawer
: ImRaii.PushColor(ImGuiCol.Button, ColorId.FavoriteStarOn.Value(), isFavorite); : ImRaii.PushColor(ImGuiCol.Button, ColorId.FavoriteStarOn.Value(), isFavorite);
var hasIcon = icon.TryGetWrap(out var wrap, out var _); var hasIcon = icon.TryGetWrap(out var wrap, out var _);
if (ImGui.ImageButton(wrap?.Handle ?? icon.GetWrapOrEmpty().Handle, _iconSize)) if (ImGui.ImageButton(wrap?.ImGuiHandle ?? icon.GetWrapOrEmpty().ImGuiHandle, _iconSize))
{ {
UpdateValue(custom.Value); UpdateValue(custom.Value);
ImGui.CloseCurrentPopup(); ImGui.CloseCurrentPopup();
@ -215,7 +215,7 @@ public partial class CustomizationDrawer
hasIcon = icon.TryGetWrap(out wrap, out _); hasIcon = icon.TryGetWrap(out wrap, out _);
} }
if (ImGui.ImageButton(wrap?.Handle ?? icon.GetWrapOrEmpty().Handle, _iconSize, Vector2.Zero, Vector2.One, if (ImGui.ImageButton(wrap?.ImGuiHandle ?? icon.GetWrapOrEmpty().ImGuiHandle, _iconSize, Vector2.Zero, Vector2.One,
(int)ImGui.GetStyle().FramePadding.X, Vector4.Zero, enabled ? Vector4.One : _redTint)) (int)ImGui.GetStyle().FramePadding.X, Vector4.Zero, enabled ? Vector4.One : _redTint))
{ {
_customize.Set(featureIdx, enabled ? CustomizeValue.Zero : CustomizeValue.Max); _customize.Set(featureIdx, enabled ? CustomizeValue.Zero : CustomizeValue.Max);

View file

@ -1,4 +1,4 @@
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Raii; using OtterGui.Raii;
using OtterGuiInternal; using OtterGuiInternal;

View file

@ -4,7 +4,7 @@ using Dalamud.Plugin.Services;
using Glamourer.GameData; using Glamourer.GameData;
using Glamourer.Services; using Glamourer.Services;
using Glamourer.Unlocks; using Glamourer.Unlocks;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Raii; using OtterGui.Raii;
using Penumbra.GameData.Enums; using Penumbra.GameData.Enums;

View file

@ -3,7 +3,7 @@ using Glamourer.Designs;
using Glamourer.GameData; using Glamourer.GameData;
using Glamourer.Interop.PalettePlus; using Glamourer.Interop.PalettePlus;
using Glamourer.State; using Glamourer.State;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Raii; using OtterGui.Raii;
using OtterGui.Services; using OtterGui.Services;
@ -287,13 +287,13 @@ public class CustomizeParameterDrawer(Configuration config, PaletteImport import
} }
private ImGuiColorEditFlags GetFlags() private ImGuiColorEditFlags GetFlags()
=> Format | Display | ImGuiColorEditFlags.Hdr | ImGuiColorEditFlags.NoOptions; => Format | Display | ImGuiColorEditFlags.HDR | ImGuiColorEditFlags.NoOptions;
private ImGuiColorEditFlags Format private ImGuiColorEditFlags Format
=> config.UseFloatForColors ? ImGuiColorEditFlags.Float : ImGuiColorEditFlags.Uint8; => config.UseFloatForColors ? ImGuiColorEditFlags.Float : ImGuiColorEditFlags.Uint8;
private ImGuiColorEditFlags Display private ImGuiColorEditFlags Display
=> config.UseRgbForColors ? ImGuiColorEditFlags.DisplayRgb : ImGuiColorEditFlags.DisplayHsv; => config.UseRgbForColors ? ImGuiColorEditFlags.DisplayRGB : ImGuiColorEditFlags.DisplayHSV;
private ImRaii.IEndObject EnsureSize() private ImRaii.IEndObject EnsureSize()
{ {

View file

@ -5,11 +5,12 @@ using Glamourer.Designs;
using Glamourer.Designs.History; using Glamourer.Designs.History;
using Glamourer.Designs.Special; using Glamourer.Designs.Special;
using Glamourer.Events; using Glamourer.Events;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Classes; using OtterGui.Classes;
using OtterGui.Extensions; using OtterGui.Extensions;
using OtterGui.Log; using OtterGui.Log;
using OtterGui.Services;
using OtterGui.Widgets; using OtterGui.Widgets;
namespace Glamourer.Gui; namespace Glamourer.Gui;
@ -21,8 +22,8 @@ public abstract class DesignComboBase : FilterComboCache<Tuple<IDesignStandIn, s
protected readonly DesignColors DesignColors; protected readonly DesignColors DesignColors;
protected readonly TabSelected TabSelected; protected readonly TabSelected TabSelected;
protected float InnerWidth; protected float InnerWidth;
public bool IsListening { get; protected set; }
private IDesignStandIn? _currentDesign; private IDesignStandIn? _currentDesign;
private bool _isCurrentSelectionDirty;
protected DesignComboBase(Func<IReadOnlyList<Tuple<IDesignStandIn, string>>> generator, Logger log, DesignChanged designChanged, protected DesignComboBase(Func<IReadOnlyList<Tuple<IDesignStandIn, string>>> generator, Logger log, DesignChanged designChanged,
TabSelected tabSelected, EphemeralConfig config, DesignColors designColors) TabSelected tabSelected, EphemeralConfig config, DesignColors designColors)
@ -33,6 +34,7 @@ public abstract class DesignComboBase : FilterComboCache<Tuple<IDesignStandIn, s
Config = config; Config = config;
DesignColors = designColors; DesignColors = designColors;
DesignChanged.Subscribe(OnDesignChanged, DesignChanged.Priority.DesignCombo); DesignChanged.Subscribe(OnDesignChanged, DesignChanged.Priority.DesignCombo);
IsListening = true;
} }
public bool Incognito public bool Incognito
@ -44,6 +46,25 @@ public abstract class DesignComboBase : FilterComboCache<Tuple<IDesignStandIn, s
GC.SuppressFinalize(this); GC.SuppressFinalize(this);
} }
public void StopListening()
{
if (!IsListening)
return;
DesignChanged.Unsubscribe(OnDesignChanged);
IsListening = false;
}
public void StartListening()
{
if (IsListening)
return;
DesignChanged.Subscribe(OnDesignChanged, DesignChanged.Priority.DesignCombo);
OnDesignChanged(DesignChanged.Type.Deleted, null);
IsListening = true;
}
protected override bool DrawSelectable(int globalIdx, bool selected) protected override bool DrawSelectable(int globalIdx, bool selected)
{ {
var (design, path) = Items[globalIdx]; var (design, path) = Items[globalIdx];
@ -85,10 +106,16 @@ public abstract class DesignComboBase : FilterComboCache<Tuple<IDesignStandIn, s
DrawRightAligned(quickDesign.ResolveName(false), "[Nothing]", DesignColors.MissingColor); DrawRightAligned(quickDesign.ResolveName(false), "[Nothing]", DesignColors.MissingColor);
} }
protected override int UpdateCurrentSelected(int currentSelected)
{
CurrentSelectionIdx = Items.IndexOf(p => _currentDesign == p.Item1);
UpdateSelection(CurrentSelectionIdx >= 0 ? Items[CurrentSelectionIdx] : null);
return CurrentSelectionIdx;
}
protected bool Draw(IDesignStandIn? currentDesign, string? label, float width) protected bool Draw(IDesignStandIn? currentDesign, string? label, float width)
{ {
_currentDesign = currentDesign; _currentDesign = currentDesign;
UpdateCurrentSelection();
InnerWidth = 400 * ImGuiHelpers.GlobalScale; InnerWidth = 400 * ImGuiHelpers.GlobalScale;
var name = label ?? "Select Design Here..."; var name = label ?? "Select Design Here...";
bool ret; bool ret;
@ -123,19 +150,15 @@ public abstract class DesignComboBase : FilterComboCache<Tuple<IDesignStandIn, s
return filter.IsContained(path) || filter.IsContained(design.ResolveName(false)); return filter.IsContained(path) || filter.IsContained(design.ResolveName(false));
} }
protected override void OnMouseWheel(string preview, ref int _2, int steps) private void OnDesignChanged(DesignChanged.Type type, Design? _1, ITransaction? _2 = null)
{ {
if (!ReferenceEquals(_currentDesign, CurrentSelection?.Item1)) switch (type)
CurrentSelectionIdx = -1;
base.OnMouseWheel(preview, ref _2, steps);
}
private void UpdateCurrentSelection()
{ {
if (!_isCurrentSelectionDirty) case DesignChanged.Type.Created:
return; case DesignChanged.Type.Renamed:
case DesignChanged.Type.ChangedColor:
case DesignChanged.Type.Deleted:
case DesignChanged.Type.QuickDesignBar:
var priorState = IsInitialized; var priorState = IsInitialized;
if (priorState) if (priorState)
Cleanup(); Cleanup();
@ -156,27 +179,8 @@ public abstract class DesignComboBase : FilterComboCache<Tuple<IDesignStandIn, s
if (!priorState) if (!priorState)
Cleanup(); Cleanup();
_isCurrentSelectionDirty = false; break;
} }
protected override int UpdateCurrentSelected(int currentSelected)
{
CurrentSelectionIdx = Items.IndexOf(p => _currentDesign == p.Item1);
UpdateSelection(CurrentSelectionIdx >= 0 ? Items[CurrentSelectionIdx] : null);
return CurrentSelectionIdx;
}
private void OnDesignChanged(DesignChanged.Type type, Design? _1, ITransaction? _2 = null)
{
_isCurrentSelectionDirty = type switch
{
DesignChanged.Type.Created => true,
DesignChanged.Type.Renamed => true,
DesignChanged.Type.ChangedColor => true,
DesignChanged.Type.Deleted => true,
DesignChanged.Type.QuickDesignBar => true,
_ => _isCurrentSelectionDirty,
};
} }
private void QuickSelectedDesignTooltip(IDesignStandIn? design) private void QuickSelectedDesignTooltip(IDesignStandIn? design)
@ -194,7 +198,7 @@ public abstract class DesignComboBase : FilterComboCache<Tuple<IDesignStandIn, s
ImGui.TextUnformatted("Currently resolving to "); ImGui.TextUnformatted("Currently resolving to ");
using var color = ImRaii.PushColor(ImGuiCol.Text, DesignColors.GetColor(linkedDesign)); using var color = ImRaii.PushColor(ImGuiCol.Text, DesignColors.GetColor(linkedDesign));
ImGui.SameLine(0, 0); ImGui.SameLine(0, 0);
ImGui.TextUnformatted(linkedDesign.Name.Text); ImGui.TextUnformatted(linkedDesign.Name);
} }
else else
{ {
@ -244,7 +248,8 @@ public abstract class DesignCombo : DesignComboBase
public sealed class QuickDesignCombo : DesignCombo public sealed class QuickDesignCombo : DesignCombo
{ {
public QuickDesignCombo(DesignFileSystem fileSystem, public QuickDesignCombo(DesignManager designs,
DesignFileSystem fileSystem,
Logger log, Logger log,
DesignChanged designChanged, DesignChanged designChanged,
TabSelected tabSelected, TabSelected tabSelected,
@ -252,9 +257,9 @@ public sealed class QuickDesignCombo : DesignCombo
DesignColors designColors) DesignColors designColors)
: base(log, designChanged, tabSelected, config, designColors, () => : base(log, designChanged, tabSelected, config, designColors, () =>
[ [
.. fileSystem .. designs.Designs
.Where(kvp => kvp.Key.QuickDesign) .Where(d => d.QuickDesign)
.Select(kvp => new Tuple<IDesignStandIn, string>(kvp.Key, kvp.Value.FullName())) .Select(d => new Tuple<IDesignStandIn, string>(d, fileSystem.FindLeaf(d, out var l) ? l.FullName() : string.Empty))
.OrderBy(d => d.Item2), .OrderBy(d => d.Item2),
]) ])
{ {
@ -295,6 +300,7 @@ public sealed class QuickDesignCombo : DesignCombo
} }
public sealed class LinkDesignCombo( public sealed class LinkDesignCombo(
DesignManager designs,
DesignFileSystem fileSystem, DesignFileSystem fileSystem,
Logger log, Logger log,
DesignChanged designChanged, DesignChanged designChanged,
@ -303,8 +309,8 @@ public sealed class LinkDesignCombo(
DesignColors designColors) DesignColors designColors)
: DesignCombo(log, designChanged, tabSelected, config, designColors, () => : DesignCombo(log, designChanged, tabSelected, config, designColors, () =>
[ [
.. fileSystem .. designs.Designs
.Select(kvp => new Tuple<IDesignStandIn, string>(kvp.Key, kvp.Value.FullName())) .Select(d => new Tuple<IDesignStandIn, string>(d, fileSystem.FindLeaf(d, out var l) ? l.FullName() : string.Empty))
.OrderBy(d => d.Item2), .OrderBy(d => d.Item2),
]); ]);
@ -318,8 +324,8 @@ public sealed class RandomDesignCombo(
DesignColors designColors) DesignColors designColors)
: DesignCombo(log, designChanged, tabSelected, config, designColors, () => : DesignCombo(log, designChanged, tabSelected, config, designColors, () =>
[ [
.. fileSystem .. designs.Designs
.Select(kvp => new Tuple<IDesignStandIn, string>(kvp.Key, kvp.Value.FullName())) .Select(d => new Tuple<IDesignStandIn, string>(d, fileSystem.FindLeaf(d, out var l) ? l.FullName() : string.Empty))
.OrderBy(d => d.Item2), .OrderBy(d => d.Item2),
]) ])
{ {
@ -345,6 +351,7 @@ public sealed class RandomDesignCombo(
} }
public sealed class SpecialDesignCombo( public sealed class SpecialDesignCombo(
DesignManager designs,
DesignFileSystem fileSystem, DesignFileSystem fileSystem,
TabSelected tabSelected, TabSelected tabSelected,
DesignColors designColors, DesignColors designColors,
@ -354,8 +361,8 @@ public sealed class SpecialDesignCombo(
EphemeralConfig config, EphemeralConfig config,
RandomDesignGenerator rng, RandomDesignGenerator rng,
QuickSelectedDesign quickSelectedDesign) QuickSelectedDesign quickSelectedDesign)
: DesignComboBase(() => fileSystem : DesignComboBase(() => designs.Designs
.Select(kvp => new Tuple<IDesignStandIn, string>(kvp.Key, kvp.Value.FullName())) .Select(d => new Tuple<IDesignStandIn, string>(d, fileSystem.FindLeaf(d, out var l) ? l.FullName() : string.Empty))
.OrderBy(d => d.Item2) .OrderBy(d => d.Item2)
.Prepend(new Tuple<IDesignStandIn, string>(new RandomDesign(rng), string.Empty)) .Prepend(new Tuple<IDesignStandIn, string>(new RandomDesign(rng), string.Empty))
.Prepend(new Tuple<IDesignStandIn, string>(quickSelectedDesign, string.Empty)) .Prepend(new Tuple<IDesignStandIn, string>(quickSelectedDesign, string.Empty))
@ -373,3 +380,29 @@ public sealed class SpecialDesignCombo(
autoDesignManager.AddDesign(set, CurrentSelection!.Item1); autoDesignManager.AddDesign(set, CurrentSelection!.Item1);
} }
} }
public class DesignComboWrapper(ServiceManager services)
{
public readonly IReadOnlyList<DesignComboBase> Combos = services.GetServicesImplementing<DesignComboBase>().ToArray();
internal DesignComboListener StopListening()
{
var list = new List<DesignComboBase>(Combos.Count);
foreach (var combo in Combos.Where(c => c.IsListening))
{
combo.StopListening();
list.Add(combo);
}
return new DesignComboListener(list);
}
internal readonly struct DesignComboListener(List<DesignComboBase> combos) : IDisposable
{
public void Dispose()
{
foreach (var combo in combos)
combo.StartListening();
}
}
}

View file

@ -8,7 +8,7 @@ using Glamourer.Automation;
using Glamourer.Designs; using Glamourer.Designs;
using Glamourer.Interop.Penumbra; using Glamourer.Interop.Penumbra;
using Glamourer.State; using Glamourer.State;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui.Classes; using OtterGui.Classes;
using OtterGui.Text; using OtterGui.Text;
using Penumbra.GameData.Actors; using Penumbra.GameData.Actors;
@ -64,7 +64,6 @@ public sealed class DesignQuickBar : Window, IDisposable
IsOpen = _config.Ephemeral.ShowDesignQuickBar; IsOpen = _config.Ephemeral.ShowDesignQuickBar;
DisableWindowSounds = true; DisableWindowSounds = true;
Size = Vector2.Zero; Size = Vector2.Zero;
RespectCloseHotkey = false;
} }
public void Dispose() public void Dispose()
@ -539,8 +538,6 @@ public sealed class DesignQuickBar : Window, IDisposable
if (_config.QdbButtons.HasFlag(QdbButtons.RevertAdvancedCustomization)) if (_config.QdbButtons.HasFlag(QdbButtons.RevertAdvancedCustomization))
++_numButtons; ++_numButtons;
if (_config.QdbButtons.HasFlag(QdbButtons.RevertAdvancedDyes))
++_numButtons;
if (_config.QdbButtons.HasFlag(QdbButtons.RevertCustomize)) if (_config.QdbButtons.HasFlag(QdbButtons.RevertCustomize))
++_numButtons; ++_numButtons;
if (_config.QdbButtons.HasFlag(QdbButtons.RevertEquip)) if (_config.QdbButtons.HasFlag(QdbButtons.RevertEquip))

View file

@ -1,7 +1,7 @@
using Dalamud.Plugin.Services; using Dalamud.Plugin.Services;
using Glamourer.Services; using Glamourer.Services;
using Glamourer.Unlocks; using Glamourer.Unlocks;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using Lumina.Excel.Sheets; using Lumina.Excel.Sheets;
using OtterGui; using OtterGui;
using OtterGui.Classes; using OtterGui.Classes;

View file

@ -1,83 +0,0 @@
using Glamourer.Services;
using Penumbra.GameData.Enums;
using Penumbra.GameData.Structs;
namespace Glamourer.Gui.Equipment;
[InlineArray(13)]
public struct EquipItemSlotCache
{
private EquipItem _element;
public EquipItem Dragged
{
get => this[^1];
set => this[^1] = value;
}
public void Clear()
=> ((Span<EquipItem>)this).Clear();
public EquipItem this[EquipSlot slot]
{
get => this[(int)slot.ToIndex()];
set => this[(int)slot.ToIndex()] = value;
}
public void Update(ItemManager items, in EquipItem item, EquipSlot startSlot)
{
if (item.Id == Dragged.Id && item.Type == Dragged.Type)
return;
switch (startSlot)
{
case EquipSlot.MainHand:
{
Clear();
this[EquipSlot.MainHand] = item;
if (item.Type is FullEquipType.Sword)
this[EquipSlot.OffHand] = items.FindClosestShield(item.ItemId, out var shield) ? shield : default;
else
this[EquipSlot.OffHand] = items.ItemData.Secondary.GetValueOrDefault(item.ItemId);
break;
}
case EquipSlot.OffHand:
{
Clear();
if (item.Type is FullEquipType.Shield)
this[EquipSlot.MainHand] = items.FindClosestSword(item.ItemId, out var sword) ? sword : default;
else
this[EquipSlot.MainHand] = items.ItemData.Primary.GetValueOrDefault(item.ItemId);
this[EquipSlot.OffHand] = item;
break;
}
default:
{
this[EquipSlot.MainHand] = default;
this[EquipSlot.OffHand] = default;
foreach (var slot in EquipSlotExtensions.EqdpSlots)
{
if (startSlot == slot)
{
this[slot] = item;
continue;
}
var slotItem = items.Identify(slot, item.PrimaryId, item.Variant);
if (!slotItem.Valid || slotItem.ItemId.Id is not 0 != item.ItemId.Id is not 0)
{
slotItem = items.Identify(EquipSlot.OffHand, item.PrimaryId, item.SecondaryId, 1, item.Type);
if (slotItem.ItemId.Id is not 0 != item.ItemId.Id is not 0)
slotItem = default;
}
this[slot] = slotItem;
}
break;
}
}
Dragged = item;
}
}

View file

@ -5,7 +5,7 @@ using Glamourer.Events;
using Glamourer.Gui.Materials; using Glamourer.Gui.Materials;
using Glamourer.Services; using Glamourer.Services;
using Glamourer.Unlocks; using Glamourer.Unlocks;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui.Extensions; using OtterGui.Extensions;
using OtterGui.Raii; using OtterGui.Raii;
using OtterGui.Text; using OtterGui.Text;
@ -38,8 +38,6 @@ public class EquipmentDrawer
private float _requiredComboWidth; private float _requiredComboWidth;
private Stain? _draggedStain; private Stain? _draggedStain;
private EquipItemSlotCache _draggedItem;
private EquipSlot _dragTarget;
public EquipmentDrawer(FavoriteManager favorites, IDataManager gameData, ItemManager items, TextureService textures, public EquipmentDrawer(FavoriteManager favorites, IDataManager gameData, ItemManager items, TextureService textures,
Configuration config, GPoseService gPose, AdvancedDyePopup advancedDyes, ItemCopyService itemCopy) Configuration config, GPoseService gPose, AdvancedDyePopup advancedDyes, ItemCopyService itemCopy)
@ -82,7 +80,6 @@ public class EquipmentDrawer
_requiredComboWidth = _requiredComboWidthUnscaled * ImGuiHelpers.GlobalScale; _requiredComboWidth = _requiredComboWidthUnscaled * ImGuiHelpers.GlobalScale;
_advancedMaterialColor = ColorId.AdvancedDyeActive.Value(); _advancedMaterialColor = ColorId.AdvancedDyeActive.Value();
_dragTarget = EquipSlot.Unknown;
} }
private bool VerifyRestrictedGear(EquipDrawData data) private bool VerifyRestrictedGear(EquipDrawData data)
@ -432,7 +429,7 @@ public class EquipmentDrawer
using var dragSource = ImUtf8.DragDropSource(); using var dragSource = ImUtf8.DragDropSource();
if (dragSource.Success) if (dragSource.Success)
{ {
DragDropSource.SetPayload("stainDragDrop"u8); if (DragDropSource.SetPayload("stainDragDrop"u8))
_draggedStain = stain; _draggedStain = stain;
ImUtf8.Text($"Dragging {stain.Name}..."); ImUtf8.Text($"Dragging {stain.Name}...");
} }
@ -458,7 +455,6 @@ public class EquipmentDrawer
using var disabled = ImRaii.Disabled(data.Locked); using var disabled = ImRaii.Disabled(data.Locked);
var change = combo.Draw(data.CurrentItem.Name, data.CurrentItem.ItemId, small ? _comboLength - ImGui.GetFrameHeight() : _comboLength, var change = combo.Draw(data.CurrentItem.Name, data.CurrentItem.ItemId, small ? _comboLength - ImGui.GetFrameHeight() : _comboLength,
_requiredComboWidth); _requiredComboWidth);
DrawGearDragDrop(data);
if (change) if (change)
data.SetItem(combo.CurrentSelection); data.SetItem(combo.CurrentSelection);
else if (combo.CustomVariant.Id > 0) else if (combo.CustomVariant.Id > 0)
@ -499,50 +495,6 @@ public class EquipmentDrawer
data.SetItem(item); data.SetItem(item);
} }
private void DrawGearDragDrop(in EquipDrawData data)
{
if (data.CurrentItem.Valid)
{
using var dragSource = ImUtf8.DragDropSource();
if (dragSource.Success)
{
DragDropSource.SetPayload("equipDragDrop"u8);
_draggedItem.Update(_items, data.CurrentItem, data.Slot);
}
}
using var dragTarget = ImUtf8.DragDropTarget();
if (!dragTarget)
return;
var item = _draggedItem[data.Slot];
if (!item.Valid)
return;
_dragTarget = data.Slot;
if (!dragTarget.IsDropping("equipDragDrop"u8))
return;
data.SetItem(item);
_draggedItem.Clear();
}
public unsafe void DrawDragDropTooltip()
{
var payload = ImGui.GetDragDropPayload().Handle;
if (payload is null)
return;
if (!MemoryMarshal.CreateReadOnlySpanFromNullTerminated((byte*)Unsafe.AsPointer(ref payload->DataType_0)).SequenceEqual("equipDragDrop"u8))
return;
using var tt = ImUtf8.Tooltip();
if (_dragTarget is EquipSlot.Unknown)
ImUtf8.Text($"Dragging {_draggedItem.Dragged.Name}...");
else
ImUtf8.Text($"Converting to {_draggedItem[_dragTarget].Name}...");
}
private static bool ResetOrClear<T>(bool locked, bool clicked, bool allowRevert, bool allowClear, private static bool ResetOrClear<T>(bool locked, bool clicked, bool allowRevert, bool allowClear,
in T currentItem, in T revertItem, in T clearItem, out T? item) where T : IEquatable<T> in T currentItem, in T revertItem, in T clearItem, out T? item) where T : IEquatable<T>
{ {
@ -594,7 +546,6 @@ public class EquipmentDrawer
else if (combo.CustomVariant.Id > 0 && (drawAll || ItemData.ConvertWeaponId(combo.CustomSetId) == mainhand.CurrentItem.Type)) else if (combo.CustomVariant.Id > 0 && (drawAll || ItemData.ConvertWeaponId(combo.CustomSetId) == mainhand.CurrentItem.Type))
changedItem = _items.Identify(mainhand.Slot, combo.CustomSetId, combo.CustomWeaponId, combo.CustomVariant); changedItem = _items.Identify(mainhand.Slot, combo.CustomSetId, combo.CustomWeaponId, combo.CustomVariant);
_itemCopy.HandleCopyPaste(mainhand); _itemCopy.HandleCopyPaste(mainhand);
DrawGearDragDrop(mainhand);
if (ResetOrClear(mainhand.Locked || unknown, open, mainhand.AllowRevert, false, mainhand.CurrentItem, mainhand.GameItem, if (ResetOrClear(mainhand.Locked || unknown, open, mainhand.AllowRevert, false, mainhand.CurrentItem, mainhand.GameItem,
default, out var c)) default, out var c))
@ -638,7 +589,6 @@ public class EquipmentDrawer
else if (combo.CustomVariant.Id > 0 && ItemData.ConvertWeaponId(combo.CustomSetId) == offhand.CurrentItem.Type) else if (combo.CustomVariant.Id > 0 && ItemData.ConvertWeaponId(combo.CustomSetId) == offhand.CurrentItem.Type)
offhand.SetItem(_items.Identify(mainhand.Slot, combo.CustomSetId, combo.CustomWeaponId, combo.CustomVariant)); offhand.SetItem(_items.Identify(mainhand.Slot, combo.CustomSetId, combo.CustomWeaponId, combo.CustomVariant));
_itemCopy.HandleCopyPaste(offhand); _itemCopy.HandleCopyPaste(offhand);
DrawGearDragDrop(offhand);
var defaultOffhand = _items.GetDefaultOffhand(mainhand.CurrentItem); var defaultOffhand = _items.GetDefaultOffhand(mainhand.CurrentItem);
if (ResetOrClear(locked, clear, offhand.AllowRevert, true, offhand.CurrentItem, offhand.GameItem, defaultOffhand, out var item)) if (ResetOrClear(locked, clear, offhand.AllowRevert, true, offhand.CurrentItem, offhand.GameItem, defaultOffhand, out var item))

View file

@ -2,7 +2,7 @@
using Dalamud.Interface.Utility; using Dalamud.Interface.Utility;
using Dalamud.Interface.Utility.Raii; using Dalamud.Interface.Utility.Raii;
using Glamourer.Unlocks; using Glamourer.Unlocks;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui.Widgets; using OtterGui.Widgets;
using Penumbra.GameData.DataContainers; using Penumbra.GameData.DataContainers;
using Penumbra.GameData.Structs; using Penumbra.GameData.Structs;

View file

@ -1,7 +1,7 @@
using Dalamud.Plugin.Services; using Dalamud.Plugin.Services;
using Glamourer.Services; using Glamourer.Services;
using Glamourer.Unlocks; using Glamourer.Unlocks;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using Lumina.Excel.Sheets; using Lumina.Excel.Sheets;
using OtterGui.Classes; using OtterGui.Classes;
using OtterGui.Extensions; using OtterGui.Extensions;

View file

@ -1,5 +1,5 @@
using Glamourer.Services; using Glamourer.Services;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui.Services; using OtterGui.Services;
using Penumbra.GameData.DataContainers; using Penumbra.GameData.DataContainers;
using Penumbra.GameData.Enums; using Penumbra.GameData.Enums;

View file

@ -1,6 +1,6 @@
using Glamourer.Services; using Glamourer.Services;
using Glamourer.Unlocks; using Glamourer.Unlocks;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui.Classes; using OtterGui.Classes;
using OtterGui.Extensions; using OtterGui.Extensions;
using OtterGui.Log; using OtterGui.Log;

View file

@ -3,7 +3,7 @@ using Dalamud.Interface.Utility;
using Dalamud.Interface.Windowing; using Dalamud.Interface.Windowing;
using Dalamud.Plugin.Services; using Dalamud.Plugin.Services;
using Glamourer.Gui.Materials; using Glamourer.Gui.Materials;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Raii; using OtterGui.Raii;

View file

@ -43,8 +43,6 @@ public class GlamourerChangelog
Add1_3_7_0(Changelog); Add1_3_7_0(Changelog);
Add1_3_8_0(Changelog); Add1_3_8_0(Changelog);
Add1_4_0_0(Changelog); Add1_4_0_0(Changelog);
Add1_5_0_0(Changelog);
Add1_5_1_0(Changelog);
} }
private (int, ChangeLogDisplayType) ConfigData() private (int, ChangeLogDisplayType) ConfigData()
@ -65,29 +63,6 @@ public class GlamourerChangelog
} }
} }
private static void Add1_5_1_0(Changelog log)
=> log.NextVersion("Version 1.5.1.0")
.RegisterHighlight("Added support for Penumbras PCP functionality to add the current state of the character as a design.")
.RegisterEntry("On import, a design for the PCP is created and, if possible, applied to the character.", 1)
.RegisterEntry("No automation is assigned.", 1)
.RegisterEntry("Finer control about this can be found in the settings.", 1)
.RegisterEntry("Fixed an issue with static visors not toggling through Glamourer (1.5.0.7).")
.RegisterEntry("The advanced dye slot combo now contains glasses (1.5.0.7).")
.RegisterEntry("Several fixes for patch-related issues (1.5.0.1 - 1.5.0.6");
private static void Add1_5_0_0(Changelog log)
=> log.NextVersion("Version 1.5.0.0")
.RegisterImportant("Updated for game version 7.30 and Dalamud API13, which uses a new GUI backend. Some things may not work as expected. Please let me know any issues you encounter.")
.RegisterHighlight("Added the new Viera Ears state to designs. Old designs will not apply the state.")
.RegisterHighlight("Added the option to make newly created designs write-protected by default to the design defaults.")
.RegisterEntry("Fixed issues with reverting state and IPC.")
.RegisterEntry("Fixed an issue when using the mousewheel to scroll through designs (1.4.0.3).")
.RegisterEntry("Fixed an issue with invalid bonus items (1.4.0.3).")
.RegisterHighlight("Added drag & drop of equipment pieces which will try to match the corresponding model IDs in other slots if possible (1.4.0.2).")
.RegisterEntry("Heavily optimized some issues when having many designs and creating new ones or updating them (1.4.0.2)")
.RegisterEntry("Fixed an issue with staining templates (1.4.0.1).")
.RegisterEntry("Fixed an issue with the QDB buttons not counting correctly (1.4.0.1).");
private static void Add1_4_0_0(Changelog log) private static void Add1_4_0_0(Changelog log)
=> log.NextVersion("Version 1.4.0.0") => log.NextVersion("Version 1.4.0.0")
.RegisterHighlight("The design selector width is now draggable within certain restrictions that depend on the total window width.") .RegisterHighlight("The design selector width is now draggable within certain restrictions that depend on the total window width.")

View file

@ -12,7 +12,7 @@ using Glamourer.Gui.Tabs.NpcTab;
using Glamourer.Gui.Tabs.SettingsTab; using Glamourer.Gui.Tabs.SettingsTab;
using Glamourer.Gui.Tabs.UnlocksTab; using Glamourer.Gui.Tabs.UnlocksTab;
using Glamourer.Interop.Penumbra; using Glamourer.Interop.Penumbra;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Classes; using OtterGui.Classes;
using OtterGui.Custom; using OtterGui.Custom;
@ -102,8 +102,6 @@ public class MainWindow : Window, IDisposable
SelectTab = _config.Ephemeral.SelectedTab; SelectTab = _config.Ephemeral.SelectedTab;
_event.Subscribe(OnTabSelected, TabSelected.Priority.MainWindow); _event.Subscribe(OnTabSelected, TabSelected.Priority.MainWindow);
IsOpen = _config.OpenWindowAtStart; IsOpen = _config.OpenWindowAtStart;
_penumbra.DrawSettingsSection += Settings.DrawPenumbraIntegrationSettings;
} }
public void OpenSettings() public void OpenSettings()
@ -122,10 +120,7 @@ public class MainWindow : Window, IDisposable
} }
public void Dispose() public void Dispose()
{ => _event.Unsubscribe(OnTabSelected);
_event.Unsubscribe(OnTabSelected);
_penumbra.DrawSettingsSection -= Settings.DrawPenumbraIntegrationSettings;
}
public override void Draw() public override void Draw()
{ {

View file

@ -8,7 +8,7 @@ using FFXIVClientStructs.Interop;
using Glamourer.Designs; using Glamourer.Designs;
using Glamourer.Interop.Material; using Glamourer.Interop.Material;
using Glamourer.State; using Glamourer.State;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui.Raii; using OtterGui.Raii;
using OtterGui.Services; using OtterGui.Services;
using OtterGui.Text; using OtterGui.Text;
@ -91,7 +91,7 @@ public sealed unsafe class AdvancedDyePopup(
var modelHandle = model == null ? null : model->ModelResourceHandle; var modelHandle = model == null ? null : model->ModelResourceHandle;
var path = materialHandle == null var path = materialHandle == null
? string.Empty ? string.Empty
: ByteString.FromSpanUnsafe(materialHandle->FileName.AsSpan(), true).ToString(); : ByteString.FromSpanUnsafe(materialHandle->ResourceHandle.FileName.AsSpan(), true).ToString();
var gamePath = modelHandle == null var gamePath = modelHandle == null
? string.Empty ? string.Empty
: modelHandle->GetMaterialFileNameBySlot(index.MaterialIndex).ToString(); : modelHandle->GetMaterialFileNameBySlot(index.MaterialIndex).ToString();

View file

@ -3,7 +3,7 @@ using Dalamud.Interface.Utility;
using Dalamud.Interface.Utility.Raii; using Dalamud.Interface.Utility.Raii;
using Glamourer.Designs; using Glamourer.Designs;
using Glamourer.Interop.Material; using Glamourer.Interop.Material;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Services; using OtterGui.Services;
using OtterGui.Text; using OtterGui.Text;
@ -18,6 +18,7 @@ public class MaterialDrawer(DesignManager _designManager, Configuration _config)
public const float GlossWidth = 100; public const float GlossWidth = 100;
public const float SpecularStrengthWidth = 125; public const float SpecularStrengthWidth = 125;
private EquipSlot _newSlot = EquipSlot.Head;
private int _newMaterialIdx; private int _newMaterialIdx;
private int _newRowIdx; private int _newRowIdx;
private MaterialValueIndex _newKey = MaterialValueIndex.FromSlot(EquipSlot.Head); private MaterialValueIndex _newKey = MaterialValueIndex.FromSlot(EquipSlot.Head);
@ -177,42 +178,14 @@ public class MaterialDrawer(DesignManager _designManager, Configuration _config)
public sealed class MaterialSlotCombo; public sealed class MaterialSlotCombo;
private void DrawSlotCombo()
{
var width = ImUtf8.CalcTextSize(EquipSlot.OffHand.ToName()).X + ImGui.GetFrameHeightWithSpacing();
ImGui.SetNextItemWidth(width);
using var combo = ImUtf8.Combo("##slot"u8, _newKey.SlotName());
if (combo)
{
var currentSlot = _newKey.ToEquipSlot();
foreach (var tmpSlot in EquipSlotExtensions.FullSlots)
{
if (ImUtf8.Selectable(tmpSlot.ToName(), tmpSlot == currentSlot) && currentSlot != tmpSlot)
_newKey = MaterialValueIndex.FromSlot(tmpSlot) with
{
MaterialIndex = (byte)_newMaterialIdx,
RowIndex = (byte)_newRowIdx,
};
}
var currentBonus = _newKey.ToBonusSlot();
foreach (var bonusSlot in BonusExtensions.AllFlags)
{
if (ImUtf8.Selectable(bonusSlot.ToName(), bonusSlot == currentBonus) && bonusSlot != currentBonus)
_newKey = MaterialValueIndex.FromSlot(bonusSlot) with
{
MaterialIndex = (byte)_newMaterialIdx,
RowIndex = (byte)_newRowIdx,
};
}
}
ImUtf8.HoverTooltip("Choose a slot for an advanced dye row."u8);
}
public void DrawNew(Design design) public void DrawNew(Design design)
{ {
DrawSlotCombo(); if (EquipSlotCombo.Draw("##slot", "Choose a slot for an advanced dye row.", ref _newSlot))
_newKey = MaterialValueIndex.FromSlot(_newSlot) with
{
MaterialIndex = (byte)_newMaterialIdx,
RowIndex = (byte)_newRowIdx,
};
ImUtf8.SameLineInner(); ImUtf8.SameLineInner();
DrawMaterialIdxDrag(); DrawMaterialIdxDrag();
ImUtf8.SameLineInner(); ImUtf8.SameLineInner();

View file

@ -3,7 +3,7 @@ using Glamourer.Events;
using Glamourer.Interop.Penumbra; using Glamourer.Interop.Penumbra;
using Glamourer.Services; using Glamourer.Services;
using Glamourer.State; using Glamourer.State;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui.Raii; using OtterGui.Raii;
using Penumbra.Api.Enums; using Penumbra.Api.Enums;
using Penumbra.GameData.Data; using Penumbra.GameData.Data;
@ -22,12 +22,11 @@ public sealed class PenumbraChangedItemTooltip : IDisposable
private readonly CustomizeService _customize; private readonly CustomizeService _customize;
private readonly GPoseService _gpose; private readonly GPoseService _gpose;
private readonly EquipItem[] _lastItems = new EquipItem[EquipFlagExtensions.NumEquipFlags / 2 + BonusExtensions.AllFlags.Count]; private readonly EquipItem[] _lastItems = new EquipItem[EquipFlagExtensions.NumEquipFlags / 2];
public IEnumerable<KeyValuePair<object, EquipItem>> LastItems public IEnumerable<KeyValuePair<EquipSlot, EquipItem>> LastItems
=> EquipSlotExtensions.EqdpSlots.Cast<object>().Append(EquipSlot.MainHand).Append(EquipSlot.OffHand) => EquipSlotExtensions.EqdpSlots.Append(EquipSlot.MainHand).Append(EquipSlot.OffHand).Zip(_lastItems)
.Concat(BonusExtensions.AllFlags.Cast<object>()).Zip(_lastItems) .Select(p => new KeyValuePair<EquipSlot, EquipItem>(p.First, p.Second));
.Select(p => new KeyValuePair<object, EquipItem>(p.First, p.Second));
public ChangedItemType LastType { get; private set; } = ChangedItemType.None; public ChangedItemType LastType { get; private set; } = ChangedItemType.None;
public uint LastId { get; private set; } public uint LastId { get; private set; }
@ -73,21 +72,6 @@ public sealed class PenumbraChangedItemTooltip : IDisposable
if (!Player()) if (!Player())
return; return;
var bonusSlot = item.Type.ToBonus();
if (bonusSlot is not BonusItemFlag.Unknown)
{
// + 2 due to weapons.
var glasses = _lastItems[bonusSlot.ToSlot() + 2];
using (_ = !openTooltip ? null : ImRaii.Tooltip())
{
ImGui.TextUnformatted($"{prefix}Right-Click to apply to current actor.");
if (glasses.Valid)
ImGui.TextUnformatted($"{prefix}Control + Right-Click to re-apply {glasses.Name} to current actor.");
}
return;
}
var slot = item.Type.ToSlot(); var slot = item.Type.ToSlot();
var last = _lastItems[slot.ToIndex()]; var last = _lastItems[slot.ToIndex()];
switch (slot) switch (slot)
@ -125,27 +109,6 @@ public sealed class PenumbraChangedItemTooltip : IDisposable
public void ApplyItem(ActorState state, EquipItem item) public void ApplyItem(ActorState state, EquipItem item)
{ {
var bonusSlot = item.Type.ToBonus();
if (bonusSlot is not BonusItemFlag.Unknown)
{
// + 2 due to weapons.
var glasses = _lastItems[bonusSlot.ToSlot() + 2];
if (ImGui.GetIO().KeyCtrl && glasses.Valid)
{
Glamourer.Log.Debug($"Re-Applying {glasses.Name} to {bonusSlot.ToName()}.");
SetLastItem(bonusSlot, default, state);
_stateManager.ChangeBonusItem(state, bonusSlot, glasses, ApplySettings.Manual);
}
else
{
Glamourer.Log.Debug($"Applying {item.Name} to {bonusSlot.ToName()}.");
SetLastItem(bonusSlot, item, state);
_stateManager.ChangeBonusItem(state, bonusSlot, item, ApplySettings.Manual);
}
return;
}
var slot = item.Type.ToSlot(); var slot = item.Type.ToSlot();
var last = _lastItems[slot.ToIndex()]; var last = _lastItems[slot.ToIndex()];
switch (slot) switch (slot)
@ -302,22 +265,7 @@ public sealed class PenumbraChangedItemTooltip : IDisposable
{ {
var oldItem = state.ModelData.Item(slot); var oldItem = state.ModelData.Item(slot);
if (oldItem.Id != item.Id) if (oldItem.Id != item.Id)
last = oldItem; _lastItems[slot.ToIndex()] = oldItem;
}
}
private void SetLastItem(BonusItemFlag slot, EquipItem item, ActorState state)
{
ref var last = ref _lastItems[slot.ToSlot() + 2];
if (!item.Valid)
{
last = default;
}
else
{
var oldItem = state.ModelData.BonusItem(slot);
if (oldItem.Id != item.Id)
last = oldItem;
} }
} }

View file

@ -11,7 +11,7 @@ using Glamourer.Gui.Equipment;
using Glamourer.Gui.Materials; using Glamourer.Gui.Materials;
using Glamourer.Interop; using Glamourer.Interop;
using Glamourer.State; using Glamourer.State;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Classes; using OtterGui.Classes;
using OtterGui.Raii; using OtterGui.Raii;
@ -238,7 +238,6 @@ public class ActorPanel
ImGui.Dummy(new Vector2(ImGui.GetTextLineHeight() / 2)); ImGui.Dummy(new Vector2(ImGui.GetTextLineHeight() / 2));
DrawEquipmentMetaToggles(); DrawEquipmentMetaToggles();
ImGui.Dummy(new Vector2(ImGui.GetTextLineHeight() / 2)); ImGui.Dummy(new Vector2(ImGui.GetTextLineHeight() / 2));
_equipmentDrawer.DrawDragDropTooltip();
} }
private void DrawParameterHeader() private void DrawParameterHeader()
@ -305,12 +304,6 @@ public class ActorPanel
EquipmentDrawer.DrawMetaToggle(ToggleDrawData.FromState(MetaIndex.WeaponState, _stateManager, _state!)); EquipmentDrawer.DrawMetaToggle(ToggleDrawData.FromState(MetaIndex.WeaponState, _stateManager, _state!));
EquipmentDrawer.DrawMetaToggle(ToggleDrawData.CrestFromState(CrestFlag.OffHand, _stateManager, _state!)); EquipmentDrawer.DrawMetaToggle(ToggleDrawData.CrestFromState(CrestFlag.OffHand, _stateManager, _state!));
} }
ImGui.SameLine();
using (_ = ImRaii.Group())
{
EquipmentDrawer.DrawMetaToggle(ToggleDrawData.FromState(MetaIndex.EarState, _stateManager, _state!));
}
} }
private void DrawMonsterPanel() private void DrawMonsterPanel()

View file

@ -1,5 +1,5 @@
using Dalamud.Interface; using Dalamud.Interface;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Classes; using OtterGui.Classes;
using OtterGui.Raii; using OtterGui.Raii;

View file

@ -1,5 +1,5 @@
using Dalamud.Interface.Utility; using Dalamud.Interface.Utility;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui.Widgets; using OtterGui.Widgets;
namespace Glamourer.Gui.Tabs.ActorTab; namespace Glamourer.Gui.Tabs.ActorTab;

View file

@ -1,5 +1,5 @@
using Dalamud.Interface.Utility; using Dalamud.Interface.Utility;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui.Widgets; using OtterGui.Widgets;
namespace Glamourer.Gui.Tabs.AutomationTab; namespace Glamourer.Gui.Tabs.AutomationTab;

View file

@ -1,12 +1,12 @@
using Dalamud.Game.ClientState.Objects.Enums; using Dalamud.Game.ClientState.Objects.Enums;
using Dalamud.Utility; using Dalamud.Utility;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Custom;
using OtterGui.Extensions; using OtterGui.Extensions;
using OtterGui.Log; using OtterGui.Log;
using OtterGui.Widgets; using OtterGui.Widgets;
using Penumbra.GameData.DataContainers; using Penumbra.GameData.DataContainers;
using OtterGui.Custom;
namespace Glamourer.Gui.Tabs.AutomationTab; namespace Glamourer.Gui.Tabs.AutomationTab;

View file

@ -1,5 +1,5 @@
using Dalamud.Game.ClientState.Objects.Enums; using Dalamud.Game.ClientState.Objects.Enums;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using Penumbra.GameData.Actors; using Penumbra.GameData.Actors;
using Penumbra.GameData.DataContainers; using Penumbra.GameData.DataContainers;
using Penumbra.GameData.Gui; using Penumbra.GameData.Gui;

View file

@ -4,7 +4,7 @@ using Glamourer.Automation;
using Glamourer.Designs; using Glamourer.Designs;
using Glamourer.Designs.Special; using Glamourer.Designs.Special;
using Glamourer.Events; using Glamourer.Events;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Raii; using OtterGui.Raii;
using OtterGui.Services; using OtterGui.Services;
@ -278,7 +278,7 @@ public sealed class RandomRestrictionDrawer : IService, IDisposable
private void LookupTooltip(IEnumerable<Design> designs) private void LookupTooltip(IEnumerable<Design> designs)
{ {
using var _ = ImRaii.Tooltip(); using var _ = ImRaii.Tooltip();
var tt = string.Join('\n', designs.Select(d => _designFileSystem.TryGetValue(d, out var l) ? l.FullName() : d.Name.Text).OrderBy(t => t)); var tt = string.Join('\n', designs.Select(d => _designFileSystem.FindLeaf(d, out var l) ? l.FullName() : d.Name.Text).OrderBy(t => t));
ImGui.TextUnformatted(tt.Length == 0 ImGui.TextUnformatted(tt.Length == 0
? "Matches no currently existing designs." ? "Matches no currently existing designs."
: "Matches the following designs:"); : "Matches the following designs:");

View file

@ -6,7 +6,7 @@ using Glamourer.Designs.Special;
using Glamourer.Interop; using Glamourer.Interop;
using Glamourer.Services; using Glamourer.Services;
using Glamourer.Unlocks; using Glamourer.Unlocks;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Extensions; using OtterGui.Extensions;
using OtterGui.Log; using OtterGui.Log;
@ -432,7 +432,7 @@ public class SetPanel(
if (source) if (source)
{ {
ImUtf8.Text($"Moving design #{index + 1:D2}..."); ImUtf8.Text($"Moving design #{index + 1:D2}...");
if (ImGui.SetDragDropPayload(dragDropLabel, null, 0)) if (ImGui.SetDragDropPayload(dragDropLabel, nint.Zero, 0))
{ {
_dragIndex = index; _dragIndex = index;
_selector.DragDesignIndex = index; _selector.DragDesignIndex = index;

View file

@ -2,7 +2,7 @@
using Dalamud.Interface.Utility; using Dalamud.Interface.Utility;
using Glamourer.Automation; using Glamourer.Automation;
using Glamourer.Events; using Glamourer.Events;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Classes; using OtterGui.Classes;
using OtterGui.Extensions; using OtterGui.Extensions;
@ -144,7 +144,7 @@ public class SetSelector : IDisposable
ImGui.SameLine(); ImGui.SameLine();
var f = _enabledFilter; var f = _enabledFilter;
if (ImGui.CheckboxFlags("##enabledFilter", ref f, 3u)) if (ImGui.CheckboxFlags("##enabledFilter", ref f, 3))
{ {
_enabledFilter = _enabledFilter switch _enabledFilter = _enabledFilter switch
{ {
@ -347,7 +347,7 @@ public class SetSelector : IDisposable
if (source) if (source)
{ {
ImGui.TextUnformatted($"Moving design set {GetSetName(set, index)} from position {index + 1}..."); ImGui.TextUnformatted($"Moving design set {GetSetName(set, index)} from position {index + 1}...");
if (ImGui.SetDragDropPayload(dragDropLabel, null, 0)) if (ImGui.SetDragDropPayload(dragDropLabel, nint.Zero, 0))
_dragIndex = index; _dragIndex = index;
} }
} }

View file

@ -2,7 +2,7 @@
using Glamourer.GameData; using Glamourer.GameData;
using Glamourer.Designs; using Glamourer.Designs;
using Glamourer.State; using Glamourer.State;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Raii; using OtterGui.Raii;
using Penumbra.GameData.Enums; using Penumbra.GameData.Enums;
@ -87,9 +87,6 @@ public class ActiveStatePanel(StateManager _stateManager, ActorObjectManager _ob
PrintRow("Visor Toggled", state.BaseData.IsVisorToggled(), state.ModelData.IsVisorToggled(), PrintRow("Visor Toggled", state.BaseData.IsVisorToggled(), state.ModelData.IsVisorToggled(),
state.Sources[MetaIndex.VisorState]); state.Sources[MetaIndex.VisorState]);
ImGui.TableNextRow(); ImGui.TableNextRow();
PrintRow("Viera Ears Visible", state.BaseData.AreEarsVisible(), state.ModelData.AreEarsVisible(),
state.Sources[MetaIndex.EarState]);
ImGui.TableNextRow();
PrintRow("Weapon Visible", state.BaseData.IsWeaponVisible(), state.ModelData.IsWeaponVisible(), PrintRow("Weapon Visible", state.BaseData.IsWeaponVisible(), state.ModelData.IsWeaponVisible(),
state.Sources[MetaIndex.WeaponState]); state.Sources[MetaIndex.WeaponState]);
ImGui.TableNextRow(); ImGui.TableNextRow();

View file

@ -1,5 +1,5 @@
using FFXIVClientStructs.FFXIV.Client.Graphics.Kernel; using FFXIVClientStructs.FFXIV.Client.Graphics.Kernel;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui.Raii; using OtterGui.Raii;
using OtterGui.Text; using OtterGui.Text;
using Penumbra.GameData.Gui.Debug; using Penumbra.GameData.Gui.Debug;

View file

@ -1,5 +1,5 @@
using Glamourer.Automation; using Glamourer.Automation;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Extensions; using OtterGui.Extensions;
using OtterGui.Raii; using OtterGui.Raii;

View file

@ -1,7 +1,7 @@
using Dalamud.Interface; using Dalamud.Interface;
using Glamourer.GameData; using Glamourer.GameData;
using Glamourer.Services; using Glamourer.Services;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Raii; using OtterGui.Raii;
using OtterGui.Text; using OtterGui.Text;

View file

@ -1,5 +1,5 @@
using Glamourer.Unlocks; using Glamourer.Unlocks;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Raii; using OtterGui.Raii;
using Penumbra.GameData.Enums; using Penumbra.GameData.Enums;

View file

@ -1,5 +1,5 @@
using Glamourer.Interop; using Glamourer.Interop;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using Penumbra.GameData.Files; using Penumbra.GameData.Files;
using Penumbra.GameData.Gui.Debug; using Penumbra.GameData.Gui.Debug;

View file

@ -1,4 +1,4 @@
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui.Raii; using OtterGui.Raii;
using OtterGui.Services; using OtterGui.Services;
using OtterGui.Widgets; using OtterGui.Widgets;

View file

@ -1,7 +1,7 @@
using Dalamud.Interface; using Dalamud.Interface;
using Glamourer.Designs; using Glamourer.Designs;
using Glamourer.Utility; using Glamourer.Utility;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using Newtonsoft.Json.Linq; using Newtonsoft.Json.Linq;
using OtterGui; using OtterGui;
using OtterGui.Raii; using OtterGui.Raii;

View file

@ -1,11 +1,9 @@
using Dalamud.Interface; using Dalamud.Interface;
using Glamourer.Designs; using Glamourer.Designs;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Extensions; using OtterGui.Extensions;
using OtterGui.Filesystem;
using OtterGui.Raii; using OtterGui.Raii;
using OtterGui.Text;
using Penumbra.GameData.Enums; using Penumbra.GameData.Enums;
using Penumbra.GameData.Gui.Debug; using Penumbra.GameData.Gui.Debug;
@ -21,7 +19,6 @@ public class DesignManagerPanel(DesignManager _designManager, DesignFileSystem _
public void Draw() public void Draw()
{ {
DrawButtons();
foreach (var (design, idx) in _designManager.Designs.WithIndex()) foreach (var (design, idx) in _designManager.Designs.WithIndex())
{ {
using var t = ImRaii.TreeNode($"{design.Name}##{idx}"); using var t = ImRaii.TreeNode($"{design.Name}##{idx}");
@ -29,8 +26,7 @@ public class DesignManagerPanel(DesignManager _designManager, DesignFileSystem _
continue; continue;
DrawDesign(design, _designFileSystem); DrawDesign(design, _designFileSystem);
var base64 = DesignBase64Migration.CreateOldBase64(design.DesignData, design.Application.Equip, design.Application.Customize, var base64 = DesignBase64Migration.CreateOldBase64(design.DesignData, design.Application.Equip, design.Application.Customize, design.Application.Meta,
design.Application.Meta,
design.WriteProtected()); design.WriteProtected());
using var font = ImRaii.PushFont(UiBuilder.MonoFont); using var font = ImRaii.PushFont(UiBuilder.MonoFont);
ImGuiUtil.TextWrapped(base64); ImGuiUtil.TextWrapped(base64);
@ -39,26 +35,6 @@ public class DesignManagerPanel(DesignManager _designManager, DesignFileSystem _
} }
} }
private void DrawButtons()
{
if (ImUtf8.Button("Generate 500 Test Designs"u8))
for (var i = 0; i < 500; ++i)
{
var design = _designManager.CreateEmpty($"Test Designs/Test Design {i}", true);
_designManager.AddTag(design, "_DebugTest");
}
ImUtf8.SameLineInner();
if (ImUtf8.Button("Remove All Test Designs"u8))
{
var designs = _designManager.Designs.Where(d => d.Tags.Contains("_DebugTest")).ToArray();
foreach (var design in designs)
_designManager.Delete(design);
if (_designFileSystem.Find("Test Designs", out var path) && path is DesignFileSystem.Folder { TotalChildren: 0 })
_designFileSystem.Delete(path);
}
}
public static void DrawDesign(DesignBase design, DesignFileSystem? fileSystem) public static void DrawDesign(DesignBase design, DesignFileSystem? fileSystem)
{ {
using var table = ImRaii.Table("##equip", 8, ImGuiTableFlags.RowBg | ImGuiTableFlags.SizingFixedFit); using var table = ImRaii.Table("##equip", 8, ImGuiTableFlags.RowBg | ImGuiTableFlags.SizingFixedFit);
@ -77,7 +53,7 @@ public class DesignManagerPanel(DesignManager _designManager, DesignFileSystem _
ImGui.TableNextRow(); ImGui.TableNextRow();
ImGuiUtil.DrawTableColumn("Design File System Path"); ImGuiUtil.DrawTableColumn("Design File System Path");
if (fileSystem != null) if (fileSystem != null)
ImGuiUtil.DrawTableColumn(fileSystem.TryGetValue(d, out var leaf) ? leaf.FullName() : "No Path Known"); ImGuiUtil.DrawTableColumn(fileSystem.FindLeaf(d, out var leaf) ? leaf.FullName() : "No Path Known");
ImGui.TableNextRow(); ImGui.TableNextRow();
ImGuiUtil.DrawTableColumn("Creation"); ImGuiUtil.DrawTableColumn("Creation");
@ -114,7 +90,6 @@ public class DesignManagerPanel(DesignManager _designManager, DesignFileSystem _
ImGuiUtil.DrawTableColumn(index.ToName()); ImGuiUtil.DrawTableColumn(index.ToName());
ImGuiUtil.DrawTableColumn(design.DesignData.GetMeta(index).ToString()); ImGuiUtil.DrawTableColumn(design.DesignData.GetMeta(index).ToString());
ImGuiUtil.DrawTableColumn(design.DoApplyMeta(index) ? "Apply" : "Keep"); ImGuiUtil.DrawTableColumn(design.DoApplyMeta(index) ? "Apply" : "Keep");
ImGui.TableNextRow();
} }
ImGuiUtil.DrawTableColumn("Model ID"); ImGuiUtil.DrawTableColumn("Model ID");

View file

@ -1,7 +1,7 @@
using Dalamud.Interface; using Dalamud.Interface;
using Glamourer.Designs; using Glamourer.Designs;
using Glamourer.Services; using Glamourer.Services;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Extensions; using OtterGui.Extensions;
using OtterGui.Raii; using OtterGui.Raii;

View file

@ -1,5 +1,5 @@
using Glamourer.State; using Glamourer.State;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using Penumbra.GameData.Gui.Debug; using Penumbra.GameData.Gui.Debug;
namespace Glamourer.Gui.Tabs.DebugTab; namespace Glamourer.Gui.Tabs.DebugTab;

View file

@ -5,7 +5,7 @@ using FFXIVClientStructs.FFXIV.Client.Game;
using Glamourer.Designs; using Glamourer.Designs;
using Glamourer.Services; using Glamourer.Services;
using Glamourer.State; using Glamourer.State;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Extensions; using OtterGui.Extensions;
using OtterGui.Text; using OtterGui.Text;

View file

@ -1,5 +1,5 @@
using FFXIVClientStructs.FFXIV.Client.Game; using FFXIVClientStructs.FFXIV.Client.Game;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Raii; using OtterGui.Raii;
using Penumbra.GameData.Gui.Debug; using Penumbra.GameData.Gui.Debug;

View file

@ -3,7 +3,7 @@ using Dalamud.Interface.Utility;
using Dalamud.Plugin; using Dalamud.Plugin;
using Glamourer.Api.Enums; using Glamourer.Api.Enums;
using Glamourer.Api.IpcSubscribers; using Glamourer.Api.IpcSubscribers;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Raii; using OtterGui.Raii;
using OtterGui.Services; using OtterGui.Services;

View file

@ -1,5 +1,8 @@
using Glamourer.Api.Enums; using Glamourer.Api.Enums;
using Dalamud.Bindings.ImGui; using Glamourer.Designs;
using ImGuiNET;
using OtterGui;
using static Penumbra.GameData.Files.ShpkFile;
namespace Glamourer.Gui.Tabs.DebugTab.IpcTester; namespace Glamourer.Gui.Tabs.DebugTab.IpcTester;

View file

@ -1,7 +1,7 @@
using Dalamud.Plugin; using Dalamud.Plugin;
using Dalamud.Plugin.Services; using Dalamud.Plugin.Services;
using Glamourer.Api.IpcSubscribers; using Glamourer.Api.IpcSubscribers;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using Penumbra.GameData.Gui.Debug; using Penumbra.GameData.Gui.Debug;
namespace Glamourer.Gui.Tabs.DebugTab.IpcTester; namespace Glamourer.Gui.Tabs.DebugTab.IpcTester;
@ -33,11 +33,6 @@ public class IpcTesterPanel(
ImGui.SameLine(); ImGui.SameLine();
ImGui.TextUnformatted($"({major}.{minor:D4})"); ImGui.TextUnformatted($"({major}.{minor:D4})");
ImGui.TextUnformatted(AutoReloadGearEnabled.Label);
var autoRedraw = new AutoReloadGearEnabled(pluginInterface).Invoke();
ImGui.SameLine();
ImGui.TextUnformatted(autoRedraw ? "Enabled" : "Disabled");
designs.Draw(); designs.Draw();
items.Draw(); items.Draw();
state.Draw(); state.Draw();
@ -54,7 +49,6 @@ public class IpcTesterPanel(
return; return;
Glamourer.Log.Debug("[IPCTester] Subscribed to IPC events for IPC tester."); Glamourer.Log.Debug("[IPCTester] Subscribed to IPC events for IPC tester.");
state.AutoRedrawChanged.Enable();
state.GPoseChanged.Enable(); state.GPoseChanged.Enable();
state.StateChanged.Enable(); state.StateChanged.Enable();
state.StateFinalized.Enable(); state.StateFinalized.Enable();
@ -78,7 +72,6 @@ public class IpcTesterPanel(
Glamourer.Log.Debug("[IPCTester] Unsubscribed from IPC events for IPC tester."); Glamourer.Log.Debug("[IPCTester] Unsubscribed from IPC events for IPC tester.");
_subscribed = false; _subscribed = false;
state.AutoRedrawChanged.Disable();
state.GPoseChanged.Disable(); state.GPoseChanged.Disable();
state.StateChanged.Disable(); state.StateChanged.Disable();
state.StateFinalized.Disable(); state.StateFinalized.Disable();

View file

@ -1,7 +1,7 @@
using Dalamud.Plugin; using Dalamud.Plugin;
using Glamourer.Api.Enums; using Glamourer.Api.Enums;
using Glamourer.Api.IpcSubscribers; using Glamourer.Api.IpcSubscribers;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Raii; using OtterGui.Raii;
using OtterGui.Services; using OtterGui.Services;

View file

@ -1,11 +1,11 @@
using Dalamud.Bindings.ImGui; using Dalamud.Interface;
using Dalamud.Interface;
using Dalamud.Interface.Utility; using Dalamud.Interface.Utility;
using Dalamud.Plugin; using Dalamud.Plugin;
using Glamourer.Api.Enums; using Glamourer.Api.Enums;
using Glamourer.Api.Helpers; using Glamourer.Api.Helpers;
using Glamourer.Api.IpcSubscribers; using Glamourer.Api.IpcSubscribers;
using Glamourer.Designs; using Glamourer.Designs;
using ImGuiNET;
using Newtonsoft.Json; using Newtonsoft.Json;
using Newtonsoft.Json.Linq; using Newtonsoft.Json.Linq;
using OtterGui; using OtterGui;
@ -31,10 +31,6 @@ public class StateIpcTester : IUiService, IDisposable
private string _base64State = string.Empty; private string _base64State = string.Empty;
private string? _getStateString; private string? _getStateString;
public readonly EventSubscriber<bool> AutoRedrawChanged;
private bool _lastAutoRedrawChangeValue;
private DateTime _lastAutoRedrawChangeTime;
public readonly EventSubscriber<nint, StateChangeType> StateChanged; public readonly EventSubscriber<nint, StateChangeType> StateChanged;
private nint _lastStateChangeActor; private nint _lastStateChangeActor;
private ByteString _lastStateChangeName = ByteString.Empty; private ByteString _lastStateChangeName = ByteString.Empty;
@ -56,11 +52,9 @@ public class StateIpcTester : IUiService, IDisposable
public StateIpcTester(IDalamudPluginInterface pluginInterface) public StateIpcTester(IDalamudPluginInterface pluginInterface)
{ {
_pluginInterface = pluginInterface; _pluginInterface = pluginInterface;
AutoRedrawChanged = AutoReloadGearChanged.Subscriber(_pluginInterface, OnAutoRedrawChanged);
StateChanged = StateChangedWithType.Subscriber(_pluginInterface, OnStateChanged); StateChanged = StateChangedWithType.Subscriber(_pluginInterface, OnStateChanged);
StateFinalized = Api.IpcSubscribers.StateFinalized.Subscriber(_pluginInterface, OnStateFinalized); StateFinalized = Api.IpcSubscribers.StateFinalized.Subscriber(_pluginInterface, OnStateFinalized);
GPoseChanged = Api.IpcSubscribers.GPoseChanged.Subscriber(_pluginInterface, OnGPoseChange); GPoseChanged = Api.IpcSubscribers.GPoseChanged.Subscriber(_pluginInterface, OnGPoseChange);
AutoRedrawChanged.Disable();
StateChanged.Disable(); StateChanged.Disable();
StateFinalized.Disable(); StateFinalized.Disable();
GPoseChanged.Disable(); GPoseChanged.Disable();
@ -68,7 +62,6 @@ public class StateIpcTester : IUiService, IDisposable
public void Dispose() public void Dispose()
{ {
AutoRedrawChanged.Dispose();
StateChanged.Dispose(); StateChanged.Dispose();
StateFinalized.Dispose(); StateFinalized.Dispose();
GPoseChanged.Dispose(); GPoseChanged.Dispose();
@ -90,8 +83,6 @@ public class StateIpcTester : IUiService, IDisposable
IpcTesterHelpers.DrawIntro("Last Error"); IpcTesterHelpers.DrawIntro("Last Error");
ImGui.TextUnformatted(_lastError.ToString()); ImGui.TextUnformatted(_lastError.ToString());
IpcTesterHelpers.DrawIntro("Last Auto Redraw Change");
ImGui.TextUnformatted($"{_lastAutoRedrawChangeValue} at {_lastAutoRedrawChangeTime.ToLocalTime().TimeOfDay}");
IpcTesterHelpers.DrawIntro("Last State Change"); IpcTesterHelpers.DrawIntro("Last State Change");
PrintChangeName(); PrintChangeName();
IpcTesterHelpers.DrawIntro("Last State Finalization"); IpcTesterHelpers.DrawIntro("Last State Finalization");
@ -147,14 +138,6 @@ public class StateIpcTester : IUiService, IDisposable
if (ImUtf8.Button("Apply Base64##Name"u8)) if (ImUtf8.Button("Apply Base64##Name"u8))
_lastError = new ApplyStateName(_pluginInterface).Invoke(_base64State, _gameObjectName, _key, _flags); _lastError = new ApplyStateName(_pluginInterface).Invoke(_base64State, _gameObjectName, _key, _flags);
IpcTesterHelpers.DrawIntro(ReapplyState.Label);
if (ImUtf8.Button("Reapply##Idx"u8))
_lastError = new ReapplyState(_pluginInterface).Invoke(_gameObjectIndex, _key, _flags);
IpcTesterHelpers.DrawIntro(ReapplyStateName.Label);
if (ImUtf8.Button("Reapply##Name"u8))
_lastError = new ReapplyStateName(_pluginInterface).Invoke(_gameObjectName, _key, _flags);
IpcTesterHelpers.DrawIntro(RevertState.Label); IpcTesterHelpers.DrawIntro(RevertState.Label);
if (ImUtf8.Button("Revert##Idx"u8)) if (ImUtf8.Button("Revert##Idx"u8))
_lastError = new RevertState(_pluginInterface).Invoke(_gameObjectIndex, _key, _flags); _lastError = new RevertState(_pluginInterface).Invoke(_gameObjectIndex, _key, _flags);
@ -242,12 +225,6 @@ public class StateIpcTester : IUiService, IDisposable
ImUtf8.Text($"at {_lastStateFinalizeTime.ToLocalTime().TimeOfDay}"); ImUtf8.Text($"at {_lastStateFinalizeTime.ToLocalTime().TimeOfDay}");
} }
private void OnAutoRedrawChanged(bool value)
{
_lastAutoRedrawChangeValue = value;
_lastAutoRedrawChangeTime = DateTime.UtcNow;
}
private void OnStateChanged(nint actor, StateChangeType type) private void OnStateChanged(nint actor, StateChangeType type)
{ {
_lastStateChangeActor = actor; _lastStateChangeActor = actor;

View file

@ -1,7 +1,7 @@
using Dalamud.Interface.Utility; using Dalamud.Interface.Utility;
using Glamourer.Services; using Glamourer.Services;
using Glamourer.Unlocks; using Glamourer.Unlocks;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Raii; using OtterGui.Raii;
using Penumbra.GameData.Enums; using Penumbra.GameData.Enums;

View file

@ -2,7 +2,7 @@
using Glamourer.GameData; using Glamourer.GameData;
using Glamourer.Interop; using Glamourer.Interop;
using Glamourer.Interop.Structs; using Glamourer.Interop.Structs;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Raii; using OtterGui.Raii;
using OtterGui.Text; using OtterGui.Text;
@ -17,7 +17,6 @@ namespace Glamourer.Gui.Tabs.DebugTab;
public unsafe class ModelEvaluationPanel( public unsafe class ModelEvaluationPanel(
ActorObjectManager _objectManager, ActorObjectManager _objectManager,
VisorService _visorService, VisorService _visorService,
VieraEarService _vieraEarService,
UpdateSlotService _updateSlotService, UpdateSlotService _updateSlotService,
ChangeCustomizeService _changeCustomizeService, ChangeCustomizeService _changeCustomizeService,
CrestService _crestService, CrestService _crestService,
@ -85,7 +84,6 @@ public unsafe class ModelEvaluationPanel(
ImGuiUtil.CopyOnClickSelectable(offhand.ToString()); ImGuiUtil.CopyOnClickSelectable(offhand.ToString());
DrawVisor(actor, model); DrawVisor(actor, model);
DrawVieraEars(actor, model);
DrawHatState(actor, model); DrawHatState(actor, model);
DrawWeaponState(actor, model); DrawWeaponState(actor, model);
DrawWetness(actor, model); DrawWetness(actor, model);
@ -137,26 +135,6 @@ public unsafe class ModelEvaluationPanel(
_visorService.SetVisorState(model, !VisorService.GetVisorState(model)); _visorService.SetVisorState(model, !VisorService.GetVisorState(model));
} }
private void DrawVieraEars(Actor actor, Model model)
{
using var id = ImRaii.PushId("Viera Ears");
ImGuiUtil.DrawTableColumn("Viera Ears");
ImGuiUtil.DrawTableColumn(actor.IsCharacter ? actor.ShowVieraEars.ToString() : "No Character");
ImGuiUtil.DrawTableColumn(model.IsHuman ? model.VieraEarsVisible.ToString() : "No Human");
ImGui.TableNextColumn();
if (!model.IsHuman)
return;
if (ImGui.SmallButton("Set True"))
_vieraEarService.SetVieraEarState(model, true);
ImGui.SameLine();
if (ImGui.SmallButton("Set False"))
_vieraEarService.SetVieraEarState(model, false);
ImGui.SameLine();
if (ImGui.SmallButton("Toggle"))
_vieraEarService.SetVieraEarState(model, !model.VieraEarsVisible);
}
private void DrawHatState(Actor actor, Model model) private void DrawHatState(Actor actor, Model model)
{ {
using var id = ImRaii.PushId("HatState"); using var id = ImRaii.PushId("HatState");

View file

@ -4,7 +4,7 @@ using FFXIVClientStructs.FFXIV.Client.Game.Object;
using Glamourer.Designs; using Glamourer.Designs;
using Glamourer.GameData; using Glamourer.GameData;
using Glamourer.State; using Glamourer.State;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui.Raii; using OtterGui.Raii;
using OtterGui.Text; using OtterGui.Text;
using Penumbra.GameData.Enums; using Penumbra.GameData.Enums;

View file

@ -1,4 +1,4 @@
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Text; using OtterGui.Text;
using Penumbra.GameData.Actors; using Penumbra.GameData.Actors;

View file

@ -1,6 +1,6 @@
using Dalamud.Interface.Utility; using Dalamud.Interface.Utility;
using Glamourer.Interop.Penumbra; using Glamourer.Interop.Penumbra;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Raii; using OtterGui.Raii;
using Penumbra.Api.Enums; using Penumbra.Api.Enums;
@ -49,7 +49,7 @@ public unsafe class PenumbraPanel(PenumbraService _penumbra, PenumbraChangedItem
ImGui.TableNextColumn(); ImGui.TableNextColumn();
var address = _drawObject.Address; var address = _drawObject.Address;
ImGui.SetNextItemWidth(200 * ImGuiHelpers.GlobalScale); ImGui.SetNextItemWidth(200 * ImGuiHelpers.GlobalScale);
if (ImGui.InputScalar("##drawObjectPtr", ImGuiDataType.U64, ref address, nint.Zero, nint.Zero, "%llx", if (ImGui.InputScalar("##drawObjectPtr", ImGuiDataType.U64, (nint)(&address), nint.Zero, nint.Zero, "%llx",
ImGuiInputTextFlags.CharsHexadecimal)) ImGuiInputTextFlags.CharsHexadecimal))
_drawObject = address; _drawObject = address;
ImGuiUtil.DrawTableColumn(_penumbra.Available ImGuiUtil.DrawTableColumn(_penumbra.Available
@ -89,13 +89,7 @@ public unsafe class PenumbraPanel(PenumbraService _penumbra, PenumbraChangedItem
ImGui.Separator(); ImGui.Separator();
foreach (var (slot, item) in _penumbraTooltip.LastItems) foreach (var (slot, item) in _penumbraTooltip.LastItems)
{ {
switch (slot) ImGuiUtil.DrawTableColumn($"{slot.ToName()} Revert-Item");
{
case EquipSlot e: ImGuiUtil.DrawTableColumn($"{e.ToName()} Revert-Item"); break;
case BonusItemFlag f: ImGuiUtil.DrawTableColumn($"{f.ToName()} Revert-Item"); break;
default: ImGuiUtil.DrawTableColumn("Unk Revert-Item"); break;
}
ImGuiUtil.DrawTableColumn(item.Valid ? item.Name : "None"); ImGuiUtil.DrawTableColumn(item.Valid ? item.Name : "None");
ImGui.TableNextColumn(); ImGui.TableNextColumn();
} }

View file

@ -1,7 +1,7 @@
using Dalamud.Interface.Utility; using Dalamud.Interface.Utility;
using Glamourer.Services; using Glamourer.Services;
using Glamourer.Unlocks; using Glamourer.Unlocks;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Raii; using OtterGui.Raii;
using Penumbra.GameData.Enums; using Penumbra.GameData.Enums;

View file

@ -1,5 +1,5 @@
using Glamourer.Designs; using Glamourer.Designs;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Raii; using OtterGui.Raii;
using OtterGui.Widgets; using OtterGui.Widgets;

View file

@ -2,7 +2,7 @@
using Dalamud.Interface.ImGuiNotification; using Dalamud.Interface.ImGuiNotification;
using Glamourer.Designs; using Glamourer.Designs;
using Glamourer.Services; using Glamourer.Services;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Classes; using OtterGui.Classes;
using OtterGui.Raii; using OtterGui.Raii;
@ -189,7 +189,10 @@ public class DesignDetailTab
else if (_selector.Selected!.Color.Length != 0) else if (_selector.Selected!.Color.Length != 0)
{ {
ImGui.SameLine(); ImGui.SameLine();
ImUtf8.Icon(FontAwesomeIcon.ExclamationCircle, "The color associated with this design does not exist."u8, _colors.MissingColor); var size = new Vector2(ImGui.GetFrameHeight());
using var font = ImRaii.PushFont(UiBuilder.IconFont);
ImGuiUtil.DrawTextButton(FontAwesomeIcon.ExclamationCircle.ToIconString(), size, 0, _colors.MissingColor);
ImUtf8.HoverTooltip("The color associated with this design does not exist."u8);
} }
ImUtf8.DrawFrameColumn("Creation Date"u8); ImUtf8.DrawFrameColumn("Creation Date"u8);

View file

@ -5,7 +5,7 @@ using Glamourer.Designs;
using Glamourer.Designs.History; using Glamourer.Designs.History;
using Glamourer.Events; using Glamourer.Events;
using Glamourer.Services; using Glamourer.Services;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Classes; using OtterGui.Classes;
using OtterGui.Filesystem; using OtterGui.Filesystem;
@ -175,7 +175,7 @@ public sealed class DesignFileSystemSelector : FileSystemSelector<Design, Design
var flag = selected ? ImGuiTreeNodeFlags.Selected | LeafFlags : LeafFlags; var flag = selected ? ImGuiTreeNodeFlags.Selected | LeafFlags : LeafFlags;
var name = IncognitoMode ? leaf.Value.Incognito : leaf.Value.Name.Text; var name = IncognitoMode ? leaf.Value.Incognito : leaf.Value.Name.Text;
using var color = ImRaii.PushColor(ImGuiCol.Text, state.Color); using var color = ImRaii.PushColor(ImGuiCol.Text, state.Color);
using var _ = ImUtf8.TreeNode(name, flag); using var _ = ImRaii.TreeNode(name, flag);
if (_config.AllowDoubleClickToApply && ImGui.IsItemHovered() && ImGui.IsMouseDoubleClicked(ImGuiMouseButton.Left)) if (_config.AllowDoubleClickToApply && ImGui.IsItemHovered() && ImGui.IsMouseDoubleClicked(ImGuiMouseButton.Left))
_designApplier.ApplyToPlayer(leaf.Value); _designApplier.ApplyToPlayer(leaf.Value);
} }

View file

@ -3,7 +3,7 @@ using Dalamud.Interface.Utility;
using Glamourer.Automation; using Glamourer.Automation;
using Glamourer.Designs; using Glamourer.Designs;
using Glamourer.Designs.Links; using Glamourer.Designs.Links;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Raii; using OtterGui.Raii;
using OtterGui.Services; using OtterGui.Services;
@ -195,7 +195,7 @@ public class DesignLinkDrawer(
{ {
if (source) if (source)
{ {
ImGui.SetDragDropPayload("DraggingLink", null, 0); ImGui.SetDragDropPayload("DraggingLink", IntPtr.Zero, 0);
ImGui.TextUnformatted($"Reordering {design.Name}..."); ImGui.TextUnformatted($"Reordering {design.Name}...");
_dragDropIndex = index; _dragDropIndex = index;
_dragDropOrder = order; _dragDropOrder = order;

View file

@ -12,7 +12,7 @@ using Glamourer.Gui.Equipment;
using Glamourer.Gui.Materials; using Glamourer.Gui.Materials;
using Glamourer.Interop; using Glamourer.Interop;
using Glamourer.State; using Glamourer.State;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Classes; using OtterGui.Classes;
using OtterGui.Raii; using OtterGui.Raii;
@ -130,7 +130,6 @@ public class DesignPanel
ImGui.Dummy(new Vector2(ImGui.GetTextLineHeight() / 2)); ImGui.Dummy(new Vector2(ImGui.GetTextLineHeight() / 2));
DrawEquipmentMetaToggles(); DrawEquipmentMetaToggles();
ImGui.Dummy(new Vector2(ImGui.GetTextLineHeight() / 2)); ImGui.Dummy(new Vector2(ImGui.GetTextLineHeight() / 2));
_equipmentDrawer.DrawDragDropTooltip();
} }
private void DrawEquipmentMetaToggles() private void DrawEquipmentMetaToggles()
@ -154,12 +153,6 @@ public class DesignPanel
EquipmentDrawer.DrawMetaToggle(ToggleDrawData.FromDesign(MetaIndex.WeaponState, _manager, _selector.Selected!)); EquipmentDrawer.DrawMetaToggle(ToggleDrawData.FromDesign(MetaIndex.WeaponState, _manager, _selector.Selected!));
EquipmentDrawer.DrawMetaToggle(ToggleDrawData.CrestFromDesign(CrestFlag.OffHand, _manager, _selector.Selected!)); EquipmentDrawer.DrawMetaToggle(ToggleDrawData.CrestFromDesign(CrestFlag.OffHand, _manager, _selector.Selected!));
} }
ImGui.SameLine();
using (var _ = ImRaii.Group())
{
EquipmentDrawer.DrawMetaToggle(ToggleDrawData.FromDesign(MetaIndex.EarState, _manager, _selector.Selected!));
}
} }
private void DrawCustomize() private void DrawCustomize()
@ -271,9 +264,11 @@ public class DesignPanel
DrawCrestApplication(); DrawCrestApplication();
ImUtf8.IconDummy(); ImUtf8.IconDummy();
DrawMetaApplication(); DrawMetaApplication();
ImUtf8.IconDummy();
DrawBonusSlotApplication();
} }
ImGui.SameLine(210 * ImUtf8.GlobalScale + ImGui.GetStyle().ItemSpacing.X); ImGui.SameLine(ImGui.GetContentRegionAvail().X / 2);
using (var _ = ImRaii.Group()) using (var _ = ImRaii.Group())
{ {
void ApplyEquip(string label, EquipFlag allFlags, bool stain, IEnumerable<EquipSlot> slots) void ApplyEquip(string label, EquipFlag allFlags, bool stain, IEnumerable<EquipSlot> slots)
@ -315,9 +310,6 @@ public class DesignPanel
ImUtf8.IconDummy(); ImUtf8.IconDummy();
DrawParameterApplication(); DrawParameterApplication();
ImUtf8.IconDummy();
DrawBonusSlotApplication();
} }
} }
@ -326,7 +318,7 @@ public class DesignPanel
var enabled = _config.DeleteDesignModifier.IsActive(); var enabled = _config.DeleteDesignModifier.IsActive();
bool? equip = null; bool? equip = null;
bool? customize = null; bool? customize = null;
var size = new Vector2(210 * ImUtf8.GlobalScale, 0); var size = new Vector2(200 * ImUtf8.GlobalScale, 0);
if (ImUtf8.ButtonEx("Disable Everything"u8, if (ImUtf8.ButtonEx("Disable Everything"u8,
"Disable application of everything, including any existing advanced dyes, advanced customizations, crests and wetness."u8, size, "Disable application of everything, including any existing advanced dyes, advanced customizations, crests and wetness."u8, size,
!enabled)) !enabled))
@ -404,7 +396,6 @@ public class DesignPanel
_manager.ChangeApplyMeta(_selector.Selected!, MetaIndex.HatState, equip.Value); _manager.ChangeApplyMeta(_selector.Selected!, MetaIndex.HatState, equip.Value);
_manager.ChangeApplyMeta(_selector.Selected!, MetaIndex.VisorState, equip.Value); _manager.ChangeApplyMeta(_selector.Selected!, MetaIndex.VisorState, equip.Value);
_manager.ChangeApplyMeta(_selector.Selected!, MetaIndex.WeaponState, equip.Value); _manager.ChangeApplyMeta(_selector.Selected!, MetaIndex.WeaponState, equip.Value);
_manager.ChangeApplyMeta(_selector.Selected!, MetaIndex.EarState, equip.Value);
} }
if (customize.HasValue) if (customize.HasValue)
@ -417,7 +408,6 @@ public class DesignPanel
"Apply Hat Visibility", "Apply Hat Visibility",
"Apply Visor State", "Apply Visor State",
"Apply Weapon Visibility", "Apply Weapon Visibility",
"Apply Viera Ear Visibility",
]; ];
private void DrawMetaApplication() private void DrawMetaApplication()

View file

@ -2,7 +2,7 @@
using Dalamud.Interface.Utility; using Dalamud.Interface.Utility;
using Glamourer.Designs; using Glamourer.Designs;
using Glamourer.Interop; using Glamourer.Interop;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui.Classes; using OtterGui.Classes;
using OtterGui.Widgets; using OtterGui.Widgets;

View file

@ -5,7 +5,7 @@ using Dalamud.Utility;
using Glamourer.Designs; using Glamourer.Designs;
using Glamourer.Interop.Penumbra; using Glamourer.Interop.Penumbra;
using Glamourer.State; using Glamourer.State;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Classes; using OtterGui.Classes;
using OtterGui.Extensions; using OtterGui.Extensions;
@ -71,8 +71,6 @@ public class ModAssociationsTab(PenumbraService penumbra, DesignFileSystemSelect
private void DrawApplyAllButton() private void DrawApplyAllButton()
{ {
var (id, name) = penumbra.CurrentCollection; var (id, name) = penumbra.CurrentCollection;
if (config.Ephemeral.IncognitoMode)
name = id.ShortGuid();
if (ImGuiUtil.DrawDisabledButton($"Try Applying All Associated Mods to {name}##applyAll", if (ImGuiUtil.DrawDisabledButton($"Try Applying All Associated Mods to {name}##applyAll",
new Vector2(ImGui.GetContentRegionAvail().X, 0), string.Empty, id == Guid.Empty)) new Vector2(ImGui.GetContentRegionAvail().X, 0), string.Empty, id == Guid.Empty))
ApplyAll(); ApplyAll();

View file

@ -1,6 +1,6 @@
using Dalamud.Interface.Utility; using Dalamud.Interface.Utility;
using Glamourer.Interop.Penumbra; using Glamourer.Interop.Penumbra;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui.Classes; using OtterGui.Classes;
using OtterGui.Log; using OtterGui.Log;
using OtterGui.Raii; using OtterGui.Raii;

View file

@ -2,7 +2,7 @@
using Dalamud.Interface.Utility; using Dalamud.Interface.Utility;
using Glamourer.Designs; using Glamourer.Designs;
using Glamourer.Interop.Material; using Glamourer.Interop.Material;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui.Extensions; using OtterGui.Extensions;
using OtterGui.Raii; using OtterGui.Raii;
using OtterGui.Text; using OtterGui.Text;
@ -14,7 +14,8 @@ public class MultiDesignPanel(
DesignFileSystemSelector selector, DesignFileSystemSelector selector,
DesignManager editor, DesignManager editor,
DesignColors colors, DesignColors colors,
Configuration config) Configuration config,
DesignComboWrapper combos)
{ {
private readonly Button[] _leftButtons = []; private readonly Button[] _leftButtons = [];
private readonly Button[] _rightButtons = [new IncognitoButton(config)]; private readonly Button[] _rightButtons = [new IncognitoButton(config)];
@ -205,6 +206,7 @@ public class MultiDesignPanel(
: $"Display all {_numDesigns} selected designs in the quick design bar. Changes {diff} designs."; : $"Display all {_numDesigns} selected designs in the quick design bar. Changes {diff} designs.";
if (ImUtf8.ButtonEx("Display Selected Designs in QDB"u8, tt, buttonWidth, diff == 0)) if (ImUtf8.ButtonEx("Display Selected Designs in QDB"u8, tt, buttonWidth, diff == 0))
{ {
using var disableListener = combos.StopListening();
foreach (var design in selector.SelectedPaths.OfType<DesignFileSystem.Leaf>()) foreach (var design in selector.SelectedPaths.OfType<DesignFileSystem.Leaf>())
editor.SetQuickDesign(design.Value, true); editor.SetQuickDesign(design.Value, true);
} }
@ -215,6 +217,7 @@ public class MultiDesignPanel(
: $"Hide all {_numDesigns} selected designs in the quick design bar. Changes {_numQuickDesignEnabled} designs."; : $"Hide all {_numDesigns} selected designs in the quick design bar. Changes {_numQuickDesignEnabled} designs.";
if (ImUtf8.ButtonEx("Hide Selected Designs in QDB"u8, tt, buttonWidth, _numQuickDesignEnabled == 0)) if (ImUtf8.ButtonEx("Hide Selected Designs in QDB"u8, tt, buttonWidth, _numQuickDesignEnabled == 0))
{ {
using var disableListener = combos.StopListening();
foreach (var design in selector.SelectedPaths.OfType<DesignFileSystem.Leaf>()) foreach (var design in selector.SelectedPaths.OfType<DesignFileSystem.Leaf>())
editor.SetQuickDesign(design.Value, false); editor.SetQuickDesign(design.Value, false);
} }
@ -336,6 +339,7 @@ public class MultiDesignPanel(
ImGui.SameLine(); ImGui.SameLine();
if (ImUtf8.ButtonEx(label, tooltip, width, _addDesigns.Count == 0)) if (ImUtf8.ButtonEx(label, tooltip, width, _addDesigns.Count == 0))
{ {
using var disableListener = combos.StopListening();
foreach (var design in _addDesigns) foreach (var design in _addDesigns)
editor.ChangeColor(design, _colorCombo.CurrentSelection!); editor.ChangeColor(design, _colorCombo.CurrentSelection!);
} }
@ -349,6 +353,7 @@ public class MultiDesignPanel(
ImGui.SameLine(); ImGui.SameLine();
if (ImUtf8.ButtonEx(label, tooltip, width, _removeDesigns.Count == 0)) if (ImUtf8.ButtonEx(label, tooltip, width, _removeDesigns.Count == 0))
{ {
using var disableListener = combos.StopListening();
foreach (var (design, _) in _removeDesigns) foreach (var (design, _) in _removeDesigns)
editor.ChangeColor(design, string.Empty); editor.ChangeColor(design, string.Empty);
} }
@ -490,7 +495,7 @@ public class MultiDesignPanel(
foreach (var leaf in selector.SelectedPaths.OfType<DesignFileSystem.Leaf>()) foreach (var leaf in selector.SelectedPaths.OfType<DesignFileSystem.Leaf>())
{ {
var index = leaf.Value.Tags.AsEnumerable().IndexOf(_tag); var index = leaf.Value.Tags.IndexOf(_tag);
if (index >= 0) if (index >= 0)
_removeDesigns.Add((leaf.Value, index)); _removeDesigns.Add((leaf.Value, index));
else else

View file

@ -1,6 +1,6 @@
using Dalamud.Interface; using Dalamud.Interface;
using Dalamud.Interface.Utility; using Dalamud.Interface.Utility;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Raii; using OtterGui.Raii;

View file

@ -2,7 +2,7 @@
using Glamourer.Designs; using Glamourer.Designs;
using Glamourer.GameData; using Glamourer.GameData;
using Glamourer.Services; using Glamourer.Services;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using Newtonsoft.Json; using Newtonsoft.Json;
using Newtonsoft.Json.Linq; using Newtonsoft.Json.Linq;

View file

@ -6,7 +6,7 @@ using Glamourer.Gui.Customization;
using Glamourer.Gui.Equipment; using Glamourer.Gui.Equipment;
using Glamourer.Gui.Tabs.DesignTab; using Glamourer.Gui.Tabs.DesignTab;
using Glamourer.State; using Glamourer.State;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Classes; using OtterGui.Classes;
using OtterGui.Raii; using OtterGui.Raii;

View file

@ -1,5 +1,5 @@
using Glamourer.GameData; using Glamourer.GameData;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Extensions; using OtterGui.Extensions;
using OtterGui.Raii; using OtterGui.Raii;

View file

@ -1,5 +1,5 @@
using Dalamud.Interface.Utility; using Dalamud.Interface.Utility;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui.Widgets; using OtterGui.Widgets;
namespace Glamourer.Gui.Tabs.NpcTab; namespace Glamourer.Gui.Tabs.NpcTab;

View file

@ -1,7 +1,7 @@
using Dalamud.Interface; using Dalamud.Interface;
using Glamourer.Services; using Glamourer.Services;
using Glamourer.State; using Glamourer.State;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui.Filesystem; using OtterGui.Filesystem;
using OtterGui.Raii; using OtterGui.Raii;
using OtterGui.Services; using OtterGui.Services;

View file

@ -1,6 +1,6 @@
using Dalamud.Interface; using Dalamud.Interface;
using Glamourer.Interop.Penumbra; using Glamourer.Interop.Penumbra;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Log; using OtterGui.Log;
using OtterGui.Raii; using OtterGui.Raii;

View file

@ -1,7 +1,7 @@
using Dalamud.Interface; using Dalamud.Interface;
using Glamourer.Interop.Penumbra; using Glamourer.Interop.Penumbra;
using Glamourer.Services; using Glamourer.Services;
using Dalamud.Bindings.ImGui; using ImGuiNET;
using OtterGui; using OtterGui;
using OtterGui.Raii; using OtterGui.Raii;
using OtterGui.Services; using OtterGui.Services;
@ -123,7 +123,7 @@ public class CollectionOverrideDrawer(
{ {
if (source) if (source)
{ {
ImGui.SetDragDropPayload("DraggingOverride", null, 0); ImGui.SetDragDropPayload("DraggingOverride", nint.Zero, 0);
ImGui.TextUnformatted($"Reordering Override #{idx + 1}..."); ImGui.TextUnformatted($"Reordering Override #{idx + 1}...");
_dragDropIndex = idx; _dragDropIndex = idx;
} }

Some files were not shown because too many files have changed in this diff Show more