Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(216)

Unified Diff: content/public/android/java/src/org/chromium/content/browser/androidoverlay/AndroidOverlayProviderImpl.java

Issue 2765443004: AndroidOverlay implementation using Dialog. (Closed)
Patch Set: fixed test Created 3 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: content/public/android/java/src/org/chromium/content/browser/androidoverlay/AndroidOverlayProviderImpl.java
diff --git a/content/public/android/java/src/org/chromium/content/browser/androidoverlay/AndroidOverlayProviderImpl.java b/content/public/android/java/src/org/chromium/content/browser/androidoverlay/AndroidOverlayProviderImpl.java
index cf4766ffda92be146b7eb04d9ff855cb517b8386..4adb149028b782d38ef1eeb41a4f3af70464fc41 100644
--- a/content/public/android/java/src/org/chromium/content/browser/androidoverlay/AndroidOverlayProviderImpl.java
+++ b/content/public/android/java/src/org/chromium/content/browser/androidoverlay/AndroidOverlayProviderImpl.java
@@ -5,7 +5,10 @@
package org.chromium.content.browser.androidoverlay;
import android.content.Context;
+import android.os.Handler;
+import android.os.HandlerThread;
+import org.chromium.base.ThreadUtils;
import org.chromium.media.mojom.AndroidOverlay;
import org.chromium.media.mojom.AndroidOverlayClient;
import org.chromium.media.mojom.AndroidOverlayConfig;
@@ -15,23 +18,87 @@ import org.chromium.mojo.system.MojoException;
import org.chromium.services.service_manager.InterfaceFactory;
/**
- * Default impl of AndroidOverlayProvider. Creates AndroidOverlayImpls.
+ * Default impl of AndroidOverlayProvider. Creates AndroidOverlayImpls. We're a singleton, in the
+ * sense that all provider clients talk to the same instance in the browser.
*/
public class AndroidOverlayProviderImpl implements AndroidOverlayProvider {
private static final String TAG = "AndroidOverlayProvider";
+ // Maximum number of concurrent overlays that we allow.
+ private static final int MAX_OVERLAYS = 1;
+
+ // We maintain a thread with a Looper for the AndroidOverlays to use, since Dialog requires one.
+ // We don't want this to be the native thread that's used to create them (the browser UI thread)
+ // since we don't want to block that waiting for sync callbacks from Android, such as
+ // surfaceDestroyed. Instead, we run all AndroidOverlays on one shared overlay-ui thread.
+ private HandlerThread mOverlayUiThread;
+ private Handler mHandler;
+
+ // Number of AndroidOverlays that have been created but not released.
+ private int mNumOverlays;
+
+ // Runnable that notifies us that a client has been released.
+ private Runnable mNotifyReleasedRunnable = new Runnable() {
+ @Override
+ public void run() {
+ notifyReleased();
+ }
+ };
+
/**
* Create an overlay matching |config| for |client|, and bind it to |request|. Remember that
* potentially many providers are created.
*/
+ @Override
public void createOverlay(InterfaceRequest<AndroidOverlay> request, AndroidOverlayClient client,
AndroidOverlayConfig config) {
- client.onDestroyed();
+ ThreadUtils.assertOnUiThread();
+
+ // Limit the number of concurrent surfaces.
+ if (mNumOverlays >= MAX_OVERLAYS) {
+ client.onDestroyed();
+ return;
+ }
+
+ startThreadIfNeeded();
+ mNumOverlays++;
+
+ DialogOverlayImpl impl =
+ new DialogOverlayImpl(client, config, mHandler, mNotifyReleasedRunnable);
+ DialogOverlayImpl.MANAGER.bind(impl, request);
+ }
+
+ /**
+ * Make sure that mOverlayUiThread and mHandler are ready for use, if needed.
+ */
+ private void startThreadIfNeeded() {
+ if (mOverlayUiThread != null) return;
+
+ mOverlayUiThread = new HandlerThread("AndroidOverlayThread");
+ mOverlayUiThread.start();
+ mHandler = new Handler(mOverlayUiThread.getLooper());
+ }
+
+ /**
+ * Called by AndroidOverlays when they no longer need the thread via |mNotifyReleasedRunnable|.
+ */
+ private void notifyReleased() {
+ ThreadUtils.assertOnUiThread();
+ assert mNumOverlays > 0;
+ mNumOverlays--;
+
+ // We don't stop the looper thread here, else android can get mad when it tries to send
+ // a message from the dialog on this thread. AndroidOverlay might have to notify us
+ // separately to tell us when it's done with the thread, if we don't want to wait until
+ // then to start creating a new SV.
+ // Instead, we just avoid shutting down the thread at all for now.
}
+ // Remember that we can't tell which client disconnected.
@Override
public void close() {}
+ // Remember that we can't tell which client disconnected.
@Override
public void onConnectionError(MojoException e) {}
@@ -39,11 +106,13 @@ public class AndroidOverlayProviderImpl implements AndroidOverlayProvider {
* Mojo factory.
*/
public static class Factory implements InterfaceFactory<AndroidOverlayProvider> {
+ private static AndroidOverlayProviderImpl sImpl;
public Factory(Context context) {}
@Override
public AndroidOverlayProvider createImpl() {
- return new AndroidOverlayProviderImpl();
+ if (sImpl == null) sImpl = new AndroidOverlayProviderImpl();
+ return sImpl;
}
}
}

Powered by Google App Engine
This is Rietveld 408576698