我需要两个摄像头previews在我的应用程序。但是,Android摄像头可以给只有一个preVIEW的时间。有没有什么办法可以流水线/复制preVIEW另一种观点?我碰到这个问题,How建立在Android的使用一台摄像机的多镜头或preVIEW他说,
I need two camera previews in my app. However, android camera can give only one preview at a time. Is there any way to pipeline/copy that preview to another view? I came across this question How to create multi lenses or preview using one camera in Android and he says that
在Android 3.0或更高版本,您可以使用set previewTexture方法来管preVIEW数据转换成一个OpenGL纹理,然后你就可以渲染到多个四边形的GLSurfaceView或等价的。
不过,我不知道如何来呈现多个四边形的 GLSurfaceView
。我需要支持Android 4.0+。但我不希望使用preVIEW框架由preVIEW回调。它会导致显著延迟。任何帮助将是AP preciated。谢谢!
But I have no idea how to render that to multiple quads in GLSurfaceView
.I need to support android 4.0+. But I don't want to use preview frame from preview callback. It causes significant delay. Any help would be appreciated. Thanks!!
下面是我的$ C $下单preVIEW
Here is my code for single preview
activity_main.xml
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@android:color/black"
tools:context=".MainActivity" >
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="horizontal"
android:weightSum="10" >
<TextureView
android:id="@+id/textureView1"
android:layout_width="0dp"
android:layout_height="match_parent"
android:layout_weight="5" />
<TextureView
android:id="@+id/textureView2"
android:layout_width="0dp"
android:layout_height="match_parent"
android:layout_weight="5" />
</LinearLayout>
</RelativeLayout>
MainActivity.java
MainActivity.java
public class MainActivity extends Activity implements SurfaceTextureListener{
private Camera mCamera;
private TextureView mTextureView1;
private TextureView mTextureView2;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mTextureView1 = (TextureView) findViewById(R.id.textureView1);
mTextureView2 = (TextureView) findViewById(R.id.textureView2);
mTextureView1.setSurfaceTextureListener(this);
}
@Override
public void onSurfaceTextureAvailable(SurfaceTexture surface, int width,
int height) {
try {
mCamera = Camera.open(getCameraId());
mCamera.setPreviewTexture(surface);
CameraInfo cameraInfo = new CameraInfo();
Camera.getCameraInfo(getCameraId(), cameraInfo);
setCameraDisplayOrientation(this, getCameraId(), mCamera);
mCamera.startPreview();
} catch (Exception e) {
e.printStackTrace();
}
}
@Override
public boolean onSurfaceTextureDestroyed(SurfaceTexture surface) {
try {
mCamera.stopPreview();
mCamera.release();
} catch (Exception e) {
e.printStackTrace();
}
return true;
}
@Override
public void onSurfaceTextureSizeChanged(SurfaceTexture surface, int width,
int height) {
}
@Override
public void onSurfaceTextureUpdated(SurfaceTexture surface) {
}
}
输出:
Output:
将相机preVIEW到的 表面纹理。这需要在摄像机的输出,并使其可用作GLES质地
Start by sending the camera preview to a SurfaceTexture instead of a Surface associated with a View. That takes the output of the camera and makes it available for use as a GLES texture.
然后,而不是有两个 TextureViews
,只呈现2质感的四边形与GLES,每个占据一半的单一视图。这比呈现两种不同的表面(只有一个EGL方面操心)更容易。如果你还没有使用OpenGL ES合作之前,可以有一定的学习曲线。
Then, instead of having two TextureViews
, just render two textured quads with GLES, each of which occupies half of a single View. This is easier than rendering to two different surfaces (only one EGL context to worry about). If you haven't worked with OpenGL ES before there can be a bit of a learning curve.
您需要的碎片可以在 Grafika 被发现。例如,考虑连续拍摄和展会+捕捉摄像头的活动。直接将相机输出到表面纹理
和渲染两次。对于这些,这是一次在屏幕上,一旦到视频连接codeR的投入,但它同样的想法。如果你看一下硬件缩放锻炼,你可以看到它的块传输带纹理的四边形反弹在屏幕上;可以使用此作为如何设置大小和四元的位置的例子。
The pieces you need can be found in Grafika. Consider for example the "Continuous capture" and "Show + capture camera" activities. Both direct the camera output to a SurfaceTexture
and render it twice. For these, it's once to the screen and once to the input of a video encoder, but it's the same idea. If you look at "Hardware scaler exerciser" you can see it blitting a textured quad that bounces around the screen; you can use this as an example of how to set the size and position of the quad.
还有双德code,这是使用一对 TextureViews
以显示两个去codeD电影并排侧。你不想做它 - 它是从两个不同的源接收内容,不显示两次单一来源
There's also "Double decode", which is using a pair of TextureViews
to show two decoded movies side-by-side. You don't want to do what it does -- it's receiving content from two different sources, not showing a single source twice.
在各种活动中使用GLES与 TextureView
, SurfaceView
和 GLSurfaceView
。每个视图类型,有独特的优势和局限性。
The various activities use GLES with TextureView
, SurfaceView
, and GLSurfaceView
. Each view type comes with unique benefits and limitations.
更新:新(ER比这个答案),纹理从相机的活动可能是最接近你想要什么。它发出的摄像头preVIEW到表面纹理,并演示了如何移动,缩放,旋转,并通过与GLES使得它放大图像。
Update: The new(er than this answer) "texture from camera" activity is probably the closest to what you want. It sends the camera preview to a SurfaceTexture and demonstrates how to move, resize, rotate, and zoom the image by rendering it with GLES.