Releases: Switch-Bros/SteamLibraryManager
Releases · Switch-Bros/SteamLibraryManager
v1.5.1
Fixed
-
External-game shortcuts now actually launch from Steam. Since v1.4.4
every Heroic / Lutris / Flatpak / itch shortcut SLM added to Steam was
broken: the URI orflatpak run ...command was written into Steam's
exefield, which Steam treats as a file path. Clicking Play silently
did nothing or, with Heroic in particular, crashed Steam outright when
the overlay tried to attach to Electron.The launch command is now split into
exe+launch_options, with
three additional protections applied to every external launch:- URIs are routed through their native launcher binary
(/usr/bin/heroic,/usr/bin/lutris) so the dbus-boundxdg-open
hop isn't needed -xdg-openis unreliable inside Steam's runtime. - The whole invocation is wrapped in
setsid -fso the launcher
detaches into its own session and Steam stops tracking it
immediately - no more "Anhalten" hangs, no more crashes when Steam
waits forever for an Electron app to exit. env -u LD_PRELOAD -u LD_LIBRARY_PATH -u SteamAppId ...strips
Steam's overlay shim and bookkeeping vars from the environment so
Heroic / Proton / Wine start clean. Without this the Steam
overlay's 32-bit shim leaks into 64-bit Wine processes and the
game silently fails to launch.
After updating, existing broken shortcuts in
shortcuts.vdfneed to
be removed and re-added via the External Games dialog for the fix
to take effect. - URIs are routed through their native launcher binary
v1.5.0
Added
- Heroic Sideload Parser: Manually added (sideloaded) apps in Heroic
Games Launcher are now visible in the "Externe Spiele verwalten"
dialog under platform "Heroic (Sideload)". Previously SLM only saw
GOG/Epic/Amazon games in Heroic - sideloads like Adobe Photoshop or
WarCraft 2 remastered were invisible. - Cover fallback in batch_add_to_steam: After a shortcut is added,
SLM now automatically tries to fetch a cover via SteamGridDB name
search. If SteamGridDB returns nothing, it falls back to the
art_coverURL the source platform already chose (e.g. Heroic's
pre-selected SteamGridDB image). Failures never break the add flow. - New optional
cover_url_hintfield onExternalGamemodel for
source-provided cover URLs. Other parsers can populate it later.
Changed
BaseHeroicParser._RUNNERdocstring now lists all four valid runner
values (legendary,gog,nile,sideload).
Fixed
_try_fetch_coverusedget_images_by_type(sgdb_game_id, ...)which
internally tried to convert the input as a Steam app id. Switched to
get_images_by_type_paged(0, "grids", game_id_override=top_id)so
the SGDB game id is used directly.
v1.4.5 - Critical appinfo.vdf metadata fix
Fixed
- Critical: Metadata edits now actually visible to Steam. A latent bug
causedupdate_app_metadatato write intodata["common"](top-level)
while Steam reads fromdata["appinfo"]["common"]. As a result, every
metadata edit since the feature was introduced silently went into a
parallel section that Steam ignored - users saw the change in SLM but
never in the Steam Library. The writer now targets the correct path,
cleans up staledata["common"]entries from older SLM versions, and
the drift detector compares against the path Steam actually reads. - The
_find_common_sectionlookup order is reversed to match Steam's
reading order (appinfo.commonfirst, top-levelcommonas fallback).
Added
- Auto-Reapply on startup:
AppInfoManager.verify_and_reapply()runs
after everyload_appinfo. If Steam overwrote the file with fresh CDN
data and wiped out the user's edits, SLM detects the drift and re-applies
the saved modifications immediately - no manual restore button needed. - Live file watcher on
appinfo.vdfviaQFileSystemWatcher. While
SLM is running, any external rewrite of the file (Steam refresh, manual
edit, etc.) is detected and re-applied. Debounced 800 ms to coalesce
Steam's burst writes; self-write suppression via timestamp window so the
watcher does not loop on our own writes. - Immediate VDF write after every save. Previously the binary VDF was
only flushed on SLM exit, so a crash between save and exit would lose
the edit.save_appinfo()now writes the VDF as soon as the in-memory
state is dirty. - 16 new unit tests covering drift detection, partial drift across
multiple apps, fallback paths, and the new save-triggers-write behavior.
Changed
update_app_metadatano longer creates a top-levelcommonblock;
always targetsappinfo.common. Stale top-level blocks are removed on
the next write so the file converges back to Steam's expected layout.
v1.4.4 - Complete External Games Overhaul
Added
- Smart Emulator Detection - SLM detects 9 emulators (Eden, Citron, Ryujinx,
Cemu, Dolphin, Azahar, RetroArch, PPSSPP, melonDS, DOSBox) by reading their
own config files for game directories. No more hardcoded ROM search paths. - Settings tab "Emulators" - per-emulator status, custom game directories,
default-emulator-per-system picker, executable override. - EmuDeck hint provider - reads
~/emudeck/settings.shas a fallback for
emulators that have no library config of their own. Works around EmuDeck's
known concatenation bug by parsingemulationPathand deriving rom dirs
ourselves. - AppImage auto-discovery in standard Linux user locations (
~/Applications,
~/AppImages,~/Apps,~/.local/bin,~/bin) - covers the common case
where users park AppImages outside the system PATH. - Shortcuts importer -
shortcuts.vdfnon-Steam entries now show up in the
main library, with their tags surfaced as SLM categories. - Bidirectional category sync for shortcuts - SLM-side category changes
write back to bothshortcuts.vdf(Steam UI live read) andcloud-storage
from-tag-Xcollections (Steam library sidebar). Steam shows the collection
populated after a restart, no manual tagging needed. - Manual SteamGridDB search - the cover picker now has a search box that
lets you look up a game by name. For non-Steam shortcuts (whose hash appids
are unknown to SteamGridDB) it auto-runs the name lookup on open. - External Games dialog: deselect-all / select-all toggle button and
user-resizable column headers. - DB Schema v12 with new tables
emulator_settingsandemulator_games.
Fixed
- Crash on click on non-Steam shortcuts - Steam Store API was being called
with negative shortcut appids and crashed on theNoneJSON response. Now
guarded: appids outside the positive int32 range skip the remote fetch, and
malformed responses no longer index intoNone. - Cover filenames for non-Steam shortcuts - SLM now writes covers under
the unsigned uint32 form of the shortcut appid, which is what Steam expects.
Old signed-form covers are still found by the lookup so existing setups
keep working.
Changed
ROM_SEARCH_PATHS,APPIMAGE_DIRS,EMUDECK_LAUNCHER_DIRSconstants
removed in favour of config-driven emulator discovery.Game.app_idfor shortcuts is now the canonical unsigned uint32 form,
matching Steam's own convention for cover paths and cloud-storage collection
entries. Conversion to/from the signed form happens at the shortcuts.vdf
boundary only.RomParseris now a thin facade overEmulatorService.
v1.4.3
Fixed
- AppImage on Mint 21.3 / Ubuntu 22.04 (GH #13) - Qt 6.5+ requires
libxcb-cursor.so.0for the xcb platform plugin, which older Debian/Ubuntu/
Mint releases do not ship by default. The library is now bundled into the
AppImage vialinuxdeploy --library. Build aborts early if the dependency
is missing on the build host.
Changed
build-appimage.shand.github/workflows/build-appimage.ymlresolve
libxcb-cursor.so.0vialdconfig -pand pass the path to linuxdeploy.- CI installs
libxcb-cursor0so the workflow finds the library.
Added
- Bug-Report-Template Versions-Dropdown auf v1.4.3, v1.4.2, v1.4.0, v1.3.9
erweitert.
v1.4.2
Fixed
- Statistics i18n - all chart labels fully translated (Deck status, ProtonDB
tiers, review scores, PEGI ratings, achievement buckets, playtime ranges).
Labels built lazily to avoid circular import issues at module init. - Genre tab - falls back to Steam tags when game_genres table is empty.
- Comparison tab - triggers on autocomplete selection (not just Enter).
HLTB values rounded to 1 decimal place. - Donut "Others" overflow bucket label translated.
- Readable bucket labels - all internal keys (op_95, lt_1h, etc.) replaced
with human-readable text in all chart legends.
Added
- Statistics screenshots (EN + DE) in README.
v1.4.0
Added
- Statistics Dashboard - complete overhaul with 7 interactive tabs:
- Overview: 4 metric cards (total games, playtime, never played, perfect games)
- genre donut chart + top 5 most played bar chart
- Genre: side-by-side donuts (by count vs by playtime) with insight text
showing "You own most RPGs but play Shooters the most" - Platform: 3 donuts showing real per-platform playtime (Windows/Linux/
Steam Deck/Mac), Deck compatibility status, and ProtonDB tier distribution - Achievements: metric cards (unlocked, rare, ultra-rare, perfect) +
completion buckets donut + almost-done bar + Trophy Wall with cover art - Playtime: playtime buckets + HLTB analysis + shame pile (installed
never-played games sorted by HLTB estimate) - Ratings: PEGI distribution + review score buckets + top 10 developers
- Comparison: search and compare any 2 games side-by-side across all metrics
- Overview: 4 metric cards (total games, playtime, never played, perfect games)
- Chart Engine - custom QPainter-based DonutChart and BarChart widgets
with hover effects, responsive legends, and "Others" bucketing. No external
charting dependencies. - Platform Playtime Tracking - per-platform playtime (Windows, Linux, Mac,
Steam Deck) persisted in database from Steam API. Shows where you actually
play instead of just "supported platforms". - Playtime Persistence - game playtime and last-played timestamps saved to
SQLite database, surviving Steam API outages.
Changed
- DB Schema v11 - added playtime_minutes, last_played, playtime_windows,
playtime_linux, playtime_mac, playtime_deck columns to games table. - Statistics dialog rebuilt as tabbed package (
ui/dialogs/statistics/)
replacing the old 177-line monolithic dialog.
Fixed
- API keys not loading from keyring - circular import at module init time
prevented TokenStore from loading keys. Now deferred to bootstrap phase.
v1.3.9
Improved
- i18n: Massive cleanup - eliminated 120+ duplicate translation keys across
all JSON files. Common terms (Username, Password, Settings, Name, Platform,
etc.) consolidated intocommon.json. Cloud Sync keys moved frommain.json
tosettings.jsonwhere they belong. - i18n: rclone setup dialog - German labels ("Passwort", "Benutzername")
hardcoded in Python source replaced with propert()calls. English users
no longer see German UI text.
Changed
- DRY: User-Agent constants - Chrome and app User-Agent strings centralized
inconfig.py(USER_AGENT_BROWSER,USER_AGENT_APP), replacing 7 scattered
hardcoded copies. - DRY: Database path - duplicated
_get_db_path()in 4 action files replaced
with a singleMainWindow.db_pathproperty.
Fixed
- Steam Store rate limiting - increased request interval to 1.5s and added
automatic 30s backoff on HTTP 429 responses. Prevents Steam from DNS-blocking
the client during bulk PEGI rating fetches. - Network error abort - all enrichment threads now abort after 3 consecutive
DNS resolution or rate-limit errors instead of pointlessly retrying thousands
of requests against an unreachable server.
Security
- API keys moved to system keyring -
STEAM_API_KEYandSTEAMGRIDDB_API_KEY
are now stored in the OS keyring (or encrypted file fallback) instead of
plaintextsettings.json. Existing keys are auto-migrated on first launch.
v1.3.8
v1.3.7
Fixed
- Flatpak: Steam-Running detection: The Steam-running warning never appeared
when running as Flatpak becausepsutil.process_iter()cannot see host
processes from inside the sandbox. Now checks for Steam's named pipe
(~/.steam/steam.pipe) first, which is visible via--filesystem=~/.steam:ro.
Falls back to psutil for native installations.
Changed
- Flatpak dependencies: Added missing
pybind11(Pillow build dependency)
andsix(steam library dependency) to Flatpak manifest.