diff --git a/examples/CMakeLists.txt b/examples/CMakeLists.txt index edfba88..42515f4 100644 --- a/examples/CMakeLists.txt +++ b/examples/CMakeLists.txt @@ -1,5 +1,11 @@ include_directories (${CMAKE_SOURCE_DIR}/src) +find_package(Qt5 COMPONENTS + Widgets + PrintSupport + REQUIRED +) + file( GLOB usage_examples @@ -9,7 +15,7 @@ file( foreach(f ${usage_examples}) get_filename_component(exampleName ${f} NAME_WE) add_executable(${exampleName} ${f}) - target_link_libraries(${exampleName} ${OpenCV_LIBS}) + target_link_libraries(${exampleName} ${OpenCV_LIBS} fftw3 plotcpp qcustomplot Qt5::Widgets Qt5::PrintSupport) install(PROGRAMS ${CMAKE_CURRENT_BINARY_DIR}/${exampleName} DESTINATION bin RENAME ${CMAKE_PROJECT_NAME}-${exampleName}) diff --git a/examples/test-fft.cpp b/examples/test-fft.cpp new file mode 100644 index 0000000..17db501 --- /dev/null +++ b/examples/test-fft.cpp @@ -0,0 +1,51 @@ +#include +#include +#include + +double pi() { + return 3.1415; +} + +std::vector tfd2vect(fftw_complex* tfd, int N) { + std::vector res; + auto it = tfd; + for (int i = 0; i != N; ++i) { + fftw_complex c = {*it[0], *it[1]}; + res.push_back(sqrt(c[0]*c[0] + c[1]*c[1])); + it++; + } + + return res; +} + +int main(int argc, char** argv) { + QApplication app(argc, argv); + fftw_complex *in, *out; + fftw_plan p; + + int N = 500; + in = (fftw_complex*) fftw_malloc(sizeof(fftw_complex) * N); + out = (fftw_complex*) fftw_malloc(sizeof(fftw_complex) * N); + p = fftw_plan_dft_1d(N, in, out, FFTW_FORWARD, FFTW_MEASURE); + + std::vector xx; + for (int i = 0; i != N; ++i) { + xx.push_back(i); + } + + for (int i = 0; i != N; ++i) { + in[i][0] = sin(2*pi()*50*i/N); + } + + fftw_execute(p); /* repeat as needed */ + + std::vector res = tfd2vect(out, N); + PlotCpp g; + g.plot(xx, res); + g.draw(); + + + fftw_destroy_plan(p); + fftw_free(in); fftw_free(out); + return app.exec(); +} diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index de84d7b..ce8f025 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -1,8 +1,11 @@ # file(GLOB headers *.hpp) # file(GLOB lib_files *.cpp) -add_executable(traitement traitement.cpp) -target_link_libraries(traitement ${OpenCV_LIBS}) +# add_executable(traitement traitement.cpp) +# target_link_libraries(traitement ${OpenCV_LIBS} fftw3) + +add_executable(test-fft test-fft.cpp) +target_link_libraries(test-fft) # target_include_directories(blk PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}) # target_compile_options (blk PUBLIC -std=c++11 ) diff --git a/src/math.hpp b/src/math.hpp new file mode 100644 index 0000000..ef2c90a --- /dev/null +++ b/src/math.hpp @@ -0,0 +1,111 @@ +#pragma once + +#include +#include +#include +#include +#include + +namespace math { + + using complex = std::complex; + using signal = std::vector; + using csignal = std::vector; + using contour = std::vector; + constexpr double pi() {return std::atan(1)*4;} + + //TODO implémenter la fft + csignal fft(const signal& input) { + //TODO: s'assurer que le signal est bien formé (i.e. bonne taille) + return fft_rec(input); + }; + + csignal fft_rec(const signal& input) { + int size = input.size(); + + if (size == 1) { + return input; + } else { + signal odd; + signal even; + std::back_insert_iterator odd_back_it(odd); + std::back_insert_iterator even_back_it(even); + bool insert_in_even = false; + + for (auto it = input.begin(); it != input.end(); ++it) { + if (insert_in_even) { + *even_back_it++ = *it; + insert_in_even = false; + } else { + *odd_back_it++ = *it; + insert_in_even = true; + } + } + + signal odd_fft = fft_rec(odd); + signal even_fft = fft_rec(even); + signal res; + res.reserve(size); + + for (int k = 0; k& contours) { + int max = 0; + int id = 0; + for (int i=0; i max) { + max = contours[i].size(); + id = i; + } + } + return id; + }; + + contour simplify_contour(const contour& cont, int cmax) { + contour res; + signal z = cont2sig(cont); + complex zm = mean(z); + signal tfd = fft(z); + res = coef2cont(tfd, zm, 0, cmax); + return res; + }; +} diff --git a/src/test-fft.cpp b/src/test-fft.cpp new file mode 100644 index 0000000..cd382a0 --- /dev/null +++ b/src/test-fft.cpp @@ -0,0 +1,13 @@ +#include +#include + +int main(int argc, char** argv) { + math::signal s; + + for (int i=0; i<100; ++i) { + s.push_back(std::sin(2*math::pi()*50*i/100)); + } + math::fft(s); + + return 0; +} diff --git a/src/traitement.cpp b/src/traitement.cpp index 76f7079..80ece67 100644 --- a/src/traitement.cpp +++ b/src/traitement.cpp @@ -1,4 +1,7 @@ #include "opencv2/opencv.hpp" +#include +#include +#include "math.hpp" int filter(const cv::Mat& img, cv::Mat output, int seuil) { bool detect = false; @@ -25,12 +28,15 @@ int filter(const cv::Mat& img, cv::Mat output, int seuil) { } int main(int argc, char** argv) { - int seuil=80; + int seuil=0; if (argc > 1) { seuil = atol(argv[1]); } + int cmax = 10; + int N = 5000; + char detect; cv::VideoCapture cap(0); if(!cap.isOpened()) @@ -39,10 +45,10 @@ int main(int argc, char** argv) { cv::namedWindow("Detection",1); cv::namedWindow("Contours",1); while(true) { - int X,Y,DIM,index; + int X, Y, DIM, index; unsigned int numc; - uchar R,G,B; - std::vector > contours; + uchar R, G, B; + std::vector> contours; std::vector hierarchy; cv::Mat frame; cap >> frame; @@ -60,15 +66,14 @@ int main(int argc, char** argv) { cv::imshow("Detection", binaire); cv::findContours(binaire, contours, hierarchy, CV_RETR_EXTERNAL, CV_CHAIN_APPROX_NONE); cv::Mat Dessin = cv::Mat::zeros(X,Y, CV_8UC1); - unsigned int max = 0; - int id = 0; - for(numc = 0; numc max) { - max = contours[numc].size(); - id = numc; - } - } + + int id = math::max_cont(contours); + std::cout << contours[id].size() << std::endl; + + std::vector new_cont = math::simplify_contour(contours[id], cmax); + cv::drawContours(Dessin, contours, id, 255); + cv::drawContours(Dessin, new_cont, id, 255); cv::imshow("Contours", Dessin); if(cv::waitKey(30) == 27) { break;