Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
PojavLauncherTeam
GitHub Repository: PojavLauncherTeam/PojavLauncher
Path: blob/v3_openjdk/app_pojavlauncher/src/main/jni/awt_bridge.c
2128 views
1
#include <jni.h>
2
#include <assert.h>
3
#include <string.h>
4
#include <stdio.h>
5
6
static JavaVM* dalvikJavaVMPtr;
7
8
static JavaVM* runtimeJavaVMPtr;
9
static JNIEnv* runtimeJNIEnvPtr_GRAPHICS;
10
static JNIEnv* runtimeJNIEnvPtr_INPUT;
11
jclass class_CTCScreen;
12
jmethodID method_GetRGB;
13
14
jclass class_CTCAndroidInput;
15
jmethodID method_ReceiveInput;
16
17
jclass class_MainActivity;
18
jmethodID method_OpenLink;
19
jmethodID method_OpenPath;
20
jmethodID method_QuerySystemClipboard;
21
jmethodID method_PutClipboardData;
22
23
jclass class_Frame;
24
jclass class_Rectangle;
25
jclass class_CTCClipboard = NULL;
26
jmethodID constructor_Rectangle;
27
jmethodID method_GetFrames;
28
jmethodID method_GetBounds;
29
jmethodID method_SetBounds;
30
jmethodID method_SystemClipboardDataReceived = NULL;
31
32
jfieldID field_x;
33
jfieldID field_y;
34
35
jint JNI_OnLoad(JavaVM* vm, void* reserved) {
36
if (dalvikJavaVMPtr == NULL) {
37
//Save dalvik global JavaVM pointer
38
dalvikJavaVMPtr = vm;
39
JNIEnv *env = NULL;
40
(*vm)->GetEnv(vm, (void**)&env, JNI_VERSION_1_4);
41
class_MainActivity = (*env)->NewGlobalRef(env,(*env)->FindClass(env, "net/kdt/pojavlaunch/MainActivity"));
42
method_OpenLink= (*env)->GetStaticMethodID(env, class_MainActivity, "openLink", "(Ljava/lang/String;)V");
43
method_OpenPath= (*env)->GetStaticMethodID(env, class_MainActivity, "openLink", "(Ljava/lang/String;)V");
44
method_QuerySystemClipboard = (*env)->GetStaticMethodID(env, class_MainActivity, "querySystemClipboard", "()V");
45
method_PutClipboardData = (*env)->GetStaticMethodID(env, class_MainActivity, "putClipboardData", "(Ljava/lang/String;Ljava/lang/String;)V");
46
} else if (dalvikJavaVMPtr != vm) {
47
runtimeJavaVMPtr = vm;
48
}
49
50
return JNI_VERSION_1_4;
51
}
52
53
JNIEXPORT void JNICALL Java_net_kdt_pojavlaunch_AWTInputBridge_nativeSendData(JNIEnv* env, jclass clazz, jint type, jint i1, jint i2, jint i3, jint i4) {
54
if (runtimeJNIEnvPtr_INPUT == NULL) {
55
if (runtimeJavaVMPtr == NULL) {
56
return;
57
} else {
58
(*runtimeJavaVMPtr)->AttachCurrentThread(runtimeJavaVMPtr, &runtimeJNIEnvPtr_INPUT, NULL);
59
}
60
}
61
62
if (method_ReceiveInput == NULL) {
63
class_CTCAndroidInput = (*runtimeJNIEnvPtr_INPUT)->FindClass(runtimeJNIEnvPtr_INPUT, "net/java/openjdk/cacio/ctc/CTCAndroidInput");
64
if ((*runtimeJNIEnvPtr_INPUT)->ExceptionCheck(runtimeJNIEnvPtr_INPUT) == JNI_TRUE) {
65
(*runtimeJNIEnvPtr_INPUT)->ExceptionClear(runtimeJNIEnvPtr_INPUT);
66
class_CTCAndroidInput = (*runtimeJNIEnvPtr_INPUT)->FindClass(runtimeJNIEnvPtr_INPUT, "com/github/caciocavallosilano/cacio/ctc/CTCAndroidInput");
67
}
68
assert(class_CTCAndroidInput != NULL);
69
method_ReceiveInput = (*runtimeJNIEnvPtr_INPUT)->GetStaticMethodID(runtimeJNIEnvPtr_INPUT, class_CTCAndroidInput, "receiveData", "(IIIII)V");
70
assert(method_ReceiveInput != NULL);
71
}
72
(*runtimeJNIEnvPtr_INPUT)->CallStaticVoidMethod(
73
runtimeJNIEnvPtr_INPUT,
74
class_CTCAndroidInput,
75
method_ReceiveInput,
76
type, i1, i2, i3, i4
77
);
78
}
79
80
// TODO: check for memory leaks
81
// int printed = 0;
82
int threadAttached = 0;
83
JNIEXPORT jintArray JNICALL Java_net_kdt_pojavlaunch_utils_JREUtils_renderAWTScreenFrame(JNIEnv* env, jclass clazz /*, jobject canvas, jint width, jint height */) {
84
if (runtimeJNIEnvPtr_GRAPHICS == NULL) {
85
if (runtimeJavaVMPtr == NULL) {
86
return NULL;
87
} else {
88
(*runtimeJavaVMPtr)->AttachCurrentThread(runtimeJavaVMPtr, &runtimeJNIEnvPtr_GRAPHICS, NULL);
89
}
90
}
91
92
int *rgbArray;
93
jintArray jreRgbArray, androidRgbArray;
94
95
if (method_GetRGB == NULL) {
96
class_CTCScreen = (*runtimeJNIEnvPtr_GRAPHICS)->FindClass(runtimeJNIEnvPtr_GRAPHICS, "net/java/openjdk/cacio/ctc/CTCScreen");
97
if ((*runtimeJNIEnvPtr_GRAPHICS)->ExceptionCheck(runtimeJNIEnvPtr_GRAPHICS) == JNI_TRUE) {
98
(*runtimeJNIEnvPtr_GRAPHICS)->ExceptionClear(runtimeJNIEnvPtr_GRAPHICS);
99
class_CTCScreen = (*runtimeJNIEnvPtr_GRAPHICS)->FindClass(runtimeJNIEnvPtr_GRAPHICS, "com/github/caciocavallosilano/cacio/ctc/CTCScreen");
100
}
101
assert(class_CTCScreen != NULL);
102
method_GetRGB = (*runtimeJNIEnvPtr_GRAPHICS)->GetStaticMethodID(runtimeJNIEnvPtr_GRAPHICS, class_CTCScreen, "getCurrentScreenRGB", "()[I");
103
assert(method_GetRGB != NULL);
104
}
105
jreRgbArray = (jintArray) (*runtimeJNIEnvPtr_GRAPHICS)->CallStaticObjectMethod(
106
runtimeJNIEnvPtr_GRAPHICS,
107
class_CTCScreen,
108
method_GetRGB
109
);
110
if (jreRgbArray == NULL) {
111
return NULL;
112
}
113
114
// Copy JRE RGB array memory to Android.
115
int arrayLength = (*runtimeJNIEnvPtr_GRAPHICS)->GetArrayLength(runtimeJNIEnvPtr_GRAPHICS, jreRgbArray);
116
rgbArray = (*runtimeJNIEnvPtr_GRAPHICS)->GetIntArrayElements(runtimeJNIEnvPtr_GRAPHICS, jreRgbArray, 0);
117
androidRgbArray = (*env)->NewIntArray(env, arrayLength);
118
(*env)->SetIntArrayRegion(env, androidRgbArray, 0, arrayLength, rgbArray);
119
120
(*runtimeJNIEnvPtr_GRAPHICS)->ReleaseIntArrayElements(runtimeJNIEnvPtr_GRAPHICS, jreRgbArray, rgbArray, NULL);
121
// (*env)->DeleteLocalRef(env, androidRgbArray);
122
// free(rgbArray);
123
124
return androidRgbArray;
125
}
126
127
JNIEXPORT void JNICALL Java_net_java_openjdk_cacio_ctc_CTCClipboard_nQuerySystemClipboard(JNIEnv *env, jclass clazz) {
128
JNIEnv *dalvikEnv;char detachable = 0;
129
if((*dalvikJavaVMPtr)->GetEnv(dalvikJavaVMPtr, (void **) &dalvikEnv, JNI_VERSION_1_6) == JNI_EDETACHED) {
130
(*dalvikJavaVMPtr)->AttachCurrentThread(dalvikJavaVMPtr, &dalvikEnv, NULL);
131
detachable = 1;
132
}
133
if(method_SystemClipboardDataReceived == NULL) {
134
class_CTCClipboard = (*env)->NewGlobalRef(env, clazz);
135
method_SystemClipboardDataReceived = (*env)->GetStaticMethodID(env, clazz, "systemClipboardDataReceived", "(Ljava/lang/String;Ljava/lang/String;)V");
136
}
137
(*dalvikEnv)->CallStaticVoidMethod(dalvikEnv, class_MainActivity, method_QuerySystemClipboard);
138
if(detachable) (*dalvikJavaVMPtr)->DetachCurrentThread(dalvikJavaVMPtr);
139
}
140
141
JNIEXPORT void JNICALL Java_net_java_openjdk_cacio_ctc_CTCClipboard_nPutClipboardData(JNIEnv* env, jclass clazz, jstring clipboardData, jstring clipboardDataMime) {
142
JNIEnv *dalvikEnv;char detachable = 0;
143
if((*dalvikJavaVMPtr)->GetEnv(dalvikJavaVMPtr, (void **) &dalvikEnv, JNI_VERSION_1_6) == JNI_EDETACHED) {
144
(*dalvikJavaVMPtr)->AttachCurrentThread(dalvikJavaVMPtr, &dalvikEnv, NULL);
145
detachable = 1;
146
}
147
148
const char* dataChars = (*env)->GetStringUTFChars(env, clipboardData, NULL);
149
const char* mimeChars = (*env)->GetStringUTFChars(env, clipboardDataMime, NULL);
150
(*dalvikEnv)->CallStaticVoidMethod(dalvikEnv, class_MainActivity, method_PutClipboardData,
151
(*dalvikEnv)->NewStringUTF(dalvikEnv, dataChars),
152
(*dalvikEnv)->NewStringUTF(dalvikEnv, mimeChars));
153
(*env)->ReleaseStringUTFChars(env, clipboardData, dataChars);
154
(*env)->ReleaseStringUTFChars(env, clipboardDataMime, mimeChars);
155
if(detachable) (*dalvikJavaVMPtr)->DetachCurrentThread(dalvikJavaVMPtr);
156
}
157
158
JNIEXPORT void JNICALL Java_com_github_caciocavallosilano_cacio_ctc_CTCClipboard_nQuerySystemClipboard(JNIEnv *env, jclass clazz) {
159
Java_net_java_openjdk_cacio_ctc_CTCClipboard_nQuerySystemClipboard(env, clazz);
160
}
161
162
JNIEXPORT void JNICALL Java_com_github_caciocavallosilano_cacio_ctc_CTCClipboard_nPutClipboardData(JNIEnv* env, jclass clazz, jstring clipboardData, jstring clipboardDataMime) {
163
Java_net_java_openjdk_cacio_ctc_CTCClipboard_nPutClipboardData(env, clazz, clipboardData, clipboardDataMime);
164
}
165
166
JNIEXPORT void JNICALL Java_net_java_openjdk_cacio_ctc_CTCDesktopPeer_openFile(JNIEnv *env, jclass clazz, jstring filePath) {
167
JNIEnv *dalvikEnv;char detachable = 0;
168
if((*dalvikJavaVMPtr)->GetEnv(dalvikJavaVMPtr, (void **) &dalvikEnv, JNI_VERSION_1_6) == JNI_EDETACHED) {
169
(*dalvikJavaVMPtr)->AttachCurrentThread(dalvikJavaVMPtr, &dalvikEnv, NULL);
170
detachable = 1;
171
}
172
const char* stringChars = (*env)->GetStringUTFChars(env, filePath, NULL);
173
(*dalvikEnv)->CallStaticVoidMethod(dalvikEnv, class_MainActivity, method_OpenPath, (*dalvikEnv)->NewStringUTF(dalvikEnv, stringChars));
174
(*env)->ReleaseStringUTFChars(env, filePath, stringChars);
175
if(detachable) (*dalvikJavaVMPtr)->DetachCurrentThread(dalvikJavaVMPtr);
176
}
177
178
JNIEXPORT void JNICALL Java_net_java_openjdk_cacio_ctc_CTCDesktopPeer_openUri(JNIEnv *env, jclass clazz, jstring uri) {
179
JNIEnv *dalvikEnv;char detachable = 0;
180
if((*dalvikJavaVMPtr)->GetEnv(dalvikJavaVMPtr, (void **) &dalvikEnv, JNI_VERSION_1_6) == JNI_EDETACHED) {
181
(*dalvikJavaVMPtr)->AttachCurrentThread(dalvikJavaVMPtr, &dalvikEnv, NULL);
182
detachable = 1;
183
}
184
const char* stringChars = (*env)->GetStringUTFChars(env, uri, NULL);
185
(*dalvikEnv)->CallStaticVoidMethod(dalvikEnv, class_MainActivity, method_OpenLink, (*dalvikEnv)->NewStringUTF(dalvikEnv, stringChars));
186
(*env)->ReleaseStringUTFChars(env, uri, stringChars);
187
if(detachable) (*dalvikJavaVMPtr)->DetachCurrentThread(dalvikJavaVMPtr);
188
}
189
190
JNIEXPORT void JNICALL Java_net_kdt_pojavlaunch_AWTInputBridge_nativeClipboardReceived(JNIEnv *env, jclass clazz, jstring clipboardData, jstring clipboardDataMime) {
191
if(method_SystemClipboardDataReceived == NULL || class_CTCClipboard == NULL) return;
192
if (runtimeJNIEnvPtr_INPUT == NULL) {
193
if (runtimeJavaVMPtr == NULL) {
194
return;
195
} else {
196
(*runtimeJavaVMPtr)->AttachCurrentThread(runtimeJavaVMPtr, &runtimeJNIEnvPtr_INPUT, NULL);
197
}
198
}
199
const char* dataChars = clipboardData != NULL ? (*env)->GetStringUTFChars(env, clipboardData, NULL) : NULL;
200
const char* mimeChars = clipboardDataMime != NULL ? (*env)->GetStringUTFChars(env, clipboardDataMime, NULL) : NULL;
201
(*runtimeJNIEnvPtr_INPUT)->CallStaticVoidMethod(runtimeJNIEnvPtr_INPUT, class_CTCClipboard, method_SystemClipboardDataReceived,
202
clipboardData != NULL ? (*runtimeJNIEnvPtr_INPUT)->NewStringUTF(runtimeJNIEnvPtr_INPUT, dataChars) : NULL,
203
clipboardDataMime != NULL ? (*runtimeJNIEnvPtr_INPUT)->NewStringUTF(runtimeJNIEnvPtr_INPUT, mimeChars) : NULL);
204
if(dataChars != NULL) (*env)->ReleaseStringUTFChars(env, clipboardData, dataChars);
205
if(mimeChars != NULL) (*env)->ReleaseStringUTFChars(env, clipboardDataMime, mimeChars);
206
}
207
208
JNIEXPORT void JNICALL
209
Java_net_kdt_pojavlaunch_AWTInputBridge_nativeMoveWindow(JNIEnv *env, jclass clazz, jint xoff, jint yoff) {
210
if (runtimeJNIEnvPtr_INPUT == NULL) {
211
if (runtimeJavaVMPtr == NULL) {
212
return;
213
} else {
214
(*runtimeJavaVMPtr)->AttachCurrentThread(runtimeJavaVMPtr, &runtimeJNIEnvPtr_INPUT, NULL);
215
}
216
}
217
if(field_y == NULL) {
218
class_Frame = (*runtimeJNIEnvPtr_INPUT)->FindClass(runtimeJNIEnvPtr_INPUT, "java/awt/Frame");
219
method_GetFrames = (*runtimeJNIEnvPtr_INPUT)->GetStaticMethodID(runtimeJNIEnvPtr_INPUT, class_Frame, "getFrames", "()[Ljava/awt/Frame;");
220
method_GetBounds = (*runtimeJNIEnvPtr_INPUT)->GetMethodID(runtimeJNIEnvPtr_INPUT, class_Frame, "getBounds", "(Ljava/awt/Rectangle;)Ljava/awt/Rectangle;");
221
method_SetBounds = (*runtimeJNIEnvPtr_INPUT)->GetMethodID(runtimeJNIEnvPtr_INPUT, class_Frame, "setBounds", "(Ljava/awt/Rectangle;)V");
222
class_Rectangle = (*runtimeJNIEnvPtr_INPUT)->FindClass(runtimeJNIEnvPtr_INPUT, "java/awt/Rectangle");
223
constructor_Rectangle = (*runtimeJNIEnvPtr_INPUT)->GetMethodID(runtimeJNIEnvPtr_INPUT, class_Rectangle, "<init>", "()V");
224
field_x = (*runtimeJNIEnvPtr_INPUT)->GetFieldID(runtimeJNIEnvPtr_INPUT, class_Rectangle, "x", "I");
225
field_y = (*runtimeJNIEnvPtr_INPUT)->GetFieldID(runtimeJNIEnvPtr_INPUT, class_Rectangle, "y", "I");
226
}
227
jobject rectangle = (*runtimeJNIEnvPtr_INPUT)->NewObject(runtimeJNIEnvPtr_INPUT, class_Rectangle, constructor_Rectangle);
228
jobjectArray frames = (*runtimeJNIEnvPtr_INPUT)->CallStaticObjectMethod(runtimeJNIEnvPtr_INPUT, class_Frame, method_GetFrames);
229
for(jsize i = 0; i < (*runtimeJNIEnvPtr_INPUT)->GetArrayLength(runtimeJNIEnvPtr_INPUT, frames); i++) {
230
jobject frame = (*runtimeJNIEnvPtr_INPUT)->GetObjectArrayElement(runtimeJNIEnvPtr_INPUT, frames, i);
231
(*runtimeJNIEnvPtr_INPUT)->CallObjectMethod(runtimeJNIEnvPtr_INPUT, frame, method_GetBounds, rectangle);
232
(*runtimeJNIEnvPtr_INPUT)->SetIntField(runtimeJNIEnvPtr_INPUT, rectangle, field_x, (*runtimeJNIEnvPtr_INPUT)->GetIntField(runtimeJNIEnvPtr_INPUT, rectangle, field_x) + xoff);
233
(*runtimeJNIEnvPtr_INPUT)->SetIntField(runtimeJNIEnvPtr_INPUT, rectangle, field_y, (*runtimeJNIEnvPtr_INPUT)->GetIntField(runtimeJNIEnvPtr_INPUT, rectangle, field_y) + yoff);
234
(*runtimeJNIEnvPtr_INPUT)->CallVoidMethod(runtimeJNIEnvPtr_INPUT, frame, method_SetBounds, rectangle);
235
(*runtimeJNIEnvPtr_INPUT)->DeleteLocalRef(runtimeJNIEnvPtr_INPUT, frame);
236
}
237
(*runtimeJNIEnvPtr_INPUT)->DeleteLocalRef(runtimeJNIEnvPtr_INPUT, rectangle);
238
(*runtimeJNIEnvPtr_INPUT)->DeleteLocalRef(runtimeJNIEnvPtr_INPUT, frames);
239
}
240
241