Skip to content

Conversation

@msk
Copy link
Contributor

@msk msk commented Feb 9, 2026

On some Onyx Boox devices (confirmed on Palma 2), the SurfaceView surface is not recreated after the rapid RESUME/PAUSE/STOP activity cycling that the Boox system performs on wake. This leaves android.app.window permanently nil, causing a black screen. The app is still running and responding to touch; it just can't render because ANativeWindow_lock has no window to lock.

The SurfaceView with setZOrderOnTop(true) and PixelFormat.TRANSPARENT was introduced for NGL4/Tolino devices. The Onyx Qualcomm EPD API (View.refreshScreen) does not require a SurfaceView; when needsView is false, einkUpdate() already falls back to the DecorView content view. Setting needsView()=false makes Onyx devices use NativeActivity's default DecorView surface, which follows the standard activity lifecycle and correctly survives the Boox wake sequence.

This fixes koreader/koreader#12445.

Diagnostics that led to this fix

Lifecycle event logging on the Boox Palma 2 revealed that after sleep/wake, INIT_WINDOW never fires when using a SurfaceView:

  1. PAUSE → TERM_WINDOW(nil) → STOP → LOST_FOCUS
  2. START → RESUME → PAUSE → RESUME → PAUSE → STOP → START → RESUME → GAINED_FOCUS(nil)

With needsView()=false (DecorView surface), INIT_WINDOW fires correctly:

  1. PAUSE → TERM_WINDOW(nil) → STOP → LOST_FOCUS
  2. START → RESUME → PAUSE → RESUME → INIT_WINDOW(valid) → PAUSE → TERM_WINDOW(nil) → STOP → START → RESUME → INIT_WINDOW(valid) → GAINED_FOCUS(valid)

Test on Boox Palma 2

See koreader/koreader#12445 (comment) for the reproduction steps.

  • Before this fix: font size change → sleep → wake causes black screen
  • After this fix: font size change → sleep → wake no longer causes black screen

This change is Reviewable

On some Onyx Boox devices (confirmed on Palma 2), the SurfaceView
surface is not recreated after the rapid RESUME/PAUSE/STOP activity
cycling that the Boox system performs on wake. This leaves
android.app.window permanently nil, causing a black screen.

The SurfaceView with setZOrderOnTop(true) and PixelFormat.TRANSPARENT
was introduced for NGL4/Tolino devices. The Onyx Qualcomm EPD API
(View.refreshScreen) does not require a SurfaceView — when needsView is
false, einkUpdate() already falls back to the DecorView content view.
Setting needsView()=false makes Onyx devices use NativeActivity's
default DecorView surface, which follows the standard activity lifecycle
and correctly survives the Boox wake sequence.
@Frenzie Frenzie requested a review from hugleo February 9, 2026 18:34
@hugleo
Copy link
Contributor

hugleo commented Feb 9, 2026

Last time I tested, my device also worked with needsView = false, and if I remember correctly, I don’t recall any Onyx device that required this feature. I think you can go ahead with that and if someone complains we can create a specific driver just for that device.

@hugleo hugleo requested review from hugleo and removed request for hugleo February 9, 2026 19:09
Copy link
Contributor

@hugleo hugleo left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

lgtm

@Frenzie Frenzie merged commit 3e149d8 into koreader:master Feb 9, 2026
3 checks passed
@BrendanL79
Copy link

Congratulations, @msk !! This one's been bugging me for a LONG time.

benoit-pierre pushed a commit to benoit-pierre/koreader that referenced this pull request Feb 10, 2026
…/android-luajit-launcher#579)

On some Onyx Boox devices (confirmed on Palma 2), the SurfaceView
surface is not recreated after the rapid RESUME/PAUSE/STOP activity
cycling that the Boox system performs on wake. This leaves
android.app.window permanently nil, causing a black screen.

The SurfaceView with setZOrderOnTop(true) and PixelFormat.TRANSPARENT
was introduced for NGL4/Tolino devices. The Onyx Qualcomm EPD API
(View.refreshScreen) does not require a SurfaceView — when needsView is
false, einkUpdate() already falls back to the DecorView content view.
Setting needsView()=false makes Onyx devices use NativeActivity's
default DecorView surface, which follows the standard activity lifecycle
and correctly survives the Boox wake sequence.
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.

[onyx boox]: black screen when starting KR or resuming from sleep

4 participants