rev |
line source |
nuclear@0
|
1 /*
|
nuclear@0
|
2 * Copyright (C) 2010 The Android Open Source Project
|
nuclear@0
|
3 *
|
nuclear@0
|
4 * Licensed under the Apache License, Version 2.0 (the "License");
|
nuclear@0
|
5 * you may not use this file except in compliance with the License.
|
nuclear@0
|
6 * You may obtain a copy of the License at
|
nuclear@0
|
7 *
|
nuclear@0
|
8 * http://www.apache.org/licenses/LICENSE-2.0
|
nuclear@0
|
9 *
|
nuclear@0
|
10 * Unless required by applicable law or agreed to in writing, software
|
nuclear@0
|
11 * distributed under the License is distributed on an "AS IS" BASIS,
|
nuclear@0
|
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
nuclear@0
|
13 * See the License for the specific language governing permissions and
|
nuclear@0
|
14 * limitations under the License.
|
nuclear@0
|
15 *
|
nuclear@0
|
16 */
|
nuclear@0
|
17
|
nuclear@0
|
18 #include <jni.h>
|
nuclear@0
|
19
|
nuclear@0
|
20 #include <errno.h>
|
nuclear@0
|
21 #include <string.h>
|
nuclear@0
|
22 #include <unistd.h>
|
nuclear@0
|
23 #include <sys/resource.h>
|
nuclear@0
|
24
|
nuclear@1
|
25 #include "native_glue.h"
|
nuclear@0
|
26 #include <android/log.h>
|
nuclear@0
|
27
|
nuclear@1
|
28 #define ACTIVITY_NAME "com/mutantstargoat/photoshoot3d/MainActivity"
|
nuclear@1
|
29
|
nuclear@1
|
30 #define LOGI(...) ((void)__android_log_print(ANDROID_LOG_INFO, APP_NAME, __VA_ARGS__))
|
nuclear@1
|
31 #define LOGE(...) ((void)__android_log_print(ANDROID_LOG_ERROR, APP_NAME, __VA_ARGS__))
|
nuclear@0
|
32
|
nuclear@0
|
33 /* For debug builds, always enable the debug traces in this library */
|
nuclear@0
|
34 #ifndef NDEBUG
|
nuclear@1
|
35 # define LOGV(...) ((void)__android_log_print(ANDROID_LOG_VERBOSE, APP_NAME, __VA_ARGS__))
|
nuclear@0
|
36 #else
|
nuclear@0
|
37 # define LOGV(...) ((void)0)
|
nuclear@0
|
38 #endif
|
nuclear@0
|
39
|
nuclear@2
|
40 /*
|
nuclear@2
|
41 jint JNI_OnLoad(JavaVM *jvm, void *unused)
|
nuclear@2
|
42 {
|
nuclear@2
|
43 JNIEnv *jni;
|
nuclear@2
|
44 jclass act_cls_local;
|
nuclear@2
|
45
|
nuclear@2
|
46 LOGI("OnLoad called ! <------------------\n");
|
nuclear@2
|
47
|
nuclear@2
|
48 if((*jvm)->GetEnv(jvm, (void**)&jni, JNI_VERSION_1_6) != JNI_OK) {
|
nuclear@2
|
49 LOGE("OnLoad: failed to get JNIEnv from VM\n");
|
nuclear@2
|
50 return -1;
|
nuclear@2
|
51 }
|
nuclear@2
|
52
|
nuclear@2
|
53 jclass foo = (*jni)->FindClass(jni, "java/lang/String");
|
nuclear@2
|
54 if(!foo) {
|
nuclear@2
|
55 LOGE("String class not found!!!!!!\n");
|
nuclear@2
|
56 } else {
|
nuclear@2
|
57 LOGE("Found String class!!!!!!\n");
|
nuclear@2
|
58 }
|
nuclear@2
|
59
|
nuclear@2
|
60 if(!(act_cls_local = (*jni)->FindClass(jni, ACTIVITY_NAME))) {
|
nuclear@2
|
61 LOGE("could not find activity: " ACTIVITY_NAME);
|
nuclear@2
|
62 return 0;
|
nuclear@2
|
63 }
|
nuclear@2
|
64 activity_class = (*jni)->NewGlobalRef(jni, act_cls_local);
|
nuclear@2
|
65
|
nuclear@2
|
66 return JNI_VERSION_1_6;
|
nuclear@2
|
67 }
|
nuclear@2
|
68 */
|
nuclear@2
|
69
|
nuclear@0
|
70 static void free_saved_state(struct android_app* android_app) {
|
nuclear@0
|
71 pthread_mutex_lock(&android_app->mutex);
|
nuclear@0
|
72 if (android_app->savedState != NULL) {
|
nuclear@0
|
73 free(android_app->savedState);
|
nuclear@0
|
74 android_app->savedState = NULL;
|
nuclear@0
|
75 android_app->savedStateSize = 0;
|
nuclear@0
|
76 }
|
nuclear@0
|
77 pthread_mutex_unlock(&android_app->mutex);
|
nuclear@0
|
78 }
|
nuclear@0
|
79
|
nuclear@0
|
80 int8_t android_app_read_cmd(struct android_app* android_app) {
|
nuclear@0
|
81 int8_t cmd;
|
nuclear@0
|
82 if (read(android_app->msgread, &cmd, sizeof(cmd)) == sizeof(cmd)) {
|
nuclear@0
|
83 switch (cmd) {
|
nuclear@0
|
84 case APP_CMD_SAVE_STATE:
|
nuclear@0
|
85 free_saved_state(android_app);
|
nuclear@0
|
86 break;
|
nuclear@0
|
87 }
|
nuclear@0
|
88 return cmd;
|
nuclear@0
|
89 } else {
|
nuclear@0
|
90 LOGE("No data on command pipe!");
|
nuclear@0
|
91 }
|
nuclear@0
|
92 return -1;
|
nuclear@0
|
93 }
|
nuclear@0
|
94
|
nuclear@0
|
95 static void print_cur_config(struct android_app* android_app) {
|
nuclear@0
|
96 char lang[2], country[2];
|
nuclear@0
|
97 AConfiguration_getLanguage(android_app->config, lang);
|
nuclear@0
|
98 AConfiguration_getCountry(android_app->config, country);
|
nuclear@0
|
99
|
nuclear@0
|
100 LOGV("Config: mcc=%d mnc=%d lang=%c%c cnt=%c%c orien=%d touch=%d dens=%d "
|
nuclear@0
|
101 "keys=%d nav=%d keysHid=%d navHid=%d sdk=%d size=%d long=%d "
|
nuclear@0
|
102 "modetype=%d modenight=%d",
|
nuclear@0
|
103 AConfiguration_getMcc(android_app->config),
|
nuclear@0
|
104 AConfiguration_getMnc(android_app->config),
|
nuclear@0
|
105 lang[0], lang[1], country[0], country[1],
|
nuclear@0
|
106 AConfiguration_getOrientation(android_app->config),
|
nuclear@0
|
107 AConfiguration_getTouchscreen(android_app->config),
|
nuclear@0
|
108 AConfiguration_getDensity(android_app->config),
|
nuclear@0
|
109 AConfiguration_getKeyboard(android_app->config),
|
nuclear@0
|
110 AConfiguration_getNavigation(android_app->config),
|
nuclear@0
|
111 AConfiguration_getKeysHidden(android_app->config),
|
nuclear@0
|
112 AConfiguration_getNavHidden(android_app->config),
|
nuclear@0
|
113 AConfiguration_getSdkVersion(android_app->config),
|
nuclear@0
|
114 AConfiguration_getScreenSize(android_app->config),
|
nuclear@0
|
115 AConfiguration_getScreenLong(android_app->config),
|
nuclear@0
|
116 AConfiguration_getUiModeType(android_app->config),
|
nuclear@0
|
117 AConfiguration_getUiModeNight(android_app->config));
|
nuclear@0
|
118 }
|
nuclear@0
|
119
|
nuclear@0
|
120 void android_app_pre_exec_cmd(struct android_app* android_app, int8_t cmd) {
|
nuclear@0
|
121 switch (cmd) {
|
nuclear@0
|
122 case APP_CMD_INPUT_CHANGED:
|
nuclear@0
|
123 LOGV("APP_CMD_INPUT_CHANGED\n");
|
nuclear@0
|
124 pthread_mutex_lock(&android_app->mutex);
|
nuclear@0
|
125 if (android_app->inputQueue != NULL) {
|
nuclear@0
|
126 AInputQueue_detachLooper(android_app->inputQueue);
|
nuclear@0
|
127 }
|
nuclear@0
|
128 android_app->inputQueue = android_app->pendingInputQueue;
|
nuclear@0
|
129 if (android_app->inputQueue != NULL) {
|
nuclear@0
|
130 LOGV("Attaching input queue to looper");
|
nuclear@0
|
131 AInputQueue_attachLooper(android_app->inputQueue,
|
nuclear@0
|
132 android_app->looper, LOOPER_ID_INPUT, NULL,
|
nuclear@0
|
133 &android_app->inputPollSource);
|
nuclear@0
|
134 }
|
nuclear@0
|
135 pthread_cond_broadcast(&android_app->cond);
|
nuclear@0
|
136 pthread_mutex_unlock(&android_app->mutex);
|
nuclear@0
|
137 break;
|
nuclear@0
|
138
|
nuclear@0
|
139 case APP_CMD_INIT_WINDOW:
|
nuclear@0
|
140 LOGV("APP_CMD_INIT_WINDOW\n");
|
nuclear@0
|
141 pthread_mutex_lock(&android_app->mutex);
|
nuclear@0
|
142 android_app->window = android_app->pendingWindow;
|
nuclear@0
|
143 pthread_cond_broadcast(&android_app->cond);
|
nuclear@0
|
144 pthread_mutex_unlock(&android_app->mutex);
|
nuclear@0
|
145 break;
|
nuclear@0
|
146
|
nuclear@0
|
147 case APP_CMD_TERM_WINDOW:
|
nuclear@0
|
148 LOGV("APP_CMD_TERM_WINDOW\n");
|
nuclear@0
|
149 pthread_cond_broadcast(&android_app->cond);
|
nuclear@0
|
150 break;
|
nuclear@0
|
151
|
nuclear@0
|
152 case APP_CMD_RESUME:
|
nuclear@0
|
153 case APP_CMD_START:
|
nuclear@0
|
154 case APP_CMD_PAUSE:
|
nuclear@0
|
155 case APP_CMD_STOP:
|
nuclear@0
|
156 LOGV("activityState=%d\n", cmd);
|
nuclear@0
|
157 pthread_mutex_lock(&android_app->mutex);
|
nuclear@0
|
158 android_app->activityState = cmd;
|
nuclear@0
|
159 pthread_cond_broadcast(&android_app->cond);
|
nuclear@0
|
160 pthread_mutex_unlock(&android_app->mutex);
|
nuclear@0
|
161 break;
|
nuclear@0
|
162
|
nuclear@0
|
163 case APP_CMD_CONFIG_CHANGED:
|
nuclear@0
|
164 LOGV("APP_CMD_CONFIG_CHANGED\n");
|
nuclear@0
|
165 AConfiguration_fromAssetManager(android_app->config,
|
nuclear@0
|
166 android_app->activity->assetManager);
|
nuclear@0
|
167 print_cur_config(android_app);
|
nuclear@0
|
168 break;
|
nuclear@0
|
169
|
nuclear@0
|
170 case APP_CMD_DESTROY:
|
nuclear@0
|
171 LOGV("APP_CMD_DESTROY\n");
|
nuclear@0
|
172 android_app->destroyRequested = 1;
|
nuclear@0
|
173 break;
|
nuclear@0
|
174 }
|
nuclear@0
|
175 }
|
nuclear@0
|
176
|
nuclear@0
|
177 void android_app_post_exec_cmd(struct android_app* android_app, int8_t cmd) {
|
nuclear@0
|
178 switch (cmd) {
|
nuclear@0
|
179 case APP_CMD_TERM_WINDOW:
|
nuclear@0
|
180 LOGV("APP_CMD_TERM_WINDOW\n");
|
nuclear@0
|
181 pthread_mutex_lock(&android_app->mutex);
|
nuclear@0
|
182 android_app->window = NULL;
|
nuclear@0
|
183 pthread_cond_broadcast(&android_app->cond);
|
nuclear@0
|
184 pthread_mutex_unlock(&android_app->mutex);
|
nuclear@0
|
185 break;
|
nuclear@0
|
186
|
nuclear@0
|
187 case APP_CMD_SAVE_STATE:
|
nuclear@0
|
188 LOGV("APP_CMD_SAVE_STATE\n");
|
nuclear@0
|
189 pthread_mutex_lock(&android_app->mutex);
|
nuclear@0
|
190 android_app->stateSaved = 1;
|
nuclear@0
|
191 pthread_cond_broadcast(&android_app->cond);
|
nuclear@0
|
192 pthread_mutex_unlock(&android_app->mutex);
|
nuclear@0
|
193 break;
|
nuclear@0
|
194
|
nuclear@0
|
195 case APP_CMD_RESUME:
|
nuclear@0
|
196 free_saved_state(android_app);
|
nuclear@0
|
197 break;
|
nuclear@0
|
198 }
|
nuclear@0
|
199 }
|
nuclear@0
|
200
|
nuclear@0
|
201 void app_dummy() {
|
nuclear@0
|
202
|
nuclear@0
|
203 }
|
nuclear@0
|
204
|
nuclear@0
|
205 static void android_app_destroy(struct android_app* android_app) {
|
nuclear@0
|
206 LOGV("android_app_destroy!");
|
nuclear@0
|
207 free_saved_state(android_app);
|
nuclear@0
|
208 pthread_mutex_lock(&android_app->mutex);
|
nuclear@0
|
209 if (android_app->inputQueue != NULL) {
|
nuclear@0
|
210 AInputQueue_detachLooper(android_app->inputQueue);
|
nuclear@0
|
211 }
|
nuclear@0
|
212 AConfiguration_delete(android_app->config);
|
nuclear@2
|
213
|
nuclear@0
|
214 android_app->destroyed = 1;
|
nuclear@0
|
215 pthread_cond_broadcast(&android_app->cond);
|
nuclear@0
|
216 pthread_mutex_unlock(&android_app->mutex);
|
nuclear@0
|
217 // Can't touch android_app object after this.
|
nuclear@0
|
218 }
|
nuclear@0
|
219
|
nuclear@0
|
220 static void process_input(struct android_app* app, struct android_poll_source* source) {
|
nuclear@0
|
221 AInputEvent* event = NULL;
|
nuclear@0
|
222 while (AInputQueue_getEvent(app->inputQueue, &event) >= 0) {
|
nuclear@0
|
223 LOGV("New input event: type=%d\n", AInputEvent_getType(event));
|
nuclear@0
|
224 if (AInputQueue_preDispatchEvent(app->inputQueue, event)) {
|
nuclear@0
|
225 continue;
|
nuclear@0
|
226 }
|
nuclear@0
|
227 int32_t handled = 0;
|
nuclear@0
|
228 if (app->onInputEvent != NULL) handled = app->onInputEvent(app, event);
|
nuclear@0
|
229 AInputQueue_finishEvent(app->inputQueue, event, handled);
|
nuclear@0
|
230 }
|
nuclear@0
|
231 }
|
nuclear@0
|
232
|
nuclear@0
|
233 static void process_cmd(struct android_app* app, struct android_poll_source* source) {
|
nuclear@0
|
234 int8_t cmd = android_app_read_cmd(app);
|
nuclear@0
|
235 android_app_pre_exec_cmd(app, cmd);
|
nuclear@0
|
236 if (app->onAppCmd != NULL) app->onAppCmd(app, cmd);
|
nuclear@0
|
237 android_app_post_exec_cmd(app, cmd);
|
nuclear@0
|
238 }
|
nuclear@0
|
239
|
nuclear@0
|
240 static void* android_app_entry(void* param) {
|
nuclear@0
|
241 struct android_app* android_app = (struct android_app*)param;
|
nuclear@0
|
242
|
nuclear@0
|
243 android_app->config = AConfiguration_new();
|
nuclear@0
|
244 AConfiguration_fromAssetManager(android_app->config, android_app->activity->assetManager);
|
nuclear@0
|
245
|
nuclear@0
|
246 print_cur_config(android_app);
|
nuclear@0
|
247
|
nuclear@0
|
248 android_app->cmdPollSource.id = LOOPER_ID_MAIN;
|
nuclear@0
|
249 android_app->cmdPollSource.app = android_app;
|
nuclear@0
|
250 android_app->cmdPollSource.process = process_cmd;
|
nuclear@0
|
251 android_app->inputPollSource.id = LOOPER_ID_INPUT;
|
nuclear@0
|
252 android_app->inputPollSource.app = android_app;
|
nuclear@0
|
253 android_app->inputPollSource.process = process_input;
|
nuclear@0
|
254
|
nuclear@0
|
255 ALooper* looper = ALooper_prepare(ALOOPER_PREPARE_ALLOW_NON_CALLBACKS);
|
nuclear@0
|
256 ALooper_addFd(looper, android_app->msgread, LOOPER_ID_MAIN, ALOOPER_EVENT_INPUT, NULL,
|
nuclear@0
|
257 &android_app->cmdPollSource);
|
nuclear@0
|
258 android_app->looper = looper;
|
nuclear@0
|
259
|
nuclear@0
|
260 pthread_mutex_lock(&android_app->mutex);
|
nuclear@0
|
261 android_app->running = 1;
|
nuclear@0
|
262 pthread_cond_broadcast(&android_app->cond);
|
nuclear@0
|
263 pthread_mutex_unlock(&android_app->mutex);
|
nuclear@0
|
264
|
nuclear@0
|
265 android_main(android_app);
|
nuclear@0
|
266
|
nuclear@0
|
267 android_app_destroy(android_app);
|
nuclear@0
|
268 return NULL;
|
nuclear@0
|
269 }
|
nuclear@0
|
270
|
nuclear@0
|
271 // --------------------------------------------------------------------
|
nuclear@0
|
272 // Native activity interaction (called from main thread)
|
nuclear@0
|
273 // --------------------------------------------------------------------
|
nuclear@0
|
274
|
nuclear@0
|
275 static struct android_app* android_app_create(ANativeActivity* activity,
|
nuclear@0
|
276 void* savedState, size_t savedStateSize) {
|
nuclear@1
|
277 struct android_app* android_app = malloc(sizeof(struct android_app));
|
nuclear@0
|
278 memset(android_app, 0, sizeof(struct android_app));
|
nuclear@0
|
279 android_app->activity = activity;
|
nuclear@0
|
280
|
nuclear@0
|
281 pthread_mutex_init(&android_app->mutex, NULL);
|
nuclear@0
|
282 pthread_cond_init(&android_app->cond, NULL);
|
nuclear@0
|
283
|
nuclear@0
|
284 if (savedState != NULL) {
|
nuclear@0
|
285 android_app->savedState = malloc(savedStateSize);
|
nuclear@0
|
286 android_app->savedStateSize = savedStateSize;
|
nuclear@0
|
287 memcpy(android_app->savedState, savedState, savedStateSize);
|
nuclear@0
|
288 }
|
nuclear@0
|
289
|
nuclear@0
|
290 int msgpipe[2];
|
nuclear@0
|
291 if (pipe(msgpipe)) {
|
nuclear@0
|
292 LOGE("could not create pipe: %s", strerror(errno));
|
nuclear@0
|
293 return NULL;
|
nuclear@0
|
294 }
|
nuclear@0
|
295 android_app->msgread = msgpipe[0];
|
nuclear@0
|
296 android_app->msgwrite = msgpipe[1];
|
nuclear@0
|
297
|
nuclear@1
|
298 pthread_attr_t attr;
|
nuclear@0
|
299 pthread_attr_init(&attr);
|
nuclear@0
|
300 pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED);
|
nuclear@0
|
301 pthread_create(&android_app->thread, &attr, android_app_entry, android_app);
|
nuclear@0
|
302
|
nuclear@0
|
303 // Wait for thread to start.
|
nuclear@0
|
304 pthread_mutex_lock(&android_app->mutex);
|
nuclear@0
|
305 while (!android_app->running) {
|
nuclear@0
|
306 pthread_cond_wait(&android_app->cond, &android_app->mutex);
|
nuclear@0
|
307 }
|
nuclear@0
|
308 pthread_mutex_unlock(&android_app->mutex);
|
nuclear@0
|
309
|
nuclear@0
|
310 return android_app;
|
nuclear@0
|
311 }
|
nuclear@0
|
312
|
nuclear@0
|
313 static void android_app_write_cmd(struct android_app* android_app, int8_t cmd) {
|
nuclear@0
|
314 if (write(android_app->msgwrite, &cmd, sizeof(cmd)) != sizeof(cmd)) {
|
nuclear@0
|
315 LOGE("Failure writing android_app cmd: %s\n", strerror(errno));
|
nuclear@0
|
316 }
|
nuclear@0
|
317 }
|
nuclear@0
|
318
|
nuclear@0
|
319 static void android_app_set_input(struct android_app* android_app, AInputQueue* inputQueue) {
|
nuclear@0
|
320 pthread_mutex_lock(&android_app->mutex);
|
nuclear@0
|
321 android_app->pendingInputQueue = inputQueue;
|
nuclear@0
|
322 android_app_write_cmd(android_app, APP_CMD_INPUT_CHANGED);
|
nuclear@0
|
323 while (android_app->inputQueue != android_app->pendingInputQueue) {
|
nuclear@0
|
324 pthread_cond_wait(&android_app->cond, &android_app->mutex);
|
nuclear@0
|
325 }
|
nuclear@0
|
326 pthread_mutex_unlock(&android_app->mutex);
|
nuclear@0
|
327 }
|
nuclear@0
|
328
|
nuclear@0
|
329 static void android_app_set_window(struct android_app* android_app, ANativeWindow* window) {
|
nuclear@0
|
330 pthread_mutex_lock(&android_app->mutex);
|
nuclear@0
|
331 if (android_app->pendingWindow != NULL) {
|
nuclear@0
|
332 android_app_write_cmd(android_app, APP_CMD_TERM_WINDOW);
|
nuclear@0
|
333 }
|
nuclear@0
|
334 android_app->pendingWindow = window;
|
nuclear@0
|
335 if (window != NULL) {
|
nuclear@0
|
336 android_app_write_cmd(android_app, APP_CMD_INIT_WINDOW);
|
nuclear@0
|
337 }
|
nuclear@0
|
338 while (android_app->window != android_app->pendingWindow) {
|
nuclear@0
|
339 pthread_cond_wait(&android_app->cond, &android_app->mutex);
|
nuclear@0
|
340 }
|
nuclear@0
|
341 pthread_mutex_unlock(&android_app->mutex);
|
nuclear@0
|
342 }
|
nuclear@0
|
343
|
nuclear@0
|
344 static void android_app_set_activity_state(struct android_app* android_app, int8_t cmd) {
|
nuclear@0
|
345 pthread_mutex_lock(&android_app->mutex);
|
nuclear@0
|
346 android_app_write_cmd(android_app, cmd);
|
nuclear@0
|
347 while (android_app->activityState != cmd) {
|
nuclear@0
|
348 pthread_cond_wait(&android_app->cond, &android_app->mutex);
|
nuclear@0
|
349 }
|
nuclear@0
|
350 pthread_mutex_unlock(&android_app->mutex);
|
nuclear@0
|
351 }
|
nuclear@0
|
352
|
nuclear@0
|
353 static void android_app_free(struct android_app* android_app) {
|
nuclear@0
|
354 pthread_mutex_lock(&android_app->mutex);
|
nuclear@0
|
355 android_app_write_cmd(android_app, APP_CMD_DESTROY);
|
nuclear@0
|
356 while (!android_app->destroyed) {
|
nuclear@0
|
357 pthread_cond_wait(&android_app->cond, &android_app->mutex);
|
nuclear@0
|
358 }
|
nuclear@0
|
359 pthread_mutex_unlock(&android_app->mutex);
|
nuclear@0
|
360
|
nuclear@0
|
361 close(android_app->msgread);
|
nuclear@0
|
362 close(android_app->msgwrite);
|
nuclear@0
|
363 pthread_cond_destroy(&android_app->cond);
|
nuclear@0
|
364 pthread_mutex_destroy(&android_app->mutex);
|
nuclear@0
|
365 free(android_app);
|
nuclear@0
|
366 }
|
nuclear@0
|
367
|
nuclear@0
|
368 static void onDestroy(ANativeActivity* activity) {
|
nuclear@0
|
369 LOGV("Destroy: %p\n", activity);
|
nuclear@0
|
370 android_app_free((struct android_app*)activity->instance);
|
nuclear@0
|
371 }
|
nuclear@0
|
372
|
nuclear@0
|
373 static void onStart(ANativeActivity* activity) {
|
nuclear@0
|
374 LOGV("Start: %p\n", activity);
|
nuclear@0
|
375 android_app_set_activity_state((struct android_app*)activity->instance, APP_CMD_START);
|
nuclear@0
|
376 }
|
nuclear@0
|
377
|
nuclear@0
|
378 static void onResume(ANativeActivity* activity) {
|
nuclear@0
|
379 LOGV("Resume: %p\n", activity);
|
nuclear@0
|
380 android_app_set_activity_state((struct android_app*)activity->instance, APP_CMD_RESUME);
|
nuclear@0
|
381 }
|
nuclear@0
|
382
|
nuclear@0
|
383 static void* onSaveInstanceState(ANativeActivity* activity, size_t* outLen) {
|
nuclear@0
|
384 struct android_app* android_app = (struct android_app*)activity->instance;
|
nuclear@0
|
385 void* savedState = NULL;
|
nuclear@0
|
386
|
nuclear@0
|
387 LOGV("SaveInstanceState: %p\n", activity);
|
nuclear@0
|
388 pthread_mutex_lock(&android_app->mutex);
|
nuclear@0
|
389 android_app->stateSaved = 0;
|
nuclear@0
|
390 android_app_write_cmd(android_app, APP_CMD_SAVE_STATE);
|
nuclear@0
|
391 while (!android_app->stateSaved) {
|
nuclear@0
|
392 pthread_cond_wait(&android_app->cond, &android_app->mutex);
|
nuclear@0
|
393 }
|
nuclear@0
|
394
|
nuclear@0
|
395 if (android_app->savedState != NULL) {
|
nuclear@0
|
396 savedState = android_app->savedState;
|
nuclear@0
|
397 *outLen = android_app->savedStateSize;
|
nuclear@0
|
398 android_app->savedState = NULL;
|
nuclear@0
|
399 android_app->savedStateSize = 0;
|
nuclear@0
|
400 }
|
nuclear@0
|
401
|
nuclear@0
|
402 pthread_mutex_unlock(&android_app->mutex);
|
nuclear@0
|
403
|
nuclear@0
|
404 return savedState;
|
nuclear@0
|
405 }
|
nuclear@0
|
406
|
nuclear@0
|
407 static void onPause(ANativeActivity* activity) {
|
nuclear@0
|
408 LOGV("Pause: %p\n", activity);
|
nuclear@0
|
409 android_app_set_activity_state((struct android_app*)activity->instance, APP_CMD_PAUSE);
|
nuclear@0
|
410 }
|
nuclear@0
|
411
|
nuclear@0
|
412 static void onStop(ANativeActivity* activity) {
|
nuclear@0
|
413 LOGV("Stop: %p\n", activity);
|
nuclear@0
|
414 android_app_set_activity_state((struct android_app*)activity->instance, APP_CMD_STOP);
|
nuclear@0
|
415 }
|
nuclear@0
|
416
|
nuclear@0
|
417 static void onConfigurationChanged(ANativeActivity* activity) {
|
nuclear@0
|
418 struct android_app* android_app = (struct android_app*)activity->instance;
|
nuclear@0
|
419 LOGV("ConfigurationChanged: %p\n", activity);
|
nuclear@0
|
420 android_app_write_cmd(android_app, APP_CMD_CONFIG_CHANGED);
|
nuclear@0
|
421 }
|
nuclear@0
|
422
|
nuclear@0
|
423 static void onLowMemory(ANativeActivity* activity) {
|
nuclear@0
|
424 struct android_app* android_app = (struct android_app*)activity->instance;
|
nuclear@0
|
425 LOGV("LowMemory: %p\n", activity);
|
nuclear@0
|
426 android_app_write_cmd(android_app, APP_CMD_LOW_MEMORY);
|
nuclear@0
|
427 }
|
nuclear@0
|
428
|
nuclear@0
|
429 static void onWindowFocusChanged(ANativeActivity* activity, int focused) {
|
nuclear@0
|
430 LOGV("WindowFocusChanged: %p -- %d\n", activity, focused);
|
nuclear@0
|
431 android_app_write_cmd((struct android_app*)activity->instance,
|
nuclear@0
|
432 focused ? APP_CMD_GAINED_FOCUS : APP_CMD_LOST_FOCUS);
|
nuclear@0
|
433 }
|
nuclear@0
|
434
|
nuclear@0
|
435 static void onNativeWindowCreated(ANativeActivity* activity, ANativeWindow* window) {
|
nuclear@0
|
436 LOGV("NativeWindowCreated: %p -- %p\n", activity, window);
|
nuclear@0
|
437 android_app_set_window((struct android_app*)activity->instance, window);
|
nuclear@0
|
438 }
|
nuclear@0
|
439
|
nuclear@0
|
440 static void onNativeWindowDestroyed(ANativeActivity* activity, ANativeWindow* window) {
|
nuclear@0
|
441 LOGV("NativeWindowDestroyed: %p -- %p\n", activity, window);
|
nuclear@0
|
442 android_app_set_window((struct android_app*)activity->instance, NULL);
|
nuclear@0
|
443 }
|
nuclear@0
|
444
|
nuclear@0
|
445 static void onInputQueueCreated(ANativeActivity* activity, AInputQueue* queue) {
|
nuclear@0
|
446 LOGV("InputQueueCreated: %p -- %p\n", activity, queue);
|
nuclear@0
|
447 android_app_set_input((struct android_app*)activity->instance, queue);
|
nuclear@0
|
448 }
|
nuclear@0
|
449
|
nuclear@0
|
450 static void onInputQueueDestroyed(ANativeActivity* activity, AInputQueue* queue) {
|
nuclear@0
|
451 LOGV("InputQueueDestroyed: %p -- %p\n", activity, queue);
|
nuclear@0
|
452 android_app_set_input((struct android_app*)activity->instance, NULL);
|
nuclear@0
|
453 }
|
nuclear@0
|
454
|
nuclear@0
|
455 void ANativeActivity_onCreate(ANativeActivity* activity,
|
nuclear@0
|
456 void* savedState, size_t savedStateSize) {
|
nuclear@0
|
457 LOGV("Creating: %p\n", activity);
|
nuclear@0
|
458 activity->callbacks->onDestroy = onDestroy;
|
nuclear@0
|
459 activity->callbacks->onStart = onStart;
|
nuclear@0
|
460 activity->callbacks->onResume = onResume;
|
nuclear@0
|
461 activity->callbacks->onSaveInstanceState = onSaveInstanceState;
|
nuclear@0
|
462 activity->callbacks->onPause = onPause;
|
nuclear@0
|
463 activity->callbacks->onStop = onStop;
|
nuclear@0
|
464 activity->callbacks->onConfigurationChanged = onConfigurationChanged;
|
nuclear@0
|
465 activity->callbacks->onLowMemory = onLowMemory;
|
nuclear@0
|
466 activity->callbacks->onWindowFocusChanged = onWindowFocusChanged;
|
nuclear@0
|
467 activity->callbacks->onNativeWindowCreated = onNativeWindowCreated;
|
nuclear@0
|
468 activity->callbacks->onNativeWindowDestroyed = onNativeWindowDestroyed;
|
nuclear@0
|
469 activity->callbacks->onInputQueueCreated = onInputQueueCreated;
|
nuclear@0
|
470 activity->callbacks->onInputQueueDestroyed = onInputQueueDestroyed;
|
nuclear@0
|
471
|
nuclear@0
|
472 activity->instance = android_app_create(activity, savedState, savedStateSize);
|
nuclear@0
|
473 }
|