#はじめに
AndroidでOpenCV3.2を利用してソーベルフィルタを実装した。
JavaのOpenCVでは思うようにできない部分がいくつかあったのでメモ
#実行環境など
##ソフトウェア
Windows 10 Home 64bit
Android Studio 2.2.3
OpenCV 3.2
##デバッグ端末
Nexus 5x (Android 7.1.1)
#OpenCVの準備
以下参照
OpenCV for AndroidをAndroid Studioに導入するメモ
#ポイント
ただの一方向のソーベルフィルタだとつまらないので、グレースケールに変換してからフィルタ処理を行わずあえてRGB成分に分割してそれぞれの色でX方向とy方向のフィルタ処理を行い二乗平均平方根をとった後で、三つの成分の値なかでの最大値を最終的な画素値とした。
#メモ
C++のOpenCVだと
matC = matA +matB;
みたいな書き方ができるけどJavaのOpenCVではできない
#コード
private Bitmap sobel(Bitmap bitmap) {
bitmap = bitmap.copy(Bitmap.Config.ARGB_8888, true);
Mat mat = new Mat();
Mat matR = new Mat();
Mat matG = new Mat();
Mat matB = new Mat();
Utils.bitmapToMat(bitmap, mat);
Core.extractChannel(mat, matR, 0);
myFiltering(matR);
Core.extractChannel(mat, matG, 1);
myFiltering(matG);
Core.extractChannel(mat, matB, 2);
myFiltering(matB);
matMax3(matB, matG, matR, matB);
Utils.matToBitmap(matB, bitmap);
return bitmap;
}
private void myFiltering(Mat src){
Mat matX = new Mat();
Mat matY = new Mat();
Imgproc.GaussianBlur(src, src, new Size(3, 3), 0, 0);
Imgproc.Sobel(src, matX, src.depth(), 0, 1);
Imgproc.Sobel(src, matY, src.depth(), 1, 0);
matRMS(matX, matY, src);
}
private void matRMS(Mat src1, Mat src2, Mat dst) {
int size = (int) (src1.total() * src1.channels());
byte[] temp1 = new byte[size];
byte[] temp2 = new byte[size];
byte[] temp3 = new byte[size];
src1.get(0, 0, temp1);
src2.get(0, 0, temp2);
for (int i = 0; i < size; i++) {
temp3[i] = (byte)Math.sqrt((temp1[i] * temp1[i] + temp2[i] * temp2[i]) / 2);
}
dst.put(0, 0, temp3);
}
private void matMax3(Mat src1, Mat src2, Mat src3, Mat dst) {
int size = (int) (src1.total() * src1.channels());
byte[] temp1 = new byte[size];
byte[] temp2 = new byte[size];
byte[] temp3 = new byte[size];
byte[] temp4 = new byte[size];
src1.get(0, 0, temp1);
src2.get(0, 0, temp2);
src3.get(0, 0, temp3);
for (int i = 0; i < size; i++) {
temp4[i] = chooseBig(chooseBig(temp1[i], temp2[i]), temp3[i]);
}
dst.put(0, 0, temp4);
}
private byte chooseBig(byte a, byte b) {
if(b > a) {
return b;
}else {
return a;
}
}
#GitHubのリンク
GUIの都合上AsyncTaskを用いて実装した。
こちら
#apk
ビルドしたapkのリンク
こちら
※Android端末にOpenCV Managerのインストールが必要です。インストールされていない場合はGoogle Play Storeへ飛ばされます
※インストールは自己責任で
#参考
OpenCVとVisual C++による画像処理と認識(7)----- いろいろなエッジ検出フィルタを使用する -----