2022-09-22 20:57:46 -04:00
|
|
|
// This file is part of Motion Watch.
|
|
|
|
|
|
|
|
// Motion Watch is free software: you can redistribute it and/or modify
|
|
|
|
// it under the terms of the GNU General Public License as published by
|
|
|
|
// the Free Software Foundation, either version 3 of the License, or
|
|
|
|
// (at your option) any later version.
|
|
|
|
|
|
|
|
// Motion Watch is distributed in the hope that it will be useful,
|
|
|
|
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
|
|
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
|
|
// GNU General Public License for more details.
|
|
|
|
|
|
|
|
#include "mo_detect.h"
|
|
|
|
|
2022-12-17 10:34:40 -05:00
|
|
|
bool imgDiff(const Mat &prev, const Mat &next, shared_t *share)
|
2022-09-22 20:57:46 -04:00
|
|
|
{
|
2022-12-16 18:24:18 -05:00
|
|
|
auto ret = false;
|
2022-12-04 15:13:39 -05:00
|
|
|
|
2022-12-16 18:24:18 -05:00
|
|
|
detLog("img_diff() -- start()", share);
|
2022-09-22 20:57:46 -04:00
|
|
|
|
2022-12-16 18:24:18 -05:00
|
|
|
if (prev.empty()) detLog("prev_frame is empty -- this should never happen (opencv to blame).", share);
|
|
|
|
if (next.empty()) detLog("next_frame is empty -- EOF assumed.", share);
|
2022-12-11 10:25:22 -05:00
|
|
|
|
2022-12-16 18:24:18 -05:00
|
|
|
if (!prev.empty() && !next.empty())
|
|
|
|
{
|
|
|
|
Mat diff;
|
|
|
|
|
|
|
|
absdiff(prev, next, diff);
|
|
|
|
threshold(diff, diff, share->pixThresh, 255, THRESH_BINARY);
|
|
|
|
|
2022-12-17 10:34:40 -05:00
|
|
|
auto diffScore = countNonZero(diff);
|
2022-12-16 18:24:18 -05:00
|
|
|
|
|
|
|
detLog("diff_score: " + to_string(diffScore), share);
|
|
|
|
|
|
|
|
ret = diffScore >= share->imgThresh;
|
|
|
|
}
|
|
|
|
|
|
|
|
detLog("img_diff() -- finished()", share);
|
|
|
|
|
|
|
|
return ret;
|
2022-09-22 20:57:46 -04:00
|
|
|
}
|
|
|
|
|
2022-12-04 15:13:39 -05:00
|
|
|
Mat frameFF(VideoCapture *cap, int gap)
|
2022-09-22 20:57:46 -04:00
|
|
|
{
|
2022-12-04 15:13:39 -05:00
|
|
|
Mat ret;
|
2022-09-22 20:57:46 -04:00
|
|
|
|
2022-12-04 15:13:39 -05:00
|
|
|
if (gap == 0) gap = 1;
|
2022-09-22 20:57:46 -04:00
|
|
|
|
2022-12-04 15:13:39 -05:00
|
|
|
for (int i = 0; i < gap; ++i)
|
|
|
|
{
|
|
|
|
cap->grab();
|
2022-09-29 11:37:10 -04:00
|
|
|
}
|
2022-09-22 20:57:46 -04:00
|
|
|
|
2022-12-04 15:13:39 -05:00
|
|
|
cap->retrieve(ret);
|
2022-09-27 18:10:04 -04:00
|
|
|
|
2022-12-04 15:13:39 -05:00
|
|
|
if (!ret.empty())
|
|
|
|
{
|
|
|
|
cvtColor(ret, ret, COLOR_BGR2GRAY);
|
|
|
|
}
|
2022-09-22 20:57:46 -04:00
|
|
|
|
2022-12-04 15:13:39 -05:00
|
|
|
return ret;
|
2022-09-22 20:57:46 -04:00
|
|
|
}
|
|
|
|
|
2022-12-04 15:13:39 -05:00
|
|
|
void wrOut(const string &buffFile, const Mat &vidThumb, shared_t *share)
|
2022-09-22 20:57:46 -04:00
|
|
|
{
|
2022-12-16 18:24:18 -05:00
|
|
|
detLog("wr_out() -- start()", share);
|
|
|
|
detLog("buff_file: " + buffFile, share);
|
|
|
|
|
2022-12-04 15:13:39 -05:00
|
|
|
auto dayStr = genTimeStr("%Y-%m-%d");
|
|
|
|
auto timStr = genTimeStr("%H%M%S");
|
|
|
|
auto outDir = cleanDir(share->outDir) + "/" + dayStr;
|
2022-10-14 11:42:59 -04:00
|
|
|
|
2022-12-04 15:13:39 -05:00
|
|
|
if (!exists(outDir))
|
2022-09-22 20:57:46 -04:00
|
|
|
{
|
2022-12-04 15:13:39 -05:00
|
|
|
enforceMaxDays(share->outDir, share);
|
2022-09-22 20:57:46 -04:00
|
|
|
}
|
|
|
|
|
2022-12-04 15:13:39 -05:00
|
|
|
auto vidOut = genDstFile(outDir, timStr.c_str(), "." + share->vidExt);
|
|
|
|
auto imgOut = genDstFile(outDir, timStr.c_str(), ".jpg");
|
2022-09-22 20:57:46 -04:00
|
|
|
|
2022-12-11 10:25:22 -05:00
|
|
|
detLog("write_out_vid: " + vidOut, share);
|
|
|
|
detLog("write_out_img: " + imgOut, share);
|
|
|
|
|
2022-12-04 15:13:39 -05:00
|
|
|
enforceMaxClips(outDir, share);
|
2022-09-29 11:37:10 -04:00
|
|
|
|
2022-12-04 15:13:39 -05:00
|
|
|
copy_file(buffFile.c_str(), vidOut.c_str());
|
|
|
|
remove(buffFile.c_str());
|
|
|
|
|
|
|
|
imwrite(imgOut.c_str(), vidThumb);
|
2022-09-29 11:37:10 -04:00
|
|
|
|
2022-12-04 15:13:39 -05:00
|
|
|
genHTMLvid(vidOut, share);
|
2022-12-11 10:25:22 -05:00
|
|
|
genHTMLul(outDir, share->camName + ": " + dayStr, share);
|
|
|
|
genHTMLul(share->outDir, share->camName, share);
|
2022-12-16 18:24:18 -05:00
|
|
|
|
|
|
|
detLog("wr_out() -- finished()", share);
|
2022-09-22 20:57:46 -04:00
|
|
|
}
|
|
|
|
|
2022-12-04 15:13:39 -05:00
|
|
|
bool moDetect(const string &buffFile, Mat &vidThumb, shared_t *share)
|
2022-09-22 20:57:46 -04:00
|
|
|
{
|
2022-12-16 18:24:18 -05:00
|
|
|
detLog("mo_detect() -- start()", share);
|
|
|
|
detLog("buff_file: " + buffFile, share);
|
|
|
|
|
2022-09-22 20:57:46 -04:00
|
|
|
auto mod = false;
|
|
|
|
|
2022-12-11 16:10:04 -05:00
|
|
|
VideoCapture capture(buffFile.c_str());
|
2022-09-22 20:57:46 -04:00
|
|
|
|
|
|
|
if (capture.isOpened())
|
|
|
|
{
|
2022-12-17 10:34:40 -05:00
|
|
|
Mat prev;
|
|
|
|
Mat next;
|
|
|
|
auto frameCount = capture.get(CAP_PROP_FRAME_COUNT);
|
|
|
|
auto frameGaps = frameCount / share->frameGap;
|
2022-09-22 20:57:46 -04:00
|
|
|
|
2022-12-17 10:34:40 -05:00
|
|
|
detLog("frame_count: " + to_string(frameCount), share);
|
|
|
|
detLog("frame_gaps: " + to_string(frameGaps), share);
|
|
|
|
|
|
|
|
for (auto i = 0; i < frameGaps; i++)
|
2022-09-22 20:57:46 -04:00
|
|
|
{
|
2022-12-04 15:13:39 -05:00
|
|
|
if (prev.empty()) prev = frameFF(&capture, 1);
|
|
|
|
else prev = next.clone();
|
|
|
|
|
|
|
|
next = frameFF(&capture, share->frameGap);
|
|
|
|
|
2022-12-17 10:34:40 -05:00
|
|
|
if (imgDiff(prev, next, share))
|
2022-09-22 20:57:46 -04:00
|
|
|
{
|
2022-12-11 10:25:22 -05:00
|
|
|
resize(next, vidThumb, Size(1280, 720), INTER_LINEAR);
|
|
|
|
|
2022-12-17 10:34:40 -05:00
|
|
|
mod = true; break;
|
2022-09-22 20:57:46 -04:00
|
|
|
}
|
2022-12-16 18:24:18 -05:00
|
|
|
}
|
2022-09-22 20:57:46 -04:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2022-12-16 18:24:18 -05:00
|
|
|
detLog("failed to open the buff file for reading. check permissions and/or opencv's video-io support (gstreamer/ffmpeg).", share);
|
2022-09-22 20:57:46 -04:00
|
|
|
}
|
|
|
|
|
2022-12-17 10:34:40 -05:00
|
|
|
capture.release();
|
|
|
|
|
2022-12-16 18:24:18 -05:00
|
|
|
detLog("mo_detect() -- finished()", share);
|
|
|
|
|
2022-09-22 20:57:46 -04:00
|
|
|
return mod;
|
|
|
|
}
|