tkVideoUtils - Python module for playing videos and camera feeds in a Tkinter label, with recording functionality
tkVideoUtils is a Python module for playing and recording videos in GUIs created with tkinter. Using imageio-ffmpeg, webcams can be indexed and streamed in a tkinter Label. They can also be recorded (in their original resolution) by calling the start_recording()
function! This project was heavily inspired by huskeee's tkvideo library, check their project out!
- Clone the repo and run
setup.py
git clone https://github.com/wsarce/tkVideoUtils.git
python ./tkvideo/setup.py
or
- Install the package from PyPI
pip install tkVideoUtils
- Clone the repo and install the module in developer mode
git clone https://github.com/wsarce/tkVideoUtils.git
python ./tkvideo/setup.py develop
or
- Install the package from PyPI in editable mode
pip install -e tkvideoplayer
This will create a shim between your code and the module binaries that gets updated every time you change your code.
from tkinter import *
from ttkwidgets import TickScale
from tkvideoutils import VideoPlayer
from tkinter import filedialog, messagebox
def on_closing():
player.loading = False
root.quit()
root.destroy()
if __name__ == '__main__':
# create instance of window
root = Tk()
# set window title
root.title('Video Player')
# load images
pause_image = PhotoImage(file='pause.png')
play_image = PhotoImage(file='play.png')
skip_backward = PhotoImage(file='skip_backward.png')
skip_forward = PhotoImage(file='skip_forward.png')
# create user interface
button = Button(root, image=play_image)
forward_button = Button(root, image=skip_forward)
backward_button = Button(root, image=skip_backward)
video_label = Label(root)
video_path = 'recorded_video.mp4'
audio_path = 'recorded_video.wav'
slider_var = IntVar(root)
slider = TickScale(root, orient="horizontal", variable=slider_var)
# place elements
video_label.pack()
button.pack()
forward_button.pack()
backward_button.pack()
slider.pack()
if video_path:
# read video to display on label
player = VideoPlayer(root, video_path, audio_path, video_label, size=(700, 500),
play_button=button, play_image=play_image, pause_image=pause_image,
slider=slider, slider_var=slider_var, keep_ratio=True, cleanup_audio=True)
else:
messagebox.showwarning("Select Video File", "Please retry and select a video file.")
sys.exit(1)
player.set_clip(50, 70)
forward_button.config(command=player.skip_video_forward)
backward_button.config(command=player.skip_video_backward)
root.protocol("WM_DELETE_WINDOW", on_closing)
root.mainloop()
from tkinter import *
from tkvideoutils import VideoRecorder
from tkinter import messagebox
def merge_sources():
if player.merge_sources(merged_path, ffmpeg_exe):
print("Sources merged!")
else:
print("Something went wrong")
def stop_recording():
player.stop_recording()
player.stop_playback()
button['command'] = merge_sources
def start_recording():
player.start_recording()
button['command'] = stop_recording
if __name__ == '__main__':
# create instance of window
root = Tk()
# set window title
root.title('Video Player')
# load images
pause_image = PhotoImage(file='pause.png')
play_image = PhotoImage(file='play.png')
# create user interface
button = Button(root, image=play_image)
video_label = Label(root)
video_path = 'raw_video.mp4'
audio_path = 'recorded_video.wav'
merged_path = 'recorded_video.mp4'
# place elements
video_label.pack()
button.pack()
# Get existing video sources
video_sources = VideoRecorder.get_video_sources()
audio_sources = VideoRecorder.get_audio_sources()
print(video_sources, audio_sources)
# TODO: Fill out FFMPEG path
ffmpeg_exe = r''
if video_sources:
if video_path:
# read video to display on label
player = VideoRecorder(video_source=video_sources[0], audio_source=audio_sources[1],
video_path=video_path, audio_path=audio_path, fps=8, label=video_label,
size=(700, 500))
player.start_playback()
else:
messagebox.showwarning("Select Video File", "Please retry and select a video file.")
sys.exit(1)
button.config(command=start_recording)
root.mainloop()
else:
print("No video sources found!")
Have a problem that needs to be solved or a suggestion to make? See the issues page.
If you want to freeze your Python scripts that reference tkVideoUtils, there are some general notes to keep in mind:
- Due to the use of ImageIO, the lazy import error causes frozen Python scripts to fail to start or fail to execute the imageio codepaths. This can make it look like imageio-ffmpeg is failing with a backend issue. To circumvent this, follow this answer. This answer says to overwrite your imageio folder in your exe output directory with the imageio folder from your virtual environment (
venv\Lib\site-packages\imageio
). I can verify that this works. - I prefer copying the ffmpeg exe version that is packaged with imageio-ffmpeg into your exe directory in a known folder and updating
os.environ['IMAGEIO_FFMPEG_EXE']
with that directory. This ensures a known path.
Distributed under the MIT License. See LICENSE
for more information.
Walker Arce - [email protected] Project Link: https://github.com/wsarce/tkVideoUtils