Skip to content

Commit e5a5aea

Browse files
kdroidFilterclaude
andcommitted
refactor(windows): migrate from JNA to JNI for native tray and mouse hook
Replace JNA-based Windows implementation with pure JNI, following the same patterns as Mac and Linux bridges. Add WindowsNativeBridge.kt with external JNI declarations and jni_bridge.c wrapping the tray.h C API. Rewrite WindowsTrayManager and WindowsOutsideClickWatcher to use JNI calls instead of JNA structures and callbacks. Remove all JNA dependencies from build configuration. Rename DLL output from tray.dll to WinTray.dll. Update GraalVM reachability metadata and CI workflow for JDK requirement. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
1 parent 43e6442 commit e5a5aea

16 files changed

Lines changed: 760 additions & 399 deletions

File tree

.github/workflows/build-natives.yaml

Lines changed: 10 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -83,6 +83,12 @@ jobs:
8383
- name: Checkout code
8484
uses: actions/checkout@v4
8585

86+
- name: Set up JDK
87+
uses: actions/setup-java@v4
88+
with:
89+
java-version: '17'
90+
distribution: 'temurin'
91+
8692
- name: Build Windows native libraries
8793
working-directory: src/native/windows
8894
run: cmd /c build.bat
@@ -92,21 +98,21 @@ jobs:
9298
- name: Verify Windows natives
9399
shell: bash
94100
run: |
95-
test -f build/nativeLibs/win32-x86-64/tray.dll
96-
test -f build/nativeLibs/win32-arm64/tray.dll
101+
test -f build/nativeLibs/win32-x86-64/WinTray.dll
102+
test -f build/nativeLibs/win32-arm64/WinTray.dll
97103
ls -la build/nativeLibs/win32-x86-64/
98104
ls -la build/nativeLibs/win32-arm64/
99105
100106
- name: Upload Windows x64 library
101107
uses: actions/upload-artifact@v4
102108
with:
103109
name: native-win32-x86-64
104-
path: build/nativeLibs/win32-x86-64/tray.dll
110+
path: build/nativeLibs/win32-x86-64/WinTray.dll
105111
retention-days: 1
106112

107113
- name: Upload Windows ARM64 library
108114
uses: actions/upload-artifact@v4
109115
with:
110116
name: native-win32-arm64
111-
path: build/nativeLibs/win32-arm64/tray.dll
117+
path: build/nativeLibs/win32-arm64/WinTray.dll
112118
retention-days: 1

build.gradle.kts

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -39,11 +39,10 @@ kotlin {
3939
implementation(compose.foundation)
4040
implementation(compose.ui)
4141
implementation(compose.components.resources)
42-
implementation(libs.jna)
43-
implementation(libs.jna.platform)
4442
implementation(libs.kotlinx.coroutines.core)
4543
implementation(libs.kotlinx.coroutines.swing)
4644
implementation(libs.platformtools.core)
45+
implementation(libs.nucleus.core.runtime)
4746
implementation(libs.nucleus.darkmode.detector)
4847
}
4948
}

gradle/libs.versions.toml

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,6 @@ kermit = "2.0.8"
33
kotlin = "2.3.10"
44
kotlinx-coroutines = "1.10.2"
55
compose = "1.10.0"
6-
jna = "5.18.1"
76
platformtools = "0.7.5"
87
detekt = "1.23.7"
98
ktlint = "12.1.2"
@@ -13,8 +12,6 @@ nucleus = "1.9.0"
1312
kermit = { module = "co.touchlab:kermit", version.ref = "kermit" }
1413
kotlinx-coroutines-core = { module = "org.jetbrains.kotlinx:kotlinx-coroutines-core", version.ref = "kotlinx-coroutines" }
1514
kotlinx-coroutines-swing = { module = "org.jetbrains.kotlinx:kotlinx-coroutines-swing", version.ref = "kotlinx-coroutines" }
16-
jna = { module = "net.java.dev.jna:jna-jpms", version.ref = "jna" }
17-
jna-platform = { module = "net.java.dev.jna:jna-platform-jpms", version.ref = "jna" }
1815
platformtools-core = { module = "io.github.kdroidfilter:platformtools.core", version.ref = "platformtools" }
1916
nucleus-core-runtime = { module = "io.github.kdroidfilter:nucleus.core-runtime", version.ref = "nucleus" }
2017
nucleus-darkmode-detector = { module = "io.github.kdroidfilter:nucleus.darkmode-detector", version.ref = "nucleus" }

src/jvmMain/kotlin/com/kdroid/composetray/lib/windows/StdCallCallback.kt

Lines changed: 0 additions & 7 deletions
This file was deleted.
Lines changed: 57 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,57 @@
1+
package com.kdroid.composetray.lib.windows
2+
3+
import com.kdroid.composetray.utils.NativeLibraryLoader
4+
5+
/**
6+
* JNI bridge to the native Windows tray library (WinTray.dll).
7+
* Replaces the previous JNA-based approach.
8+
* Follows the same patterns as MacNativeBridge and LinuxNativeBridge.
9+
*/
10+
internal object WindowsNativeBridge {
11+
12+
init {
13+
NativeLibraryLoader.load("WinTray", WindowsNativeBridge::class.java)
14+
}
15+
16+
// -- Tray lifecycle --
17+
18+
@JvmStatic external fun nativeCreateTray(iconPath: String, tooltip: String): Long
19+
@JvmStatic external fun nativeFreeTray(handle: Long)
20+
@JvmStatic external fun nativeSetTrayIcon(handle: Long, iconPath: String)
21+
@JvmStatic external fun nativeSetTrayTooltip(handle: Long, tooltip: String)
22+
@JvmStatic external fun nativeSetTrayCallback(handle: Long, callback: Runnable?)
23+
@JvmStatic external fun nativeSetTrayMenu(trayHandle: Long, menuHandle: Long)
24+
@JvmStatic external fun nativeClearTrayMenu(trayHandle: Long)
25+
@JvmStatic external fun nativeInitTray(handle: Long): Int
26+
@JvmStatic external fun nativeLoopTray(blocking: Int): Int
27+
@JvmStatic external fun nativeUpdateTray(handle: Long)
28+
@JvmStatic external fun nativeExitTray()
29+
30+
// -- Menu items --
31+
32+
@JvmStatic external fun nativeCreateMenuItems(count: Int): Long
33+
@JvmStatic external fun nativeSetMenuItem(
34+
menuHandle: Long,
35+
index: Int,
36+
text: String,
37+
iconPath: String?,
38+
disabled: Int,
39+
checked: Int,
40+
)
41+
@JvmStatic external fun nativeSetMenuItemCallback(menuHandle: Long, index: Int, callback: Runnable?)
42+
@JvmStatic external fun nativeSetMenuItemSubmenu(menuHandle: Long, index: Int, submenuHandle: Long)
43+
@JvmStatic external fun nativeFreeMenuItems(menuHandle: Long, count: Int)
44+
45+
// -- Position --
46+
47+
/** Writes [x, y] into outXY. Returns non-zero if precise. */
48+
@JvmStatic external fun nativeGetNotificationIconsPosition(outXY: IntArray): Int
49+
@JvmStatic external fun nativeGetNotificationIconsRegion(): String?
50+
51+
// -- Mouse hook (for outside-click detection) --
52+
53+
@JvmStatic external fun nativeInstallMouseHook(callback: Runnable): Long
54+
@JvmStatic external fun nativeRunMouseHookLoop(hookId: Long)
55+
@JvmStatic external fun nativeStopMouseHook(hookId: Long)
56+
@JvmStatic external fun nativeGetLastMouseHookClick(outXY: IntArray)
57+
}

src/jvmMain/kotlin/com/kdroid/composetray/lib/windows/WindowsNativeTray.kt

Lines changed: 0 additions & 34 deletions
This file was deleted.

src/jvmMain/kotlin/com/kdroid/composetray/lib/windows/WindowsNativeTrayLibrary.kt

Lines changed: 0 additions & 29 deletions
This file was deleted.

src/jvmMain/kotlin/com/kdroid/composetray/lib/windows/WindowsNativeTrayMenuItem.kt

Lines changed: 0 additions & 35 deletions
This file was deleted.

0 commit comments

Comments
 (0)