c/main,ipc/android: Deferred render target initialization for Android.

This commit is contained in:
Maxim Kizub 2022-11-29 03:31:30 +02:00 committed by Ryan Pavlik
parent f6e1ea7aa9
commit e600cdaabf
3 changed files with 49 additions and 31 deletions

View file

@ -138,8 +138,17 @@ comp_window_android_init_swapchain(struct comp_target *ct, uint32_t width, uint3
/* In process: Creating surface from activity */
window = _create_android_window(cwa);
} else {
/* Out of process: Getting cached surface */
window = (struct ANativeWindow *)android_globals_get_window();
/* Out of process: Getting cached surface.
* This loop polls for a surface created by Client.java in blockingConnect.
* TODO: change java code to callback native code to notify Session lifecycle progress, instead of
* polling here
*/
for (int i = 0; i < 100; i++) {
window = (struct ANativeWindow *)android_globals_get_window();
if (window)
break;
os_nanosleep(20 * U_TIME_1MS_IN_NS);
}
}
if (window == NULL) {
@ -215,7 +224,7 @@ struct comp_target_factory comp_target_factory_android = {
.name = "Android",
.identifier = "android",
.requires_vulkan_for_create = false,
.is_deferred = false,
.is_deferred = true,
.required_instance_extensions = instance_extensions,
.required_instance_extension_count = ARRAY_SIZE(instance_extensions),
.detect = detect,

View file

@ -161,40 +161,48 @@ public class Client implements ServiceConnection {
return -1;
}
boolean surfaceCreated = false;
Activity activity = null;
if (context_ instanceof Activity) {
activity = (Activity) context_;
}
// This block of code asynchronously create a MonadoView attached to activity and
// waits for Surface creation. Native code (comp_window_android_init_swapchain() method)
// will poll for ANativeWindow created from this Surface.
// TODO: just initiate MonadoView attachement and add callback to native code to
// notify about Surface status and pass it to OpenXR application as a Session lifecycle
// (ready ... synchronized ... visible ... focused)
new Thread(()-> {
boolean surfaceCreated = false;
Activity activity = null;
if (context_ instanceof Activity) {
activity = (Activity) context_;
}
try {
// Determine whether runtime or client should create surface
if (monado.canDrawOverOtherApps()) {
WindowManager wm = (WindowManager) context_.getSystemService(Context.WINDOW_SERVICE);
surfaceCreated = monado.createSurface(wm.getDefaultDisplay().getDisplayId(), false);
} else {
if (activity != null) {
Surface surface = attachViewAndGetSurface(activity);
surfaceCreated = (surface != null);
if (surfaceCreated) {
monado.passAppSurface(surface);
try {
// Determine whether runtime or client should create surface
if (monado.canDrawOverOtherApps()) {
WindowManager wm = (WindowManager) context_.getSystemService(Context.WINDOW_SERVICE);
surfaceCreated = monado.createSurface(wm.getDefaultDisplay().getDisplayId(), false);
} else {
if (activity != null) {
Surface surface = attachViewAndGetSurface(activity);
surfaceCreated = (surface != null);
if (surfaceCreated) {
monado.passAppSurface(surface);
}
}
}
} catch (RemoteException e) {
e.printStackTrace();
}
} catch (RemoteException e) {
e.printStackTrace();
}
if (!surfaceCreated) {
Log.e(TAG, "Failed to create surface");
handleFailure();
return -1;
}
if (!surfaceCreated) {
Log.e(TAG, "Failed to create surface");
handleFailure();
return;
}
if (activity != null) {
systemUiController = new SystemUiController(activity);
systemUiController.hide();
}
if (activity != null) {
systemUiController = new SystemUiController(activity);
systemUiController.hide();
}
}).start();
// Create socket pair
ParcelFileDescriptor theirs;

View file

@ -65,6 +65,7 @@ public class MonadoImpl extends IMonado.Stub {
@Override
public void connect(@NotNull ParcelFileDescriptor parcelFileDescriptor) {
nativeStartServer();
int fd = parcelFileDescriptor.getFd();
Log.i(TAG, "connect: given fd " + fd);
if (nativeAddClient(fd) != 0) {