| @ -0,0 +1,34 @@ | |||||
| [remap] | |||||
| importer="texture" | |||||
| type="CompressedTexture2D" | |||||
| uid="uid://by4w5ll3le7g6" | |||||
| path="res://.godot/imported/folder-open-hover.png-a1ef3a807e674ab8f8806dada553ab61.ctex" | |||||
| metadata={ | |||||
| "vram_texture": false | |||||
| } | |||||
| [deps] | |||||
| source_file="res://save_load/assets/folder-open-hover.png" | |||||
| dest_files=["res://.godot/imported/folder-open-hover.png-a1ef3a807e674ab8f8806dada553ab61.ctex"] | |||||
| [params] | |||||
| compress/mode=0 | |||||
| compress/high_quality=false | |||||
| compress/lossy_quality=0.7 | |||||
| compress/hdr_compression=1 | |||||
| compress/normal_map=0 | |||||
| compress/channel_pack=0 | |||||
| mipmaps/generate=false | |||||
| mipmaps/limit=-1 | |||||
| roughness/mode=0 | |||||
| roughness/src_normal="" | |||||
| process/fix_alpha_border=true | |||||
| process/premult_alpha=false | |||||
| process/normal_map_invert_y=false | |||||
| process/hdr_as_srgb=false | |||||
| process/hdr_clamp_exposure=false | |||||
| process/size_limit=0 | |||||
| detect_3d/compress_to=1 | |||||
| @ -0,0 +1,34 @@ | |||||
| [remap] | |||||
| importer="texture" | |||||
| type="CompressedTexture2D" | |||||
| uid="uid://cmq51cgasug81" | |||||
| path="res://.godot/imported/folder-open-normal.png-f7f228a37723c0515dbd7272838372e1.ctex" | |||||
| metadata={ | |||||
| "vram_texture": false | |||||
| } | |||||
| [deps] | |||||
| source_file="res://save_load/assets/folder-open-normal.png" | |||||
| dest_files=["res://.godot/imported/folder-open-normal.png-f7f228a37723c0515dbd7272838372e1.ctex"] | |||||
| [params] | |||||
| compress/mode=0 | |||||
| compress/high_quality=false | |||||
| compress/lossy_quality=0.7 | |||||
| compress/hdr_compression=1 | |||||
| compress/normal_map=0 | |||||
| compress/channel_pack=0 | |||||
| mipmaps/generate=false | |||||
| mipmaps/limit=-1 | |||||
| roughness/mode=0 | |||||
| roughness/src_normal="" | |||||
| process/fix_alpha_border=true | |||||
| process/premult_alpha=false | |||||
| process/normal_map_invert_y=false | |||||
| process/hdr_as_srgb=false | |||||
| process/hdr_clamp_exposure=false | |||||
| process/size_limit=0 | |||||
| detect_3d/compress_to=1 | |||||
| @ -0,0 +1,34 @@ | |||||
| [remap] | |||||
| importer="texture" | |||||
| type="CompressedTexture2D" | |||||
| uid="uid://blyryo60jydgi" | |||||
| path="res://.godot/imported/folder-open-pressed.png-b69b4af3e2256bb46d3464e4d48a50c0.ctex" | |||||
| metadata={ | |||||
| "vram_texture": false | |||||
| } | |||||
| [deps] | |||||
| source_file="res://save_load/assets/folder-open-pressed.png" | |||||
| dest_files=["res://.godot/imported/folder-open-pressed.png-b69b4af3e2256bb46d3464e4d48a50c0.ctex"] | |||||
| [params] | |||||
| compress/mode=0 | |||||
| compress/high_quality=false | |||||
| compress/lossy_quality=0.7 | |||||
| compress/hdr_compression=1 | |||||
| compress/normal_map=0 | |||||
| compress/channel_pack=0 | |||||
| mipmaps/generate=false | |||||
| mipmaps/limit=-1 | |||||
| roughness/mode=0 | |||||
| roughness/src_normal="" | |||||
| process/fix_alpha_border=true | |||||
| process/premult_alpha=false | |||||
| process/normal_map_invert_y=false | |||||
| process/hdr_as_srgb=false | |||||
| process/hdr_clamp_exposure=false | |||||
| process/size_limit=0 | |||||
| detect_3d/compress_to=1 | |||||
| @ -0,0 +1,34 @@ | |||||
| [remap] | |||||
| importer="texture" | |||||
| type="CompressedTexture2D" | |||||
| uid="uid://o3l0j53mgkan" | |||||
| path="res://.godot/imported/save-hover.png-a059532ff43c1b9b7f190c464e6ac95e.ctex" | |||||
| metadata={ | |||||
| "vram_texture": false | |||||
| } | |||||
| [deps] | |||||
| source_file="res://save_load/assets/save-hover.png" | |||||
| dest_files=["res://.godot/imported/save-hover.png-a059532ff43c1b9b7f190c464e6ac95e.ctex"] | |||||
| [params] | |||||
| compress/mode=0 | |||||
| compress/high_quality=false | |||||
| compress/lossy_quality=0.7 | |||||
| compress/hdr_compression=1 | |||||
| compress/normal_map=0 | |||||
| compress/channel_pack=0 | |||||
| mipmaps/generate=false | |||||
| mipmaps/limit=-1 | |||||
| roughness/mode=0 | |||||
| roughness/src_normal="" | |||||
| process/fix_alpha_border=true | |||||
| process/premult_alpha=false | |||||
| process/normal_map_invert_y=false | |||||
| process/hdr_as_srgb=false | |||||
| process/hdr_clamp_exposure=false | |||||
| process/size_limit=0 | |||||
| detect_3d/compress_to=1 | |||||
| @ -0,0 +1,34 @@ | |||||
| [remap] | |||||
| importer="texture" | |||||
| type="CompressedTexture2D" | |||||
| uid="uid://ja8bc1h5x85o" | |||||
| path="res://.godot/imported/save-normal.png-126e9be66da8efc0f0eb84b8cc03c6ff.ctex" | |||||
| metadata={ | |||||
| "vram_texture": false | |||||
| } | |||||
| [deps] | |||||
| source_file="res://save_load/assets/save-normal.png" | |||||
| dest_files=["res://.godot/imported/save-normal.png-126e9be66da8efc0f0eb84b8cc03c6ff.ctex"] | |||||
| [params] | |||||
| compress/mode=0 | |||||
| compress/high_quality=false | |||||
| compress/lossy_quality=0.7 | |||||
| compress/hdr_compression=1 | |||||
| compress/normal_map=0 | |||||
| compress/channel_pack=0 | |||||
| mipmaps/generate=false | |||||
| mipmaps/limit=-1 | |||||
| roughness/mode=0 | |||||
| roughness/src_normal="" | |||||
| process/fix_alpha_border=true | |||||
| process/premult_alpha=false | |||||
| process/normal_map_invert_y=false | |||||
| process/hdr_as_srgb=false | |||||
| process/hdr_clamp_exposure=false | |||||
| process/size_limit=0 | |||||
| detect_3d/compress_to=1 | |||||
| @ -0,0 +1,34 @@ | |||||
| [remap] | |||||
| importer="texture" | |||||
| type="CompressedTexture2D" | |||||
| uid="uid://crqgyft4gfilt" | |||||
| path="res://.godot/imported/save-pressed.png-49f5851a0548d3847310651a4ef477c2.ctex" | |||||
| metadata={ | |||||
| "vram_texture": false | |||||
| } | |||||
| [deps] | |||||
| source_file="res://save_load/assets/save-pressed.png" | |||||
| dest_files=["res://.godot/imported/save-pressed.png-49f5851a0548d3847310651a4ef477c2.ctex"] | |||||
| [params] | |||||
| compress/mode=0 | |||||
| compress/high_quality=false | |||||
| compress/lossy_quality=0.7 | |||||
| compress/hdr_compression=1 | |||||
| compress/normal_map=0 | |||||
| compress/channel_pack=0 | |||||
| mipmaps/generate=false | |||||
| mipmaps/limit=-1 | |||||
| roughness/mode=0 | |||||
| roughness/src_normal="" | |||||
| process/fix_alpha_border=true | |||||
| process/premult_alpha=false | |||||
| process/normal_map_invert_y=false | |||||
| process/hdr_as_srgb=false | |||||
| process/hdr_clamp_exposure=false | |||||
| process/size_limit=0 | |||||
| detect_3d/compress_to=1 | |||||
| @ -0,0 +1,34 @@ | |||||
| [remap] | |||||
| importer="texture" | |||||
| type="CompressedTexture2D" | |||||
| uid="uid://cmrtuy0i5qc01" | |||||
| path="res://.godot/imported/trash-hover.png-0c87af6ed9b10a21de0dd22a56db8a47.ctex" | |||||
| metadata={ | |||||
| "vram_texture": false | |||||
| } | |||||
| [deps] | |||||
| source_file="res://save_load/assets/trash-hover.png" | |||||
| dest_files=["res://.godot/imported/trash-hover.png-0c87af6ed9b10a21de0dd22a56db8a47.ctex"] | |||||
| [params] | |||||
| compress/mode=0 | |||||
| compress/high_quality=false | |||||
| compress/lossy_quality=0.7 | |||||
| compress/hdr_compression=1 | |||||
| compress/normal_map=0 | |||||
| compress/channel_pack=0 | |||||
| mipmaps/generate=false | |||||
| mipmaps/limit=-1 | |||||
| roughness/mode=0 | |||||
| roughness/src_normal="" | |||||
| process/fix_alpha_border=true | |||||
| process/premult_alpha=false | |||||
| process/normal_map_invert_y=false | |||||
| process/hdr_as_srgb=false | |||||
| process/hdr_clamp_exposure=false | |||||
| process/size_limit=0 | |||||
| detect_3d/compress_to=1 | |||||
| @ -0,0 +1,34 @@ | |||||
| [remap] | |||||
| importer="texture" | |||||
| type="CompressedTexture2D" | |||||
| uid="uid://dvp5yeoqw36yt" | |||||
| path="res://.godot/imported/trash-normal.png-9a70475e0bfa21e155c8f068d078dd58.ctex" | |||||
| metadata={ | |||||
| "vram_texture": false | |||||
| } | |||||
| [deps] | |||||
| source_file="res://save_load/assets/trash-normal.png" | |||||
| dest_files=["res://.godot/imported/trash-normal.png-9a70475e0bfa21e155c8f068d078dd58.ctex"] | |||||
| [params] | |||||
| compress/mode=0 | |||||
| compress/high_quality=false | |||||
| compress/lossy_quality=0.7 | |||||
| compress/hdr_compression=1 | |||||
| compress/normal_map=0 | |||||
| compress/channel_pack=0 | |||||
| mipmaps/generate=false | |||||
| mipmaps/limit=-1 | |||||
| roughness/mode=0 | |||||
| roughness/src_normal="" | |||||
| process/fix_alpha_border=true | |||||
| process/premult_alpha=false | |||||
| process/normal_map_invert_y=false | |||||
| process/hdr_as_srgb=false | |||||
| process/hdr_clamp_exposure=false | |||||
| process/size_limit=0 | |||||
| detect_3d/compress_to=1 | |||||
| @ -0,0 +1,34 @@ | |||||
| [remap] | |||||
| importer="texture" | |||||
| type="CompressedTexture2D" | |||||
| uid="uid://brwa8yljyrlgy" | |||||
| path="res://.godot/imported/trash-pressed.png-635c7d9409ea36b0244299e895c300c2.ctex" | |||||
| metadata={ | |||||
| "vram_texture": false | |||||
| } | |||||
| [deps] | |||||
| source_file="res://save_load/assets/trash-pressed.png" | |||||
| dest_files=["res://.godot/imported/trash-pressed.png-635c7d9409ea36b0244299e895c300c2.ctex"] | |||||
| [params] | |||||
| compress/mode=0 | |||||
| compress/high_quality=false | |||||
| compress/lossy_quality=0.7 | |||||
| compress/hdr_compression=1 | |||||
| compress/normal_map=0 | |||||
| compress/channel_pack=0 | |||||
| mipmaps/generate=false | |||||
| mipmaps/limit=-1 | |||||
| roughness/mode=0 | |||||
| roughness/src_normal="" | |||||
| process/fix_alpha_border=true | |||||
| process/premult_alpha=false | |||||
| process/normal_map_invert_y=false | |||||
| process/hdr_as_srgb=false | |||||
| process/hdr_clamp_exposure=false | |||||
| process/size_limit=0 | |||||
| detect_3d/compress_to=1 | |||||
| @ -1,90 +1,10 @@ | |||||
| ## Performs the actual saving and loading of data related to this level/scene | |||||
| ## Utilized by the SaveGameManager | |||||
| ## Provides an easy reference for save settings through an export rather than code | |||||
| ## Should be attached to the main world/level scene | |||||
| class_name SaveLevelDataComponent | class_name SaveLevelDataComponent | ||||
| extends Node | extends Node | ||||
| ## See documentation to where this path is: https://docs.godotengine.org/en/stable/tutorials/io/data_paths.html#accessing-persistent-user-data-user[br][br] | |||||
| ## Default Paths:[br] | |||||
| ## * Windows: %APPDATA%\Godot\app_userdata\[project_name][br] | |||||
| ## * macOS: ~/Library/Application Support/Godot/app_userdata/[project_name][br] | |||||
| ## * Linux: ~/.local/share/godot/app_userdata/[project_name][br] | |||||
| @export var save_game_data_path: String = "user://game_data/" | |||||
| @export var save_file_name: String = "save_%s_game_data.tres" | |||||
| var level_scene_name: String | |||||
| var game_data_resource: SaveGameDataResource | |||||
| var level_save_file_name: String | |||||
| var save_game_file_path: String | |||||
| @export var settings: SaveGameSettings ## The SaveGameSettings resource | |||||
| func _ready() -> void: | func _ready() -> void: | ||||
| add_to_group("save_level_data_component") | add_to_group("save_level_data_component") | ||||
| level_scene_name = get_parent().name | |||||
| level_save_file_name = save_file_name % level_scene_name | |||||
| save_game_file_path = save_game_data_path + level_save_file_name | |||||
| func save_node_data() -> void: | |||||
| var nodes: Array = get_tree().get_nodes_in_group("save_data_component") | |||||
| if nodes == null: return | |||||
| game_data_resource = SaveGameDataResource.new() | |||||
| for node: Node in nodes: | |||||
| if node is SaveDataComponent: | |||||
| @warning_ignore("unsafe_method_access") | |||||
| var save_data_resource: Node3DDataResource = node._save_data() | |||||
| var save_final_resource: Node3DDataResource = save_data_resource.duplicate() | |||||
| game_data_resource.save_data_nodes.append(save_final_resource) | |||||
| func save_game() -> void: | |||||
| if !DirAccess.dir_exists_absolute(save_game_data_path): | |||||
| DirAccess.make_dir_absolute(save_game_data_path) | |||||
| save_node_data() | |||||
| var result: int = ResourceSaver.save(game_data_resource, save_game_file_path) | |||||
| if result != OK: | |||||
| printerr("Failed to save game: ", result) | |||||
| func load_game() -> void: | |||||
| if !FileAccess.file_exists(save_game_file_path): | |||||
| printerr("Failed to load save. File does not exist: ", save_game_file_path) | |||||
| return | |||||
| game_data_resource = ResourceLoader.load(save_game_file_path) | |||||
| if game_data_resource == null: | |||||
| printerr("Failed to load save. Unknown format? ", save_game_file_path) | |||||
| return | |||||
| var root_node: Window = get_tree().root | |||||
| for resource: Resource in game_data_resource.save_data_nodes: | |||||
| if resource is Node3DDataResource: | |||||
| (resource as Node3DDataResource)._load_data(root_node) | |||||
| func list_saves() -> Array[SaveFileDetailsResource]: # TODO: Update hints | |||||
| var save_files: Array[SaveFileDetailsResource] = [] | |||||
| if !DirAccess.dir_exists_absolute(save_game_data_path): | |||||
| return save_files | |||||
| for filename: String in ResourceLoader.list_directory(save_game_data_path): | |||||
| if !filename.begins_with("save_"): continue | |||||
| if !filename.ends_with(".tres"): continue # Screenshots, etc | |||||
| var _save_path: String = save_game_data_path + filename | |||||
| var _save_icon: String = filename.replace(".tres", ".png") | |||||
| var _save_resource: SaveFileDetailsResource = SaveFileDetailsResource.new() | |||||
| var _loaded_file: FileAccess = FileAccess.open(_save_path, FileAccess.READ) | |||||
| _save_resource.filename = filename | |||||
| _save_resource.date_created = Time.get_datetime_string_from_unix_time(FileAccess.get_modified_time(_save_path)) | |||||
| _save_resource.filesize = _loaded_file.get_length() | |||||
| if FileAccess.file_exists(save_game_data_path + _save_icon): | |||||
| _save_resource.save_icon = _save_icon | |||||
| save_files.append(_save_resource) | |||||
| return save_files | |||||
| @ -1,6 +1,8 @@ | |||||
| [gd_scene load_steps=2 format=3 uid="uid://c3pqilb6yh5kc"] | |||||
| [gd_scene load_steps=3 format=3 uid="uid://c3pqilb6yh5kc"] | |||||
| [ext_resource type="Script" uid="uid://c7x2qvyu62230" path="res://save_load/components/save_level_data_component.gd" id="1_exguq"] | [ext_resource type="Script" uid="uid://c7x2qvyu62230" path="res://save_load/components/save_level_data_component.gd" id="1_exguq"] | ||||
| [ext_resource type="Resource" uid="uid://o32fooj1lxg7" path="res://save_load/resources/save_game_settings_resource.tres" id="2_rkr1f"] | |||||
| [node name="SaveLevelDataComponent" type="Node"] | [node name="SaveLevelDataComponent" type="Node"] | ||||
| script = ExtResource("1_exguq") | script = ExtResource("1_exguq") | ||||
| settings = ExtResource("2_rkr1f") | |||||
| @ -0,0 +1,4 @@ | |||||
| [gd_resource type="StyleBoxFlat" format=3 uid="uid://bwm315lqbbb87"] | |||||
| [resource] | |||||
| bg_color = Color(0.728173, 0.579132, 0.164487, 1) | |||||
| @ -0,0 +1,8 @@ | |||||
| [gd_resource type="StyleBoxFlat" format=3 uid="uid://biousyggn7iua"] | |||||
| [resource] | |||||
| content_margin_left = 5.0 | |||||
| content_margin_top = 5.0 | |||||
| content_margin_right = 5.0 | |||||
| content_margin_bottom = 5.0 | |||||
| bg_color = Color(0, 0.65098, 0.886275, 0) | |||||
| @ -0,0 +1,15 @@ | |||||
| class_name SaveGameSettings | |||||
| extends Resource | |||||
| ## See documentation to where this path is: https://docs.godotengine.org/en/stable/tutorials/io/data_paths.html#accessing-persistent-user-data-user[br][br] | |||||
| ## Default Paths:[br] | |||||
| ## * Windows: %APPDATA%\Godot\app_userdata\[project_name][br] | |||||
| ## * macOS: ~/Library/Application Support/Godot/app_userdata/[project_name][br] | |||||
| ## * Linux: ~/.local/share/godot/app_userdata/[project_name][br] | |||||
| @export var save_game_data_path: String = "user://game_data/" | |||||
| @export var max_auto_saves: int = 5 | |||||
| @export var save_file_name: String = "save_game_data.tres" | |||||
| @export var quicksave_file_name: String = "quicksave_game_data.tres" | |||||
| @export var autosave_file_name: String = "autosave_%s_game_data.tres" ## %s is the save number (probably 01) | |||||
| @ -0,0 +1 @@ | |||||
| uid://d0iptf06t7f47 | |||||
| @ -0,0 +1,12 @@ | |||||
| [gd_resource type="Resource" script_class="SaveGameSettings" load_steps=2 format=3 uid="uid://o32fooj1lxg7"] | |||||
| [ext_resource type="Script" uid="uid://d0iptf06t7f47" path="res://save_load/resources/save_game_settings_resource.gd" id="1_o1tpj"] | |||||
| [resource] | |||||
| script = ExtResource("1_o1tpj") | |||||
| save_game_data_path = "user://game_data/" | |||||
| max_auto_saves = 5 | |||||
| save_file_name = "save_%s_game_data.tres" | |||||
| quicksave_file_name = "quicksave_game_data.tres" | |||||
| autosave_file_name = "autosave_%s_game_data.tres" | |||||
| metadata/_custom_type_script = "uid://d0iptf06t7f47" | |||||
| @ -0,0 +1,67 @@ | |||||
| class_name SaveFilePanel | |||||
| extends Panel | |||||
| @export var save_panel_highlight: StyleBoxFlat | |||||
| @export var save_panel_normal: StyleBoxFlat | |||||
| @export_group("Node Exports") | |||||
| @export var save_name_label: Label | |||||
| @export var save_date_label: Label | |||||
| @export var save_icon: TextureRect | |||||
| @export var load_button: TextureButton | |||||
| @export var delete_confirm_ui: Control | |||||
| @export var delete_button: TextureButton | |||||
| @export var delete_confirm_button: BaseButton | |||||
| @export var delete_cancel_button: BaseButton | |||||
| var save_file_details: SaveFileDetailsResource | |||||
| func _ready() -> void: | |||||
| mouse_entered.connect(_on_mouse_entered) | |||||
| mouse_exited.connect(_on_mouse_exited) | |||||
| delete_button.pressed.connect(_on_delete_button_pressed) | |||||
| load_button.pressed.connect(_on_load_button_pressed) | |||||
| delete_confirm_button.pressed.connect(_on_delete_confirm_button_pressed) | |||||
| delete_cancel_button.pressed.connect(_on_delete_cancel_button_pressed) | |||||
| func initialize(_resource: SaveFileDetailsResource) -> void: | |||||
| save_file_details = _resource | |||||
| set_save_date() | |||||
| set_save_icon() | |||||
| set_save_name() | |||||
| func set_save_date() -> void: | |||||
| save_date_label.text = save_file_details.date_created | |||||
| func set_save_icon() -> void: | |||||
| save_icon.texture = load(save_file_details.save_icon) | |||||
| func set_save_name() -> void: | |||||
| save_name_label.text = save_file_details.save_name | |||||
| if save_file_details.save_name == null or save_file_details.save_name == "": | |||||
| save_name_label.text = save_file_details.filename | |||||
| func _on_delete_button_pressed() -> void: | |||||
| delete_confirm_ui.show() | |||||
| func _on_delete_confirm_button_pressed() -> void: | |||||
| SaveGameManager.delete_save_file.emit(save_file_details.filename) | |||||
| queue_free() | |||||
| func _on_delete_cancel_button_pressed() -> void: | |||||
| delete_confirm_ui.hide() | |||||
| func _on_load_button_pressed() -> void: | |||||
| SaveGameManager.load_save_file.emit(save_file_details.filename) | |||||
| func _on_mouse_entered() -> void: | |||||
| set("theme_override_styles/panel", save_panel_highlight) | |||||
| func _on_mouse_exited() -> void: | |||||
| set("theme_override_styles/panel", save_panel_normal) | |||||
| @ -0,0 +1 @@ | |||||
| uid://dcfdyua5gwpw4 | |||||
| @ -0,0 +1,127 @@ | |||||
| [gd_scene load_steps=11 format=3 uid="uid://bb7poutsn4ex2"] | |||||
| [ext_resource type="Texture2D" uid="uid://dknv7amroftm8" path="res://assets/icon.svg" id="1_714lu"] | |||||
| [ext_resource type="StyleBox" uid="uid://biousyggn7iua" path="res://save_load/resources/save_file_panel_theme.tres" id="1_cqw77"] | |||||
| [ext_resource type="Texture2D" uid="uid://cmq51cgasug81" path="res://save_load/assets/folder-open-normal.png" id="1_k6haa"] | |||||
| [ext_resource type="Script" uid="uid://dcfdyua5gwpw4" path="res://save_load/ui/save_file.gd" id="2_5g2eu"] | |||||
| [ext_resource type="Texture2D" uid="uid://blyryo60jydgi" path="res://save_load/assets/folder-open-pressed.png" id="2_714lu"] | |||||
| [ext_resource type="StyleBox" uid="uid://bwm315lqbbb87" path="res://save_load/resources/save_file_highlight_panel_theme.tres" id="3_om23c"] | |||||
| [ext_resource type="Texture2D" uid="uid://by4w5ll3le7g6" path="res://save_load/assets/folder-open-hover.png" id="3_ubfnn"] | |||||
| [ext_resource type="Texture2D" uid="uid://dvp5yeoqw36yt" path="res://save_load/assets/trash-normal.png" id="4_c2bnc"] | |||||
| [ext_resource type="Texture2D" uid="uid://brwa8yljyrlgy" path="res://save_load/assets/trash-pressed.png" id="5_jgxci"] | |||||
| [ext_resource type="Texture2D" uid="uid://cmrtuy0i5qc01" path="res://save_load/assets/trash-hover.png" id="6_cqw77"] | |||||
| [node name="SaveFilePanel" type="Panel" node_paths=PackedStringArray("save_name_label", "save_date_label", "save_icon", "load_button", "delete_confirm_ui", "delete_button", "delete_confirm_button", "delete_cancel_button")] | |||||
| custom_minimum_size = Vector2(420, 60) | |||||
| offset_right = 420.0 | |||||
| offset_bottom = 60.0 | |||||
| theme_override_styles/panel = ExtResource("1_cqw77") | |||||
| script = ExtResource("2_5g2eu") | |||||
| save_panel_highlight = ExtResource("3_om23c") | |||||
| save_panel_normal = ExtResource("1_cqw77") | |||||
| save_name_label = NodePath("HBoxContainer/NameDate/SaveName") | |||||
| save_date_label = NodePath("HBoxContainer/NameDate/SaveDate") | |||||
| save_icon = NodePath("HBoxContainer/SaveFileIcon") | |||||
| load_button = NodePath("HBoxContainer/Actions/LoadButton") | |||||
| delete_confirm_ui = NodePath("ConfirmDeletePanel") | |||||
| delete_button = NodePath("HBoxContainer/Actions/DeleteButton") | |||||
| delete_confirm_button = NodePath("ConfirmDeletePanel/VBoxContainer/HBoxContainer/ConfirmButton") | |||||
| delete_cancel_button = NodePath("ConfirmDeletePanel/VBoxContainer/HBoxContainer/CancelButton") | |||||
| [node name="HBoxContainer" type="HBoxContainer" parent="."] | |||||
| custom_minimum_size = Vector2(400, 0) | |||||
| layout_mode = 1 | |||||
| anchors_preset = 8 | |||||
| anchor_left = 0.5 | |||||
| anchor_top = 0.5 | |||||
| anchor_right = 0.5 | |||||
| anchor_bottom = 0.5 | |||||
| offset_left = -200.0 | |||||
| offset_top = -20.5 | |||||
| offset_right = 200.0 | |||||
| offset_bottom = 20.5 | |||||
| grow_horizontal = 2 | |||||
| grow_vertical = 2 | |||||
| size_flags_horizontal = 0 | |||||
| [node name="SaveFileIcon" type="TextureRect" parent="HBoxContainer"] | |||||
| layout_mode = 2 | |||||
| texture = ExtResource("1_714lu") | |||||
| expand_mode = 3 | |||||
| [node name="NameDate" type="VBoxContainer" parent="HBoxContainer"] | |||||
| layout_mode = 2 | |||||
| size_flags_vertical = 8 | |||||
| [node name="SaveName" type="Label" parent="HBoxContainer/NameDate"] | |||||
| layout_mode = 2 | |||||
| text = "Save name #1" | |||||
| [node name="SaveDate" type="Label" parent="HBoxContainer/NameDate"] | |||||
| layout_mode = 2 | |||||
| theme_override_font_sizes/font_size = 10 | |||||
| text = "2025/03/20 13:43:12" | |||||
| [node name="Actions" type="HBoxContainer" parent="HBoxContainer"] | |||||
| layout_mode = 2 | |||||
| size_flags_horizontal = 10 | |||||
| [node name="LoadButton" type="TextureButton" parent="HBoxContainer/Actions"] | |||||
| clip_contents = true | |||||
| custom_minimum_size = Vector2(32, 32) | |||||
| layout_mode = 2 | |||||
| tooltip_text = "Load Save" | |||||
| texture_normal = ExtResource("1_k6haa") | |||||
| texture_pressed = ExtResource("2_714lu") | |||||
| texture_hover = ExtResource("3_ubfnn") | |||||
| ignore_texture_size = true | |||||
| stretch_mode = 5 | |||||
| [node name="DeleteButton" type="TextureButton" parent="HBoxContainer/Actions"] | |||||
| custom_minimum_size = Vector2(32, 32) | |||||
| layout_mode = 2 | |||||
| tooltip_text = "Delete Save" | |||||
| texture_normal = ExtResource("4_c2bnc") | |||||
| texture_pressed = ExtResource("5_jgxci") | |||||
| texture_hover = ExtResource("6_cqw77") | |||||
| ignore_texture_size = true | |||||
| stretch_mode = 5 | |||||
| [node name="ConfirmDeletePanel" type="Panel" parent="."] | |||||
| visible = false | |||||
| layout_mode = 1 | |||||
| anchors_preset = 15 | |||||
| anchor_right = 1.0 | |||||
| anchor_bottom = 1.0 | |||||
| grow_horizontal = 2 | |||||
| grow_vertical = 2 | |||||
| [node name="VBoxContainer" type="VBoxContainer" parent="ConfirmDeletePanel"] | |||||
| layout_mode = 1 | |||||
| anchors_preset = 8 | |||||
| anchor_left = 0.5 | |||||
| anchor_top = 0.5 | |||||
| anchor_right = 0.5 | |||||
| anchor_bottom = 0.5 | |||||
| offset_left = -61.5 | |||||
| offset_top = -29.0 | |||||
| offset_right = 61.5 | |||||
| offset_bottom = 29.0 | |||||
| grow_horizontal = 2 | |||||
| grow_vertical = 2 | |||||
| [node name="Label" type="Label" parent="ConfirmDeletePanel/VBoxContainer"] | |||||
| layout_mode = 2 | |||||
| text = "Delete Save?" | |||||
| horizontal_alignment = 1 | |||||
| [node name="HBoxContainer" type="HBoxContainer" parent="ConfirmDeletePanel/VBoxContainer"] | |||||
| layout_mode = 2 | |||||
| [node name="ConfirmButton" type="Button" parent="ConfirmDeletePanel/VBoxContainer/HBoxContainer"] | |||||
| layout_mode = 2 | |||||
| text = "Confirm" | |||||
| [node name="CancelButton" type="Button" parent="ConfirmDeletePanel/VBoxContainer/HBoxContainer"] | |||||
| layout_mode = 2 | |||||
| text = "Cancel" | |||||
| @ -0,0 +1,29 @@ | |||||
| extends VBoxContainer | |||||
| @export var save_file_scene: PackedScene | |||||
| func _ready() -> void: | |||||
| SaveGameManager.refresh_saves_list.connect(_on_refresh_saves_list) | |||||
| refresh_saves_list() | |||||
| ## Clear the SaveFilesList node of all saves and load most recent saves | |||||
| func refresh_saves_list() -> void: | |||||
| _clear_save_files_list() | |||||
| var save_files: Array[SaveFileDetailsResource] = SaveGameManager.list_saves() | |||||
| for save_resource: SaveFileDetailsResource in save_files: | |||||
| var _save_file: SaveFilePanel = save_file_scene.instantiate() | |||||
| _save_file.initialize(save_resource) | |||||
| add_child(_save_file) | |||||
| func _clear_save_files_list() -> void: | |||||
| for _panel: SaveFilePanel in get_children(): | |||||
| _panel.queue_free() | |||||
| func _on_refresh_saves_list() -> void: | |||||
| refresh_saves_list() | |||||
| @ -0,0 +1 @@ | |||||
| uid://cqabj86bq8whn | |||||
| @ -0,0 +1,10 @@ | |||||
| [gd_scene load_steps=3 format=3 uid="uid://cyxieflejsggu"] | |||||
| [ext_resource type="Script" uid="uid://cqabj86bq8whn" path="res://save_load/ui/save_files_list.gd" id="1_sh1p7"] | |||||
| [ext_resource type="PackedScene" uid="uid://bb7poutsn4ex2" path="res://save_load/ui/save_file.tscn" id="2_kb5u8"] | |||||
| [node name="SaveFilesList" type="VBoxContainer"] | |||||
| clip_contents = true | |||||
| size_flags_horizontal = 4 | |||||
| script = ExtResource("1_sh1p7") | |||||
| save_file_scene = ExtResource("2_kb5u8") | |||||
| @ -0,0 +1,36 @@ | |||||
| class_name SaveLoadUI | |||||
| extends Control | |||||
| @export var show_save_ui_button: BaseButton | |||||
| @export var new_save_ui: Control | |||||
| @export var save_name_input: LineEdit | |||||
| @export var create_save_button: BaseButton | |||||
| @export var create_save_cancel_button: BaseButton | |||||
| func _ready() -> void: | |||||
| show_save_ui_button.pressed.connect(_on_show_save_ui_button_pressed) | |||||
| create_save_button.pressed.connect(_on_create_save_button_pressed) | |||||
| create_save_cancel_button.pressed.connect(_on_create_save_cancel_button_pressed) | |||||
| new_save_ui.hide() | |||||
| func _on_create_save_button_pressed() -> void: | |||||
| var save_name: String = save_name_input.text | |||||
| if save_name.strip_edges() == "": | |||||
| save_name = Time.get_datetime_string_from_system().replace(":", "") | |||||
| SaveGameManager.create_save_file.emit(save_name) | |||||
| SaveGameManager.refresh_saves_list.emit() | |||||
| new_save_ui.hide() | |||||
| SignalManager.resume_game.emit() | |||||
| func _on_create_save_cancel_button_pressed() -> void: | |||||
| new_save_ui.hide() | |||||
| func _on_show_save_ui_button_pressed() -> void: | |||||
| var current_date: String = Time.get_datetime_string_from_system() | |||||
| save_name_input.text = current_date.replace(":", "") | |||||
| new_save_ui.show() | |||||
| @ -0,0 +1 @@ | |||||
| uid://b6831eygibii7 | |||||
| @ -0,0 +1,132 @@ | |||||
| [gd_scene load_steps=7 format=3 uid="uid://dauchkhmnyk7n"] | |||||
| [ext_resource type="Script" uid="uid://b6831eygibii7" path="res://save_load/ui/save_load_ui.gd" id="1_lo08d"] | |||||
| [ext_resource type="PackedScene" uid="uid://cyxieflejsggu" path="res://save_load/ui/save_files_list.tscn" id="1_tqtxm"] | |||||
| [ext_resource type="PackedScene" uid="uid://bb7poutsn4ex2" path="res://save_load/ui/save_file.tscn" id="2_6uxbh"] | |||||
| [ext_resource type="Texture2D" uid="uid://ja8bc1h5x85o" path="res://save_load/assets/save-normal.png" id="3_lo08d"] | |||||
| [ext_resource type="Texture2D" uid="uid://crqgyft4gfilt" path="res://save_load/assets/save-pressed.png" id="4_md7la"] | |||||
| [ext_resource type="Texture2D" uid="uid://o3l0j53mgkan" path="res://save_load/assets/save-hover.png" id="5_hmxxn"] | |||||
| [node name="SaveLoadUI" type="Control" node_paths=PackedStringArray("show_save_ui_button", "new_save_ui", "save_name_input", "create_save_button", "create_save_cancel_button")] | |||||
| process_mode = 3 | |||||
| layout_mode = 3 | |||||
| anchors_preset = 15 | |||||
| anchor_right = 1.0 | |||||
| anchor_bottom = 1.0 | |||||
| grow_horizontal = 2 | |||||
| grow_vertical = 2 | |||||
| size_flags_horizontal = 6 | |||||
| size_flags_vertical = 4 | |||||
| script = ExtResource("1_lo08d") | |||||
| show_save_ui_button = NodePath("Panel/MarginContainer/VBoxContainer/BottomRow/SaveButton") | |||||
| new_save_ui = NodePath("Panel/NewSaveUI") | |||||
| save_name_input = NodePath("Panel/NewSaveUI/MarginContainer/VBoxContainer/SaveNameInput") | |||||
| create_save_button = NodePath("Panel/NewSaveUI/MarginContainer/VBoxContainer/SaveButton") | |||||
| create_save_cancel_button = NodePath("Panel/NewSaveUI/MarginContainer/VBoxContainer/CancelButton") | |||||
| [node name="Panel" type="Panel" parent="."] | |||||
| layout_mode = 1 | |||||
| anchors_preset = 15 | |||||
| anchor_right = 1.0 | |||||
| anchor_bottom = 1.0 | |||||
| grow_horizontal = 2 | |||||
| grow_vertical = 2 | |||||
| [node name="MarginContainer" type="MarginContainer" parent="Panel"] | |||||
| layout_mode = 1 | |||||
| anchors_preset = 15 | |||||
| anchor_right = 1.0 | |||||
| anchor_bottom = 1.0 | |||||
| grow_horizontal = 2 | |||||
| grow_vertical = 2 | |||||
| theme_override_constants/margin_left = 20 | |||||
| theme_override_constants/margin_top = 20 | |||||
| theme_override_constants/margin_right = 20 | |||||
| theme_override_constants/margin_bottom = 20 | |||||
| [node name="VBoxContainer" type="VBoxContainer" parent="Panel/MarginContainer"] | |||||
| layout_mode = 2 | |||||
| [node name="Label" type="Label" parent="Panel/MarginContainer/VBoxContainer"] | |||||
| layout_mode = 2 | |||||
| theme_override_font_sizes/font_size = 40 | |||||
| text = "Save/Load Game" | |||||
| horizontal_alignment = 1 | |||||
| [node name="ScrollContainer" type="ScrollContainer" parent="Panel/MarginContainer/VBoxContainer"] | |||||
| custom_minimum_size = Vector2(0, 500) | |||||
| layout_mode = 2 | |||||
| horizontal_scroll_mode = 0 | |||||
| [node name="SaveFilesList" parent="Panel/MarginContainer/VBoxContainer/ScrollContainer" instance=ExtResource("1_tqtxm")] | |||||
| layout_mode = 2 | |||||
| size_flags_horizontal = 6 | |||||
| [node name="SaveFilePanel" parent="Panel/MarginContainer/VBoxContainer/ScrollContainer/SaveFilesList" instance=ExtResource("2_6uxbh")] | |||||
| layout_mode = 2 | |||||
| [node name="BottomRow" type="HBoxContainer" parent="Panel/MarginContainer/VBoxContainer"] | |||||
| layout_mode = 2 | |||||
| alignment = 1 | |||||
| [node name="SaveButton" type="TextureButton" parent="Panel/MarginContainer/VBoxContainer/BottomRow"] | |||||
| clip_contents = true | |||||
| custom_minimum_size = Vector2(32, 32) | |||||
| layout_mode = 2 | |||||
| tooltip_text = "New Save" | |||||
| texture_normal = ExtResource("3_lo08d") | |||||
| texture_pressed = ExtResource("4_md7la") | |||||
| texture_hover = ExtResource("5_hmxxn") | |||||
| ignore_texture_size = true | |||||
| stretch_mode = 5 | |||||
| [node name="NewSaveUI" type="Panel" parent="Panel"] | |||||
| visible = false | |||||
| custom_minimum_size = Vector2(450, 100) | |||||
| layout_mode = 1 | |||||
| anchors_preset = 15 | |||||
| anchor_right = 1.0 | |||||
| anchor_bottom = 1.0 | |||||
| grow_horizontal = 2 | |||||
| grow_vertical = 2 | |||||
| [node name="MarginContainer" type="MarginContainer" parent="Panel/NewSaveUI"] | |||||
| layout_mode = 1 | |||||
| anchors_preset = 8 | |||||
| anchor_left = 0.5 | |||||
| anchor_top = 0.5 | |||||
| anchor_right = 0.5 | |||||
| anchor_bottom = 0.5 | |||||
| offset_left = -205.0 | |||||
| offset_top = -29.5 | |||||
| offset_right = 205.0 | |||||
| offset_bottom = 29.5 | |||||
| grow_horizontal = 2 | |||||
| grow_vertical = 2 | |||||
| theme_override_constants/margin_left = 5 | |||||
| theme_override_constants/margin_top = 5 | |||||
| theme_override_constants/margin_right = 5 | |||||
| theme_override_constants/margin_bottom = 5 | |||||
| [node name="VBoxContainer" type="VBoxContainer" parent="Panel/NewSaveUI/MarginContainer"] | |||||
| layout_mode = 2 | |||||
| size_flags_horizontal = 4 | |||||
| size_flags_vertical = 4 | |||||
| [node name="SaveNameLabel" type="Label" parent="Panel/NewSaveUI/MarginContainer/VBoxContainer"] | |||||
| layout_mode = 2 | |||||
| theme_override_font_sizes/font_size = 20 | |||||
| text = "Create New Save" | |||||
| [node name="SaveNameInput" type="LineEdit" parent="Panel/NewSaveUI/MarginContainer/VBoxContainer"] | |||||
| custom_minimum_size = Vector2(400, 0) | |||||
| layout_mode = 2 | |||||
| placeholder_text = "New Save File Name" | |||||
| [node name="SaveButton" type="Button" parent="Panel/NewSaveUI/MarginContainer/VBoxContainer"] | |||||
| layout_mode = 2 | |||||
| text = "Create Save" | |||||
| [node name="CancelButton" type="Button" parent="Panel/NewSaveUI/MarginContainer/VBoxContainer"] | |||||
| layout_mode = 2 | |||||
| text = "Cancel" | |||||