@@ -237,11 +237,15 @@ private static Dictionary<string, List<NModMenuRow>> GroupRows(List<NModMenuRow>
237237 private static void BuildGroupHeaders ( Control container , Dictionary < string , List < NModMenuRow > > groups )
238238 {
239239 int idx = 0 ;
240- foreach ( var kvp in groups )
240+ var orderedGroups = new List < string > { "Unassigned" } ;
241+ orderedGroups . AddRange ( ProfileManager . CustomGroups ) ;
242+
243+ foreach ( var grpName in orderedGroups )
241244 {
242- string grpName = kvp . Key ;
245+ if ( ! groups . TryGetValue ( grpName , out var groupRows ) )
246+ continue ;
243247
244- if ( grpName == "Unassigned" && kvp . Value . Count == 0 )
248+ if ( grpName == "Unassigned" && groupRows . Count == 0 )
245249 continue ;
246250
247251 bool isCollapsed = ProfileManager . CollapsedGroups . Contains ( grpName ) ;
@@ -266,7 +270,7 @@ private static void BuildGroupHeaders(Control container, Dictionary<string, List
266270 header . AddChild ( collapseBtn ) ;
267271
268272 bool allEnabled = true ;
269- foreach ( var r in kvp . Value )
273+ foreach ( var r in groupRows )
270274 {
271275 var tick = r . GetNodeOrNull < NTickbox > ( "Tickbox" ) ;
272276 if ( tick != null && ! ( bool ) tick . Get ( "IsTicked" ) ) allEnabled = false ;
@@ -277,6 +281,18 @@ private static void BuildGroupHeaders(Control container, Dictionary<string, List
277281
278282 if ( grpName != "Unassigned" )
279283 {
284+ var renameBtn = new Button { Text = "Rename" } ;
285+ renameBtn . Pressed += ( ) => RenameGroup ( grpName ) ;
286+ header . AddChild ( renameBtn ) ;
287+
288+ var upBtn = new Button { Text = "^" } ;
289+ upBtn . Pressed += ( ) => MoveGroup ( grpName , - 1 ) ;
290+ header . AddChild ( upBtn ) ;
291+
292+ var downBtn = new Button { Text = "v" } ;
293+ downBtn . Pressed += ( ) => MoveGroup ( grpName , 1 ) ;
294+ header . AddChild ( downBtn ) ;
295+
280296 var deleteBtn = new Button { Text = "Del" } ;
281297 deleteBtn . Pressed += ( ) => {
282298 ProfileManager . CustomGroups . Remove ( grpName ) ;
@@ -291,14 +307,72 @@ private static void BuildGroupHeaders(Control container, Dictionary<string, List
291307 container . AddChild ( header ) ;
292308 container . MoveChild ( header , idx ++ ) ;
293309
294- foreach ( var row in kvp . Value )
310+ foreach ( var row in groupRows )
295311 {
296312 container . MoveChild ( row , idx ++ ) ;
297313 row . Visible = ! isCollapsed ;
298314 }
299315 }
300316 }
301317
318+ private static void MoveGroup ( string grpName , int direction )
319+ {
320+ int idx = ProfileManager . CustomGroups . IndexOf ( grpName ) ;
321+ if ( idx == - 1 ) return ;
322+ int newIdx = idx + direction ;
323+ if ( newIdx >= 0 && newIdx < ProfileManager . CustomGroups . Count )
324+ {
325+ ProfileManager . CustomGroups . RemoveAt ( idx ) ;
326+ ProfileManager . CustomGroups . Insert ( newIdx , grpName ) ;
327+ ProfileManager . SaveProfiles ( ) ;
328+ RefreshGroupsUI ( ) ;
329+ }
330+ }
331+
332+ private static void RenameGroup ( string oldName )
333+ {
334+ if ( _currentScreen == null || ! GodotObject . IsInstanceValid ( _currentScreen ) ) return ;
335+
336+ var popup = new AcceptDialog ( ) ;
337+ popup . Title = "Rename Group" ;
338+ popup . DialogText = "" ;
339+
340+ var input = new LineEdit
341+ {
342+ Text = oldName ,
343+ CustomMinimumSize = new Vector2 ( 250 , 0 )
344+ } ;
345+ popup . AddChild ( input ) ;
346+
347+ popup . Confirmed += ( ) =>
348+ {
349+ var newName = input . Text . Trim ( ) ;
350+ if ( ! string . IsNullOrEmpty ( newName ) && newName != "Unassigned" && ! ProfileManager . CustomGroups . Contains ( newName ) )
351+ {
352+ int idx = ProfileManager . CustomGroups . IndexOf ( oldName ) ;
353+ if ( idx != - 1 )
354+ {
355+ ProfileManager . CustomGroups [ idx ] = newName ;
356+
357+ var grpMods = ProfileManager . ModGroups . Where ( x => x . Value == oldName ) . Select ( x => x . Key ) . ToList ( ) ;
358+ foreach ( var m in grpMods ) ProfileManager . ModGroups [ m ] = newName ;
359+
360+ if ( ProfileManager . CollapsedGroups . Contains ( oldName ) )
361+ {
362+ ProfileManager . CollapsedGroups . Remove ( oldName ) ;
363+ ProfileManager . CollapsedGroups . Add ( newName ) ;
364+ }
365+
366+ ProfileManager . SaveProfiles ( ) ;
367+ RefreshGroupsUI ( ) ;
368+ }
369+ }
370+ } ;
371+
372+ _currentScreen . AddChild ( popup ) ;
373+ popup . PopupCentered ( new Vector2I ( 300 , 100 ) ) ;
374+ }
375+
302376 public static void MoveModOrder ( string modId , int direction , NModMenuRow rowNode )
303377 {
304378 var options = SaveManager . Instance . SettingsSave . ModSettings ;
0 commit comments