Метод onDraw () расширенного SurfaceView никогда не вызывался

Я пытаюсь изменить SurfaceView, который я использую для предварительного просмотра камеры, чтобы отобразить наложенный квадрат. Однако метод onDraw расширенного SurfaceView никогда не вызывается.

Вот источник:

public class CameraPreviewView extends SurfaceView {

    protected final Paint rectanglePaint = new Paint();

    public CameraPreviewView(Context context, AttributeSet attrs) {
        super(context, attrs);
        rectanglePaint.setARGB(255, 200, 0, 0);
        rectanglePaint.setStyle(Paint.Style.FILL);
        rectanglePaint.setStrokeWidth(2);
    }

    @Override
    protected void onDraw(Canvas canvas){
        canvas.drawRect(new Rect(10,10,200,200), rectanglePaint);
        Log.w(this.getClass().getName(), "On Draw Called");
    }
}

public class CameraPreview extends Activity implements SurfaceHolder.Callback{

    private SurfaceHolder holder;
    private Camera camera;

    @Override
    protected void onCreate(Bundle savedInstanceState){
        super.onCreate(savedInstanceState);

        // We remove the status bar, title bar and make the application fullscreen
        requestWindowFeature(Window.FEATURE_NO_TITLE);
        getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,
                WindowManager.LayoutParams.FLAG_FULLSCREEN);

        // We set the content view to be the layout we made
        setContentView(R.layout.camera_preview);

        // We register the activity to handle the callbacks of the SurfaceView
        CameraPreviewView surfaceView = (CameraPreviewView) findViewById(R.id.camera_surface);
        holder = surfaceView.getHolder();

        holder.addCallback(this);
        holder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS);
    }

    public void surfaceChanged(SurfaceHolder holder, int format, int width,
            int height) {

        Camera.Parameters params = camera.getParameters();

        params.setPreviewSize(width, height);
        camera.setParameters(params);

        try {
            camera.setPreviewDisplay(holder);
        } catch (IOException e) {
            e.printStackTrace();
        }

        camera.startPreview();

    }

    public void surfaceCreated(SurfaceHolder holder) {
        camera = Camera.open();
    }

    public void surfaceDestroyed(SurfaceHolder holder) {
        camera.stopPreview();
        camera.release();   
    }


}

4 ответа

Решение

Нашел это на android-разработчиках гугл группы. Вы просто должны добавить:

setWillNotDraw(false)

Для конструктора. Теперь, если бы кто-то мог объяснить мне, почему, это было бы очень ценно.

Незначительная коррекция:

Добавление setWillNotDraw(false) в конструктор вызовет сбои, поскольку базовый объект Surface еще не создан.

Вместо этого поместите оператор setWillNotDraw(false) в метод surfaceCreated(). Это задерживает вызов до тех пор, пока не появится реальный объект для работы, и работает правильно.

(и большое спасибо пользователям, которые разместили это решение, оно решило большую проблему для меня)

Ромэн Гай объяснил это:

Для эффективности макеты не получают их onDraw() метод называется. Чтобы включить его, позвоните setWillNotDrawEnabled(false) (или установите эквивалентный атрибут XML в false.)

Основываясь на всех приведенных выше комментариях, я использовал:

Добавьте setWillNotDraw(false) в событие onAttachedToWindow().

@Override protected void onAttachedToWindow() { super.onAttachedToWindow(); setWillNotDraw(false); }

и это сработало.

Другие вопросы по тегам