android 目标跟踪动画,Android调用Opencv3.0.0实现对运动目标的跟踪

package

com.example.opencv_open_camera_vedio;import

java.util.ArrayList;import

java.util.List;import

org.opencv.android.BaseLoaderCallback;import

org.opencv.android.CameraBridgeViewBase;import

org.opencv.android.CameraBridgeViewBase.CvCameraViewFrame;import

org.opencv.android.CameraBridgeViewBase.CvCameraViewListener2;import

org.opencv.android.LoaderCallbackInterface;import

org.opencv.android.OpenCVLoader;import

org.opencv.core.Core;import

org.opencv.core.CvType;import

org.opencv.core.Mat;import

org.opencv.core.MatOfFloat;import

org.opencv.core.MatOfInt;import

org.opencv.core.Rect;import

org.opencv.core.RotatedRect;import

org.opencv.core.Scalar;import

org.opencv.core.TermCriteria;import

org.opencv.imgproc.Imgproc;import

org.opencv.samples.colorblobdetect.R;import

org.opencv.video.Video;import

android.app.Activity;import

android.os.Bundle;import

android.view.MotionEvent;import

android.view.View;import

android.view.View.OnClickListener;import

android.view.View.OnTouchListener;import

android.view.Window;import

android.view.WindowManager;import

android.widget.Button;import

android.widget.SeekBar;import

android.widget.SeekBar.OnSeekBarChangeListener;import

android.widget.Toast;public class MyTracker extends

Activity implements

OnTouchListener,CvCameraViewListener2 {//

公共模块private CameraBridgeViewBase

mOpenCvCameraView;private Scalar

mColor;private Mat mRgba;//

跟踪模块private boolean mIsColorSelected =

false;private int winWidth = 130;private

MatOfFloat rangesH, rangesS, rangesV;//

HSV限定值范围private MatOfInt chansH, chansS, chansV;//

分别代表h、s、v通道private int H_Min = 0, H_Max =

180;private int S_Min = 0, S_Max =

180;private int V_Min = 0, V_Max =

180;private Mat mHist;private RotatedRect

mRect;private Mat mHue;private Rect

mTrackWindow;private Mat

mHueImage;private

List planes;private MatOfInt

histSize;private Mat backproject;private

ArrayList images;private MatOfInt moi;private

MatOfFloat mof;private TermCriteria term;private SeekBar HminBar,

HmaxBar;private SeekBar SminBar, SmaxBar;private SeekBar VminBar,

VmaxBar;private SeekBar trackBox;// 转换摄像头private boolean chgCam =

false;private Button chg_camBtn;private BaseLoaderCallback

mLoaderCallback = new BaseLoaderCallback(this) {@Overridepublic

void onManagerConnected(int status) {switch (status) {case

LoaderCallbackInterface.SUCCESS:

{mOpenCvCameraView.enableView();mOpenCvCameraView.setOnTouchListener(MyTracker.this);}break;default:

{super.onManagerConnected(status);}break;}}};public Mat

onCameraFrame(CvCameraViewFrame inputFrame) {mRgba =

inputFrame.rgba();if (mIsColorSelected) {// 获取hsv颜色空间if (mHueImage

== null)mHueImage = new Mat(mRgba.size(),

mRgba.type());Imgproc.cvtColor(mRgba, mHueImage,

Imgproc.COLOR_RGB2HSV);//

获取hsv中的hue分量Core.extractChannel(mHueImage, mHue, 0);rangesH = new

MatOfFloat(H_Min, H_Max);rangesS = new MatOfFloat(S_Min,

S_Max);rangesV = new MatOfFloat(V_Min,

V_Max);planes.add(mHueImage);// 得到直方图// Imgproc.calcHist(planes,

chans0, new Mat(), mHist, histSize,//

ranges);Imgproc.calcHist(planes, chansH, new Mat(), mHist,

histSize,rangesH);Imgproc.calcHist(planes, chansS, new Mat(),

mHist, histSize,rangesS);Imgproc.calcHist(planes, chansV, new

Mat(), mHist, histSize,rangesV);// 直方图标准化Core.normalize(mHist,

mHist, 0, 255, Core.NORM_MINMAX);//

反向投影图images.add(mHue);Imgproc.calcBackProject(images, moi, mHist,

backproject, mof, 1.0);// 获取跟踪框并用椭圆轮廓画出来mRect =

Video.CamShift(backproject, mTrackWindow,

term);Imgproc.ellipse(mRgba, mRect, mColor);//

通知系统释放内存,但不是实时的,所以并没什么用?System.gc();} else {mHue = new

Mat(mRgba.size(), CvType.CV_8UC1);backproject = mHue;}if (mRect !=

null) {int y = (int) mRect.center.y - winWidth / 2;int x = (int)

mRect.center.x - winWidth / 2;mTrackWindow.x = x;mTrackWindow.y =

y;mTrackWindow.width = winWidth;mTrackWindow.height =

winWidth;}return mRgba;}public void onCameraViewStarted(int width,

int height) {// 公共模块mColor = new Scalar(255, 0, 0);//

跟踪模块mTrackWindow = new Rect();mHist = new Mat();planes = new

ArrayList();// 设置hsv通道chansH = new MatOfInt(0);chansS = new

MatOfInt(1);chansV = new MatOfInt(2);histSize = new

MatOfInt(10);images = new ArrayList();//

用H分量作为跟踪对象.其余两个做限定条件提高跟踪准确率moi = chansH;mof = new MatOfFloat(0,

180);term = new TermCriteria(TermCriteria.COUNT, 200, 1);}public

boolean onTouch(View v, MotionEvent event) {int cols =

mRgba.cols();int rows = mRgba.rows();int xOffset =

(mOpenCvCameraView.getWidth() - cols) / 2;int yOffset =

(mOpenCvCameraView.getHeight() - rows) / 2;int x = (int)

event.getX() - xOffset;int y = (int) event.getY() - yOffset;if ((x

< 0) || (y < 0) || (x

> cols) || (y > rows))return

false;mTrackWindow = new Rect(x - winWidth / 2, y - winWidth / 2,

winWidth,winWidth);mIsColorSelected = true;return false; // don't

need subsequent touch events}@Overridepublic void onCreate(Bundle

savedInstanceState)

{super.onCreate(savedInstanceState);requestWindowFeature(Window.FEATURE_NO_TITLE);getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);setContentView(R.layout.color_blob_detection_surface_view);mOpenCvCameraView

= (CameraBridgeViewBase)

findViewById(R.id.color_blob_detection_activity_surface_view);mOpenCvCameraView.setCvCameraViewListener(this);mOpenCvCameraView.setCameraIndex(CameraBridgeViewBase.CAMERA_ID_FRONT);//

mOpenCvCameraView.setCameraIndex(CameraBridgeViewBase.CAMERA_ID_BACK);//

获取滚动条,通过设置滑动条监听改变v通道值的范围MyseekbarListener sbListen = new

MyseekbarListener();// HHminBar = (SeekBar)

findViewById(R.id.HseekBarMin);HmaxBar = (SeekBar)

findViewById(R.id.HseekBarMax);HminBar.setOnSeekBarChangeListener(sbListen);HmaxBar.setOnSeekBarChangeListener(sbListen);//

SSminBar = (SeekBar) findViewById(R.id.SseekBarMin);SmaxBar =

(SeekBar)

findViewById(R.id.SseekBarMax);SminBar.setOnSeekBarChangeListener(sbListen);SmaxBar.setOnSeekBarChangeListener(sbListen);//

VVminBar = (SeekBar) findViewById(R.id.VseekBarMin);VmaxBar =

(SeekBar)

findViewById(R.id.VseekBarMax);VminBar.setOnSeekBarChangeListener(sbListen);VmaxBar.setOnSeekBarChangeListener(sbListen);//

可设置跟踪框的大小trackBox = (SeekBar)

findViewById(R.id.seekBarTracBox);trackBox.setOnSeekBarChangeListener(sbListen);//

摄像头转换按钮MyOnClickListen click = new MyOnClickListen();chg_camBtn =

(Button)

findViewById(R.id.chg_cam);chg_camBtn.setOnClickListener(click);}//

按钮监听器class MyOnClickListen implements OnClickListener

{@Overridepublic void onClick(View v) {if (v.equals(chg_camBtn))

{if (chgCam)

{mOpenCvCameraView.setCameraIndex(CameraBridgeViewBase.CAMERA_ID_FRONT);}

else

{mOpenCvCameraView.setCameraIndex(CameraBridgeViewBase.CAMERA_ID_BACK);}chgCam

= !chgCam;}}}// 创建一个滑动条监听内部类class MyseekbarListener implements

OnSeekBarChangeListener {@Overridepublic void

onProgressChanged(SeekBar sb, int progress, boolean arg2) {// Hif

(sb.equals(HminBar)) {if (progress < H_Max)H_Min =

progress;else

{Toast.makeText(getApplicationContext(),"H分量设置错误:H_Min必须小于H_Max",

Toast.LENGTH_SHORT).show();}}if (sb.equals(HmaxBar)) {if (progress

> H_Min)H_Max = progress;else

{Toast.makeText(getApplicationContext(),"H分量设置错误:H_Min必须小于H_Max",

Toast.LENGTH_SHORT).show();}}// Sif (sb.equals(SminBar)) {if

(progress < S_Max)S_Min = progress;else

{Toast.makeText(getApplicationContext(),"S分量设置错误:S_Min必须小于S_Max",

Toast.LENGTH_SHORT).show();}}if (sb.equals(SmaxBar)) {if (progress

> S_Min)S_Max = progress;else

{Toast.makeText(getApplicationContext(),"S分量设置错误:S_Min必须小于S_Max",

Toast.LENGTH_SHORT).show();}}// Vif (sb.equals(VminBar)) {if

(progress < V_Max)V_Min = progress;else

{Toast.makeText(getApplicationContext(),"V分量设置错误:V_Min必须小于V_Max",

Toast.LENGTH_SHORT).show();}}if (sb.equals(VmaxBar)) {if (progress

> V_Min)V_Max = progress;else

{Toast.makeText(getApplicationContext(),"V分量设置错误:V_Min必须小于V_Max",

Toast.LENGTH_SHORT).show();}}if (sb.equals(trackBox)) {if (progress

> 0)winWidth = progress;}}@Overridepublic void

onStartTrackingTouch(SeekBar arg0) {}@Overridepublic void

onStopTrackingTouch(SeekBar arg0) {}}@Overridepublic void onPause()

{super.onPause();if (mOpenCvCameraView !=

null)mOpenCvCameraView.disableView();}@Overridepublic void

onResume()

{super.onResume();OpenCVLoader.initAsync(OpenCVLoader.OPENCV_VERSION_2_4_9,

this,mLoaderCallback);}public void onDestroy()

{super.onDestroy();if (mOpenCvCameraView !=

null)mOpenCvCameraView.disableView();}public void

onCameraViewStopped() {mRgba.release();}}

你可能感兴趣的:(android,目标跟踪动画)