A Kotlin Multiplatform Even Hub Web demo using Compose Multiplatform for the UI, targeting Kotlin/JS and Kotlin/Wasm. It is a simple novel reader: bookshelf, chapter list, and reading view, plus Even Hub integration for device and page containers.
- User & device: User info, device status (glasses, ring, etc.)
- Bookshelf & reading: Book list, chapter selection, reading dialog
- Image test: Custom-size canvas, 3D preview, screenshot upload to Even Hub container
- Even Hub: Create/rebuild page containers, update image raw data, text container upgrade, shut down page container
- Even Hub SDK: npm package
@evenrealities/even_hub_sdk(version^0.0.6) - Kotlin/JS and Kotlin/Wasm expect/actual bridge; shared
webMainlogic
Bridge and helpers:
| Description | Path |
|---|---|
| Bridge API | composeApp/src/webMain/kotlin/.../sdk/EvenHubBridge.kt |
| JS/Wasm impl | composeApp/src/jsMain/.../sdk/EvenHubBridge.js.kt, .../wasmJsMain/.../EvenHubBridge.wasmJs.kt |
| Types & parsing | EvenHubTypes.kt, EvenHubJsParsers.kt |
| JS interop | EvenHubJsInterop.kt, JsInteropUtils.kt |
Usage: Call ensureEvenAppBridge() first; then use Basic API for user/device, and Even Hub API for page containers and events.
Bridge setup and user/device access (in EvenHubBridge.kt). Call these before or alongside Even Hub features.
| API | Description |
|---|---|
ensureEvenAppBridge() |
Initialize and wait for Even App bridge. Must be called once before any other SDK usage. |
getUserInfo(): UserInfo? |
Get current user info |
getDeviceInfo(): DeviceInfo? |
Get device info (glasses, ring, etc.) |
observeDeviceStatus(onChange): () -> Unit |
Subscribe to device status; returns unsubscribe |
Page containers and event subscription (aligned with host BleG2CmdProtoEvenHubExt). Use these for Even Hub–specific features; do not call low-level generic methods.
| API | Description |
|---|---|
observeEvenHubEvent(onChange): () -> Unit |
Subscribe to EvenHub events (list/text/system); returns unsubscribe |
| API | Description |
|---|---|
createStartUpPageContainer(container): Int? |
Create startup page container (text/list/image); returns container ID |
rebuildPageContainer(container): Boolean |
Rebuild page container |
updateImageRawData(data): Boolean |
Update image raw data (e.g. imageData as number[]) |
textContainerUpgrade(container): Boolean |
Upgrade text container content |
shutDownPageContainer(container): Boolean |
Shut down page container (exit Even Hub page) |
- CreateStartUpPageContainer:
containerTotalNum,listObject,textObject,imageObject - RebuildPageContainer: same fields, for rebuild
- ImageRawDataUpdate:
containerID,containerName,imageData(prefer number[]) - TextContainerUpgrade:
containerID,containerName,content, etc. - ShutDownContainer:
exitMode(e.g. 0)
Construct these data classes and pass them to the Even Hub API; serialization is in EvenHubJsParsers.kt.
- JDK: 24 (see
jvmToolchain(24)incomposeApp/build.gradle.kts) - Node.js: for Webpack and npm (Gradle uses it automatically)
git clone <repository-url>
cd InNovelDefault port: 2000.
Wasm (recommended, modern browsers):
- macOS / Linux:
./gradlew :composeApp:wasmJsBrowserDevelopmentRun
- Windows:
.\gradlew.bat :composeApp:wasmJsBrowserDevelopmentRun
JS (older browsers):
- macOS / Linux:
./gradlew :composeApp:jsBrowserDevelopmentRun
- Windows:
.\gradlew.bat :composeApp:jsBrowserDevelopmentRun
(Change devServer.port in composeApp/build.gradle.kts if the port is in use.)
- Wasm:
./gradlew :composeApp:wasmJsBrowserDevelopmentWebpack - JS:
./gradlew :composeApp:jsBrowserDevelopmentWebpack
composeApp/src/commonMain: Shared Compose theme, etc.composeApp/src/webMain: Web shared logic and UI (bookshelf, reading, image test, SDK bridge and types)composeApp/src/jsMain: Kotlin/JS platform impl (Bridge, Interop)composeApp/src/wasmJsMain: Kotlin/Wasm platform impl (Bridge, Interop)
Feedback: #compose-web. Issues: YouTrack.