Add more edit options, some small fixes.

This commit is contained in:
Ottermandias 2022-05-03 18:15:35 +02:00
parent 65bbece9cf
commit 54460c39f3
13 changed files with 697 additions and 227 deletions

View file

@ -23,6 +23,7 @@ public static class Colors
public const uint PressEnterWarningBg = 0xFF202080;
public const uint RegexWarningBorder = 0xFF0000B0;
public const uint MetaInfoText = 0xAAFFFFFF;
public const uint RedTableBgTint = 0x40000080;
public static (uint DefaultColor, string Name, string Description) Data( this ColorId color )
=> color switch

View file

@ -1,13 +1,18 @@
using System;
using System.IO;
using System.Linq;
using System.Numerics;
using Dalamud.Interface;
using Dalamud.Interface.Components;
using Dalamud.Interface.Windowing;
using ImGuiNET;
using OtterGui;
using OtterGui.Raii;
using Penumbra.GameData.ByteString;
using Penumbra.GameData.Enums;
using Penumbra.Meta.Manipulations;
using Penumbra.Mods;
using Penumbra.Util;
namespace Penumbra.UI.Classes;
@ -28,6 +33,11 @@ public class ModEditWindow : Window, IDisposable
_editor = new Mod.Editor( mod );
_mod = mod;
WindowName = $"{mod.Name}{WindowBaseLabel}";
SizeConstraints = new WindowSizeConstraints
{
MinimumSize = ImGuiHelpers.ScaledVector2( 800, 600 ),
MaximumSize = 4000 * Vector2.One,
};
}
public void ChangeOption( int groupIdx, int optionIdx )
@ -50,6 +60,168 @@ public class ModEditWindow : Window, IDisposable
DrawMissingFilesTab();
DrawUnusedFilesTab();
DrawDuplicatesTab();
DrawMaterialChangeTab();
}
// A row of three buttonSizes and a help marker that can be used for material suffix changing.
private static class MaterialSuffix
{
private static string _materialSuffixFrom = string.Empty;
private static string _materialSuffixTo = string.Empty;
private static GenderRace _raceCode = GenderRace.Unknown;
private static string RaceCodeName( GenderRace raceCode )
{
if( raceCode == GenderRace.Unknown )
{
return "All Races and Genders";
}
var (gender, race) = raceCode.Split();
return $"({raceCode.ToRaceCode()}) {race.ToName()} {gender.ToName()} ";
}
private static void DrawRaceCodeCombo( Vector2 buttonSize )
{
ImGui.SetNextItemWidth( buttonSize.X );
using var combo = ImRaii.Combo( "##RaceCode", RaceCodeName( _raceCode ) );
if( !combo )
{
return;
}
foreach( var raceCode in Enum.GetValues< GenderRace >() )
{
if( ImGui.Selectable( RaceCodeName( raceCode ), _raceCode == raceCode ) )
{
_raceCode = raceCode;
}
}
}
public static void Draw( Mod.Editor editor, Vector2 buttonSize )
{
DrawRaceCodeCombo( buttonSize );
ImGui.SameLine();
ImGui.SetNextItemWidth( buttonSize.X );
ImGui.InputTextWithHint( "##suffixFrom", "From...", ref _materialSuffixFrom, 32 );
ImGui.SameLine();
ImGui.SetNextItemWidth( buttonSize.X );
ImGui.InputTextWithHint( "##suffixTo", "To...", ref _materialSuffixTo, 32 );
ImGui.SameLine();
var disabled = !Mod.Editor.ValidString( _materialSuffixTo );
var tt = _materialSuffixTo.Length == 0
? "Please enter a target suffix."
: _materialSuffixFrom == _materialSuffixTo
? "The source and target are identical."
: disabled
? "The suffix is invalid."
: _materialSuffixFrom.Length == 0
? _raceCode == GenderRace.Unknown ? "Convert all skin material suffices to the target."
: "Convert all skin material suffices for the given race code to the target."
: _raceCode == GenderRace.Unknown
? $"Convert all skin material suffices that are currently '{_materialSuffixFrom}' to '{_materialSuffixTo}'."
: $"Convert all skin material suffices for the given race code that are currently '{_materialSuffixFrom}' to '{_materialSuffixTo}'.";
if( ImGuiUtil.DrawDisabledButton( "Change Material Suffix", buttonSize, tt, disabled ) )
{
editor.ReplaceAllMaterials( _materialSuffixTo, _materialSuffixFrom, _raceCode );
}
var anyChanges = editor.ModelFiles.Any( m => m.Changed );
if( ImGuiUtil.DrawDisabledButton( "Save All Changes", buttonSize,
anyChanges ? "Irreversibly rewrites all currently applied changes to model files." : "No changes made yet.", !anyChanges ) )
{
editor.SaveAllModels();
}
ImGui.SameLine();
if( ImGuiUtil.DrawDisabledButton( "Revert All Changes", buttonSize,
anyChanges ? "Revert all currently made and unsaved changes." : "No changes made yet.", !anyChanges ) )
{
editor.RestoreAllModels();
}
ImGui.SameLine();
ImGuiComponents.HelpMarker(
"Model files refer to the skin material they should use. This skin material is always the same, but modders have started using different suffices to differentiate between body types.\n"
+ "This option allows you to switch the suffix of all model files to another. This changes the files, so you do this on your own risk.\n"
+ "If you do not know what the currently used suffix of this mod is, you can leave 'From' blank and it will replace all suffices with 'To', instead of only the matching ones." );
}
}
private void DrawMaterialChangeTab()
{
using var tab = ImRaii.TabItem( "Model Materials" );
if( !tab )
{
return;
}
if( _editor!.ModelFiles.Count == 0 )
{
ImGui.NewLine();
ImGui.TextUnformatted( "No .mdl files detected." );
}
else
{
ImGui.NewLine();
MaterialSuffix.Draw( _editor, ImGuiHelpers.ScaledVector2( 175, 0 ) );
ImGui.NewLine();
using var child = ImRaii.Child( "##mdlFiles", -Vector2.One, true );
if( !child )
{
return;
}
using var table = ImRaii.Table( "##files", 4, ImGuiTableFlags.RowBg | ImGuiTableFlags.SizingFixedFit, -Vector2.One );
if( !table )
{
return;
}
var iconSize = ImGui.GetFrameHeight() * Vector2.One;
foreach( var (info, idx) in _editor.ModelFiles.WithIndex() )
{
using var id = ImRaii.PushId( idx );
ImGui.TableNextColumn();
if( ImGuiUtil.DrawDisabledButton( FontAwesomeIcon.Save.ToIconString(), iconSize,
"Save the changed mdl file.\nUse at own risk!", !info.Changed, true ) )
{
info.Save();
}
ImGui.TableNextColumn();
if( ImGuiUtil.DrawDisabledButton( FontAwesomeIcon.Recycle.ToIconString(), iconSize,
"Restore current changes to default.", !info.Changed, true ) )
{
info.Restore();
}
ImGui.TableNextColumn();
ImGui.TextUnformatted( info.Path.FullName[ ( _mod!.ModPath.FullName.Length + 1 ).. ] );
ImGui.TableNextColumn();
ImGui.SetNextItemWidth( 400 * ImGuiHelpers.GlobalScale );
var tmp = info.CurrentMaterials[ 0 ];
if( ImGui.InputText( "##0", ref tmp, 64 ) )
{
info.SetMaterial( tmp, 0 );
}
for( var i = 1; i < info.Count; ++i )
{
ImGui.TableNextColumn();
ImGui.TableNextColumn();
ImGui.TableNextColumn();
ImGui.TableNextColumn();
ImGui.SetNextItemWidth( 400 * ImGuiHelpers.GlobalScale );
tmp = info.CurrentMaterials[ i ];
if( ImGui.InputText( $"##{i}", ref tmp, 64 ) )
{
info.SetMaterial( tmp, i );
}
}
}
}
}
private void DrawMissingFilesTab()
@ -62,6 +234,7 @@ public class ModEditWindow : Window, IDisposable
if( _editor!.MissingPaths.Count == 0 )
{
ImGui.NewLine();
ImGui.TextUnformatted( "No missing files detected." );
}
else
@ -71,6 +244,12 @@ public class ModEditWindow : Window, IDisposable
_editor.RemoveMissingPaths();
}
using var child = ImRaii.Child( "##unusedFiles", -Vector2.One, true );
if( !child )
{
return;
}
using var table = ImRaii.Table( "##missingFiles", 1, ImGuiTableFlags.RowBg, -Vector2.One );
if( !table )
{
@ -113,7 +292,9 @@ public class ModEditWindow : Window, IDisposable
if( _editor.Duplicates.Count == 0 )
{
ImGui.NewLine();
ImGui.TextUnformatted( "No duplicates found." );
return;
}
if( ImGui.Button( "Delete and Redirect Duplicates" ) )
@ -173,12 +354,68 @@ public class ModEditWindow : Window, IDisposable
foreach( var duplicate in set.Skip( 1 ) )
{
ImGui.TableNextColumn();
ImGui.TableSetBgColor( ImGuiTableBgTarget.CellBg, 0x40000080 );
ImGui.TableSetBgColor( ImGuiTableBgTarget.CellBg, Colors.RedTableBgTint );
using var node = ImRaii.TreeNode( duplicate.FullName[ ( _mod!.ModPath.FullName.Length + 1 ).. ], ImGuiTreeNodeFlags.Leaf );
ImGui.TableNextColumn();
ImGui.TableSetBgColor( ImGuiTableBgTarget.CellBg, 0x40000080 );
ImGui.TableSetBgColor( ImGuiTableBgTarget.CellBg, Colors.RedTableBgTint );
ImGui.TableNextColumn();
ImGui.TableSetBgColor( ImGuiTableBgTarget.CellBg, 0x40000080 );
ImGui.TableSetBgColor( ImGuiTableBgTarget.CellBg, Colors.RedTableBgTint );
}
}
}
private void DrawOptionSelectHeader()
{
const string defaultOption = "Default Option";
using var style = ImRaii.PushStyle( ImGuiStyleVar.ItemSpacing, Vector2.Zero ).Push( ImGuiStyleVar.FrameRounding, 0 );
var width = new Vector2( ImGui.GetWindowWidth() / 3, 0 );
var isDefaultOption = _editor!.GroupIdx == -1 && _editor!.OptionIdx == 0;
if( ImGuiUtil.DrawDisabledButton( defaultOption, width, "Switch to the default option for the mod.\nThis resets unsaved changes.",
isDefaultOption ) )
{
_editor.SetSubMod( -1, 0 );
}
ImGui.SameLine();
if( ImGuiUtil.DrawDisabledButton( "Refresh Data", width, "Refresh data for the current option.\nThis resets unsaved changes.", false ) )
{
_editor.SetSubMod( _editor.GroupIdx, _editor.OptionIdx );
}
ImGui.SameLine();
string GetLabel()
{
if( isDefaultOption )
{
return defaultOption;
}
var group = _mod!.Groups[ _editor!.GroupIdx ];
return $"{group.Name}: {group[ _editor.OptionIdx ].Name}";
}
var groupLabel = GetLabel();
using var combo = ImRaii.Combo( "##optionSelector", groupLabel, ImGuiComboFlags.NoArrowButton );
if( !combo )
{
return;
}
if( ImGui.Selectable( $"{defaultOption}###-1_0", isDefaultOption ) )
{
_editor.SetSubMod( -1, 0 );
}
foreach( var (group, groupIdx) in _mod!.Groups.WithIndex() )
{
foreach( var (option, optionIdx) in group.WithIndex() )
{
var name = $"{group.Name}: {option.Name}###{groupIdx}_{optionIdx}";
if( ImGui.Selectable( name, groupIdx == _editor.GroupIdx && optionIdx == _editor.OptionIdx ) )
{
_editor.SetSubMod( groupIdx, optionIdx );
}
}
}
}
@ -193,6 +430,7 @@ public class ModEditWindow : Window, IDisposable
if( _editor!.UnusedFiles.Count == 0 )
{
ImGui.NewLine();
ImGui.TextUnformatted( "No unused files detected." );
}
else
@ -202,12 +440,19 @@ public class ModEditWindow : Window, IDisposable
_editor.AddUnusedPathsToDefault();
}
ImGui.SameLine();
if( ImGui.Button( "Delete Unused Files from Filesystem" ) )
{
_editor.DeleteUnusedPaths();
}
using var table = ImRaii.Table( "##unusedFiles", 1, ImGuiTableFlags.RowBg, -Vector2.One );
using var child = ImRaii.Child( "##unusedFiles", -Vector2.One, true );
if( !child )
{
return;
}
using var table = ImRaii.Table( "##table", 1, ImGuiTableFlags.RowBg );
if( !table )
{
return;
@ -230,7 +475,14 @@ public class ModEditWindow : Window, IDisposable
return;
}
using var list = ImRaii.Table( "##files", 2 );
DrawOptionSelectHeader();
using var child = ImRaii.Child( "##files", -Vector2.One, true );
if( !child )
{
return;
}
using var list = ImRaii.Table( "##table", 2 );
if( !list )
{
return;
@ -253,7 +505,30 @@ public class ModEditWindow : Window, IDisposable
return;
}
using var list = ImRaii.Table( "##meta", 3 );
DrawOptionSelectHeader();
var setsEqual = _editor!.CurrentManipulations.SetEquals( _editor.CurrentOption.Manipulations );
var tt = setsEqual ? "No changes staged." : "Apply the currently staged changes to the option.";
ImGui.NewLine();
if( ImGuiUtil.DrawDisabledButton( "Apply Changes", Vector2.Zero, tt, setsEqual ) )
{
_editor.ApplyManipulations();
}
ImGui.SameLine();
tt = setsEqual ? "No changes staged." : "Revert all currently staged changes.";
if( ImGuiUtil.DrawDisabledButton( "Revert Changes", Vector2.Zero, tt, setsEqual ) )
{
_editor.RevertManipulations();
}
using var child = ImRaii.Child( "##meta", -Vector2.One, true );
if( !child )
{
return;
}
using var list = ImRaii.Table( "##table", 3 );
if( !list )
{
return;
@ -288,6 +563,8 @@ public class ModEditWindow : Window, IDisposable
}
}
private string _newSwapKey = string.Empty;
private string _newSwapValue = string.Empty;
private void DrawSwapTab()
{
using var tab = ImRaii.TabItem( "File Swaps" );
@ -296,19 +573,94 @@ public class ModEditWindow : Window, IDisposable
return;
}
using var list = ImRaii.Table( "##swaps", 3 );
DrawOptionSelectHeader();
var setsEqual = _editor!.CurrentSwaps.SetEquals( _editor.CurrentOption.FileSwaps );
var tt = setsEqual ? "No changes staged." : "Apply the currently staged changes to the option.";
ImGui.NewLine();
if( ImGuiUtil.DrawDisabledButton( "Apply Changes", Vector2.Zero, tt, setsEqual ) )
{
_editor.ApplySwaps();
}
ImGui.SameLine();
tt = setsEqual ? "No changes staged." : "Revert all currently staged changes.";
if( ImGuiUtil.DrawDisabledButton( "Revert Changes", Vector2.Zero, tt, setsEqual ) )
{
_editor.RevertSwaps();
}
using var child = ImRaii.Child( "##swaps", -Vector2.One, true );
if( !child )
{
return;
}
using var list = ImRaii.Table( "##table", 3, ImGuiTableFlags.RowBg, -Vector2.One );
if( !list )
{
return;
}
foreach( var (gamePath, file) in _editor!.CurrentSwaps )
var idx = 0;
var iconSize = ImGui.GetFrameHeight() * Vector2.One;
var pathSize = ImGui.GetContentRegionAvail().X / 2 - iconSize.X;
ImGui.TableSetupColumn( "button", ImGuiTableColumnFlags.WidthFixed, iconSize.X );
ImGui.TableSetupColumn( "source", ImGuiTableColumnFlags.WidthFixed, pathSize );
ImGui.TableSetupColumn( "value", ImGuiTableColumnFlags.WidthFixed, pathSize );
foreach( var (gamePath, file) in _editor!.CurrentSwaps.ToList() )
{
using var id = ImRaii.PushId( idx++ );
ImGui.TableNextColumn();
ConfigWindow.Text( gamePath.Path );
if( ImGuiUtil.DrawDisabledButton( FontAwesomeIcon.Trash.ToIconString(), iconSize, "Delete this swap.", false, true ) )
{
_editor.CurrentSwaps.Remove( gamePath );
}
ImGui.TableNextColumn();
ImGui.TextUnformatted( file.FullName );
var tmp = gamePath.Path.ToString();
ImGui.SetNextItemWidth( -1 );
if( ImGui.InputText( "##key", ref tmp, Utf8GamePath.MaxGamePathLength )
&& Utf8GamePath.FromString( tmp, out var path )
&& !_editor.CurrentSwaps.ContainsKey( path ) )
{
_editor.CurrentSwaps.Remove( gamePath );
if( path.Length > 0 )
{
_editor.CurrentSwaps[ path ] = file;
}
}
ImGui.TableNextColumn();
tmp = file.FullName;
ImGui.SetNextItemWidth( -1 );
if( ImGui.InputText( "##value", ref tmp, Utf8GamePath.MaxGamePathLength ) && tmp.Length > 0 )
{
_editor.CurrentSwaps[ gamePath ] = new FullPath( tmp );
}
}
ImGui.TableNextColumn();
var addable = Utf8GamePath.FromString( _newSwapKey, out var newPath )
&& newPath.Length > 0
&& _newSwapValue.Length > 0
&& _newSwapValue != _newSwapKey
&& !_editor.CurrentSwaps.ContainsKey( newPath );
if( ImGuiUtil.DrawDisabledButton( FontAwesomeIcon.Plus.ToIconString(), iconSize, "Add a new file swap to this option.", !addable,
true ) )
{
_editor.CurrentSwaps[ newPath ] = new FullPath( _newSwapValue );
_newSwapKey = string.Empty;
_newSwapValue = string.Empty;
}
ImGui.TableNextColumn();
ImGui.SetNextItemWidth( -1 );
ImGui.InputTextWithHint( "##swapKey", "New Swap Source...", ref _newSwapKey, Utf8GamePath.MaxGamePathLength );
ImGui.TableNextColumn();
ImGui.SetNextItemWidth( -1 );
ImGui.InputTextWithHint( "##swapValue", "New Swap Target...", ref _newSwapValue, Utf8GamePath.MaxGamePathLength );
}
public ModEditWindow()

View file

@ -5,11 +5,11 @@ using System.IO;
using System.Numerics;
using Dalamud.Interface;
using Dalamud.Interface.Components;
using Dalamud.Memory;
using ImGuiNET;
using OtterGui;
using OtterGui.Raii;
using Penumbra.Mods;
using Penumbra.Util;
namespace Penumbra.UI;
@ -84,9 +84,6 @@ public partial class ConfigWindow
MoveDirectory.Draw( _mod, buttonSize );
MaterialSuffix.Draw( _mod, buttonSize );
ImGui.Dummy( _window._defaultSpace );
}
@ -135,13 +132,12 @@ public partial class ConfigWindow
Process.Start( new ProcessStartInfo( _mod.MetaFile.FullName ) { UseShellExecute = true } );
}
if( ImGui.Button( "Edit Default Mod", reducedSize ) )
if( ImGui.Button( "Edit Mod Details", reducedSize ) )
{
_window.ModEditPopup.ChangeMod( _mod );
_window.ModEditPopup.ChangeOption( -1, 0 );
_window.ModEditPopup.IsOpen = true;
}
ImGui.SameLine();
fileExists = File.Exists( _mod.DefaultFile );
tt = fileExists
@ -171,6 +167,9 @@ public partial class ConfigWindow
{
private static string _newGroupName = string.Empty;
public static void Reset()
=> _newGroupName = string.Empty;
public static void Draw( ConfigWindow window, Mod mod )
{
ImGui.SetNextItemWidth( window._inputTextWidth.X );
@ -183,66 +182,30 @@ public partial class ConfigWindow
tt, !nameValid, true ) )
{
Penumbra.ModManager.AddModGroup( mod, SelectType.Single, _newGroupName );
_newGroupName = string.Empty;
Reset();
}
}
}
// A row of three buttonSizes and a help marker that can be used for material suffix changing.
private static class MaterialSuffix
{
private static string _materialSuffixFrom = string.Empty;
private static string _materialSuffixTo = string.Empty;
public static void Draw( Mod mod, Vector2 buttonSize )
{
ImGui.SetNextItemWidth( buttonSize.X );
ImGui.InputTextWithHint( "##suffixFrom", "From...", ref _materialSuffixFrom, 32 );
ImGui.SameLine();
ImGui.SetNextItemWidth( buttonSize.X );
ImGui.InputTextWithHint( "##suffixTo", "To...", ref _materialSuffixTo, 32 );
ImGui.SameLine();
var disabled = !ModelChanger.ValidStrings( _materialSuffixFrom, _materialSuffixTo );
var tt = _materialSuffixTo.Length == 0 ? "Please enter a target suffix."
: _materialSuffixFrom == _materialSuffixTo ? "The source and target are identical."
: disabled ? "The suffices are not valid suffices."
: _materialSuffixFrom.Length == 0 ? "Convert all skin material suffices to the target."
: $"Convert all skin material suffices that are currently '{_materialSuffixFrom}' to '{_materialSuffixTo}'.";
if( ImGuiUtil.DrawDisabledButton( "Change Material Suffix", buttonSize, tt, disabled ) )
{
ModelChanger.ChangeModMaterials( mod, _materialSuffixFrom, _materialSuffixTo );
}
ImGui.SameLine();
ImGuiComponents.HelpMarker(
"Model files refer to the skin material they should use. This skin material is always the same, but modders have started using different suffices to differentiate between body types.\n"
+ "This option allows you to switch the suffix of all model files to another. This changes the files, so you do this on your own risk.\n"
+ "If you do not know what the currently used suffix of this mod is, you can leave 'From' blank and it will replace all suffices with 'To', instead of only the matching ones." );
}
}
// A text input for the new directory name and a button to apply the move.
private static class MoveDirectory
{
private static string? _currentModDirectory;
private static Mod? _modForDirectory;
private static Mod.Manager.NewDirectoryState _state = Mod.Manager.NewDirectoryState.Identical;
public static void Reset()
{
_currentModDirectory = null;
_state = Mod.Manager.NewDirectoryState.Identical;
}
public static void Draw( Mod mod, Vector2 buttonSize )
{
ImGui.SetNextItemWidth( buttonSize.X * 2 + ImGui.GetStyle().ItemSpacing.X );
var tmp = _currentModDirectory ?? mod.ModPath.Name;
if( mod != _modForDirectory )
{
tmp = mod.ModPath.Name;
_currentModDirectory = null;
_state = Mod.Manager.NewDirectoryState.Identical;
}
if( ImGui.InputText( "##newModMove", ref tmp, 64 ) )
{
_currentModDirectory = tmp;
_modForDirectory = mod;
_state = Mod.Manager.NewDirectoryValid( mod.ModPath.Name, _currentModDirectory, out _ );
}
@ -262,8 +225,7 @@ public partial class ConfigWindow
if( ImGuiUtil.DrawDisabledButton( "Rename Mod Directory", buttonSize, tt, disabled ) && _currentModDirectory != null )
{
Penumbra.ModManager.MoveModDirectory( mod.Index, _currentModDirectory );
_currentModDirectory = null;
_state = Mod.Manager.NewDirectoryState.Identical;
Reset();
}
ImGui.SameLine();
@ -372,14 +334,6 @@ public partial class ConfigWindow
ImGui.SameLine();
if( ImGuiUtil.DrawDisabledButton( FontAwesomeIcon.Edit.ToIconString(), _window._iconButtonSize,
"Edit group description.", false, true ) )
{
_delayedActions.Enqueue( () => DescriptionEdit.OpenPopup( _mod, groupIdx ) );
}
ImGui.SameLine();
if( Input.Priority( "##Priority", groupIdx, Input.None, group.Priority, out var priority, 50 * ImGuiHelpers.GlobalScale ) )
{
Penumbra.ModManager.ChangeGroupPriority( _mod, groupIdx, priority );
@ -407,6 +361,14 @@ public partial class ConfigWindow
_delayedActions.Enqueue( () => Penumbra.ModManager.MoveModGroup( _mod, groupIdx, groupIdx + 1 ) );
}
ImGui.SameLine();
if( ImGuiUtil.DrawDisabledButton( FontAwesomeIcon.Edit.ToIconString(), _window._iconButtonSize,
"Edit group description.", false, true ) )
{
_delayedActions.Enqueue( () => DescriptionEdit.OpenPopup( _mod, groupIdx ) );
}
ImGui.SameLine();
var fileName = group.FileName( _mod.ModPath, groupIdx );
var fileExists = File.Exists( fileName );
@ -433,9 +395,17 @@ public partial class ConfigWindow
private static int _dragDropGroupIdx = -1;
private static int _dragDropOptionIdx = -1;
public static void Reset()
{
_newOptionNameIdx = -1;
_newOptionName = string.Empty;
_dragDropGroupIdx = -1;
_dragDropOptionIdx = -1;
}
public static void Draw( ModPanel panel, int groupIdx )
{
using var table = ImRaii.Table( string.Empty, 5, ImGuiTableFlags.SizingFixedFit );
using var table = ImRaii.Table( string.Empty, 4, ImGuiTableFlags.SizingFixedFit );
if( !table )
{
return;
@ -445,7 +415,6 @@ public partial class ConfigWindow
ImGui.TableSetupColumn( "name", ImGuiTableColumnFlags.WidthFixed,
panel._window._inputTextWidth.X - 62 * ImGuiHelpers.GlobalScale );
ImGui.TableSetupColumn( "delete", ImGuiTableColumnFlags.WidthFixed, panel._window._iconButtonSize.X );
ImGui.TableSetupColumn( "edit", ImGuiTableColumnFlags.WidthFixed, panel._window._iconButtonSize.X );
ImGui.TableSetupColumn( "priority", ImGuiTableColumnFlags.WidthFixed, 50 * ImGuiHelpers.GlobalScale );
var group = panel._mod.Groups[ groupIdx ];
@ -481,15 +450,6 @@ public partial class ConfigWindow
panel._delayedActions.Enqueue( () => Penumbra.ModManager.DeleteOption( panel._mod, groupIdx, optionIdx ) );
}
ImGui.TableNextColumn();
if( ImGuiUtil.DrawDisabledButton( FontAwesomeIcon.Edit.ToIconString(), panel._window._iconButtonSize,
"Edit this option.", false, true ) )
{
panel._window.ModEditPopup.ChangeMod( panel._mod );
panel._window.ModEditPopup.ChangeOption( groupIdx, optionIdx );
panel._window.ModEditPopup.IsOpen = true;
}
ImGui.TableNextColumn();
if( group.Type == SelectType.Multi )
{
@ -621,8 +581,16 @@ public partial class ConfigWindow
// Temporary strings
private static string? _currentEdit;
private static int? _currentGroupPriority;
private static int _currentField = -1;
private static int _optionIndex = -1;
private static int _currentField = None;
private static int _optionIndex = None;
public static void Reset()
{
_currentEdit = null;
_currentGroupPriority = null;
_currentField = None;
_optionIndex = None;
}
public static bool Text( string label, int field, int option, string oldValue, out string value, uint maxLength, float width )
{
@ -638,10 +606,8 @@ public partial class ConfigWindow
if( ImGui.IsItemDeactivatedAfterEdit() && _currentEdit != null )
{
var ret = _currentEdit != oldValue;
value = _currentEdit;
_currentEdit = null;
_currentField = None;
_optionIndex = None;
value = _currentEdit;
Reset();
return ret;
}
@ -663,10 +629,8 @@ public partial class ConfigWindow
if( ImGui.IsItemDeactivatedAfterEdit() && _currentGroupPriority != null )
{
var ret = _currentGroupPriority != oldValue;
value = _currentGroupPriority.Value;
_currentGroupPriority = null;
_currentField = None;
_optionIndex = None;
value = _currentGroupPriority.Value;
Reset();
return ret;
}

View file

@ -40,15 +40,15 @@ public partial class ConfigWindow
}
catch( Exception e )
{
PluginLog.Error($"Exception thrown during ModPanel Render:\n{e}" );
PluginLog.Error($"{Penumbra.ModManager.Count} Mods\n"
PluginLog.Error( $"Exception thrown during ModPanel Render:\n{e}" );
PluginLog.Error( $"{Penumbra.ModManager.Count} Mods\n"
+ $"{Penumbra.CollectionManager.Current.Name} Current Collection\n"
+ $"{Penumbra.CollectionManager.Current.Settings.Count} Settings\n"
+ $"{_selector.SortMode} Sort Mode\n"
+ $"{_selector.SelectedLeaf?.Name ?? "NULL"} Selected Leaf\n"
+ $"{_selector.Selected?.Name ?? "NULL"} Selected Mod\n"
+ $"{string.Join(", ", Penumbra.CollectionManager.Current.Inheritance)} Inheritances\n"
+ $"{_selector.SelectedSettingCollection.Name} Collection\n");
+ $"{_selector.Selected?.Name ?? "NULL"} Selected Mod\n"
+ $"{string.Join( ", ", Penumbra.CollectionManager.Current.Inheritance )} Inheritances\n"
+ $"{_selector.SelectedSettingCollection.Name} Collection\n" );
}
}
@ -62,7 +62,7 @@ public partial class ConfigWindow
ImGui.SameLine();
DrawInheritedCollectionButton( 3 * buttonSize );
ImGui.SameLine();
DrawCollectionSelector( "##collection", 2 * buttonSize.X, ModCollection.Type.Current, false, null );
DrawCollectionSelector( "##collectionSelector", 2 * buttonSize.X, ModCollection.Type.Current, false, null );
}
private static void DrawDefaultCollectionButton( Vector2 width )
@ -148,5 +148,28 @@ public partial class ConfigWindow
UpdateSettingsData( selector );
UpdateModData();
}
public void OnSelectionChange( Mod? old, Mod? mod, in ModFileSystemSelector.ModState _ )
{
if( old == mod )
{
return;
}
if( mod == null )
{
_window.ModEditPopup.IsOpen = false;
}
else if( _window.ModEditPopup.IsOpen )
{
_window.ModEditPopup.ChangeMod( mod );
}
_currentPriority = null;
MoveDirectory.Reset();
OptionTable.Reset();
Input.Reset();
AddOptionGroup.Reset();
}
}
}

View file

@ -26,14 +26,15 @@ public sealed partial class ConfigWindow : Window, IDisposable
public ConfigWindow( Penumbra penumbra )
: base( GetLabel() )
{
_penumbra = penumbra;
_settingsTab = new SettingsTab( this );
_selector = new ModFileSystemSelector( _penumbra.ModFileSystem );
_modPanel = new ModPanel( this );
_collectionsTab = new CollectionsTab( this );
_effectiveTab = new EffectiveTab();
_debugTab = new DebugTab( this );
_resourceTab = new ResourceTab( this );
_penumbra = penumbra;
_settingsTab = new SettingsTab( this );
_selector = new ModFileSystemSelector( _penumbra.ModFileSystem );
_modPanel = new ModPanel( this );
_selector.SelectionChanged += _modPanel.OnSelectionChange;
_collectionsTab = new CollectionsTab( this );
_effectiveTab = new EffectiveTab();
_debugTab = new DebugTab( this );
_resourceTab = new ResourceTab( this );
Dalamud.PluginInterface.UiBuilder.DisableGposeUiHide = true;
Dalamud.PluginInterface.UiBuilder.DisableCutsceneUiHide = true;