[英]Camera preview on SurfaceView is stretched despite setting sizes
I'm trying to make the camera preview correctly show up on a SurfaceView
. 我试图使相机预览正确显示在SurfaceView
。 However, despite trying to getSupportedPictureSizes()
and setting both pictureSize
and previewSize
to one of the values from the list, the preview is still very, very stretched. 但是,尽管尝试获取getSupportedPictureSizes()
并将pictureSize
和previewSize
都设置为列表中的值之一,但预览仍然非常非常拉伸。
I decided I wanted the size to be 1280 by 720 pixels, and I've set this value everywhere (and again, it's on the getSupportedPictureSizes()
, as well as getSupportedPreviewSizes()
) 我决定我希望尺寸为1280 x 720像素,并且在所有位置都设置了此值(同样,它在getSupportedPictureSizes()
和getSupportedPreviewSizes()
)
I have browsed all of the Stackoverflow posts on the issue, and I can't seem to get it solved. 我已经浏览了有关此问题的所有Stackoverflow帖子,但似乎无法解决。 Any help is appreciated. 任何帮助表示赞赏。
surfaceCreated() for my SurfaceHolder: 我的SurfaceHolder的surfaceCreated():
public void surfaceCreated(SurfaceHolder holder)
{
Camera.Parameters parameters = camera.getParameters();
parameters.setPictureSize(1280, 720);
parameters.setPreviewSize(1280, 720);
Log.d("SurfaceView", surfaceView.getWidth() + ", " + surfaceView.getHeight());
camera.setParameters(parameters);
camera.setDisplayOrientation(90);
previewCamera();
}
SurfaceView design XML: SurfaceView设计XML:
<SurfaceView
android:layout_width="1280px"
android:layout_height="720px"
android:layout_gravity="center_horizontal"
android:id="@+id/surfaceViewCamera"
android:layout_alignParentBottom="true"
android:layout_centerHorizontal="true"/>
Entire activity class: 整个活动类别:
package org.ownzone.security_droid;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.hardware.Camera;
import android.os.AsyncTask;
import android.os.Bundle;
import android.support.v7.app.ActionBarActivity;
import android.util.Log;
import android.view.SurfaceHolder;
import android.view.SurfaceView;
import android.view.WindowManager;
import android.widget.CompoundButton;
import android.widget.Switch;
import android.widget.TextView;
public class AuthenticatedActivity extends ActionBarActivity
{
private ServerConnection sc = ServerConnection.getServerConnectionInstance();
private boolean active;
private Camera camera;
private SurfaceView surfaceView;
private SurfaceHolder surfaceHolder;
private boolean isPreviewRunning;
@Override
protected void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_authenticated);
active = false;
isPreviewRunning = false;
TextView headline = (TextView) findViewById(R.id.textViewHeadLine);
headline.setText(getIntent().getStringExtra("cardholder") + " authenticated");
Switch activeSwitch = (Switch) findViewById(R.id.switchActive);
activeSwitch.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener()
{
@Override
public void onCheckedChanged(CompoundButton buttonView, boolean isChecked)
{
active = isChecked;
}
});
surfaceView = (SurfaceView) findViewById(R.id.surfaceViewCamera);
camera = Camera.open();
for (Camera.Size size : camera.getParameters().getSupportedPictureSizes())
{
Log.d("Size", size.width + ", " + size.height);
}
surfaceHolder = surfaceView.getHolder();
surfaceHolder.addCallback(surfaceHolderCallback);
//camera.setPreviewDisplay(surfaceView.getHolder());
//camera.startPreview();
getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);
}
private void takePhoto()
{
camera.takePicture(shutterCallback, rawPictureCallback, jpegPictureCallback);
}
SurfaceHolder.Callback surfaceHolderCallback = new SurfaceHolder.Callback()
{
@Override
public void surfaceCreated(SurfaceHolder holder)
{
Camera.Parameters parameters = camera.getParameters();
parameters.setPictureSize(1280, 720);
parameters.setPreviewSize(1280, 720);
Log.d("SurfaceView", surfaceView.getWidth() + ", " + surfaceView.getHeight());
camera.setParameters(parameters);
camera.setDisplayOrientation(90);
previewCamera();
}
@Override
public void surfaceChanged(SurfaceHolder holder, int format, int width, int height)
{
}
@Override
public void surfaceDestroyed(SurfaceHolder holder)
{
}
};
public void previewCamera()
{
try
{
camera.setPreviewDisplay(surfaceHolder);
camera.startPreview();
isPreviewRunning = true;
}
catch (Exception e)
{
Log.d("AuthenticatedActivity", "Cannot start preview", e);
}
}
Camera.ShutterCallback shutterCallback = new Camera.ShutterCallback()
{
public void onShutter()
{
}
};
Camera.PictureCallback rawPictureCallback = new Camera.PictureCallback()
{
public void onPictureTaken(byte[] data, Camera camera)
{
}
};
Camera.PictureCallback jpegPictureCallback = new Camera.PictureCallback()
{
public void onPictureTaken(byte[] data, Camera camera)
{
Bitmap bitmapPicture = BitmapFactory.decodeByteArray(data, 0, data.length);
Bitmap correctBmp = Bitmap.createBitmap(bitmapPicture, 0, 0, bitmapPicture.getWidth(), bitmapPicture.getHeight(), null, true);
}
};
}
Without a screenshot, this is a bit of a guess, but I'd suspect your call to setDisplayOrientation. 没有屏幕截图,这有点猜测,但是我怀疑您对setDisplayOrientation的调用。
A hardcoded value there may work for a single device or a set of devices, but in general, you need to take into account several factors - see the documentation here: http://developer.android.com/reference/android/hardware/Camera.html#setDisplayOrientation(int) 此处的硬编码值可能适用于单个设备或一组设备,但是通常,您需要考虑多个因素-请参见此处的文档: http : //developer.android.com/reference/android/hardware/ Camera.html#setDisplayOrientation(int)
And in general, on most devices (but not all!), if you have a landscape app on a phone, you'll end up with calling setDisplayOrientation(0), not 90. 通常,在大多数设备上(但不是全部!),如果手机上有风景应用程序,则最终会调用setDisplayOrientation(0)而不是90。
Is your app landscape- or portrait-oriented (or flexible?)? 您的应用是横向还是纵向(还是灵活的?)? And a screenshot would be very helpful in ruling out various issues. 屏幕截图对于排除各种问题非常有帮助。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.