Android教程網
  1. 首頁
  2. Android 技術
  3. Android 手機
  4. Android 系統教程
  5. Android 游戲
 Android教程網 >> Android技術 >> 關於Android編程 >> OpenCV使用Harris算法實現角點檢測

OpenCV使用Harris算法實現角點檢測

編輯:關於Android編程

效果圖

效果圖

原圖

源碼

KqwOpenCVFeaturesDemo

角點是兩條邊緣的交點或者在局部鄰域中有多個顯著邊緣方向的點。Harris角點檢測是一種在角點檢測中最常見的技術。

Harris角點檢測器在圖像上使用滑動窗口計算亮度的變化。

封裝

這裡用到了RxJava。主要是因為圖片處理是耗時操作,會阻塞線程,為了防止界面卡頓,這裡使用RxJava進行了線程切換。

/**
 * Harris角點檢測
 *
 * @param bitmap 要檢測的圖片
 */
public void harris(Bitmap bitmap) {
    if (null != mSubscriber)
        Observable
                .just(bitmap)
                // 檢測邊緣
                .map(new Func1() {
                    @Override
                    public Mat call(Bitmap bitmap) {
                        Mat grayMat = new Mat();
                        Mat cannyEdges = new Mat();

                        // Bitmap轉為Mat
                        Mat src = new Mat(bitmap.getHeight(), bitmap.getWidth(), CvType.CV_8UC4);
                        Utils.bitmapToMat(bitmap, src);

                        // 原圖置灰
                        Imgproc.cvtColor(src, grayMat, Imgproc.COLOR_BGR2GRAY);
                        // Canny邊緣檢測器檢測圖像邊緣
                        Imgproc.Canny(grayMat, cannyEdges, 10, 100);

                        return cannyEdges;
                    }
                })
                // Harris對角檢測
                .map(new Func1() {

                    @Override
                    public Bitmap call(Mat cannyEdges) {
                        Mat corners = new Mat();
                        Mat tempDst = new Mat();

                        // 找出角點
                        Imgproc.cornerHarris(cannyEdges, tempDst, 2, 3, 0.04);

                        // 歸一化Harris角點的輸出
                        Mat tempDstNorm = new Mat();
                        Core.normalize(tempDst, tempDstNorm, 0, 255, Core.NORM_MINMAX);
                        Core.convertScaleAbs(tempDstNorm, corners);

                        // 在新的圖像上繪制角點
                        Random r = new Random();
                        for (int i = 0; i < tempDstNorm.cols(); i++) {
                            for (int j = 0; j < tempDstNorm.rows(); j++) {
                                double[] value = tempDstNorm.get(j, i);
                                if (value[0] > 150) {
                                    Core.circle(corners, new Point(i, j), 5, new Scalar(r.nextInt(255), 2));
                                }
                            }
                        }

                        // Mat轉Bitmap
                        Bitmap processedImage = Bitmap.createBitmap(corners.cols(), corners.rows(), Bitmap.Config.ARGB_8888);
                        Utils.matToBitmap(corners, processedImage);

                        return processedImage;
                    }
                })
                .subscribeOn(Schedulers.io())
                .observeOn(AndroidSchedulers.mainThread())
                .subscribe(mSubscriber);
}

使用

// 圖片特征提取的工具類
mFeaturesUtil = new FeaturesUtil(new Subscriber() {
    @Override
    public void onCompleted() {
        // 圖片處理完成
        dismissProgressDialog();
    }

    @Override
    public void onError(Throwable e) {
        // 圖片處理異常
        dismissProgressDialog();
    }

    @Override
    public void onNext(Bitmap bitmap) {
        // 獲取到處理後的圖片
        mImageView.setImageBitmap(bitmap);
    }
});

// Harris角點檢測
mFeaturesUtil.harris(mSelectImage);
  1. 上一頁:
  2. 下一頁:
熱門文章
閱讀排行版
Copyright © Android教程網 All Rights Reserved