2012-03-15 4 views
9

J'ai une application qui prend un aperçu de la caméra, effectue une fonction de traitement d'image de base sur chaque image (par exemple détection de bord, changement de couleur, etc.) et affiche le cadre modifié à l'écran. "temps réél". Similaire à l'application "Paper Camera" dans Android Market.Android: traitement d'image en temps réel

Un résumé de mon approche:

1: Créer deux vues qui se chevauchent dans un framelayout:

A SurfaceView passer à Camera.setPreviewDisplay(). (Passing null empêcherait l'aperçu de la caméra de démarrer sur certains appareils - opencv utilisé pour faire cela avant Android 4.0?).

Une classe appelée "LiveView" qui étend View et implémente Camera.PreviewCallBack. Cette vue reçoit des trames de la caméra et affiche la trame après modification (par exemple détection de bord). Cette vue est au dessus de SurfaceView.

2: J'appelle Camera.setPreviewCallbackWithBuffer(), de sorte que les cadres sont envoyés à mon LiveView

3: Dans le onPreviewFrame() du LiveView, je prends la trame capturée (octet []) , convertir YUV à RVB et exécuter des fonctions de traitement d'image, et appeler postInvalidate() (le traitement de conversion et de l'image YUV2RGB sont réalisées en code natif)

4: méthode de LiveView, dans le OnDraw() créer un bitmap de l'image RGB modifiée (octet []), et dessine l'image bitmap sur canvas.

Cela fonctionne (entre 5fps et 10fps sur divers appareils), mais je voudrais entendre comment d'autres ont abordé ce problème, et comment il pourrait être amélioré. En particulier:

  • Est-ce que j'aurais des performances en étendant GLSurfaceView plutôt que View pour créer la classe LiveView?
  • Il semble très inefficace d'avoir deux surfaces mises à jour pour chaque image. Y a-t-il une alternative?
  • Pour ce faire plus efficacement, devrais-je accéder à la caméra au niveau natif? - Je crois qu'OpenCV adopte cette approche?

Merci beaucoup

Répondre

4

J'ai aussi fait quelque chose comme ça. Ce que je fais est d'étendre la vue de la caméra. Je ne pense pas que la vue de la caméra soit mise à jour à chaque image, mais récupérée. Et seule la vue que vous avez modifiée devrait être mise à jour. OpenCv fait un meilleur travail que la caméra native. Après avoir importé org.opencv.highgui.VideoCapture, vous pouvez accéder directement à la caméra à l'aide:

VideoCapture camera; 
camera.retrieve(mGrayMat, Highgui.CV_CAP_ANDROID_GREY_FRAME); 

pour convertir mGrayMat à mRgbaMat: (org.opencv.imgproc.Imgproc)

Imgproc.cvtColor(mGrayMat, mRgbaMat, Imgproc.COLOR_GRAY2BGRA, 4);