From b0267388f2d6008fde86b458757bef0e4914e95b Mon Sep 17 00:00:00 2001 From: William Edwards Date: Mon, 3 Jun 2024 02:14:53 -0700 Subject: [PATCH] feat(Library): add option and menu to hide items in library --- .../state/states/game_settings_library.tres | 8 +++ assets/state/states/settings_library.tres | 8 +++ core/global/library_manager.gd | 15 +++++ core/systems/debug/logger.gd | 6 ++ core/systems/library/library_item.gd | 12 ++++ core/ui/card_ui/launch/game_settings.gd | 13 +++- core/ui/card_ui/launch/game_settings.tscn | 23 ++++++- .../card_ui/launch/game_settings_library.gd | 48 ++++++++++++++ .../card_ui/launch/game_settings_library.tscn | 52 +++++++++++++++ core/ui/card_ui/library/library_menu.gd | 45 +++++++------ core/ui/card_ui/library/library_menu.tscn | 44 ------------- .../card_ui/library/library_tabs_state.tres | 2 +- .../card_ui/settings/general_settings_menu.gd | 5 -- .../settings/general_settings_menu.tscn | 16 +---- .../card_ui/settings/library_settings_menu.gd | 58 +++++++++++++++++ .../settings/library_settings_menu.tscn | 65 +++++++++++++++++++ core/ui/card_ui/settings/settings_menu.tscn | 23 ++++++- .../common/launch/game_boxart_settings.tscn | 2 +- core/ui/components/card.gd | 1 + 19 files changed, 359 insertions(+), 87 deletions(-) create mode 100644 assets/state/states/game_settings_library.tres create mode 100644 assets/state/states/settings_library.tres create mode 100644 core/ui/card_ui/launch/game_settings_library.gd create mode 100644 core/ui/card_ui/launch/game_settings_library.tscn create mode 100644 core/ui/card_ui/settings/library_settings_menu.gd create mode 100644 core/ui/card_ui/settings/library_settings_menu.tscn diff --git a/assets/state/states/game_settings_library.tres b/assets/state/states/game_settings_library.tres new file mode 100644 index 00000000..a35ece9c --- /dev/null +++ b/assets/state/states/game_settings_library.tres @@ -0,0 +1,8 @@ +[gd_resource type="Resource" script_class="State" load_steps=2 format=3 uid="uid://bnw36g1l7shcy"] + +[ext_resource type="Script" path="res://core/systems/state/state.gd" id="1_ds0g8"] + +[resource] +script = ExtResource("1_ds0g8") +name = "library" +data = {} diff --git a/assets/state/states/settings_library.tres b/assets/state/states/settings_library.tres new file mode 100644 index 00000000..9998afde --- /dev/null +++ b/assets/state/states/settings_library.tres @@ -0,0 +1,8 @@ +[gd_resource type="Resource" script_class="State" load_steps=2 format=3 uid="uid://blcfrofi5oawd"] + +[ext_resource type="Script" path="res://core/systems/state/state.gd" id="1_728sf"] + +[resource] +script = ExtResource("1_728sf") +name = "library" +data = {} diff --git a/core/global/library_manager.gd b/core/global/library_manager.gd index 5d30a043..42845f05 100644 --- a/core/global/library_manager.gd +++ b/core/global/library_manager.gd @@ -40,11 +40,17 @@ signal library_loaded(library_id: String) signal library_item_added(item: LibraryItem) ## Emitted when a [LibraryItem] is removed from the library signal library_item_removed(item: LibraryItem) +## Emitted when a [LibraryItem] is hidden from the library +signal library_item_hidden(item: LibraryItem) +## Emitted when a [LibraryItem] is unhidden from the library +signal library_item_unhidden(item: LibraryItem) ## Emitted when a [LibraryLaunchItem] is added to a [LibraryItem] signal library_launch_item_added(item: LibraryLaunchItem) ## Emitted when a [LibraryLaunchItem] is removed from a [LibraryItem] signal library_launch_item_removed(item: LibraryLaunchItem) +var settings_manager := load("res://core/global/settings_manager.tres") as SettingsManager + # Dictionary of registered library providers # The dictionary is in the form of: # { @@ -106,6 +112,12 @@ func filter_by_library(apps: Array[LibraryItem], library_id: String) -> Array[Li return apps.filter(filter) +## Filters the given array of apps by hidden +func filter_by_hidden(apps: Array[LibraryItem]) -> Array[LibraryItem]: + var filter := func(item: LibraryItem): return item.is_hidden + return apps.filter(filter) + + ## Returns an dictionary of all available apps func get_available() -> Dictionary: return _available_apps.duplicate() @@ -135,6 +147,9 @@ func add_library_launch_item(library_id: String, item: LibraryLaunchItem) -> voi library_item = LibraryItem.new_from_launch_item(item) _available_apps[item.name] = library_item is_new = true + var is_hidden := settings_manager.get_library_value(library_item, "hidden", false) as bool + if is_hidden: + library_item.is_hidden = is_hidden # Update the provider fields on the library item item._provider_id = library_id diff --git a/core/systems/debug/logger.gd b/core/systems/debug/logger.gd index 6582068a..1e76a879 100644 --- a/core/systems/debug/logger.gd +++ b/core/systems/debug/logger.gd @@ -74,3 +74,9 @@ func error(message: Variant, xtra2: Variant = null, xtra3: Variant = null, xtra4 var msg := _stringify(message, xtra2, xtra3, xtra4, xtra5, xtra6) push_error(prefix, msg) print_rich("[color=red]", prefix, "[/color]", msg) + + +func deprecated(message: Variant) -> void: + var prefix := _format_prefix("DEPRECATED", _get_caller()) + var msg := str(message) + print_rich("[color=pink]", prefix, "[/color]", msg) diff --git a/core/systems/library/library_item.gd b/core/systems/library/library_item.gd index c3328b28..e3dd488f 100644 --- a/core/systems/library/library_item.gd +++ b/core/systems/library/library_item.gd @@ -20,6 +20,10 @@ signal installed(launch_item: LibraryLaunchItem) signal uninstalled(launch_item: LibraryLaunchItem) ## Emitted when the [InstallManager] has updated this library item signal upgraded(launch_item: LibraryLaunchItem) +## Emitted when this library item is hidden from the library +signal hidden +## Emitted when this library item is unhidden from the library +signal unhidden ## The unique ID of the library item @export var _id: String @@ -31,6 +35,14 @@ signal upgraded(launch_item: LibraryLaunchItem) @export var tags: PackedStringArray ## An array of categories the game belongs to @export var categories: PackedStringArray +## Whether or not this library item should be hidden in the library +var is_hidden: bool: + set(_is_hidden): + is_hidden = _is_hidden + if is_hidden: + hidden.emit() + else: + unhidden.emit() ## Creates a new library item from the given library launch item diff --git a/core/ui/card_ui/launch/game_settings.gd b/core/ui/card_ui/launch/game_settings.gd index e39044c2..830255ec 100644 --- a/core/ui/card_ui/launch/game_settings.gd +++ b/core/ui/card_ui/launch/game_settings.gd @@ -12,11 +12,14 @@ var library_item: LibraryItem # Called when the node enters the scene tree for the first time. func _ready() -> void: game_settings_state.state_entered.connect(_on_state_entered) + game_settings_state.state_exited.connect(_on_state_exited) settings_state_machine.state_changed.connect(_on_settings_state_changed) func _on_state_entered(_from: State) -> void: - if "item" in game_settings_state.data: + if game_settings_state.has_meta("item"): + library_item = game_settings_state.get_meta("item") as LibraryItem + elif "item" in game_settings_state.data: library_item = game_settings_state.data["item"] as LibraryItem # Set the selected game's name @@ -33,7 +36,15 @@ func _on_state_entered(_from: State) -> void: break +func _on_state_exited(_to: State) -> void: + settings_state_machine.pop_state() + game_settings_state.data.erase("item") + game_settings_state.remove_meta("item") + + func _on_settings_state_changed(_from: State, to: State) -> void: + if not to: + return var text := to.name text = text.capitalize() text = text.replace("_", " ") diff --git a/core/ui/card_ui/launch/game_settings.tscn b/core/ui/card_ui/launch/game_settings.tscn index a1380a22..97e6319d 100644 --- a/core/ui/card_ui/launch/game_settings.tscn +++ b/core/ui/card_ui/launch/game_settings.tscn @@ -1,4 +1,4 @@ -[gd_scene load_steps=24 format=3 uid="uid://58qlqqbh58im"] +[gd_scene load_steps=26 format=3 uid="uid://58qlqqbh58im"] [ext_resource type="Script" path="res://core/ui/card_ui/launch/game_settings.gd" id="1_vrr6s"] [ext_resource type="PackedScene" uid="uid://orey8uxm7v6v" path="res://core/systems/state/visibility_manager.tscn" id="2_pga6u"] @@ -19,7 +19,9 @@ [ext_resource type="Resource" uid="uid://1dnelmxp0tuq" path="res://assets/state/state_machines/game_settings_state_machine.tres" id="20_cokg3"] [ext_resource type="Resource" uid="uid://d3rbp3ws1ejal" path="res://assets/state/states/game_settings_launch.tres" id="21_tdepl"] [ext_resource type="PackedScene" uid="uid://dl3lxwakvk7l2" path="res://core/ui/common/launch/game_boxart_settings.tscn" id="24_4afdc"] +[ext_resource type="Resource" uid="uid://bnw36g1l7shcy" path="res://assets/state/states/game_settings_library.tres" id="24_um3vy"] [ext_resource type="Resource" uid="uid://bn8ih6qafytvi" path="res://assets/state/states/game_settings_boxart.tres" id="25_3xebk"] +[ext_resource type="PackedScene" uid="uid://bvdasrjrvyp11" path="res://core/ui/card_ui/launch/game_settings_library.tscn" id="25_c26mp"] [ext_resource type="PackedScene" uid="uid://dithv38oqgy58" path="res://core/ui/components/section_label.tscn" id="27_06vpr"] [ext_resource type="PackedScene" uid="uid://bo077a5mwi7xl" path="res://core/ui/components/transition_fade_in.tscn" id="29_voua8"] [ext_resource type="Script" path="res://core/ui/components/transition_container.gd" id="34_j5cnx"] @@ -150,6 +152,20 @@ on_signal = "focus_entered" target = NodePath("../../../../../../../../../ContentContainer/VBoxContainer/ContentContainer/MarginContainer/BoxArtSettings/MarginContainer/VBoxContainer/FocusGroup") on_signal = "pressed" +[node name="LibraryButton" parent="MarginContainer/HBoxContainer/MenuContainer/VBoxContainer/ButtonContainer/MarginContainer/ScrollContainer/MarginContainer/ButtonsContainer" instance=ExtResource("19_1erbu")] +layout_mode = 2 +text = "Library" + +[node name="StateUpdater" parent="MarginContainer/HBoxContainer/MenuContainer/VBoxContainer/ButtonContainer/MarginContainer/ScrollContainer/MarginContainer/ButtonsContainer/LibraryButton" instance=ExtResource("15_lmmqq")] +state_machine = ExtResource("20_cokg3") +state = ExtResource("24_um3vy") +action = 3 +on_signal = "focus_entered" + +[node name="FocusGroupSetter" parent="MarginContainer/HBoxContainer/MenuContainer/VBoxContainer/ButtonContainer/MarginContainer/ScrollContainer/MarginContainer/ButtonsContainer/LibraryButton" node_paths=PackedStringArray("target") instance=ExtResource("18_qwki4")] +target = NodePath("../../../../../../../../../ContentContainer/VBoxContainer/ContentContainer/MarginContainer/LibrarySettings/MarginContainer/VBoxContainer/FocusGroup") +on_signal = "pressed" + [node name="ContentContainer" type="MarginContainer" parent="MarginContainer/HBoxContainer"] layout_mode = 2 size_flags_horizontal = 3 @@ -216,5 +232,10 @@ script = ExtResource("34_j5cnx") [node name="TransitionFadeIn" parent="MarginContainer/HBoxContainer/ContentContainer/VBoxContainer/ContentContainer/MarginContainer/BoxArtSettings/TransitionContainer" instance=ExtResource("29_voua8")] +[node name="LibrarySettings" parent="MarginContainer/HBoxContainer/ContentContainer/VBoxContainer/ContentContainer/MarginContainer" instance=ExtResource("25_c26mp")] +visible = false +layout_mode = 2 + [editable path="MarginContainer/HBoxContainer/ContentContainer/VBoxContainer/ContentContainer/MarginContainer/LaunchSettings"] [editable path="MarginContainer/HBoxContainer/ContentContainer/VBoxContainer/ContentContainer/MarginContainer/BoxArtSettings"] +[editable path="MarginContainer/HBoxContainer/ContentContainer/VBoxContainer/ContentContainer/MarginContainer/LibrarySettings"] diff --git a/core/ui/card_ui/launch/game_settings_library.gd b/core/ui/card_ui/launch/game_settings_library.gd new file mode 100644 index 00000000..5614af5b --- /dev/null +++ b/core/ui/card_ui/launch/game_settings_library.gd @@ -0,0 +1,48 @@ +extends ScrollContainer + +var settings_manager := load("res://core/global/settings_manager.tres") as SettingsManager +var library_manager := load("res://core/global/library_manager.tres") as LibraryManager +var library_state := load("res://assets/state/states/game_settings_library.tres") as State +var game_settings_state := load("res://assets/state/states/game_settings.tres") as State +var library_item: LibraryItem +var logger := Log.get_logger("GameSettingsLibrary") + +@onready var hide_toggle := $%HideToggle as Toggle + + +# Called when the node enters the scene tree for the first time. +func _ready() -> void: + library_state.state_entered.connect(_on_state_entered) + library_state.state_exited.connect(_on_state_exited) + + # When the hide button is toggled, update the settings for this library item + var on_hide_toggled := func(is_hidden: bool): + if not library_item: + return + settings_manager.set_library_value(library_item, "hidden", is_hidden) + library_item.is_hidden = is_hidden + if is_hidden: + library_manager.library_item_hidden.emit(library_item) + else: + library_manager.library_item_unhidden.emit(library_item) + hide_toggle.toggled.connect(on_hide_toggled) + + +func _on_state_entered(_from: State) -> void: + # Get the current library item + if game_settings_state.has_meta("item"): + library_item = game_settings_state.get_meta("item") as LibraryItem + elif "item" in game_settings_state.data: + library_item = game_settings_state.data["item"] as LibraryItem + + if not library_item: + logger.warn("No library item set in game settings state to configure") + return + + # Find the settings + var is_hidden := settings_manager.get_library_value(library_item, "hidden", false) as bool + hide_toggle.button_pressed = is_hidden + + +func _on_state_exited(_to: State) -> void: + library_item = null diff --git a/core/ui/card_ui/launch/game_settings_library.tscn b/core/ui/card_ui/launch/game_settings_library.tscn new file mode 100644 index 00000000..4658a861 --- /dev/null +++ b/core/ui/card_ui/launch/game_settings_library.tscn @@ -0,0 +1,52 @@ +[gd_scene load_steps=8 format=3 uid="uid://bvdasrjrvyp11"] + +[ext_resource type="Script" path="res://core/ui/card_ui/launch/game_settings_library.gd" id="1_f1pex"] +[ext_resource type="PackedScene" uid="uid://shvyhrv5sx3v" path="res://core/systems/state/state_watcher.tscn" id="1_mk47q"] +[ext_resource type="Resource" uid="uid://bnw36g1l7shcy" path="res://assets/state/states/game_settings_library.tres" id="2_j1lqu"] +[ext_resource type="PackedScene" uid="uid://bw8113ocotx2r" path="res://core/systems/effects/fade_effect.tscn" id="3_tkmdj"] +[ext_resource type="PackedScene" uid="uid://8m20p2s0v5gb" path="res://core/systems/input/focus_group.tscn" id="4_qj1l3"] +[ext_resource type="Resource" uid="uid://cc6i4i264dmqd" path="res://core/ui/card_ui/launch/game_settings_focus.tres" id="5_7h7mk"] +[ext_resource type="PackedScene" uid="uid://d1qb7euwlu7bh" path="res://core/ui/components/toggle.tscn" id="6_e3kvo"] + +[node name="LibrarySettings" type="ScrollContainer"] +anchors_preset = 15 +anchor_right = 1.0 +anchor_bottom = 1.0 +grow_horizontal = 2 +grow_vertical = 2 +size_flags_horizontal = 3 +size_flags_vertical = 3 +follow_focus = true +script = ExtResource("1_f1pex") + +[node name="StateWatcher" parent="." instance=ExtResource("1_mk47q")] +state = ExtResource("2_j1lqu") + +[node name="FadeEffect" parent="StateWatcher" node_paths=PackedStringArray("target") instance=ExtResource("3_tkmdj")] +target = NodePath("../..") +on_signal = "state_entered" +fade_out_signal = "state_exited" +on_signal = "state_entered" + +[node name="MarginContainer" type="MarginContainer" parent="."] +layout_mode = 2 +size_flags_horizontal = 3 +size_flags_vertical = 3 +theme_override_constants/margin_left = 4 +theme_override_constants/margin_top = 4 +theme_override_constants/margin_right = 4 +theme_override_constants/margin_bottom = 4 + +[node name="VBoxContainer" type="VBoxContainer" parent="MarginContainer"] +layout_mode = 2 + +[node name="FocusGroup" parent="MarginContainer/VBoxContainer" node_paths=PackedStringArray("current_focus") instance=ExtResource("4_qj1l3")] +current_focus = NodePath("../HideToggle") +focus_stack = ExtResource("5_7h7mk") + +[node name="HideToggle" parent="MarginContainer/VBoxContainer" instance=ExtResource("6_e3kvo")] +unique_name_in_owner = true +layout_mode = 2 +text = "Hidden in library" +description = "Prevent this item from showing up in your library" +button_pressed = false diff --git a/core/ui/card_ui/library/library_menu.gd b/core/ui/card_ui/library/library_menu.gd index 1601744d..4618475b 100644 --- a/core/ui/card_ui/library/library_menu.gd +++ b/core/ui/card_ui/library/library_menu.gd @@ -2,14 +2,14 @@ extends Control signal refresh_completed -var BoxArtManager := load("res://core/global/boxart_manager.tres") as BoxArtManager -var LibraryManager := load("res://core/global/library_manager.tres") as LibraryManager -var InstallManager := preload("res://core/global/install_manager.tres") -var state_machine := preload("res://assets/state/state_machines/global_state_machine.tres") as StateMachine -var library_state := preload("res://assets/state/states/library.tres") as State -var launcher_state := preload("res://assets/state/states/game_launcher.tres") as State -var osk_state := preload("res://assets/state/states/osk.tres") as State -var card_scene := preload("res://core/ui/components/card.tscn") as PackedScene +var settings_manager := load("res://core/global/settings_manager.tres") as SettingsManager +var library_manager := load("res://core/global/library_manager.tres") as LibraryManager +var install_manager := load("res://core/global/install_manager.tres") as InstallManager +var state_machine := load("res://assets/state/state_machines/global_state_machine.tres") as StateMachine +var library_state := load("res://assets/state/states/library.tres") as State +var launcher_state := load("res://assets/state/states/game_launcher.tres") as State +var osk_state := load("res://assets/state/states/osk.tres") as State +var card_scene := load("res://core/ui/components/card.tscn") as PackedScene var tween: Tween var refresh_requested := false @@ -39,15 +39,16 @@ func _ready() -> void: tabs_state.tab_changed.connect(_on_tab_container_tab_changed) # Listen for library changes - var on_library_changed := func(item: LibraryItem): + var on_library_changed := func(_item: LibraryItem): queue_refresh() - LibraryManager.library_item_added.connect(on_library_changed) - LibraryManager.library_item_removed.connect(on_library_changed) + library_manager.library_item_added.connect(on_library_changed) + library_manager.library_item_removed.connect(on_library_changed) + library_manager.library_item_unhidden.connect(on_library_changed) # Listen for app install/uninstall changes - InstallManager.install_queued.connect(_on_install_queued) - InstallManager.install_completed.connect(_on_installed) - InstallManager.uninstall_completed.connect(_on_uninstalled) + install_manager.install_queued.connect(_on_install_queued) + install_manager.install_completed.connect(_on_installed) + install_manager.uninstall_completed.connect(_on_uninstalled) if global_search != null: global_search.search_submitted.connect(_on_search) @@ -110,7 +111,7 @@ func _reload_library() -> void: const available_tab_idx := 1 # Load our library entries and add them to all games - var available := LibraryManager.get_library_items() + var available := library_manager.get_library_items() # If the library has been loaded before, check for removed items if _library.size() > 0: @@ -118,7 +119,7 @@ func _reload_library() -> void: # Delete any library cards that no longer exist in the library for card_name in card_names: - if LibraryManager.has_app(card_name): + if library_manager.has_app(card_name): continue var card := _library[available_tab_idx][card_name] as Control _library[available_tab_idx].erase(card_name) @@ -134,10 +135,10 @@ func _reload_library() -> void: # Populate the installed games grid var modifiers: Array[Callable] = [ - LibraryManager.filter_installed, - LibraryManager.sort_by_name, + library_manager.filter_installed, + library_manager.sort_by_name, ] - var installed := LibraryManager.get_library_items(modifiers) + var installed := library_manager.get_library_items(modifiers) await _populate_grid(installed_games_grid, installed, installed_tab_idx) @@ -161,6 +162,11 @@ func _populate_grid(grid: HFlowContainer, library_items: Array, tab_num: int): for i in range(library_items.size()): var item: LibraryItem = library_items[i] + # Check to see if this library item should be hidden + var is_hidden := settings_manager.get_library_value(item, "hidden", false) as bool + if is_hidden: + continue + # If the card node already exists, move it to the correct place if tab_num in _library and item.name in _library[tab_num]: var card := _library[tab_num][item.name] as GameCard @@ -178,6 +184,7 @@ func _populate_grid(grid: HFlowContainer, library_items: Array, tab_num: int): var on_removed := func(): _library[tab_num].erase(item.name) item.removed_from_library.connect(on_removed) + item.hidden.connect(on_removed) # Add the card to the grid grid.add_child(card) diff --git a/core/ui/card_ui/library/library_menu.tscn b/core/ui/card_ui/library/library_menu.tscn index 2c4d6f90..8063421d 100644 --- a/core/ui/card_ui/library/library_menu.tscn +++ b/core/ui/card_ui/library/library_menu.tscn @@ -123,47 +123,3 @@ layout_mode = 2 size_flags_horizontal = 3 theme_override_constants/h_separation = 4 theme_override_constants/v_separation = 16 - -[node name="FavoritesTab" type="ScrollContainer" parent="TabContainer"] -visible = false -layout_mode = 2 -horizontal_scroll_mode = 0 - -[node name="ScrollerJoystick" parent="TabContainer/FavoritesTab" instance=ExtResource("11_27umd")] - -[node name="MarginContainer" type="MarginContainer" parent="TabContainer/FavoritesTab"] -layout_mode = 2 -size_flags_horizontal = 3 -size_flags_vertical = 3 -theme_override_constants/margin_left = 15 -theme_override_constants/margin_top = 100 -theme_override_constants/margin_right = 15 - -[node name="FavoritesGrid" type="HFlowContainer" parent="TabContainer/FavoritesTab/MarginContainer"] -unique_name_in_owner = true -layout_mode = 2 -size_flags_horizontal = 3 -theme_override_constants/h_separation = 4 -theme_override_constants/v_separation = 16 - -[node name="CollectionsTab" type="ScrollContainer" parent="TabContainer"] -visible = false -layout_mode = 2 -horizontal_scroll_mode = 0 - -[node name="ScrollerJoystick" parent="TabContainer/CollectionsTab" instance=ExtResource("11_27umd")] - -[node name="MarginContainer" type="MarginContainer" parent="TabContainer/CollectionsTab"] -layout_mode = 2 -size_flags_horizontal = 3 -size_flags_vertical = 3 -theme_override_constants/margin_left = 15 -theme_override_constants/margin_top = 100 -theme_override_constants/margin_right = 15 - -[node name="CollectionsGrid" type="HFlowContainer" parent="TabContainer/CollectionsTab/MarginContainer"] -unique_name_in_owner = true -layout_mode = 2 -size_flags_horizontal = 3 -theme_override_constants/h_separation = 4 -theme_override_constants/v_separation = 16 diff --git a/core/ui/card_ui/library/library_tabs_state.tres b/core/ui/card_ui/library/library_tabs_state.tres index a552d7b7..017e3f94 100644 --- a/core/ui/card_ui/library/library_tabs_state.tres +++ b/core/ui/card_ui/library/library_tabs_state.tres @@ -4,4 +4,4 @@ [resource] script = ExtResource("1_yv172") -tabs_text = PackedStringArray("Installed", "All Games", "Favorites", "Collections") +tabs_text = PackedStringArray("Installed", "All Games") diff --git a/core/ui/card_ui/settings/general_settings_menu.gd b/core/ui/card_ui/settings/general_settings_menu.gd index 45b63d3c..a115f57e 100644 --- a/core/ui/card_ui/settings/general_settings_menu.gd +++ b/core/ui/card_ui/settings/general_settings_menu.gd @@ -19,7 +19,6 @@ var logger := Log.get_logger("GeneralSettings") @onready var check_update_button := $%CheckUpdateButton @onready var update_button := $%UpdateButton @onready var themes_container := $%ThemeButtonContainer -@onready var max_recent_slider := $%MaxRecentAppsSlider @onready var platform_container := $%PlatformContainer @onready var platform_image := $%PlatformImage @onready var platform_name := $%PlatformNameLabel @@ -60,10 +59,6 @@ func _ready() -> void: # Add user theme selection buttons _add_user_themes() - # Configure home menu - var max_recent := SettingsManager.get_value("general.home", "max_home_items", 10) as int - max_recent_slider.value = max_recent - # Configure check updates var on_check_updates := func(): var check_update_text := check_update_button.text as String diff --git a/core/ui/card_ui/settings/general_settings_menu.tscn b/core/ui/card_ui/settings/general_settings_menu.tscn index 2c805553..dc10b7f2 100644 --- a/core/ui/card_ui/settings/general_settings_menu.tscn +++ b/core/ui/card_ui/settings/general_settings_menu.tscn @@ -1,4 +1,4 @@ -[gd_scene load_steps=19 format=3 uid="uid://dsgrw1grwef4m"] +[gd_scene load_steps=18 format=3 uid="uid://dsgrw1grwef4m"] [ext_resource type="Script" path="res://core/ui/card_ui/settings/general_settings_menu.gd" id="1_if7xt"] [ext_resource type="PackedScene" uid="uid://bnhxravpuheh2" path="res://core/systems/updater/software_updater.tscn" id="2_ogwq4"] @@ -8,7 +8,6 @@ [ext_resource type="PackedScene" uid="uid://d1qb7euwlu7bh" path="res://core/ui/components/toggle.tscn" id="6_ghdw1"] [ext_resource type="PackedScene" uid="uid://c71ayw7pcw6u6" path="res://core/ui/components/card_button.tscn" id="7_qenel"] [ext_resource type="PackedScene" uid="uid://d0u3rsa5qpj57" path="res://core/ui/components/subsection_label.tscn" id="8_2m3jw"] -[ext_resource type="PackedScene" uid="uid://cemxrvvjgm4g" path="res://core/ui/components/slider.tscn" id="8_58mcr"] [ext_resource type="PackedScene" uid="uid://xei5afwefxud" path="res://core/ui/components/dropdown.tscn" id="8_r15pa"] [ext_resource type="Texture2D" uid="uid://ckbrrln8fngno" path="res://assets/images/platform/ayaneoair-ctr_v1a_1172023.png" id="9_00g0t"] [ext_resource type="PackedScene" uid="uid://c6dpw6swmcbw6" path="res://core/systems/user_interface/theme_setter.tscn" id="9_bci6g"] @@ -161,22 +160,11 @@ layout_mode = 2 theme_override_constants/separation = 10 [node name="FocusGroup" parent="MarginContainer/VBoxContainer/VBoxContainer3" node_paths=PackedStringArray("current_focus", "focus_neighbor_bottom", "focus_neighbor_top") instance=ExtResource("3_36sdt")] -current_focus = NodePath("../MaxRecentAppsSlider") +current_focus = NodePath("../ClientVersionText") focus_stack = ExtResource("4_fyrmg") focus_neighbor_bottom = NodePath("../../VBoxContainer/FocusGroup") focus_neighbor_top = NodePath("../../ThemeButtonContainer/FocusGroup") -[node name="HomeLabel" parent="MarginContainer/VBoxContainer/VBoxContainer3" instance=ExtResource("8_2m3jw")] -layout_mode = 2 -text = "Home" - -[node name="MaxRecentAppsSlider" parent="MarginContainer/VBoxContainer/VBoxContainer3" instance=ExtResource("8_58mcr")] -unique_name_in_owner = true -layout_mode = 2 -text = "Maximum Recent Apps" -value = 10.0 -max_value = 30.0 - [node name="HSeparator3" type="HSeparator" parent="MarginContainer/VBoxContainer/VBoxContainer3"] layout_mode = 2 diff --git a/core/ui/card_ui/settings/library_settings_menu.gd b/core/ui/card_ui/settings/library_settings_menu.gd new file mode 100644 index 00000000..f33f84cd --- /dev/null +++ b/core/ui/card_ui/settings/library_settings_menu.gd @@ -0,0 +1,58 @@ +extends ScrollContainer + +var settings_manager := load("res://core/global/settings_manager.tres") as SettingsManager +var library_manager := load("res://core/global/library_manager.tres") as LibraryManager +var state_machine := load("res://assets/state/state_machines/global_state_machine.tres") as StateMachine +var settings_state := load("res://assets/state/states/settings.tres") as State +var game_settings_state := preload("res://assets/state/states/game_settings.tres") as State +var button_scene := load("res://core/ui/components/card_button.tscn") as PackedScene + +@onready var max_recent_slider := $%MaxRecentAppsSlider +@onready var no_hidden_label := $%NoHiddenLabel +@onready var container := $%VBoxContainer + + +# Called when the node enters the scene tree for the first time. +func _ready() -> void: + settings_state.state_entered.connect(_on_state_entered) + settings_state.state_exited.connect(_on_state_exited) + + # Configure home menu + var max_recent := settings_manager.get_value("general.home", "max_home_items", 10) as int + max_recent_slider.value = max_recent + + +func _on_state_entered(_from: State) -> void: + # Clear old buttons + for child in container.get_children(): + if not child is CardButton: + continue + container.remove_child(child) + child.queue_free() + + # Find all hidden library items + var modifiers: Array[Callable] = [ + library_manager.filter_by_hidden, + ] + var hidden := library_manager.get_library_items(modifiers) + + # Show the label if no hidden items are found + no_hidden_label.visible = hidden.size() == 0 + + # Create a button for each hidden library item + for item in hidden: + var button := button_scene.instantiate() as CardButton + button.text = item.name + + # Configure the button to open the game settings menu + var on_pressed := func(): + game_settings_state.data["item"] = item + game_settings_state.set_meta("item", item) + state_machine.push_state(game_settings_state) + button.pressed.connect(on_pressed) + + container.add_child(button) + + +func _on_state_exited(_to: State) -> void: + pass diff --git a/core/ui/card_ui/settings/library_settings_menu.tscn b/core/ui/card_ui/settings/library_settings_menu.tscn new file mode 100644 index 00000000..8e703fcb --- /dev/null +++ b/core/ui/card_ui/settings/library_settings_menu.tscn @@ -0,0 +1,65 @@ +[gd_scene load_steps=9 format=3 uid="uid://drbp6ec8646v3"] + +[ext_resource type="Script" path="res://core/ui/card_ui/settings/library_settings_menu.gd" id="1_0w1vu"] +[ext_resource type="PackedScene" uid="uid://cemxrvvjgm4g" path="res://core/ui/components/slider.tscn" id="1_obgkx"] +[ext_resource type="PackedScene" uid="uid://shvyhrv5sx3v" path="res://core/systems/state/state_watcher.tscn" id="2_guba0"] +[ext_resource type="PackedScene" uid="uid://dithv38oqgy58" path="res://core/ui/components/section_label.tscn" id="3_x5lfl"] +[ext_resource type="Resource" uid="uid://blcfrofi5oawd" path="res://assets/state/states/settings_library.tres" id="3_ykj28"] +[ext_resource type="PackedScene" uid="uid://bw8113ocotx2r" path="res://core/systems/effects/fade_effect.tscn" id="4_148sd"] +[ext_resource type="PackedScene" uid="uid://8m20p2s0v5gb" path="res://core/systems/input/focus_group.tscn" id="5_sh522"] +[ext_resource type="Resource" uid="uid://dgi16frh3mgj8" path="res://core/ui/card_ui/settings/settings_menu_focus.tres" id="6_ou60g"] + +[node name="LibrarySettingsMenu" type="ScrollContainer"] +anchors_preset = 15 +anchor_right = 1.0 +anchor_bottom = 1.0 +grow_horizontal = 2 +grow_vertical = 2 +follow_focus = true +script = ExtResource("1_0w1vu") + +[node name="StateWatcher" parent="." instance=ExtResource("2_guba0")] +state = ExtResource("3_ykj28") + +[node name="FadeEffect" parent="StateWatcher" node_paths=PackedStringArray("target") instance=ExtResource("4_148sd")] +target = NodePath("../..") +on_signal = "state_entered" +fade_out_signal = "state_exited" +on_signal = "state_entered" + +[node name="MarginContainer" type="MarginContainer" parent="."] +layout_mode = 2 +size_flags_horizontal = 3 +size_flags_vertical = 3 +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="MarginContainer"] +unique_name_in_owner = true +layout_mode = 2 + +[node name="FocusGroup" parent="MarginContainer/VBoxContainer" node_paths=PackedStringArray("current_focus") instance=ExtResource("5_sh522")] +current_focus = NodePath("../MaxRecentAppsSlider") +focus_stack = ExtResource("6_ou60g") + +[node name="HomeLabel" parent="MarginContainer/VBoxContainer" instance=ExtResource("3_x5lfl")] +layout_mode = 2 +text = "Home" + +[node name="MaxRecentAppsSlider" parent="MarginContainer/VBoxContainer" instance=ExtResource("1_obgkx")] +unique_name_in_owner = true +layout_mode = 2 +text = "Maximum Recent Apps" +value = 10.0 +max_value = 30.0 + +[node name="HiddenItemsLabel" parent="MarginContainer/VBoxContainer" instance=ExtResource("3_x5lfl")] +layout_mode = 2 +text = "Hidden Library Items" + +[node name="NoHiddenLabel" type="Label" parent="MarginContainer/VBoxContainer"] +unique_name_in_owner = true +layout_mode = 2 +text = "No hidden library items" diff --git a/core/ui/card_ui/settings/settings_menu.tscn b/core/ui/card_ui/settings/settings_menu.tscn index 4d71d029..ba4e6eef 100644 --- a/core/ui/card_ui/settings/settings_menu.tscn +++ b/core/ui/card_ui/settings/settings_menu.tscn @@ -1,4 +1,4 @@ -[gd_scene load_steps=44 format=3 uid="uid://d2jiecrd5sw4s"] +[gd_scene load_steps=46 format=3 uid="uid://d2jiecrd5sw4s"] [ext_resource type="Script" path="res://core/ui/card_ui/settings/settings_menu.gd" id="1_x5bjx"] [ext_resource type="PackedScene" uid="uid://orey8uxm7v6v" path="res://core/systems/state/visibility_manager.tscn" id="2_xwevg"] @@ -20,6 +20,7 @@ [ext_resource type="PackedScene" uid="uid://uljtdvmuol3l" path="res://core/systems/input/focus_group_setter.tscn" id="18_axp35"] [ext_resource type="Resource" uid="uid://bfx7p4n4fhjwd" path="res://assets/state/states/settings_display.tres" id="18_ljeud"] [ext_resource type="Resource" uid="uid://2efht48q7i6v" path="res://assets/state/states/settings_network.tres" id="19_l8vuu"] +[ext_resource type="Resource" uid="uid://blcfrofi5oawd" path="res://assets/state/states/settings_library.tres" id="19_wexln"] [ext_resource type="Resource" uid="uid://bdvbnao6j0o18" path="res://assets/state/states/settings_audio.tres" id="20_5v03o"] [ext_resource type="Resource" uid="uid://doxatxmp2mlty" path="res://assets/state/states/settings_plugins.tres" id="21_6lg2v"] [ext_resource type="Resource" uid="uid://5r7ehi4t5mri" path="res://assets/state/states/settings_bluetooth.tres" id="21_cbayw"] @@ -36,6 +37,7 @@ [ext_resource type="PackedScene" uid="uid://cpss2bhdwm8t7" path="res://core/ui/common/settings/network_settings_menu.tscn" id="31_35x2h"] [ext_resource type="PackedScene" path="res://core/ui/common/settings/audio_settings_menu.tscn" id="32_dqi6v"] [ext_resource type="PackedScene" uid="uid://6ygxdkvh1hib" path="res://core/ui/card_ui/settings/bluetooth_settings_menu.tscn" id="33_a7xb2"] +[ext_resource type="PackedScene" uid="uid://drbp6ec8646v3" path="res://core/ui/card_ui/settings/library_settings_menu.tscn" id="34_lrrl0"] [ext_resource type="PackedScene" uid="uid://cf5bdr4sh2irb" path="res://core/ui/card_ui/settings/plugin_store_menu.tscn" id="35_0u4bv"] [ext_resource type="PackedScene" uid="uid://cliqk7lo4t8ao" path="res://core/ui/card_ui/settings/plugin_settings_menu.tscn" id="35_dooq8"] [ext_resource type="PackedScene" uid="uid://bfu4edkk5dqt2" path="res://core/ui/common/debug/processes_menu.tscn" id="36_hnokx"] @@ -188,6 +190,20 @@ on_signal = "focus_entered" target = NodePath("../../../../../../../../../ContentContainer/VBoxContainer/ContentContainer/MarginContainer/GeneralSettings/MarginContainer/VBoxContainer/VBoxContainer/FocusGroup") on_signal = "button_up" +[node name="LibraryButton" parent="MarginContainer/HBoxContainer/MenuContainer/VBoxContainer/ButtonContainer/MarginContainer/ScrollContainer/MarginContainer/SettingButtonsContainer" instance=ExtResource("14_obber")] +layout_mode = 2 +text = "Library" + +[node name="StateUpdater" parent="MarginContainer/HBoxContainer/MenuContainer/VBoxContainer/ButtonContainer/MarginContainer/ScrollContainer/MarginContainer/SettingButtonsContainer/LibraryButton" instance=ExtResource("14_cid64")] +state_machine = ExtResource("15_cb33u") +state = ExtResource("19_wexln") +action = 3 +on_signal = "focus_entered" + +[node name="FocusGroupSetter" parent="MarginContainer/HBoxContainer/MenuContainer/VBoxContainer/ButtonContainer/MarginContainer/ScrollContainer/MarginContainer/SettingButtonsContainer/LibraryButton" node_paths=PackedStringArray("target") instance=ExtResource("18_axp35")] +target = NodePath("../../../../../../../../../ContentContainer/VBoxContainer/ContentContainer/MarginContainer/LibrarySettingsMenu/MarginContainer/VBoxContainer/FocusGroup") +on_signal = "button_up" + [node name="HSeparator3" type="HSeparator" parent="MarginContainer/HBoxContainer/MenuContainer/VBoxContainer/ButtonContainer/MarginContainer/ScrollContainer/MarginContainer/SettingButtonsContainer"] layout_mode = 2 @@ -388,6 +404,10 @@ state = ExtResource("16_sfk74") [node name="TransitionFadeIn" parent="MarginContainer/HBoxContainer/ContentContainer/VBoxContainer/ContentContainer/MarginContainer/GeneralSettings/VisibilityManager" instance=ExtResource("29_grs7x")] +[node name="LibrarySettingsMenu" parent="MarginContainer/HBoxContainer/ContentContainer/VBoxContainer/ContentContainer/MarginContainer" instance=ExtResource("34_lrrl0")] +visible = false +layout_mode = 2 + [node name="DisplaySettings" parent="MarginContainer/HBoxContainer/ContentContainer/VBoxContainer/ContentContainer/MarginContainer" instance=ExtResource("30_22tgj")] visible = false layout_mode = 2 @@ -470,6 +490,7 @@ visible = false layout_mode = 2 [editable path="MarginContainer/HBoxContainer/ContentContainer/VBoxContainer/ContentContainer/MarginContainer/GeneralSettings"] +[editable path="MarginContainer/HBoxContainer/ContentContainer/VBoxContainer/ContentContainer/MarginContainer/LibrarySettingsMenu"] [editable path="MarginContainer/HBoxContainer/ContentContainer/VBoxContainer/ContentContainer/MarginContainer/DisplaySettings"] [editable path="MarginContainer/HBoxContainer/ContentContainer/VBoxContainer/ContentContainer/MarginContainer/NetworkSettings"] [editable path="MarginContainer/HBoxContainer/ContentContainer/VBoxContainer/ContentContainer/MarginContainer/BluetoothSettingsMenu"] diff --git a/core/ui/common/launch/game_boxart_settings.tscn b/core/ui/common/launch/game_boxart_settings.tscn index 3877f787..6d9652b5 100644 --- a/core/ui/common/launch/game_boxart_settings.tscn +++ b/core/ui/common/launch/game_boxart_settings.tscn @@ -66,7 +66,7 @@ custom_minimum_size = Vector2(0, 300) layout_mode = 2 focus_mode = 2 texture = ExtResource("5_nvn2v") -expand_mode = 3 +expand_mode = 5 stretch_mode = 5 [node name="CenterContainer" type="CenterContainer" parent="MarginContainer/VBoxContainer/BannerTexture"] diff --git a/core/ui/components/card.gd b/core/ui/components/card.gd index 4bd0cfd3..69c74ef9 100644 --- a/core/ui/components/card.gd +++ b/core/ui/components/card.gd @@ -86,6 +86,7 @@ func set_library_item(item: LibraryItem, free_on_remove: bool = true) -> void: logger.debug("Removing card: " + name) queue_free() item.removed_from_library.connect(on_removed, CONNECT_ONE_SHOT) + item.hidden.connect(on_removed, CONNECT_ONE_SHOT) func _on_focus() -> void: