From 5af1c6aca223533ace818dd1cca92aad1c599bf6 Mon Sep 17 00:00:00 2001 From: GitHusbando Date: Mon, 23 Feb 2026 13:10:35 -0800 Subject: [PATCH 1/4] Made the bare beginnings of an editor for the genre substitutions file Currently, it can save and load correctly-formatted json files, but can't actually edit them. --- .../genre_substitution_wizard.gd | 87 +++++++++++++++++++ .../genre_substitution_wizard.tscn | 54 ++++++++++++ 2 files changed, 141 insertions(+) create mode 100644 Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.gd create mode 100644 Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.tscn diff --git a/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.gd b/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.gd new file mode 100644 index 00000000..dc8e1863 --- /dev/null +++ b/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.gd @@ -0,0 +1,87 @@ +extends Control + +export var display_tree_path : NodePath +onready var display_tree = get_node(display_tree_path) + +export var file_dialog_path : NodePath +onready var file_dialog = get_node(file_dialog_path) + +var replacements_dict : Dictionary = {} +var genre_array : Array = [] # doesn't seem strictly necessary; for export into expected format + + +# Called when the node enters the scene tree for the first time. +func _ready(): + display_tree.set_hide_root(true) + +func _get_data_as_json(): + var json_data = {"GENRES":genre_array, "REPLACEMENTS":replacements_dict} + return to_json(json_data) + +func _load_data_from_json(json_text): + var parsed_json = parse_json(json_text) + print(parsed_json) + replacements_dict = parsed_json.get("REPLACEMENTS") + genre_array = parsed_json.get("GENRES") + +func _add_genre(genre_name : String): + # add genre to genre_dict + if (genre_array.has(genre_name)): + print("that genre already exists!") + return + + genre_array.append(genre_name) + replacements_dict[genre_name] = {} + +func _remove_genre(genre_name: String): + # doesn't cause any problems if the genre_name isn't there + genre_array.erase(genre_name) + replacements_dict.erase(genre_name) + +# also works to override an existing replacement; will add a genre if it doesn't exist because why not? +func _add_replacement(genre_name:String, generic:String, replacement:String): + if !replacements_dict.has(genre_name): + _add_genre(genre_name) + replacements_dict[genre_name][generic] = replacement + +func _remove_replacement(genre_name:String, generic:String): + replacements_dict[genre_name].erase(generic) + + +func _fill_tree(): # why, yes, i am iterating through dicts. cry about it + for genre in replacements_dict.keys(): + var genre_node = display_tree.create_item(display_tree.get_root()) + genre_node.set_text(0, genre) + for generic in replacements_dict[genre].keys(): + var replacement = replacements_dict[genre][generic] + var replacement_node = display_tree.create_item(genre_node) + replacement_node.set_text(0, generic + " -> " + replacement) + +func _refresh_tree(): + display_tree.clear() + var root_node = display_tree.create_item() + root_node.set_text(0,"Genres") + + +func _on_LoadButton_pressed(): + file_dialog.set_mode(FileDialog.MODE_OPEN_FILE) + file_dialog.popup() + +func _on_SaveButton_pressed(): + file_dialog.set_mode(FileDialog.MODE_SAVE_FILE) + file_dialog.popup() + +func _on_FileDialog_file_selected(path): + var file = File.new() + if file_dialog.get_mode() == FileDialog.MODE_OPEN_FILE: + file.open(path, File.READ) + var file_text = file.get_as_text() + _load_data_from_json(file_text) + _refresh_tree() + _fill_tree() + elif file_dialog.get_mode() == FileDialog.MODE_SAVE_FILE: + if file.file_exists(path): + print("existing file; jusst fyi it's gonna overwrite") + file.open(path, File.WRITE) + file.store_string(_get_data_as_json()) + file.close() diff --git a/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.tscn b/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.tscn new file mode 100644 index 00000000..738fc4bf --- /dev/null +++ b/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.tscn @@ -0,0 +1,54 @@ +[gd_scene load_steps=2 format=2] + +[ext_resource path="res://screens/wizards/genre_substitution/genre_substitution_wizard.gd" type="Script" id=1] + +[node name="GenreSubstitutionWizard" type="Control"] +script = ExtResource( 1 ) +display_tree_path = NodePath("VBoxContainer/DisplayTree") +file_dialog_path = NodePath("FileDialog") + +[node name="FileDialog" type="FileDialog" parent="."] +visible = true +popup_exclusive = true +window_title = "Open a File" +resizable = true +mode = 0 +access = 2 + +[node name="VBoxContainer" type="VBoxContainer" parent="."] +margin_right = 1024.0 +margin_bottom = 600.0 +size_flags_horizontal = 3 +size_flags_vertical = 3 + +[node name="HBoxContainer" type="HBoxContainer" parent="VBoxContainer"] +margin_right = 1024.0 +margin_bottom = 298.0 +size_flags_horizontal = 3 +size_flags_vertical = 3 + +[node name="LoadButton" type="Button" parent="VBoxContainer/HBoxContainer"] +margin_right = 510.0 +margin_bottom = 298.0 +size_flags_horizontal = 3 +size_flags_vertical = 3 +text = "Load" + +[node name="SaveButton" type="Button" parent="VBoxContainer/HBoxContainer"] +margin_left = 514.0 +margin_right = 1024.0 +margin_bottom = 298.0 +size_flags_horizontal = 3 +size_flags_vertical = 3 +text = "Save" + +[node name="DisplayTree" type="Tree" parent="VBoxContainer"] +margin_top = 302.0 +margin_right = 1024.0 +margin_bottom = 600.0 +size_flags_horizontal = 3 +size_flags_vertical = 3 + +[connection signal="file_selected" from="FileDialog" to="." method="_on_FileDialog_file_selected"] +[connection signal="pressed" from="VBoxContainer/HBoxContainer/LoadButton" to="." method="_on_LoadButton_pressed"] +[connection signal="pressed" from="VBoxContainer/HBoxContainer/SaveButton" to="." method="_on_SaveButton_pressed"] From 4b28687f771033494dacf794c925aba766b41c18 Mon Sep 17 00:00:00 2001 From: GitHusbando Date: Sun, 8 Mar 2026 16:57:37 -0700 Subject: [PATCH 2/4] Made a scene for creating/editing genre substitution JSONs There's no main menu, so the scene needs to be launched directly. There are buttons for loading, saving, and creating new genre substitution files. It seems to work as intended, but isn't especially user-friendly. Also changed some project settings so the scene can expand with the window. --- ...e.png-98a4c039ca15f3d568027e4f1424e999.md5 | 3 + ....png-98a4c039ca15f3d568027e4f1424e999.stex | Bin 0 -> 74 bytes ...e.png-15cbc37d7deab63dc33e5542837efac4.md5 | 3 + ....png-15cbc37d7deab63dc33e5542837efac4.stex | Bin 0 -> 72 bytes .../Main/assets/add_button_texture.png | Bin 0 -> 445 bytes .../Main/assets/add_button_texture.png.import | 35 ++++ .../Main/assets/remove_button_texture.png | Bin 0 -> 445 bytes .../assets/remove_button_texture.png.import | 35 ++++ Phase2/Godot_Toolset/Main/project.godot | 5 + .../genre_substitution_wizard.gd | 149 +++++++++++++----- .../genre_substitution_wizard.tscn | 69 +++++--- 11 files changed, 236 insertions(+), 63 deletions(-) create mode 100644 Phase2/Godot_Toolset/Main/.import/add_button_texture.png-98a4c039ca15f3d568027e4f1424e999.md5 create mode 100644 Phase2/Godot_Toolset/Main/.import/add_button_texture.png-98a4c039ca15f3d568027e4f1424e999.stex create mode 100644 Phase2/Godot_Toolset/Main/.import/remove_button_texture.png-15cbc37d7deab63dc33e5542837efac4.md5 create mode 100644 Phase2/Godot_Toolset/Main/.import/remove_button_texture.png-15cbc37d7deab63dc33e5542837efac4.stex create mode 100644 Phase2/Godot_Toolset/Main/assets/add_button_texture.png create mode 100644 Phase2/Godot_Toolset/Main/assets/add_button_texture.png.import create mode 100644 Phase2/Godot_Toolset/Main/assets/remove_button_texture.png create mode 100644 Phase2/Godot_Toolset/Main/assets/remove_button_texture.png.import diff --git a/Phase2/Godot_Toolset/Main/.import/add_button_texture.png-98a4c039ca15f3d568027e4f1424e999.md5 b/Phase2/Godot_Toolset/Main/.import/add_button_texture.png-98a4c039ca15f3d568027e4f1424e999.md5 new file mode 100644 index 00000000..82b9daa2 --- /dev/null +++ b/Phase2/Godot_Toolset/Main/.import/add_button_texture.png-98a4c039ca15f3d568027e4f1424e999.md5 @@ -0,0 +1,3 @@ +source_md5="3386c5f924ab454d044de923826a8863" +dest_md5="89c345643a6ed38f4f5e69c507b3a7fe" + diff --git a/Phase2/Godot_Toolset/Main/.import/add_button_texture.png-98a4c039ca15f3d568027e4f1424e999.stex b/Phase2/Godot_Toolset/Main/.import/add_button_texture.png-98a4c039ca15f3d568027e4f1424e999.stex new file mode 100644 index 0000000000000000000000000000000000000000..5a50a8cb5488a38d1e4fe8d37a8aaec7b10bd50a GIT binary patch literal 74 zcmZ>F2@c_4U|;}Y2vA^W1Tyr1INa4KAjs3rO$o{l3$XAJ1+w+o4=@Vw8~p!l|Npam NyT!43m;cPn3;=@{4^jXC literal 0 HcmV?d00001 diff --git a/Phase2/Godot_Toolset/Main/.import/remove_button_texture.png-15cbc37d7deab63dc33e5542837efac4.md5 b/Phase2/Godot_Toolset/Main/.import/remove_button_texture.png-15cbc37d7deab63dc33e5542837efac4.md5 new file mode 100644 index 00000000..e70fef90 --- /dev/null +++ b/Phase2/Godot_Toolset/Main/.import/remove_button_texture.png-15cbc37d7deab63dc33e5542837efac4.md5 @@ -0,0 +1,3 @@ +source_md5="a53ac63cf06100eacb004d186a71fced" +dest_md5="1d771ff18448ae2586bc9f65bb2ac41a" + diff --git a/Phase2/Godot_Toolset/Main/.import/remove_button_texture.png-15cbc37d7deab63dc33e5542837efac4.stex b/Phase2/Godot_Toolset/Main/.import/remove_button_texture.png-15cbc37d7deab63dc33e5542837efac4.stex new file mode 100644 index 0000000000000000000000000000000000000000..73c901e0ee5f0c926e129a68d322da98cbdff5d1 GIT binary patch literal 72 zcmZ>F2@c_4U|;}Y2vA^W1Tu7hINa4KAjs3rO##Xd3$XAJ0kZYk4=@Vw8~p!l|Npam L`;7k`|Jd08XLS#; literal 0 HcmV?d00001 diff --git a/Phase2/Godot_Toolset/Main/assets/add_button_texture.png b/Phase2/Godot_Toolset/Main/assets/add_button_texture.png new file mode 100644 index 0000000000000000000000000000000000000000..811e977690d00bad667d0a0f61d43e4ba9274574 GIT binary patch literal 445 zcmeAS@N?(olHy`uVBq!ia0vp^93afW1|*O0@9PFqjKx9jPK-BC>eK@{Ea{HEjtmSN z`?>!lvI6-E$sR$z3=CCj3=9n|3=F@3LJcn%7)lKo7+xhXFj&oCU=S~uvn$XBD8X6a z5n0T@pr;JNj1^1m%YcIHC7!;n?5~&^g{3vvzI@yPv`^U6#W6%el97Y)`#+!x1o#gH y2oVMbCS(paHbDi9AXBmFgozO}0j3a4)5eik)(ii5aQK8M$O=zaKbLh*2~7Y2uRq!V literal 0 HcmV?d00001 diff --git a/Phase2/Godot_Toolset/Main/assets/add_button_texture.png.import b/Phase2/Godot_Toolset/Main/assets/add_button_texture.png.import new file mode 100644 index 00000000..32394ffc --- /dev/null +++ b/Phase2/Godot_Toolset/Main/assets/add_button_texture.png.import @@ -0,0 +1,35 @@ +[remap] + +importer="texture" +type="StreamTexture" +path="res://.import/add_button_texture.png-98a4c039ca15f3d568027e4f1424e999.stex" +metadata={ +"vram_texture": false +} + +[deps] + +source_file="res://assets/add_button_texture.png" +dest_files=[ "res://.import/add_button_texture.png-98a4c039ca15f3d568027e4f1424e999.stex" ] + +[params] + +compress/mode=0 +compress/lossy_quality=0.7 +compress/hdr_mode=0 +compress/bptc_ldr=0 +compress/normal_map=0 +flags/repeat=0 +flags/filter=false +flags/mipmaps=false +flags/anisotropic=false +flags/srgb=2 +process/fix_alpha_border=true +process/premult_alpha=false +process/HDR_as_SRGB=false +process/invert_color=false +process/normal_map_invert_y=false +stream=false +size_limit=0 +detect_3d=true +svg/scale=1.0 diff --git a/Phase2/Godot_Toolset/Main/assets/remove_button_texture.png b/Phase2/Godot_Toolset/Main/assets/remove_button_texture.png new file mode 100644 index 0000000000000000000000000000000000000000..bedb7c02638e0e980dbb7c2bb46d69ea174e110b GIT binary patch literal 445 zcmeAS@N?(olHy`uVBq!ia0vp^93afW1|*O0@9PFqjKx9jPK-BC>eK@{Ea{HEjtmSN z`?>!lvI6-E$sR$z3=CCj3=9n|3=F@3LJcn%7)lKo7+xhXFj&oCU=S~uvn$XBD8X6a z5n0T@pr;JNj1^1m%YcIHC7!;n?5~(PL@iBsAAL~?v`^U6#W6%el97Y)`#+!xS_8)a gK!DE@CVY}~lI!whVc7WZkP^r`Pgg&ebxsLQ0OA}jumAu6 literal 0 HcmV?d00001 diff --git a/Phase2/Godot_Toolset/Main/assets/remove_button_texture.png.import b/Phase2/Godot_Toolset/Main/assets/remove_button_texture.png.import new file mode 100644 index 00000000..3d0335bd --- /dev/null +++ b/Phase2/Godot_Toolset/Main/assets/remove_button_texture.png.import @@ -0,0 +1,35 @@ +[remap] + +importer="texture" +type="StreamTexture" +path="res://.import/remove_button_texture.png-15cbc37d7deab63dc33e5542837efac4.stex" +metadata={ +"vram_texture": false +} + +[deps] + +source_file="res://assets/remove_button_texture.png" +dest_files=[ "res://.import/remove_button_texture.png-15cbc37d7deab63dc33e5542837efac4.stex" ] + +[params] + +compress/mode=0 +compress/lossy_quality=0.7 +compress/hdr_mode=0 +compress/bptc_ldr=0 +compress/normal_map=0 +flags/repeat=0 +flags/filter=false +flags/mipmaps=false +flags/anisotropic=false +flags/srgb=2 +process/fix_alpha_border=true +process/premult_alpha=false +process/HDR_as_SRGB=false +process/invert_color=false +process/normal_map_invert_y=false +stream=false +size_limit=0 +detect_3d=true +svg/scale=1.0 diff --git a/Phase2/Godot_Toolset/Main/project.godot b/Phase2/Godot_Toolset/Main/project.godot index 8e684ea2..dc609e5d 100644 --- a/Phase2/Godot_Toolset/Main/project.godot +++ b/Phase2/Godot_Toolset/Main/project.godot @@ -28,6 +28,11 @@ config/icon="res://icon.png" SpecialAbility="*res://middleware/specialabliities/SpecialAbility.gd" +[display] + +window/stretch/mode="viewport" +window/stretch/aspect="expand" + [global] filters=false diff --git a/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.gd b/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.gd index dc8e1863..d25cc970 100644 --- a/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.gd +++ b/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.gd @@ -6,56 +6,108 @@ onready var display_tree = get_node(display_tree_path) export var file_dialog_path : NodePath onready var file_dialog = get_node(file_dialog_path) -var replacements_dict : Dictionary = {} -var genre_array : Array = [] # doesn't seem strictly necessary; for export into expected format +export var add_button_texture : Texture +export var remove_button_texture : Texture + +#var replacements_dict : Dictionary = {} +#var genre_array : Array = [] # doesn't seem strictly necessary; for export into expected format # Called when the node enters the scene tree for the first time. func _ready(): display_tree.set_hide_root(true) + display_tree.columns = 4 + display_tree.set_column_min_width(0, 32) + display_tree.set_column_expand(0, false) + display_tree.set_column_min_width(2, 32) + display_tree.set_column_expand(2, false) + display_tree.connect("button_pressed", self, "_on_tree_button_pressed") func _get_data_as_json(): - var json_data = {"GENRES":genre_array, "REPLACEMENTS":replacements_dict} + var tree_dict = _display_tree_to_dict() + var json_data = {"GENRES":tree_dict.keys(), "REPLACEMENTS":tree_dict} return to_json(json_data) func _load_data_from_json(json_text): var parsed_json = parse_json(json_text) print(parsed_json) - replacements_dict = parsed_json.get("REPLACEMENTS") - genre_array = parsed_json.get("GENRES") + var replacements_dict = parsed_json.get("REPLACEMENTS") + #genre_array = parsed_json.get("GENRES") + _refresh_tree() + _fill_tree(replacements_dict) func _add_genre(genre_name : String): - # add genre to genre_dict - if (genre_array.has(genre_name)): - print("that genre already exists!") - return - - genre_array.append(genre_name) - replacements_dict[genre_name] = {} - -func _remove_genre(genre_name: String): - # doesn't cause any problems if the genre_name isn't there - genre_array.erase(genre_name) - replacements_dict.erase(genre_name) - -# also works to override an existing replacement; will add a genre if it doesn't exist because why not? -func _add_replacement(genre_name:String, generic:String, replacement:String): - if !replacements_dict.has(genre_name): - _add_genre(genre_name) - replacements_dict[genre_name][generic] = replacement - -func _remove_replacement(genre_name:String, generic:String): - replacements_dict[genre_name].erase(generic) - - -func _fill_tree(): # why, yes, i am iterating through dicts. cry about it + # add genre to tree + # todo: prevent duplicates???? + + var new_genre = display_tree.create_item(display_tree.get_root()) + new_genre.set_text(1, genre_name) + new_genre.set_editable(1, true) + new_genre.set_expand_right(1, true) + new_genre.add_button(0, remove_button_texture, -1, false, "Remove Genre") + + return new_genre + +func _add_replacement(genre_node, generic, replacement): + var new_replacement = display_tree.create_item(genre_node) + new_replacement.set_text(1, generic) + new_replacement.set_text(2, " -> ") + new_replacement.set_text(3, replacement) + + new_replacement.set_editable(1, true) + new_replacement.set_editable(3, true) + + new_replacement.set_selectable(2, false) + + new_replacement.add_button(0, remove_button_texture, -1, false, "Remove Replacement") + + return new_replacement + +func _add_genre_button(): + var add_genre_button = display_tree.create_item(display_tree.get_root()) + add_genre_button.add_button(0, add_button_texture, -1, false, "Add Genre") + add_genre_button.set_selectable(1, false) + add_genre_button.set_selectable(2, false) + add_genre_button.set_selectable(3, false) + +func _add_replacement_button(genre_node): + var add_replacement_button = display_tree.create_item(genre_node) + add_replacement_button.add_button(0, add_button_texture, -1, false, "Add Replacement") + add_replacement_button.set_selectable(1, false) + add_replacement_button.set_selectable(2, false) + add_replacement_button.set_selectable(3, false) + + +func _display_tree_to_dict(): + var tree_dict = {} # make a dict to store our tree in + var current_genre = display_tree.get_root().get_children() # the root exists to store our subtrees; we don't want it in the dict + + while current_genre != null: + var current_genre_text = current_genre.get_text(1) + if current_genre_text != "": # currently, the buttons are blank tree items with texture buttons in them, so we'll skip them + tree_dict[current_genre_text] = {} + var current_generic = current_genre.get_children() # fyi, get_children actually just gets the first child item + + while current_generic != null: + var current_generic_text = current_generic.get_text(1) + if current_generic_text != "": + tree_dict[current_genre_text][current_generic_text] = current_generic.get_text(3) + current_generic = current_generic.get_next() + + current_genre = current_genre.get_next() + return tree_dict + +func _fill_tree(replacements_dict): # why, yes, i am iterating through dicts. cry about it for genre in replacements_dict.keys(): - var genre_node = display_tree.create_item(display_tree.get_root()) - genre_node.set_text(0, genre) + var genre_node = _add_genre(genre) + for generic in replacements_dict[genre].keys(): var replacement = replacements_dict[genre][generic] - var replacement_node = display_tree.create_item(genre_node) - replacement_node.set_text(0, generic + " -> " + replacement) + _add_replacement(genre_node, generic, replacement) + + _add_replacement_button(genre_node) + _add_genre_button() + #_add_tree_buttons() func _refresh_tree(): display_tree.clear() @@ -65,7 +117,7 @@ func _refresh_tree(): func _on_LoadButton_pressed(): file_dialog.set_mode(FileDialog.MODE_OPEN_FILE) - file_dialog.popup() + file_dialog.popup_centered() func _on_SaveButton_pressed(): file_dialog.set_mode(FileDialog.MODE_SAVE_FILE) @@ -77,11 +129,34 @@ func _on_FileDialog_file_selected(path): file.open(path, File.READ) var file_text = file.get_as_text() _load_data_from_json(file_text) - _refresh_tree() - _fill_tree() + + #_fill_tree() elif file_dialog.get_mode() == FileDialog.MODE_SAVE_FILE: if file.file_exists(path): - print("existing file; jusst fyi it's gonna overwrite") + print("existing file; just fyi it's gonna overwrite") file.open(path, File.WRITE) file.store_string(_get_data_as_json()) file.close() + +func _on_NewButton_pressed(): + _refresh_tree() + _add_genre_button() + +func _on_tree_button_pressed(button_tree_item, column, id): + var button_index = button_tree_item.get_button_by_id(0, id) + var button_texture = button_tree_item.get_button(0, button_index) + + if button_texture == remove_button_texture: + button_tree_item.get_parent().remove_child(button_tree_item) + button_tree_item.free() + elif button_texture == add_button_texture: + if button_tree_item.get_parent() == display_tree.get_root(): + print("adding genre") + var new_genre_node = _add_genre("") + _add_replacement_button(new_genre_node) + else: + print("adding replacement") + _add_replacement(button_tree_item.get_parent(), "", "") + button_tree_item.move_to_bottom() + else: + print("unrecognized button! Initializing self-destruct sequence.") diff --git a/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.tscn b/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.tscn index 738fc4bf..11c83a1a 100644 --- a/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.tscn +++ b/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.tscn @@ -1,54 +1,71 @@ -[gd_scene load_steps=2 format=2] +[gd_scene load_steps=4 format=2] [ext_resource path="res://screens/wizards/genre_substitution/genre_substitution_wizard.gd" type="Script" id=1] +[ext_resource path="res://assets/add_button_texture.png" type="Texture" id=2] +[ext_resource path="res://assets/remove_button_texture.png" type="Texture" id=3] [node name="GenreSubstitutionWizard" type="Control"] +anchor_right = 1.0 +anchor_bottom = 1.0 +size_flags_horizontal = 7 +size_flags_vertical = 3 script = ExtResource( 1 ) -display_tree_path = NodePath("VBoxContainer/DisplayTree") +display_tree_path = NodePath("DisplayTree") file_dialog_path = NodePath("FileDialog") +add_button_texture = ExtResource( 2 ) +remove_button_texture = ExtResource( 3 ) [node name="FileDialog" type="FileDialog" parent="."] -visible = true +margin_right = 1024.0 +margin_bottom = 600.0 popup_exclusive = true window_title = "Open a File" resizable = true mode = 0 access = 2 -[node name="VBoxContainer" type="VBoxContainer" parent="."] -margin_right = 1024.0 -margin_bottom = 600.0 -size_flags_horizontal = 3 -size_flags_vertical = 3 +[node name="HBoxContainer" type="HBoxContainer" parent="."] +anchor_right = 1.0 +anchor_bottom = 0.125 -[node name="HBoxContainer" type="HBoxContainer" parent="VBoxContainer"] -margin_right = 1024.0 -margin_bottom = 298.0 -size_flags_horizontal = 3 -size_flags_vertical = 3 - -[node name="LoadButton" type="Button" parent="VBoxContainer/HBoxContainer"] -margin_right = 510.0 -margin_bottom = 298.0 +[node name="LoadButton" type="Button" parent="HBoxContainer"] +margin_right = 338.0 +margin_bottom = 75.0 +grow_horizontal = 2 +grow_vertical = 2 size_flags_horizontal = 3 size_flags_vertical = 3 text = "Load" -[node name="SaveButton" type="Button" parent="VBoxContainer/HBoxContainer"] -margin_left = 514.0 -margin_right = 1024.0 -margin_bottom = 298.0 +[node name="SaveButton" type="Button" parent="HBoxContainer"] +margin_left = 342.0 +margin_right = 681.0 +margin_bottom = 75.0 +grow_horizontal = 2 +grow_vertical = 2 size_flags_horizontal = 3 size_flags_vertical = 3 text = "Save" -[node name="DisplayTree" type="Tree" parent="VBoxContainer"] -margin_top = 302.0 +[node name="NewButton" type="Button" parent="HBoxContainer"] +margin_left = 685.0 margin_right = 1024.0 -margin_bottom = 600.0 +margin_bottom = 75.0 +grow_horizontal = 2 +grow_vertical = 2 +size_flags_horizontal = 3 +text = "New" + +[node name="DisplayTree" type="Tree" parent="."] +anchor_top = 0.125 +anchor_right = 1.0 +anchor_bottom = 1.0 +margin_right = 1.0 +margin_bottom = 1.0 size_flags_horizontal = 3 size_flags_vertical = 3 [connection signal="file_selected" from="FileDialog" to="." method="_on_FileDialog_file_selected"] -[connection signal="pressed" from="VBoxContainer/HBoxContainer/LoadButton" to="." method="_on_LoadButton_pressed"] -[connection signal="pressed" from="VBoxContainer/HBoxContainer/SaveButton" to="." method="_on_SaveButton_pressed"] +[connection signal="pressed" from="HBoxContainer/LoadButton" to="." method="_on_LoadButton_pressed"] +[connection signal="pressed" from="HBoxContainer/SaveButton" to="." method="_on_SaveButton_pressed"] +[connection signal="pressed" from="HBoxContainer/NewButton" to="." method="_on_NewButton_pressed"] From 27f928ed4cf547ba4c869b971a5809d0fad4cff4 Mon Sep 17 00:00:00 2001 From: GitHusbando Date: Sun, 15 Mar 2026 11:01:14 -0700 Subject: [PATCH 3/4] Button texture changes, added navigation Added a new set of textures for adding/removing genres to distinguish from the add/remove replacement buttons Created a main menu from which to open the wizards and added back buttons to return to the menu to the wizards Very slightly changed the layout of the character creation wizard because it was bothering me --- ...2.png-b44fd960bb4c5d20fcb1af17f813f357.md5 | 3 + ....png-b44fd960bb4c5d20fcb1af17f813f357.stex | Bin 0 -> 86 bytes ...2.png-0e5b8f541716f13afdc7ff9ae04ab75e.md5 | 3 + ....png-0e5b8f541716f13afdc7ff9ae04ab75e.stex | Bin 0 -> 86 bytes .../Main/assets/add_button_texture_2.png | Bin 0 -> 591 bytes .../assets/add_button_texture_2.png.import | 35 +++ .../Main/assets/remove_button_texture_2.png | Bin 0 -> 591 bytes .../assets/remove_button_texture_2.png.import | 35 +++ Phase2/Godot_Toolset/Main/project.godot | 2 +- .../Godot_Toolset/Main/screens/main_menu.tscn | 28 +++ .../character_creation_wizard.tscn | 12 +- .../genre_substitution_wizard.gd | 3 +- .../genre_substitution_wizard.tscn | 204 ++++++++++++++++-- .../user_interface/button_change_scene.gd | 10 + .../bcirpg_game_mvp_2024_0831A/project.godot | 6 +- 15 files changed, 321 insertions(+), 20 deletions(-) create mode 100644 Phase2/Godot_Toolset/Main/.import/add_button_texture_2.png-b44fd960bb4c5d20fcb1af17f813f357.md5 create mode 100644 Phase2/Godot_Toolset/Main/.import/add_button_texture_2.png-b44fd960bb4c5d20fcb1af17f813f357.stex create mode 100644 Phase2/Godot_Toolset/Main/.import/remove_button_texture_2.png-0e5b8f541716f13afdc7ff9ae04ab75e.md5 create mode 100644 Phase2/Godot_Toolset/Main/.import/remove_button_texture_2.png-0e5b8f541716f13afdc7ff9ae04ab75e.stex create mode 100644 Phase2/Godot_Toolset/Main/assets/add_button_texture_2.png create mode 100644 Phase2/Godot_Toolset/Main/assets/add_button_texture_2.png.import create mode 100644 Phase2/Godot_Toolset/Main/assets/remove_button_texture_2.png create mode 100644 Phase2/Godot_Toolset/Main/assets/remove_button_texture_2.png.import create mode 100644 Phase2/Godot_Toolset/Main/screens/main_menu.tscn create mode 100644 Phase2/Godot_Toolset/Main/user_interface/button_change_scene.gd diff --git a/Phase2/Godot_Toolset/Main/.import/add_button_texture_2.png-b44fd960bb4c5d20fcb1af17f813f357.md5 b/Phase2/Godot_Toolset/Main/.import/add_button_texture_2.png-b44fd960bb4c5d20fcb1af17f813f357.md5 new file mode 100644 index 00000000..a3dff158 --- /dev/null +++ b/Phase2/Godot_Toolset/Main/.import/add_button_texture_2.png-b44fd960bb4c5d20fcb1af17f813f357.md5 @@ -0,0 +1,3 @@ +source_md5="2c84ab820e6ab4fd3edac0e8021dc46b" +dest_md5="f999f4cf7e7b734127087a318237503c" + diff --git a/Phase2/Godot_Toolset/Main/.import/add_button_texture_2.png-b44fd960bb4c5d20fcb1af17f813f357.stex b/Phase2/Godot_Toolset/Main/.import/add_button_texture_2.png-b44fd960bb4c5d20fcb1af17f813f357.stex new file mode 100644 index 0000000000000000000000000000000000000000..b28440743c0622d075e6ae8c90a0dd9e83f44a7f GIT binary patch literal 86 zcmZ>F2@c_6U|;}Y2vA^W1Tw6EINa4KAjs3rO%KWr3$XA}1hVxx9he084gP<&|NmLO aT|r<0$8(=gm-cr2JFf9`;?w0*7#RR?c^1zA literal 0 HcmV?d00001 diff --git a/Phase2/Godot_Toolset/Main/.import/remove_button_texture_2.png-0e5b8f541716f13afdc7ff9ae04ab75e.md5 b/Phase2/Godot_Toolset/Main/.import/remove_button_texture_2.png-0e5b8f541716f13afdc7ff9ae04ab75e.md5 new file mode 100644 index 00000000..b8ff3506 --- /dev/null +++ b/Phase2/Godot_Toolset/Main/.import/remove_button_texture_2.png-0e5b8f541716f13afdc7ff9ae04ab75e.md5 @@ -0,0 +1,3 @@ +source_md5="feb0f2665450f2f4c618fb985bcc5ffc" +dest_md5="f5865bc9861031704e2be9e39c2f56ce" + diff --git a/Phase2/Godot_Toolset/Main/.import/remove_button_texture_2.png-0e5b8f541716f13afdc7ff9ae04ab75e.stex b/Phase2/Godot_Toolset/Main/.import/remove_button_texture_2.png-0e5b8f541716f13afdc7ff9ae04ab75e.stex new file mode 100644 index 0000000000000000000000000000000000000000..ae90e9a2a4fd2b9d2cca587d3026ad1bea21e02d GIT binary patch literal 86 zcmZ>F2@c_6U|;}Y2vA^W1Tw6EINa4KAjs3rO%KWr3$XA}1hVxx9he084gP<&|NmLO aJ>bGN-phyOi+3|CE&AUn9vsrc&Hw;sC={Il literal 0 HcmV?d00001 diff --git a/Phase2/Godot_Toolset/Main/assets/add_button_texture_2.png b/Phase2/Godot_Toolset/Main/assets/add_button_texture_2.png new file mode 100644 index 0000000000000000000000000000000000000000..3249e84f2bb8ee64eaa3bbca793fc9bd6497887a GIT binary patch literal 591 zcmeAS@N?(olHy`uVBq!ia0vp^AT}2V8<6ZZI=>f4F%}28J2BoosZ$T+u%tWsIx;Y9 z?C1WI$O_~uBzpw;GB8xBF)%c=FfjZA3N^f7U???UV0e|lz+g3lfkC`r&aOZkpaf@u zM`SSrgPt-7Ggd6MF9Qm)mw5WRvcF>H7i3`NbUO;PopGtBi(`m{B;zc`)PIaXC2;T` z2;dwbgAoXj`EWL}LS!~b0TWym0R{`YPGt2cawr^RRY+`*8ltUcL^l!UQ*?183m6!X nC6U=6MMPW8f?_0)gKiQ`es`Px%L|@U>Og!?S3j3^P6f4F%}28J2BoosZ$T+u%tWsIx;Y9 z?C1WI$O_~uBzpw;GB8xBF)%c=FfjZA3N^f7U???UV0e|lz+g3lfkC`r&aOZkpaf@u zM`SSrgPt-7Ggd6MF9Qm)mw5WRvcF>H7c^u&FMVhS(7vUfE{-7*l8mz$Q~v=~3>0Ae t4+KP6PK-j38YZGl11cikYGO^KzPjJr_`fdyw!0f-vZt$`%Q~loCID6mJmvrZ literal 0 HcmV?d00001 diff --git a/Phase2/Godot_Toolset/Main/assets/remove_button_texture_2.png.import b/Phase2/Godot_Toolset/Main/assets/remove_button_texture_2.png.import new file mode 100644 index 00000000..4d7cb033 --- /dev/null +++ b/Phase2/Godot_Toolset/Main/assets/remove_button_texture_2.png.import @@ -0,0 +1,35 @@ +[remap] + +importer="texture" +type="StreamTexture" +path="res://.import/remove_button_texture_2.png-0e5b8f541716f13afdc7ff9ae04ab75e.stex" +metadata={ +"vram_texture": false +} + +[deps] + +source_file="res://assets/remove_button_texture_2.png" +dest_files=[ "res://.import/remove_button_texture_2.png-0e5b8f541716f13afdc7ff9ae04ab75e.stex" ] + +[params] + +compress/mode=0 +compress/lossy_quality=0.7 +compress/hdr_mode=0 +compress/bptc_ldr=0 +compress/normal_map=0 +flags/repeat=0 +flags/filter=false +flags/mipmaps=false +flags/anisotropic=false +flags/srgb=2 +process/fix_alpha_border=true +process/premult_alpha=false +process/HDR_as_SRGB=false +process/invert_color=false +process/normal_map_invert_y=false +stream=false +size_limit=0 +detect_3d=true +svg/scale=1.0 diff --git a/Phase2/Godot_Toolset/Main/project.godot b/Phase2/Godot_Toolset/Main/project.godot index dc609e5d..b650b05a 100644 --- a/Phase2/Godot_Toolset/Main/project.godot +++ b/Phase2/Godot_Toolset/Main/project.godot @@ -21,7 +21,7 @@ _global_script_class_icons={ [application] config/name="bcirpg_toolset" -run/main_scene="res://screens/wizards/character_creation/character_creation_wizard.tscn" +run/main_scene="res://screens/main_menu.tscn" config/icon="res://icon.png" [autoload] diff --git a/Phase2/Godot_Toolset/Main/screens/main_menu.tscn b/Phase2/Godot_Toolset/Main/screens/main_menu.tscn new file mode 100644 index 00000000..bdcf59e2 --- /dev/null +++ b/Phase2/Godot_Toolset/Main/screens/main_menu.tscn @@ -0,0 +1,28 @@ +[gd_scene load_steps=2 format=2] + +[ext_resource path="res://user_interface/button_change_scene.gd" type="Script" id=1] + +[node name="menu" type="Control"] +anchor_right = 1.0 +anchor_bottom = 1.0 + +[node name="VBoxContainer" type="VBoxContainer" parent="."] +anchor_left = 0.333 +anchor_top = 0.125 +anchor_right = 0.666 +anchor_bottom = 0.875 + +[node name="ButtonCharacterCreation" type="Button" parent="VBoxContainer"] +margin_right = 340.0 +margin_bottom = 20.0 +text = "Character Creation" +script = ExtResource( 1 ) +next_scene_path = "res://screens/wizards/character_creation/character_creation_wizard.tscn" + +[node name="ButtonGenreSubstitution" type="Button" parent="VBoxContainer"] +margin_top = 24.0 +margin_right = 340.0 +margin_bottom = 44.0 +text = "Genre Substitution" +script = ExtResource( 1 ) +next_scene_path = "res://screens/wizards/genre_substitution/genre_substitution_wizard.tscn" diff --git a/Phase2/Godot_Toolset/Main/screens/wizards/character_creation/character_creation_wizard.tscn b/Phase2/Godot_Toolset/Main/screens/wizards/character_creation/character_creation_wizard.tscn index 606acce5..91553142 100644 --- a/Phase2/Godot_Toolset/Main/screens/wizards/character_creation/character_creation_wizard.tscn +++ b/Phase2/Godot_Toolset/Main/screens/wizards/character_creation/character_creation_wizard.tscn @@ -1,8 +1,9 @@ -[gd_scene load_steps=4 format=2] +[gd_scene load_steps=5 format=2] [ext_resource path="res://screens/wizards/character_creation/skills_option_button.gd" type="Script" id=1] [ext_resource path="res://screens/wizards/character_creation/specials_option_button.gd" type="Script" id=2] [ext_resource path="res://screens/wizards/character_creation/character_creation_wizard.gd" type="Script" id=3] +[ext_resource path="res://user_interface/button_change_scene.gd" type="Script" id=4] [node name="Control" type="Control"] anchor_right = 1.0 @@ -12,8 +13,6 @@ script = ExtResource( 3 ) [node name="ColorRect" type="ColorRect" parent="."] anchor_right = 1.0 anchor_bottom = 1.0 -margin_top = -6.0 -margin_bottom = -6.0 color = Color( 0.537255, 0.537255, 0.537255, 1 ) [node name="RootVBoxContainer" type="VBoxContainer" parent="."] @@ -685,5 +684,12 @@ margin_right = 400.0 margin_bottom = 368.0 text = "Export Character To Module" +[node name="ButtonBack" type="Button" parent="."] +margin_right = 12.0 +margin_bottom = 20.0 +text = "Back" +script = ExtResource( 4 ) +next_scene_path = "res://screens/main_menu.tscn" + [connection signal="pressed" from="RootVBoxContainer/TopHBoxContainer/RightVBoxContainer/VBoxContainer/Button" to="." method="_on_Button_pressed"] [connection signal="tree_entered" from="RootVBoxContainer/TopHBoxContainer/RightVBoxContainer/VBoxContainer/Button" to="." method="_on_Button_tree_entered"] diff --git a/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.gd b/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.gd index d25cc970..01661ce6 100644 --- a/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.gd +++ b/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.gd @@ -7,6 +7,7 @@ export var file_dialog_path : NodePath onready var file_dialog = get_node(file_dialog_path) export var add_button_texture : Texture +export var add_button_texture_2 : Texture export var remove_button_texture : Texture #var replacements_dict : Dictionary = {} @@ -65,7 +66,7 @@ func _add_replacement(genre_node, generic, replacement): func _add_genre_button(): var add_genre_button = display_tree.create_item(display_tree.get_root()) - add_genre_button.add_button(0, add_button_texture, -1, false, "Add Genre") + add_genre_button.add_button(0, add_button_texture_2, -1, false, "Add Genre") add_genre_button.set_selectable(1, false) add_genre_button.set_selectable(2, false) add_genre_button.set_selectable(3, false) diff --git a/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.tscn b/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.tscn index 11c83a1a..0d8729d7 100644 --- a/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.tscn +++ b/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.tscn @@ -1,19 +1,190 @@ -[gd_scene load_steps=4 format=2] +[gd_scene load_steps=7 format=2] -[ext_resource path="res://screens/wizards/genre_substitution/genre_substitution_wizard.gd" type="Script" id=1] +[ext_resource path="res://assets/remove_button_texture_2.png" type="Texture" id=1] [ext_resource path="res://assets/add_button_texture.png" type="Texture" id=2] [ext_resource path="res://assets/remove_button_texture.png" type="Texture" id=3] +[ext_resource path="res://assets/add_button_texture_2.png" type="Texture" id=4] +[ext_resource path="res://user_interface/button_change_scene.gd" type="Script" id=5] + +[sub_resource type="GDScript" id=1] +script/source = "extends Control + +export var display_tree_path : NodePath +onready var display_tree = get_node(display_tree_path) + +export var file_dialog_path : NodePath +onready var file_dialog = get_node(file_dialog_path) + +export var add_button_texture : Texture +export var add_button_texture_2 : Texture +export var remove_button_texture : Texture +export var remove_button_texture_2 : Texture + +#var replacements_dict : Dictionary = {} +#var genre_array : Array = [] # doesn't seem strictly necessary; for export into expected format + + +# Called when the node enters the scene tree for the first time. +func _ready(): + display_tree.set_hide_root(true) + display_tree.columns = 4 + display_tree.set_column_min_width(0, 32) + display_tree.set_column_expand(0, false) + display_tree.set_column_min_width(2, 32) + display_tree.set_column_expand(2, false) + display_tree.connect(\"button_pressed\", self, \"_on_tree_button_pressed\") + +func _get_data_as_json(): + var tree_dict = _display_tree_to_dict() + var json_data = {\"GENRES\":tree_dict.keys(), \"REPLACEMENTS\":tree_dict} + return to_json(json_data) + +func _load_data_from_json(json_text): + var parsed_json = parse_json(json_text) + print(parsed_json) + var replacements_dict = parsed_json.get(\"REPLACEMENTS\") + #genre_array = parsed_json.get(\"GENRES\") + _refresh_tree() + _fill_tree(replacements_dict) + +func _add_genre(genre_name : String): + # add genre to tree + # todo: prevent duplicates???? + + var new_genre = display_tree.create_item(display_tree.get_root()) + new_genre.set_text(1, genre_name) + new_genre.set_editable(1, true) + new_genre.set_expand_right(1, true) + new_genre.add_button(0, remove_button_texture_2, -1, false, \"Remove Genre\") + + return new_genre + +func _add_replacement(genre_node, generic, replacement): + var new_replacement = display_tree.create_item(genre_node) + new_replacement.set_text(1, generic) + new_replacement.set_text(2, \" -> \") + new_replacement.set_text(3, replacement) + + new_replacement.set_editable(1, true) + new_replacement.set_editable(3, true) + + new_replacement.set_selectable(2, false) + + new_replacement.add_button(0, remove_button_texture, -1, false, \"Remove Replacement\") + + return new_replacement + +func _add_genre_button(): + var add_genre_button = display_tree.create_item(display_tree.get_root()) + add_genre_button.add_button(0, add_button_texture_2, -1, false, \"Add Genre\") + add_genre_button.set_selectable(1, false) + add_genre_button.set_selectable(2, false) + add_genre_button.set_selectable(3, false) + +func _add_replacement_button(genre_node): + var add_replacement_button = display_tree.create_item(genre_node) + add_replacement_button.add_button(0, add_button_texture, -1, false, \"Add Replacement\") + add_replacement_button.set_selectable(1, false) + add_replacement_button.set_selectable(2, false) + add_replacement_button.set_selectable(3, false) + + +func _display_tree_to_dict(): + var tree_dict = {} # make a dict to store our tree in + var current_genre = display_tree.get_root().get_children() # the root exists to store our subtrees; we don't want it in the dict + + while current_genre != null: + var current_genre_text = current_genre.get_text(1) + if current_genre_text != \"\": # currently, the buttons are blank tree items with texture buttons in them, so we'll skip them + tree_dict[current_genre_text] = {} + var current_generic = current_genre.get_children() # fyi, get_children actually just gets the first child item + + while current_generic != null: + var current_generic_text = current_generic.get_text(1) + if current_generic_text != \"\": + tree_dict[current_genre_text][current_generic_text] = current_generic.get_text(3) + current_generic = current_generic.get_next() + + current_genre = current_genre.get_next() + return tree_dict + +func _fill_tree(replacements_dict): # why, yes, i am iterating through dicts. cry about it + for genre in replacements_dict.keys(): + var genre_node = _add_genre(genre) + + for generic in replacements_dict[genre].keys(): + var replacement = replacements_dict[genre][generic] + _add_replacement(genre_node, generic, replacement) + + _add_replacement_button(genre_node) + _add_genre_button() + #_add_tree_buttons() + +func _refresh_tree(): + display_tree.clear() + var root_node = display_tree.create_item() + root_node.set_text(0,\"Genres\") + + +func _on_LoadButton_pressed(): + file_dialog.set_mode(FileDialog.MODE_OPEN_FILE) + file_dialog.popup_centered() + +func _on_SaveButton_pressed(): + file_dialog.set_mode(FileDialog.MODE_SAVE_FILE) + file_dialog.popup() + +func _on_FileDialog_file_selected(path): + var file = File.new() + if file_dialog.get_mode() == FileDialog.MODE_OPEN_FILE: + file.open(path, File.READ) + var file_text = file.get_as_text() + _load_data_from_json(file_text) + + #_fill_tree() + elif file_dialog.get_mode() == FileDialog.MODE_SAVE_FILE: + if file.file_exists(path): + print(\"existing file; just fyi it's gonna overwrite\") + file.open(path, File.WRITE) + file.store_string(_get_data_as_json()) + file.close() + +func _on_NewButton_pressed(): + _refresh_tree() + _add_genre_button() + +func _on_tree_button_pressed(button_tree_item, column, id): + var button_index = button_tree_item.get_button_by_id(0, id) + var button_texture = button_tree_item.get_button(0, button_index) + + if button_texture == remove_button_texture || button_texture == remove_button_texture_2: + button_tree_item.get_parent().remove_child(button_tree_item) + button_tree_item.free() + elif button_texture == add_button_texture || button_texture == add_button_texture_2: + if button_tree_item.get_parent() == display_tree.get_root(): + print(\"adding genre\") + var new_genre_node = _add_genre(\"\") + _add_replacement_button(new_genre_node) + else: + print(\"adding replacement\") + _add_replacement(button_tree_item.get_parent(), \"\", \"\") + button_tree_item.move_to_bottom() + else: + print(\"unrecognized button! Initializing self-destruct sequence.\") +" [node name="GenreSubstitutionWizard" type="Control"] anchor_right = 1.0 anchor_bottom = 1.0 size_flags_horizontal = 7 size_flags_vertical = 3 -script = ExtResource( 1 ) +script = SubResource( 1 ) display_tree_path = NodePath("DisplayTree") file_dialog_path = NodePath("FileDialog") add_button_texture = ExtResource( 2 ) +add_button_texture_2 = ExtResource( 4 ) remove_button_texture = ExtResource( 3 ) +remove_button_texture_2 = ExtResource( 1 ) [node name="FileDialog" type="FileDialog" parent="."] margin_right = 1024.0 @@ -26,11 +197,20 @@ access = 2 [node name="HBoxContainer" type="HBoxContainer" parent="."] anchor_right = 1.0 -anchor_bottom = 0.125 +anchor_bottom = 0.075 + +[node name="BackButton" type="Button" parent="HBoxContainer"] +margin_right = 253.0 +margin_bottom = 45.0 +size_flags_horizontal = 3 +text = "Back" +script = ExtResource( 5 ) +next_scene_path = "res://screens/main_menu.tscn" [node name="LoadButton" type="Button" parent="HBoxContainer"] -margin_right = 338.0 -margin_bottom = 75.0 +margin_left = 257.0 +margin_right = 510.0 +margin_bottom = 45.0 grow_horizontal = 2 grow_vertical = 2 size_flags_horizontal = 3 @@ -38,9 +218,9 @@ size_flags_vertical = 3 text = "Load" [node name="SaveButton" type="Button" parent="HBoxContainer"] -margin_left = 342.0 -margin_right = 681.0 -margin_bottom = 75.0 +margin_left = 514.0 +margin_right = 767.0 +margin_bottom = 45.0 grow_horizontal = 2 grow_vertical = 2 size_flags_horizontal = 3 @@ -48,16 +228,16 @@ size_flags_vertical = 3 text = "Save" [node name="NewButton" type="Button" parent="HBoxContainer"] -margin_left = 685.0 +margin_left = 771.0 margin_right = 1024.0 -margin_bottom = 75.0 +margin_bottom = 45.0 grow_horizontal = 2 grow_vertical = 2 size_flags_horizontal = 3 text = "New" [node name="DisplayTree" type="Tree" parent="."] -anchor_top = 0.125 +anchor_top = 0.075 anchor_right = 1.0 anchor_bottom = 1.0 margin_right = 1.0 diff --git a/Phase2/Godot_Toolset/Main/user_interface/button_change_scene.gd b/Phase2/Godot_Toolset/Main/user_interface/button_change_scene.gd new file mode 100644 index 00000000..fbf63dff --- /dev/null +++ b/Phase2/Godot_Toolset/Main/user_interface/button_change_scene.gd @@ -0,0 +1,10 @@ +extends Button + + +export(String, FILE) var next_scene_path: = "" + +func _ready(): + connect("button_up", self, "_on_button_up") + +func _on_button_up(): + var _next_scene_load = get_tree().change_scene(next_scene_path) diff --git a/Phase2/MVP/Game/bcirpg_game_mvp_2024_0831A/project.godot b/Phase2/MVP/Game/bcirpg_game_mvp_2024_0831A/project.godot index 042e9f44..4a3e832a 100644 --- a/Phase2/MVP/Game/bcirpg_game_mvp_2024_0831A/project.godot +++ b/Phase2/MVP/Game/bcirpg_game_mvp_2024_0831A/project.godot @@ -120,17 +120,17 @@ GameCurrent="*res://globalScripts/gameCurrent.gd" open_file_hotkey={ "deadzone": 0.5, -"events": [ Object(InputEventKey,"resource_local_to_scene":false,"resource_name":"","device":0,"alt":false,"shift":false,"control":false,"meta":true,"command":true,"pressed":false,"scancode":0,"physical_scancode":79,"unicode":0,"echo":false,"script":null) +"events": [ Object(InputEventKey,"resource_local_to_scene":false,"resource_name":"","device":0,"alt":false,"shift":false,"control":true,"meta":true,"command":true,"pressed":false,"scancode":0,"physical_scancode":79,"unicode":0,"echo":false,"script":null) ] } save_character_file_hotkey={ "deadzone": 0.5, -"events": [ Object(InputEventKey,"resource_local_to_scene":false,"resource_name":"","device":0,"alt":false,"shift":false,"control":false,"meta":true,"command":true,"pressed":false,"scancode":0,"physical_scancode":83,"unicode":0,"echo":false,"script":null) +"events": [ Object(InputEventKey,"resource_local_to_scene":false,"resource_name":"","device":0,"alt":false,"shift":false,"control":true,"meta":true,"command":true,"pressed":false,"scancode":0,"physical_scancode":83,"unicode":0,"echo":false,"script":null) ] } back_to_main_menu_hotkey={ "deadzone": 0.5, -"events": [ Object(InputEventKey,"resource_local_to_scene":false,"resource_name":"","device":0,"alt":false,"shift":false,"control":false,"meta":true,"command":true,"pressed":false,"scancode":0,"physical_scancode":77,"unicode":0,"echo":false,"script":null) +"events": [ Object(InputEventKey,"resource_local_to_scene":false,"resource_name":"","device":0,"alt":false,"shift":false,"control":true,"meta":true,"command":true,"pressed":false,"scancode":0,"physical_scancode":77,"unicode":0,"echo":false,"script":null) ] } From 5e889b1a2ac730f8777d8a553bce36eca8c950a9 Mon Sep 17 00:00:00 2001 From: GitHusbando <67436617+GitHusbando@users.noreply.github.com> Date: Sun, 19 Apr 2026 15:02:44 -0700 Subject: [PATCH 4/4] redesigned the menu scene to allow opening wizards in separate windows this sort of ui seems a bit more toolset-like and hopefully serves as a better base for future additions the scenes themselves need to be reworked to be resizeable, but they already kind did --- .../Godot_Toolset/Main/screens/main_menu.tscn | 12 +- .../character_creation_wizard.tscn | 10 +- .../genre_substitution_wizard.tscn | 38 ++---- .../Main/user_interface/PersistentWindow.tscn | 126 ++++++++++++++++++ .../button_opene_scene_in_window.gd | 22 +++ .../Main/user_interface/move_parent.gd | 27 ++++ .../user_interface/remove_parent_button.gd | 4 + .../Main/user_interface/resize_parent.gd | 53 ++++++++ 8 files changed, 254 insertions(+), 38 deletions(-) create mode 100644 Phase2/Godot_Toolset/Main/user_interface/PersistentWindow.tscn create mode 100644 Phase2/Godot_Toolset/Main/user_interface/button_opene_scene_in_window.gd create mode 100644 Phase2/Godot_Toolset/Main/user_interface/move_parent.gd create mode 100644 Phase2/Godot_Toolset/Main/user_interface/remove_parent_button.gd create mode 100644 Phase2/Godot_Toolset/Main/user_interface/resize_parent.gd diff --git a/Phase2/Godot_Toolset/Main/screens/main_menu.tscn b/Phase2/Godot_Toolset/Main/screens/main_menu.tscn index bdcf59e2..193fb1f6 100644 --- a/Phase2/Godot_Toolset/Main/screens/main_menu.tscn +++ b/Phase2/Godot_Toolset/Main/screens/main_menu.tscn @@ -1,6 +1,6 @@ [gd_scene load_steps=2 format=2] -[ext_resource path="res://user_interface/button_change_scene.gd" type="Script" id=1] +[ext_resource path="res://user_interface/button_opene_scene_in_window.gd" type="Script" id=2] [node name="menu" type="Control"] anchor_right = 1.0 @@ -16,13 +16,15 @@ anchor_bottom = 0.875 margin_right = 340.0 margin_bottom = 20.0 text = "Character Creation" -script = ExtResource( 1 ) -next_scene_path = "res://screens/wizards/character_creation/character_creation_wizard.tscn" +script = ExtResource( 2 ) +scene_path = "res://screens/wizards/character_creation/character_creation_wizard.tscn" +window_title = "Character Editor" [node name="ButtonGenreSubstitution" type="Button" parent="VBoxContainer"] margin_top = 24.0 margin_right = 340.0 margin_bottom = 44.0 text = "Genre Substitution" -script = ExtResource( 1 ) -next_scene_path = "res://screens/wizards/genre_substitution/genre_substitution_wizard.tscn" +script = ExtResource( 2 ) +scene_path = "res://screens/wizards/genre_substitution/genre_substitution_wizard.tscn" +window_title = "Genre Substitution" diff --git a/Phase2/Godot_Toolset/Main/screens/wizards/character_creation/character_creation_wizard.tscn b/Phase2/Godot_Toolset/Main/screens/wizards/character_creation/character_creation_wizard.tscn index 91553142..77a78c91 100644 --- a/Phase2/Godot_Toolset/Main/screens/wizards/character_creation/character_creation_wizard.tscn +++ b/Phase2/Godot_Toolset/Main/screens/wizards/character_creation/character_creation_wizard.tscn @@ -1,9 +1,8 @@ -[gd_scene load_steps=5 format=2] +[gd_scene load_steps=4 format=2] [ext_resource path="res://screens/wizards/character_creation/skills_option_button.gd" type="Script" id=1] [ext_resource path="res://screens/wizards/character_creation/specials_option_button.gd" type="Script" id=2] [ext_resource path="res://screens/wizards/character_creation/character_creation_wizard.gd" type="Script" id=3] -[ext_resource path="res://user_interface/button_change_scene.gd" type="Script" id=4] [node name="Control" type="Control"] anchor_right = 1.0 @@ -684,12 +683,5 @@ margin_right = 400.0 margin_bottom = 368.0 text = "Export Character To Module" -[node name="ButtonBack" type="Button" parent="."] -margin_right = 12.0 -margin_bottom = 20.0 -text = "Back" -script = ExtResource( 4 ) -next_scene_path = "res://screens/main_menu.tscn" - [connection signal="pressed" from="RootVBoxContainer/TopHBoxContainer/RightVBoxContainer/VBoxContainer/Button" to="." method="_on_Button_pressed"] [connection signal="tree_entered" from="RootVBoxContainer/TopHBoxContainer/RightVBoxContainer/VBoxContainer/Button" to="." method="_on_Button_tree_entered"] diff --git a/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.tscn b/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.tscn index 0d8729d7..ff699616 100644 --- a/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.tscn +++ b/Phase2/Godot_Toolset/Main/screens/wizards/genre_substitution/genre_substitution_wizard.tscn @@ -1,10 +1,9 @@ -[gd_scene load_steps=7 format=2] +[gd_scene load_steps=6 format=2] [ext_resource path="res://assets/remove_button_texture_2.png" type="Texture" id=1] [ext_resource path="res://assets/add_button_texture.png" type="Texture" id=2] [ext_resource path="res://assets/remove_button_texture.png" type="Texture" id=3] [ext_resource path="res://assets/add_button_texture_2.png" type="Texture" id=4] -[ext_resource path="res://user_interface/button_change_scene.gd" type="Script" id=5] [sub_resource type="GDScript" id=1] script/source = "extends Control @@ -195,21 +194,21 @@ resizable = true mode = 0 access = 2 +[node name="DisplayTree" type="Tree" parent="."] +anchor_top = 0.075 +anchor_right = 1.0 +anchor_bottom = 1.0 +margin_right = 1.0 +margin_bottom = 1.0 +size_flags_horizontal = 3 +size_flags_vertical = 3 + [node name="HBoxContainer" type="HBoxContainer" parent="."] anchor_right = 1.0 anchor_bottom = 0.075 -[node name="BackButton" type="Button" parent="HBoxContainer"] -margin_right = 253.0 -margin_bottom = 45.0 -size_flags_horizontal = 3 -text = "Back" -script = ExtResource( 5 ) -next_scene_path = "res://screens/main_menu.tscn" - [node name="LoadButton" type="Button" parent="HBoxContainer"] -margin_left = 257.0 -margin_right = 510.0 +margin_right = 338.0 margin_bottom = 45.0 grow_horizontal = 2 grow_vertical = 2 @@ -218,8 +217,8 @@ size_flags_vertical = 3 text = "Load" [node name="SaveButton" type="Button" parent="HBoxContainer"] -margin_left = 514.0 -margin_right = 767.0 +margin_left = 342.0 +margin_right = 681.0 margin_bottom = 45.0 grow_horizontal = 2 grow_vertical = 2 @@ -228,7 +227,7 @@ size_flags_vertical = 3 text = "Save" [node name="NewButton" type="Button" parent="HBoxContainer"] -margin_left = 771.0 +margin_left = 685.0 margin_right = 1024.0 margin_bottom = 45.0 grow_horizontal = 2 @@ -236,15 +235,6 @@ grow_vertical = 2 size_flags_horizontal = 3 text = "New" -[node name="DisplayTree" type="Tree" parent="."] -anchor_top = 0.075 -anchor_right = 1.0 -anchor_bottom = 1.0 -margin_right = 1.0 -margin_bottom = 1.0 -size_flags_horizontal = 3 -size_flags_vertical = 3 - [connection signal="file_selected" from="FileDialog" to="." method="_on_FileDialog_file_selected"] [connection signal="pressed" from="HBoxContainer/LoadButton" to="." method="_on_LoadButton_pressed"] [connection signal="pressed" from="HBoxContainer/SaveButton" to="." method="_on_SaveButton_pressed"] diff --git a/Phase2/Godot_Toolset/Main/user_interface/PersistentWindow.tscn b/Phase2/Godot_Toolset/Main/user_interface/PersistentWindow.tscn new file mode 100644 index 00000000..71cf1967 --- /dev/null +++ b/Phase2/Godot_Toolset/Main/user_interface/PersistentWindow.tscn @@ -0,0 +1,126 @@ +[gd_scene load_steps=4 format=2] + +[ext_resource path="res://user_interface/resize_parent.gd" type="Script" id=1] +[ext_resource path="res://user_interface/move_parent.gd" type="Script" id=2] +[ext_resource path="res://user_interface/remove_parent_button.gd" type="Script" id=3] + +[node name="PersistentWindow" type="Control"] +anchor_left = 0.25 +anchor_top = 0.25 +anchor_right = 0.75 +anchor_bottom = 0.75 + +[node name="Panel" type="Panel" parent="."] +anchor_right = 1.0 +anchor_bottom = 1.0 +margin_left = -10.0 +margin_top = -20.0 +margin_right = 10.0 +margin_bottom = 10.0 + +[node name="move" type="Control" parent="."] +anchor_right = 1.0 +margin_top = -15.0 +script = ExtResource( 2 ) + +[node name="ColorRect" type="ColorRect" parent="move"] +anchor_right = 1.0 +anchor_bottom = 1.0 +mouse_filter = 2 + +[node name="resize top left" type="Control" parent="."] +margin_left = -15.0 +margin_top = -25.0 +margin_right = 10.0 +script = ExtResource( 1 ) +resize_left = true +resize_top = true + +[node name="resize top right" type="Control" parent="."] +anchor_left = 1.0 +anchor_right = 1.0 +margin_left = -10.0 +margin_top = -25.0 +margin_right = 15.0 +script = ExtResource( 1 ) +resize_right = true +resize_top = true + +[node name="resize bottom left" type="Control" parent="."] +anchor_top = 1.0 +anchor_bottom = 1.0 +margin_left = -15.0 +margin_top = -10.0 +margin_right = 10.0 +margin_bottom = 15.0 +script = ExtResource( 1 ) +resize_left = true +resize_bottom = true + +[node name="resize bottom right" type="Control" parent="."] +anchor_left = 1.0 +anchor_top = 1.0 +anchor_right = 1.0 +anchor_bottom = 1.0 +margin_left = -10.0 +margin_top = -10.0 +margin_right = 15.0 +margin_bottom = 15.0 +script = ExtResource( 1 ) +resize_right = true +resize_bottom = true + +[node name="resize top" type="Control" parent="."] +anchor_right = 1.0 +margin_left = 10.0 +margin_top = -25.0 +margin_right = -10.0 +margin_bottom = -15.0 +script = ExtResource( 1 ) +resize_top = true + +[node name="resize bottom" type="Control" parent="."] +anchor_top = 1.0 +anchor_right = 1.0 +anchor_bottom = 1.0 +margin_left = 10.0 +margin_top = 5.0 +margin_right = -10.0 +margin_bottom = 15.0 +script = ExtResource( 1 ) +resize_bottom = true + +[node name="resize left" type="Control" parent="."] +anchor_bottom = 1.0 +margin_left = -15.0 +margin_top = 10.0 +margin_right = -5.0 +margin_bottom = -10.0 +script = ExtResource( 1 ) +resize_left = true + +[node name="resize right" type="Control" parent="."] +anchor_left = 1.0 +anchor_right = 1.0 +anchor_bottom = 1.0 +margin_left = 5.0 +margin_top = 10.0 +margin_right = 15.0 +margin_bottom = -10.0 +script = ExtResource( 1 ) +resize_right = true + +[node name="close window" type="Button" parent="."] +anchor_left = 1.0 +anchor_right = 1.0 +margin_left = -10.0 +margin_top = -15.0 +margin_right = 10.0 +margin_bottom = 5.0 +grow_horizontal = 0 +rect_scale = Vector2( 0.75, 0.75 ) +text = "x" +icon_align = 1 +script = ExtResource( 3 ) + +[connection signal="button_up" from="close window" to="close window" method="_on_close_window_button_up"] diff --git a/Phase2/Godot_Toolset/Main/user_interface/button_opene_scene_in_window.gd b/Phase2/Godot_Toolset/Main/user_interface/button_opene_scene_in_window.gd new file mode 100644 index 00000000..15792ba5 --- /dev/null +++ b/Phase2/Godot_Toolset/Main/user_interface/button_opene_scene_in_window.gd @@ -0,0 +1,22 @@ +extends Button + + +export(String, FILE) var scene_path: = "Scene Path" +export(String) var window_title = "New Window" + +var persistent_window_path = "res://user_interface/PersistentWindow.tscn" + +func _ready(): + connect("button_up", self, "_on_button_up") + +func _on_button_up(): + # see if our scene path exists. if so, load it and add it to a new panel in the main scene + # godot 4 has resizeable non-popup-style windows we could use here, but we're in 3.x, so we'll have to make our own instead + if ResourceLoader.exists(scene_path): + var new_scene = ResourceLoader.load(scene_path).instance() + var new_panel = ResourceLoader.load(persistent_window_path).instance() + new_panel.add_child(new_scene) + get_tree().current_scene.add_child(new_panel) + + else: + print("oh no") diff --git a/Phase2/Godot_Toolset/Main/user_interface/move_parent.gd b/Phase2/Godot_Toolset/Main/user_interface/move_parent.gd new file mode 100644 index 00000000..ce8f8b9b --- /dev/null +++ b/Phase2/Godot_Toolset/Main/user_interface/move_parent.gd @@ -0,0 +1,27 @@ +extends Control + + +var mouse_in_move_area = false +var is_dragging = false + + +func _ready(): + connect("mouse_entered", self, "_mouse_entered_move_area") + connect("mouse_exited", self, "_mouse_exited_move_area") + +func _mouse_entered_move_area(): + mouse_in_move_area = true + +func _mouse_exited_move_area(): + mouse_in_move_area = false + +func _input(event): + if event is InputEventMouseButton: + if event.is_pressed(): + is_dragging = true + elif event.is_released(): + is_dragging = false + + if mouse_in_move_area && event is InputEventMouseMotion: + if is_dragging: + get_parent().rect_position += event.relative diff --git a/Phase2/Godot_Toolset/Main/user_interface/remove_parent_button.gd b/Phase2/Godot_Toolset/Main/user_interface/remove_parent_button.gd new file mode 100644 index 00000000..bec936bb --- /dev/null +++ b/Phase2/Godot_Toolset/Main/user_interface/remove_parent_button.gd @@ -0,0 +1,4 @@ +extends Button + +func _on_close_window_button_up(): + get_parent().queue_free() diff --git a/Phase2/Godot_Toolset/Main/user_interface/resize_parent.gd b/Phase2/Godot_Toolset/Main/user_interface/resize_parent.gd new file mode 100644 index 00000000..44365ec7 --- /dev/null +++ b/Phase2/Godot_Toolset/Main/user_interface/resize_parent.gd @@ -0,0 +1,53 @@ +extends Control + + +# Declare member variables here. Examples: +# var a = 2 +# var b = "text" +var is_dragging = false +var mouse_in_resize_area = false + +export(bool) var resize_left = false +export(bool) var resize_right = false +export(bool) var resize_top = false +export(bool) var resize_bottom = false + +# Called when the node enters the scene tree for the first time. +func _ready(): + if resize_left || resize_right: + set_default_cursor_shape(Control.CURSOR_HSIZE) + if resize_top || resize_bottom: + set_default_cursor_shape(Control.CURSOR_VSIZE) + if (resize_left && resize_top) || (resize_right && resize_bottom): + set_default_cursor_shape(Control.CURSOR_FDIAGSIZE) + if (resize_left && resize_bottom) || (resize_right && resize_top): + set_default_cursor_shape(Control.CURSOR_BDIAGSIZE) + + connect("mouse_entered", self, "_mouse_entered_resize_area") + connect("mouse_exited", self, "_mouse_exited_resize_area") + + +func _mouse_entered_resize_area(): + mouse_in_resize_area = true + +func _mouse_exited_resize_area(): + mouse_in_resize_area = false + + +func _input(event): + if event is InputEventMouseButton: + if event.is_pressed(): + is_dragging = true + elif event.is_released(): + is_dragging = false + + if mouse_in_resize_area && event is InputEventMouseMotion: + if is_dragging: + if resize_left: + get_parent().margin_left += event.relative.x + if resize_right: + get_parent().margin_right += event.relative.x + if resize_top: + get_parent().margin_top += event.relative.y + if resize_bottom: + get_parent().margin_bottom += event.relative.y