提交 25246fa4 authored 作者: blu's avatar blu

new feature: object detection v0.1

上级 e448f193
...@@ -23,6 +23,7 @@ update: 2019/09/10 ...@@ -23,6 +23,7 @@ update: 2019/09/10
#include "common.hpp" #include "common.hpp"
#include "avcvhelpers.hpp" #include "avcvhelpers.hpp"
#include "database.h" #include "database.h"
#include "yolo.hpp"
using namespace std; using namespace std;
using namespace zmqhelper; using namespace zmqhelper;
...@@ -81,6 +82,7 @@ private: ...@@ -81,6 +82,7 @@ private:
long long packetTsDelta = 0; long long packetTsDelta = 0;
float pps = 0; float pps = 0;
int pktLag = 0; int pktLag = 0;
unique_ptr<YoloDectect> pYolo = nullptr;
// //
int handleCloudMsg(vector<vector<uint8_t> > v) int handleCloudMsg(vector<vector<uint8_t> > v)
...@@ -358,6 +360,9 @@ private: ...@@ -358,6 +360,9 @@ private:
} }
//ping //ping
ret = ping(); ret = ping();
//
pYolo = unique_ptr<YoloDectect>(new YoloDectect("../opencv-yolo"));
} }
catch(exception &e) { catch(exception &e) {
spdlog::error("evmlmotion {} exception in EvPuller.init {:s} retrying", selfId, e.what()); spdlog::error("evmlmotion {} exception in EvPuller.init {:s} retrying", selfId, e.what());
...@@ -559,10 +564,26 @@ private: ...@@ -559,10 +564,26 @@ private:
void detectMotion(AVPixelFormat format,AVFrame *pFrame, bool detect = true) void detectMotion(AVPixelFormat format,AVFrame *pFrame, bool detect = true)
{ {
static bool first = true; static bool first = true;
static unsigned long detCnt = 0;
static cv::Mat avg; static cv::Mat avg;
static vector<vector<cv::Point> > cnts; static vector<vector<cv::Point> > cnts;
cv::Mat origin, gray, thresh; cv::Mat origin, gray, thresh;
avcvhelpers::frame2mat(format, pFrame, origin); avcvhelpers::frame2mat(format, pFrame, origin);
if(detCnt % 6 == 0) {
auto objDetRes = pYolo->process(origin, nullptr);
if(objDetRes.size() > 0) {
string s = fmt::format("{} {} object detected:\n", selfId, objDetRes.size());
int i = 0;
for(auto &[n, c, _]: objDetRes) {
i++;
s += fmt::format("\t\tobj {}:{}, prob: {}, x:{}, y:{}, w: {}, h:{}\n", i, n, c, _.x, _.y, _.width, _.height);
}
spdlog::info(s);
}
}
detCnt++;
cv::resize(origin, gray, cv::Size(FRAME_SIZE,FRAME_SIZE)); cv::resize(origin, gray, cv::Size(FRAME_SIZE,FRAME_SIZE));
cv::cvtColor(gray, thresh, cv::COLOR_BGR2GRAY); cv::cvtColor(gray, thresh, cv::COLOR_BGR2GRAY);
float fent = avcvhelpers::getEntropy(thresh); float fent = avcvhelpers::getEntropy(thresh);
......
...@@ -35,6 +35,9 @@ private: ...@@ -35,6 +35,9 @@ private:
bool bOutputIsImg = false; bool bOutputIsImg = false;
string outFileBase; string outFileBase;
bool cmdStop = false; bool cmdStop = false;
unsigned int wrapNum = 0;
unsigned long numFrameProcessed = 0;
unsigned int numLogSkip = 0;
// Get the names of the output layers // Get the names of the output layers
vector<String> getOutputsNames(const Net& net) vector<String> getOutputsNames(const Net& net)
...@@ -77,7 +80,7 @@ private: ...@@ -77,7 +80,7 @@ private:
} }
// post process // post process
vector<tuple<string, double, Rect>> postprocess(Mat& frame, const vector<Mat>& outs) vector<tuple<string, double, Rect>> postprocess(Mat& frame, const vector<Mat>& outs, bool bModify = true)
{ {
vector<int> classIds; vector<int> classIds;
vector<float> confidences; vector<float> confidences;
...@@ -117,6 +120,7 @@ private: ...@@ -117,6 +120,7 @@ private:
int idx = indices[i]; int idx = indices[i];
Rect box = boxes[idx]; Rect box = boxes[idx];
ret.push_back(tuple<string, double, Rect>(classes[classIds[idx]], confidences[idx], box)); ret.push_back(tuple<string, double, Rect>(classes[classIds[idx]], confidences[idx], box));
if(bModify)
drawPred(classIds[idx], confidences[idx], box.x, box.y, box.x + box.width, box.y + box.height, frame); drawPred(classIds[idx], confidences[idx], box.x, box.y, box.x + box.width, box.y + box.height, frame);
} }
...@@ -129,12 +133,15 @@ protected: ...@@ -129,12 +133,15 @@ protected:
// //
public: public:
typedef int (*callback)(vector<tuple<string, double, Rect>>&, Mat); typedef int (*callback)(vector<tuple<string, double, Rect>>&, Mat);
YoloDectect(string path = "") YoloDectect(string path = "", unsigned int _wrapNum = 10, unsigned int _numLogSkip = 380)
{ {
if(path.empty()) { if(path.empty()) {
path = "."; path = ".";
} }
wrapNum = _wrapNum;
numLogSkip = _numLogSkip;
// Load names of classes // Load names of classes
string classesFile = path + "/coco.names"; string classesFile = path + "/coco.names";
// Give the configuration and weight files for the model // Give the configuration and weight files for the model
...@@ -159,7 +166,7 @@ public: ...@@ -159,7 +166,7 @@ public:
spdlog::info("{} inited", selfId); spdlog::info("{} inited", selfId);
} }
vector<tuple<string, double, Rect>> process(Mat &inFrame, Mat &outFrame) vector<tuple<string, double, Rect>> process(Mat &inFrame, Mat* pOutFrame)
{ {
if(inFrame.empty()) { if(inFrame.empty()) {
return vector<tuple<string, double, Rect>>(); return vector<tuple<string, double, Rect>>();
...@@ -176,15 +183,20 @@ public: ...@@ -176,15 +183,20 @@ public:
net.forward(outs, getOutputsNames(net)); net.forward(outs, getOutputsNames(net));
// Remove the bounding boxes with low confidence // Remove the bounding boxes with low confidence
auto ret = postprocess(inFrame, outs); auto ret = postprocess(inFrame, outs, true);
// The function getPerfProfile returns the overall time for inference(t) and the timings for each of the layers(in layersTimes) // The function getPerfProfile returns the overall time for inference(t) and the timings for each of the layers(in layersTimes)
vector<double> layersTimes; vector<double> layersTimes;
if(numLogSkip == 0 || numFrameProcessed % numLogSkip == 0) {
double freq = getTickFrequency() / 1000; double freq = getTickFrequency() / 1000;
double t = net.getPerfProfile(layersTimes) / freq; double t = net.getPerfProfile(layersTimes) / freq;
spdlog::info("{} infer time: {} ms", selfId, t); spdlog::info("{} infer time: {} ms", selfId, t);
}
if(pOutFrame != nullptr){
inFrame.convertTo(*pOutFrame, CV_8U);
}
inFrame.convertTo(outFrame, CV_8U); numFrameProcessed++;
return ret; return ret;
} }
...@@ -217,8 +229,8 @@ public: ...@@ -217,8 +229,8 @@ public:
spdlog::info("{} try to process video {} to {}", selfId, inVideoUri, outFile); spdlog::info("{} try to process video {} to {}", selfId, inVideoUri, outFile);
long frameCnt = 0; unsigned long frameCnt = 0;
long detCnt = 0, skipCnt = 0; unsigned long detCnt = 0, skipCnt = 0;
Mat frame, outFrame; Mat frame, outFrame;
while (waitKey(1) < 0) { while (waitKey(1) < 0) {
// get frame from the video // get frame from the video
...@@ -238,11 +250,11 @@ public: ...@@ -238,11 +250,11 @@ public:
continue; continue;
} }
vector<tuple<string, double, Rect>> ret = process(frame, outFrame); vector<tuple<string, double, Rect>> ret = process(frame, &outFrame);
if(cb == nullptr) { if(cb == nullptr) {
if(ret.size() == 0 && bOutputIsImg) { if(ret.size() == 0 && bOutputIsImg) {
// no detection // no detection
if(skipCnt % 100 == 0) { if(numLogSkip == 0|| skipCnt % numLogSkip == 0) {
spdlog::info("{} no valid object detected skipped frame count {}", selfId, skipCnt); spdlog::info("{} no valid object detected skipped frame count {}", selfId, skipCnt);
} }
skipCnt++; skipCnt++;
...@@ -250,6 +262,10 @@ public: ...@@ -250,6 +262,10 @@ public:
} }
if (bOutputIsImg) { if (bOutputIsImg) {
if(wrapNum > 0) {
detCnt = detCnt % wrapNum;
}
string ofname = outFileBase + to_string(detCnt) + ".jpg"; string ofname = outFileBase + to_string(detCnt) + ".jpg";
imwrite(ofname, outFrame); imwrite(ofname, outFrame);
detCnt++; detCnt++;
...@@ -272,7 +288,7 @@ public: ...@@ -272,7 +288,7 @@ public:
int main(int argc, char** argv) int main(int argc, char** argv)
{ {
YoloDectect det; YoloDectect det;
det.process("rtsp://admin:ZQEAAI@192.168.0.101:554/h264/ch1/main/av_stream", "a.avi"); det.process("rtsp://admin:ZQEAAI@192.168.0.101:554/h264/ch1/main/av_stream", "a.jpg");
return 0; return 0;
} }
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论