Shu*_*uri 0 android surfaceview android-camera
我的SurfaceView
实现Camera.PreviewCallback
&的子类SurfaceHolder.Callback
.
private SurfaceHolder mHolder;
private Camera mCamera;
private final FPSCounter fpscounter = new FPSCounter();
public MySurfaceView(Context context, AttributeSet attrs) {
super(context, attrs);
mHolder = getHolder();
mHolder.addCallback(this);
}
@Override
public void onPreviewFrame(byte[] data, Camera camera) {
fpscounter.logFrame();
Log.d("fps", String.valueOf(fpscounter.getLastFrameCount()));
}
@Override
public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
synchronized (this) {
mCamera.stopPreview();
Camera.Parameters parameters = mCamera.getParameters();
parameters.setRecordingHint(true);
parameters.setPreviewFormat(ImageFormat.NV21);
mCamera.setParameters(parameters);
try {
mCamera.setPreviewDisplay(holder);
mCamera.setPreviewCallback(this);
mCamera.startPreview();
} catch (IOException e) {
e.printStackTrace();
}
}
}
@Override
public void surfaceCreated(SurfaceHolder holder) {
synchronized (this) {
setWillNotDraw(false);
mCamera = Camera.open();
}
}
@Override
public void surfaceDestroyed(SurfaceHolder holder) {
synchronized (this) {
try {
if (mCamera != null) {
mCamera.stopPreview();
mCamera.release();
}
} catch (Exception e) {
Log.e("cam error", e.getMessage());
}
}
}
Run Code Online (Sandbox Code Playgroud)
和FPSCounter
班级
private long startTime;
private int frames, lastFrameCount;
public void logFrame() {
frames++;
if (System.nanoTime() - startTime >= 1000000000) {
lastFrameCount = frames;
frames = 0;
startTime = System.nanoTime();
}
}
public int getLastFrameCount() {
return lastFrameCount;
}
Run Code Online (Sandbox Code Playgroud)
尽管相机预览非常流畅,但该onPreviewFrame()
方法每秒仅调用约5次.为什么不是每个帧都要调用它?
您可能已经想到了它:Camera.setPreviewCallback()对垃圾收集器施加了太大的压力.您可以使用Camera.setPreviewCallbackWithBuffer()代替.
其次,如果onPreviewFrame()到达主(UI)线程,那么它会与触摸,布局甚至渲染等UI事件竞争单个CPU时间.要在单独的线程上保持onPreviewFrame(),您应该在辅助Looper线程上打开()相机,请参阅例如/sf/answers/1340810691/.
第三,即使在这种情况下,预览回调也是序列化的.如果fpscounter.logFrame()
并且Log().d
采用X毫秒,那么FPS将不会超过1000/X.
归档时间: |
|
查看次数: |
3687 次 |
最近记录: |