我有一个简单的程序,可以将Camera
的预览绘制成SurfaceView
。我要做的是使用onPreviewFrame
方法,每次将新帧绘制到SurfaceView
时调用该方法,以便执行应该使用的invalidate
方法调用onDraw
方法。实际上,正在调用onDraw
方法,但没有打印任何内容(我猜相机预览会覆盖我正在尝试绘制的文本)。
这是我拥有的SurfaceView
子类的简化版本:
public class Superficie extends SurfaceView implements SurfaceHolder.Callback {
SurfaceHolder mHolder;
public Camera camera;
Superficie(Context context) {
super(context);
mHolder = getHolder();
mHolder.addCallback(this);
mHolder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS);
}
public void surfaceCreated(final SurfaceHolder holder) {
camera = Camera.open();
try {
camera.setPreviewDisplay(holder);
camera.setPreviewCallback(new PreviewCallback() {
public void onPreviewFrame(byte[] data, Camera arg1) {
invalidar();
}
});
} catch (IOException e) {}
}
public void invalidar(){
invalidate();
}
public void surfaceChanged(SurfaceHolder holder, int format, int w, int h) {
Camera.Parameters parameters = camera.getParameters();
parameters.setPreviewSize(w, h);
camera.setParameters(parameters);
camera.startPreview();
}
@Override
public void draw(Canvas canvas) {
super.draw(canvas);
// nothing gets drawn :(
Paint p = new Paint(Color.RED);
canvas.drawText("PREVIEW", canvas.getWidth() / 2,
canvas.getHeight() / 2, p);
}
}
答案 0 :(得分:84)
SurfaceView
可能不像常规View
那样有效。
相反,请执行以下操作:
SurfaceView
放入
FrameLayout
或RelativeLayout
in
你的布局XML文件,因为两者都有
那些允许堆叠小部件
Z轴View
类FrameLayout
或。{的孩子
RelativeLayout
,但有它出现
在SurfaceView
这会导致您的自定义View
课程浮动在SurfaceView
之上。
See here for a sample project将用于视频播放的SurfaceView
上方的图层弹出面板分层。
答案 1 :(得分:17)
尝试从setWillNotDraw(false)
致电surfaceCreated
:
public void surfaceCreated(SurfaceHolder holder) {
try {
setWillNotDraw(false);
mycam.setPreviewDisplay(holder);
mycam.startPreview();
} catch (Exception e) {
e.printStackTrace();
Log.d(TAG,"Surface not created");
}
}
@Override
protected void onDraw(Canvas canvas) {
canvas.drawRect(area, rectanglePaint);
Log.w(this.getClass().getName(), "On Draw Called");
}
并从invalidate
致电onTouchEvent
:
public boolean onTouch(View v, MotionEvent event) {
invalidate();
return true;
}
答案 2 :(得分:1)
我认为在SurfaceView的draw方法中执行任何操作之前,应先调用super.draw()
方法。