80 lines
4.2 KiB
Markdown
80 lines
4.2 KiB
Markdown
# Development
|
|
|
|
Short guide for anyone working on the PLWL codebase.
|
|
|
|
## Layout
|
|
|
|
```
|
|
src/ main process (Node/Electron backend)
|
|
main.js entry point: tray, single-instance handoff, --launch / --open
|
|
argv.js command-line parsing shared by boot and second-instance handoff
|
|
window.js main window creation
|
|
ipc/ all ipcMain handlers
|
|
index.js handler registration, icon protocol, dialogs
|
|
games.js games service: run/stop state, wine resolution, open-with handoff
|
|
lansync.js LAN sync handlers (identity, devices, re-roll, sync + progress)
|
|
runner.js spawns wine/proton (env, prefix, playtime, logs)
|
|
library.js apps registry (apps.json) + settings + playtime files
|
|
wines.js wine/proton build scan, registry, portable symlink healing
|
|
prefixes.js prefix registry (files/wineprefixes)
|
|
importer.js app import (copy/move/leave/prefix)
|
|
openwith.js "Open with PLWL": ad-hoc runs, no library entry
|
|
shortcuts.js .desktop shortcut generation
|
|
paths.js portable layout, FILES-relative path helpers, translation sync
|
|
i18n.js translation loading + {0} placeholder filling
|
|
preload.js contextBridge API exposed to the renderer
|
|
lansync.js LAN sync: identity + pairing, hashing, HTTP receiver, UDP discovery
|
|
lansyncpush.js the pushing side (createPusher factory, keeps helper state out)
|
|
appicon.js window/taskbar icon
|
|
renderer/ UI (plain HTML/CSS/JS, no framework)
|
|
app.js views, modals, custom-select, all renderer logic
|
|
index.html static markup for every view
|
|
style.css the whole look; CSS variables at the top
|
|
files/ portable data the launcher ships/creates at runtime
|
|
translations/ en-us.json, pl.json (copied to the data dir on start)
|
|
test/ plain node scripts, run them with `node test/<name>.test.js`
|
|
tools/ install.sh / createshortcut.sh / build helpers
|
|
```
|
|
|
|
Main process vs renderer: the renderer never touches Node/Electron directly -
|
|
everything goes through the `window.plwl` bridge (preload.js) and ipcMain
|
|
handlers in src/ipc/. Keep new APIs in that pattern.
|
|
|
|
## Rules
|
|
|
|
- Keep it simple. Plain functions over classes, no abstractions "for later".
|
|
- Comments explain the WHY (quirks, workarounds, races), not the WHAT. If the
|
|
code says it, don't repeat it in words. No comments at all when nothing
|
|
needs explaining.
|
|
- No duplicate logic: the second time you copy something, move it into a
|
|
helper (a shared module in src/ or a function next to its users) and call
|
|
it from both places.
|
|
- Everything user-visible goes through the translation files (en-us.json,
|
|
pl.json) with `{0}`, `{1}` placeholders. No hardcoded strings in app.js.
|
|
- Paths stored on disk are FILES-relative (portable layout): write with
|
|
toPortablePath(), read with resolvePortablePath() - never store absolute
|
|
paths for anything inside files/.
|
|
- Registries (apps.json, wines.json, prefixes.json) are rewritten whole via
|
|
writeJson(); playtime lives in its own tiny file so the registry is not
|
|
rewritten while a game runs.
|
|
- Deleting user data needs a confirm modal; best-effort cleanup is
|
|
try/catch-and-ignore with a comment saying why it is safe to ignore.
|
|
- Windows apps run through runGame()/buildEnv() - never spawn wine directly
|
|
somewhere else (prefix handling, Proton env and playtime live there).
|
|
- CSS: reuse the existing variables/classes (.button, .field-label,
|
|
.custom-select, form-card); spacing rhythm comes from --button-margin and
|
|
the flex gap of the container, not per-element magic numbers.
|
|
- LAN sync has two sides: the receiver lives in lansync.js, the sender in
|
|
lansyncpush.js and is built by createPusher(helpers) - several launcher
|
|
states share the module, so nothing may be kept in its module scope.
|
|
- Tests are plain assert-by-print scripts (see test/): set PLWL_BUILD_DIR to
|
|
a temp dir, check(), exit 1 on failure. Add one when fixing a bug.
|
|
|
|
## Verify before you commit
|
|
|
|
```
|
|
node --check <changed js files> # syntax
|
|
node test/import.test.js # ...and the other test files
|
|
node test/lansync.test.js # LAN sync contract (identity, pairing, mirror)
|
|
npm start # click through the flow you touched
|
|
```
|