Рисование в SurfaceView - холст является нулевым при вызове holder.lockCanvas () в surfaceCreated () - PullRequest
0 голосов
/ 01 июня 2018

Я нашел несколько сообщений, связанных с моим вопросом, но ни одна из них не решила его.Я пытаюсь это снова.Надеюсь, мой пример достаточно прост, и я не забыл ничего важного.У меня есть Fragment и внутренний класс CameraPreview, полученный из SurfaceView и реализующий SurfaceHolder.Callback.Чего я хочу добиться, так это рисовать поверх предварительного просмотра камеры, который отображается в полноэкранном режиме с помощью CameraPreview.Я думал, что вызов canvas = holder.lockCanvas() в surfaceCreated() даст мне Canvas для последующего рисования, но mCanvas всегда null, если вызывать после setPreviewDisplay() и startPreview().Если попытаться создать холст перед этими двумя вызовами, я получу холст, но сразу после этого произойдет сбой приложения.

Может кто-нибудь объяснить, почему?

public class CameraFragment extends Fragment {
    final static String TAG = "CameraFragment";

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
                         Bundle savedInstanceState) {
        View view = inflater.inflate(R.layout.fragment_native_camera, container, false);
        // Create our Preview view and set it as the content of our activity.
        safeCameraOpenInView(view);

        return view;
    }

    public void safeCameraOpenInView(View view) {
        FrameLayout preview;
        Camera camera = null;

        try {
            camera = Camera.open();
        } catch (Exception e) {
            e.printStackTrace();
        }

        if (camera != null) {
            mPreview = new CameraPreview(getActivity().getApplicationContext(), camera);
            if (view.findViewById(R.id.camera_preview) != null) {
                preview = (FrameLayout) view.findViewById(R.id.camera_preview);
                preview.addView(mPreview);
                Log.d(TAG, "view found and set");
            } else Log.d(TAG, "FrameLayout is null");
        } 
    }

    class CameraPreview extends SurfaceView implements SurfaceHolder.Callback {

        private Camera mCamera;
        private Canvas mCanvas;

        public CameraPreview(Context context, Camera camera) {
            super(context);
            // not sure the following is necessary
            setWillNotDraw(false);
            // do camera initialisation etc.
            mCamera = camera;
            // ...
        }

        public void surfaceCreated(SurfaceHolder holder) {
            // here's the problem: If I initialize the canvas
            // before setting the preview display and start previewing
            // I get a canvas but the app crashes immediately after
            // If I request the canvas afterwards it's simply null
            mCamera.setPreviewDisplay(holder);
            mCamera.startpreview();
            mCanvas = holder.lockCanvas();
            // mCanvas is null
            Log.d(TAG, "canvas: " + mCanvas);
        }
    }
}
...