From d154c56566b0fc20c9ed1e1c59bb5ede26fecee3 Mon Sep 17 00:00:00 2001 From: boltgolt Date: Thu, 3 Dec 2020 00:36:22 +0100 Subject: [PATCH] First working implementation of auth ui in gtk --- howdy-gtk/authsticky.py | 125 ++++++++++++++++++++++++++++++++++++++++ howdy-gtk/logo.png | Bin 0 -> 13307 bytes src/compare.py | 58 ++++++++++++++++--- 3 files changed, 174 insertions(+), 9 deletions(-) create mode 100644 howdy-gtk/authsticky.py create mode 100644 howdy-gtk/logo.png diff --git a/howdy-gtk/authsticky.py b/howdy-gtk/authsticky.py new file mode 100644 index 0000000..0e3e040 --- /dev/null +++ b/howdy-gtk/authsticky.py @@ -0,0 +1,125 @@ +# Shows a floating window when authenticating +import cairo +import gi +import signal +import sys +import os + +# Make sure we have the libs we need +gi.require_version("Gtk", "3.0") +gi.require_version("Gdk", "3.0") + +# Import them +from gi.repository import Gtk as gtk +from gi.repository import Gdk as gdk +from gi.repository import GObject as gobject + +# Set window size constants +windowWidth = 400 +windowHeight = 100 + +message = "Starting up... " +subtext = "" + + +class StickyWindow(gtk.Window): + def __init__(self): + gtk.Window.__init__(self) + + self.set_title("Howdy Authentication UI") + + # Set a bunch of options to make the window stick and be on top of everything + self.stick() + self.set_gravity(gdk.Gravity.STATIC) + self.set_resizable(False) + self.set_keep_above(True) + self.set_app_paintable(True) + self.set_skip_pager_hint(True) + self.set_skip_taskbar_hint(True) + self.set_can_focus(False) + self.set_can_default(False) + self.set_focus(None) + self.set_type_hint(gdk.WindowTypeHint.NOTIFICATION) + self.set_decorated(False) + + # Draw + self.connect("draw", self.draw) + self.connect("destroy", self.exit) + self.connect("button-press-event", self.exit) + + darea = gtk.DrawingArea() + darea.set_size_request(windowWidth, windowHeight) + self.add(darea) + + screen = self.get_screen() + visual = screen.get_rgba_visual() + if visual and screen.is_composited(): + self.set_visual(visual) + + # TODO: handle more than 1 screen + self.move((screen.get_width() / 2) - (windowWidth / 2), 0) + + self.show_all() + self.resize(windowWidth, windowHeight) + + gobject.timeout_add(100, self.test) + + gtk.main() + + def draw(self, widget, ctx): + # Change cursor to the kill icon + self.get_window().set_cursor(gdk.Cursor(gdk.CursorType.PIRATE)) + + ctx.set_source_rgba(0, 0, 0, .9) + ctx.set_operator(cairo.OPERATOR_SOURCE) + ctx.paint() + ctx.set_operator(cairo.OPERATOR_OVER) + + dir = os.path.dirname(os.path.abspath(__file__)) + + image_surface = cairo.ImageSurface.create_from_png(dir + "/logo.png") + ratio = float(windowHeight - 20) / float(image_surface.get_height()) + + ctx.translate(15, 10) + ctx.scale(ratio, ratio) + ctx.set_source_surface(image_surface) + ctx.paint() + + ctx.set_source_rgba(255, 255, 255, .9) + ctx.set_font_size(80) + + if subtext: + ctx.move_to(380, 145) + else: + ctx.move_to(380, 170) + + ctx.select_font_face("Arial", cairo.FONT_SLANT_NORMAL, cairo.FONT_WEIGHT_NORMAL) + ctx.show_text(message) + + ctx.set_source_rgba(230, 230, 230, .8) + ctx.set_font_size(40) + ctx.move_to(380, 210) + ctx.select_font_face("Arial", cairo.FONT_SLANT_NORMAL, cairo.FONT_WEIGHT_NORMAL) + ctx.show_text(subtext) + + def exit(self, widget, context): + gtk.main_quit() + + def test(self): + global message, subtext + + comm = sys.stdin.readline()[:-1] + + if comm: + if comm[0] == "M": + message = comm[2:] + if comm[0] == "S": + subtext = comm[2:] + + self.queue_draw() + gobject.timeout_add(100, self.test) + + +signal.signal(signal.SIGINT, signal.SIG_DFL) + +window = StickyWindow() diff --git a/howdy-gtk/logo.png b/howdy-gtk/logo.png new file mode 100644 index 0000000000000000000000000000000000000000..78c620b37b91f6bf98ebfc0d63fd8defa2e295ea GIT binary patch literal 13307 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 literal 0 HcmV?d00001 diff --git a/src/compare.py b/src/compare.py index d0ea5ea..8427363 100644 --- a/src/compare.py +++ b/src/compare.py @@ -17,12 +17,21 @@ import configparser import dlib import cv2 import datetime +import subprocess import snapshot import numpy as np import _thread as thread from recorders.video_capture import VideoCapture +def exit(code): + """Exit while closeing howdy-gtk properly""" + global gtk_proc + + gtk_proc.terminate() + sys.exit(code) + + def init_detector(lock): """Start face detector, encoder and predictor in a new thread""" global face_detector, pose_predictor, face_encoder @@ -33,7 +42,7 @@ def init_detector(lock): print("\n\tcd " + PATH + "/dlib-data") print("\tsudo ./install.sh\n") lock.release() - sys.exit(1) + exit(1) # Use the CNN detector if enabled if use_cnn: @@ -62,9 +71,24 @@ def make_snapshot(type): ]) +def send_to_ui(type, message): + """Send message to the auth ui""" + global gtk_proc + + # Format message so the ui can parse it + message = type + "=" + message + " \n" + + # Try to send the message to the auth ui, but it's okay if that fails + try: + gtk_proc.stdin.write(bytearray(message.encode("ascii"))) + gtk_proc.stdin.flush() + except IOError as err: + pass + + # Make sure we were given an username to tast against if len(sys.argv) < 2: - sys.exit(12) + exit(12) # Get the absolute path to the current directory PATH = os.path.abspath(__file__ + "/..") @@ -90,6 +114,11 @@ face_detector = None pose_predictor = None face_encoder = None +# Start the auth ui +gtk_proc = subprocess.Popen(["python3", "-u", "../howdy-gtk/authsticky.py"], stdin=subprocess.PIPE, stdout=subprocess.DEVNULL, stderr=subprocess.DEVNULL) +# Write to the stdin to redraw ui +send_to_ui("M", "Starting up...") + # Try to load the face model from the models folder try: models = json.load(open(PATH + "/models/" + user + ".dat")) @@ -97,11 +126,11 @@ try: for model in models: encodings += model["data"] except FileNotFoundError: - sys.exit(10) + exit(10) # Check if the file contains a model if len(models) < 1: - sys.exit(10) + exit(10) # Read config from disk config = configparser.ConfigParser() @@ -156,18 +185,29 @@ timeout = config.getint("video", "timeout") dark_threshold = config.getfloat("video", "dark_threshold") end_report = config.getboolean("debug", "end_report") +# Initiate histogram equalization +clahe = cv2.createCLAHE(clipLimit=2.0, tileGridSize=(8, 8)) + +# Let the ui know that we're ready +send_to_ui("M", "Identifying you...") + # Start the read loop frames = 0 valid_frames = 0 timings["fr"] = time.time() dark_running_total = 0 -clahe = cv2.createCLAHE(clipLimit=2.0, tileGridSize=(8, 8)) - while True: # Increment the frame count every loop frames += 1 + # Form a string to let the user know we're real busy + ui_subtext = "Scanned " + str(valid_frames) + " frames" + if (dark_tries > 1): + ui_subtext += " (skipped " + str(dark_tries) + " dark frames)" + # Show it in the ui as subtext + send_to_ui("S", ui_subtext) + # Stop if we've exceded the time limit if time.time() - timings["fr"] > timeout: # Create a timeout snapshot if enabled @@ -177,9 +217,9 @@ while True: if dark_tries == valid_frames: print("All frames were too dark, please check dark_threshold in config") print("Average darkness: " + str(dark_running_total / max(1, valid_frames)) + ", Threshold: " + str(dark_threshold)) - sys.exit(13) + exit(13) else: - sys.exit(11) + exit(11) # Grab a single frame of video frame, gsframe = video_capture.read_frame() @@ -283,7 +323,7 @@ while True: make_snapshot("SUCCESSFUL") # End peacefully - sys.exit(0) + exit(0) if exposure != -1: # For a strange reason on some cameras (e.g. Lenoxo X1E)