Skip to content

Web client: install to a home screen as a full-screen app, and keep the screen awake - #490

Merged
dividebysandwich merged 1 commit into
dividebysandwich:mainfrom
dielectric-coder:web-home-screen-app
Sep 20, 2026
Merged

dividebysandwich merged 1 commit into
dividebysandwich:mainfrom
dielectric-coder:web-home-screen-app

Conversation

@dielectric-coder

Copy link
Copy Markdown
Contributor

On a tablet a browser tab spends about a third of the screen on an address bar and toolbars, and they never go away. That is partly the client's own doing: the page sets overflow: hidden so a drag pans the waterfall rather than scrolling the document, which is also what stops the browser auto-hiding its chrome the way it does on an ordinary site.

A web app manifest fixes it. "Add page to Home screen" then installs the client rather than bookmarking it, and launching from that icon gives the whole panel. display_override asks for fullscreen and falls back to standalone where that is not honoured.

The screen also has to stay on. A receiver panel is watched rather than read — minutes of waterfall without touching the glass — and a tablet blanks after thirty seconds of that. Installed full screen, the blank screen takes the whole application away and brings it back behind a lock screen. wake_lock.js holds a screen wake lock while the page is visible, gives it up whenever the page is hidden (a backgrounded client has no business keeping a screen lit — the browser does this part itself), and takes a fresh one on the way back, which is the only work there is. A browser without the API, or one refused by battery saver or a device policy, sleeps exactly as before and nothing is reported: it is a comfort, not a requirement. It is exposed as window.sdroxideWakeLock so the client can drive it if it ever grows a setting.

Notes on the details

  • start_url and scope are ./, for the same reason public_url is and the hand-written <script> tags are: the client is commonly served under a prefix rather than at the root (support behind reverse proxy on subpath #241), and an absolute scope would leave it installable only from a server that owns its whole host.
  • The icons come from packaging/icons, the same artwork every other platform renders from, pulled in by Trunk — no second copy in the tree. Android wants a 192 px one, which did not exist; render.sh gains that size and the file is committed with the rest. I rendered only the new size rather than re-running the script, so no unrelated icons churn.
  • No Rust is touched. The manifest does nothing at all unless a browser is asked to install the page, so the desktop web client and the native build are unaffected.
  • Installing needs a secure context, the same as audio (§9.3), so it is another reason to put a server behind HTTPS or reach it over a tunnel or VPN. The manual says so.

Testing

On a Galaxy Tab S7+ with Samsung Internet, served over HTTPS: it installs from the home-screen icon and runs true full screen — the status bar is gone, so fullscreen is honoured rather than the standalone fallback — and it behaves as an ordinary window under Samsung DeX.

The wake lock is not yet confirmed on that hardware, only the full-screen half. I will report back once it has been sat in front of for long enough to be sure, and I am happy to hold this until then.

One choice worth questioning: the wake lock is unconditional while the page is visible, rather than tied to a setting or to whether audio is playing. That suits a receiver, but it is the piece most likely to want an opinion.

Documentation

  • Manual §9.5 gains "Installing it to the home screen": the per-browser steps, the reminder to launch from the icon rather than a tab, the secure-context requirement, and what the wake lock does and when it does not.
  • README gains a clause on the server bullet.

…ll-screen app, and hold the screen awake while it is in front, so the panel gets the glass instead of browser chrome

On a tablet a browser tab spends about a third of the screen on an address bar
and toolbars, and they never go away: the page sets `overflow: hidden` so a drag
pans the waterfall rather than scrolling the document, which is also what stops
the browser auto-hiding its own chrome the way it does on an ordinary site.

A web app manifest fixes it. "Add page to Home screen" then installs the client
rather than bookmarking it, and launching it from that icon gives the whole
panel — no address bar, no status bar. `display_override` asks for `fullscreen`
and falls back to `standalone` where that is not honoured.

`start_url` and `scope` are `./`, for the same reason `public_url` is and the
hand-written script tags are: the client is commonly served under a prefix
rather than at the root (issue dividebysandwich#241), and an absolute manifest scope would leave
it installable only from a server that owns its whole host.

The icons come from `packaging/icons`, the same artwork every other platform
renders from, so there is no second copy of it in the tree. Android wants a
192 px one, which did not exist; `render.sh` gains that size and the file is
committed with the rest.

The screen also has to stay on. A receiver panel is watched rather than read —
minutes of waterfall without touching the glass — and a tablet blanks after
thirty seconds of that; installed full screen, the blank screen takes the whole
application away and comes back behind a lock screen. `wake_lock.js` holds a
screen wake lock while the page is visible. The browser drops it whenever the
page is hidden, which is the behaviour wanted, so the work is taking a fresh one
on the way back; a browser without the API, or one refused by battery saver or a
device policy, simply sleeps as before and nothing is reported. It is exposed as
`window.sdroxideWakeLock` so the client can drive it if it ever grows a setting.

Tested on a Galaxy Tab S7+ with Samsung Internet: installs from the home screen
icon and runs true full screen, with the status bar gone rather than the
`standalone` fallback, and behaves as an ordinary window under Samsung DeX. The
wake lock is not yet confirmed on that hardware.

Manual gets the how-to under 9.5, including that installing needs the same
secure context audio does.
@dielectric-coder

Copy link
Copy Markdown
Contributor Author

Closing the gap left in the description: the wake lock is confirmed on the same hardware. Galaxy Tab S7+, Samsung Internet, installed to the home screen and served over HTTPS — the panel is left untouched and the screen stays on, where the same tablet blanks in about thirty seconds on any ordinary page.

So both halves are now tested on device rather than one:

Galaxy Tab S7+ / Samsung Internet
installs from the home-screen icon yes
fullscreen honoured, status bar gone yes — not the standalone fallback
Samsung DeX behaves as an ordinary window
screen held awake while in front yes

Nothing has changed in the branch; this is the missing measurement, not a new commit.

The open question from the description still stands and is worth an opinion: the lock is taken unconditionally while the page is visible, rather than behind a setting or tied to whether audio is playing. Happy to put it behind a Settings → UI switch if you would rather it were the operator's choice — that would mean touching the client, which this branch deliberately does not.

@dividebysandwich
dividebysandwich merged commit c0e09de into dividebysandwich:main Sep 20, 2026
@dielectric-coder
dielectric-coder deleted the web-home-screen-app branch September 22, 2026 16:49
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants