Camera2 API如何实现预览画面填满整个视图?

4

我正在使用谷歌示例中的Camera2Basic案例(https://github.com/googlesamples/android-Camera2Basic),以在片段中显示摄像机预览。 该片段包含一个RelativeLayout和一个自定义的AutoFitTextureView。您可以在上面的链接中找到后者。我已经调整了布局,使预览居中,并删除了控制按钮:

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:id="@+id/camera_rel">

    <uk.co.deluxe_digital.messngr.AutoFitTextureView
    android:id="@+id/texture"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_centerInParent="true"
    android:layout_centerHorizontal="true"
    android:layout_centerVertical="true" />

</RelativeLayout>

我有三个片段在ViewPager中显示。我对Camera2BasicFragment进行了一些小改动,使其成为android.support.v4.app.Fragment,以便与我的ViewPager配合使用并删除按钮。
我想让相机预览填满整个屏幕。通过拉伸预览图像可以实现这一点。但这不是我想要的。有人知道一种缩放预览或TextureView的方法,使预览的高度与容器匹配,即使两侧被裁剪也不会影响。我希望它能够填满视图并保持纵横比。这意味着两侧的预览会被裁剪,但这没关系。
这是我目前的情况: current incorrect display of camera preview FloatingActionButton负责捕获图像。它位于主父活动上。
即使您能指导我正确的方向来解决这个问题,那也会是一个巨大的帮助!
2个回答

5

我曾经遇到同样的问题,我使用了Google的例子并将其应用到我的项目中。为了解决这个问题,我在configuredTransform方法中添加了一个else选项,以正确缩放垂直位置。

private void configureTransform(int viewWidth, int viewHeight) {
    Activity activity = getActivity();
    if (null == mTextureView || null == mPreviewSize || null == activity) {
        return;
    }
    int rotation = activity.getWindowManager().getDefaultDisplay().getRotation();
    Matrix matrix = new Matrix();
    RectF viewRect = new RectF(0, 0, viewWidth, viewHeight);
    RectF bufferRect = new RectF(0, 0, mPreviewSize.getHeight(), mPreviewSize.getWidth());
    float centerX = viewRect.centerX();
    float centerY = viewRect.centerY();
    if (Surface.ROTATION_90 == rotation || Surface.ROTATION_270 == rotation) {
        bufferRect.offset(centerX - bufferRect.centerX(), centerY - bufferRect.centerY());
        matrix.setRectToRect(viewRect, bufferRect, Matrix.ScaleToFit.FILL);
        float scale = Math.max(
                (float) viewHeight / mPreviewSize.getHeight(),
                (float) viewWidth / mPreviewSize.getWidth());
        matrix.postScale(scale, scale, centerX, centerY);
        matrix.postRotate(90 * (rotation - 2), centerX, centerY);
    } else if (Surface.ROTATION_180 == rotation) {
        matrix.postRotate(180, centerX, centerY);
    } /*I added this else*/ else {
        bufferRect.offset(centerX - bufferRect.centerX(), centerY - bufferRect.centerY());
        matrix.setRectToRect(viewRect, bufferRect, Matrix.ScaleToFit.FILL);
        float scale = Math.max(
                (float) viewHeight / mPreviewSize.getHeight(),
                (float) viewWidth / mPreviewSize.getWidth());
        matrix.postScale(scale, scale, centerX, centerY);
        matrix.postRotate(0, centerX, centerY);

    }
    mTextureView.setTransform(matrix);
}

1
AutoFitTextureView扩展了TextureView以保持宽高比。如果您想填充整个屏幕,只需使用:
<TextureView
    android:id="@+id/texture"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
 />

我已经尝试过这个,但它拉伸了预览,使其失真。我正在寻找一种方法将其缩放以适应屏幕同时保持纵横比。 - user2216919
然后你应该设置转换矩阵:texturePreview.setTransform(matrix);如何操作的示例: https://android.googlesource.com/platform/packages/apps/Camera2/+/android-6.0.1_r63/src/com/android/camera/TextureViewHelper.java - Sergey Voloshyn
我切换到了TextureView,然后计算出它向上拉伸了多少。接着我按照同样的比例拉伸了宽度。目前一切都很好。谢谢! - user2216919
我的问题也是一样。 - Mohsin

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接