-
Notifications
You must be signed in to change notification settings - Fork 83
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
WIP : Made a screen recorder and automated tutorial for use of waypoints #1040
Conversation
* Allow specification of file for default * Simplify if condition
* Add wms_control tests * Add more mscolab tests * Add mpl_qtwidget coverage * Add mss_pyui coverage * Add transparency, noframe and xml checks * Add more wms tests * Test import with plugins * Add linearview tests * Add more multilayering tests * Revert to old testing.yml * Leave no dangling windows * Remove todo, move ConnectionError to bottom Co-authored-by: ReimarBauer <rb.proj@gmail.com>
…#1009) * removed functions from thermolib.py functions to be replaced by metpy were removed * fixed: flake8 * fixed: flake8 * migrated to metpy functions Co-Authored-By: J. Ungermann <28449201+joernu76@users.noreply.github.com> * Fixed: flake8 * Fixed: flake8 * Fixed tests * Fixed: flake8 * Fixed: failing tests * Ficed: tests * Units discarded upon returning results Co-Authored-By: J. Ungermann <28449201+joernu76@users.noreply.github.com> * `omega_to_w` migrated to metpy Co-authored-by: ReimarBauer <rb.proj@gmail.com> Co-authored-by: J. Ungermann <28449201+joernu76@users.noreply.github.com>
* updated documentation * improved install/update procedure Co-authored-by: Reimar Bauer <rb.proj@gmail.com>
* .format replaced with f" string * updated copyright year
Co-authored-by: ReimarBauer <rb.proj@gmail.com>
* fixed tableview not opening bug; added test * added raising of mscolab window after closing view
* preparation of v4.0.1 * updated install instruction Co-authored-by: J. Ungermann <j.ungermann@fz-juelich.de>
Stable to develop
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.
please move tutorials/requirements.txt to requirements.d/tutorials.txt
This file should only have later the new packages or different versions you need to use not the full mamba list of packages which are already installed.
We have already the requirements.d to collect lists for different purposes
next time when you want to merge changes from the main repository please do this by a seperated merge request. e.g. name it "merge develop to my branch" |
import os | ||
import sys | ||
import time | ||
import mss |
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 guess that this is another mss, with an identical name as our project, or?
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.
Yeah. This mss is (multi screen shot) Its used for grabbing images while recording. Since, it is a cross platform compatible, I used this. (And not pillow)
channels: | ||
- conda-forge | ||
- defaults | ||
prefix: C:\Users\HRITHIK\anaconda3\envs\gsoc\envs\gsoc |
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.
this is a constant on your system, is this needed for others?
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 actually created this yml env file purposefully to help in the creating of a new environment for anybody wanting to test my code. It's not needed later. (I guess I should remove this now.)
I'm not sure if the additional prefix tut_ before picures is needed. If you have no other directory in mind then it could be just pictures, or images? tutorials/tut pictures/zoom.PNG |
Okay. I will do it that way. |
So sorry for this. I actually had no idea this 'merge develop into GSOC21-HrithikKumarVerma' will be this big in changes. I will take care the next time. |
Yeah, it sounds good. 'Pictures' or simply 'Images' should do the work. Also since the tut_pictures here can give the idea of pictures of the tutorials to someone even if its not so..! Hence, I also think this name is not appropriate. |
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 a few comments regarding your FPS problem you mentioned last week.
cv2.resizeWindow(self.window_name, 480, 480) | ||
cv2.moveWindow(self.window_name, self.width - 480, 0) | ||
|
||
def get_fps(self): |
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.
Your loop in here does not contain everything you have in your capture loop.
The FPS you get here are always higher than your computer is able to produce, since the capture loop also writes to the mp4 file and is thus slower.
def capture(self): | ||
""" | ||
Captures the frames of the screen at the rate of fps frames/second and writes into the | ||
video writer object with the defined fourcc, codec and colour format. | ||
""" | ||
with mss.mss() as sct: | ||
bbox = {"top": 0, "left": 0, "width": self.width, "height": self.height} | ||
self.start_rec_time = time.time() | ||
print(f"Starting to record with FPS value {self.fps} ...") | ||
while self.record: | ||
img = sct.grab(bbox) | ||
img_np = np.array(img) | ||
img_final = cv2.cvtColor(img_np, cv2.COLOR_RGBA2RGB) | ||
cv2.imshow(self.window_name, img_final) | ||
self.recorded_video.write(img_final) | ||
# Exits the screen capturing when user press 'q' | ||
if cv2.waitKey(1) & 0xFF == ord('q'): | ||
break |
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.
Regardless of your FPS calculation, the time to record and write and image fluctuates and creates inconsistent results.
To achieve somewhat consistent FPS during your recording, it would make sense to keep track of the captured frames vs expected frames.
You can then duplicate old frames or wait additional time to exactly match your desired FPS.
Here I have a suggestion on how to do that:
def capture(self): | |
""" | |
Captures the frames of the screen at the rate of fps frames/second and writes into the | |
video writer object with the defined fourcc, codec and colour format. | |
""" | |
with mss.mss() as sct: | |
bbox = {"top": 0, "left": 0, "width": self.width, "height": self.height} | |
self.start_rec_time = time.time() | |
print(f"Starting to record with FPS value {self.fps} ...") | |
while self.record: | |
img = sct.grab(bbox) | |
img_np = np.array(img) | |
img_final = cv2.cvtColor(img_np, cv2.COLOR_RGBA2RGB) | |
cv2.imshow(self.window_name, img_final) | |
self.recorded_video.write(img_final) | |
# Exits the screen capturing when user press 'q' | |
if cv2.waitKey(1) & 0xFF == ord('q'): | |
break | |
def capture(self): | |
""" | |
Captures the frames of the screen at the rate of fps frames/second and writes into the | |
video writer object with the defined fourcc, codec and colour format. | |
""" | |
with mss.mss() as sct: | |
bbox = {"top": 0, "left": 0, "width": self.width, "height": self.height} | |
self.start_rec_time = time.time() | |
frame_time_ms = 1000 / self.fps | |
frames = 0 | |
print(f"Starting to record with FPS value {self.fps} ...") | |
while self.record: | |
img = sct.grab(bbox) | |
img_np = np.array(img) | |
img_final = cv2.cvtColor(img_np, cv2.COLOR_RGBA2RGB) | |
cv2.imshow(self.window_name, img_final) | |
self.recorded_video.write(img_final) | |
frames += 1 | |
expected_frames = ((time.time() - self.start_rec_time) * 1000) / frame_time_ms | |
surplus = frames - expected_frames | |
# Duplicate previous frame to meet FPS quota. Consider lowering the FPS instead! | |
if int(surplus) <= -1: | |
frames -= int(surplus) | |
for i in range(int(-surplus)): | |
self.recorded_video.write(img_final) | |
# Exits the screen capturing when user press 'q' | |
if cv2.waitKey(max(int(surplus * frame_time_ms), 1)) & 0xFF == ord('q'): | |
break |
Hey @Marilyth The code you suggested is much better than what I have tried myself. I have tried this thing before but not exactly like you. So, for much of the parts its working fine. The recorded video is not playing too fast as of now after implementing this code. Earlier when I was adding the repeated frames it was kind of slow and therefore, I discarded the idea. But the changes you have done in the waitkey() is nice and its recording and playing much better now. Thanks. |
superseeded by PR #1067 |
Here is a google doc file explaining the details:
https://docs.google.com/document/d/14nNaPpIvkWXEl3MwDzD_4BItpKhOaphvUSuP_rw5rxg/edit?usp=sharing