- The search field is a single-line field, so Enter no longer adds a
line break that made every search come up empty.
- The field, button and list use real font sizes from the theme instead
of being drawn at half size and scaled up, so the text is sharp, and
everything fits inside the panel.
- Results have alternating row backgrounds like the other lists, a count
("3 of 1045 soundtracks") and a message when nothing matches.
- The letters that matched are highlighted.
- Searches shorter than Settings.LETTERS_FOR_LOOSE_SEARCH (3) only find
names that contain the text, instead of names with the letters far
apart, which matched most of the library. The Statistics tab uses the
same search.
133 lines
4.3 KiB
GDScript
133 lines
4.3 KiB
GDScript
extends MainWindowTestSuite
|
|
## All popups share BasePopup: clicking outside the panel closes them, the backdrop
|
|
## dims the window behind them, and the closing click does not reach the main window.
|
|
## The main window and the quiz each have their own popups and their own backdrop.
|
|
|
|
## Popups in the main window: the ones opened from the top bar, and the log.
|
|
const MAIN_POPUPS: Array[String] = [
|
|
"SearchPopup", "SyncPopup", "QRPopup", "ShortcutsPopup", "AboutPopup", "LogPopup",
|
|
]
|
|
|
|
## Popups opened from the quiz, in the Quiz scene.
|
|
const QUIZ_POPUPS: Array[String] = [
|
|
"SettingsPopup", "CharacterSelectPopup", "WinnerPopup",
|
|
]
|
|
|
|
|
|
func _popup(node_name: String) -> BasePopup:
|
|
return _quiz.get_node(node_name) if node_name in QUIZ_POPUPS \
|
|
else _window.get_node(node_name)
|
|
|
|
|
|
## The backdrop that shows behind [param popup].
|
|
func _backdrop(popup: BasePopup = _popup("SettingsPopup")) -> ColorRect:
|
|
return popup.get_parent().get_node("PopupBackdrop")
|
|
|
|
|
|
## A point on screen outside the popup's panel.
|
|
func _outside(popup: BasePopup) -> Vector2:
|
|
var rect: Rect2 = popup.panel.get_global_rect()
|
|
return Vector2(rect.end.x + 5, rect.end.y + 5) if rect.end.x < 1900 \
|
|
else Vector2(rect.position.x - 5, rect.position.y - 5)
|
|
|
|
|
|
func test_backdrops_are_hidden_without_popups() -> void:
|
|
assert_bool(_backdrop(_popup("SettingsPopup")).visible).is_false()
|
|
assert_bool(_backdrop(_popup("AboutPopup")).visible).is_false()
|
|
|
|
|
|
func test_backdrops_cover_the_whole_window() -> void:
|
|
for node_name: String in ["SettingsPopup", "AboutPopup"]:
|
|
var popup: BasePopup = _popup(node_name)
|
|
popup.open()
|
|
|
|
assert_object(_backdrop(popup).get_global_rect()).override_failure_message(
|
|
"%s: backdrop does not cover the window" % node_name) \
|
|
.is_equal(_window.get_viewport_rect())
|
|
popup.close()
|
|
|
|
|
|
func test_every_popup_is_a_popup_window() -> void:
|
|
for node_name: String in MAIN_POPUPS + QUIZ_POPUPS:
|
|
assert_object(_popup(node_name)).is_instanceof(BasePopup)
|
|
|
|
|
|
func test_every_popup_shows_backdrop_and_closes_on_outside_click() -> void:
|
|
for node_name: String in MAIN_POPUPS + QUIZ_POPUPS:
|
|
var popup: BasePopup = _popup(node_name)
|
|
popup.open()
|
|
await _runner.simulate_frames(1)
|
|
assert_bool(_backdrop(popup).visible).override_failure_message(
|
|
"%s: backdrop not shown" % node_name).is_true()
|
|
|
|
await _click_at(_outside(popup))
|
|
|
|
assert_bool(popup.visible).override_failure_message(
|
|
"%s: not closed by outside click" % node_name).is_false()
|
|
assert_bool(_backdrop(popup).visible).override_failure_message(
|
|
"%s: backdrop still shown" % node_name).is_false()
|
|
|
|
|
|
func test_click_inside_popup_keeps_it_open() -> void:
|
|
var settings: BasePopup = _popup("SettingsPopup")
|
|
settings.open()
|
|
await _runner.simulate_frames(1)
|
|
|
|
await _click_at(settings.panel.get_global_rect().get_center())
|
|
|
|
assert_bool(settings.visible).is_true()
|
|
|
|
|
|
func test_closing_click_does_not_press_button_behind_popup() -> void:
|
|
var settings: BasePopup = _popup("SettingsPopup")
|
|
var reset_button: Button = _quiz.get_node("QuizToolbar/ResetPlaylistButton")
|
|
settings.open()
|
|
await _runner.simulate_frames(1)
|
|
assert_bool(settings.panel.get_global_rect().intersects(reset_button.get_global_rect())) \
|
|
.is_false()
|
|
|
|
await _click_at(reset_button.get_global_rect().get_center())
|
|
|
|
assert_bool(settings.visible).is_false()
|
|
assert_int(_server.count("/music/reset")).is_equal(0)
|
|
|
|
|
|
func test_button_works_again_after_popup_closed() -> void:
|
|
var reset_button: Button = _quiz.get_node("QuizToolbar/ResetPlaylistButton")
|
|
|
|
await _click_at(reset_button.get_global_rect().get_center())
|
|
|
|
assert_int(_server.count("/music/reset")).is_equal(1)
|
|
|
|
|
|
func test_closing_search_clears_the_search() -> void:
|
|
var search: BasePopup = _popup("SearchPopup")
|
|
search.open()
|
|
var search_field: LineEdit = search.search_field
|
|
search_field.text = "mario"
|
|
|
|
search.close()
|
|
|
|
assert_str(search_field.text).is_empty()
|
|
|
|
|
|
func test_closing_character_select_allows_song_clicks_again() -> void:
|
|
var character_select: BasePopup = _popup("CharacterSelectPopup")
|
|
character_select.show_grid("Crono")
|
|
assert_bool(Settings.character_select_open).is_true()
|
|
|
|
character_select.close()
|
|
|
|
assert_bool(Settings.character_select_open).is_false()
|
|
|
|
|
|
func test_toggle_opens_and_closes() -> void:
|
|
var shortcuts: BasePopup = _popup("ShortcutsPopup")
|
|
|
|
shortcuts.toggle()
|
|
assert_bool(shortcuts.visible).is_true()
|
|
|
|
shortcuts.toggle()
|
|
assert_bool(shortcuts.visible).is_false()
|
|
|