Commit Graph
73 Commits
Author SHA1 Message Date
Sansan a7bf38c5f9 Version 2.0.0
Build / test (pull_request) Successful in 31s
Build / build (pull_request) Skipped
2026-10-06 12:04:42 +02:00
Sansan 5519afb5f6 Add what's new in 2.0.0 to the About popup
The layout test lets the changelog grow in height with its text, and still
checks its position and width.
2026-10-06 12:02:55 +02:00
Sansan d77b72159d Sort the scripts and scenes into folders
main/ holds the main window and top bar, quiz/ the quiz and its parts,
player/ the music player, popups/ every popup and what they share, data/ the
songs, players, playlist and settings, server/ the MusicServer client,
common/ the list row and GameLog, and themes/ the themes and style boxes.
2026-10-06 11:57:29 +02:00
Sansan a0428e3475 Follow the GDScript style guide in every script
- Types on every parameter, return value and variable, and snake_case names
  (the player name limit is the constant MAX_NAME_LENGTH).
- Spelling fixes: *_triggered, character_selected, separator, caught_errors.
  The server's catched_errors key stays as the server sends it.
- Signals are connected with signal.connect() instead of by name.
- Code is ordered signals, constants, exported vars, vars, @onready vars,
  functions, with @onready on one line and two blank lines between functions.
- Every script starts with a ## description. Template comments, old LOC notes
  and commented-out code are gone, apart from the local play code.
- Lines are at most 100 characters, apart from the local play path.
- The screenshot tour turns off the blinking text cursor so pictures match.
2026-10-06 11:53:26 +02:00
Sansan 674604425f Reach nodes by unique name instead of long paths
Nodes a script uses through a path of several nodes are marked unique in their
scene and found with %Name. The search list is renamed SearchResults, and the
player row's nodes get their real types.
2026-10-06 11:44:47 +02:00
Sansan 390da577d7 Name popups *Popup and give scripts, scenes and classes matching names
Every popup is now called *Popup instead of *Window in its file, root node,
node name, class and variable, and PopupWindow becomes BasePopup. Player is
PlayerRow, SongListObject is SongRow and Character is CharacterCard. Script
files are snake_case and scene files PascalCase, each matching its class or
root node, and LightGrayTheme.tres is light_gray_theme.tres.
2026-10-06 11:22:39 +02:00
Sansan b7d67b573e Give every script a class name and use it for typed references
The popups, the volume slider, the player name field and the main window get
a class_name, so the main window and the quiz hold them by their real type
instead of Control. The classes already use the names the files will get.
2026-10-06 11:16:09 +02:00
Sansan 5831e1e73d Log through a GameLog autoload instead of print()
GameLog.debug() prints only in debug builds, and GameLog.warning() reports
problems such as unexpected server data or failed downloads.
2026-10-06 11:15:03 +02:00
Sansan 5cdec5cc8f Move the log popup to the main window
The quiz reports point changes with an event_logged signal, and the main
window adds them to the log. Alt+L is handled by the main window.
2026-10-06 11:13:11 +02:00
Sansan e94c75e84d Split now playing, the quiz buttons and song loading out of the quiz
NowPlaying, QuizToolbar and SongControls become their own scenes, the auto
repeat switch moves into the music player scene, and downloading songs moves
into a SongLoader node. The quiz only wires the parts together. Every node
keeps its place on screen.

Screenshots of every UI state are pixel-identical to before, the layout test
still matches the original baseline, and each new part has its own tests.
2026-10-06 11:11:18 +02:00
Sansan bad4b3ad8b Indent every script with tabs, like the Godot editor does 2026-10-06 10:28:12 +02:00
Sansan 8c1987807c Make the music list, player list and inspiration list their own scenes
MusicListPanel, PlayersPanel (was Players) and InspirationList (was
ScrollContainer) each get their own scene and script. They report what
happens through signals, and the quiz wires them to the playlist, the
music player, the log and the popups. Every node keeps its place on screen.

Screenshots of every UI state are pixel-identical to before, the layout
test still matches the original baseline, and each part is tested on its
own as well as through the quiz.
2026-10-06 10:27:35 +02:00
Sansan 3c7b4e5c9d Split the main window into TopBar and Quiz scenes
The quiz (song, playlist, players, music player and the popups opened from
it) moves into Quiz.tscn and the top panel into TopBar.tscn. The main window
keeps only the top bar, the quiz and the popups opened from the top bar, so
other views can be added next to the quiz later. Every node keeps its place
on screen.

Screenshots of every UI state before and after are pixel-identical, and a
layout test checks each node against a baseline taken before the split.
2026-10-06 10:02:22 +02:00
Sansan 75c59eb223 Move Sync to the top row and Settings next to the reset buttons 2026-10-06 08:43:05 +02:00
Sansan 10e9e7b2a4 New app icon, packaged with a menu entry for Linux
Build / test (pull_request) Successful in 22s
Build / build (pull_request) Skipped
The icon is a plate wearing headphones with a red Nordic house cookie
on it. It replaces the default Godot icon, so the game window, Windows
and macOS builds use it.

Linux programs can't carry their own icon, so the build now also makes
MusicPlayer_<version>_linux.tar.gz with the game, the icon as a PNG, a
.desktop menu entry and install.sh, which installs them for the current
user. The bare Linux binary is still published.
2026-10-06 08:32:56 +02:00
Sansan 29b11560b5 Show where each item starts in the inspiration and sync lists
Items in the inspiration list and the sync result columns now each have
their own background box, alternating between two shades, with a small
gap between them. When a long name wraps over several lines it is
still clear which lines belong together. The sync columns keep their
alternating white and orange text.
2026-10-06 08:32:56 +02:00
Sansan 2a332c2d19 Make the sync result look right with any number of columns
- Visible columns share the width equally, whether one or five are shown
- Long soundtrack names and errors wrap inside their column instead of
  widening the window, which pushed the title and Restart button out of
  view and cut off text
- Separators only go between columns; the extra one before the first
  column is gone
- Wider, centred panel with inner margins, and spacing above the
  Restart button
- The Re-added header no longer reads ReAdded
2026-10-06 08:32:56 +02:00
Sansan 6cbbfee6a1 Tidy up popup layouts
- Settings: labels in one column and switches and number buttons lined
  up in another, with margins inside the panel
- Log: title and margins; text no longer touches the panel edge
- Sync result: error list centred under its header, which now reads
  Errors instead of CatchedErrors
- About: text wraps inside the panel instead of running under the
  scrollbar
- Character select: wider panel, so the right column of characters is
  no longer right next to the scrollbar
2026-10-06 08:32:56 +02:00
Sansan c7d49bc5cc Rework popups and fix blurry text and player list layout
Popups:
- All nine popups now extend a shared PopupWindow class with open(),
  close() and toggle(), instead of each copying its own close-on-click
  code. Popups that need cleanup override close().
- A click outside a popup closed it and also pressed whatever was
  underneath, e.g. Reset playlist. The closing click is now consumed.
- Popups used Godot's see-through default panel, so the song list and
  titles showed through. They now use an opaque popup theme, and a
  backdrop dims the window behind them.
- The main window root now fills the screen, so the backdrop covers it.

Text and images:
- Many labels and buttons forced nearest filtering, which made text and
  icons jagged when the window is not 1920x1080. They now use the
  default smooth filtering. Only the pixel-art "no character" picture
  keeps nearest filtering when the winner window enlarges it.

Player list:
- A long player name pushed that row's character and buttons to the
  right. Names now take the free space and shorten with an ellipsis, so
  all rows line up and use the full width of the panel.
2026-10-06 08:32:56 +02:00
Sansan 6288739de0 Use the Compatibility renderer
The game is a 2D interface without 3D, shaders or lights, so it does
not need Forward+. With Compatibility it uses about 25% less CPU and
30 MB less memory while running, with no visible difference.
2026-10-06 08:32:56 +02:00
Sansan d79f5f92c5 Remove unused code
- The old character select scene, which was never shown but loaded
  every character image at startup
- Unused SyncResponse and ProgressResponse classes
- Playlist.set_last_played_answered and select/local-loading code in
  the new character select, none of which were called
- Settings.delete_player_children, identical to delete_children
- An unused variable holding a local file path
2026-10-06 08:32:56 +02:00
Sansan 14c166614d Add one log row at a time and pad log times
The log rebuilt every row each time a point was given or taken. It now
adds just the new row, and shows times as 09:05:03 instead of 9:5:3.
2026-10-06 08:32:56 +02:00
Sansan 428decf73a Turn statistics back on for a new game and fix low winning scores
Winning turned statistics off and nothing turned them back on, while
the Settings checkbox still showed them as on. Resetting points now
turns them back on if the win turned them off, and the checkbox shows
the current state when Settings is opened.

A winning score of 1 could never be won and with 2 the first point was
not announced as match point, because the first-point check ran first.
The winning score also could not be kept from going below 1.
2026-10-06 08:32:56 +02:00
Sansan 739d0f7af6 Preload songs only after the song list has loaded
At startup and after resetting the playlist, loading the song list and
preloading the first song started at the same time. When the list
answered last, it cleared the playlist and dropped the preloaded song.
Preloading now starts once the list has loaded, and loading the list is
retried if it fails.
2026-10-06 08:32:56 +02:00
Sansan ed292877ef Ignore Show answer when no song is playing
Before the first song played, currently_playing_song is -1, so pressing
Show answer marked the last song in the list as answered. That is the
preloaded song, so its title was shown as soon as it started playing,
and played?song=-1 was sent to the server. With an empty playlist it
crashed.
2026-10-06 08:32:56 +02:00
Sansan 5a979fca48 Time out requests the server never answers
HTTPRequest has no timeout by default, so a server that accepts the
connection but never responds left song downloads waiting forever.
Requests now fail after 120 seconds, which triggers the normal retry.
2026-10-06 08:32:56 +02:00
Sansan 1acc757981 Fill the song cache when the settings menu is closed
Raising the cache size used to have no effect until the next song was
played. Downloads now start when the settings window closes, so clicking
the number up and down while it is open does not start any downloads.
2026-10-06 08:32:56 +02:00
Sansan 16724922ed Test that the song cache fills up to the cache size setting
Covers a cache size above 1: songs are preloaded until the setting is
reached, playing a song tops the cache up again, and the cache keeps
filling after a failed download once the server answers again.
2026-10-06 08:32:56 +02:00
Sansan c1fc24adf9 Release from the version in project.godot
The version now lives in project.godot (application/config/version)
and Settings.version reads it from there. The Build workflow tests and
exports on every push, and on main creates the tag, uploads the builds
and creates the Gitea release when that version has no tag yet. This
replaces gitea-release.yaml, which released when a branch named after
the version was pushed.

Godot setup moves into a local .gitea/actions/setup-godot action shared
by the test and build jobs, and Godot is updated to 4.7.2 to match the
editor the project is made with.
2026-10-06 08:32:56 +02:00
Sansan f67dccbf52 Retry failed song downloads instead of getting stuck
MusicServerClient functions now take an optional on_failed callback,
called when a request fails or returns invalid JSON. Before, a failed
request was silently dropped, so a failure while preloading a song left
Playlist.is_song_downloading set forever and no more songs were fetched.

Song fetching retries the step that failed (download, queue or info)
every song_fetch_retry_seconds, so the server and the game keep the same
playlist.
2026-10-06 08:32:56 +02:00
Sansan c985a6ce5b Replace the broken test suite with working GdUnit4 tests
The previous tests never compiled: they used GUT's assert functions,
Godot 3 APIs and reassigned autoload functions, so no test ran.

- 90 tests: unit tests for the playlist, songs, player scoring, time
  formatting, search and the server client, plus integration tests
  that run MainWindow and SyncWindow against a fake server
- Keybind tests check that Alt+<number> and Ctrl+Alt+<number> keep
  following the player rows while players are added and removed
- run_tests.sh finds Godot and runs the suite headless (~10 seconds)
- CI runs the tests before the build job in gitea-build.yaml; the
  separate test.yml used a GitHub action that does not exist
- GdUnit4 is committed instead of ignored, since the project enables
  it, and .gitea/ is no longer ignored
- Exported builds leave out tests/ and addons/gdUnit4/
2026-10-06 08:32:56 +02:00
Sansan 56e9fe66d3 Move server calls to MusicServerClient and give players stable ids
Server requests move out of Settings into a new MusicServerClient
autoload with one function per endpoint. It sends requests through a
swappable HttpTransport so tests can fake the server, and it frees its
HTTPRequest nodes after use.

Players now have a UUID that never changes. Their position in
Settings.player_array is only used for the Alt+<number> keybinds.
Previously the position doubled as the id, so removing a player made
points and wins land on the wrong player, and could delete another
player's point from a song.

Also fixes:
- format_time showed 59.6 seconds as "00:60"
- searches containing regex characters such as "Q*bert" broke search
- SongObject and PlayerObject were Nodes that were never freed; they
  are now RefCounted
- search matching is split out of the UI code into find_matches()
2026-10-06 08:32:55 +02:00
Sansan ab338b0696 Add GdUnit4 testing framework with comprehensive test coverage
- Add GdUnit4 v6.2.1 framework in addons/gdUnit4/
- Create test directory structure (tests/unit/, tests/integration/, tests/mocks/)
- Add unit tests for MusicPlayer.gd (8 tests)
- Add unit tests for MainWindow.gd (15+ tests)
- Add unit tests for Settings.gd (5 tests)
- Add unit tests for Playlist.gd (11 tests)
- Add integration tests for full flow (10+ tests)
- Add MockHTTPRequest for HTTP request mocking
- Add TestHelpers with utility functions
- Add Gitea Actions CI workflow (.gitea/workflows/test.yml)
- Add .runsettings for GdUnit4 CLI configuration
- Add run_tests.sh for convenient test execution
- Add TESTING.md with comprehensive documentation
- Add TESTING_PLAN.md with implementation details
- Update .gitignore for test artifacts
- Enable GdUnit4 plugin in project.godot

Features:
- Test button functionality (play, pause, search, sync, etc.)
- Mock REST API requests to server
- Test complete application flows
- Run tests in CI (headless mode)
- Run tests in GUI for visual feedback
- JUnit XML and HTML test reports

Generated by OpenCode AI assistant.
2026-10-06 08:32:55 +02:00
Sansan 9a91d969bd Merge pull request 'Made improvements to the Search window, Made small changes to the inspiration list scrolling, Made small changes to the player list, Changed the term game to soundtrack, #28: Made changes to the sync window' (#37) from develop into main
Build / build (push) Successful in 1m6s
Reviewed-on: #37
2026-10-05 22:53:08 +02:00
Sansan 8da6fc442f Made improvements to the Search window, Made small changes to the inspiration list scrolling, Made small changes to the player list, Changed the term game to soundtrack, #28: Made changes to the sync window
Build / build (push) Successful in 1m14s
Publish / build (push) Successful in 1m10s
2026-09-26 16:21:02 +02:00
Sansan 235bdcbcb5 #34: Fixed bug in Character Select when clicking or scrolling
Build / build (push) Successful in 1m6s
2026-05-17 12:14:07 +02:00
Sansan 6989b53dda Merge pull request 'Fixed workflow' (#35) from 1.8.0 into main
Build / build (push) Successful in 1m5s
Publish / build (push) Successful in 1m13s
Reviewed-on: #35
2026-05-16 17:50:05 +02:00
Sansan 899e99864f #9 #32 #33 : New winner screen, new setting for hide beginning and fixed bug
Build / build (push) Successful in 1m25s
2026-05-16 17:46:09 +02:00
Sansan 84608c95c2 Fixed workflow
Publish / build (push) Successful in 1m13s
2026-05-15 11:03:20 +02:00
Sansan acd8d65b95 #29 Small fixes
Build / build (push) Successful in 1m6s
Publish / build (push) Failing after 1m16s
2026-05-15 10:52:26 +02:00
Sansan d957c02373 #14 #15 #29 #31 : Added qr, added more settings, added keymap, changed about page.
Build / build (push) Successful in 1m5s
2026-05-14 12:24:50 +02:00
Sansan 0316df2f95 #14,#15,#29,#31: Added qr, added more settings, added keymap, changed about page.
Build / build (push) Successful in 1m10s
2026-05-14 12:18:42 +02:00
Sansan b4ba96cf63 #20 #24 Winnersong can be stopped. Inspirationlist speed can be changed. Some other small fixes
Build / build (push) Successful in 1m36s
2025-12-27 14:05:56 +01:00
Sansan 2a32cc34ef Sync result can be seen multiple times
Build / build (push) Successful in 1m19s
Publish / build (push) Successful in 1m33s
2025-11-15 15:02:21 +01:00
Sansan bae5831a3e #22: Now block add player if player name is empty
Build / build (push) Successful in 1m21s
#23: Add a log for when points are given to players
#25: Fixed some graphical stuff
#26: Changed so the same character can be on a song multiple times
#27: Turning off statistics after win
2025-11-15 14:53:51 +01:00
Sansan c6ed3c8e53 #17 #18: Removed Debug text in release and fixed bug with new character select screen
Build / build (push) Successful in 1m31s
Publish / build (push) Successful in 1m32s
2025-11-13 18:17:25 +01:00
Sansan 166705f2ab #4 #5 Added a new character select window that now fetches images from the server
Publish / build (push) Successful in 2m39s
Build / build (push) Successful in 1m31s
2025-11-07 20:46:45 +01:00
Sansan 734a463db9 #8: Added functionality to cache more than one song
Build / build (push) Successful in 1m25s
2025-10-26 20:48:35 +01:00
Sansan 4e6e37775d #2 #6 #7 Added a new sync screen that shows progress during sync
Build / build (push) Successful in 1m22s
2025-09-19 22:15:37 +02:00
Sansan 3e4d417b4f #1: Fixed bug with inspiration list and search list not updating on sync and server changed
Build / build (push) Successful in 1m30s
2025-08-24 12:00:29 +02:00
Sansan f46e742cdc Fix for macOS build
Build / build (push) Successful in 1m22s
Publish / build (push) Successful in 1m37s
2025-06-07 23:40:55 +02:00
Sansan f2b362067a Uppgraded to 4.4 and added:d gitea-ci
Build / build (push) Failing after 1m22s
2025-06-07 23:23:04 +02:00
Sansan 6d008b7715 Removed id from player name 2024-12-29 09:51:48 +01:00
Sansan 23f2ed11eb Updated how players and song list works
Made many changes with caching, how players works, added sound effects
and animations any many more things
2024-12-27 20:35:28 +01:00
Sansan c4a7d743d3 Added auto repeat and made some small fixes 2024-10-20 20:28:06 +02:00
Sansan e8171d81a9 Fixed light icons. Made the search "better". Added more shortcuts and tried to fix som bugs. 2024-08-15 20:10:22 +02:00
Sansan 1a7b371161 Mini fixes 2024-06-12 22:23:26 +02:00
Sansan 2f12c1e25c Added icons, a lot of refactoring and optimising 2024-06-12 22:20:33 +02:00
Sansan f0b57981bc Changed path for sound test 2024-05-30 17:47:49 +02:00
Sansan d43a1c7df6 Fixed settings and updated player view. Fixed many other smaler things 2024-05-19 13:39:18 +02:00
Sansan 0d0b5280f8 Merge branch 'main' of https://gitea.sanplex.tech/Sansan/MusicPlayer 2024-05-18 13:58:53 +02:00
Sansan b36e2271a8 Fixes 2024-05-18 13:57:08 +02:00
Sansan c5e6366760 Added shortcuts. Added dialog for winner. Started cleaning code. 2023-09-11 21:20:48 +02:00
Sansan 724455b232 Added hopping between songs. Added settings menu, not finished. 2023-09-10 22:37:57 +02:00
Sansan c9ea40215d Fixed sounds effects with points. Fixed buttons statistics and about 2023-09-08 22:14:54 +02:00
Sansan 050d19039c Fixed add player process where name can be set. Added signals for points. Added settings file. Changed some shortcuts. 2023-09-07 21:55:31 +02:00
Sansan 5b6169ed6c Changed Play/Pause button. Fixed sync games. Fixed sound test, both local and online. 2023-09-03 21:32:30 +02:00
Sansan 90ce661982 Added some buttons and added search view 2023-09-02 23:14:19 +02:00
Sansan 1045bf2f9e Fixed auto scrolling to inspiration. Fixed show answer changes song list. Started working on some colors 2023-09-02 14:05:41 +02:00
Sansan 3fabf45985 Added functionallity to some buttons. Hides answer from start. Updated song que list. 2023-09-01 22:12:24 +02:00
Sansan c15afc3dc5 Added volume bar and song list and refactored character select 2023-08-29 21:06:19 +02:00
Sansan a48fc04e3b Added media player and character select and started some other stuff 2023-08-27 21:34:02 +02:00
Sansan aad5f3d421 First commit
* Can open dir and play song
* Can fetch song from server and show game
* Can fetch list of games
2023-03-18 21:17:04 +01:00