aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorperkj <perkj@webrtc.org>2015-12-02 01:07:18 -0800
committerCommit bot <commit-bot@chromium.org>2015-12-02 09:07:22 +0000
commit40455d6f37fda78ea069a51d95f28994bd736864 (patch)
tree1f0372871e12ba51177d141a97071e8403063e20
parente3384990ea2c2d1ab6ea4f00ac1f84c8322645d8 (diff)
downloadwebrtc-40455d6f37fda78ea069a51d95f28994bd736864.tar.gz
This cl change so that we use EGL14 where it is supported and EGL10 otherwise. The idea is to make this agnostic to an application and for WebRTC except in EGLBase.
The reason we want to use EGL14 is to be able to use EGLExt.eglPresentationTimeANDROID when writing textures to MediaEncoder. BUG=webrtc:4993 TBR=glaznew@webrtc.org Review URL: https://codereview.webrtc.org/1461083002 Cr-Commit-Position: refs/heads/master@{#10864}
-rw-r--r--talk/app/webrtc/androidtests/src/org/webrtc/GlRectDrawerTest.java21
-rw-r--r--talk/app/webrtc/androidtests/src/org/webrtc/MediaCodecVideoEncoderTest.java14
-rw-r--r--talk/app/webrtc/androidtests/src/org/webrtc/SurfaceTextureHelperTest.java30
-rw-r--r--talk/app/webrtc/androidtests/src/org/webrtc/SurfaceViewRendererOnMeasureTest.java6
-rw-r--r--talk/app/webrtc/androidtests/src/org/webrtc/VideoCapturerAndroidTest.java41
-rw-r--r--talk/app/webrtc/java/android/org/webrtc/EglBase.java64
-rw-r--r--talk/app/webrtc/java/android/org/webrtc/EglBase14.java281
-rw-r--r--talk/app/webrtc/java/android/org/webrtc/SurfaceTextureHelper.java12
-rw-r--r--talk/app/webrtc/java/android/org/webrtc/SurfaceViewRenderer.java13
-rw-r--r--talk/app/webrtc/java/android/org/webrtc/VideoCapturerAndroid.java10
-rw-r--r--talk/app/webrtc/java/android/org/webrtc/VideoRendererGui.java5
-rw-r--r--talk/app/webrtc/java/jni/androidmediadecoder_jni.cc2
-rw-r--r--talk/app/webrtc/java/jni/androidmediaencoder_jni.cc4
-rw-r--r--talk/app/webrtc/java/jni/classreferenceholder.cc1
-rw-r--r--talk/app/webrtc/java/jni/peerconnection_jni.cc32
-rw-r--r--talk/app/webrtc/java/jni/surfacetexturehelper_jni.cc2
-rw-r--r--talk/app/webrtc/java/src/org/webrtc/MediaCodecVideoEncoder.java6
-rwxr-xr-xtalk/libjingle.gyp1
-rw-r--r--webrtc/examples/androidapp/src/org/appspot/apprtc/PeerConnectionClient.java3
19 files changed, 464 insertions, 84 deletions
diff --git a/talk/app/webrtc/androidtests/src/org/webrtc/GlRectDrawerTest.java b/talk/app/webrtc/androidtests/src/org/webrtc/GlRectDrawerTest.java
index 1c01ffa0b8..36424aa144 100644
--- a/talk/app/webrtc/androidtests/src/org/webrtc/GlRectDrawerTest.java
+++ b/talk/app/webrtc/androidtests/src/org/webrtc/GlRectDrawerTest.java
@@ -28,7 +28,6 @@ package org.webrtc;
import android.graphics.SurfaceTexture;
import android.opengl.GLES20;
-import android.opengl.Matrix;
import android.test.ActivityTestCase;
import android.test.suitebuilder.annotation.MediumTest;
import android.test.suitebuilder.annotation.SmallTest;
@@ -36,9 +35,6 @@ import android.test.suitebuilder.annotation.SmallTest;
import java.nio.ByteBuffer;
import java.util.Random;
-import javax.microedition.khronos.egl.EGL10;
-import javax.microedition.khronos.egl.EGLContext;
-
public final class GlRectDrawerTest extends ActivityTestCase {
// Resolution of the test image.
private static final int WIDTH = 16;
@@ -46,7 +42,7 @@ public final class GlRectDrawerTest extends ActivityTestCase {
// Seed for random pixel creation.
private static final int SEED = 42;
// When comparing pixels, allow some slack for float arithmetic and integer rounding.
- private static final float MAX_DIFF = 1.0f;
+ private static final float MAX_DIFF = 1.5f;
private static float normalizedByte(byte b) {
return (b & 0xFF) / 255.0f;
@@ -100,7 +96,7 @@ public final class GlRectDrawerTest extends ActivityTestCase {
@SmallTest
public void testRgbRendering() {
// Create EGL base with a pixel buffer as display output.
- final EglBase eglBase = new EglBase(EGL10.EGL_NO_CONTEXT, EglBase.ConfigType.PIXEL_BUFFER);
+ final EglBase eglBase = EglBase.create(null, EglBase.ConfigType.PIXEL_BUFFER);
eglBase.createPbufferSurface(WIDTH, HEIGHT);
eglBase.makeCurrent();
@@ -137,7 +133,7 @@ public final class GlRectDrawerTest extends ActivityTestCase {
@SmallTest
public void testYuvRendering() {
// Create EGL base with a pixel buffer as display output.
- EglBase eglBase = new EglBase(EGL10.EGL_NO_CONTEXT, EglBase.ConfigType.PIXEL_BUFFER);
+ EglBase eglBase = EglBase.create(null, EglBase.ConfigType.PIXEL_BUFFER);
eglBase.createPbufferSurface(WIDTH, HEIGHT);
eglBase.makeCurrent();
@@ -231,8 +227,9 @@ public final class GlRectDrawerTest extends ActivityTestCase {
private final int rgbTexture;
public StubOesTextureProducer(
- EGLContext sharedContext, SurfaceTexture surfaceTexture, int width, int height) {
- eglBase = new EglBase(sharedContext, EglBase.ConfigType.PLAIN);
+ EglBase.Context sharedContext, SurfaceTexture surfaceTexture, int width,
+ int height) {
+ eglBase = EglBase.create(sharedContext, EglBase.ConfigType.PLAIN);
surfaceTexture.setDefaultBufferSize(width, height);
eglBase.createSurface(surfaceTexture);
assertEquals(eglBase.surfaceWidth(), width);
@@ -266,14 +263,14 @@ public final class GlRectDrawerTest extends ActivityTestCase {
}
// Create EGL base with a pixel buffer as display output.
- final EglBase eglBase = new EglBase(EGL10.EGL_NO_CONTEXT, EglBase.ConfigType.PIXEL_BUFFER);
+ final EglBase eglBase = EglBase.create(null, EglBase.ConfigType.PIXEL_BUFFER);
eglBase.createPbufferSurface(WIDTH, HEIGHT);
// Create resources for generating OES textures.
final SurfaceTextureHelper surfaceTextureHelper =
- SurfaceTextureHelper.create(eglBase.getContext());
+ SurfaceTextureHelper.create(eglBase.getEglBaseContext());
final StubOesTextureProducer oesProducer = new StubOesTextureProducer(
- eglBase.getContext(), surfaceTextureHelper.getSurfaceTexture(), WIDTH, HEIGHT);
+ eglBase.getEglBaseContext(), surfaceTextureHelper.getSurfaceTexture(), WIDTH, HEIGHT);
final SurfaceTextureHelperTest.MockTextureListener listener =
new SurfaceTextureHelperTest.MockTextureListener();
surfaceTextureHelper.setListener(listener);
diff --git a/talk/app/webrtc/androidtests/src/org/webrtc/MediaCodecVideoEncoderTest.java b/talk/app/webrtc/androidtests/src/org/webrtc/MediaCodecVideoEncoderTest.java
index ee62008010..1367189fe3 100644
--- a/talk/app/webrtc/androidtests/src/org/webrtc/MediaCodecVideoEncoderTest.java
+++ b/talk/app/webrtc/androidtests/src/org/webrtc/MediaCodecVideoEncoderTest.java
@@ -38,8 +38,6 @@ import org.webrtc.MediaCodecVideoEncoder.OutputBufferInfo;
import java.nio.ByteBuffer;
-import javax.microedition.khronos.egl.EGL10;
-
@TargetApi(Build.VERSION_CODES.ICE_CREAM_SANDWICH_MR1)
public final class MediaCodecVideoEncoderTest extends ActivityTestCase {
final static String TAG = "MediaCodecVideoEncoderTest";
@@ -63,11 +61,13 @@ public final class MediaCodecVideoEncoderTest extends ActivityTestCase {
Log.i(TAG, "hardware does not support VP8 encoding, skipping testEncoderUsingTextures");
return;
}
+ EglBase eglBase = EglBase.create();
MediaCodecVideoEncoder encoder = new MediaCodecVideoEncoder();
assertTrue(encoder.initEncode(
MediaCodecVideoEncoder.VideoCodecType.VIDEO_CODEC_VP8, 640, 480, 300, 30,
- EGL10.EGL_NO_CONTEXT));
+ eglBase.getEglBaseContext()));
encoder.release();
+ eglBase.release();
}
@SmallTest
@@ -81,10 +81,12 @@ public final class MediaCodecVideoEncoderTest extends ActivityTestCase {
MediaCodecVideoEncoder.VideoCodecType.VIDEO_CODEC_VP8, 640, 480, 300, 30,
null));
encoder.release();
+ EglBase eglBase = EglBase.create();
assertTrue(encoder.initEncode(
MediaCodecVideoEncoder.VideoCodecType.VIDEO_CODEC_VP8, 640, 480, 300, 30,
- EGL10.EGL_NO_CONTEXT));
+ eglBase.getEglBaseContext()));
encoder.release();
+ eglBase.release();
}
@SmallTest
@@ -141,7 +143,7 @@ public final class MediaCodecVideoEncoderTest extends ActivityTestCase {
final int height = 480;
final long presentationTs = 2;
- final EglBase eglOesBase = new EglBase(EGL10.EGL_NO_CONTEXT, EglBase.ConfigType.PIXEL_BUFFER);
+ final EglBase eglOesBase = EglBase.create(null, EglBase.ConfigType.PIXEL_BUFFER);
eglOesBase.createDummyPbufferSurface();
eglOesBase.makeCurrent();
int oesTextureId = GlUtil.generateTexture(GLES11Ext.GL_TEXTURE_EXTERNAL_OES);
@@ -154,7 +156,7 @@ public final class MediaCodecVideoEncoderTest extends ActivityTestCase {
assertTrue(encoder.initEncode(
MediaCodecVideoEncoder.VideoCodecType.VIDEO_CODEC_VP8, width, height, 300, 30,
- eglOesBase.getContext()));
+ eglOesBase.getEglBaseContext()));
assertTrue(encoder.encodeTexture(true, oesTextureId, RendererCommon.identityMatrix(),
presentationTs));
GlUtil.checkNoGLES2Error("encodeTexture");
diff --git a/talk/app/webrtc/androidtests/src/org/webrtc/SurfaceTextureHelperTest.java b/talk/app/webrtc/androidtests/src/org/webrtc/SurfaceTextureHelperTest.java
index 5a3b9b66e7..9879522cc9 100644
--- a/talk/app/webrtc/androidtests/src/org/webrtc/SurfaceTextureHelperTest.java
+++ b/talk/app/webrtc/androidtests/src/org/webrtc/SurfaceTextureHelperTest.java
@@ -37,8 +37,6 @@ import android.test.suitebuilder.annotation.SmallTest;
import java.nio.ByteBuffer;
-import javax.microedition.khronos.egl.EGL10;
-
public final class SurfaceTextureHelperTest extends ActivityTestCase {
/**
* Mock texture listener with blocking wait functionality.
@@ -109,20 +107,21 @@ public final class SurfaceTextureHelperTest extends ActivityTestCase {
final int width = 16;
final int height = 16;
// Create EGL base with a pixel buffer as display output.
- final EglBase eglBase = new EglBase(EGL10.EGL_NO_CONTEXT, EglBase.ConfigType.PIXEL_BUFFER);
+ final EglBase eglBase = EglBase.create(null, EglBase.ConfigType.PIXEL_BUFFER);
eglBase.createPbufferSurface(width, height);
final GlRectDrawer drawer = new GlRectDrawer();
// Create SurfaceTextureHelper and listener.
final SurfaceTextureHelper surfaceTextureHelper =
- SurfaceTextureHelper.create(eglBase.getContext());
+ SurfaceTextureHelper.create(eglBase.getEglBaseContext());
final MockTextureListener listener = new MockTextureListener();
surfaceTextureHelper.setListener(listener);
surfaceTextureHelper.getSurfaceTexture().setDefaultBufferSize(width, height);
// Create resources for stubbing an OES texture producer. |eglOesBase| has the SurfaceTexture in
// |surfaceTextureHelper| as the target EGLSurface.
- final EglBase eglOesBase = new EglBase(eglBase.getContext(), EglBase.ConfigType.PLAIN);
+ final EglBase eglOesBase =
+ EglBase.create(eglBase.getEglBaseContext(), EglBase.ConfigType.PLAIN);
eglOesBase.createSurface(surfaceTextureHelper.getSurfaceTexture());
assertEquals(eglOesBase.surfaceWidth(), width);
assertEquals(eglOesBase.surfaceHeight(), height);
@@ -176,19 +175,20 @@ public final class SurfaceTextureHelperTest extends ActivityTestCase {
final int width = 16;
final int height = 16;
// Create EGL base with a pixel buffer as display output.
- final EglBase eglBase = new EglBase(EGL10.EGL_NO_CONTEXT, EglBase.ConfigType.PIXEL_BUFFER);
+ final EglBase eglBase = EglBase.create(null, EglBase.ConfigType.PIXEL_BUFFER);
eglBase.createPbufferSurface(width, height);
// Create SurfaceTextureHelper and listener.
final SurfaceTextureHelper surfaceTextureHelper =
- SurfaceTextureHelper.create(eglBase.getContext());
+ SurfaceTextureHelper.create(eglBase.getEglBaseContext());
final MockTextureListener listener = new MockTextureListener();
surfaceTextureHelper.setListener(listener);
surfaceTextureHelper.getSurfaceTexture().setDefaultBufferSize(width, height);
// Create resources for stubbing an OES texture producer. |eglOesBase| has the SurfaceTexture in
// |surfaceTextureHelper| as the target EGLSurface.
- final EglBase eglOesBase = new EglBase(eglBase.getContext(), EglBase.ConfigType.PLAIN);
+ final EglBase eglOesBase =
+ EglBase.create(eglBase.getEglBaseContext(), EglBase.ConfigType.PLAIN);
eglOesBase.createSurface(surfaceTextureHelper.getSurfaceTexture());
assertEquals(eglOesBase.surfaceWidth(), width);
assertEquals(eglOesBase.surfaceHeight(), height);
@@ -240,11 +240,11 @@ public final class SurfaceTextureHelperTest extends ActivityTestCase {
public static void testDisconnect() throws InterruptedException {
// Create SurfaceTextureHelper and listener.
final SurfaceTextureHelper surfaceTextureHelper =
- SurfaceTextureHelper.create(EGL10.EGL_NO_CONTEXT);
+ SurfaceTextureHelper.create(null);
final MockTextureListener listener = new MockTextureListener();
surfaceTextureHelper.setListener(listener);
// Create EglBase with the SurfaceTexture as target EGLSurface.
- final EglBase eglBase = new EglBase(EGL10.EGL_NO_CONTEXT, EglBase.ConfigType.PLAIN);
+ final EglBase eglBase = EglBase.create(null, EglBase.ConfigType.PLAIN);
eglBase.createSurface(surfaceTextureHelper.getSurfaceTexture());
eglBase.makeCurrent();
// Assert no frame has been received yet.
@@ -276,7 +276,7 @@ public final class SurfaceTextureHelperTest extends ActivityTestCase {
@SmallTest
public static void testDisconnectImmediately() {
final SurfaceTextureHelper surfaceTextureHelper =
- SurfaceTextureHelper.create(EGL10.EGL_NO_CONTEXT);
+ SurfaceTextureHelper.create(null);
surfaceTextureHelper.disconnect();
}
@@ -292,14 +292,14 @@ public final class SurfaceTextureHelperTest extends ActivityTestCase {
// Create SurfaceTextureHelper and listener.
final SurfaceTextureHelper surfaceTextureHelper =
- SurfaceTextureHelper.create(EGL10.EGL_NO_CONTEXT, handler);
+ SurfaceTextureHelper.create(null, handler);
// Create a mock listener and expect frames to be delivered on |thread|.
final MockTextureListener listener = new MockTextureListener(thread);
surfaceTextureHelper.setListener(listener);
// Create resources for stubbing an OES texture producer. |eglOesBase| has the
// SurfaceTexture in |surfaceTextureHelper| as the target EGLSurface.
- final EglBase eglOesBase = new EglBase(EGL10.EGL_NO_CONTEXT, EglBase.ConfigType.PLAIN);
+ final EglBase eglOesBase = EglBase.create(null, EglBase.ConfigType.PLAIN);
eglOesBase.createSurface(surfaceTextureHelper.getSurfaceTexture());
eglOesBase.makeCurrent();
// Draw a frame onto the SurfaceTexture.
@@ -328,14 +328,14 @@ public final class SurfaceTextureHelperTest extends ActivityTestCase {
// Create SurfaceTextureHelper and listener.
final SurfaceTextureHelper surfaceTextureHelper =
- SurfaceTextureHelper.create(EGL10.EGL_NO_CONTEXT, handler);
+ SurfaceTextureHelper.create(null, handler);
// Create a mock listener and expect frames to be delivered on |thread|.
final MockTextureListener listener = new MockTextureListener(thread);
surfaceTextureHelper.setListener(listener);
// Create resources for stubbing an OES texture producer. |eglOesBase| has the
// SurfaceTexture in |surfaceTextureHelper| as the target EGLSurface.
- final EglBase eglOesBase = new EglBase(EGL10.EGL_NO_CONTEXT, EglBase.ConfigType.PLAIN);
+ final EglBase eglOesBase = EglBase.create(null, EglBase.ConfigType.PLAIN);
eglOesBase.createSurface(surfaceTextureHelper.getSurfaceTexture());
eglOesBase.makeCurrent();
// Draw a frame onto the SurfaceTexture.
diff --git a/talk/app/webrtc/androidtests/src/org/webrtc/SurfaceViewRendererOnMeasureTest.java b/talk/app/webrtc/androidtests/src/org/webrtc/SurfaceViewRendererOnMeasureTest.java
index 47fe780124..341c632b58 100644
--- a/talk/app/webrtc/androidtests/src/org/webrtc/SurfaceViewRendererOnMeasureTest.java
+++ b/talk/app/webrtc/androidtests/src/org/webrtc/SurfaceViewRendererOnMeasureTest.java
@@ -36,8 +36,6 @@ import java.nio.ByteBuffer;
import java.util.Arrays;
import java.util.List;
-import javax.microedition.khronos.egl.EGL10;
-
public final class SurfaceViewRendererOnMeasureTest extends ActivityTestCase {
/**
* List with all possible scaling types.
@@ -111,7 +109,7 @@ public final class SurfaceViewRendererOnMeasureTest extends ActivityTestCase {
}
// Test behaviour after SurfaceViewRenderer.init() is called, but still no frame.
- surfaceViewRenderer.init(EGL10.EGL_NO_CONTEXT, null);
+ surfaceViewRenderer.init((EglBase.Context) null, null);
for (RendererCommon.ScalingType scalingType : scalingTypes) {
for (int measureSpecMode : measureSpecModes) {
final int zeroMeasureSize = MeasureSpec.makeMeasureSpec(0, measureSpecMode);
@@ -134,7 +132,7 @@ public final class SurfaceViewRendererOnMeasureTest extends ActivityTestCase {
public void testFrame1280x720() {
final SurfaceViewRenderer surfaceViewRenderer =
new SurfaceViewRenderer(getInstrumentation().getContext());
- surfaceViewRenderer.init(EGL10.EGL_NO_CONTEXT, null);
+ surfaceViewRenderer.init((EglBase.Context) null, null);
// Test different rotation degress, but same rotated size.
for (int rotationDegree : new int[] {0, 90, 180, 270}) {
diff --git a/talk/app/webrtc/androidtests/src/org/webrtc/VideoCapturerAndroidTest.java b/talk/app/webrtc/androidtests/src/org/webrtc/VideoCapturerAndroidTest.java
index f89d222428..dfa7c0a298 100644
--- a/talk/app/webrtc/androidtests/src/org/webrtc/VideoCapturerAndroidTest.java
+++ b/talk/app/webrtc/androidtests/src/org/webrtc/VideoCapturerAndroidTest.java
@@ -36,8 +36,6 @@ import org.webrtc.CameraEnumerationAndroid.CaptureFormat;
import java.util.HashSet;
import java.util.Set;
-import javax.microedition.khronos.egl.EGL10;
-
@SuppressWarnings("deprecation")
public class VideoCapturerAndroidTest extends ActivityTestCase {
static final String TAG = "VideoCapturerAndroidTest";
@@ -86,8 +84,10 @@ public class VideoCapturerAndroidTest extends ActivityTestCase {
@SmallTest
public void testCreateAndReleaseUsingTextures() {
+ EglBase eglBase = EglBase.create();
VideoCapturerAndroidTestFixtures.release(
- VideoCapturerAndroid.create("", null, EGL10.EGL_NO_CONTEXT));
+ VideoCapturerAndroid.create("", null, eglBase.getEglBaseContext()));
+ eglBase.release();
}
@SmallTest
@@ -109,9 +109,11 @@ public class VideoCapturerAndroidTest extends ActivityTestCase {
@SmallTest
public void testStartVideoCapturerUsingTextures() throws InterruptedException {
+ EglBase eglBase = EglBase.create();
VideoCapturerAndroid capturer =
- VideoCapturerAndroid.create("", null, EGL10.EGL_NO_CONTEXT);
+ VideoCapturerAndroid.create("", null, eglBase.getEglBaseContext());
VideoCapturerAndroidTestFixtures.startCapturerAndRender(capturer);
+ eglBase.release();
}
@SmallTest
@@ -151,8 +153,11 @@ public class VideoCapturerAndroidTest extends ActivityTestCase {
@SmallTest
public void testSwitchVideoCapturerUsingTextures() throws InterruptedException {
- VideoCapturerAndroid capturer = VideoCapturerAndroid.create("", null, EGL10.EGL_NO_CONTEXT);
+ EglBase eglBase = EglBase.create();
+ VideoCapturerAndroid capturer =
+ VideoCapturerAndroid.create("", null, eglBase.getEglBaseContext());
VideoCapturerAndroidTestFixtures.switchCamera(capturer);
+ eglBase.release();
}
@MediumTest
@@ -176,12 +181,14 @@ public class VideoCapturerAndroidTest extends ActivityTestCase {
@MediumTest
public void testCameraCallsAfterStopUsingTextures() throws InterruptedException {
+ EglBase eglBase = EglBase.create();
final String deviceName = CameraEnumerationAndroid.getDeviceName(0);
final VideoCapturerAndroid capturer = VideoCapturerAndroid.create(deviceName, null,
- EGL10.EGL_NO_CONTEXT);
+ eglBase.getEglBaseContext());
VideoCapturerAndroidTestFixtures.cameraCallsAfterStop(capturer,
getInstrumentation().getContext());
+ eglBase.release();
}
@SmallTest
@@ -194,8 +201,11 @@ public class VideoCapturerAndroidTest extends ActivityTestCase {
@SmallTest
public void testStopRestartVideoSourceUsingTextures() throws InterruptedException {
- VideoCapturerAndroid capturer = VideoCapturerAndroid.create("", null, EGL10.EGL_NO_CONTEXT);
+ EglBase eglBase = EglBase.create();
+ VideoCapturerAndroid capturer =
+ VideoCapturerAndroid.create("", null, eglBase.getEglBaseContext());
VideoCapturerAndroidTestFixtures.stopRestartVideoSource(capturer);
+ eglBase.release();
}
@SmallTest
@@ -211,11 +221,13 @@ public class VideoCapturerAndroidTest extends ActivityTestCase {
@SmallTest
public void testStartStopWithDifferentResolutionsUsingTextures() throws InterruptedException {
+ EglBase eglBase = EglBase.create();
String deviceName = CameraEnumerationAndroid.getDeviceName(0);
VideoCapturerAndroid capturer =
- VideoCapturerAndroid.create(deviceName, null, EGL10.EGL_NO_CONTEXT);
+ VideoCapturerAndroid.create(deviceName, null, eglBase.getEglBaseContext());
VideoCapturerAndroidTestFixtures.startStopWithDifferentResolutions(capturer,
getInstrumentation().getContext());
+ eglBase.release();
}
@SmallTest
@@ -266,11 +278,13 @@ public class VideoCapturerAndroidTest extends ActivityTestCase {
@SmallTest
public void testReturnBufferLateUsingTextures() throws InterruptedException {
+ EglBase eglBase = EglBase.create();
String deviceName = CameraEnumerationAndroid.getDeviceName(0);
VideoCapturerAndroid capturer =
- VideoCapturerAndroid.create(deviceName, null, EGL10.EGL_NO_CONTEXT);
+ VideoCapturerAndroid.create(deviceName, null, eglBase.getEglBaseContext());
VideoCapturerAndroidTestFixtures.returnBufferLate(capturer,
getInstrumentation().getContext());
+ eglBase.release();
}
@MediumTest
@@ -284,9 +298,11 @@ public class VideoCapturerAndroidTest extends ActivityTestCase {
@MediumTest
public void testReturnBufferLateEndToEndUsingTextures() throws InterruptedException {
+ EglBase eglBase = EglBase.create();
final VideoCapturerAndroid capturer =
- VideoCapturerAndroid.create("", null, EGL10.EGL_NO_CONTEXT);
+ VideoCapturerAndroid.create("", null, eglBase.getEglBaseContext());
VideoCapturerAndroidTestFixtures.returnBufferLateEndToEnd(capturer);
+ eglBase.release();
}
@MediumTest
@@ -312,7 +328,10 @@ public class VideoCapturerAndroidTest extends ActivityTestCase {
// This test that frames forwarded to a renderer is scaled if onOutputFormatRequest is
// called. This test both Java and C++ parts of of the stack.
public void testScaleCameraOutputUsingTextures() throws InterruptedException {
- VideoCapturerAndroid capturer = VideoCapturerAndroid.create("", null, EGL10.EGL_NO_CONTEXT);
+ EglBase eglBase = EglBase.create();
+ VideoCapturerAndroid capturer =
+ VideoCapturerAndroid.create("", null, eglBase.getEglBaseContext());
VideoCapturerAndroidTestFixtures.scaleCameraOutput(capturer);
+ eglBase.release();
}
}
diff --git a/talk/app/webrtc/java/android/org/webrtc/EglBase.java b/talk/app/webrtc/java/android/org/webrtc/EglBase.java
index 1de34d254e..a68840c8c8 100644
--- a/talk/app/webrtc/java/android/org/webrtc/EglBase.java
+++ b/talk/app/webrtc/java/android/org/webrtc/EglBase.java
@@ -34,6 +34,8 @@ import android.view.Surface;
import android.view.SurfaceHolder;
import org.webrtc.Logging;
+import org.webrtc.EglBase.ConfigType;
+import org.webrtc.EglBase.Context;
import javax.microedition.khronos.egl.EGL10;
import javax.microedition.khronos.egl.EGLConfig;
@@ -42,7 +44,8 @@ import javax.microedition.khronos.egl.EGLDisplay;
import javax.microedition.khronos.egl.EGLSurface;
/**
- * Holds EGL state and utility methods for handling an EGLContext, an EGLDisplay, and an EGLSurface.
+ * Holds EGL state and utility methods for handling an egl 1.0 EGLContext, an EGLDisplay,
+ * and an EGLSurface.
*/
public class EglBase {
private static final String TAG = "EglBase";
@@ -62,6 +65,15 @@ public class EglBase {
private EGLDisplay eglDisplay;
private EGLSurface eglSurface = EGL10.EGL_NO_SURFACE;
+ // EGL wrapper for an actual EGLContext.
+ public static class Context {
+ private final EGLContext eglContext;
+
+ public Context(EGLContext eglContext) {
+ this.eglContext = eglContext;
+ }
+ }
+
// EGLConfig constructor type. Influences eglChooseConfig arguments.
public static enum ConfigType {
// No special parameters.
@@ -74,14 +86,39 @@ public class EglBase {
RECORDABLE
}
- // Create root context without any EGLSurface or parent EGLContext. This can be used for branching
+ // Create a new context with the specified config type, sharing data with sharedContext.
+ // |sharedContext| can be null.
+ public static EglBase create(Context sharedContext, ConfigType configType) {
+ return (EglBase14.isEGL14Supported()
+ && (sharedContext == null || sharedContext instanceof EglBase14.Context))
+ ? new EglBase14((EglBase14.Context) sharedContext, configType)
+ : new EglBase(sharedContext, configType);
+ }
+
+ public static EglBase create() {
+ return create(null, ConfigType.PLAIN);
+ }
+
+ //Create root context without any EGLSurface or parent EGLContext. This can be used for branching
// new contexts that share data.
+ @Deprecated
public EglBase() {
- this(EGL10.EGL_NO_CONTEXT, ConfigType.PLAIN);
+ this((Context) null, ConfigType.PLAIN);
}
- // Create a new context with the specified config type, sharing data with sharedContext.
+ @Deprecated
public EglBase(EGLContext sharedContext, ConfigType configType) {
+ this(new Context(sharedContext), configType);
+ Logging.d(TAG, "EglBase created");
+ }
+
+ @Deprecated
+ public EGLContext getContext() {
+ return eglContext;
+ }
+
+ // Create a new context with the specified config type, sharing data with sharedContext.
+ EglBase(Context sharedContext, ConfigType configType) {
this.egl = (EGL10) EGLContext.getEGL();
this.configType = configType;
eglDisplay = getEglDisplay();
@@ -89,7 +126,13 @@ public class EglBase {
eglContext = createEglContext(sharedContext, eglDisplay, eglConfig);
}
- // Create EGLSurface from the Android Surface.
+ // TODO(perkj): This is a hacky ctor used to allow us to create an EGLBase14. Remove this and
+ // make EglBase an abstract class once all applications have started using the create factory
+ // method.
+ protected EglBase(boolean dummy) {
+ this.egl = null;
+ }
+
public void createSurface(Surface surface) {
/**
* We have to wrap Surface in a SurfaceHolder because for some reason eglCreateWindowSurface
@@ -114,6 +157,7 @@ public class EglBase {
return false;
}
+ @Deprecated
@Override
public void setType(int i) {}
@@ -201,8 +245,8 @@ public class EglBase {
}
}
- public EGLContext getContext() {
- return eglContext;
+ public Context getEglBaseContext() {
+ return new Context(eglContext);
}
public boolean hasSurface() {
@@ -324,10 +368,12 @@ public class EglBase {
// Return an EGLConfig, or die trying.
private EGLContext createEglContext(
- EGLContext sharedContext, EGLDisplay eglDisplay, EGLConfig eglConfig) {
+ Context sharedContext, EGLDisplay eglDisplay, EGLConfig eglConfig) {
int[] contextAttributes = {EGL_CONTEXT_CLIENT_VERSION, 2, EGL10.EGL_NONE};
+ EGLContext rootContext =
+ sharedContext == null ? EGL10.EGL_NO_CONTEXT : sharedContext.eglContext;
EGLContext eglContext =
- egl.eglCreateContext(eglDisplay, eglConfig, sharedContext, contextAttributes);
+ egl.eglCreateContext(eglDisplay, eglConfig, rootContext, contextAttributes);
if (eglContext == EGL10.EGL_NO_CONTEXT) {
throw new RuntimeException("Failed to create EGL context");
}
diff --git a/talk/app/webrtc/java/android/org/webrtc/EglBase14.java b/talk/app/webrtc/java/android/org/webrtc/EglBase14.java
new file mode 100644
index 0000000000..20db000a43
--- /dev/null
+++ b/talk/app/webrtc/java/android/org/webrtc/EglBase14.java
@@ -0,0 +1,281 @@
+/*
+ * libjingle
+ * Copyright 2015 Google Inc.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright notice,
+ * this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright notice,
+ * this list of conditions and the following disclaimer in the documentation
+ * and/or other materials provided with the distribution.
+ * 3. The name of the author may not be used to endorse or promote products
+ * derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO
+ * EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
+ * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+ * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
+ * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+package org.webrtc;
+
+import android.annotation.TargetApi;
+import android.graphics.SurfaceTexture;
+import android.opengl.EGL14;
+import android.opengl.EGLConfig;
+import android.opengl.EGLContext;
+import android.opengl.EGLDisplay;
+import android.opengl.EGLSurface;
+import android.view.Surface;
+
+import org.webrtc.Logging;
+
+/**
+ * Holds EGL state and utility methods for handling an EGL14 EGLContext, an EGLDisplay,
+ * and an EGLSurface.
+ */
+@TargetApi(17)
+final class EglBase14 extends EglBase {
+ private static final String TAG = "EglBase14";
+ private static final int EGL14_SDK_VERSION = android.os.Build.VERSION_CODES.JELLY_BEAN_MR1;
+ private static final int CURRENT_SDK_VERSION = android.os.Build.VERSION.SDK_INT;
+ // Android-specific extension.
+ private static final int EGL_RECORDABLE_ANDROID = 0x3142;
+
+ private EGLContext eglContext;
+ private ConfigType configType;
+ private EGLConfig eglConfig;
+ private EGLDisplay eglDisplay;
+ private EGLSurface eglSurface = EGL14.EGL_NO_SURFACE;
+
+ public static boolean isEGL14Supported() {
+ Logging.d(TAG, "SDK version: " + CURRENT_SDK_VERSION
+ + ". isEGL14Supported: " + (CURRENT_SDK_VERSION >= EGL14_SDK_VERSION));
+ return (CURRENT_SDK_VERSION >= EGL14_SDK_VERSION);
+ }
+
+ public static class Context extends EglBase.Context {
+ private final android.opengl.EGLContext egl14Context;
+
+ Context(android.opengl.EGLContext eglContext) {
+ super(null);
+ this.egl14Context = eglContext;
+ }
+ }
+
+ // Create a new context with the specified config type, sharing data with sharedContext.
+ // |sharedContext| may be null.
+ EglBase14(EglBase14.Context sharedContext, ConfigType configType) {
+ super(true /* dummy */);
+ this.configType = configType;
+ eglDisplay = getEglDisplay();
+ eglConfig = getEglConfig(eglDisplay, configType);
+ eglContext = createEglContext(sharedContext, eglDisplay, eglConfig);
+ }
+
+ // Create EGLSurface from the Android Surface.
+ @Override
+ public void createSurface(Surface surface) {
+ createSurfaceInternal(surface);
+ }
+
+ // Create EGLSurface from the Android SurfaceTexture.
+ @Override
+ public void createSurface(SurfaceTexture surfaceTexture) {
+ createSurfaceInternal(surfaceTexture);
+ }
+
+ // Create EGLSurface from either Surface or SurfaceTexture.
+ private void createSurfaceInternal(Object surface) {
+ if (!(surface instanceof Surface) && !(surface instanceof SurfaceTexture)) {
+ throw new IllegalStateException("Input must be either a Surface or SurfaceTexture");
+ }
+ checkIsNotReleased();
+ if (configType == ConfigType.PIXEL_BUFFER) {
+ Logging.w(TAG, "This EGL context is configured for PIXEL_BUFFER, but uses regular Surface");
+ }
+ if (eglSurface != EGL14.EGL_NO_SURFACE) {
+ throw new RuntimeException("Already has an EGLSurface");
+ }
+ int[] surfaceAttribs = {EGL14.EGL_NONE};
+ eglSurface = EGL14.eglCreateWindowSurface(eglDisplay, eglConfig, surface, surfaceAttribs, 0);
+ if (eglSurface == EGL14.EGL_NO_SURFACE) {
+ throw new RuntimeException("Failed to create window surface");
+ }
+ }
+
+ @Override
+ public void createDummyPbufferSurface() {
+ createPbufferSurface(1, 1);
+ }
+
+ @Override
+ public void createPbufferSurface(int width, int height) {
+ checkIsNotReleased();
+ if (configType != ConfigType.PIXEL_BUFFER) {
+ throw new RuntimeException(
+ "This EGL context is not configured to use a pixel buffer: " + configType);
+ }
+ if (eglSurface != EGL14.EGL_NO_SURFACE) {
+ throw new RuntimeException("Already has an EGLSurface");
+ }
+ int[] surfaceAttribs = {EGL14.EGL_WIDTH, width, EGL14.EGL_HEIGHT, height, EGL14.EGL_NONE};
+ eglSurface = EGL14.eglCreatePbufferSurface(eglDisplay, eglConfig, surfaceAttribs, 0);
+ if (eglSurface == EGL14.EGL_NO_SURFACE) {
+ throw new RuntimeException("Failed to create pixel buffer surface");
+ }
+ }
+
+ @Override
+ public Context getEglBaseContext() {
+ return new EglBase14.Context(eglContext);
+ }
+
+ @Override
+ public boolean hasSurface() {
+ return eglSurface != EGL14.EGL_NO_SURFACE;
+ }
+
+ @Override
+ public int surfaceWidth() {
+ final int widthArray[] = new int[1];
+ EGL14.eglQuerySurface(eglDisplay, eglSurface, EGL14.EGL_WIDTH, widthArray, 0);
+ return widthArray[0];
+ }
+
+ @Override
+ public int surfaceHeight() {
+ final int heightArray[] = new int[1];
+ EGL14.eglQuerySurface(eglDisplay, eglSurface, EGL14.EGL_HEIGHT, heightArray, 0);
+ return heightArray[0];
+ }
+
+ @Override
+ public void releaseSurface() {
+ if (eglSurface != EGL14.EGL_NO_SURFACE) {
+ EGL14.eglDestroySurface(eglDisplay, eglSurface);
+ eglSurface = EGL14.EGL_NO_SURFACE;
+ }
+ }
+
+ private void checkIsNotReleased() {
+ if (eglDisplay == EGL14.EGL_NO_DISPLAY || eglContext == EGL14.EGL_NO_CONTEXT
+ || eglConfig == null) {
+ throw new RuntimeException("This object has been released");
+ }
+ }
+
+ @Override
+ public void release() {
+ checkIsNotReleased();
+ releaseSurface();
+ detachCurrent();
+ EGL14.eglDestroyContext(eglDisplay, eglContext);
+ EGL14.eglReleaseThread();
+ EGL14.eglTerminate(eglDisplay);
+ eglContext = EGL14.EGL_NO_CONTEXT;
+ eglDisplay = EGL14.EGL_NO_DISPLAY;
+ eglConfig = null;
+ }
+
+ @Override
+ public void makeCurrent() {
+ checkIsNotReleased();
+ if (eglSurface == EGL14.EGL_NO_SURFACE) {
+ throw new RuntimeException("No EGLSurface - can't make current");
+ }
+ if (!EGL14.eglMakeCurrent(eglDisplay, eglSurface, eglSurface, eglContext)) {
+ throw new RuntimeException("eglMakeCurrent failed");
+ }
+ }
+
+ // Detach the current EGL context, so that it can be made current on another thread.
+ @Override
+ public void detachCurrent() {
+ if (!EGL14.eglMakeCurrent(
+ eglDisplay, EGL14.EGL_NO_SURFACE, EGL14.EGL_NO_SURFACE, EGL14.EGL_NO_CONTEXT)) {
+ throw new RuntimeException("eglMakeCurrent failed");
+ }
+ }
+
+ @Override
+ public void swapBuffers() {
+ checkIsNotReleased();
+ if (eglSurface == EGL14.EGL_NO_SURFACE) {
+ throw new RuntimeException("No EGLSurface - can't swap buffers");
+ }
+ EGL14.eglSwapBuffers(eglDisplay, eglSurface);
+ }
+
+ // Return an EGLDisplay, or die trying.
+ private static EGLDisplay getEglDisplay() {
+ EGLDisplay eglDisplay = EGL14.eglGetDisplay(EGL14.EGL_DEFAULT_DISPLAY);
+ if (eglDisplay == EGL14.EGL_NO_DISPLAY) {
+ throw new RuntimeException("Unable to get EGL14 display");
+ }
+ int[] version = new int[2];
+ if (!EGL14.eglInitialize(eglDisplay, version, 0, version, 1)) {
+ throw new RuntimeException("Unable to initialize EGL14");
+ }
+ return eglDisplay;
+ }
+
+ // Return an EGLConfig, or die trying.
+ private static EGLConfig getEglConfig(EGLDisplay eglDisplay, ConfigType configType) {
+ // Always RGB888, GLES2.
+ int[] configAttributes = {
+ EGL14.EGL_RED_SIZE, 8,
+ EGL14.EGL_GREEN_SIZE, 8,
+ EGL14.EGL_BLUE_SIZE, 8,
+ EGL14.EGL_RENDERABLE_TYPE, EGL14.EGL_OPENGL_ES2_BIT,
+ EGL14.EGL_NONE, 0, // Allocate dummy fields for specific options.
+ EGL14.EGL_NONE
+ };
+
+ // Fill in dummy fields based on configType.
+ switch (configType) {
+ case PLAIN:
+ break;
+ case PIXEL_BUFFER:
+ configAttributes[configAttributes.length - 3] = EGL14.EGL_SURFACE_TYPE;
+ configAttributes[configAttributes.length - 2] = EGL14.EGL_PBUFFER_BIT;
+ break;
+ case RECORDABLE:
+ configAttributes[configAttributes.length - 3] = EGL_RECORDABLE_ANDROID;
+ configAttributes[configAttributes.length - 2] = 1;
+ break;
+ default:
+ throw new IllegalArgumentException();
+ }
+
+ EGLConfig[] configs = new EGLConfig[1];
+ int[] numConfigs = new int[1];
+ if (!EGL14.eglChooseConfig(
+ eglDisplay, configAttributes, 0, configs, 0, configs.length, numConfigs, 0)) {
+ throw new RuntimeException("Unable to find RGB888 " + configType + " EGL config");
+ }
+ return configs[0];
+ }
+
+ // Return an EGLConfig, or die trying.
+ private static EGLContext createEglContext(
+ EglBase14.Context sharedContext, EGLDisplay eglDisplay, EGLConfig eglConfig) {
+ int[] contextAttributes = {EGL14.EGL_CONTEXT_CLIENT_VERSION, 2, EGL14.EGL_NONE};
+ EGLContext rootContext =
+ sharedContext == null ? EGL14.EGL_NO_CONTEXT : sharedContext.egl14Context;
+ EGLContext eglContext =
+ EGL14.eglCreateContext(eglDisplay, eglConfig, rootContext, contextAttributes, 0);
+ if (eglContext == EGL14.EGL_NO_CONTEXT) {
+ throw new RuntimeException("Failed to create EGL context");
+ }
+ return eglContext;
+ }
+}
diff --git a/talk/app/webrtc/java/android/org/webrtc/SurfaceTextureHelper.java b/talk/app/webrtc/java/android/org/webrtc/SurfaceTextureHelper.java
index 2df7716446..193ebd9676 100644
--- a/talk/app/webrtc/java/android/org/webrtc/SurfaceTextureHelper.java
+++ b/talk/app/webrtc/java/android/org/webrtc/SurfaceTextureHelper.java
@@ -39,8 +39,6 @@ import java.util.concurrent.Callable;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.TimeUnit;
-import javax.microedition.khronos.egl.EGLContext;
-
/**
* Helper class to create and synchronize access to a SurfaceTexture. The caller will get notified
* of new frames in onTextureFrameAvailable(), and should call returnTextureFrame() when done with
@@ -65,7 +63,7 @@ class SurfaceTextureHelper {
int oesTextureId, float[] transformMatrix, long timestampNs);
}
- public static SurfaceTextureHelper create(EGLContext sharedContext) {
+ public static SurfaceTextureHelper create(EglBase.Context sharedContext) {
return create(sharedContext, null);
}
@@ -74,7 +72,8 @@ class SurfaceTextureHelper {
* |handler| is non-null, the callback will be executed on that handler's thread. If |handler| is
* null, a dedicated private thread is created for the callbacks.
*/
- public static SurfaceTextureHelper create(final EGLContext sharedContext, final Handler handler) {
+ public static SurfaceTextureHelper create(final EglBase.Context sharedContext,
+ final Handler handler) {
final Handler finalHandler;
if (handler != null) {
finalHandler = handler;
@@ -105,14 +104,15 @@ class SurfaceTextureHelper {
private boolean isTextureInUse = false;
private boolean isQuitting = false;
- private SurfaceTextureHelper(EGLContext sharedContext, Handler handler, boolean isOwningThread) {
+ private SurfaceTextureHelper(EglBase.Context sharedContext,
+ Handler handler, boolean isOwningThread) {
if (handler.getLooper().getThread() != Thread.currentThread()) {
throw new IllegalStateException("SurfaceTextureHelper must be created on the handler thread");
}
this.handler = handler;
this.isOwningThread = isOwningThread;
- eglBase = new EglBase(sharedContext, EglBase.ConfigType.PIXEL_BUFFER);
+ eglBase = EglBase.create(sharedContext, EglBase.ConfigType.PIXEL_BUFFER);
eglBase.createDummyPbufferSurface();
eglBase.makeCurrent();
diff --git a/talk/app/webrtc/java/android/org/webrtc/SurfaceViewRenderer.java b/talk/app/webrtc/java/android/org/webrtc/SurfaceViewRenderer.java
index ed6e8dd2d6..9ca7a9e66f 100644
--- a/talk/app/webrtc/java/android/org/webrtc/SurfaceViewRenderer.java
+++ b/talk/app/webrtc/java/android/org/webrtc/SurfaceViewRenderer.java
@@ -153,7 +153,7 @@ public class SurfaceViewRenderer extends SurfaceView
* reinitialize the renderer after a previous init()/release() cycle.
*/
public void init(
- EGLContext sharedContext, RendererCommon.RendererEvents rendererEvents) {
+ EglBase.Context sharedContext, RendererCommon.RendererEvents rendererEvents) {
synchronized (handlerLock) {
if (renderThreadHandler != null) {
throw new IllegalStateException(getResourceName() + "Already initialized");
@@ -163,12 +163,19 @@ public class SurfaceViewRenderer extends SurfaceView
renderThread = new HandlerThread(TAG);
renderThread.start();
drawer = new GlRectDrawer();
- eglBase = new EglBase(sharedContext, EglBase.ConfigType.PLAIN);
+ eglBase = EglBase.create(sharedContext, EglBase.ConfigType.PLAIN);
renderThreadHandler = new Handler(renderThread.getLooper());
}
tryCreateEglSurface();
}
+ @Deprecated
+ // TODO(perkj): Remove when applications has been updated.
+ public void init(
+ EGLContext sharedContext, RendererCommon.RendererEvents rendererEvents) {
+ init(sharedContext != null ? new EglBase.Context(sharedContext) : null, rendererEvents);
+ }
+
/**
* Create and make an EGLSurface current if both init() and surfaceCreated() have been called.
*/
@@ -560,7 +567,7 @@ public class SurfaceViewRenderer extends SurfaceView
if (framesReceived > 0 && framesRendered > 0) {
final long timeSinceFirstFrameNs = System.nanoTime() - firstFrameTimeNs;
Logging.d(TAG, getResourceName() + "Duration: " + (int) (timeSinceFirstFrameNs / 1e6) +
- " ms. FPS: " + (float) framesRendered * 1e9 / timeSinceFirstFrameNs);
+ " ms. FPS: " + framesRendered * 1e9 / timeSinceFirstFrameNs);
Logging.d(TAG, getResourceName() + "Average render time: "
+ (int) (renderTimeNs / (1000 * framesRendered)) + " us.");
}
diff --git a/talk/app/webrtc/java/android/org/webrtc/VideoCapturerAndroid.java b/talk/app/webrtc/java/android/org/webrtc/VideoCapturerAndroid.java
index 66b4048b9d..72ef309de3 100644
--- a/talk/app/webrtc/java/android/org/webrtc/VideoCapturerAndroid.java
+++ b/talk/app/webrtc/java/android/org/webrtc/VideoCapturerAndroid.java
@@ -50,9 +50,6 @@ import java.util.Set;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.TimeUnit;
-import javax.microedition.khronos.egl.EGLContext;
-import javax.microedition.khronos.egl.EGL10;
-
// Android specific implementation of VideoCapturer.
// An instance of this class can be created by an application using
// VideoCapturerAndroid.create();
@@ -235,7 +232,7 @@ public class VideoCapturerAndroid extends VideoCapturer implements
}
public static VideoCapturerAndroid create(String name,
- CameraEventsHandler eventsHandler, EGLContext sharedEglContext) {
+ CameraEventsHandler eventsHandler, EglBase.Context sharedEglContext) {
final int cameraId = lookupDeviceName(name);
if (cameraId == -1) {
return null;
@@ -351,7 +348,7 @@ public class VideoCapturerAndroid extends VideoCapturer implements
}
private VideoCapturerAndroid(int cameraId, CameraEventsHandler eventsHandler,
- EGLContext sharedContext) {
+ EglBase.Context sharedContext) {
Logging.d(TAG, "VideoCapturerAndroid");
this.id = cameraId;
this.eventsHandler = eventsHandler;
@@ -362,8 +359,7 @@ public class VideoCapturerAndroid extends VideoCapturer implements
isCapturingToTexture = (sharedContext != null);
cameraStatistics =
new CameraStatistics(isCapturingToTexture ? 1 : videoBuffers.numCaptureBuffers);
- surfaceHelper = SurfaceTextureHelper.create(
- isCapturingToTexture ? sharedContext : EGL10.EGL_NO_CONTEXT, cameraThreadHandler);
+ surfaceHelper = SurfaceTextureHelper.create(sharedContext, cameraThreadHandler);
if (isCapturingToTexture) {
surfaceHelper.setListener(this);
}
diff --git a/talk/app/webrtc/java/android/org/webrtc/VideoRendererGui.java b/talk/app/webrtc/java/android/org/webrtc/VideoRendererGui.java
index da6e51bc29..e9e95abedf 100644
--- a/talk/app/webrtc/java/android/org/webrtc/VideoRendererGui.java
+++ b/talk/app/webrtc/java/android/org/webrtc/VideoRendererGui.java
@@ -415,10 +415,15 @@ public class VideoRendererGui implements GLSurfaceView.Renderer {
eglContextReady = eglContextReadyCallback;
}
+ @Deprecated
public static synchronized EGLContext getEGLContext() {
return eglContext;
}
+ public static synchronized EglBase.Context getEglBaseContext() {
+ return new EglBase.Context(eglContext);
+ }
+
/** Releases GLSurfaceView video renderer. */
public static synchronized void dispose() {
if (instance == null){
diff --git a/talk/app/webrtc/java/jni/androidmediadecoder_jni.cc b/talk/app/webrtc/java/jni/androidmediadecoder_jni.cc
index 4554e7b59c..fa111968f6 100644
--- a/talk/app/webrtc/java/jni/androidmediadecoder_jni.cc
+++ b/talk/app/webrtc/java/jni/androidmediadecoder_jni.cc
@@ -858,7 +858,7 @@ void MediaCodecVideoDecoderFactory::SetEGLContext(
render_egl_context_ = NULL;
} else {
jclass j_egl_context_class =
- FindClass(jni, "javax/microedition/khronos/egl/EGLContext");
+ FindClass(jni, "org/webrtc/EglBase$Context");
if (!jni->IsInstanceOf(render_egl_context_, j_egl_context_class)) {
ALOGE << "Wrong EGL Context.";
jni->DeleteGlobalRef(render_egl_context_);
diff --git a/talk/app/webrtc/java/jni/androidmediaencoder_jni.cc b/talk/app/webrtc/java/jni/androidmediaencoder_jni.cc
index 37eeb6ccc5..92ec4f05cf 100644
--- a/talk/app/webrtc/java/jni/androidmediaencoder_jni.cc
+++ b/talk/app/webrtc/java/jni/androidmediaencoder_jni.cc
@@ -278,7 +278,7 @@ MediaCodecVideoEncoder::MediaCodecVideoEncoder(
*j_media_codec_video_encoder_class_,
"initEncode",
"(Lorg/webrtc/MediaCodecVideoEncoder$VideoCodecType;"
- "IIIILjavax/microedition/khronos/egl/EGLContext;)Z");
+ "IIIILorg/webrtc/EglBase$Context;)Z");
j_get_input_buffers_method_ = GetMethodID(
jni,
*j_media_codec_video_encoder_class_,
@@ -1123,7 +1123,7 @@ void MediaCodecVideoEncoderFactory::SetEGLContext(
egl_context_ = NULL;
} else {
jclass j_egl_context_class =
- FindClass(jni, "javax/microedition/khronos/egl/EGLContext");
+ FindClass(jni, "org/webrtc/EglBase$Context");
if (!jni->IsInstanceOf(egl_context_, j_egl_context_class)) {
ALOGE << "Wrong EGL Context.";
jni->DeleteGlobalRef(egl_context_);
diff --git a/talk/app/webrtc/java/jni/classreferenceholder.cc b/talk/app/webrtc/java/jni/classreferenceholder.cc
index 13883bedbe..ea56c25e5d 100644
--- a/talk/app/webrtc/java/jni/classreferenceholder.cc
+++ b/talk/app/webrtc/java/jni/classreferenceholder.cc
@@ -79,6 +79,7 @@ ClassReferenceHolder::ClassReferenceHolder(JNIEnv* jni) {
LoadClass(jni, "org/webrtc/VideoCapturerAndroid");
LoadClass(jni, "org/webrtc/VideoCapturerAndroid$NativeObserver");
LoadClass(jni, "org/webrtc/EglBase");
+ LoadClass(jni, "org/webrtc/EglBase$Context");
LoadClass(jni, "org/webrtc/NetworkMonitor");
LoadClass(jni, "org/webrtc/MediaCodecVideoEncoder");
LoadClass(jni, "org/webrtc/MediaCodecVideoEncoder$OutputBufferInfo");
diff --git a/talk/app/webrtc/java/jni/peerconnection_jni.cc b/talk/app/webrtc/java/jni/peerconnection_jni.cc
index 194f9ff98c..560b61cf3c 100644
--- a/talk/app/webrtc/java/jni/peerconnection_jni.cc
+++ b/talk/app/webrtc/java/jni/peerconnection_jni.cc
@@ -1338,12 +1338,40 @@ JOW(void, PeerConnectionFactory_nativeSetVideoHwAccelerationOptions)(
OwnedFactoryAndThreads* owned_factory =
reinterpret_cast<OwnedFactoryAndThreads*>(native_factory);
+ // TODO(perkj): In order to not break existing applications we need to
+ // check if |local_egl_context| or |remote_egl_context| is an
+ // EGL10 context. If so, create an EGLBase10.EGL10Context instead.
+ // Remove this once existing applications has been updated.
+ jobject local_eglbase_context = local_egl_context;
+ jobject remote_eglbase_context = remote_egl_context;
+
+ jclass j_egl10_context_class =
+ FindClass(jni, "javax/microedition/khronos/egl/EGLContext");
+ jclass j_eglbase_context_class =
+ FindClass(jni, "org/webrtc/EglBase$Context");
+
+ jmethodID j_eglbase_context_ctor = GetMethodID(
+ jni, j_eglbase_context_class,
+ "<init>", "(Ljavax/microedition/khronos/egl/EGLContext;)V");
+ if (local_egl_context != nullptr &&
+ jni->IsInstanceOf(local_egl_context, j_egl10_context_class)) {
+ local_eglbase_context = jni->NewObject(
+ j_eglbase_context_class, j_eglbase_context_ctor,
+ local_egl_context);
+ }
+ if (remote_egl_context != nullptr &&
+ jni->IsInstanceOf(remote_egl_context, j_egl10_context_class)) {
+ remote_eglbase_context = jni->NewObject(
+ j_eglbase_context_class, j_eglbase_context_ctor,
+ remote_egl_context);
+ }
+
MediaCodecVideoEncoderFactory* encoder_factory =
static_cast<MediaCodecVideoEncoderFactory*>
(owned_factory->encoder_factory());
if (encoder_factory) {
LOG(LS_INFO) << "Set EGL context for HW encoding.";
- encoder_factory->SetEGLContext(jni, local_egl_context);
+ encoder_factory->SetEGLContext(jni, local_eglbase_context);
}
MediaCodecVideoDecoderFactory* decoder_factory =
@@ -1351,7 +1379,7 @@ JOW(void, PeerConnectionFactory_nativeSetVideoHwAccelerationOptions)(
(owned_factory->decoder_factory());
if (decoder_factory) {
LOG(LS_INFO) << "Set EGL context for HW decoding.";
- decoder_factory->SetEGLContext(jni, remote_egl_context);
+ decoder_factory->SetEGLContext(jni, remote_eglbase_context);
}
#endif
}
diff --git a/talk/app/webrtc/java/jni/surfacetexturehelper_jni.cc b/talk/app/webrtc/java/jni/surfacetexturehelper_jni.cc
index 65c1737268..8fd42a0a58 100644
--- a/talk/app/webrtc/java/jni/surfacetexturehelper_jni.cc
+++ b/talk/app/webrtc/java/jni/surfacetexturehelper_jni.cc
@@ -47,7 +47,7 @@ SurfaceTextureHelper::SurfaceTextureHelper(JNIEnv* jni,
GetStaticMethodID(jni,
*j_surface_texture_helper_class_,
"create",
- "(Ljavax/microedition/khronos/egl/EGLContext;)"
+ "(Lorg/webrtc/EglBase$Context;)"
"Lorg/webrtc/SurfaceTextureHelper;"),
egl_shared_context)),
j_return_texture_method_(GetMethodID(jni,
diff --git a/talk/app/webrtc/java/src/org/webrtc/MediaCodecVideoEncoder.java b/talk/app/webrtc/java/src/org/webrtc/MediaCodecVideoEncoder.java
index 47886effd7..f10df98f9f 100644
--- a/talk/app/webrtc/java/src/org/webrtc/MediaCodecVideoEncoder.java
+++ b/talk/app/webrtc/java/src/org/webrtc/MediaCodecVideoEncoder.java
@@ -45,8 +45,6 @@ import java.util.Arrays;
import java.util.List;
import java.util.concurrent.CountDownLatch;
-import javax.microedition.khronos.egl.EGLContext;
-
// Java-side of peerconnection_jni.cc:MediaCodecVideoEncoder.
// This class is an implementation detail of the Java PeerConnection API.
@TargetApi(19)
@@ -270,7 +268,7 @@ public class MediaCodecVideoEncoder {
}
boolean initEncode(VideoCodecType type, int width, int height, int kbps, int fps,
- EGLContext sharedContext) {
+ EglBase.Context sharedContext) {
final boolean useSurface = sharedContext != null;
Logging.d(TAG, "Java initEncode: " + type + " : " + width + " x " + height +
". @ " + kbps + " kbps. Fps: " + fps + ". Encode from texture : " + useSurface);
@@ -323,7 +321,7 @@ public class MediaCodecVideoEncoder {
format, null, null, MediaCodec.CONFIGURE_FLAG_ENCODE);
if (useSurface) {
- eglBase = new EglBase(sharedContext, EglBase.ConfigType.RECORDABLE);
+ eglBase = EglBase.create(sharedContext, EglBase.ConfigType.RECORDABLE);
// Create an input surface and keep a reference since we must release the surface when done.
inputSurface = mediaCodec.createInputSurface();
eglBase.createSurface(inputSurface);
diff --git a/talk/libjingle.gyp b/talk/libjingle.gyp
index 4f32102232..0a272c7be9 100755
--- a/talk/libjingle.gyp
+++ b/talk/libjingle.gyp
@@ -149,6 +149,7 @@
'app/webrtc/java/android/org/webrtc/CameraEnumerationAndroid.java',
'app/webrtc/java/android/org/webrtc/CameraEnumerator.java',
'app/webrtc/java/android/org/webrtc/EglBase.java',
+ 'app/webrtc/java/android/org/webrtc/EglBase14.java',
'app/webrtc/java/android/org/webrtc/GlRectDrawer.java',
'app/webrtc/java/android/org/webrtc/GlShader.java',
'app/webrtc/java/android/org/webrtc/GlUtil.java',
diff --git a/webrtc/examples/androidapp/src/org/appspot/apprtc/PeerConnectionClient.java b/webrtc/examples/androidapp/src/org/appspot/apprtc/PeerConnectionClient.java
index 77e78c4a22..1bdbc3b6fc 100644
--- a/webrtc/examples/androidapp/src/org/appspot/apprtc/PeerConnectionClient.java
+++ b/webrtc/examples/androidapp/src/org/appspot/apprtc/PeerConnectionClient.java
@@ -17,6 +17,7 @@ import org.appspot.apprtc.AppRTCClient.SignalingParameters;
import org.appspot.apprtc.util.LooperExecutor;
import org.webrtc.CameraEnumerationAndroid;
import org.webrtc.DataChannel;
+import org.webrtc.EglBase;
import org.webrtc.IceCandidate;
import org.webrtc.Logging;
import org.webrtc.MediaCodecVideoEncoder;
@@ -465,7 +466,7 @@ public class PeerConnectionClient {
}
Log.d(TAG, "Opening camera: " + cameraDeviceName);
videoCapturer = VideoCapturerAndroid.create(cameraDeviceName, null,
- peerConnectionParameters.captureToTexture ? renderEGLContext : null);
+ peerConnectionParameters.captureToTexture ? new EglBase.Context(renderEGLContext) : null);
if (videoCapturer == null) {
reportError("Failed to open camera");
return;