Objects not found in OpenCV4 - c++

This is my dir tree (root dir is untitled)
This is the content of CMakeLists.txt
cmake_minimum_required(VERSION 3.0.0)
project(untitled)
set(CMAKE_CXX_STANDARD 11)
find_package (OpenCV 4.5.2 REQUIRED)
include_directories ("/usr/local/include/opencv4/")
add_executable(untitled main.cpp)
This is my code in main.cpp:
#include <iostream>
#include <string>
#include <sstream>
#include <opencv4/opencv2/core.hpp>
#include <opencv4/opencv2/highgui.hpp>
using namespace cv;
using namespace std;
int main(int argc, const char** argv) {
Mat color = imread("./lenna.png");
Mat gray = imread("./lenna.png", 0);
imwrite("./lennaGray.png", gray);
int myRow = color.cols - 1;
int myCol = color.rows - 1;
Vec3b pixel = color.at<Vec3b>(myRow, myCol);
cout << "Pixel value (B, G, R): (" << (int)pixel[0] << ", " << (int)pixel[1] << ", " << (int)pixel[2] << ")" << endl;
imshow("Lenna BGR", color);
imshow("Lenna Gray", gray);
waitKey(0);
return 0;
}
This is the entire error when I ran make command:
But if I ran my code in terminal by this command:
g++ main.cpp -o main -lopencv_core -lopencv_highgui -lopencv_imgproc -lopencv_imgcodecs -I/usr/local/include/opencv4 && ./main
then it worked.
I don't know what happened, I just learned OpenCV and I am using Ubuntu 20.04 and OpenCV-4.5.2.

Related

OpenCV C++ cannot open video unless program is run as root

I'm trying to open a video file in Opencv C++, but it doesn't work in a weird way.
I'm on Fedora, and opencv is installed through dnf's opencv-devel package.
Here is the test code I'm using :
#include <iostream>
#include <opencv2/core/core.hpp>
#include <opencv2/imgcodecs/imgcodecs.hpp>
#include <opencv2/imgproc/imgproc.hpp>
#include <opencv2/highgui/highgui.hpp>
#include <opencv2/videoio/videoio.hpp>
int main(int argc, char *argv[])
{
std::string imagePath = "/home/me/picture.png";
cv::Mat image = cv::imread(imagePath);
std::cout << image << std::endl;
std::string videoPath = "/home/me/video.mp4";
cv::VideoCapture cap{ videoPath };
if(!cap.isOpened())
{
std::cout << "Error while opening video" << std::endl;
return -1;
}
cv::Mat startFrame;
cap >> startFrame;
std::cout << startFrame;
cap.release();
return 0;
}
Then, I Compile it with the libraries:
g++ -c -Wall -Wno-unknown-pragmas -I/usr/include/opencv4/ -o dist/obj/main.o src/main.cpp
g++ -lopencv_core -lopencv_highgui -lopencv_imgcodecs -lopencv_imgproc -lopencv_videoio dist/obj/main.o -o dist/bin/main
And when I run it, the image is read fine, but the video shows an error.
However, when I run it as sudo, the video reads just fine. I searched around a lot and couldn't find someone with a similar problem, so I'm posting this here.
Also, the python version works fine, so it shouldn'ttm be a codec problem.

Correct way to make library with priv / public header and pass cv::Mat

I need to make a .so or .a library and different headers, one of them to be shared with users to compile my main program (and link, in the code, processmatinlibrary_pub.h) and other to use in definitions and separated to the main code (processmatinlibrary.h).
When I use the public header (whitout some private definitions of methods), some times, depending on the structure of my program, I get segmentation faults or opencv assertions, below I paste my code, it could be dowloaded from https://github.com/eld1e6o/TestErrorOnLibrary
Here is my code and some comments
Files to create my main program, that uses functions on my library
This is the main function, I use it to check the library with public header
I get some segmentation faults depending on the structure of my program
I can force errors commenting #defines
#define _MAKE_ASSERT_OPENCV 1
#define _MAKE_SEGFAULT_ 1
*If I change the public header to the private header, I have not problems:
#include "processmatinlibrary.h" it works but the headers are not cshared
Instead of
#include "processmatinlibrary_pub.h"
It seems that is a stack problem and I need to define the library or the headers in the right way
Main.cpp
#include <opencv2/imgproc.hpp>
#include <opencv2/objdetect.hpp>
#include <opencv2/highgui.hpp>
#include <iostream>
#include "processmatinlibrary_pub.h" //If I change this header to #include "processmatinlibrary.h" it works but the headers are not cshared
using namespace std;
using namespace cv;
#define _MAKE_ASSERT_OPENCV 1
//#define _MAKE_SEGFAULT_ 1
void testEmpty(cv::Mat test_img, std::string msg)
{
cout << "* Check empty " << msg ;
if(test_img.empty())
{
cout << ": Image is Empty " << endl;
exit(1);
}
else cout << ": Image is not empty " << endl;
}
int main(int argc, char* argv[])
{
// Classify and get probabilities
Mat test_img = imread(argv[1], CV_LOAD_IMAGE_COLOR);
testEmpty(test_img, "After load image");
cv::resize(test_img, test_img, cv::Size(256, 256));
cout << " After resize " << endl;
testEmpty(test_img, "Before initialize library ");
ProcessMatInLibrary matToLibrary;
#ifdef _MAKE_SEGFAULT_
return 0; // If I comment this line, I got a segmentation fault: Segmentation Fault (`core' generated)
#endif
testEmpty(test_img, "After initialize library ");
bool b = matToLibrary.flip(test_img);
testEmpty(test_img, "After use function in library ");
cout << "In main " << endl;
/*
* If I define _MAKE_ASSERT_OPENCV, I got errors
OpenCV(3.4.1) Error: Assertion failed (0 <= _dims && _dims <= 32) in setSize, file /home/diego/Code/opencv/modules/core/src/matrix.cpp, line 209
terminate called after throwing an instance of 'cv::Exception'
what(): OpenCV(3.4.1) /home/diego/Code/opencv/modules/core/src/matrix.cpp:209: error: (-215) 0 <= _dims && _dims <= 32 in function setSize
*/
#ifndef _MAKE_ASSERT_OPENCV
imshow("Test before close", test_img); //If i comment this two lines, I got segmentation faults (OpenCV exception)
waitKey(0);
#endif
}
processmathlibrary_pub.h
This is my public header, used to define functions as publics
#ifndef PROCESSMATINLIBRARY_H
#define PROCESSMATINLIBRARY_H
#include <opencv2/imgproc.hpp>
#include <opencv2/objdetect.hpp>
#include <opencv2/highgui.hpp>
class ProcessMatInLibrary
{
public:
ProcessMatInLibrary();
bool flip(cv::Mat image);
bool myTest(cv::Mat one);
};
#endif // PROCESSMATINLIBRARY_H
Files to create my library
processmathinlibrary.cpp
#include "processmatinlibrary.h"
using namespace std;
using namespace cv;
#include <iostream>
ProcessMatInLibrary::ProcessMatInLibrary()
{
cout << "Initialized " << endl;
}
bool ProcessMatInLibrary::flip(cv::Mat image)
{
cout << "** Inside Library: " << endl;
if(image.empty())
{
cout << " Image is empty" << endl;
return false;
}
cout << " Image is not empty " << endl;
// return false;
Mat image2;
cv::flip(image, image2, 0);
imshow("Image in library", image);
imshow("Image2 in library", image2);
waitKey(0);
cout << "Inside Library: Image is not empty" << endl;
return true;
}
bool ProcessMatInLibrary::myTest(cv::Mat one)
{
one.copyTo(_img);
}
processmathlibrary.h
This is my private header, used to compile my library, it only differs on private declarations
#ifndef PROCESSMATINLIBRARY_LIB_H
#define PROCESSMATINLIBRARY_LIB_H
#include <opencv2/imgproc.hpp>
#include <opencv2/objdetect.hpp>
#include <opencv2/highgui.hpp>
class ProcessMatInLibrary
{
public:
ProcessMatInLibrary();
bool flip(cv::Mat image);
bool myTest(cv::Mat one);
private:
cv::Mat _img;
};
#endif // PROCESSMATINLIBRARY_LIB_H
How to compile all of this
CMakeLists.txt
Note that I have defined other PATH for OpenCV library, maybe there is an error to compile in the default PATH, I cannot check that
find_package(OpenCV REQUIRED) is working
cmake_minimum_required(VERSION 2.8.12)
project(test_pub_priv)
set(CMAKE_CXX_FLAGS "-Wall -Wextra -O3 -std=c++11")
#set(OpenCV_INCLUDE_DIRS "./include/")
find_package(OpenCV REQUIRED)
message(" ** Test with public private libraries ** ")
include_directories(${OpenCV_INCLUDE_DIRS})
aux_source_directory(./src SRC_LIST)
include_directories(./hpp SRC_LIST)
FILE(GLOB_RECURSE LibFiles "./hpp/*.h")
add_custom_target(headers SOURCES ${LibFiles})
add_library(myFramework ${SRC_LIST} )
add_executable(test_pub_priv ./examples/Main.cpp)
target_link_libraries(test_pub_priv ${OpenCV_LIBS} myFramework)
My question and problem is: What is the right way to pass a cv::Mat as argument trough library with one private header to the library and other (public header) to be shared?
Complete code can be seen here:
https://github.com/eld1e6o/TestErrorOnLibrary
Thanks!

Include Library in my C++ binary - Cmake

I am using the poppler-cpp library in my project.
It build & start it correctly, but I need to have popple installed in my system.
What is the way to import (include) the poppler library in my project, the aim is to execute it on another linux system which has not poppler lib installed, is it possible ?
My current cmakeList.txt file:
cmake_minimum_required(VERSION 3.5)
project(poppler_test)
set(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} "${CMAKE_SOURCE_DIR}/extra-cmake-modules/find-modules")
find_package(Poppler REQUIRED)
include(CMakeToolsHelpers OPTIONAL)
include_directories(${Poppler_INCLUDE_DIRS})
set(CMAKE_CXX_STANDARD 14)
set(SOURCE_FILES main.cpp)
ADD_LIBRARY(poppler STATIC IMPORTED)
add_dependencies( poppler poppler_test )
add_executable(poppler_test ${SOURCE_FILES})
target_link_libraries(${PROJECT_NAME} ${Poppler_LIBRARIES})
My main.cpp Programm
#include <algorithm>
#include <cpp/poppler-document.h>
#include <cpp/poppler-page.h>
#include <exception>
#include <iostream>
#include <memory>
#include <string>
#include <vector>
using namespace std;
int main(int argc, char* argv[]) {
auto input = "/Home/Dev/poppler-test/test.pdf";
shared_ptr<poppler::document> doc{poppler::document::load_from_file(input)};
const int pagesNbr = doc->pages();
cout << "page count: " << pagesNbr << endl;
vector<string> infoKeys{doc->info_keys()};
for_each(infoKeys.begin(), infoKeys.end(),
[doc](string infoKey) { cout << doc->info_key(infoKey).to_latin1() << endl; });
for (int i = 0; i < pagesNbr; ++i) {
shared_ptr<poppler::page> currentPage{doc->create_page(i)};
if (currentPage == nullptr) {
auto byteArrayResult = currentPage->text().to_utf8();
string result{byteArrayResult.begin(), byteArrayResult.end()};
cout << result << endl;
}
}
}

Opencv 3.0 features2d.hpp error : unknown AlgorithmInfo

I'm developing a project using opencv3.0 with extra module found in opencv_contrib github. Im using Xcode 7.0, Yosemite 10.10.
I have done the setting in Xcode
Header Search path :
/Users/kimloonghew/Documents/opencv/opencv-3.0.0/build/include /usr/local/Cellar/libiomp/20150401/include/libiomp/omp.h /usr/local/include
Library Search path :
/Users/kimloonghew/Documents/opencv/opencv-3.0.0/build/lib /usr/local/lib
Other Linker Flag : -lopencv_calib3d -lopencv_core -lopencv_features2d -lopencv_flann -lopencv_highgui -lopencv_imgcodecs -lopencv_imgproc -lopencv_ml -lopencv_objdetect -lopencv_photo -lopencv_shape -lopencv_stitching -lopencv_superres -lopencv_ts -lopencv_video -lopencv_videoio -lopencv_videostab -lopencv_nonfree -lopencv_ml -lopencv_xfeatures2d
Here the code below:
#include <stdio.h>
#include <stdlib.h>
#include <iostream>
#include <fstream>
#include <dirent.h>
#include <string>
#include <unistd.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <opencv2/core.hpp>
#include <opencv2/opencv.hpp>
#include <opencv2/features2d/features2d.hpp>
#include <opencv2/nonfree/nonfree.hpp>
#include <opencv2/xfeatures2d.hpp>
#include <opencv2/nonfree/features2d.hpp>
#include <opencv2/ml/ml.hpp>
using namespace std;
using namespace cv;
int main(int argc, const char * argv[]) {
int minHessin = 400;
string dir = "/Users/DYKLhew/Documents/Food_proj/MIT/foodcamimages/TRAIN", filepath;
DIR *dp;
struct dirent *dirp;
struct stat filestat;
dp = opendir(dir.c_str());
SurfFeatureDetector detector(minHessin);
//Ptr<xfeatures2d::SURF> detector = xfeatures2d::SURF::create(minHessin);
vector<KeyPoint> keypoints, keypoints_scene;
Mat descriptors_object, descriptor_scene;
Mat img;
cout << "------- build vocabulary ---------\n";
cout << "extract descriptors.."<<endl;
int count = 0;
while (count++ < 15 && (dirp = readdir(dp))) {
filepath = dir + "/" + dirp->d_name;
if(stat( filepath.c_str(), &filestat )) continue;
if(S_ISDIR(filestat.st_mode)) continue;
img = imread(filepath);
detector.detect(img, keypoints);
cout << ".";
}
cout << endl;
closedir(dp);
cout << "Total descriptors : " << count << endl;
//BOWKMeansTrainer bowtrainer(150);
return 0;
}
When I run the file, it BUILD fail with the errors detected in featuares2d.hpp files. Errors as below
1) Unknown type name 'AlgorigthmInfo'; did you mean 'Algorigthm'?
2) No template named 'vector'; did you mean 'std::vector?'
Anything i did wrong when setup or installing opencv? or any linkpath i have to define?
Appreciated, for your advice. Thanks
Issues Solved:
Xcode compiler is smart and it able to predict solutions it match to your current machine configuration. If you just follow the suggestion given from the Xcode compiler, the issues was solve.
System not recognise AlgorigthmInfo, you may change to Algorigthm as well as vector to std::vector.
Now is completely working well openCV in my machine.
Hope, this will help some others if facing same issues.

crash without error message opencv under Qt

I have a problem under Qt, Actually I want to use opencv under it (ubuntu) and there is a crash.
If I compile under the terminal :
g++ pkg-config --cflags opencv example.cc -o output_file pkg-config --libs opencv
All is all right but under QT there is a crashed problem and I just read this message error :
Starting /home/quentin/build-test_opencv-Desktop_Qt_5_2_1_GCC_64bit-Release/test_opencv...
The program has unexpectedly finished.
/home/quentin/build-test_opencv-Desktop_Qt_5_2_1_GCC_64bit-Release/test_opencv crashed
This is my .pro :
QT += core
QT -= gui
TARGET = test_opencv
CONFIG += console
CONFIG -= app_bundle
TEMPLATE = app
CONFIG += link_pkgconfig
PKGCONFIG += opencv
SOURCES += main.cpp
INCLUDEPATH += -I /usr/local/include/opencv
LIBS += `pkg-config opencv --libs`
and this is my main.cpp :
#include <QCoreApplication>
#include <iostream>
#include "cv.h"
#include "highgui.h"
using namespace std;
int main(int argc, char *argv[])
{
IplImage* img = cvLoadImage( "lena.png" );
cout << "Image WIDTH = " << img->width << endl;
cout << "Image HEIGHT = " << img->height << endl;
cvReleaseImage( &img );
return 0;
}
Most likely cvLoadImage fails and returns nullptr. You never bother checking for that.
What version of openCV do you use? What berak means is that IplImage is not used in the newer versions of openCV. Use Mat instead of IplImage. Try this code and tell me what happens:
#include <QCoreApplication>
#include <iostream>
#include <stdio.h>
#include <opencv2/core/core.hpp>
#include "opencv2/highgui/highgui.hpp"
int main(int argc, char *argv[])
{
Mat* img = new cv::Mat(cv::imread("lena.png",CV_LOAD_IMAGE_COLOR));
if(img == NULL){
perror("Could not load image");
}
std::cout << "Image WIDTH = " << img->cols << std::endl;
std::cout << "Image HEIGHT = " << img->rows << std::endl;
img->release();
return 0;
}
This will work in opencv 2.4.X. Also make sure your image is in the same folder as your program. Please tell me of any error.