Feature/retro console emulation - #622
Open
maxjivi05 wants to merge 6 commits into
Open
Conversation
|
You have reached your Codex usage limits for code reviews. You can see your limits in the Codex usage dashboard. |
maxjivi05
force-pushed
the
feature/retro-console-emulation
branch
3 times, most recently
from
July 23, 2026 17:10
f08b60f to
2f126b7
Compare
Adds retro console support alongside the existing Wine/PC library: NES, SNES, Game Boy / Color / Advance, Genesis, Master System, Game Gear, N64, PlayStation, PlayStation 2 and GameCube / Wii. Retro games live in the same Library and launch like PC games, but run on a libretro backend, on ARMSX2 in a separate :ps2 process, or on an embedded standalone Dolphin in :gc. No core ships in the APK. Each emulator is built from its own fork under the WinNative-Emu org, WinNative-Emu/Retro-Consoles packs every core plus the Dolphin and ARMSX2 runtime data into one retro-consoles.tzst, and the app downloads and SHA-256-verifies it from Settings > Retro. The forks rebuild every Friday at 17:00 ET and the bundle is packed at 18:00; both compare against what is already published and release nothing when the output is byte-identical, so a quiet week costs users no download. bundle-info.json carries the tag, build date, checksum and size; the installed copy is the marker file, so the app only offers an update when the published checksum actually differs. Also included: - RetroAchievements via rcheevos, softcore only (hardcore needs per-client registration and is hidden until then) - Per-console core options generated from each core's own source, grouped into Display / Sound / Performance / Controls / System tabs - Touch controls, netplay for the libretro cores and Dolphin, save states, cloud save sync and a performance HUD - 22 locales translated
maxjivi05
force-pushed
the
feature/retro-console-emulation
branch
from
July 28, 2026 15:09
6fea9a9 to
02b7412
Compare
…ease" /releases/latest/download resolves to whichever release was published most recently, which is the immutable bundle-<date>-<sha> tag, not the rolling "latest" tag the workflow maintains. Both carry the same assets today, so this worked by luck; a run that created the immutable tag and then failed before updating latest would have pointed the app at the wrong archive. /releases/download/latest names the tag itself.
Turning the HUD off in a game changed a single global preference (retro_def_hud_global, which ignored the system id it was passed), so it went off for every game on every console. The shortcut settings screen edited that same global value while presenting it as a per-game setting. The HUD now follows the pattern every other setting already used: the shortcut extra is the value, the console default is only the fallback when the shortcut has never been set. Both the in-game menu and the shortcut settings screen read and write that one place, on all three launch paths (libretro, embedded Dolphin, and PS2). The PS2 process had no shortcut reference at all, so it also gained the shortcut path and container id at launch, and queues writes until the shortcut loads. Auditing the rest of the menu turned up the same bug twice more, in the PS2 overlay only: on-screen controls and adaptive sticks wrote the console default where libretro and Dolphin persist them per game. Both now write the shortcut, and the PS2 launch seeds its cross-process prefs from the shortcut rather than from whatever the last game left behind. Settings > Retro still edits the console defaults, which is its job; the two HUD call sites now say explicitly which store they write. HUD element selection and style stay global.
Adds a second way to run Pokémon Red/Blue/Yellow: gen1recomp, a Lua
reimplementation of the games, with the Dramatic Shape voxel mod drawing the
overworld as a 3D diorama. It is hosted the way Dolphin is -- in WinNative's
own process, with WinNative keeping the menus, the settings and the controls
-- so the engine's own launcher, options menu and touch pad never appear.
Offered per game, above Play and on the Graphics pane, and only for a ROM
whose SHA-1 matches a supported title with the engine present in the bundle.
Everything else launches on the standard core exactly as before.
The menu is the real Retro drawer, the same composable the GB/GBC/GBA paths
use. It turned out never to have been tied to libretro: RetroMenuController
takes callbacks that return rows, so these rows come from the engine
instead. They are the engine's OWN option rows, read over a file bridge, so
the mod's settings appear without WinNative knowing anything about them and
stepping a row runs the engine's own handler with its side effects. An
earlier attempt drove the engine by injecting keystrokes; that could never
read a value back, so every switch was a guess, and it deadlocked SDL.
Notable pieces:
Gen1EngineActivity hosts the engine. SDLActivity extends plain Activity,
so this supplies the lifecycle owners Compose needs --
on the window's decor view, since Compose resolves them
from the window root, not from the ComposeView.
Gen1EngineBridge the host half of the control channel.
Gen1ModInstaller unpacks the mod from the bundle. It must be the app
that writes those files: files placed in its external
storage by another uid are listed but cannot be opened
through Android's FUSE layer, which made the engine
report zero mods installed with no error.
RetroShortcuts usesEmbeddedLauncher, now the single answer to "does
this shortcut need a non-libretro launcher". Two
callers each had their own list, and the one in
UnifiedActivityLaunch knew about PS2 and Dolphin but
not this, so 3D-enabled games silently opened on the
standard core.
RetroDrawerMenu a Stepper row, for a setting whose value set the host
does not know. Choice cannot express that.
app/src/main/engine SDL2 and love-android glue, vendored under
org.love2d.sdl. ARMSX2 ships org.libsdl.app from a
different SDL version and only one copy survives dex
merge; the engine build renames its half to match.
The engine surface is sized to a whole multiple of 160x144 rather than to
whatever fits, because the engine scales by an integer factor and centres the
remainder -- so an exact-fit rectangle just moved the black border inside the
surface, leaving the picture floating below a band with its lower edge behind
the buttons.
maxjivi05
force-pushed
the
feature/retro-console-emulation
branch
from
July 31, 2026 02:43
58821f8 to
ca42263
Compare
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Adds retro console support alongside the existing Wine/PC library. Retro games sit in the same Library and launch like PC games, but run on a libretro backend instead of Wine — or, for PS2 and GameCube/Wii, on a full emulator in its own process.
No emulator core ships in the APK. Every core is built from its own fork under
WinNative-Emu, packed into a single archive byWinNative-Emu/Retro-Consoles, and downloaded on demand from Settings › Retro.Consoles
:ps2:gcCore delivery
The app used to carry ~150 MB of core binaries and emulator data in git. That is gone.
latestrelease.Retro-Consolespulls every core plus the DolphinSystree and ARMSX2 runtime assets into oneretro-consoles.tzst(currently 38.5 MB, 11 cores).Updates
bundle-info.jsonis published beside the archive carrying the tag, build date, checksum and size. A copy of the installed one is the on-disk marker, so "is there an update" is an exact checksum comparison rather than a guess from timestamps. Settings › Retro checks once when the screen opens (a 193-byte fetch) and the row reads Installed — build 2026-07-28 until something newer exists, at which point it becomes Update available — build … (36 MB) and the button changes from Check for updates to Update console cores. Nothing downloads without a tap.Release train
Every core fork rebuilds Friday 17:00 ET, syncing its upstream parent first; the bundle is packed at 18:00 ET. Both compare their output against what is already published and release nothing when it is byte-identical, so a week with no upstream change costs users no download. This required making the archive reproducible (
tar --sort=name --mtime=@0 --owner=0 --group=0 --numeric-owner, single-threaded zstd, no run-stamped files inside) — verified by two consecutive runs producing identical archives and skipping the release.Also in this branch
Notes for review
libdolphin_libretro_android.sois the one core still in the APK: it is the legacy libretro GameCube path behind thewn.gc.embeddedtoggle, and no fork builds it. Everything else resolves from the bundle only — there are deliberately no APK fallbacks, so a missing bundle fails loudly instead of silently degrading.dlopened by name from the APK's own library directory and are intentionally absent from the bundle.libretrodroid/src/main/cpp,org.libsdl,dolphin/vendored,app/src/main/cpp) are carried as-is.