opencv4android--RGB2HSV

opencv4android–RGB2HSV

最近上班,工作强度不大,自己就找点东西学,正好碰见之前一个朋友面试,面试官出了一个题,自己闲着无聊也就研究研究,学习些新的东西。,先看一下题目。

题目中关键点估计就是opencv的hsv转换,说实话我当是也不知道那是什么东西,百度稍微了解下大致有了个思路。

  1. 调用相机拍照
  2. 将拍好的照片截图
  3. 配置opencv使用环境
  4. 调用opencv的方法

总体说来应该就这四步,前两步不难虽然我不会写,但是会百度啊,使用opencv就得自己研究了!

拍照加截图

百度了一圈,试了好几种方案,只有这个成功了,就用这个吧!思路是先调用相机,拍照返回后调用系统自带的截图,确定大小之后返回确定之后的uri。具体代码如下:
初始化一些常量

String path = getSDCardPath();
    File file = new File(path + "/temp.jpg");
    imageUri = Uri.fromFile(file);
    File cropFile = new File(getSDCardPath() + "/temp_crop.jpg");
    imageCropUri = Uri.fromFile(cropFile);

getSDcardPath方法

public static String getSDCardPath() {
    String cmd = "cat /proc/mounts";
    Runtime run = Runtime.getRuntime();
    try {
        Process p = run.exec(cmd);
        BufferedInputStream in = new BufferedInputStream(p.getInputStream());
        BufferedReader inBr = new BufferedReader(new InputStreamReader(in));

        String lineStr;
        while ((lineStr = inBr.readLine()) != null) {
            if (lineStr.contains("sdcard")
                    && lineStr.contains(".android_secure")) {
                String[] strArray = lineStr.split(" ");
                if (strArray != null && strArray.length >= 5) {
                    String result = strArray[1].replace("/.android_secure",
                            "");
                    return result;
                }
            }
            if (p.waitFor() != 0 && p.exitValue() == 1) {
            }
        }
        inBr.close();
        in.close();
    } catch (Exception e) {

        return Environment.getExternalStorageDirectory().getPath();
    }

    return Environment.getExternalStorageDirectory().getPath();
}

启动相机

  Intent  intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);//action is capture
    intent.putExtra("return-data", false);
    intent.putExtra(MediaStore.EXTRA_OUTPUT, imageUri);
    intent.putExtra("outputFormat", Bitmap.CompressFormat.JPEG.toString());
    intent.putExtra("noFaceDetection", true);
    startActivityForResult(intent, RESULT_CAMERA_ONLY);

启动截图

    private void cropImg(Uri imageUri) {
    Intent intent = new Intent("com.android.camera.action.CROP");
    intent.setDataAndType(imageUri, "image/*");
    intent.putExtra("crop", "true");
    intent.putExtra("aspectX", 1);
    intent.putExtra("aspectY", 1);
    intent.putExtra("outputX", 700);
    intent.putExtra("outputY", 700);
    intent.putExtra("return-data", false);
    intent.putExtra(MediaStore.EXTRA_OUTPUT, imageCropUri);
    intent.putExtra("outputFormat", Bitmap.CompressFormat.JPEG.toString());
    intent.putExtra("noFaceDetection", true);
    startActivityForResult(intent, RESULT_CAMERA_CROP_PATH_RESULT);

}

onActivityResult回调

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    super.onActivityResult(requestCode, resultCode, data);
    Log.d("TAG","onActivityResult");
    if(resultCode!=RESULT_OK){
        Toast.makeText(MainActivity.this,"ActivityResult resultCode error",Toast.LENGTH_SHORT).show();
        return;
    }
    switch (requestCode) {
        case RESULT_CAMERA_ONLY://拍照成功回调
            cropImg(imageUri);
            break;
        case RESULT_CAMERA_CROP_PATH_RESULT://截图成功回调
            Bundle extras = data.getExtras();
            if (extras != null) {
                try {
                    mBitmap = BitmapFactory.decodeStream(getContentResolver().openInputStream(imageCropUri));
                    mImage.setImageBitmap(mBitmap);
                } catch (Exception e) {
                    e.printStackTrace();
                }
            }
    }
}

主要的就是上面这些代码,先调用相机之后返回调用截图之后在返回,imageview加载由本地url生成的bitmap图像,这样钱两步就完成了。

配置opencv环境

opencv下载地址:https://pan.baidu.com/s/1geNBqSV
本来是csdn的不过有点大就上传不了,目前版本是3.1,最新的。

不懂是什么东西的可以去百度。当然我百度完了也不明白是什么东西,大概了解是做图像处理的,反正特别XX就是了,先说一下集成环境,网上有很多方案不过都是很久以前的了,参考很多资料之后决定用这位大神的,简单明了。步步到位。http://www.cnblogs.com/tail/p/4618476.html
最后一步测试成功什么的就不用了,咱们直接继续。

简单使用

网上很多都说需要什么NDK调用,也不会啊,不过上面的大神提到了在opencv3.0之后就可以非常简单的使用了,可以去参考sample中第一个例子。代码

@Override
protected void onResume() {
    {
        super.onResume();
        if (!OpenCVLoader.initDebug()) {
            Log.d("TAG", "Internal OpenCV library not found. Using OpenCV Manager for initialization");
            OpenCVLoader.initAsync(OpenCVLoader.OPENCV_VERSION_3_0_0, this, mLoaderCallback);
        } else {
            Log.d("TAG", "OpenCV library found inside package. Using it!");
            mLoaderCallback.onManagerConnected(LoaderCallbackInterface.SUCCESS);
        }
    }
}

复制粘贴之后会发现mLoaderCallback报错,因为没有嘛,还需要创建一个成员变量。

 private BaseLoaderCallback mLoaderCallback = new BaseLoaderCallback(this) {

    @Override
    public void onManagerConnected(int status) {
        switch (status) {
            case LoaderCallbackInterface.SUCCESS:
            {
                Log.i("TAG", "OpenCV loaded successfully");

                /* Now enable camera view to start receiving frames */

            } break;
            default:
            {
                super.onManagerConnected(status);
            } break;
        }
    }
};

运行的时候要是成功打印log了,说明之前的配置都是没有问题的。
接下来就是简单实用,因为要将RGB转化为HSV,简单百度下,没找到完成的例子,发现一个改变图片灰度的例子,于是尝试了一下。说一下具体步骤:

  1. 创建两个bitmap,一个用来保存变化之前的图像,一个用来保存变化之后的图像
  2. 创建两个图像对应的矩阵
  3. 使用opencv方法变成灰度图
  4. imageview显示

    Mat rgbMat=new Mat();//rgb矩阵
    Mat grayMat=new Mat();//gray矩阵
    //灰度之后的Bitmap,mBitmap为RgbBitmap,之前已经赋过值了。
    grayBitmap=Bitmap.createBitmap(mBitmap.getWidth(),mBitmap.getHeight(), Bitmap.Config.RGB_565);
    Utils.bitmapToMat(mBitmap,rgbMat);//将图像转换为矩阵
    Imgproc.cvtColor(rgbMat,grayMat,Imgproc.COLOR_RGB2GRAY);//矩阵变化
    Utils.matToBitmap(grayMat,grayBitmap);//将矩阵转化为图像
    mImage.setImageBitmap(grayBitmap);//显示图像
    

    在敲的过程中可以发现,在矩阵变化的时候有很多种变化的方式,由于要使用RGB2HSV,正好也有这种模式就把COLOR_RGB2GRAY变成COLOR_RGB2HSV,也不知道这么写对不对,反正是有变化,已经让朋友给那个面试的人看了效果,准备再深入研究研究opencv,确实很强大啊!效果图:

可能有点卡,将就吧,等面试的那个人看看是不是想要的效果。

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值