From 9cd267bc7da6435753ca4e9fb1e5e62e8bb37890 Mon Sep 17 00:00:00 2001 From: Raphael Maenle <17550607+g-spacewhale@users.noreply.github.com> Date: Sat, 27 Jan 2018 16:27:06 +0100 Subject: [PATCH] added color check --- Source/CMakeLists.txt | 1 + .../AbstractionLayer_ColorMatching.cpp | 134 ++++++++++++++++++ .../AbstractionLayer_ColorMatching.h | 47 ++++++ ...bstractionLayer_ColorMatching_Properties.h | 30 ++++ Source/functions/solve/puzzleExtension.cpp | 4 + Source/functions/solve/structure.cpp | 21 ++- Source/header/input.h | 2 + Source/header/solve.h | 2 + 8 files changed, 229 insertions(+), 12 deletions(-) create mode 100644 Source/functions/AbstractionLayers/Layer_ColorMatching/AbstractionLayer_ColorMatching.cpp create mode 100644 Source/functions/AbstractionLayers/Layer_ColorMatching/AbstractionLayer_ColorMatching.h create mode 100644 Source/functions/AbstractionLayers/Layer_ColorMatching/AbstractionLayer_ColorMatching_Properties.h diff --git a/Source/CMakeLists.txt b/Source/CMakeLists.txt index cbdec11..f544bf4 100644 --- a/Source/CMakeLists.txt +++ b/Source/CMakeLists.txt @@ -12,6 +12,7 @@ set(SOURCE_FILES functions/AbstractionLayers/Layer1/AbstractionLayer_1.cpp functions/AbstractionLayers/Layer3_PoempelPosition/AbstractionLayer_PoempelPosition.cpp functions/AbstractionLayers/Layer_SURFFeatures/AbstractionLayer_SURFFeatures.cpp + functions/AbstractionLayers/Layer_ColorMatching/AbstractionLayer_ColorMatching.cpp functions/AbstractionLayers/DestructionPower/DestructionPower.cpp header/solve.h header/input.h diff --git a/Source/functions/AbstractionLayers/Layer_ColorMatching/AbstractionLayer_ColorMatching.cpp b/Source/functions/AbstractionLayers/Layer_ColorMatching/AbstractionLayer_ColorMatching.cpp new file mode 100644 index 0000000..f791ba4 --- /dev/null +++ b/Source/functions/AbstractionLayers/Layer_ColorMatching/AbstractionLayer_ColorMatching.cpp @@ -0,0 +1,134 @@ +#include "AbstractionLayer_ColorMatching.h" +#include "../../../header.h" +#include +#include + +bool AbstractionLayer_ColorMatching::PreProcessing(coor mySize, const vector* partArray) { + + InitialiseConstraintMatrixSize(mySize.col, mySize.row); //col row switched in this function + + //**Get color for constraint matrix**// + Mat puzzle = imread("puzzle1.jpg", IMREAD_COLOR); // Read the picture of the puzzle + if (puzzle.empty()) // Check for invalid input + { + cout << "Could not open or find the image" << std::endl; + return -1; + } + int width = puzzle.size().width; + int height = puzzle.size().height; + int X = width / mySize.col; + int Y = height / mySize.row; + + for (int r = 0; r < mySize.row; r++) { + for (int c = 0; c < mySize.col; c++) { + Mat ExtPart = puzzle(CvRect(c*X, r*Y, X, Y)); + + // crop image to ROI + Mat ExtPartCropped = ExtPart( + Rect(ExtPart.size().width / 3, ExtPart.size().height / 3, ExtPart.size().width / 3, + ExtPart.size().height / 3)); + + // Create a new matrix to hold the HSV image + Mat HSVExtPart; + // convert RGB image to HSV + cvtColor(ExtPartCropped, HSVExtPart, CV_BGR2HSV); + + //namedWindow("ExtPartCropped", WINDOW_AUTOSIZE); // Create a window for display. + //imshow("ExtPartCropped", ExtPartCropped); + //waitKey(0); // Wait for a keystroke in the window + + vector hsv_planes_ext; + split(HSVExtPart, hsv_planes_ext); + + Scalar tempHue_ext = mean(hsv_planes_ext[0]); + Scalar tempSaturation_ext = mean(hsv_planes_ext[1]); + Scalar tempValue_ext = mean(hsv_planes_ext[2]); + + //cout << "Hue: " << tempHue_ext.val[0] << endl; + //cout << "Saturation: " << tempSaturation_ext.val[0] << endl; + //cout << "Value: " << tempValue_ext.val[0] << endl; + + m_constraintMatrix[c][r].m_centerColor.h = tempHue_ext.val[0]; + m_constraintMatrix[c][r].m_centerColor.s = tempSaturation_ext.val[0]; + m_constraintMatrix[c][r].m_centerColor.v = tempSaturation_ext.val[0]; + + //**********************************************************// + } + } + //**Get color of all parts**// + + const vector &ref_partArray = *partArray; + int iterator = 0; + + for(int count =0;count< mySize.row*mySize.col*4;count++)// multiplied by 4 for all rotations + { + Scalar tempHue, tempSaturation, tempValue; + + if(count%4) { + char name[100]; + + sprintf(name, PATH, count); + Mat Part = imread(name, 1); + if (!Part.data) { + cerr << "Could not open or find the image" << endl; + return -1; + } + + Mat PartCropped = Part(Rect(Part.size().width / 3, Part.size().height / 3, Part.size().width / 3, + Part.size().height / 3)); + + //namedWindow("PartCropped", WINDOW_AUTOSIZE); // Create a window for display. + //imshow("PartCropped", PartCropped); + //waitKey(0); // Wait for a keystroke in the window + + // Create a new matrix to hold the HSV image + Mat HSVPart; + + // convert RGB image to HSV + cvtColor(PartCropped, HSVPart, CV_BGR2HSV); + + vector hsv_planes; + split(HSVPart, hsv_planes); + + tempHue = mean(hsv_planes[0]); + tempSaturation = mean(hsv_planes[1]); + tempValue = mean(hsv_planes[2]); + + //cout << "Hue: " << tempHue.val[0] << endl; + //cout << "Saturation: " << tempSaturation.val[0] << endl; + //cout << "Value: " << tempValue.val[0] << endl; + } + + ref_partArray[iterator]->m_acm.m_centerColor.h = tempHue.val[0]; + ref_partArray[iterator]->m_acm.m_centerColor.s = tempSaturation.val[1]; + ref_partArray[iterator]->m_acm.m_centerColor.v = tempValue.val[2]; + + iterator ++; + } + + return true; +} + +bool AbstractionLayer_ColorMatching::EvaluateQuality (const coor constraintCoordinate, qualityVector& qVector) +{ + for(int i = 0;im_acm.m_partColor); + qVector[i].first = value; + } +} + +float AbstractionLayer_ColorMatching::PlaceOfPartGood(coor myCoor, HSV myPart) +{ + //Hue max 360° + if(m_constraintMatrix[myCoor.col][myCoor.row].m_partColor.h >= 180) + { + return 1-abs((m_constraintMatrix[myCoor.col][myCoor.row].m_centerColor.h-myPart.h) + /m_constraintMatrix[myCoor.col][myCoor.row].m_centerColor.h); + } + else if(m_constraintMatrix[myCoor.col][myCoor.row].m_partColor.h < 180) + { + return 1-((myPart.h-m_constraintMatrix[myCoor.col][myCoor.row].m_centerColor.h) + /(360-m_constraintMatrix[myCoor.col][myCoor.row].m_centerColor.h)); + } +} \ No newline at end of file diff --git a/Source/functions/AbstractionLayers/Layer_ColorMatching/AbstractionLayer_ColorMatching.h b/Source/functions/AbstractionLayers/Layer_ColorMatching/AbstractionLayer_ColorMatching.h new file mode 100644 index 0000000..3c5da05 --- /dev/null +++ b/Source/functions/AbstractionLayers/Layer_ColorMatching/AbstractionLayer_ColorMatching.h @@ -0,0 +1,47 @@ + +#ifndef SOURCE_ABSTRACTIONLAYER_ColorMatching_H +#define SOURCE_ABSTRACTIONLAYER_ColorMatching_H + +#include "AbstractionLayer_ColorMatching_Properties.h" +#include "../AbstraktionLayer_Base.h" + +//#include +#include +#include +//#include +//#include +#include "opencv2/highgui/highgui.hpp" +#include "opencv2/imgproc/imgproc.hpp" +//#include +//#include +#include + + +#ifdef _WIN32 +//#define PATH "..\\..\\..\\pieces\\%04d.jpg" +#elif defined __unix__ +#define PATH "..//..//..//pieces//%04d.jpg" +#elif defined __APPLE__ + #define PATH "..//..//..//pieces//%04d.jpg" +#endif + + +using namespace std; +using namespace cv; + +class AbstractionLayer_ColorMatching : public AbstractionLayer_Base +{ +public: + bool PreProcessing(coor mySize, const vector* partArray) ; + bool EvaluateQuality (const coor constraintCoordinate, qualityVector& qVector); + bool SetConstraintOnPosition(const coor constraintCoordinate,const AbstractionLayer_ColorMatching_Properties constraint){} + bool RemoveConstraintOnPosition(const coor constraintCoordinate){} + float PlaceOfPartGood(coor myCoor, HSV myPart); + + + qualityVector returnInBox(vector& PuzzleBox); + +private: +}; + +#endif //SOURCE_ABSTRACTIONLAYER_ColorMatching_H diff --git a/Source/functions/AbstractionLayers/Layer_ColorMatching/AbstractionLayer_ColorMatching_Properties.h b/Source/functions/AbstractionLayers/Layer_ColorMatching/AbstractionLayer_ColorMatching_Properties.h new file mode 100644 index 0000000..303ddc1 --- /dev/null +++ b/Source/functions/AbstractionLayers/Layer_ColorMatching/AbstractionLayer_ColorMatching_Properties.h @@ -0,0 +1,30 @@ + +#ifndef SOURCE_ABSTRACTIONLAYER_COLORMATCHING_H +#define SOURCE_ABSTRACTIONLAYER_COLORMATCHING_H + +#include + +class HSV +{ +public: + HSV(): h(0.0), s(0.0), v(0.0){} + double h, s,v; +}; + + + +class AbstractionLayer_ColorMatching_Properties +{ +public: + AbstractionLayer_ColorMatching_Properties() {} + + +private: + HSV m_centerColor; + HSV m_partColor; + friend class AbstractionLayer_ColorMatching; +}; + + + +#endif //SOURCE_ABSTRACTIONLAYER_COLORMATCHING_H diff --git a/Source/functions/solve/puzzleExtension.cpp b/Source/functions/solve/puzzleExtension.cpp index bb42a14..457b715 100644 --- a/Source/functions/solve/puzzleExtension.cpp +++ b/Source/functions/solve/puzzleExtension.cpp @@ -68,6 +68,7 @@ void Puzzle::removeConstrains(coor removeCoordinates) this->a1.RemoveConstraintOnPosition(removeCoordinates); this->a3.RemoveConstraintOnPosition(removeCoordinates); this->a4.RemoveConstraintOnPosition(removeCoordinates); + this->acm.RemoveConstraintOnPosition(removeCoordinates); //TODO!! Add other layer remove here } void Puzzle::setConstraints(coor setConstraints, Part* constraintPiece) @@ -85,6 +86,9 @@ void Puzzle::setConstraints(coor setConstraints, Part* constraintPiece) //a4 this->a4.SetConstraintOnPosition(setConstraints,constraintPiece->m_a4); + + //a2 + this->acm.SetConstraintOnPosition(setConstraints,constraintPiece->m_acm); //TODO!! Add other layer remove here } diff --git a/Source/functions/solve/structure.cpp b/Source/functions/solve/structure.cpp index 5b3f95e..5fab820 100755 --- a/Source/functions/solve/structure.cpp +++ b/Source/functions/solve/structure.cpp @@ -80,13 +80,17 @@ void solve(vector& log,Puzzle& puzzleMat) puzzleMat.a1.EvaluateQuality(log.back().myCoor,log.back().PieceCollector); //puzzleMat.a1.EvaluateQuality(log.back().myCoor, log.back().PieceCollector); break; - case 1://SURFFeature + case 2://SURFFeature // return; puzzleMat.a4.EvaluateQuality(log.back().myCoor,log.back().PieceCollector); break; - case 2://poempelposition + case 3://poempelposition + return; puzzleMat.a3.EvaluateQuality(log.back().myCoor,log.back().PieceCollector); break; + case 1://color + puzzleMat.a4.EvaluateQuality(log.back().myCoor,log.back().PieceCollector); + break; case -1://random setsolution(log,puzzleMat); return; @@ -116,11 +120,6 @@ void setsolution(vector& log, Puzzle& puzzleMat) puzzleMat.setConstraints(log.back().myCoor,log.back().PieceCollector.begin()->second); cout << "set:" << log.back().myCoor.col << "," << log.back().myCoor.row << endl; //cout << "ID: " << log.back().PieceCollector[0].second->GetPartID() << endl; - if(log.back().myCoor.col==32 && log.back().myCoor.row==16) - { - puzzleMat.resultImage(log); - waitKey(0); - } } bool backtrack(vector& log, Puzzle& puzzleMat) @@ -141,9 +140,9 @@ bool backtrack(vector& log, Puzzle& puzzleMat) //remove similar in log - //Part myPart = *log.back().PieceCollector[0].second;//tmpsaves bad part + Part myPart = *log.back().PieceCollector[0].second;//tmpsaves bad part log.back().PieceCollector.erase(log.back().PieceCollector.begin());//removes bad part from log - //puzzleMat.removeSimilar(log.back().PieceCollector,myPart); //removes all pieces from log that are similar to bad part + puzzleMat.removeSimilar(log.back().PieceCollector,myPart); //removes all pieces from log that are similar to bad part //TODO reprogram similar removal to allow multilayer tracking if(log.back().PieceCollector.size()) // this checks if 'removeSimilar' has cleared entire LogElement { @@ -224,13 +223,11 @@ float capLogElements(vector& log) newid = id; } } -// if(log.back().abstractionLevel==0) + if(log.back().abstractionLevel==0) cut(log,newid); vectorsizeAfter = log.back().PieceCollector.size(); destroyed = ((double)vectorsizeBefore - (double)vectorsizeAfter) / (double)vectorsizeBefore; - if(log.back().abstractionLevel==1 && destroyed) - cerr << "destroyed something!" << endl; return (float)sqrt(destroyed*maxdiff); diff --git a/Source/header/input.h b/Source/header/input.h index 98506b5..848e75a 100755 --- a/Source/header/input.h +++ b/Source/header/input.h @@ -8,6 +8,7 @@ #include "../functions/AbstractionLayers/Layer1/AbstractionLayer_1_Properties.h" #include "../functions/AbstractionLayers/DestructionPower/DestructionPower_Properties.h" #include "../functions/AbstractionLayers/Layer3_PoempelPosition/AbstractionLayer_PoempelPosition_Properties.h" +#include "../functions/AbstractionLayers/Layer_ColorMatching/AbstractionLayer_ColorMatching_Properties.h" #include "../functions/AbstractionLayers/Layer_SURFFeatures/AbstractionLayer_SURFFeatures_Properties.h" class LayerContainer; @@ -45,6 +46,7 @@ public: AbstractionLayer_1_Properties m_a1; AbstractionLayer_PoempelPosition_Properties m_a3; AbstractionLayer_SURFFeatures_Properties m_a4; + AbstractionLayer_ColorMatching_Properties m_acm; private: int32_t m_partID; uint8_t m_numOfRotations; diff --git a/Source/header/solve.h b/Source/header/solve.h index 2e3f509..707c560 100755 --- a/Source/header/solve.h +++ b/Source/header/solve.h @@ -8,6 +8,7 @@ #include "../functions/AbstractionLayers/Layer1/AbstractionLayer_1.h" #include "../functions/AbstractionLayers/Layer3_PoempelPosition/AbstractionLayer_PoempelPosition.h" #include "../functions/AbstractionLayers/Layer_SURFFeatures/AbstractionLayer_SURFFeatures.h" +#include "../functions/AbstractionLayers/Layer_ColorMatching/AbstractionLayer_ColorMatching.h" #include "../functions/AbstractionLayers/DestructionPower/DestructionPower.h" using namespace std; @@ -58,6 +59,7 @@ public: AbstractionLayer_1 a1; AbstractionLayer_PoempelPosition a3; AbstractionLayer_SURFFeatures a4; + AbstractionLayer_ColorMatching acm; void removeConstrains(coor removeCoordinates); void setConstraints(coor setConstraints, Part *constraintPiece);