Open8
opencvのQRCodeのコードを読む

detectAndDecodeがない
detectAndDecodeは4.8.0で削除されて,detectAndDecodeCurved一本に統一されたっぽい.
基底クラスのGraphicalCodeDetectorのほうにはあるし,pythonのopencvでは使えるので,実装がどっかにあるはずだけど見つけられなかった

本体
多分本体のコード 関数は全部で4つ
qrcode.cpp,2897
std::string ImplContour::detectAndDecodeCurved(InputArray in, OutputArray points_,
OutputArray straight_qrcode)
{
Mat inarr;
if (!checkQRInputImage(in, inarr))
{
points_.release();
return std::string();
}
vector<Point2f> points;
bool ok = detect(inarr, points);
if (!ok)
{
points_.release();
return std::string();
}
updatePointsResult(points_, points);
std::string decoded_info = decodeCurved(inarr, points, straight_qrcode);
return decoded_info;
}

checkQRInputImage
画像が小さすぎる場合に弾いて,グレイスケールに変換した画像をinarryに入れている.
qrcode.cpp,29
static bool checkQRInputImage(InputArray img, Mat& gray)
{
CV_Assert(!img.empty());
CV_CheckDepthEQ(img.depth(), CV_8U, "");
if (img.cols() <= 20 || img.rows() <= 20)
{
return false; // image data is not enough for providing reliable results
}
int incn = img.channels();
CV_Check(incn, incn == 1 || incn == 3 || incn == 4, "");
if (incn == 3 || incn == 4)
{
cvtColor(img, gray, COLOR_BGR2GRAY);
}
else
{
gray = img.getMat();
}
return true;
}

detect
Qiitaに解説してる人がいた
-
qrdet.init(inarr, epsX, epsY)
- 画像を短辺が512になるようにリサイズ
- adaptiveThresholdで二値化
qrcode.cpp,988
Mat inarr;
if (!checkQRInputImage(in, inarr))
return false;
QRDetect qrdet;
qrdet.init(inarr, epsX, epsY);
if (!qrdet.localization()) { return false; }
if (!qrdet.computeTransformationPoints()) { return false; }
vector<Point2f> pnts2f = qrdet.getTransformationPoints();
updatePointsResult(points, pnts2f);
return true;