profile dump
This commit is contained in:
parent
f44bc3bae9
commit
0f344bd8ad
1 changed files with 125 additions and 12 deletions
137
lines.cpp
137
lines.cpp
|
@ -1,5 +1,8 @@
|
||||||
#include<cmath>
|
#include<cmath>
|
||||||
#include<algorithm>
|
#include<algorithm>
|
||||||
|
#include<unistd.h>
|
||||||
|
#include<fstream>
|
||||||
|
#include<iomanip>
|
||||||
|
|
||||||
#ifdef HAS_OPENCV3
|
#ifdef HAS_OPENCV3
|
||||||
#include <opencv2/core.hpp> //Any OPENCV3 code
|
#include <opencv2/core.hpp> //Any OPENCV3 code
|
||||||
|
@ -22,18 +25,103 @@ auto BROWN = cv::Scalar(90,100,60);
|
||||||
auto BLACK = cv::Scalar(0,0,0);
|
auto BLACK = cv::Scalar(0,0,0);
|
||||||
auto YELLOW = cv::Scalar(20,200,200);
|
auto YELLOW = cv::Scalar(20,200,200);
|
||||||
|
|
||||||
|
void usage(char* program, std::ostream &buf) {
|
||||||
|
buf << "Usage: " << program << "[options] IMAGE-INPUT" << std::endl;
|
||||||
|
buf << "Identify the image as a book in perspective, get deperspectivized content" << std::endl;
|
||||||
|
buf << std::endl;
|
||||||
|
buf << "Options:" << std::endl;
|
||||||
|
buf << " -p PROFILE Save the transformation matrix in PROFILE" << std::endl;
|
||||||
|
buf << " -l LEFTPAGE Save the left page in LEFTPAGE" << std::endl;
|
||||||
|
buf << " -r RIGHTPAGE Save the right page in RIGHTPAGE" << std::endl;
|
||||||
|
buf << " -h HELP Show this help and exit" << std::endl;
|
||||||
|
}
|
||||||
|
|
||||||
|
class Options
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
char *left;
|
||||||
|
char *right;
|
||||||
|
char *profile;
|
||||||
|
char *input;
|
||||||
|
Options();
|
||||||
|
Options(int argc, char*argv[]);
|
||||||
|
bool parse(int argc, char*argv[]);
|
||||||
|
~Options();
|
||||||
|
};
|
||||||
|
Options::Options()
|
||||||
|
{
|
||||||
|
left = right = profile = input = NULL;
|
||||||
|
}
|
||||||
|
Options::~Options()
|
||||||
|
{
|
||||||
|
if(left == NULL) {
|
||||||
|
free(left);
|
||||||
|
}
|
||||||
|
if(right == NULL) {
|
||||||
|
free(right);
|
||||||
|
}
|
||||||
|
if(profile == NULL) {
|
||||||
|
free(profile);
|
||||||
|
}
|
||||||
|
//input doesn't need to be free-d: it points to argv[argc-1]
|
||||||
|
}
|
||||||
|
Options::Options(int argc, char *argv[])
|
||||||
|
{
|
||||||
|
left = right = profile = input = NULL;
|
||||||
|
parse(argc, argv);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Options::parse parse arguments, return true if help is requested */
|
||||||
|
bool Options::parse(int argc, char *argv[])
|
||||||
|
{
|
||||||
|
int c;
|
||||||
|
while((c=getopt(argc, argv, "p:l:r:h")) != -1)
|
||||||
|
{
|
||||||
|
switch(c)
|
||||||
|
{
|
||||||
|
case 'l':
|
||||||
|
left = strdup(optarg);
|
||||||
|
break;
|
||||||
|
case 'r':
|
||||||
|
right = strdup(optarg);
|
||||||
|
break;
|
||||||
|
case 'p':
|
||||||
|
profile = strdup(optarg);
|
||||||
|
break;
|
||||||
|
case 'h':
|
||||||
|
return true;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
throw std::runtime_error("Parsing error: invalid argument");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if(optind >= argc) {
|
||||||
|
std::cerr << "Error: " << argv[0] << " needs an argument" << std::endl;
|
||||||
|
throw std::runtime_error("Parsing error: argument needed");
|
||||||
|
}
|
||||||
|
input = argv[optind++];
|
||||||
|
if(optind < argc) {
|
||||||
|
std::cerr << "Error: too many arguments supplied" << std::endl;
|
||||||
|
throw std::runtime_error("Parsing error: too many arguments");
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
int main(int argc, char *argv[])
|
int main(int argc, char *argv[])
|
||||||
{
|
{
|
||||||
char const *fname = "files/masckera.png";
|
Options args;
|
||||||
if( 1<argc )
|
try{
|
||||||
fname = argv[1];
|
if(args.parse(argc, argv)) {
|
||||||
if( 3<argc) {
|
usage(argv[0], std::cout);
|
||||||
std::cerr << "Too many arguments" << std::endl;
|
return EXIT_SUCCESS;
|
||||||
|
}
|
||||||
|
} catch(std::runtime_error) {
|
||||||
|
usage(argv[0], std::cerr);
|
||||||
return EXIT_FAILURE;
|
return EXIT_FAILURE;
|
||||||
}
|
}
|
||||||
|
|
||||||
cv::Mat img;
|
cv::Mat img;
|
||||||
img=cv::imread(fname,CV_LOAD_IMAGE_GRAYSCALE);
|
img=cv::imread(args.input,CV_LOAD_IMAGE_GRAYSCALE);
|
||||||
if( img.empty() ) {
|
if( img.empty() ) {
|
||||||
std::cerr << "Error opening image, aborting" << std::endl;
|
std::cerr << "Error opening image, aborting" << std::endl;
|
||||||
return EXIT_FAILURE;
|
return EXIT_FAILURE;
|
||||||
|
@ -76,7 +164,7 @@ int main(int argc, char *argv[])
|
||||||
corn_4 = hull[(maxdistances[1]+1)%hull.size()];
|
corn_4 = hull[(maxdistances[1]+1)%hull.size()];
|
||||||
|
|
||||||
#ifdef _DEBUG
|
#ifdef _DEBUG
|
||||||
img = cv::imread(fname,CV_LOAD_IMAGE_COLOR); // uncomment to this to display image with colors
|
img = cv::imread(args.input,CV_LOAD_IMAGE_COLOR); // uncomment to this to display image with colors
|
||||||
std::cout << "Maxdist1:" << maxdistances[0] << " " << corn_1 << corn_2 << std::endl;
|
std::cout << "Maxdist1:" << maxdistances[0] << " " << corn_1 << corn_2 << std::endl;
|
||||||
std::cout << "Maxdist2:" << maxdistances[1] << " " << corn_3 << corn_4 << std::endl;
|
std::cout << "Maxdist2:" << maxdistances[1] << " " << corn_3 << corn_4 << std::endl;
|
||||||
cv::namedWindow("win", CV_GUI_NORMAL);
|
cv::namedWindow("win", CV_GUI_NORMAL);
|
||||||
|
@ -138,9 +226,28 @@ int main(int argc, char *argv[])
|
||||||
img = cv::imread(args.input,CV_LOAD_IMAGE_COLOR);
|
img = cv::imread(args.input,CV_LOAD_IMAGE_COLOR);
|
||||||
for(int i=0; i < 2; i++) {
|
for(int i=0; i < 2; i++) {
|
||||||
trasf[i] = cv::getPerspectiveTransform(trapezoid[i], outsizes);
|
trasf[i] = cv::getPerspectiveTransform(trapezoid[i], outsizes);
|
||||||
|
assert(9==trasf[i].total()); // 3x3
|
||||||
cv::warpPerspective(img, rect[i], trasf[i], cv::Size(xsize, ysize));
|
cv::warpPerspective(img, rect[i], trasf[i], cv::Size(xsize, ysize));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if(args.profile) {
|
||||||
|
// format: each line is a tab-delimited 3x3 transformation matrix (as get by getPerspectiveTransform)
|
||||||
|
// first three elements is the first line, etc
|
||||||
|
std::ofstream profilebuf;
|
||||||
|
profilebuf.open(args.profile);
|
||||||
|
for(int t=0; t<2; t++) {
|
||||||
|
for(int i=0; i<3; i++) {
|
||||||
|
double* row= trasf[t].ptr<double>(i);
|
||||||
|
for(int j=0; j < 3; j++) {
|
||||||
|
profilebuf << std::fixed << std::setprecision(16);
|
||||||
|
profilebuf << row[j] << "\t"; //yes, there's a trailing tab
|
||||||
|
}
|
||||||
|
}
|
||||||
|
profilebuf << std::endl;
|
||||||
|
}
|
||||||
|
profilebuf.close();
|
||||||
|
}
|
||||||
|
|
||||||
#ifdef _DEBUG
|
#ifdef _DEBUG
|
||||||
cv::line(img, corn_1, middle1, MAGENTA, dotwidth>>3);
|
cv::line(img, corn_1, middle1, MAGENTA, dotwidth>>3);
|
||||||
cv::line(img, corn_2, middle1, MAGENTA, dotwidth>>3);
|
cv::line(img, corn_2, middle1, MAGENTA, dotwidth>>3);
|
||||||
|
@ -158,13 +265,19 @@ int main(int argc, char *argv[])
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
if(2<argc) {
|
|
||||||
std::vector<int> params;
|
|
||||||
|
//TODO: distinguish left and right
|
||||||
|
std::vector<int> params;
|
||||||
|
if(args.left || args.right) {
|
||||||
params.push_back(CV_IMWRITE_PNG_COMPRESSION);
|
params.push_back(CV_IMWRITE_PNG_COMPRESSION);
|
||||||
params.push_back(9);
|
params.push_back(9);
|
||||||
Mat dst;
|
if(args.left) {
|
||||||
img.convertTo(dst, CV_8UC3);
|
cv::imwrite(args.left, rect[0], params);
|
||||||
cv::imwrite(argv[2], dst, params);
|
}
|
||||||
|
if(args.right) {
|
||||||
|
cv::imwrite(args.right, rect[1], params);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return EXIT_SUCCESS;
|
return EXIT_SUCCESS;
|
||||||
|
|
Loading…
Reference in a new issue