8#ifndef META_OCEAN_CV_DETECTOR_MESSENGER_CODE_DETECTOR_H
9#define META_OCEAN_CV_DETECTOR_MESSENGER_CODE_DETECTOR_H
37 friend class QRCodeDetector;
44 static constexpr size_t numberCodeBits = 260;
54 using Codes = std::vector<CodeBits>;
90 inline const Vector2& position()
const;
96 inline Scalar radius()
const;
102 inline unsigned int grayThreshold()
const;
108 inline bool isValid()
const;
119 unsigned int grayThreshold_ = (
unsigned int)(-1);
182 static constexpr int deltaThreshold = 20;
200 inline int history1();
206 inline int history2();
212 inline int history3();
219 inline void push(
const int newDelta);
249 static Codes detectMessengerCodes(
const uint8_t*
const yFrame,
const unsigned int width,
const unsigned int height,
const unsigned int paddingElements,
Worker* worker =
nullptr);
276 template <
bool tCreateDebugInformation>
288 static inline Bullseyes detectBullseyes(
const uint8_t*
const yFrame,
const unsigned int width,
const unsigned int height,
const unsigned int yFramePaddingElements,
Worker* worker =
nullptr);
301 static void detectBullseyesSubset(
const uint8_t*
const yFrame,
const unsigned int width,
const unsigned int height,
Bullseyes* bullseyes,
Lock* multiThreadLock,
const unsigned int yFramePaddingElements,
const unsigned int firstRow,
const unsigned int numberRows);
341 static bool correctRotation(
const uint8_t* yFrame,
const unsigned int width,
const unsigned int height,
const Vector2* bullseyes,
const Scalar codeSize,
SquareMatrix3& homography,
const unsigned int yFramePaddingElements);
368 template <
bool tCreateDebugInformation>
369 static bool extractCodeBits(
const uint8_t* yFrame,
const unsigned int width,
const unsigned int height,
const Scalar codeSize,
const SquareMatrix3& homography,
CodeBits& codeBits,
const unsigned int grayThreshold,
const unsigned int yFramePaddingElements,
Vectors2* codeBitsLocationFrame =
nullptr);
380 static void detectBullseyesInRow(
const uint8_t*
const yFrame,
const unsigned int width,
const unsigned int height,
const unsigned int y,
Bullseyes& bullseyes,
const unsigned int yFramePaddingElements);
399 static bool checkBullseyeInColumn(
const uint8_t*
const yFrame,
const unsigned int frameStrideElements,
const unsigned int height,
const unsigned int xCenter,
const unsigned int yCenter,
const unsigned int threshold,
const unsigned int blackRingSegmentMin,
const unsigned int blackRingSegmentMax,
const unsigned int whiteRingSegmentMin,
const unsigned int whiteRingSegmentMax,
const unsigned int dotSegmentMin,
const unsigned int dotSegmentMax);
416 static bool checkBullseyeInNeighborhood(
const uint8_t*
const yFrame,
const unsigned int width,
const unsigned int height,
const unsigned int xCenter,
const unsigned int yCenter,
const unsigned int threshold,
const float whiteRingRadius,
const float blackRingRadius,
const float whiteBorderRadius,
const unsigned int yFramePaddingElements);
431 static unsigned int determineThreshold(
const uint8_t* yPosition,
const unsigned int segmentSize1,
const unsigned int segmentSize2,
const unsigned int segmentSize3,
const unsigned int segmentSize4,
const unsigned int segmentSize5);
439 static inline bool isTransitionToBlack(
const uint8_t* pixel,
TransitionHistory& history);
447 static inline bool isTransitionToWhite(
const uint8_t* pixel,
TransitionHistory& history);
460 template <
bool tFindBlackPixel>
461 static bool findNextUpperPixel(
const uint8_t* yPointer,
const unsigned int y,
const unsigned int maximalRows,
const unsigned int threshold,
const unsigned int frameStrideElements,
unsigned int& rows);
475 template <
bool tFindBlackPixel>
476 static bool findNextLowerPixel(
const uint8_t* yPointer,
const unsigned int y,
const unsigned int height,
const unsigned int maximalRows,
const unsigned int threshold,
const unsigned int frameStrideElements,
unsigned int& rows);
490 static bool determineAccurateBullseyeLocation(
const uint8_t* yFrame,
const unsigned int width,
const unsigned int height,
const unsigned int xBullseye,
const unsigned int yBullseye,
const unsigned int threshold,
Vector2& location,
const unsigned int framePaddingElements);
497 static inline Scalar radius2bullseyesDistanceShort(
const Scalar radius);
504 static inline Scalar radius2bullseyesDistanceLong(
const Scalar radius);
539 grayThreshold_(grayThreshold)
556 return grayThreshold_;
561 return position_.
x() >= 0 && position_.
y() >= 0 && radius_ > 0 && grayThreshold_ != 0u && grayThreshold_ < 256u;
579 return deltaMinus1 + deltaMinus2;
584 return deltaMinus1 + deltaMinus2 + deltaMinus3;
589 deltaMinus3 = deltaMinus2;
590 deltaMinus2 = deltaMinus1;
591 deltaMinus1 = newDelta;
603 ocean_assert(yFrame !=
nullptr);
604 ocean_assert(width >= 21u && height >= 21u);
607 bullseyes.reserve(16);
609 if (worker && height >= 600u)
611 Lock multiThreadLock;
612 worker->
executeFunction(
Worker::Function::createStatic(&
MessengerCodeDetector::detectBullseyesSubset, yFrame, width, height, &bullseyes, &multiThreadLock, yFramePaddingElements, 0u, 0u), 10u, height - 20u);
616 detectBullseyesSubset(yFrame, width, height, &bullseyes,
nullptr, yFramePaddingElements, 10u, height - 20u);
624 const int currentDelta = int(*(pixel + 0) - *(pixel - 1));
639 history.
push(currentDelta);
646 const int currentDelta = int(*(pixel + 0) - *(pixel - 1));
661 history.
push(currentDelta);
666template <
bool tFindBlackPixel>
669 ocean_assert(yPointer !=
nullptr);
670 ocean_assert(maximalRows != 0u);
671 ocean_assert(frameStrideElements != 0u);
680 while (
int(--y) >= 0 && ++rows <= maximalRows && (tFindBlackPixel ? (
int(*(yPointer - frameStrideElements)) >
int(threshold)) : (int(*(yPointer - frameStrideElements)) < int(threshold))))
682 yPointer -= frameStrideElements;
685 return int(y) >= 0 && rows <= maximalRows;
688template <
bool tFindBlackPixel>
689bool MessengerCodeDetector::findNextLowerPixel(
const uint8_t* yPointer,
unsigned int y,
const unsigned int height,
const unsigned int maximalRows,
const unsigned int threshold,
const unsigned int frameStrideElements,
unsigned int& rows)
691 ocean_assert(yPointer !=
nullptr);
692 ocean_assert(maximalRows != 0u);
693 ocean_assert(y < height);
694 ocean_assert(frameStrideElements != 0u);
696 if (y >= height - 1u)
703 while (++y < height && ++rows <= maximalRows && (tFindBlackPixel ? (
int(*(yPointer + frameStrideElements)) >
int(threshold)) : (int(*(yPointer + frameStrideElements)) < int(threshold))))
705 yPointer += frameStrideElements;
708 return y < height && rows <= maximalRows;
732 return radius *
Scalar(512.0 / 27.0);
Definition of a class holding a bullseye composed of a location and a radius.
Definition MessengerCodeDetector.h:70
bool isValid() const
Returns whether this bullseye is valid.
Definition MessengerCodeDetector.h:559
const Vector2 & position() const
Returns the (center) position of the bullseye.
Definition MessengerCodeDetector.h:544
Bullseye()
Creates an invalid bullseye object.
Definition MessengerCodeDetector.h:528
unsigned int grayThreshold() const
Returns the threshold that was used for the detection of this bullseye.
Definition MessengerCodeDetector.h:554
Scalar radius() const
Returns the radius of the bullseye.
Definition MessengerCodeDetector.h:549
This class implements a simple history for previous pixel transitions (a sliding window of pixel tran...
Definition MessengerCodeDetector.h:188
int deltaMinus3
The third previous delta.
Definition MessengerCodeDetector.h:235
int deltaMinus1
The previous delta.
Definition MessengerCodeDetector.h:229
void push(const int newDelta)
Adds a new delta object as most recent history.
Definition MessengerCodeDetector.h:587
int history2()
Returns the history with window size 2.
Definition MessengerCodeDetector.h:577
int history1()
Returns the history with window size 1.
Definition MessengerCodeDetector.h:572
int history3()
Returns the history with window size 3.
Definition MessengerCodeDetector.h:582
TransitionHistory()
Creates a new history object.
Definition MessengerCodeDetector.h:564
int deltaMinus2
The second previous delta.
Definition MessengerCodeDetector.h:232
void reset()
Resets the history object.
Definition MessengerCodeDetector.h:594
This class implements a detector for circular Messenger Codes.
Definition MessengerCodeDetector.h:36
static IndexQuartets extractCodeCandidates(const Vector2 *bullseyes, const Scalar *radii, const size_t size, const Scalar radiusScaleTolerance=Scalar(0.35), const Scalar distanceScaleTolerance=Scalar(0.17))
Extracts quartets of code bullseyes from a given set of bullseyes.
std::vector< CodeBits > Codes
Definition of a vector holding codes.
Definition MessengerCodeDetector.h:54
static bool isCodeInsideFrame(const unsigned int width, const unsigned int height, const SquareMatrix3 &homography, const Scalar codeSize)
Returns whether a Messenger Code, defined by a rectifying homography and code size,...
static void calculateRingBitCoordinates(const unsigned int bits, const IndexSet32 &bitsToSkip, const Scalar radius, Vectors2 &coordinates)
Calculates the bit coordinates of a ring of the Messenger Code.
static Scalar radius2bullseyesDistanceLong(const Scalar radius)
Returns the long distance between two bullseyes of the same Messenger Code (for opposite bullseyes) b...
Definition MessengerCodeDetector.h:724
static bool determineHomographyForBullseyeQuartet(const Vector2 *bullseyes, SquareMatrix3 &homography, Scalar &codeSize)
Calculates the homography rectifying the image content covered (and defined) by four bullseyes.
static void detectBullseyesSubset(const uint8_t *const yFrame, const unsigned int width, const unsigned int height, Bullseyes *bullseyes, Lock *multiThreadLock, const unsigned int yFramePaddingElements, const unsigned int firstRow, const unsigned int numberRows)
Detects Messenger Code bullseyes in subset of a given 8 bit grayscale image.
static Vectors2 calculateBitCoordiantes()
Returns 260 coordinates of the Messenger Code's bit elements origin in the center of the Code and nor...
std::vector< Bullseye > Bullseyes
Definition of a vector holding bullseyes.
Definition MessengerCodeDetector.h:125
static void detectBullseyesInRow(const uint8_t *const yFrame, const unsigned int width, const unsigned int height, const unsigned int y, Bullseyes &bullseyes, const unsigned int yFramePaddingElements)
Detects Messenger Code bullseyes in a row of an grayscale image.
static bool checkBullseyeInColumn(const uint8_t *const yFrame, const unsigned int frameStrideElements, const unsigned int height, const unsigned int xCenter, const unsigned int yCenter, const unsigned int threshold, const unsigned int blackRingSegmentMin, const unsigned int blackRingSegmentMax, const unsigned int whiteRingSegmentMin, const unsigned int whiteRingSegmentMax, const unsigned int dotSegmentMin, const unsigned int dotSegmentMax)
Checks whether a column contains a bullseye at a specified location.
static bool isTransitionToBlack(const uint8_t *pixel, TransitionHistory &history)
Checks whether the given pixel is a transition-to-black pixel (whether the direct left neighbor is a ...
Definition MessengerCodeDetector.h:622
static bool determineAccurateBullseyeLocation(const uint8_t *yFrame, const unsigned int width, const unsigned int height, const unsigned int xBullseye, const unsigned int yBullseye, const unsigned int threshold, Vector2 &location, const unsigned int framePaddingElements)
Determines the sub-pixel location of the center dot of a known bullseye.
static unsigned int determineThreshold(const uint8_t *yPosition, const unsigned int segmentSize1, const unsigned int segmentSize2, const unsigned int segmentSize3, const unsigned int segmentSize4, const unsigned int segmentSize5)
Determines the gray threshold separating bright pixels form dark pixels.
static const Vectors2 & codeBitCoordinates()
Returns the reference to 260 coordinates of the Messenger Code's bit elements origin in the center of...
static Scalar radius2bullseyesDistanceShort(const Scalar radius)
Returns the short distance between two bullseyes of the same Messenger Code (for neighboring bullseye...
Definition MessengerCodeDetector.h:711
static bool extractCodeBits(const uint8_t *yFrame, const unsigned int width, const unsigned int height, const Scalar codeSize, const SquareMatrix3 &homography, CodeBits &codeBits, const unsigned int grayThreshold, const unsigned int yFramePaddingElements, Vectors2 *codeBitsLocationFrame=nullptr)
Extracts the Messenger Code's bit information.
std::array< unsigned int, 4 > IndexQuartet
Definition of an index quartet (an array with exactly four indices).
Definition MessengerCodeDetector.h:59
std::vector< IndexQuartet > IndexQuartets
Definition of a vector holding index quartets.
Definition MessengerCodeDetector.h:64
static bool findNextUpperPixel(const uint8_t *yPointer, const unsigned int y, const unsigned int maximalRows, const unsigned int threshold, const unsigned int frameStrideElements, unsigned int &rows)
Finds either the next black or the next white pixel towards negative y direction (upwards in an image...
Definition MessengerCodeDetector.h:667
static bool checkBullseyeInNeighborhood(const uint8_t *const yFrame, const unsigned int width, const unsigned int height, const unsigned int xCenter, const unsigned int yCenter, const unsigned int threshold, const float whiteRingRadius, const float blackRingRadius, const float whiteBorderRadius, const unsigned int yFramePaddingElements)
Checks whether the direction neighborhood contains a bullseye at a specified location.
static Bullseyes detectBullseyes(const uint8_t *const yFrame, const unsigned int width, const unsigned int height, const unsigned int yFramePaddingElements, Worker *worker=nullptr)
Detects Messenger Code bullseyes in a given 8 bit grayscale image.
Definition MessengerCodeDetector.h:601
static bool findNextLowerPixel(const uint8_t *yPointer, const unsigned int y, const unsigned int height, const unsigned int maximalRows, const unsigned int threshold, const unsigned int frameStrideElements, unsigned int &rows)
Finds either the next black or the next white pixel towards positive y direction (downwards in an ima...
Definition MessengerCodeDetector.h:689
static bool isTransitionToWhite(const uint8_t *pixel, TransitionHistory &history)
Checks whether the given pixel is a transition-to-white pixel (whether the direct left neighbor is a ...
Definition MessengerCodeDetector.h:644
static Codes detectMessengerCodesWithDebugInformation(const uint8_t *const yFrame, const unsigned int width, const unsigned int height, DebugInformation &debugInformation, const unsigned int yFramePaddingElements, Worker *worker=nullptr)
Detects Messenger Codes in a given 8 bit grayscale image and returns debug information.
static Codes detectMessengerCodes(const uint8_t *const yFrame, const unsigned int width, const unsigned int height, const unsigned int paddingElements, Worker *worker=nullptr)
Detects Messenger Codes in a given 8 bit grayscale image.
static constexpr int deltaThreshold
The intensity threshold between two successive pixels to count as a transition from black to white (o...
Definition MessengerCodeDetector.h:182
static bool correctRotation(const uint8_t *yFrame, const unsigned int width, const unsigned int height, const Vector2 *bullseyes, const Scalar codeSize, SquareMatrix3 &homography, const unsigned int yFramePaddingElements)
Corrects the orientation of a given homography already rectifying the content of a Messenger Code.
std::bitset< numberCodeBits > CodeBits
Definition of a bitset containing the information of a Messenger Code.
Definition MessengerCodeDetector.h:49
static Codes detectMessengerCodes(const uint8_t *const yFrame, const unsigned int width, const unsigned int height, const unsigned int yFramePaddingElements, DebugInformation *debugInformation=nullptr, Worker *worker=nullptr)
Detects Messenger Codes in a given 8 bit grayscale image.
static Caller< void > createStatic(typename StaticFunctionPointerMaker< void, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass >::Type function)
Creates a new caller container for a static function with no function parameter.
Definition Caller.h:2877
This class implements Ocean's image class.
Definition Frame.h:1808
This class implements a recursive lock object.
Definition Lock.h:31
const T & x() const noexcept
Returns the x value.
Definition Vector2.h:710
const T & y() const noexcept
Returns the y value.
Definition Vector2.h:722
This class implements a worker able to distribute function calls over different threads.
Definition Worker.h:33
bool executeFunction(const Function &function, const unsigned int first, const unsigned int size, const unsigned int firstIndex=(unsigned int)(-1), const unsigned int sizeIndex=(unsigned int)(-1), const unsigned int minimalIterations=1u, const unsigned int threadIndex=(unsigned int)(-1))
Executes a callback function separable by two function parameters.
std::set< Index32 > IndexSet32
Definition of a set holding 32 bit indices.
Definition Base.h:114
float Scalar
Definition of a scalar type.
Definition Math.h:129
std::vector< Vector2 > Vectors2
Definition of a vector holding Vector2 objects.
Definition Vector2.h:64
The namespace covering the entire Ocean framework.
Definition Accessor.h:15