Support the following options:

- The live camera display as you see it in the front-facing camera frame (like iPhone's Mirror Front Camera).
- The live camera frame is resizable.
Note: These options are turned off by default. Enabling both options may reduce performance by ~2%.

Signed-off-by: Vic P <vic4key@gmail.com>
This commit is contained in:
Vic P
2024-08-22 00:35:05 +07:00
parent 42b54ef330
commit 4f62119c2e
4 changed files with 42 additions and 11 deletions

View File

@@ -18,7 +18,9 @@ ROOT_WIDTH = 600
PREVIEW = None
PREVIEW_MAX_HEIGHT = 700
PREVIEW_MAX_WIDTH = 1200
PREVIEW_MAX_WIDTH = 1200
PREVIEW_DEFAULT_WIDTH = 960
PREVIEW_DEFAULT_HEIGHT = 540
RECENT_DIRECTORY_SOURCE = None
RECENT_DIRECTORY_TARGET = None
@@ -123,7 +125,7 @@ def create_preview(parent: ctk.CTkToplevel) -> ctk.CTkToplevel:
preview.title('Preview')
preview.configure()
preview.protocol('WM_DELETE_WINDOW', lambda: toggle_preview())
preview.resizable(width=False, height=False)
preview.resizable(width=True, height=True)
preview_label = ctk.CTkLabel(preview, text=None)
preview_label.pack(fill='both', expand=True)
@@ -209,6 +211,21 @@ def check_and_ignore_nsfw(target, destroy: Callable = None) -> bool:
else: return False
def fit_image_to_size(image, width: int, height: int):
if width is None and height is None:
return image
h, w, _ = image.shape
ratio_h = 0.0
ratio_w = 0.0
if width > height:
ratio_h = height / h
else:
ratio_w = width / w
ratio = max(ratio_w, ratio_h)
new_size = (int(ratio * w), int(ratio * h))
return cv2.resize(image, dsize=new_size)
def render_image_preview(image_path: str, size: Tuple[int, int]) -> ctk.CTkImage:
image = Image.open(image_path)
if size:
@@ -273,14 +290,14 @@ def webcam_preview():
global preview_label, PREVIEW
cap = cv2.VideoCapture(0) # Use index for the webcam (adjust the index accordingly if necessary)
cap.set(cv2.CAP_PROP_FRAME_WIDTH, 960) # Set the width of the resolution
cap.set(cv2.CAP_PROP_FRAME_HEIGHT, 540) # Set the height of the resolution
cap.set(cv2.CAP_PROP_FPS, 60) # Set the frame rate of the webcam
camera = cv2.VideoCapture(0) # Use index for the webcam (adjust the index accordingly if necessary)
camera.set(cv2.CAP_PROP_FRAME_WIDTH, 960) # Set the width of the resolution
camera.set(cv2.CAP_PROP_FRAME_HEIGHT, 540) # Set the height of the resolution
camera.set(cv2.CAP_PROP_FPS, 60) # Set the frame rate of the webcam
PREVIEW_MAX_WIDTH = 960
PREVIEW_MAX_HEIGHT = 540
preview_label.configure(image=None) # Reset the preview image before startup
preview_label.configure(width=PREVIEW_DEFAULT_WIDTH, height=PREVIEW_DEFAULT_HEIGHT) # Reset the preview image before startup
PREVIEW.deiconify() # Open preview window
@@ -288,8 +305,8 @@ def webcam_preview():
source_image = None # Initialize variable for the selected face image
while True:
ret, frame = cap.read()
while camera:
ret, frame = camera.read()
if not ret:
break
@@ -299,12 +316,18 @@ def webcam_preview():
temp_frame = frame.copy() #Create a copy of the frame
if modules.globals.live_mirror:
temp_frame = cv2.flip(temp_frame, 1) # horizontal flipping
if modules.globals.live_resizable:
temp_frame = fit_image_to_size(temp_frame, PREVIEW.winfo_width(), PREVIEW.winfo_height())
for frame_processor in frame_processors:
temp_frame = frame_processor.process_frame(source_image, temp_frame)
image = cv2.cvtColor(temp_frame, cv2.COLOR_BGR2RGB) # Convert the image to RGB format to display it with Tkinter
image = Image.fromarray(image)
image = ImageOps.contain(image, (PREVIEW_MAX_WIDTH, PREVIEW_MAX_HEIGHT), Image.LANCZOS)
image = ImageOps.contain(image, (temp_frame.shape[1], temp_frame.shape[0]), Image.LANCZOS)
image = ctk.CTkImage(image, size=image.size)
preview_label.configure(image=image)
ROOT.update()
@@ -312,5 +335,5 @@ def webcam_preview():
if PREVIEW.state() == 'withdrawn':
break
cap.release()
camera.release()
PREVIEW.withdraw() # Close preview window when loop is finished