#endif
#include <deque>
+#include <algorithm>
+
using namespace std;
#undef NDEBUG
#include <assert.h>
+
+
class Sampler {
public:
CvMat *im;
CvMat *perim;
CvPoint fcoord(float fx, float fy);
CvPoint coord(int ix, int iy);
- Sampler() {}
Sampler(CvMat *_im, CvPoint _o, CvPoint _c, CvPoint _cc);
uint8 getpixel(int ix, int iy);
int isinside(int x, int y);
int hasbars();
void timing();
CvMat *extract();
+ Sampler():im(0),perim(0){}
+ ~Sampler(){}
};
class code { // used in this file only
uint8 Sampler::getpixel(int ix, int iy)
{
CvPoint pt = coord(ix, iy);
- // printf("%d,%d\n", pt.x, pt.y);
- return *cvPtr2D(im, pt.y, pt.x);
+ if ((0 <= pt.x) && (pt.x < im->cols) && (0 <= pt.y) && (pt.y < im->rows))
+ return *cvPtr2D(im, pt.y, pt.x);
+ else
+ return 0;
}
int Sampler::isinside(int x, int y)
{
- CvPoint2D32f fp;
- fp.x = (float)x;
- fp.y = (float)y;
- return cvPointPolygonTest(perim, fp, 0) < 0;
+ CvPoint2D32f pt;
+ pt.x = (float)x;
+ pt.y = (float)y;
+ if ((0 <= pt.x) && (pt.x < im->cols) && (0 <= pt.y) && (pt.y < im->rows))
+ return cvPointPolygonTest(perim, pt, 0) < 0;
+ else
+ return 0;
}
int Sampler::overlap(Sampler &other)
return r;
}
-deque <DataMatrixCode> cvFindDataMatrix(CvMat *im)
+deque <CvDataMatrixCode> cvFindDataMatrix(CvMat *im)
{
#if CV_SSE2
int r = im->rows;
__m128 iscand = _mm_and_ps(_mm_cmpgt_ps(cmag, Kf(30)), _mm_cmpgt_ps(ccmag, Kf(30)));
iscand = _mm_and_ps(iscand, _mm_cmpgt_ps(_mm_mul_ps(_mm_min_ps(cmag, ccmag), Kf(1.1f)), _mm_max_ps(cmag, ccmag)));
- iscand = _mm_and_ps(iscand, _mm_cmplt_ps(_mm_abs_ps(dot), Kf(0.25f)));
+ iscand = _mm_and_ps(iscand, _mm_cmplt_ps(_mm_abs_ps(dot), Kf(0.25f)));
unsigned int CV_DECL_ALIGNED(16) result[4];
_mm_store_ps((float*)result, iscand);
Sampler sa(im, o, ptc[j], ptcc[k]);
for (i = 0; i < codes.size(); i++) {
if (sa.overlap(codes[i].sa))
+ {
+ cvReleaseMat(&sa.perim);
goto endo;
+ }
}
if (codes.size() > 0) {
printf("searching for more\n");
codes.push_back(cc);
goto endo;
}
+
+ cvReleaseMat(&sa.perim);
}
}
endo: ; // end search for this o
}
- cvFree(&thresh);
- cvFree(&vecpic);
- cvFree(&vc);
- cvFree(&vcc);
- cvFree(&cxy);
- cvFree(&ccxy);
+ cvReleaseMat(&thresh);
+ cvReleaseMat(&vecpic);
+ cvReleaseMat(&vc);
+ cvReleaseMat(&vcc);
+ cvReleaseMat(&cxy);
+ cvReleaseMat(&ccxy);
- deque <DataMatrixCode> rc;
+ deque <CvDataMatrixCode> rc;
for (i = 0; i < codes.size(); i++) {
- DataMatrixCode cc;
+ CvDataMatrixCode cc;
strcpy(cc.msg, codes[i].msg);
cc.original = codes[i].original;
cc.corners = codes[i].sa.perim;
}
return rc;
#else
- deque <DataMatrixCode> rc;
+ deque <CvDataMatrixCode> rc;
return rc;
#endif
}
+
+#include <opencv2/imgproc/imgproc.hpp>
+#include <opencv2/highgui/highgui.hpp>
+
+namespace cv
+{
+namespace
+{
+ struct CvDM2DM_transform
+ {
+ DataMatrixCode operator()(CvDataMatrixCode& cvdm)
+ {
+ DataMatrixCode dm;
+ std::memcpy(dm.msg,cvdm.msg,sizeof(cvdm.msg));
+ dm.original = cv::Mat(cvdm.original,true);
+ cvReleaseMat(&cvdm.original);
+ cv::Mat c(cvdm.corners,true);
+ dm.corners[0] = c.at<Point>(0,0);
+ dm.corners[1] = c.at<Point>(1,0);
+ dm.corners[2] = c.at<Point>(2,0);
+ dm.corners[3] = c.at<Point>(3,0);
+ cvReleaseMat(&cvdm.corners);
+ return dm;
+ }
+ };
+
+ struct DrawDataMatrixCode
+ {
+ DrawDataMatrixCode(cv::Mat& image):image(image){}
+ void operator()(const DataMatrixCode& code)
+ {
+ Scalar c(0, 255, 0);
+ Scalar c2(255, 0,0);
+ line(image, code.corners[0], code.corners[1], c);
+ line(image, code.corners[1], code.corners[2], c);
+ line(image, code.corners[2], code.corners[3], c);
+ line(image, code.corners[3], code.corners[0], c);
+ string code_text(code.msg,4);
+ int baseline = 0;
+ Size sz = getTextSize(code_text, CV_FONT_HERSHEY_SIMPLEX, 1, 1, &baseline);
+ putText(image, code_text, code.corners[0], CV_FONT_HERSHEY_SIMPLEX, 0.8, c2, 1, CV_AA, false);
+ }
+ cv::Mat& image;
+ };
+}
+
+void findDataMatrix(const cv::Mat& image, std::vector<DataMatrixCode>& codes)
+{
+ CvMat m(image);
+ deque <CvDataMatrixCode> rc = cvFindDataMatrix(&m);
+ codes.clear();
+ codes.resize(rc.size());
+ std::transform(rc.begin(),rc.end(),codes.begin(),CvDM2DM_transform());
+}
+
+void drawDataMatrixCodes(const std::vector<DataMatrixCode>& codes, Mat& drawImage)
+{
+ std::for_each(codes.begin(),codes.end(),DrawDataMatrixCode(drawImage));
+}
+
+}
--- /dev/null
+/*
+ * starter_video.cpp
+ *
+ * Created on: Nov 23, 2010
+ * Author: Ethan Rublee
+ *
+ * A starter sample for using opencv, get a video stream and display the images
+ * easy as CV_PI right?
+ */
+#include "opencv2/highgui/highgui.hpp"
+#include <opencv2/objdetect/objdetect.hpp>
+#include <opencv2/imgproc/imgproc.hpp>
+#include <iostream>
+#include <vector>
+#include <stdio.h>
+
+using namespace cv;
+using namespace std;
+
+//hide the local functions in an anon namespace
+namespace
+{
+void help(char** av)
+{
+ cout << "\nThis program justs gets you started reading images from video\n"
+ "Usage:\n./" << av[0] << " <video device number>\n" << "q,Q,esc -- quit\n"
+ << "space -- save frame\n\n"
+ << "\tThis is a starter sample, to get you up and going in a copy pasta fashion\n"
+ << "\tThe program captures frames from a camera connected to your computer.\n"
+ << "\tTo find the video device number, try ls /dev/video* \n"
+ << "\tYou may also pass a video file, like my_vide.avi instead of a device number"
+ << endl;
+}
+
+int process(VideoCapture& capture)
+{
+ std::vector<DataMatrixCode> codes;
+ int n = 0;
+ char filename[200];
+ string window_name = "video | q or esc to quit";
+ cout << "press space to save a picture. q or esc to quit" << endl;
+ namedWindow(window_name, CV_WINDOW_KEEPRATIO); //resizable window;
+ Mat frame;
+ for (;;)
+ {
+ capture >> frame;
+ if (frame.empty())
+ continue;
+ cv::Mat gray;
+ cv::cvtColor(frame,gray,CV_RGB2GRAY);
+ findDataMatrix(gray, codes);
+ drawDataMatrixCodes(codes, frame);
+ imshow(window_name, frame);
+ char key = (char) waitKey(5); //delay N millis, usually long enough to display and capture input
+ switch (key)
+ {
+ case 'q':
+ case 'Q':
+ case 27: //escape key
+ return 0;
+ case ' ': //Save an image
+ sprintf(filename, "filename%.3d.jpg", n++);
+ imwrite(filename, frame);
+ cout << "Saved " << filename << endl;
+ break;
+ default:
+ break;
+ }
+ }
+ return 0;
+}
+
+}
+
+int main(int ac, char** av)
+{
+
+ if (ac != 2)
+ {
+ help(av);
+ return 1;
+ }
+ std::string arg = av[1];
+ VideoCapture capture(arg); //try to open string, this will attempt to open it as a video file
+ if (!capture.isOpened()) //if this fails, try to open as a video camera, through the use of an integer param
+ capture.open(atoi(arg.c_str()));
+ if (!capture.isOpened())
+ {
+ cerr << "Failed to open a video device or video file!\n" << endl;
+ help(av);
+ return 1;
+ }
+ return process(capture);
+}