I developed an Document scanner. I am using opencv for image processing. It works perfectly with C++ code, but i want that in java so i converted it. But not detecting document properly when i am using java code.
Actually cant implement this line in java
sort(contours.begin(), contours.end(), compareContourAreas);
C++ code
using namespace cv;
using namespace std;
extern "C"
bool compareContourAreas(std::vector<cv::Point> contour1,
std::vector<cv::Point> contour2) {
double i = fabs(contourArea(cv::Mat(contour1)));
double j = fabs(contourArea(cv::Mat(contour2)));
return (i > j);
}
extern "C"
JNIEXPORT jobject JNICALL
Java_com_example_setlmint_setlmint_CameraScreen_doWithMat(JNIEnv *env, jobject instance,
jlong matAddrGr, jlong matAddrRgba) {
Mat &image = *(Mat *) matAddrRgba;
Rect bounding_rect;
Mat thr(image.rows, image.cols, CV_8UC1);
cvtColor(image, thr, CV_BGR2GRAY); //Convert to gray
threshold(thr, thr, 150, 255, THRESH_BINARY + THRESH_OTSU); //Threshold the gray
vector<vector<Point> > contours; // Vector for storing contour
vector<Vec4i> hierarchy;
findContours(thr, contours, hierarchy, CV_RETR_CCOMP,
CV_CHAIN_APPROX_SIMPLE); // Find the contours in the image
sort(contours.begin(), contours.end(),
compareContourAreas); //Store the index of largest contour
bounding_rect = boundingRect((const _InputArray &) contours[0]);
rectangle(image, bounding_rect, Scalar(250, 250, 250) , 3);
jclass rectClass = env->FindClass("org/opencv/core/Rect");
jmethodID rectCtorID = env->GetMethodID(rectClass, "<init>", "(IIII)V");
return env->NewObject(rectClass, rectCtorID, bounding_rect.x, bounding_rect.y, bounding_rect.width, bounding_rect.height);
}
Converted into Java
Rect bounding_rect;
@Override
public Mat onCameraFrame(CameraBridgeViewBase.CvCameraViewFrame inputFrame) {
mRgba = inputFrame.rgba();
mGray = inputFrame.gray();
mRgbaT = mRgba.t();
Core.flip(mRgba.t(), mRgbaT, 1);
Imgproc.resize(mRgbaT, mRgbaT, mRgba.size());
Imgproc.cvtColor( mRgba, mGray, Imgproc.COLOR_BGR2GRAY );
Imgproc.threshold( mGray, mGray, 155, 255, Imgproc.THRESH_BINARY + Imgproc.THRESH_OTSU );
List<MatOfPoint> contours = new ArrayList<MatOfPoint>();
Mat hierarchy = new Mat();
Imgproc.findContours( mGray, contours, hierarchy, Imgproc.RETR_CCOMP, Imgproc.CHAIN_APPROX_SIMPLE );
int index= 0 ;
double maxim = 0;
for (int contourIdx = 0; contourIdx<contours.size();contourIdx++){
double temp;
temp = contourArea( contours.get(contourIdx) );
if (maxim<temp){
maxim=temp;
index=contourIdx;
}
}
bounding_rect = Imgproc.boundingRect( contours.get( index ) );
Imgproc.rectangle( mRgbaT, new Point( bounding_rect.x, bounding_rect.y ), new Point( bounding_rect.x + bounding_rect.height, bounding_rect.y + bounding_rect.width ), new Scalar( 250, 250, 250 ), 5 );
return mRgbaT;
}
onCamera Function when using C++ code
public Mat onCameraFrame(CameraBridgeViewBase.CvCameraViewFrame inputFrame) {
mRgba = inputFrame.rgba();
mGray = inputFrame.gray();
mRgbaT = mRgba.t();
Core.flip(mRgba.t(), mRgbaT, 1);
Imgproc.resize(mRgbaT, mRgbaT, mRgba.size());
mBoundingRect = doWithMat(mGray.getNativeObjAddr(), mRgbaT.getNativeObjAddr());
return mRgbaT;
}