-
Notifications
You must be signed in to change notification settings - Fork 86
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
added cropping of capture/background #153
base: main
Are you sure you want to change the base?
Conversation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Couldn't test things yet, but those are what I noticed while skimming over.
I will review my code and hopefully fix the little issues. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
capGeo.value().first
/capGeo.value().second
can be shortened to capGeo->first
/capGeo->second
app/background.cc
Outdated
frm = pbkd->frame; | ||
} else { | ||
// resize still image as requested into out | ||
cv::resize(pbkd->raw, out, cv::Size(width, height)); | ||
cv::Rect_<int> crop = calcCropping(pbkd->raw.cols,pbkd->raw.rows,width,height); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
cv::Rect_<int> crop = calcCropping(pbkd->raw.cols,pbkd->raw.rows,width,height); | |
cv::Rect crop = calcCropping(pbkd->raw.cols, pbkd->raw.rows, width, height); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I have updates my cropping branch accordingly. Your suggestion is within my code
On my fork jjsarton/backscrub the origin branch contain the latest code including your suggestions or the revised code. I thing that your suggestion concerning line 680 to 687 (grab_background) may not be changed we pass 2 variables and don't need to use a class in order to put them the variables into a class and extracting them later! |
Github is very slow! |
Looks already good so far. Care to squash/fixup those commits into one (or few) … |
I have to learn how to deal with GitHub! I hope that I will learn this. |
@BenBE |
app/background.cc
Outdated
@@ -183,11 +185,17 @@ int grab_background(std::shared_ptr<background_t> pbkd, int width, int height, c | |||
if (pbkd->video) { | |||
// grab frame & frame no. under mutex | |||
std::unique_lock<std::mutex> hold(pbkd->rawmux); | |||
cv::resize(pbkd->raw, out, cv::Size(width, height)); | |||
cv::Rect crop = calcCropping(pbkd->raw.cols, pbkd->raw.rows, width, height); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We could lift this calculation out of the processing loop to a structure variable, as sizes will not change during operation.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
see below
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Size will not change, the frame content will change. Mofifying this implies:
if ! rect_calculated
crop = calc_cropping()
else
crop = get_stored_crop_value()
...
I don't think that the calculation will take a lot ot time more than filling the cv::Rect from already calculated variables.
app/background.cc
Outdated
frm = pbkd->frame; | ||
} else { | ||
// resize still image as requested into out | ||
cv::resize(pbkd->raw, out, cv::Size(width, height)); | ||
cv::Rect crop = calcCropping(pbkd->raw.cols, pbkd->raw.rows, width, height); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
..as above, could be removed in favour of a state variable, calculated just once.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I must think about that.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I must review this part.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I have put the variable bg_stored into the structure background_t.
The code is now:
} else {
if (!pbkd->bg_stored) {
// resize still image as requested into out
cv::Rect crop = bs_calc_cropping(pbkd->raw.cols, pbkd->raw.rows, width, height);
// Under some circumstances we must do the job in two steps!
// Otherwise this resize(pbkd->raw(crop), pbkd->raw, ...) may fail.
pbkd->raw(crop).copyTo(pbkd->raw);
cv::resize(pbkd->raw, pbkd->raw, cv::Size(width, height));
pbkd->bg_stored = true;
}
out = pbkd->raw;
frm = 1;
}
return frm;
For the video processing the code remain to the old code, we will probably every time read a new picture from the video source.
Please note that the changes are not effective now, the tests for video or still image don't work as required.
I propose to detect according to the value cnt which has the value -1 for still image and a greater value for video.
I have also changed the corresponding code.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Don't worry too much about this, it's a minor performance enhancement to avoid a couple of floating point ops per frame, when we are running a whole inference model too.. I'd rather the code was readable than maximum speed 😄
I have pushed the modified code to my cropping branch. |
app/background.cc
Outdated
@@ -18,6 +20,7 @@ struct background_t { | |||
int frame; | |||
double fps; | |||
cv::Mat raw; | |||
int bg_stored; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
bool
perhaps as it's used only for true/false?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You are right, I have modified this. Initializing was done with false, setting with true.
app/background.cc
Outdated
@@ -143,7 +147,7 @@ std::shared_ptr<background_t> load_background(const std::string& path, int debug | |||
// if: can read 2 video frames => it's a video | |||
// else: is loaded as an image => it's an image | |||
// else: it's not usable. | |||
if (pbkd->cap.read(pbkd->raw) && pbkd->cap.read(pbkd->raw)) { | |||
if (cnt > -1) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If I recall, I chose this current method as cnt
could be > 1 for some image files (multiple resolutions?) but they would not play as a video... please test with all the variations in backgrounds
folder 😄
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I will perform the tests. Using fps which shall be greater than 0.00000 for a video may be better.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Unfortunately, my system don't work with animated.gif. Due to this I can't check if the fps which would be processed on systems allowing this will return a frame rate of 45 Fps (value obtained while converting the file via ffmpeg to a stream.
Jpg file may contain a thumbnail image, do reading twice work, and the file is recognized as video. Reading 3 times will give the expected result, but this shall not be the right way.
The test for picture/video is now based on the fps. I think that this shall always work.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'll grab your PR and check what I find here in the next day or so - thanks.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
OK, I've checked the behaviour as the current PR has it (fps > 0
), and it detects all the backgrounds as videos, but does not fail, since the video loop logic resets the position on each request... we may be able to simplify all this to assume video at all times?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I am surprised!
The backsrcrub binary for the cropping branch work as expected, a video is recognized as video and pictures as pictures.
For total_landscaping.jpg I get as output:
background properties:
vid: no
fcc: 00000000 ()
fps: 0.000000
cnt: -1
What tell your system?
I use Fedora 36 XFCE with opencv 4.5.5. What do you use?
May be that we check for fps > 0.001 in order to have the right condition.
I have tried the following on my development environment:
int w1,w2=0;
if(pbkd->cap.read(pbkd->raw)) {
w1=pbkd->raw.cols;
if (pbkd->cap.read(pbkd->raw)) {
w2=pbkd->raw.cols;
}
}
if(w2 == w1) {
This is basically the same as the old condition, but I assume that the width of 2 consecutive images has to be the same.
The final test will pass if we have a video, fail if we have an image, even width thumbnails (must have a lower size).
The detection was okay on my system.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
According to opencv cap.get(cv::CAP_PROP_FRAME_COUNT) return the 'Number of frames in the video file'
The first intention to use the count as flag for video or still image, what okay. Asking for CAP_PROP_FPS shall also work.
Work with images as if they were a video is not a great idea. If the image has a big size, reading, ... will take more time as
Retrieving the thumb as now realized within background.cc (Your suggestion).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@phlash If I recall, I chose this current method as cnt could be > 1 for some image files (multiple resolutions?) but they would not play as a video... please test with all the variations in backgrounds folder smile
This was your statement, this should not be true if I see the definition for CAP_PROP_FRAME_COUNT.
For my image, which is recognized as video (old code) I get -1 as value. Am image is not considered as frame.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@jjsarton I'm running on Debian stable (11), OpenCV 4.5.1, here's what I get for each background type:
animated.gif
=> vid: yes, fps: 45.0.., cnt: 36background_bauhaus.png
=> vid: yes, fps: 25.0.., cnt: -2147483648rotating_earth.webm
=> vid: yes, fps: 30.0.., cnt: 916total_landscaping.jpg
=> vid: yes, fps: 25.0.., cnt: 1
..so this looks like we are heavily dependant on unstable OpenCV behaviour 😞, and the reason I chose to ignore both fps and cnt, instead attempting to load two frames in sequence.
Thanks for your patience @jjsarton, this is looking good. You might have missed a comment I put on the issue: #149 (comment), which refers back to @BenBE asking for the cropping behaviour to be controlled by a switch, as it's opinionated behaviour that others may not want. |
Pushed the actual revised version. |
Could you squash all the fixup and correction commits into their respective commit of where they should have gone in the first place? You can/should keep commits that introduce/change behavior though. If I'm not too mistaken you should end up at around 5-ish commits. Makes the whole commit history much more reasonable. FWIW: Each (intermediate) commit should compile on its own. |
I will not do this (not meaning full). My cropping directory respect the suggestion done unless there was not okay. |
Unfortunately I'm not sure what you were trying to say and how that related to the comment of mine that you quoted. |
I have configured and installed my own opencv version. With this version ffmpeg work and unfortunately, still picture are recognized as video. In order to solve this I modified (on my test version) background.cc, load_background).
The test video or still picture is now
I have tested this against the original installed opencv with don*t support ffmpeg and my own compiled opencv. For both the video detection worked. I propose that I implement this within my cropping branch. We can also delete the comments concerning the detection or add some if you tell me what I should insert. |
I see a couple of issues with this approach:
My existing implementation is a reduced form of this function, reading two frames to detect a video source. May I suggest we leave the existing mechanism alone, to get your work here merged? |
Improvements:Detect kind of background fileThe detection video or still image ist done with:
We have the following cases:
Opencv with ffmpegNo further changes needed Opencv with gstreamerGstreamer don't respect the loop indicator, without the check if Within the read thread the frame number is checked against the Not fixed behaviour
This must not been fixed, the user shall use a correct file. TestsTest were performed with various more files as such delivered with
The other version was an own compiled openvc:
Attached the result of git status against the last commit. |
I think that my code can remain how it is with the following exceptions: |
We may conditionaly include cv::imcount(). If we have this after the #include lines, we have knowledge about the used opencv version.
The modified code will be:
With this, the output messages are ok if the OCV version is high enough. If OCV support only gstreamer and the version is too old, line
will be reached if a video file is not recognized, but opened (cnt==-1). We can also modify the text to |
@jjsarton Thank you for the effort investigating the behaviour of OpenCV with various input files.. can I ask you to move that work (and related code changes) to a fresh PR against issue #158 please? It's not directly connected to your work here on croppping, and I'd like to get this work completed for the benefit of others, then we can spend more time on the format issue(s). Many thanks, |
A lot to do! |
@jjsarton I personally prefer small and concise PRs with focussed changes. Currently this PR consists of >20 commits which I already asked previously to squash down into a more sensible set of commits. As this was not done yet I refrained from touching anywhere near the merge button for this PR. ;-) If you have crashes or other bugs that are unrelated to the core issue of an PR, they should be separate. There's no problem with having multiple PRs in parallel aiming at specific aspects of the code. In fact: Doing so makes integrating them actually easier. If there are some dependencies for the order of PRs, just state them. Blowing up one PR over weeks doesn't make merging it any easier. Marking this as draft for now, until the commit squashing has been resolved. |
@BenBE I Know, I had to learn, and my approach was not the best. The next PR I will prepare will only cover a problem and the corresponding code, so that the chance that there will not be a need to request many changes. |
There's absolutely no problem if a PR accumulates many comments for changes that need to be done. In fact with any non-trivial change this is completely natural. But once those are resolved would you rather read a commit history of 24 changes partially reverting each other or a concise set of about 5-10 commits "telling a story" of what needed to be changed to get to the solution? Thus please have a look at rewriting your commit history with |
@BenBE I has already wrote a reply to a comment like: # 153 I will definitely do this, this IMHO not a good idea. I have joined diff files against the floe/main and the (not pushed code) I would like to have. The reason is that backscrub shall work on different distributions, not only Debian or Debian based. Some Distribution have integrates ffmpeg within OCV, others don't do this. The diff files contain all changes. deepseek.cc (6 changes), libbackscrub.h (1 change) and libbackscrub.cc (2 changes). There include only the changes we have discussed. For background.cc, there are actually 6 changes. The diff is performed against a not pushed version and contain, if possible, The file type detection as realized with the main sources is definitively worse. Reading a still image 2 times is possible with The only subject of changes is normally (I assume that the other file are as wanted) background.cc. background.cc.txt |
Added cropping
Fixes #149