diff --git a/README.md b/README.md index f75c6bf..50930d4 100644 --- a/README.md +++ b/README.md @@ -19,7 +19,6 @@ It includes the XWinWrap binary and source code for Shantanu Goel's version of X # TODO * Better/automatic screen detection. -* Run chmod against newly created launch scripts. # Credit diff --git a/bin/gwinwrap-0-0-1-x64.deb b/bin/gwinwrap-0-0-1-x64.deb deleted file mode 100644 index 3c3e925..0000000 Binary files a/bin/gwinwrap-0-0-1-x64.deb and /dev/null differ diff --git a/bin/gwinwrap-0-0-2-x64.deb b/bin/gwinwrap-0-0-2-x64.deb deleted file mode 100644 index b7801e9..0000000 Binary files a/bin/gwinwrap-0-0-2-x64.deb and /dev/null differ diff --git a/src/debs/chownAll.sh b/src/debs/chown_all.sh similarity index 100% rename from src/debs/chownAll.sh rename to src/debs/chown_all.sh diff --git a/src/debs/gwinwrap-0-0-1-x64/DEBIAN/control b/src/debs/gwinwrap-0-0-1-x64/DEBIAN/control deleted file mode 100644 index a23c389..0000000 --- a/src/debs/gwinwrap-0-0-1-x64/DEBIAN/control +++ /dev/null @@ -1,8 +0,0 @@ -Package: gwinwrap64 -Version: 0.0-1 -Section: python -Priority: optional -Architecture: amd64 -Depends: ffmpegthumbnailer (>= 2.0.10-0.1), mplayer (>=2.0-728-g2c378c7-4), gifsicle (>=1.86-1), nitrogen (>=1.5.2-2), xscreensaver (>=5.36-1ubuntu1), xscreensaver-gl (>=5.36-1ubuntu1), xscreensaver-gl-extra (>=5.36-1ubuntu1), xscreensaver-screensaver-dizzy (>=0.3-3), xscreensaver-screensaver-bsod (>=5.36-1ubuntu1), xscreensaver-data (>=5.36-1ubuntu1), xscreensaver-data-extra (>=5.36-1ubuntu1), xscreensaver-screensaver-webcollage (>=5.36-1ubuntu1) -Maintainer: Maxim Stewart <1itdominator@gmail.com> -Description: GWinWrap is a GUI to handle setting XWinWrap options. diff --git a/src/debs/gwinwrap-0-0-1-x64/DEBIAN/postrm b/src/debs/gwinwrap-0-0-1-x64/DEBIAN/postrm deleted file mode 100755 index 0f30ccd..0000000 --- a/src/debs/gwinwrap-0-0-1-x64/DEBIAN/postrm +++ /dev/null @@ -1,11 +0,0 @@ -#!/bin/bash -#postrm (script executed after uninstalling the package) -#set -e - -if [ -f /bin/xwinwrap ]; then - rm /bin/xwinwrap -fi - -if [ -d /opt/GWinWrap ]; then - rm -rf /opt/GWinWrap -fi diff --git a/src/debs/gwinwrap-0-0-1-x64/bin/gwinwrap b/src/debs/gwinwrap-0-0-1-x64/bin/gwinwrap deleted file mode 100755 index 2166a10..0000000 Binary files a/src/debs/gwinwrap-0-0-1-x64/bin/gwinwrap and /dev/null differ diff --git a/src/debs/gwinwrap-0-0-1-x64/bin/xwinwrap b/src/debs/gwinwrap-0-0-1-x64/bin/xwinwrap deleted file mode 100755 index 26eafd7..0000000 Binary files a/src/debs/gwinwrap-0-0-1-x64/bin/xwinwrap and /dev/null differ diff --git a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/GWinWrap.desktop b/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/GWinWrap.desktop deleted file mode 100644 index 543fdb6..0000000 --- a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/GWinWrap.desktop +++ /dev/null @@ -1,9 +0,0 @@ -[Desktop Entry] -Encoding=UTF-8 -Name=GWinWrap -Comment=Glade gui with python controls for XWinWrap -Exec=gwinwrap -Icon=/opt/GWinWrap/resources/icons/GWinWrap.png -Terminal=false -Type=Application -Categories=Accessories;System;Settings; diff --git a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/__init__.py b/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/__init__.py deleted file mode 100644 index 0beb3ee..0000000 --- a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/__init__.py +++ /dev/null @@ -1,41 +0,0 @@ -#!/usr/bin/python3 - -# Gtk imports -import gi, faulthandler, signal -gi.require_version('Gtk', '3.0') - -from gi.repository import Gtk as gtk -from gi.repository import Gdk as gdk -from gi.repository import GLib - -# Python imports -import inspect - -from setproctitle import setproctitle - -# Application imports -from utils import Settings -from signal_classes import CrossClassSignals - - -class Main: - def __init__(self): - setproctitle('GWinWrap') - GLib.unix_signal_add(GLib.PRIORITY_DEFAULT, signal.SIGINT, gtk.main_quit) - faulthandler.enable() # For better debug info - - settings = Settings() - builder = settings.returnBuilder() - - # Gets the methods from the classes and sets to handler. - # Then, builder connects to any signals it needs. - classes = [CrossClassSignals(settings)] - - handlers = {} - for c in classes: - methods = inspect.getmembers(c, predicate=inspect.ismethod) - handlers.update(methods) - - builder.connect_signals(handlers) - window = settings.createWindow() - window.show() diff --git a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/__main__.py b/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/__main__.py deleted file mode 100644 index 60c7ea2..0000000 --- a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/__main__.py +++ /dev/null @@ -1,9 +0,0 @@ -from __init__ import Main, gtk - - -if __name__ == "__main__": - try: - main = Main() - gtk.main() - except Exception as e: - print(e) diff --git a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/gwinwrap b/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/gwinwrap deleted file mode 100755 index 2166a10..0000000 Binary files a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/gwinwrap and /dev/null differ diff --git a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/resources/Main_Window.glade b/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/resources/Main_Window.glade deleted file mode 100644 index 495ebfe..0000000 --- a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/resources/Main_Window.glade +++ /dev/null @@ -1,844 +0,0 @@ - - - - - - - inode/directory - - - - - - - - - - True - False - gtk-clear - 3 - - - True - False - gtk-quit - 3 - - - True - False - gtk-cancel - 3 - - - True - False - gtk-jump-to - 3 - - - True - False - gtk-save - 3 - - - True - False - gtk-save - 3 - - - True - False - Settings.... - gtk-properties - 3 - - - True - False - gtk-media-play - 3 - - - True - False - gtk-media-stop - 3 - - - 950 - 600 - False - GWinWrap - center - 950 - 600 - icons/GWinWrap.png - center - - - - - - True - False - - - True - False - 15 - 15 - 15 - vertical - - - True - False - 5 - - - True - False - 15 - Note: Double click an image to view the video or image. - - - True - True - 0 - - - - - True - False - Chose Dream Scene / Image Directory - select-folder - False - Folders - Dream Scene / Image Dir - - - - False - True - 1 - - - - - True - True - True - settingsImage - True - - - - False - True - 2 - - - - - False - True - 0 - - - - - True - False - True - - - False - True - 1 - - - - - True - True - in - - - True - False - - - True - False - vertical - 10 - 10 - True - True - - - 640 - 525 - True - False - Choose Image/Video Directory... - - - - - - 0 - 0 - - - - - - - - - True - True - 2 - - - - - Clear - True - True - True - clearImage - True - - - - False - True - 3 - - - - - True - True - 0 - - - - - 300 - True - False - 10 - 15 - 15 - 15 - False - vertical - - - True - False - vertical - - - Use XScreenSaver - True - True - False - center - 5 - True - - - - False - True - 0 - - - - - True - True - in - - - True - False - True - XScreensaver List - False - - - - - - - - XScreensaves - - - - 0 - - - - - - - - - True - True - 1 - - - - - True - True - 0 - - - - - True - False - False - vertical - - - True - False - vertical - - - True - False - - - True - False - 10 - 10 - Playback Resolutions - - - True - True - 0 - - - - - True - False - 10 - 10 - Position Offset - - - True - True - 1 - - - - - False - True - 0 - - - - - True - False - - - True - False - 3 - - 7680x4320 - 3840x2160 - 2048x1080 - 1920x1080 - 1440x720 - 1600x900 - 1280x720 - 800x600 - - - - True - True - 0 - - - - - True - False - - - True - True - 1 - - - - - False - True - 1 - - - - - False - True - 0 - - - - - True - False - vertical - - - True - False - 10 - 5 - Save Path - - - True - True - 0 - - - - - True - False - 0 - - .animatedBGstarter.sh - .animatedBGstarter2.sh - .animatedBGstarter3.sh - - - - True - True - 1 - - - - - False - True - 1 - - - - - True - False - - - Save - True - True - True - True - True - saveImage - True - - - - 1 - 0 - - - - - (Re)Start - True - True - True - True - True - startImage - True - - - - 0 - 0 - - - - - Stop - True - True - True - True - True - stopImage - True - - - - 0 - 1 - - - - - Close - True - True - True - True - True - closeImage - True - - - - 1 - 1 - - - - - False - True - 2 - - - - - False - False - end - 1 - - - - - False - True - 1 - 1 - - - - - - - 640 - 525 - False - 350 - True - True - helpLabel - bottom - False - - - True - False - vertical - - - True - False - - - True - True - True - Close Demo Window - closePopupImage - True - - - - False - True - end - 0 - - - - - False - True - 0 - - - - - True - False - 0 - none - - - True - False - - - - - True - True - 1 - - - - - - - 640 - 525 - False - True - True - helpLabel - bottom - - - True - False - vertical - - - True - False - bottom - - - Main Image Viewer - True - True - True - openProgImage - True - - - - False - True - 0 - - - - - True - True - True - True - - - - False - True - 1 - - - - - False - True - 0 - - - - - True - True - in - False - - - True - False - - - True - False - gtk-missing-image - 6 - - - - - - - True - True - 1 - - - - - - - 250 - False - button1 - - - True - False - vertical - - - True - False - - - True - False - icons/folder.png - - - False - True - 0 - - - - - 330 - 26 - True - True - Set Custom Default Path - Set Custom Default Path - - - False - True - 1 - - - - - False - True - 0 - - - - - True - False - - - True - False - icons/player.png - - - False - True - 0 - - - - - 330 - 26 - True - True - Set Custom Video Player - Set Custom Video Player - - - False - True - 1 - - - - - False - True - 1 - - - - - True - False - - - True - False - icons/picture.png - - - False - True - 0 - - - - - 330 - 26 - True - True - Set Custom Image Viewer - Set Custom Image Viewer - - - False - True - 1 - - - - - False - True - 2 - - - - - Save - True - True - True - saveImag - True - - - - False - True - 3 - - - - - - diff --git a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/resources/icons/GWinWrap.png b/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/resources/icons/GWinWrap.png deleted file mode 100644 index cdd708d..0000000 Binary files a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/resources/icons/GWinWrap.png and /dev/null differ diff --git a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/resources/icons/folder.png b/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/resources/icons/folder.png deleted file mode 100644 index 909f052..0000000 Binary files a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/resources/icons/folder.png and /dev/null differ diff --git a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/resources/icons/picture.png b/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/resources/icons/picture.png deleted file mode 100644 index 46f1ae6..0000000 Binary files a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/resources/icons/picture.png and /dev/null differ diff --git a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/resources/icons/player.png b/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/resources/icons/player.png deleted file mode 100644 index 4f5ebda..0000000 Binary files a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/resources/icons/player.png and /dev/null differ diff --git a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/resources/stylesheet.css b/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/resources/stylesheet.css deleted file mode 100644 index 722921b..0000000 --- a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/resources/stylesheet.css +++ /dev/null @@ -1,3 +0,0 @@ -window { - -} diff --git a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/signal_classes/CrossClassSignals.py b/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/signal_classes/CrossClassSignals.py deleted file mode 100644 index 751f33d..0000000 --- a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/signal_classes/CrossClassSignals.py +++ /dev/null @@ -1,397 +0,0 @@ -# Gtk imports -import gi - -gi.require_version('Gtk', '3.0') -gi.require_version('Gdk', '3.0') - -from gi.repository import Gtk as gtk -from gi.repository import Gdk as gdk -from gi.repository import GLib as glib -from gi.repository import GdkPixbuf - -# Python imports -import threading, subprocess, signal, os, sys, re, hashlib, time - -from os import listdir -from os.path import isfile, join - -# Application imports -from utils import SaveStateToXWinWarp, SaveGWinWrapSettings - - - -def threaded(fn): - def wrapper(*args, **kwargs): - threading.Thread(target=fn, args=args, kwargs=kwargs).start() - - return wrapper - - -class CrossClassSignals: - def __init__(self, settings): - self.settings = settings - self.builder = self.settings.returnBuilder() - - self.WINDOW = self.builder.get_object("Main_Window").get_window() - self.stateSaver = SaveStateToXWinWarp() - self.sttngsSver = SaveGWinWrapSettings() - - # Add filter to allow only folders to be selected - dialog = self.builder.get_object("selectedDirDialog") - filefilter = self.builder.get_object("Folders") - dialog.add_filter(filefilter) - - # Get reference to remove and add it back... - self.gridLabel = self.builder.get_object("gridLabel") - - self.focusedImg = gtk.Image() - self.usrHome = os.path.expanduser('~') - self.xScreenVal = None - self.toSavePath = None # Global file path and type for saving to file - self.applyType = 1 # 1 is XWinWrap and 2 is Nitrogen - - self.loadProgress = self.builder.get_object("loadProgress") - self.helpLabel = self.builder.get_object("helpLabel") - self.defaultLabel = "Note: Double click an image to view the video or image." - self.savedLabel = "Saved settings..." - self.appliedLabel = "Running xwinwrap..." - self.stoppedLabel = "Stopped xwinwrap..." - # foreground=\"#ffa800\" - # foreground=\"#88cc27\" - # foreground=\"#ff0000\" - - # Fill list xscreensaver - self.xscrPth = "/usr/lib/xscreensaver/" - xscreenList = self.builder.get_object("XScreensaver List") - list = [f for f in listdir(self.xscrPth) if isfile(join(self.xscrPth, f))] - list.sort() - - for file in list: - xscreenList.append((file,)) - - self.selectedImg = None # EventBox holder - self.defPath = None - self.player = None - self.imgVwr = None - self.demoAreaPid = None - - self.setPosData() - self.retrieveSettings() - - - - def setNewDir(self, widget, data=None): - dir = widget.get_filename() - threading.Thread(target=self.newDir, args=(dir,)).start() - - @threaded - def newDir(self, dir): - imageGrid = self.builder.get_object("imageGrid") - dirPath = dir - list = [f for f in listdir(dirPath) if isfile(join(dirPath, f))] - files = [] - row = 0 - col = 0 - - for file in list: - if file.lower().endswith(('.mkv', '.avi', '.flv', '.mov', '.m4v', '.mpg', '.wmv', '.mpeg', '.mp4', '.webm', '.png', '.jpg', '.jpeg', '.gif')): - files.append(file) - - fractionTick = 1.0 / 1.0 if len(files) == 0 else len(files) - tickCount = 0.0 - self.clear() - imageGrid.remove_column(0) - self.loadProgress.set_text("Loading...") - self.loadProgress.set_fraction(0.0) - self.helpLabel.set_markup("" + dirPath.strip(self.usrHome) + "") - for file in files: - fullPathFile = dirPath + "/" + file - eveBox = gtk.EventBox() - thumbnl = gtk.Image() - - if file.lower().endswith(('.mkv', '.avi', '.flv', '.mov', '.m4v', '.mpg', '.wmv', '.mpeg', '.mp4', '.webm')): - fileHash = hashlib.sha256(str.encode(fullPathFile)).hexdigest() - hashImgpth = self.usrHome + "/.thumbnails/normal/" + fileHash + ".png" - if isfile(hashImgpth) == False: - self.generateThumbnail(fullPathFile, hashImgpth) - - thumbnl = self.createGtkImage(hashImgpth, [310, 310]) - eveBox.connect("button_press_event", self.runMplayerProcess, (fullPathFile, file, eveBox,)) - eveBox.connect("enter_notify_event", self.mouseOver, ()) - eveBox.connect("leave_notify_event", self.mouseOut, ()) - elif file.lower().endswith(('.png', '.jpg', '.jpeg', '.gif')): - thumbnl = self.createGtkImage(fullPathFile, [310, 310]) - eveBox.connect("button_press_event", self.runImageViewerProcess, (fullPathFile, file, eveBox,)) - eveBox.connect("enter_notify_event", self.mouseOver, ()) - eveBox.connect("leave_notify_event", self.mouseOut, ()) - else: - print("Not a video or image file.") - continue - - glib.idle_add(self.preGridSetup, (eveBox, thumbnl, )) - glib.idle_add(self.addToGrid, (imageGrid, eveBox, col, row,)) - tickCount = tickCount + fractionTick - self.loadProgress.set_fraction(tickCount) - - col += 1 - if col == 2: - col = 0 - row += 1 - - self.loadProgress.set_text("Finished...") - - def preGridSetup(self, args): - args[0].show() - args[1].show() - args[0].add(args[1]) - - def addToGrid(self, args): - args[0].attach(args[1], args[2], args[3], 1, 1) - - def generateThumbnail(self, fullPathFile, hashImgpth): - # Stream duration - command = ["ffprobe", "-v", "error", "-select_streams", "v:0", "-show_entries", "stream=duration", "-of", "default=noprint_wrappers=1:nokey=1", fullPathFile] - data = subprocess.run(command, stdout=subprocess.PIPE) - duration = data.stdout.decode('utf-8') - - # Format (container) duration - if "N/A" in duration: - command = ["ffprobe", "-v", "error", "-show_entries", "format=duration", "-of", "default=noprint_wrappers=1:nokey=1", fullPathFile] - data = subprocess.run(command , stdout=subprocess.PIPE) - duration = data.stdout.decode('utf-8') - - # Stream duration type: image2 - if "N/A" in duration: - command = ["ffprobe", "-v", "error", "-select_streams", "v:0", "-f", "image2", "-show_entries", "stream=duration", "-of", "default=noprint_wrappers=1:nokey=1", fullPathFile] - data = subprocess.run(command, stdout=subprocess.PIPE) - duration = data.stdout.decode('utf-8') - - # Format (container) duration type: image2 - if "N/A" in duration: - command = ["ffprobe", "-v", "error", "-f", "image2", "-show_entries", "format=duration", "-of", "default=noprint_wrappers=1:nokey=1", fullPathFile] - data = subprocess.run(command , stdout=subprocess.PIPE) - duration = data.stdout.decode('utf-8') - - # Get frame roughly 35% through video - grabTime = str( int( float( duration.split(".")[0] ) * 0.35) ) - command = ["ffmpeg", "-ss", grabTime, "-i", fullPathFile, "-an", "-vframes", "1", "-s", "320x180", "-q:v", "2", hashImgpth] - subprocess.call(command) - - def createGtkImage(self, path, wxh): - try: - pixbuf = GdkPixbuf.Pixbuf.new_from_file_at_scale( - filename = path, - width = wxh[0], - height = wxh[1], - preserve_aspect_ratio = True) - return gtk.Image.new_from_pixbuf(pixbuf) - except Exception as e: - print(e) - - return gtk.Image() - - - def openMainImageViewer(self, widget): - subprocess.call([self.imgVwr, self.toSavePath]) - - def runImageViewerProcess(self, widget, eve, params): - self.setSelected(params[2]) - - if eve.type == gdk.EventType.DOUBLE_BUTTON_PRESS: - previewWindow = self.builder.get_object("previewWindow") - previewImg = self.builder.get_object("previewImg") - previewImg.set_from_file(params[0]) - previewWindow.show_all() - previewWindow.popup() - - self.toSavePath = params[0] - self.applyType = 2 - self.helpLabel.set_markup("" + params[1] + "") - - def setSelected(self, eveBox): - if self.selectedImg: - col = gdk.RGBA(0.0, 0.0, 0.0, 0.0) - self.selectedImg.override_background_color(gtk.StateType.NORMAL, col) - - col = gdk.RGBA(0.9, 0.7, 0.4, 0.74) - eveBox.override_background_color(gtk.StateType.NORMAL, col) - self.selectedImg = eveBox - - def closePopup(self, widget): - self.builder.get_object("previewWindow").popdown() - - def mouseOver(self, widget, eve, args): - hand_cursor = gdk.Cursor(gdk.CursorType.HAND2) - self.builder.get_object("Main_Window").get_window().set_cursor(hand_cursor) - - def mouseOut(self, widget, eve, args): - watch_cursor = gdk.Cursor(gdk.CursorType.LEFT_PTR) - self.builder.get_object("Main_Window").get_window().set_cursor(watch_cursor) - - def toggleXscreenUsageField(self, widget, data=None): - useXscreenSaver = self.builder.get_object("useXScrnList") - if useXscreenSaver.get_active(): - self.builder.get_object("xScreenSvrList").set_sensitive(True) - else: - self.builder.get_object("xScreenSvrList").set_sensitive(False) - - def popSttingsWindow(self, widget): - self.builder.get_object("settingsWindow").popup() - - def saveToSettingsFile(self, widget): - self.defPath = self.builder.get_object("customDefaultPath").get_text().strip() - self.player = self.builder.get_object("customVideoPlyr").get_text().strip() - self.imgVwr = self.builder.get_object("customImgVwr").get_text().strip() - - self.sttngsSver.saveSettings(self.defPath, self.player, self.imgVwr) - - def retrieveSettings(self): - data = self.sttngsSver.retrieveSettings() - self.defPath = data[0] - self.player = data[1] - self.imgVwr = data[2] - - self.builder.get_object("customDefaultPath").set_text(self.defPath) - self.builder.get_object("customVideoPlyr").set_text(self.player) - self.builder.get_object("customImgVwr").set_text(self.imgVwr) - self.builder.get_object("selectedDirDialog").set_filename(self.defPath) - - if self.defPath: - self.newDir(self.defPath) - - - def saveToFile(self, widget, data=None): - saveLoc = self.builder.get_object("saveLoc").get_active_text() - useXscreenSaver = self.builder.get_object("useXScrnList").get_active() - plyBckRes = self.builder.get_object("playbackResolution") - offset4Res = self.builder.get_object("posOffset") - resolution = plyBckRes.get_active_text() + offset4Res.get_active_text() - self.applyType = self.stateSaver.saveToFile(self.toSavePath, resolution, - saveLoc, useXscreenSaver, self.xScreenVal, self.player) - if self.applyType == -1: - self.helpLabel.set_markup("Nothing saved...") - return - - self.helpLabel.set_markup(self.savedLabel) - - def applySttngs(self, widget, data=None): - os.system("killall xwinwrap &") - if self.applyType == 1: - files = os.listdir(self.usrHome) - for file in files: - fPath = self.usrHome + "/" + file - if os.path.isfile(fPath) and "animatedBGstarter" in file: - os.system("bash -c '~/" + file + "' &") - elif self.applyType == 2: - os.system("nitrogen --restore &") - else: - os.system("nitrogen --restore &") - self.helpLabel.set_markup(self.appliedLabel) - - def killXWinWrp(self, widget, data=None): - os.system("killall xwinwrap &") - self.helpLabel.set_markup(self.stoppedLabel) - - def passXScreenVal(self, widget): - xSvrListStore = self.builder.get_object("XScreensaver List") - row = widget.get_cursor() - path = gtk.TreePath(row.path) - treeiter = xSvrListStore.get_iter(path[0]) - self.xScreenVal = xSvrListStore.get_value(treeiter, 0) - - - def runMplayerProcess(self, widget, eve, params): - self.setSelected(params[2]) - video = params[0] - - if eve.type == gdk.EventType.DOUBLE_BUTTON_PRESS: - if self.player == "mplayer": - xid = self.getXID() - command = [self.player, video, "-slave", "-wid", str(xid), "-really-quiet", "-ao", "null", "-loop", "0"] - self.runDemoToDrawArea(command) - else: - subprocess.call([self.player, video, "-really-quiet", "-ao", "null", "-loop", "0"]) - - self.toSavePath = params[0] - self.applyType = 1 - self.helpLabel.set_markup("" + params[1] + "") - - def previewXscreen(self, widget, eve): - if eve.type == gdk.EventType.DOUBLE_BUTTON_PRESS: - demoXscrnSaver = self.xscrPth + self.xScreenVal - xid = self.getXID() - command = [demoXscrnSaver, "-window-id", str(xid)] - self.runDemoToDrawArea(command) - - def getXID(self): - # Must be actualized before getting window - demoWindowPopup = self.builder.get_object("demoPreviewPopWindow") - - if demoWindowPopup.get_visible() == False: - demoWindowPopup.show_all() - demoWindowPopup.popup() - - demoPreview = self.builder.get_object("demoPreview") - drwWindow = demoPreview.get_window() - return drwWindow.get_xid() - - def runDemoToDrawArea(self, command): - self.helpLabel.set_markup("") - - if self.demoAreaPid: - os.kill(self.demoAreaPid, signal.SIGTERM) #or signal.SIGKILL - self.demoAreaPid = None - time.sleep(.800) # 800 mili-seconds to ensure first process dead - - process = subprocess.Popen(command) - self.demoAreaPid = process.pid - - def closeDemoWindow(self, widget, data=None): - os.kill(self.demoAreaPid, signal.SIGTERM) #or signal.SIGKILL - self.demoAreaPid = None - time.sleep(.200) - self.builder.get_object("demoPreviewPopWindow").popdown() - - def clearSelection(self, widget, data=None): - self.clear() - - def clear(self): - imageGrid = self.builder.get_object("imageGrid") - - while True: - if imageGrid.get_child_at(0,0)!= None: - imageGrid.remove_row(0) - else: - break - - imageGrid.attach(self.gridLabel, 0, 0, 1, 1) - self.builder.get_object("xScreenSvrList").set_sensitive(False) - self.builder.get_object("useXScrnList").set_active(False) - self.helpLabel.set_markup(self.defaultLabel) - self.loadProgress.set_text("") - self.loadProgress.set_fraction(0.0) - self.toSavePath = None - self.xScreenVal = None - self.applyType = 1 # Default to XWinWrap - - - - def setPosData(self): - monitors = self.settings.getMonitorData() - posOff = self.builder.get_object("posOffset") - - for monitor in monitors: - if monitor.x >= 0 and monitor.y >= 0: - posOff.append_text("+" + str(monitor.x) + "+" + str(monitor.y)) - elif monitor.x <= 0 and monitor.y <= 0: - posOff.append_text(str(monitor.x) + str(monitor.y)) - elif monitor.x >= 0 and monitor.y <= 0: - posOff.append_text("+" + str(monitor.x) + str(monitor.y)) - elif monitor.x <= 0 and monitor.y >= 0: - posOff.append_text(str(monitor.x) + "+" + str(monitor.y)) - - posOff.set_active(0) - - - def closeProgram(self, widget, data=None): - sys.exit(0) diff --git a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/signal_classes/__init__.py b/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/signal_classes/__init__.py deleted file mode 100644 index d2d4cdf..0000000 --- a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/signal_classes/__init__.py +++ /dev/null @@ -1 +0,0 @@ -from signal_classes.CrossClassSignals import CrossClassSignals diff --git a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/utils/SaveGWinWrapSettings.py b/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/utils/SaveGWinWrapSettings.py deleted file mode 100644 index a26fbb5..0000000 --- a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/utils/SaveGWinWrapSettings.py +++ /dev/null @@ -1,52 +0,0 @@ -#!/usr/bin/env python - -import os, json - -class SaveGWinWrapSettings: - def __init__(self): - configFolder = os.path.expanduser('~') + "/.config/gwinwrap/" - self.configFile = configFolder + "settings.ini" - - if os.path.isdir(configFolder) == False: - os.mkdir(configFolder) - - if os.path.isfile(self.configFile) == False: - open(self.configFile, 'a').close() - - - def saveSettings(self, defPath, player, imgVwr): - data = {} - data['gwinwrap_settings'] = [] - - data['gwinwrap_settings'].append({ - 'defPath' : defPath, - 'player' : player, - 'imgvwr' : imgVwr - }) - - with open(self.configFile, 'w') as outfile: - json.dump(data, outfile) - - - def retrieveSettings(self): - returnData = [] - - with open(self.configFile) as infile: - try: - data = json.load(infile) - for obj in data['gwinwrap_settings']: - returnData = [obj['defPath'], obj['player'], obj['imgvwr']] - except Exception as e: - returnData = ['', 'mplayer', 'xdg-open'] - - - if returnData[0] == '': - returnData[0] = '' - - if returnData[1] == '': - returnData[1] = 'mplayer' - - if returnData[2] == '': - returnData[2] = 'xdg-open' - - return returnData diff --git a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/utils/SaveStateToXWinWarp.py b/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/utils/SaveStateToXWinWarp.py deleted file mode 100644 index 1e086be..0000000 --- a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/utils/SaveStateToXWinWarp.py +++ /dev/null @@ -1,69 +0,0 @@ -#!/usr/bin/env python - -import os - -class SaveStateToXWinWarp: - def __init__(self): - self.fileWriter = None - self.toSavePath = None - self.useXSvrn = None - self.xScreenVal = None - self.sveFileLoc = None - self.resolution = None - self.player = None - - - def saveToFile(self, toSavePath, resolution, - saveLoc, useXSvrn, xScreenVal, player): - - self.toSavePath = toSavePath - self.useXSvrn = useXSvrn - self.xScreenVal = xScreenVal - self.resolution = resolution - self.player = player - userPth = os.path.expanduser('~') - - # Saves to file with selected and needed settings - if toSavePath: - if toSavePath.lower().endswith(('.png', '.jpg', '.jpeg')): - self.sveFileLoc = userPth + "/" + ".config/nitrogen/bg-saved.cfg" - else: - self.sveFileLoc = userPth + "/" + saveLoc - elif useXSvrn and xScreenVal: - self.sveFileLoc = userPth + "/" + saveLoc - else: - return -1 - - if self.sveFileLoc: - self.fileWriter = open(self.sveFileLoc, "w") - - return self.startSave() - - def startSave(self): - applyType = 1 - output = None - - # XSCREENSAVER - if self.useXSvrn: - output = "xwinwrap -ov -g " + self.resolution + " -st -sp -b -nf -s -ni -- /usr/lib/xscreensaver/" + self.xScreenVal + " -window-id WID -root"; - # GIF - elif self.toSavePath.lower().endswith(('.gif')): - output = "xwinwrap -ov -g " + self.resolution + " -st -sp -b -nf -s -ni -- gifview -a -w WID " + self.toSavePath; - # Standard images using nitrogen - elif self.toSavePath.lower().endswith(('.png', 'jpg', '.jpeg')): - output = "[xin_0] \nfile=" + self.toSavePath + "\nmode=0 \nbgcolor=#000000\n\n[xin_1] \nfile=" + self.toSavePath + "\nmode=0 \nbgcolor=#000000"; - applyType = 2; - # VIDEO - else: - output = "xwinwrap -ov -g " + self.resolution + " -st -sp -b -nf -s -ni -- " + self.player + " -wid WID -really-quiet -ao null -loop 0 '" + self.toSavePath + "'"; - pass - - try: - if self.fileWriter: - self.fileWriter.write(output) - self.fileWriter.close() - except Exception as e: - print(":: Write failed! ::") - print(e) - - return applyType; diff --git a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/utils/Settings.py b/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/utils/Settings.py deleted file mode 100644 index 1f5479f..0000000 --- a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/utils/Settings.py +++ /dev/null @@ -1,74 +0,0 @@ -# Gtk imports -import gi, cairo -gi.require_version('Gtk', '3.0') -gi.require_version('Gdk', '3.0') - -from gi.repository import Gtk as gtk -from gi.repository import Gdk as gdk - -# Python imports -import os - -# Application imports - - -class Settings: - def __init__(self): - self.builder = gtk.Builder() - self.builder.add_from_file("resources/Main_Window.glade") - - # 'Filters' - self.office = ('.doc', '.docx', '.xls', '.xlsx', '.xlt', '.xltx', '.xlm', - '.ppt', 'pptx', '.pps', '.ppsx', '.odt', '.rtf') - self.vids = ('.mkv', '.avi', '.flv', '.mov', '.m4v', '.mpg', '.wmv', - '.mpeg', '.mp4', '.webm') - self.txt = ('.txt', '.text', '.sh', '.cfg', '.conf') - self.music = ('.psf', '.mp3', '.ogg' , '.flac') - self.images = ('.png', '.jpg', '.jpeg', '.gif') - self.pdf = ('.pdf') - - - def createWindow(self): - # Get window and connect signals - window = self.builder.get_object("Main_Window") - window.connect("delete-event", gtk.main_quit) - self.setWindowData(window) - return window - - def setWindowData(self, window): - screen = window.get_screen() - visual = screen.get_rgba_visual() - - if visual != None and screen.is_composited(): - window.set_visual(visual) - - # bind css file - cssProvider = gtk.CssProvider() - cssProvider.load_from_path('resources/stylesheet.css') - screen = gdk.Screen.get_default() - styleContext = gtk.StyleContext() - styleContext.add_provider_for_screen(screen, cssProvider, gtk.STYLE_PROVIDER_PRIORITY_USER) - - # window.set_app_paintable(True) - - def getMonitorData(self): - screen = self.builder.get_object("Main_Window").get_screen() - monitors = [] - for m in range(screen.get_n_monitors()): - monitors.append(screen.get_monitor_geometry(m)) - - for monitor in monitors: - print(str(monitor.width) + "x" + str(monitor.height) + "+" + str(monitor.x) + "+" + str(monitor.y)) - - return monitors - - - def returnBuilder(self): return self.builder - - # Filter returns - def returnOfficeFilter(self): return self.office - def returnVidsFilter(self): return self.vids - def returnTextFilter(self): return self.txt - def returnMusicFilter(self): return self.music - def returnImagesFilter(self): return self.images - def returnPdfFilter(self): return self.pdf diff --git a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/utils/__init__.py b/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/utils/__init__.py deleted file mode 100644 index ca4b01b..0000000 --- a/src/debs/gwinwrap-0-0-1-x64/opt/GWinWrap/utils/__init__.py +++ /dev/null @@ -1,3 +0,0 @@ -from utils.Settings import Settings -from utils.SaveStateToXWinWarp import SaveStateToXWinWarp -from utils.SaveGWinWrapSettings import SaveGWinWrapSettings diff --git a/src/debs/gwinwrap-0-0-1-x64/usr/share/doc/gwinwrap/copyright b/src/debs/gwinwrap-0-0-1-x64/usr/share/doc/gwinwrap/copyright deleted file mode 100644 index 53b78e8..0000000 --- a/src/debs/gwinwrap-0-0-1-x64/usr/share/doc/gwinwrap/copyright +++ /dev/null @@ -1,22 +0,0 @@ -GWinWrap is copyright 2016, 2017 Maxim Stewart. -GWinWrap is currently developed by ITDominator <1itdominator@gmail.com>. - -License: GPLv2+ - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. - -See /usr/share/common-licenses/GPL-2, or - for the terms of the latest version -of the GNU General Public License. diff --git a/src/debs/gwinwrap-0-0-2-x64/DEBIAN/postrm b/src/debs/gwinwrap-0-0-2-x64/DEBIAN/postrm index 5a54f11..60e24bf 100755 --- a/src/debs/gwinwrap-0-0-2-x64/DEBIAN/postrm +++ b/src/debs/gwinwrap-0-0-2-x64/DEBIAN/postrm @@ -6,8 +6,16 @@ if [ -f /bin/xwinwrap ]; then rm /bin/xwinwrap fi -if [ -d /opt/GWinWrap ]; then - rm -rf /opt/GWinWrap +if [ -f /bin/gwinwrap ]; then + rm /bin/gwinwrap +fi + +if [ -f /usr/share/applications/gwinwrap.desktop ]; then + rm /usr/share/applications/gwinwrap.desktop +fi + +if [ -f /opt/gwinwrap.zip ]; then + rm /opt/gwinwrap.zip fi if [ -d /usr/share/gwinwrap ]; then diff --git a/src/debs/gwinwrap-0-0-2-x64/bin/gwinwrap b/src/debs/gwinwrap-0-0-2-x64/bin/gwinwrap index 2166a10..6b4c244 100755 Binary files a/src/debs/gwinwrap-0-0-2-x64/bin/gwinwrap and b/src/debs/gwinwrap-0-0-2-x64/bin/gwinwrap differ diff --git a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/__builtins__.py b/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/__builtins__.py deleted file mode 100644 index 287a5fb..0000000 --- a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/__builtins__.py +++ /dev/null @@ -1,73 +0,0 @@ -import builtins - -# Python imports -import builtins - -# Lib imports - -# Application imports -from signal_classes import IPCServerMixin - - - -class Builtins(IPCServerMixin): - """Docstring for __builtins__ extender""" - - def __init__(self): - # NOTE: The format used is list of [type, target, data] - # Where data may be any kind of data - self._gui_events = [] - self._fm_events = [] - self.is_ipc_alive = False - self.ipc_authkey = b'GWinWrap-ipc' - self.ipc_address = '127.0.0.1' - self.ipc_port = 8888 - self.ipc_timeout = 15.0 - - # Makeshift fake "events" type system FIFO - def _pop_gui_event(self): - if len(self._gui_events) > 0: - return self._gui_events.pop(0) - return None - - def _pop_fm_event(self): - if len(self._fm_events) > 0: - return self._fm_events.pop(0) - return None - - - def push_gui_event(self, event): - if len(event) == 3: - self._gui_events.append(event) - return None - - raise Exception("Invald event format! Please do: [type, target, data]") - - def push_fm_event(self, event): - if len(event) == 3: - self._fm_events.append(event) - return None - - raise Exception("Invald event format! Please do: [type, target, data]") - - def read_gui_event(self): - return self._gui_events[0] - - def read_fm_event(self): - return self._fm_events[0] - - def consume_gui_event(self): - return self._pop_gui_event() - - def consume_fm_event(self): - return self._pop_fm_event() - - - -# NOTE: Just reminding myself we can add to builtins two different ways... -# __builtins__.update({"event_system": Builtins()}) -builtins.app_name = "GWinWrap" -builtins.event_system = Builtins() -builtins.event_sleep_time = 0.2 -builtins.debug = False -builtins.trace_debug = False diff --git a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/__init__.py b/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/__init__.py deleted file mode 100644 index 56356ba..0000000 --- a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/__init__.py +++ /dev/null @@ -1,50 +0,0 @@ -# Python imports -import os, inspect, time - -# Lib imports - -# Application imports -from utils import Settings -from signal_classes import Controller -from __builtins__ import Builtins - - - - -class Main(Builtins): - def __init__(self, args, unknownargs): - if not debug: - event_system.create_ipc_server() - - time.sleep(0.2) - if not trace_debug: - if not event_system.is_ipc_alive: - if unknownargs: - for arg in unknownargs: - if os.path.isdir(arg): - message = f"FILE|{arg}" - event_system.send_ipc_message(message) - - raise Exception("IPC Server Exists: Will send data to it and close...") - - - settings = Settings() - settings.create_window() - - controller = Controller(settings, args, unknownargs) - if not controller: - raise Exception("Controller exited and doesn't exist...") - - # Gets the methods from the classes and sets to handler. - # Then, builder from settings will connect to any signals it needs. - classes = [controller] - handlers = {} - for c in classes: - methods = None - try: - methods = inspect.getmembers(c, predicate=inspect.ismethod) - handlers.update(methods) - except Exception as e: - print(repr(e)) - - settings.get_builder().connect_signals(handlers) diff --git a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/__main__.py b/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/__main__.py deleted file mode 100644 index dc06b1a..0000000 --- a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/__main__.py +++ /dev/null @@ -1,39 +0,0 @@ -#!/usr/bin/python3 - - -# Python imports -import argparse, faulthandler, traceback -from setproctitle import setproctitle - -import tracemalloc -tracemalloc.start() - - -# Lib imports -import gi -gi.require_version('Gtk', '3.0') -from gi.repository import Gtk - -# Application imports -from __init__ import Main - - -if __name__ == "__main__": - try: - # import web_pdb - # web_pdb.set_trace() - - setproctitle('GWinWrap') - faulthandler.enable() # For better debug info - parser = argparse.ArgumentParser() - # Add long and short arguments - parser.add_argument("--file", "-f", default="default", help="JUST SOME FILE ARG.") - - # Read arguments (If any...) - args, unknownargs = parser.parse_known_args() - - Main(args, unknownargs) - Gtk.main() - except Exception as e: - traceback.print_exc() - quit() diff --git a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/Controller.py b/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/Controller.py deleted file mode 100644 index adcb743..0000000 --- a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/Controller.py +++ /dev/null @@ -1,151 +0,0 @@ -# Python imports -import threading, signal, subprocess, inspect, os, time - -# Gtk imports -import gi -gi.require_version('Gtk', '3.0') -gi.require_version('Gdk', '3.0') -from gi.repository import Gtk, GLib, Gdk - -# Application imports -from .mixins import * -from . import Controller_Data - - -def threaded(fn): - def wrapper(*args, **kwargs): - threading.Thread(target=fn, args=args, kwargs=kwargs).start() - - return wrapper - - -class Controller(ThumbnailMixin, ImageViewerMixin, DrawAreaMixin, GridMixin, Controller_Data): - def __init__(self, _settings, args, unknownargs): - self.setup_controller_data(_settings) - self.window.show() - self.retrieve_settings() - - - def tear_down(self, widget=None, eve=None): - event_system.send_ipc_message("close server") - if self.demo_area_pid: - self.close_demo_popup() - - self.close_image_popup() - time.sleep(event_sleep_time) - Gtk.main_quit() - - def close_program(self, widget, data=None): - self.tear_down() - - - @threaded - def gui_event_observer(self): - while True: - time.sleep(event_sleep_time) - event = event_system.consume_gui_event() - if event: - try: - type, target, data = event - method = getattr(self.__class__, type) - GLib.idle_add(method, (self, data,)) - except Exception as e: - print(repr(e)) - - - - def apply_settings(self, widget, data=None): - os.system("killall xwinwrap &") - user_home = self.settings.get_home_path() - - if self.apply_type == 1: - files = os.listdir(user_home) - for file in files: - fPath = f"{user_home}/{file}" - if os.path.isfile(fPath) and "animatedBGstarter" in file: - os.system(f"bash -c '~/{file}' &") - elif self.apply_type == 2: - os.system("nitrogen --restore &") - else: - os.system("nitrogen --restore &") - - self.help_label.set_markup(self.appliedLabel) - - def save_to_settings_file(self, widget): - self.start_path = self.builder.get_object("customStartPath").get_text().strip() - self.default_player = self.builder.get_object("customVideoPlayer").get_text().strip() - self.default_img_viewer = self.builder.get_object("customImgViewer").get_text().strip() - - self.settings_saver.save_settings(self.start_path, self.default_player, self.default_img_viewer) - - def save_to_file(self, widget, data=None): - save_location = self.builder.get_object("saveLoc").get_active_text() - use_xscreensvr = self.builder.get_object("useXScrnList").get_active() - playBackRes = self.builder.get_object("playbackResolution") - monitorOffset = self.builder.get_object("monitorOffsetData") - resolution = playBackRes.get_active_text() + monitorOffset.get_active_text() - self.apply_type = self.state_saver.save_to_file(self.to_be_background, resolution, save_location, use_xscreensvr, self.xscreen_value, self.default_player) - - if self.apply_type == -1: - self.help_label.set_markup("Nothing saved...") - return - - self.help_label.set_markup(self.savedLabel) - - - def toggle_xscreen_list(self, widget, data=None): - use_xscreensvr = self.builder.get_object("useXScrnList") - if use_xscreensvr.get_active(): - self.builder.get_object("xScreenSvrList").set_sensitive(True) - else: - self.builder.get_object("xScreenSvrList").set_sensitive(False) - - def show_settings_popup(self, widget): - self.builder.get_object("settingsWindow").popup() - - - def preview_xscreensaver(self, widget, eve): - if eve.type == Gdk.EventType.DOUBLE_BUTTON_PRESS: - demoXscrnSaver = self.xscreensavers + self.xscreen_value - xid = self.getXID() - command = [demoXscrnSaver, "-window-id", str(xid)] - self.run_demo_in_draw_area(command) - - def pass_xscreen_value(self, widget): - row = widget.get_cursor() - path = Gtk.TreePath(row.path) - treeiter = self.xscreen_store.get_iter(path[0]) - self.xscreen_value = self.xscreen_store.get_value(treeiter, 0) - - def kill_xwinwrap(self, widget, data=None): - os.system("killall xwinwrap &") - self.help_label.set_markup(self.stoppedLabel) - - def set_selected_eve_box(self, eveBox): - if self.selected_eve_box: - color = Gdk.RGBA(0.0, 0.0, 0.0, 0.0) - self.selected_eve_box.override_background_color(Gtk.StateType.NORMAL, color) - - color = Gdk.RGBA(0.9, 0.7, 0.4, 0.74) - eveBox.override_background_color(Gtk.StateType.NORMAL, color) - self.selected_eve_box = eveBox - - def mouse_over(self, widget, eve, args): - hand_cursor = Gdk.Cursor(Gdk.CursorType.HAND2) - self.window.get_window().set_cursor(hand_cursor) - - def mouse_out(self, widget, eve, args): - watch_cursor = Gdk.Cursor(Gdk.CursorType.LEFT_PTR) - self.window.get_window().set_cursor(watch_cursor) - - def get_clipboard_data(self): - proc = subprocess.Popen(['xclip','-selection', 'clipboard', '-o'], stdout=subprocess.PIPE) - retcode = proc.wait() - data = proc.stdout.read() - return data.decode("utf-8").strip() - - def set_clipboard_data(self, data): - proc = subprocess.Popen(['xclip','-selection','clipboard'], stdin=subprocess.PIPE) - proc.stdin.write(data) - proc.stdin.close() - retcode = proc.wait() diff --git a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/Controller_Data.py b/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/Controller_Data.py deleted file mode 100644 index e651a46..0000000 --- a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/Controller_Data.py +++ /dev/null @@ -1,102 +0,0 @@ -# Python imports -import signal -from os import listdir -from os.path import isfile, join - -# Lib imports -from gi.repository import GLib - -# Application imports -from . import SaveStateToXWinWarp, SaveGWinWrapSettings - - - -class Controller_Data: - def has_method(self, obj, name): - return callable(getattr(obj, name, None)) - - def setup_controller_data(self, _settings): - self.settings = _settings - self.state_saver = SaveStateToXWinWarp(_settings) - self.settings_saver = SaveGWinWrapSettings(_settings) - - - self.builder = self.settings.get_builder() - self.window = self.settings.get_main_window() - self.logger = self.settings.get_logger() - - self.home_path = self.settings.get_home_path() - self.success_color = self.settings.get_success_color() - self.warning_color = self.settings.get_warning_color() - self.error_color = self.settings.get_error_color() - - - self.image_grid = self.builder.get_object("imageGrid") - self.grid_label = self.builder.get_object("gridLabel") - self.help_label = self.builder.get_object("helpLabel") - self.xscreen_store = self.builder.get_object("XScreensaverStore") - - self.defaultLabel = "Note: Double click an image to view the video or image." - self.savedLabel = f"Saved settings..." - self.appliedLabel = f"Running xwinwrap..." - self.stoppedLabel = f"Stopped xwinwrap..." - - # Add filter to allow only folders to be selected - dialog = self.builder.get_object("selectedDirDialog") - file_filter = self.builder.get_object("Folders") - dialog.add_filter(file_filter) - - self.xscreensavers = self.settings.get_xscreensavers() - list = [f for f in listdir(self.xscreensavers) if isfile(join(self.xscreensavers , f))] - list.sort() - for file in list: - self.xscreen_store.append((file,)) - - - self.selected_eve_box = None - self.start_path = None - self.default_player = None - self.default_img_viewer = None - self.demo_area_pid = None - - self.apply_type = 1 # 1 is XWinWrap and 2 is Nitrogen - self.xscreen_value = None - self.to_be_background = None # Global file path and type for saving to file - - - self.window.connect("delete-event", self.tear_down) - GLib.unix_signal_add(GLib.PRIORITY_DEFAULT, signal.SIGINT, self.tear_down) - - self.set_monitor_offset_data() - self.retrieve_settings() - - - def set_monitor_offset_data(self): - monitors = self.settings.get_monitor_data() - monitorOffsetData = self.builder.get_object("monitorOffsetData") - - for monitor in monitors: - if monitor.x >= 0 and monitor.y >= 0: - monitorOffsetData.append_text("+" + str(monitor.x) + "+" + str(monitor.y)) - elif monitor.x <= 0 and monitor.y <= 0: - monitorOffsetData.append_text(str(monitor.x) + str(monitor.y)) - elif monitor.x >= 0 and monitor.y <= 0: - monitorOffsetData.append_text("+" + str(monitor.x) + str(monitor.y)) - elif monitor.x <= 0 and monitor.y >= 0: - monitorOffsetData.append_text(str(monitor.x) + "+" + str(monitor.y)) - - monitorOffsetData.set_active(0) - - def retrieve_settings(self): - data = self.settings_saver.retrieve_settings() - self.start_path = data[0] - self.default_player = data[1] - self.default_img_viewer = data[2] - - self.builder.get_object("customStartPath").set_text(self.start_path) - self.builder.get_object("customVideoPlayer").set_text(self.default_player) - self.builder.get_object("customImgViewer").set_text(self.default_img_viewer) - self.builder.get_object("selectedDirDialog").set_filename(self.start_path) - - if self.start_path: - self.load_path(None, self.start_path) diff --git a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/IPCServerMixin.py b/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/IPCServerMixin.py deleted file mode 100644 index be92ace..0000000 --- a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/IPCServerMixin.py +++ /dev/null @@ -1,64 +0,0 @@ -# Python imports -import threading, socket, time -from multiprocessing.connection import Listener, Client - -# Lib imports - -# Application imports - - -def threaded(fn): - def wrapper(*args, **kwargs): - threading.Thread(target=fn, args=args, kwargs=kwargs, daemon=True).start() - return wrapper - - - - -class IPCServerMixin: - - @threaded - def create_ipc_server(self): - listener = Listener((self.ipc_address, self.ipc_port), authkey=self.ipc_authkey) - self.is_ipc_alive = True - while True: - conn = listener.accept() - start_time = time.time() - - print(f"New Connection: {listener.last_accepted}") - while True: - msg = conn.recv() - if debug: - print(msg) - - if "FILE|" in msg: - file = msg.split("FILE|")[1].strip() - if file: - event_system.push_gui_event(["create_tab_from_ipc", None, file]) - - conn.close() - break - - - if msg == 'close connection': - conn.close() - break - if msg == 'close server': - conn.close() - break - - # NOTE: Not perfect but insures we don't lockup the connection for too long. - end_time = time.time() - if (end - start) > self.ipc_timeout: - conn.close() - - listener.close() - - - def send_ipc_message(self, message="Empty Data..."): - try: - conn = Client((self.ipc_address, self.ipc_port), authkey=self.ipc_authkey) - conn.send(message) - conn.send('close connection') - except Exception as e: - print(repr(e)) diff --git a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/SaveGWinWrapSettings.py b/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/SaveGWinWrapSettings.py deleted file mode 100644 index 38025a1..0000000 --- a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/SaveGWinWrapSettings.py +++ /dev/null @@ -1,49 +0,0 @@ -#!/usr/bin/env python - -import os, json - -class SaveGWinWrapSettings: - def __init__(self, settings): - self.config_file = settings.get_config_file() - - if os.path.isfile(self.config_file) == False: - open(self.config_file, 'a').close() - - - def save_settings(self, start_path, default_player, default_img_viewer): - data = {} - data['settings'] = [] - - data['settings'].append({ - 'start_path': start_path, - 'default_player': default_player, - 'default_img_viewer': default_img_viewer - }) - - with open(self.config_file, 'w') as outfile: - json.dump(data, outfile, separators=(',', ':'), indent=4) - - - def retrieve_settings(self): - data = [] - - with open(self.config_file) as infile: - try: - _data = json.load(infile) - for obj in _data['settings']: - data = [obj['start_path'], obj['default_player'], obj['default_img_viewer']] - except Exception as e: - print(repr(e)) - data = ['', 'mplayer', 'xdg-open'] - - - if data[0] == '': - data[0] = '' - - if data[1] == '': - data[1] = 'mplayer' - - if data[2] == '': - data[2] = 'xdg-open' - - return data diff --git a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/__init__.py b/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/__init__.py deleted file mode 100644 index 97a8b3b..0000000 --- a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/__init__.py +++ /dev/null @@ -1,9 +0,0 @@ -""" - Gtk Bound Signal Module -""" -from .mixins import * -from .SaveStateToXWinWarp import SaveStateToXWinWarp -from .SaveGWinWrapSettings import SaveGWinWrapSettings -from .IPCServerMixin import IPCServerMixin -from .Controller_Data import Controller_Data -from .Controller import Controller diff --git a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/mixins/DrawAreaMixin.py b/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/mixins/DrawAreaMixin.py deleted file mode 100644 index 833d3ae..0000000 --- a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/mixins/DrawAreaMixin.py +++ /dev/null @@ -1,59 +0,0 @@ -# Python imports -import os, subprocess, signal, time - -# Gtk imports -import gi -gi.require_version('Gdk', '3.0') -from gi.repository import Gdk - -# Application imports - - -class DrawAreaMixin: - """docstring for DrawAreaMixin""" - - def close_demo_popup(self, widget=None, data=None): - os.kill(self.demo_area_pid, signal.SIGTERM) #or signal.SIGKILL - self.demo_area_pid = None - time.sleep(.200) - self.builder.get_object("demoPreviewPopWindow").popdown() - - def run_mplayer_process(self, widget, eve, params): - video, file, eveBox = params - self.set_selected_eve_box(eveBox) - - if eve.type == Gdk.EventType.DOUBLE_BUTTON_PRESS: - if self.default_player == "mplayer": - xid = self.getXID() - command = [self.default_player, video, "-slave", "-wid", str(xid), "-really-quiet", "-ao", "null", "-loop", "0"] - self.run_demo_in_draw_area(command) - else: - subprocess.call([self.default_player, video, "-really-quiet", "-ao", "null", "-loop", "0"]) - - - self.to_be_background = video - self.applyType = 1 - self.help_label.set_markup(f"{file}") - - def run_demo_in_draw_area(self, command): - self.help_label.set_markup("") - - if self.demo_area_pid: - os.kill(self.demo_area_pid, signal.SIGTERM) #or signal.SIGKILL - self.demo_area_pid = None - time.sleep(.800) # 800 mili-seconds to ensure first process dead - - process = subprocess.Popen(command) - self.demo_area_pid = process.pid - - def getXID(self): - # Must be actualized before getting window - popup = self.builder.get_object("demoPreviewPopWindow") - - if popup.get_visible() == False: - popup.show_all() - popup.popup() - - preview = self.builder.get_object("demoPreview") - window = preview.get_window() - return window.get_xid() diff --git a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/mixins/GridMixin.py b/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/mixins/GridMixin.py deleted file mode 100644 index 513d7b1..0000000 --- a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/mixins/GridMixin.py +++ /dev/null @@ -1,116 +0,0 @@ -# Python imports -import threading, hashlib -from os import listdir -from os.path import isfile, join - -# Gtk imports -import gi -gi.require_version('Gtk', '3.0') -from gi.repository import Gtk, GLib - -# Application imports - - - - - -def threaded(fn): - def wrapper(*args, **kwargs): - threading.Thread(target=fn, args=args, kwargs=kwargs).start() - - return wrapper - - -class GridMixin: - """docstring for GridMixin.""" - - def set_new_path(self, widget, data=None): - dir = widget.get_filename() - self.load_path(None, dir) - - def load_path(self, widget=None, dir=''): - path = dir - list = [f for f in listdir(path) if isfile(join(path, f))] - files = [] - row = 0 - col = 0 - - for file in list: - if file.lower().endswith(self.settings.get_vids_filter() + \ - self.settings.get_images_filter()): - files.append(file) - - # fractionTick = 1.0 / 1.0 if len(files) == 0 else len(files) - # tickCount = 0.0 - self.clear() - self.image_grid.remove_column(0) - # self.loadProgress.set_text("Loading...") - # self.loadProgress.set_fraction(0.0) - self.help_label.set_markup(f"{path.strip(self.settings.get_home_path())}") - for file in files: - self.porocess_file(path, file, col, row) - - col += 1 - if col == 2: - col = 0 - row += 1 - - # self.loadProgress.set_text("Finished...") - - @threaded - def porocess_file(self, path, file, col, row): - fPath = f"{path}/{file}" - eveBox = Gtk.EventBox() - thumbnl = Gtk.Image() - - if file.lower().endswith(self.settings.get_vids_filter()): - fileHash = hashlib.sha256(str.encode(fPath)).hexdigest() - hashImgPath = f"{self.settings.get_home_path()}/.thumbnails/normal/{fileHash}.png" - if isfile(hashImgPath) == False: - self.generate_thumbnail(fPath, hashImgPath) - - thumbnl = self.create_gtk_image(hashImgPath, [310, 310]) - eveBox.connect("button_press_event", self.run_mplayer_process, (fPath, file, eveBox,)) - eveBox.connect("enter_notify_event", self.mouse_over, ()) - eveBox.connect("leave_notify_event", self.mouse_out, ()) - elif file.lower().endswith(self.settings.get_images_filter()): - thumbnl = self.create_gtk_image(fPath, [310, 310]) - eveBox.connect("button_press_event", self.run_image_viewer_process, (fPath, file, eveBox,)) - eveBox.connect("enter_notify_event", self.mouse_over, ()) - eveBox.connect("leave_notify_event", self.mouse_out, ()) - else: - print("Not a video or image file.") - return - - GLib.idle_add(self.pre_grid_setup, (eveBox, thumbnl, )) - GLib.idle_add(self.add_to_grid, (self.image_grid, eveBox, col, row,)) - # tickCount = tickCount + fractionTick - # self.loadProgress.set_fraction(tickCount) - - def pre_grid_setup(self, args): - args[0].show() - args[1].show() - args[0].add(args[1]) - - def add_to_grid(self, args): - args[0].attach(args[1], args[2], args[3], 1, 1) - - def clear_selection(self, widget, data=None): - self.clear() - - def clear(self): - while True: - if self.image_grid.get_child_at(0,0)!= None: - self.image_grid.remove_row(0) - else: - break - - self.image_grid.attach(self.grid_label, 0, 0, 1, 1) - self.builder.get_object("xScreenSvrList").set_sensitive(False) - self.builder.get_object("useXScrnList").set_active(False) - self.help_label.set_markup(self.defaultLabel) - # self.loadProgress.set_text("") - # self.loadProgress.set_fraction(0.0) - self.xscreen_value = None - self.to_be_background = None - self.apply_type = 1 diff --git a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/mixins/ImageViewerMixin.py b/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/mixins/ImageViewerMixin.py deleted file mode 100644 index e4dd1b6..0000000 --- a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/mixins/ImageViewerMixin.py +++ /dev/null @@ -1,34 +0,0 @@ -# Python imports -import subprocess - -# Gtk imports -import gi -gi.require_version('Gdk', '3.0') -from gi.repository import Gdk - -# Application imports - - -class ImageViewerMixin: - """docstring for ImageViewerMixin""" - - def close_image_popup(self, widget=None): - self.builder.get_object("previewWindow").popdown() - - def open_main_image_viewer(self, widget): - subprocess.call([self.default_img_viewer, self.to_be_background]) - - def run_image_viewer_process(self, widget, eve, params): - image, file, eveBox = params - self.set_selected(eveBox) - - if eve.type == Gdk.EventType.DOUBLE_BUTTON_PRESS: - previewWindow = self.builder.get_object("previewWindow") - previewImg = self.builder.get_object("previewImg") - previewImg.set_from_file(image) - previewWindow.show_all() - previewWindow.popup() - - self.to_be_background = image - self.apply_type = 2 - self.help_label.set_markup(f"{file}") diff --git a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/utils/Logger.py b/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/utils/Logger.py deleted file mode 100644 index 06eed47..0000000 --- a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/utils/Logger.py +++ /dev/null @@ -1,56 +0,0 @@ -# Python imports -import os, logging - -# Application imports - - -class Logger: - def __init__(self, config_path): - self._CONFIG_PATH = config_path - - def get_logger(self, loggerName = "NO_LOGGER_NAME_PASSED", createFile = True): - """ - Create a new logging object and return it. - :note: - NOSET # Don't know the actual log level of this... (defaulting or literally none?) - Log Levels (From least to most) - Type Value - CRITICAL 50 - ERROR 40 - WARNING 30 - INFO 20 - DEBUG 10 - :param loggerName: Sets the name of the logger object. (Used in log lines) - :param createFile: Whether we create a log file or just pump to terminal - - :return: the logging object we created - """ - - globalLogLvl = logging.DEBUG # Keep this at highest so that handlers can filter to their desired levels - chLogLevel = logging.CRITICAL # Prety musch the only one we change ever - fhLogLevel = logging.DEBUG - log = logging.getLogger(loggerName) - log.setLevel(globalLogLvl) - - # Set our log output styles - fFormatter = logging.Formatter('[%(asctime)s] %(pathname)s:%(lineno)d %(levelname)s - %(message)s', '%m-%d %H:%M:%S') - cFormatter = logging.Formatter('%(pathname)s:%(lineno)d] %(levelname)s - %(message)s') - - ch = logging.StreamHandler() - ch.setLevel(level=chLogLevel) - ch.setFormatter(cFormatter) - log.addHandler(ch) - - if createFile: - folder = self._CONFIG_PATH - file = f"{folder}/application.log" - - if not os.path.exists(folder): - os.mkdir(folder) - - fh = logging.FileHandler(file) - fh.setLevel(level=fhLogLevel) - fh.setFormatter(fFormatter) - log.addHandler(fh) - - return log diff --git a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/utils/Settings.py b/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/utils/Settings.py deleted file mode 100644 index 0bf6325..0000000 --- a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/utils/Settings.py +++ /dev/null @@ -1,112 +0,0 @@ -# Python imports -import os - -# Gtk imports -import gi, cairo -gi.require_version('Gtk', '3.0') -gi.require_version('Gdk', '3.0') - -from gi.repository import Gtk -from gi.repository import Gdk - - -# Application imports -from . import Logger - - - -class Settings: - def __init__(self): - self._SCRIPT_PTH = os.path.dirname(os.path.realpath(__file__)) - self._USER_HOME = os.path.expanduser('~') - self._CONFIG_PATH = f"{self._USER_HOME}/.config/{app_name.lower()}" - self._GLADE_FILE = f"{self._CONFIG_PATH}/Main_Window.glade" - self._CSS_FILE = f"{self._CONFIG_PATH}/stylesheet.css" - self._DEFAULT_ICONS = f"{self._CONFIG_PATH}/icons" - self._WINDOW_ICON = f"{self._DEFAULT_ICONS}/{app_name.lower()}.png" - self._USR_PATH = f"/usr/share/{app_name.lower()}" - self._CONFIG_FILE = f"{self._CONFIG_PATH}/settings.json" - self._XSCREEN_SAVERS = "/usr/lib/xscreensaver/" - - - self._logger = Logger(self._CONFIG_PATH).get_logger() - self._builder = Gtk.Builder() - self._main_window = None - - # '_filters' - self._vids_filter = ('.mkv', '.avi', '.flv', '.mov', '.m4v', '.mpg', '.wmv', '.mpeg', '.mp4', '.webm') - self._images_filter = ('.png', '.jpg', '.jpeg', '.gif') - - self._success_color = "#88cc27" - self._warning_color = "#ffa800" - self._error_color = "#ff0000" - - if not os.path.exists(self._GLADE_FILE): - self._GLADE_FILE = f"{self._USR_PATH}/Main_Window.glade" - if not os.path.exists(self._CSS_FILE): - self._CSS_FILE = f"{self._USR_PATH}/stylesheet.css" - if not os.path.exists(self._WINDOW_ICON): - self._WINDOW_ICON = f"{self._USR_PATH}/icons/{app_name.lower()}.png" - if not os.path.exists(self._DEFAULT_ICONS): - self.DEFAULT_ICONS = f"{self._USR_PATH}/icons" - - self._builder.add_from_file(self._GLADE_FILE) - - - - def create_window(self): - # Get window and connect signals - self._main_window = self._builder.get_object("Main_Window") - self.set_window_data() - - def set_window_data(self): - self._main_window.set_icon_from_file(self._WINDOW_ICON) - screen = self._main_window.get_screen() - visual = screen.get_rgba_visual() - - if visual != None and screen.is_composited(): - self._main_window.set_visual(visual) - self._main_window.set_app_paintable(True) - self._main_window.connect("draw", self.draw_area) - - # bind css file - cssProvider = Gtk.CssProvider() - cssProvider.load_from_path(self._CSS_FILE) - screen = Gdk.Screen.get_default() - styleContext = Gtk.StyleContext() - styleContext.add_provider_for_screen(screen, cssProvider, Gtk.STYLE_PROVIDER_PRIORITY_USER) - - def get_monitor_data(self): - screen = self._builder.get_object("Main_Window").get_screen() - monitors = [] - for m in range(screen.get_n_monitors()): - monitors.append(screen.get_monitor_geometry(m)) - - for monitor in monitors: - print("{}x{}|{}+{}".format(monitor.width, monitor.height, monitor.x, monitor.y)) - - return monitors - - def draw_area(self, widget, cr): - cr.set_source_rgba(0, 0, 0, 0.54) - cr.set_operator(cairo.OPERATOR_SOURCE) - cr.paint() - cr.set_operator(cairo.OPERATOR_OVER) - - - - - def get_builder(self): return self._builder - def get_logger(self): return self._logger - def get_main_window(self): return self._main_window - def get_home_path(self): return self._USER_HOME - def get_config_file(self): return self._CONFIG_FILE - def get_xscreensavers(self): return self._XSCREEN_SAVERS - - # Filter returns - def get_vids_filter(self): return self._vids_filter - def get_images_filter(self): return self._images_filter - - def get_success_color(self): return self._success_color - def get_warning_color(self): return self._warning_color - def get_error_color(self): return self._error_color diff --git a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/utils/__init__.py b/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/utils/__init__.py deleted file mode 100644 index 15fcd01..0000000 --- a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/utils/__init__.py +++ /dev/null @@ -1,2 +0,0 @@ -from .Logger import Logger -from .Settings import Settings diff --git a/src/debs/gwinwrap-0-0-2-x64/opt/gwinwrap.zip b/src/debs/gwinwrap-0-0-2-x64/opt/gwinwrap.zip new file mode 100644 index 0000000..40161a2 Binary files /dev/null and b/src/debs/gwinwrap-0-0-2-x64/opt/gwinwrap.zip differ diff --git a/src/debs/gwinwrap-0-0-2-x64/usr/share/applications/gwinwrap.desktop b/src/debs/gwinwrap-0-0-2-x64/usr/share/applications/gwinwrap.desktop new file mode 100755 index 0000000..4451f4a --- /dev/null +++ b/src/debs/gwinwrap-0-0-2-x64/usr/share/applications/gwinwrap.desktop @@ -0,0 +1,9 @@ +[Desktop Entry] +Encoding=UTF-8 +Name=GWinWrap +Comment=Glade GUI with python controls for XWinWrap +Exec=/bin/gwinwrap %f +Icon=/usr/share/gwinwrap/icons/gwinwrap.png +Terminal=false +Type=Application +Categories=Accessories;System;Settings; diff --git a/src/debs/gwinwrap-0-0-2-x64/usr/share/gwinwrap/Main_Window.glade b/src/debs/gwinwrap-0-0-2-x64/usr/share/gwinwrap/Main_Window.glade index c6df58f..f26f25a 100644 --- a/src/debs/gwinwrap-0-0-2-x64/usr/share/gwinwrap/Main_Window.glade +++ b/src/debs/gwinwrap-0-0-2-x64/usr/share/gwinwrap/Main_Window.glade @@ -1,5 +1,5 @@ - + @@ -31,6 +31,11 @@ gtk-cancel 3 + + True + False + gtk-close + True False @@ -68,90 +73,45 @@ gtk-media-stop 3 - - 950 - 600 + + True False - GWinWrap - center - 950 - 600 - usr/share/gwinwrap/icons/gwinwrap.png - center - + True False + 15 + 15 + 15 + vertical True False - 15 - 15 - 15 - vertical + 5 - + True False - 5 - - - True - False - 15 - Note: Double click an image to view the video or image. - - - True - True - 0 - - - - - True - False - Chose Dream Scene / Image Directory - select-folder - False - Folders - Dream Scene / Image Dir - - - - False - True - 1 - - - - - True - True - True - settingsImage - True - - - - False - True - 2 - - + 15 + Note: Double click an image to view the video or image. - False + True True 0 - + True False - True + Chose Dream Scene / Image Directory + select-folder + False + Folders + Dream Scene / Image Dir + False @@ -159,64 +119,191 @@ 1 + + + True + True + True + settingsImage + True + + + + False + True + 2 + + + + + False + True + 0 + + + + + True + False + True + + + False + True + 1 + + + + + True + True + in + + + True + False + + + + True + False + vertical + 10 + 10 + True + True + + + 640 + 525 + True + False + Choose Image/Video Directory... + + + + + + 0 + 0 + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + True + True + 2 + + + + + Clear + True + True + True + clearImage + True + + + + False + True + 3 + + + + + True + True + 0 + + + + + 300 + True + False + 10 + 15 + 15 + 15 + False + vertical + + + True + False + vertical + + + Use XScreenSaver + True + True + False + center + 5 + True + + + + False + True + 0 + + True True in - + True - False + False + True + XScreensaverStore + False + + + + + - - - True - False - vertical - 10 - 10 - True - True + + XScreensaves - - 640 - 525 - True - False - Choose Image/Video Directory... - - - - - - 0 - 0 - - - - - - - - - - - - - - - - - - - - - - - - - + + + 0 + @@ -226,23 +313,7 @@ True True - 2 - - - - - Clear - True - True - True - clearImage - True - - - - False - True - 3 + 1 @@ -254,14 +325,9 @@ - 300 True False - 10 - 15 - 15 - 15 - False + False vertical @@ -269,15 +335,37 @@ False vertical - - Use XScreenSaver + True - True - False - center - 5 - True - + False + + + True + False + 10 + 10 + Playback Resolutions + + + True + True + 0 + + + + + True + False + 10 + 10 + Position Offset + + + True + True + 1 + + False @@ -286,35 +374,85 @@ - + True - True - in + False - + True - False - True - XScreensaverStore - False - - - - - - - - XScreensaves - - - - 0 - - - - + False + 3 + + 7680x4320 + 3840x2160 + 2048x1080 + 1920x1080 + 1440x720 + 1600x900 + 1280x720 + 800x600 + + + True + True + 0 + + + + True + False + + + True + True + 1 + + + + + False + True + 1 + + + + + False + True + 0 + + + + + True + False + vertical + + + True + False + 10 + 5 + Save Path + + + True + True + 0 + + + + + True + False + 0 + + .animatedBGstarter.sh + .animatedBGstarter2.sh + .animatedBGstarter3.sh + True @@ -324,267 +462,121 @@ - True + False True - 0 + 1 - + + True False - False - vertical - + + Save True - False - vertical - - - True - False - - - True - False - 10 - 10 - Playback Resolutions - - - True - True - 0 - - - - - True - False - 10 - 10 - Position Offset - - - True - True - 1 - - - - - False - True - 0 - - - - - True - False - - - True - False - 3 - - 7680x4320 - 3840x2160 - 2048x1080 - 1920x1080 - 1440x720 - 1600x900 - 1280x720 - 800x600 - - - - True - True - 0 - - - - - True - False - - - True - True - 1 - - - - - False - True - 1 - - + True + True + True + True + saveImage + True + - False - True - 0 + 1 + 0 - + + (Re)Start True - False - vertical - - - True - False - 10 - 5 - Save Path - - - True - True - 0 - - - - - True - False - 0 - - .animatedBGstarter.sh - .animatedBGstarter2.sh - .animatedBGstarter3.sh - - - - True - True - 1 - - + True + True + True + True + startImage + True + - False - True - 1 + 0 + 0 - - + + Stop True - False - - - Save - True - True - True - True - True - saveImage - True - - - - 1 - 0 - - - - - (Re)Start - True - True - True - True - True - startImage - True - - - - 0 - 0 - - - - - Stop - True - True - True - True - True - stopImage - True - - - - 0 - 1 - - - - - Close - True - True - True - True - True - closeImage - True - - - - 1 - 1 - - - - - - - - - - - - - - - - - + True + True + True + True + stopImage + True + - False - True - 2 + 0 + 1 + + + Close + True + True + True + True + True + closeImage + True + + + + 1 + 1 + + + + + + + + + + + + + + + + + False - False - end - 1 + True + 2 False - True - 1 + False + end 1 + + False + True + 1 + 1 + @@ -691,6 +683,7 @@ True True True + closePopupImage2 True @@ -770,6 +763,7 @@ True Set Custom Default Path Set Custom Start Path + True @@ -808,6 +802,7 @@ True Set Custom Video Player Set Custom Video Player + True @@ -846,6 +841,7 @@ True Set Custom Image Viewer Set Custom Image Viewer + False diff --git a/src/debs/gwinwrap-0-0-2-x64/usr/share/gwinwrap/settings.json b/src/debs/gwinwrap-0-0-2-x64/usr/share/gwinwrap/settings.json index 596ddd2..b373664 100644 --- a/src/debs/gwinwrap-0-0-2-x64/usr/share/gwinwrap/settings.json +++ b/src/debs/gwinwrap-0-0-2-x64/usr/share/gwinwrap/settings.json @@ -1,9 +1,36 @@ { - "settings":[ - { - "start_path":"/home/abaddon/LazyShare/Movies-TV-Music/Dream Scenes/Games/Halo", - "default_player":"mpv", - "default_img_viewer":"mirage" - } - ] -} \ No newline at end of file + "config":{ + "start_path":"", + "xscreensaver_path":"/usr/lib/xscreensaver/", + "default_player":"mpv", + "default_img_viewer":"mirage" + }, + "filters":{ + "videos":[ + ".mkv", + ".mp4", + ".webm", + ".avi", + ".mov", + ".m4v", + ".mpg", + ".mpeg", + ".wmv", + ".flv" + ], + "images":[ + ".png", + ".jpg", + ".jpeg", + ".gif", + ".ico", + ".tga", + ".webp" + ] + }, + "theming":{ + "success_color":"#88cc27", + "warning_color":"#ffa800", + "error_color":"#ff0000" + } +} diff --git a/src/versions/0.0.1/GWinWrap/GWinWrap.desktop b/src/versions/0.0.1/GWinWrap/GWinWrap.desktop deleted file mode 100644 index 543fdb6..0000000 --- a/src/versions/0.0.1/GWinWrap/GWinWrap.desktop +++ /dev/null @@ -1,9 +0,0 @@ -[Desktop Entry] -Encoding=UTF-8 -Name=GWinWrap -Comment=Glade gui with python controls for XWinWrap -Exec=gwinwrap -Icon=/opt/GWinWrap/resources/icons/GWinWrap.png -Terminal=false -Type=Application -Categories=Accessories;System;Settings; diff --git a/src/versions/0.0.1/GWinWrap/__init__.py b/src/versions/0.0.1/GWinWrap/__init__.py deleted file mode 100644 index 0beb3ee..0000000 --- a/src/versions/0.0.1/GWinWrap/__init__.py +++ /dev/null @@ -1,41 +0,0 @@ -#!/usr/bin/python3 - -# Gtk imports -import gi, faulthandler, signal -gi.require_version('Gtk', '3.0') - -from gi.repository import Gtk as gtk -from gi.repository import Gdk as gdk -from gi.repository import GLib - -# Python imports -import inspect - -from setproctitle import setproctitle - -# Application imports -from utils import Settings -from signal_classes import CrossClassSignals - - -class Main: - def __init__(self): - setproctitle('GWinWrap') - GLib.unix_signal_add(GLib.PRIORITY_DEFAULT, signal.SIGINT, gtk.main_quit) - faulthandler.enable() # For better debug info - - settings = Settings() - builder = settings.returnBuilder() - - # Gets the methods from the classes and sets to handler. - # Then, builder connects to any signals it needs. - classes = [CrossClassSignals(settings)] - - handlers = {} - for c in classes: - methods = inspect.getmembers(c, predicate=inspect.ismethod) - handlers.update(methods) - - builder.connect_signals(handlers) - window = settings.createWindow() - window.show() diff --git a/src/versions/0.0.1/GWinWrap/__main__.py b/src/versions/0.0.1/GWinWrap/__main__.py deleted file mode 100644 index 60c7ea2..0000000 --- a/src/versions/0.0.1/GWinWrap/__main__.py +++ /dev/null @@ -1,9 +0,0 @@ -from __init__ import Main, gtk - - -if __name__ == "__main__": - try: - main = Main() - gtk.main() - except Exception as e: - print(e) diff --git a/src/versions/0.0.1/GWinWrap/resources/Main_Window.glade b/src/versions/0.0.1/GWinWrap/resources/Main_Window.glade deleted file mode 100644 index 495ebfe..0000000 --- a/src/versions/0.0.1/GWinWrap/resources/Main_Window.glade +++ /dev/null @@ -1,844 +0,0 @@ - - - - - - - inode/directory - - - - - - - - - - True - False - gtk-clear - 3 - - - True - False - gtk-quit - 3 - - - True - False - gtk-cancel - 3 - - - True - False - gtk-jump-to - 3 - - - True - False - gtk-save - 3 - - - True - False - gtk-save - 3 - - - True - False - Settings.... - gtk-properties - 3 - - - True - False - gtk-media-play - 3 - - - True - False - gtk-media-stop - 3 - - - 950 - 600 - False - GWinWrap - center - 950 - 600 - icons/GWinWrap.png - center - - - - - - True - False - - - True - False - 15 - 15 - 15 - vertical - - - True - False - 5 - - - True - False - 15 - Note: Double click an image to view the video or image. - - - True - True - 0 - - - - - True - False - Chose Dream Scene / Image Directory - select-folder - False - Folders - Dream Scene / Image Dir - - - - False - True - 1 - - - - - True - True - True - settingsImage - True - - - - False - True - 2 - - - - - False - True - 0 - - - - - True - False - True - - - False - True - 1 - - - - - True - True - in - - - True - False - - - True - False - vertical - 10 - 10 - True - True - - - 640 - 525 - True - False - Choose Image/Video Directory... - - - - - - 0 - 0 - - - - - - - - - True - True - 2 - - - - - Clear - True - True - True - clearImage - True - - - - False - True - 3 - - - - - True - True - 0 - - - - - 300 - True - False - 10 - 15 - 15 - 15 - False - vertical - - - True - False - vertical - - - Use XScreenSaver - True - True - False - center - 5 - True - - - - False - True - 0 - - - - - True - True - in - - - True - False - True - XScreensaver List - False - - - - - - - - XScreensaves - - - - 0 - - - - - - - - - True - True - 1 - - - - - True - True - 0 - - - - - True - False - False - vertical - - - True - False - vertical - - - True - False - - - True - False - 10 - 10 - Playback Resolutions - - - True - True - 0 - - - - - True - False - 10 - 10 - Position Offset - - - True - True - 1 - - - - - False - True - 0 - - - - - True - False - - - True - False - 3 - - 7680x4320 - 3840x2160 - 2048x1080 - 1920x1080 - 1440x720 - 1600x900 - 1280x720 - 800x600 - - - - True - True - 0 - - - - - True - False - - - True - True - 1 - - - - - False - True - 1 - - - - - False - True - 0 - - - - - True - False - vertical - - - True - False - 10 - 5 - Save Path - - - True - True - 0 - - - - - True - False - 0 - - .animatedBGstarter.sh - .animatedBGstarter2.sh - .animatedBGstarter3.sh - - - - True - True - 1 - - - - - False - True - 1 - - - - - True - False - - - Save - True - True - True - True - True - saveImage - True - - - - 1 - 0 - - - - - (Re)Start - True - True - True - True - True - startImage - True - - - - 0 - 0 - - - - - Stop - True - True - True - True - True - stopImage - True - - - - 0 - 1 - - - - - Close - True - True - True - True - True - closeImage - True - - - - 1 - 1 - - - - - False - True - 2 - - - - - False - False - end - 1 - - - - - False - True - 1 - 1 - - - - - - - 640 - 525 - False - 350 - True - True - helpLabel - bottom - False - - - True - False - vertical - - - True - False - - - True - True - True - Close Demo Window - closePopupImage - True - - - - False - True - end - 0 - - - - - False - True - 0 - - - - - True - False - 0 - none - - - True - False - - - - - True - True - 1 - - - - - - - 640 - 525 - False - True - True - helpLabel - bottom - - - True - False - vertical - - - True - False - bottom - - - Main Image Viewer - True - True - True - openProgImage - True - - - - False - True - 0 - - - - - True - True - True - True - - - - False - True - 1 - - - - - False - True - 0 - - - - - True - True - in - False - - - True - False - - - True - False - gtk-missing-image - 6 - - - - - - - True - True - 1 - - - - - - - 250 - False - button1 - - - True - False - vertical - - - True - False - - - True - False - icons/folder.png - - - False - True - 0 - - - - - 330 - 26 - True - True - Set Custom Default Path - Set Custom Default Path - - - False - True - 1 - - - - - False - True - 0 - - - - - True - False - - - True - False - icons/player.png - - - False - True - 0 - - - - - 330 - 26 - True - True - Set Custom Video Player - Set Custom Video Player - - - False - True - 1 - - - - - False - True - 1 - - - - - True - False - - - True - False - icons/picture.png - - - False - True - 0 - - - - - 330 - 26 - True - True - Set Custom Image Viewer - Set Custom Image Viewer - - - False - True - 1 - - - - - False - True - 2 - - - - - Save - True - True - True - saveImag - True - - - - False - True - 3 - - - - - - diff --git a/src/versions/0.0.1/GWinWrap/resources/icons/GWinWrap.png b/src/versions/0.0.1/GWinWrap/resources/icons/GWinWrap.png deleted file mode 100644 index cdd708d..0000000 Binary files a/src/versions/0.0.1/GWinWrap/resources/icons/GWinWrap.png and /dev/null differ diff --git a/src/versions/0.0.1/GWinWrap/resources/icons/folder.png b/src/versions/0.0.1/GWinWrap/resources/icons/folder.png deleted file mode 100644 index 909f052..0000000 Binary files a/src/versions/0.0.1/GWinWrap/resources/icons/folder.png and /dev/null differ diff --git a/src/versions/0.0.1/GWinWrap/resources/icons/picture.png b/src/versions/0.0.1/GWinWrap/resources/icons/picture.png deleted file mode 100644 index 46f1ae6..0000000 Binary files a/src/versions/0.0.1/GWinWrap/resources/icons/picture.png and /dev/null differ diff --git a/src/versions/0.0.1/GWinWrap/resources/icons/player.png b/src/versions/0.0.1/GWinWrap/resources/icons/player.png deleted file mode 100644 index 4f5ebda..0000000 Binary files a/src/versions/0.0.1/GWinWrap/resources/icons/player.png and /dev/null differ diff --git a/src/versions/0.0.1/GWinWrap/resources/stylesheet.css b/src/versions/0.0.1/GWinWrap/resources/stylesheet.css deleted file mode 100644 index 722921b..0000000 --- a/src/versions/0.0.1/GWinWrap/resources/stylesheet.css +++ /dev/null @@ -1,3 +0,0 @@ -window { - -} diff --git a/src/versions/0.0.1/GWinWrap/signal_classes/CrossClassSignals.py b/src/versions/0.0.1/GWinWrap/signal_classes/CrossClassSignals.py deleted file mode 100644 index 6cbbb7e..0000000 --- a/src/versions/0.0.1/GWinWrap/signal_classes/CrossClassSignals.py +++ /dev/null @@ -1,403 +0,0 @@ -# Gtk imports -import gi - -gi.require_version('Gtk', '3.0') -gi.require_version('Gdk', '3.0') - -from gi.repository import Gtk as gtk -from gi.repository import Gdk as gdk -from gi.repository import GLib as glib -from gi.repository import GdkPixbuf - -# Python imports -import threading, subprocess, signal, os, sys, re, hashlib, time - -from os import listdir -from os.path import isfile, join - -# Application imports -from utils import SaveStateToXWinWarp, SaveGWinWrapSettings - - - -def threaded(fn): - def wrapper(*args, **kwargs): - threading.Thread(target=fn, args=args, kwargs=kwargs).start() - - return wrapper - - -class CrossClassSignals: - def __init__(self, settings): - self.settings = settings - self.builder = self.settings.returnBuilder() - - self.WINDOW = self.builder.get_object("Main_Window").get_window() - self.stateSaver = SaveStateToXWinWarp() - self.sttngsSver = SaveGWinWrapSettings() - - # Add filter to allow only folders to be selected - dialog = self.builder.get_object("selectedDirDialog") - filefilter = self.builder.get_object("Folders") - dialog.add_filter(filefilter) - - # Get reference to remove and add it back... - self.gridLabel = self.builder.get_object("gridLabel") - - self.focusedImg = gtk.Image() - self.usrHome = os.path.expanduser('~') - self.xScreenVal = None - self.toSavePath = None # Global file path and type for saving to file - self.applyType = 1 # 1 is XWinWrap and 2 is Nitrogen - - self.loadProgress = self.builder.get_object("loadProgress") - self.helpLabel = self.builder.get_object("helpLabel") - self.defaultLabel = "Note: Double click an image to view the video or image." - self.savedLabel = "Saved settings..." - self.appliedLabel = "Running xwinwrap..." - self.stoppedLabel = "Stopped xwinwrap..." - # foreground=\"#ffa800\" - # foreground=\"#88cc27\" - # foreground=\"#ff0000\" - - # Fill list xscreensaver - self.xscrPth = "/usr/lib/xscreensaver/" - xscreenList = self.builder.get_object("XScreensaver List") - list = [f for f in listdir(self.xscrPth) if isfile(join(self.xscrPth, f))] - list.sort() - - for file in list: - xscreenList.append((file,)) - - self.selectedImg = None # EventBox holder - self.defPath = None - self.player = None - self.imgVwr = None - self.demoAreaPid = None - - self.setPosData() - self.retrieveSettings() - - - - def setNewDir(self, widget, data=None): - dir = widget.get_filename() - threading.Thread(target=self.newDir, args=(dir,)).start() - - def newDir(self, dir): - imageGrid = self.builder.get_object("imageGrid") - dirPath = dir - list = [f for f in listdir(dirPath) if isfile(join(dirPath, f))] - files = [] - row = 0 - col = 0 - - for file in list: - if file.lower().endswith(('.mkv', '.avi', '.flv', '.mov', '.m4v', '.mpg', '.wmv', '.mpeg', '.mp4', '.webm', '.png', '.jpg', '.jpeg', '.gif')): - files.append(file) - - # fractionTick = 1.0 / 1.0 if len(files) == 0 else len(files) - # tickCount = 0.0 - self.clear() - imageGrid.remove_column(0) - self.loadProgress.set_text("Loading...") - self.loadProgress.set_fraction(0.0) - self.helpLabel.set_markup("" + dirPath.strip(self.usrHome) + "") - for file in files: - self.porocess_file(imageGrid, dirPath, file, col, row) - - col += 1 - if col == 2: - col = 0 - row += 1 - - self.loadProgress.set_text("Finished...") - - @threaded - def porocess_file(self, imageGrid, dirPath, file, col, row): - fullPathFile = dirPath + "/" + file - eveBox = gtk.EventBox() - thumbnl = gtk.Image() - - if file.lower().endswith(('.mkv', '.avi', '.flv', '.mov', '.m4v', '.mpg', '.wmv', '.mpeg', '.mp4', '.webm')): - fileHash = hashlib.sha256(str.encode(fullPathFile)).hexdigest() - hashImgpth = self.usrHome + "/.thumbnails/normal/" + fileHash + ".png" - if isfile(hashImgpth) == False: - self.generateThumbnail(fullPathFile, hashImgpth) - - thumbnl = self.createGtkImage(hashImgpth, [310, 310]) - eveBox.connect("button_press_event", self.runMplayerProcess, (fullPathFile, file, eveBox,)) - eveBox.connect("enter_notify_event", self.mouseOver, ()) - eveBox.connect("leave_notify_event", self.mouseOut, ()) - elif file.lower().endswith(('.png', '.jpg', '.jpeg', '.gif')): - thumbnl = self.createGtkImage(fullPathFile, [310, 310]) - eveBox.connect("button_press_event", self.runImageViewerProcess, (fullPathFile, file, eveBox,)) - eveBox.connect("enter_notify_event", self.mouseOver, ()) - eveBox.connect("leave_notify_event", self.mouseOut, ()) - else: - print("Not a video or image file.") - return - - glib.idle_add(self.preGridSetup, (eveBox, thumbnl, )) - glib.idle_add(self.addToGrid, (imageGrid, eveBox, col, row,)) - # tickCount = tickCount + fractionTick - # self.loadProgress.set_fraction(tickCount) - - - - - def preGridSetup(self, args): - args[0].show() - args[1].show() - args[0].add(args[1]) - - def addToGrid(self, args): - args[0].attach(args[1], args[2], args[3], 1, 1) - - def generateThumbnail(self, fullPathFile, hashImgpth): - # Stream duration - command = ["ffprobe", "-v", "error", "-select_streams", "v:0", "-show_entries", "stream=duration", "-of", "default=noprint_wrappers=1:nokey=1", fullPathFile] - data = subprocess.run(command, stdout=subprocess.PIPE) - duration = data.stdout.decode('utf-8') - - # Format (container) duration - if "N/A" in duration: - command = ["ffprobe", "-v", "error", "-show_entries", "format=duration", "-of", "default=noprint_wrappers=1:nokey=1", fullPathFile] - data = subprocess.run(command , stdout=subprocess.PIPE) - duration = data.stdout.decode('utf-8') - - # Stream duration type: image2 - if "N/A" in duration: - command = ["ffprobe", "-v", "error", "-select_streams", "v:0", "-f", "image2", "-show_entries", "stream=duration", "-of", "default=noprint_wrappers=1:nokey=1", fullPathFile] - data = subprocess.run(command, stdout=subprocess.PIPE) - duration = data.stdout.decode('utf-8') - - # Format (container) duration type: image2 - if "N/A" in duration: - command = ["ffprobe", "-v", "error", "-f", "image2", "-show_entries", "format=duration", "-of", "default=noprint_wrappers=1:nokey=1", fullPathFile] - data = subprocess.run(command , stdout=subprocess.PIPE) - duration = data.stdout.decode('utf-8') - - # Get frame roughly 35% through video - grabTime = str( int( float( duration.split(".")[0] ) * 0.35) ) - command = ["ffmpeg", "-ss", grabTime, "-i", fullPathFile, "-an", "-vframes", "1", "-s", "320x180", "-q:v", "2", hashImgpth] - subprocess.call(command) - - def createGtkImage(self, path, wxh): - try: - pixbuf = GdkPixbuf.Pixbuf.new_from_file_at_scale( - filename = path, - width = wxh[0], - height = wxh[1], - preserve_aspect_ratio = True) - return gtk.Image.new_from_pixbuf(pixbuf) - except Exception as e: - print(e) - - return gtk.Image() - - - def openMainImageViewer(self, widget): - subprocess.call([self.imgVwr, self.toSavePath]) - - def runImageViewerProcess(self, widget, eve, params): - self.setSelected(params[2]) - - if eve.type == gdk.EventType.DOUBLE_BUTTON_PRESS: - previewWindow = self.builder.get_object("previewWindow") - previewImg = self.builder.get_object("previewImg") - previewImg.set_from_file(params[0]) - previewWindow.show_all() - previewWindow.popup() - - self.toSavePath = params[0] - self.applyType = 2 - self.helpLabel.set_markup("" + params[1] + "") - - def setSelected(self, eveBox): - if self.selectedImg: - col = gdk.RGBA(0.0, 0.0, 0.0, 0.0) - self.selectedImg.override_background_color(gtk.StateType.NORMAL, col) - - col = gdk.RGBA(0.9, 0.7, 0.4, 0.74) - eveBox.override_background_color(gtk.StateType.NORMAL, col) - self.selectedImg = eveBox - - def closePopup(self, widget): - self.builder.get_object("previewWindow").popdown() - - def mouseOver(self, widget, eve, args): - hand_cursor = gdk.Cursor(gdk.CursorType.HAND2) - self.builder.get_object("Main_Window").get_window().set_cursor(hand_cursor) - - def mouseOut(self, widget, eve, args): - watch_cursor = gdk.Cursor(gdk.CursorType.LEFT_PTR) - self.builder.get_object("Main_Window").get_window().set_cursor(watch_cursor) - - def toggleXscreenUsageField(self, widget, data=None): - useXscreenSaver = self.builder.get_object("useXScrnList") - if useXscreenSaver.get_active(): - self.builder.get_object("xScreenSvrList").set_sensitive(True) - else: - self.builder.get_object("xScreenSvrList").set_sensitive(False) - - def popSttingsWindow(self, widget): - self.builder.get_object("settingsWindow").popup() - - def saveToSettingsFile(self, widget): - self.defPath = self.builder.get_object("customDefaultPath").get_text().strip() - self.player = self.builder.get_object("customVideoPlyr").get_text().strip() - self.imgVwr = self.builder.get_object("customImgVwr").get_text().strip() - - self.sttngsSver.saveSettings(self.defPath, self.player, self.imgVwr) - - def retrieveSettings(self): - data = self.sttngsSver.retrieveSettings() - self.defPath = data[0] - self.player = data[1] - self.imgVwr = data[2] - - self.builder.get_object("customDefaultPath").set_text(self.defPath) - self.builder.get_object("customVideoPlyr").set_text(self.player) - self.builder.get_object("customImgVwr").set_text(self.imgVwr) - self.builder.get_object("selectedDirDialog").set_filename(self.defPath) - - if self.defPath: - self.newDir(self.defPath) - - - def saveToFile(self, widget, data=None): - saveLoc = self.builder.get_object("saveLoc").get_active_text() - useXscreenSaver = self.builder.get_object("useXScrnList").get_active() - plyBckRes = self.builder.get_object("playbackResolution") - offset4Res = self.builder.get_object("posOffset") - resolution = plyBckRes.get_active_text() + offset4Res.get_active_text() - self.applyType = self.stateSaver.saveToFile(self.toSavePath, resolution, - saveLoc, useXscreenSaver, self.xScreenVal, self.player) - if self.applyType == -1: - self.helpLabel.set_markup("Nothing saved...") - return - - self.helpLabel.set_markup(self.savedLabel) - - def applySttngs(self, widget, data=None): - os.system("killall xwinwrap &") - if self.applyType == 1: - files = os.listdir(self.usrHome) - for file in files: - fPath = self.usrHome + "/" + file - if os.path.isfile(fPath) and "animatedBGstarter" in file: - os.system("bash -c '~/" + file + "' &") - elif self.applyType == 2: - os.system("nitrogen --restore &") - else: - os.system("nitrogen --restore &") - self.helpLabel.set_markup(self.appliedLabel) - - def killXWinWrp(self, widget, data=None): - os.system("killall xwinwrap &") - self.helpLabel.set_markup(self.stoppedLabel) - - def passXScreenVal(self, widget): - xSvrListStore = self.builder.get_object("XScreensaver List") - row = widget.get_cursor() - path = gtk.TreePath(row.path) - treeiter = xSvrListStore.get_iter(path[0]) - self.xScreenVal = xSvrListStore.get_value(treeiter, 0) - - - def runMplayerProcess(self, widget, eve, params): - self.setSelected(params[2]) - video = params[0] - - if eve.type == gdk.EventType.DOUBLE_BUTTON_PRESS: - if self.player == "mplayer": - xid = self.getXID() - command = [self.player, video, "-slave", "-wid", str(xid), "-really-quiet", "-ao", "null", "-loop", "0"] - self.runDemoToDrawArea(command) - else: - subprocess.call([self.player, video, "-really-quiet", "-ao", "null", "-loop", "0"]) - - self.toSavePath = params[0] - self.applyType = 1 - self.helpLabel.set_markup("" + params[1] + "") - - def previewXscreen(self, widget, eve): - if eve.type == gdk.EventType.DOUBLE_BUTTON_PRESS: - demoXscrnSaver = self.xscrPth + self.xScreenVal - xid = self.getXID() - command = [demoXscrnSaver, "-window-id", str(xid)] - self.runDemoToDrawArea(command) - - def getXID(self): - # Must be actualized before getting window - demoWindowPopup = self.builder.get_object("demoPreviewPopWindow") - - if demoWindowPopup.get_visible() == False: - demoWindowPopup.show_all() - demoWindowPopup.popup() - - demoPreview = self.builder.get_object("demoPreview") - drwWindow = demoPreview.get_window() - return drwWindow.get_xid() - - def runDemoToDrawArea(self, command): - self.helpLabel.set_markup("") - - if self.demoAreaPid: - os.kill(self.demoAreaPid, signal.SIGTERM) #or signal.SIGKILL - self.demoAreaPid = None - time.sleep(.800) # 800 mili-seconds to ensure first process dead - - process = subprocess.Popen(command) - self.demoAreaPid = process.pid - - def closeDemoWindow(self, widget, data=None): - os.kill(self.demoAreaPid, signal.SIGTERM) #or signal.SIGKILL - self.demoAreaPid = None - time.sleep(.200) - self.builder.get_object("demoPreviewPopWindow").popdown() - - def clearSelection(self, widget, data=None): - self.clear() - - def clear(self): - imageGrid = self.builder.get_object("imageGrid") - - while True: - if imageGrid.get_child_at(0,0)!= None: - imageGrid.remove_row(0) - else: - break - - imageGrid.attach(self.gridLabel, 0, 0, 1, 1) - self.builder.get_object("xScreenSvrList").set_sensitive(False) - self.builder.get_object("useXScrnList").set_active(False) - self.helpLabel.set_markup(self.defaultLabel) - self.loadProgress.set_text("") - self.loadProgress.set_fraction(0.0) - self.toSavePath = None - self.xScreenVal = None - self.applyType = 1 # Default to XWinWrap - - - - def setPosData(self): - monitors = self.settings.getMonitorData() - posOff = self.builder.get_object("posOffset") - - for monitor in monitors: - if monitor.x >= 0 and monitor.y >= 0: - posOff.append_text("+" + str(monitor.x) + "+" + str(monitor.y)) - elif monitor.x <= 0 and monitor.y <= 0: - posOff.append_text(str(monitor.x) + str(monitor.y)) - elif monitor.x >= 0 and monitor.y <= 0: - posOff.append_text("+" + str(monitor.x) + str(monitor.y)) - elif monitor.x <= 0 and monitor.y >= 0: - posOff.append_text(str(monitor.x) + "+" + str(monitor.y)) - - posOff.set_active(0) - - - def closeProgram(self, widget, data=None): - sys.exit(0) diff --git a/src/versions/0.0.1/GWinWrap/signal_classes/__init__.py b/src/versions/0.0.1/GWinWrap/signal_classes/__init__.py deleted file mode 100644 index d2d4cdf..0000000 --- a/src/versions/0.0.1/GWinWrap/signal_classes/__init__.py +++ /dev/null @@ -1 +0,0 @@ -from signal_classes.CrossClassSignals import CrossClassSignals diff --git a/src/versions/0.0.1/GWinWrap/utils/SaveGWinWrapSettings.py b/src/versions/0.0.1/GWinWrap/utils/SaveGWinWrapSettings.py deleted file mode 100644 index a26fbb5..0000000 --- a/src/versions/0.0.1/GWinWrap/utils/SaveGWinWrapSettings.py +++ /dev/null @@ -1,52 +0,0 @@ -#!/usr/bin/env python - -import os, json - -class SaveGWinWrapSettings: - def __init__(self): - configFolder = os.path.expanduser('~') + "/.config/gwinwrap/" - self.configFile = configFolder + "settings.ini" - - if os.path.isdir(configFolder) == False: - os.mkdir(configFolder) - - if os.path.isfile(self.configFile) == False: - open(self.configFile, 'a').close() - - - def saveSettings(self, defPath, player, imgVwr): - data = {} - data['gwinwrap_settings'] = [] - - data['gwinwrap_settings'].append({ - 'defPath' : defPath, - 'player' : player, - 'imgvwr' : imgVwr - }) - - with open(self.configFile, 'w') as outfile: - json.dump(data, outfile) - - - def retrieveSettings(self): - returnData = [] - - with open(self.configFile) as infile: - try: - data = json.load(infile) - for obj in data['gwinwrap_settings']: - returnData = [obj['defPath'], obj['player'], obj['imgvwr']] - except Exception as e: - returnData = ['', 'mplayer', 'xdg-open'] - - - if returnData[0] == '': - returnData[0] = '' - - if returnData[1] == '': - returnData[1] = 'mplayer' - - if returnData[2] == '': - returnData[2] = 'xdg-open' - - return returnData diff --git a/src/versions/0.0.1/GWinWrap/utils/SaveStateToXWinWarp.py b/src/versions/0.0.1/GWinWrap/utils/SaveStateToXWinWarp.py deleted file mode 100644 index 1e086be..0000000 --- a/src/versions/0.0.1/GWinWrap/utils/SaveStateToXWinWarp.py +++ /dev/null @@ -1,69 +0,0 @@ -#!/usr/bin/env python - -import os - -class SaveStateToXWinWarp: - def __init__(self): - self.fileWriter = None - self.toSavePath = None - self.useXSvrn = None - self.xScreenVal = None - self.sveFileLoc = None - self.resolution = None - self.player = None - - - def saveToFile(self, toSavePath, resolution, - saveLoc, useXSvrn, xScreenVal, player): - - self.toSavePath = toSavePath - self.useXSvrn = useXSvrn - self.xScreenVal = xScreenVal - self.resolution = resolution - self.player = player - userPth = os.path.expanduser('~') - - # Saves to file with selected and needed settings - if toSavePath: - if toSavePath.lower().endswith(('.png', '.jpg', '.jpeg')): - self.sveFileLoc = userPth + "/" + ".config/nitrogen/bg-saved.cfg" - else: - self.sveFileLoc = userPth + "/" + saveLoc - elif useXSvrn and xScreenVal: - self.sveFileLoc = userPth + "/" + saveLoc - else: - return -1 - - if self.sveFileLoc: - self.fileWriter = open(self.sveFileLoc, "w") - - return self.startSave() - - def startSave(self): - applyType = 1 - output = None - - # XSCREENSAVER - if self.useXSvrn: - output = "xwinwrap -ov -g " + self.resolution + " -st -sp -b -nf -s -ni -- /usr/lib/xscreensaver/" + self.xScreenVal + " -window-id WID -root"; - # GIF - elif self.toSavePath.lower().endswith(('.gif')): - output = "xwinwrap -ov -g " + self.resolution + " -st -sp -b -nf -s -ni -- gifview -a -w WID " + self.toSavePath; - # Standard images using nitrogen - elif self.toSavePath.lower().endswith(('.png', 'jpg', '.jpeg')): - output = "[xin_0] \nfile=" + self.toSavePath + "\nmode=0 \nbgcolor=#000000\n\n[xin_1] \nfile=" + self.toSavePath + "\nmode=0 \nbgcolor=#000000"; - applyType = 2; - # VIDEO - else: - output = "xwinwrap -ov -g " + self.resolution + " -st -sp -b -nf -s -ni -- " + self.player + " -wid WID -really-quiet -ao null -loop 0 '" + self.toSavePath + "'"; - pass - - try: - if self.fileWriter: - self.fileWriter.write(output) - self.fileWriter.close() - except Exception as e: - print(":: Write failed! ::") - print(e) - - return applyType; diff --git a/src/versions/0.0.1/GWinWrap/utils/Settings.py b/src/versions/0.0.1/GWinWrap/utils/Settings.py deleted file mode 100644 index 8ffc52a..0000000 --- a/src/versions/0.0.1/GWinWrap/utils/Settings.py +++ /dev/null @@ -1,74 +0,0 @@ -# Gtk imports -import gi, cairo -gi.require_version('Gtk', '3.0') -gi.require_version('Gdk', '3.0') - -from gi.repository import Gtk as gtk -from gi.repository import Gdk as gdk - -# Python imports -import os - -# Application imports - - -class Settings: - def __init__(self): - self.builder = gtk.Builder() - self.builder.add_from_file("resources/Main_Window.glade") - - # 'Filters' - self.office = ('.doc', '.docx', '.xls', '.xlsx', '.xlt', '.xltx', '.xlm', - '.ppt', 'pptx', '.pps', '.ppsx', '.odt', '.rtf') - self.vids = ('.mkv', '.avi', '.flv', '.mov', '.m4v', '.mpg', '.wmv', - '.mpeg', '.mp4', '.webm') - self.txt = ('.txt', '.text', '.sh', '.cfg', '.conf') - self.music = ('.psf', '.mp3', '.ogg' , '.flac') - self.images = ('.png', '.jpg', '.jpeg', '.gif') - self.pdf = ('.pdf') - - - def createWindow(self): - # Get window and connect signals - window = self.builder.get_object("Main_Window") - window.connect("delete-event", gtk.main_quit) - self.setWindowData(window) - return window - - def setWindowData(self, window): - screen = window.get_screen() - visual = screen.get_rgba_visual() - - if visual != None and screen.is_composited(): - window.set_visual(visual) - - # bind css file - cssProvider = gtk.CssProvider() - cssProvider.load_from_path('resources/stylesheet.css') - screen = gdk.Screen.get_default() - styleContext = gtk.StyleContext() - styleContext.add_provider_for_screen(screen, cssProvider, gtk.STYLE_PROVIDER_PRIORITY_USER) - - # window.set_app_paintable(True) - - def getMonitorData(self): - screen = self.builder.get_object("Main_Window").get_screen() - monitors = [] - for m in range(screen.get_n_monitors()): - monitors.append(screen.get_monitor_geometry(m)) - - for monitor in monitors: - print("{}x{}+{}+{}".format(monitor.width, monitor.height, monitor.x, monitor.y)) - - return monitors - - - def returnBuilder(self): return self.builder - - # Filter returns - def returnOfficeFilter(self): return self.office - def returnVidsFilter(self): return self.vids - def returnTextFilter(self): return self.txt - def returnMusicFilter(self): return self.music - def returnImagesFilter(self): return self.images - def returnPdfFilter(self): return self.pdf diff --git a/src/versions/0.0.1/GWinWrap/utils/__init__.py b/src/versions/0.0.1/GWinWrap/utils/__init__.py deleted file mode 100644 index ca4b01b..0000000 --- a/src/versions/0.0.1/GWinWrap/utils/__init__.py +++ /dev/null @@ -1,3 +0,0 @@ -from utils.Settings import Settings -from utils.SaveStateToXWinWarp import SaveStateToXWinWarp -from utils.SaveGWinWrapSettings import SaveGWinWrapSettings diff --git a/src/versions/0.0.1/XWinWrap/Makefile b/src/versions/0.0.1/XWinWrap/Makefile deleted file mode 100644 index 4a67078..0000000 --- a/src/versions/0.0.1/XWinWrap/Makefile +++ /dev/null @@ -1,20 +0,0 @@ -all: all64 all32 - -all64: - gcc -Wall -Wstrict-prototypes -Wmissing-prototypes -Wmissing-declarations -Wredundant-decls -lX11 -lXext -lXrender xwinwrap.c -o xwinwrap - -mkdir x86_64 - mv ./xwinwrap ./x86_64 - -all32: - gcc -m32 -Wall -Wstrict-prototypes -Wmissing-prototypes -Wmissing-declarations -Wredundant-decls -lX11 -lXext -lXrender xwinwrap.c -o xwinwrap - -mkdir i386 - mv ./xwinwrap ./i386 - -install64: - cp x86_64/xwinwrap /usr/bin - -install32: - cp i386/xwinwrap /usr/bin - -clean: - -rm -rf x86_64/ i386/ diff --git a/src/versions/0.0.1/XWinWrap/xwinwrap.c b/src/versions/0.0.1/XWinWrap/xwinwrap.c deleted file mode 100644 index a2daa04..0000000 --- a/src/versions/0.0.1/XWinWrap/xwinwrap.c +++ /dev/null @@ -1,459 +0,0 @@ -/* - * Copyright © 2005 Novell, Inc. - * - * Permission to use, copy, modify, distribute, and sell this software - * and its documentation for any purpose is hereby granted without - * fee, provided that the above copyright notice appear in all copies - * and that both that copyright notice and this permission notice - * appear in supporting documentation, and that the name of - * Novell, Inc. not be used in advertising or publicity pertaining to - * distribution of the software without specific, written prior permission. - * Novell, Inc. makes no representations about the suitability of this - * software for any purpose. It is provided "as is" without express or - * implied warranty. - * - * NOVELL, INC. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, - * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN - * NO EVENT SHALL NOVELL, INC. BE LIABLE FOR ANY SPECIAL, INDIRECT OR - * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS - * OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, - * NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION - * WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. - * - * Author: David Reveman - */ - -/* - * Modified by: Shantanu Goel - * Tech Blog: http://tech.shantanugoel.com - * Blog: http://blog.shantanugoel.com - * Home Page: http://tech.shantanugoel.com/projects/linux/shantz-xwinwrap - * - * Changelog: - * 15-Jan-09: 1. Fixed the bug where XFetchName returning a NULL for "name" - * resulted in a crash. - * 2. Provided an option to specify the desktop window name. - * 3. Added debug messages - * - * 24-Aug-08: 1. Fixed the geometry option (-g) so that it works - * 2. Added override option (-ov), for seamless integration with - * desktop like a background in non-fullscreen modes - * 3. Added shape option (-sh), to create non-rectangular windows. - * Currently supporting circlular and triangular windows - */ - - /* - * Modified by: Maxim Stewart - * Tech Blog: https://www.itdominator.com/ - * - * Changelog: - * 3-March-19: 1. Cleaned up code formatting. - * 2. Removed unused DEBUG_MSG reference. - * 3. Moved functions to a more reasonable order. - * 4. Compile dev library list 32 & 64 bit: - * # 32 - * sudo apt install libxext-dev:i386 libxrender-dev:i386 libc6-dev-i386 - * - * # 64 - * sudo apt install libxext-dev libxrender-dev libc6-dev - */ - -#include -#include -#include -#include -#include -#include - -#include -#include -#include -#include -#include -#include -#include -#include - -#define WIDTH 512 -#define HEIGHT 384 -#define OPAQUE 0xffffffff -#define NAME "xwinwrap" -#define VERSION "0.3" -#define DESKTOP_WINDOW_NAME_MAX_SIZE 25 -#define DEFAULT_DESKTOP_WINDOW_NAME "Desktop" -#define DEBUG_MSG(x) if(debug) { fprintf(stderr, x); } - -typedef enum { - SHAPE_RECT = 0, - SHAPE_CIRCLE, - SHAPE_TRIG, -} win_shape; - -static pid_t pid = 0; -static char **childArgv = 0; -static int nChildArgv = 0; -int debug = 0; -char desktop_window_name[DESKTOP_WINDOW_NAME_MAX_SIZE]; - -static int addArguments(char **argv, int n) { - char **newArgv; - int i; - - newArgv = realloc (childArgv, sizeof (char *) * (nChildArgv + n)); - if (!newArgv) - return 0; - - for (i = 0; i < n; i++) - newArgv[nChildArgv + i] = argv[i]; - - childArgv = newArgv; - nChildArgv += n; - - return n; -} - -static void setWindowOpacity(Display *dpy, Window win, unsigned int opacity) { - CARD32 o; - o = opacity; - XChangeProperty (dpy, win, XInternAtom (dpy, "_NET_WM_WINDOW_OPACITY", 0), - XA_CARDINAL, 32, PropModeReplace, - (unsigned char *) &o, 1); -} - -static Visual * findArgbVisual(Display *dpy, int scr) { - XVisualInfo *xvi; - XVisualInfo template; - int nvi; - int i; - XRenderPictFormat *format; - Visual *visual; - - template.screen = scr; - template.depth = 32; - template.class = TrueColor; - - xvi = XGetVisualInfo (dpy, - VisualScreenMask | - VisualDepthMask | - VisualClassMask, - &template, - &nvi); - - if (!xvi) - return 0; - - visual = 0; - for (i = 0; i < nvi; i++) { - format = XRenderFindVisualFormat (dpy, xvi[i].visual); - if (format->type == PictTypeDirect && format->direct.alphaMask) { - visual = xvi[i].visual; - break; - } - } - - XFree (xvi); - return visual; -} - -static Window find_desktop_window(Display *display, int screen, - Window *root, Window *p_desktop) { - int i; - unsigned int n; - Window win = *root; - Window troot, parent, *children; - char *name; - int status; - int width = DisplayWidth(display, screen); - int height = DisplayHeight(display, screen); - XWindowAttributes attrs; - - XQueryTree(display, *root, &troot, &parent, &children, &n); - for (i = 0; i < (int) n; i++) { - status = XFetchName(display, children[i], &name); - status |= XGetWindowAttributes(display, children[i], &attrs); - - if ((status != 0) && (NULL != name)) { - if( (attrs.map_state != 0) && (attrs.width == width) && - (attrs.height == height) && (!strcmp(name, desktop_window_name)) ) { - win = children[i]; - XFree(children); - XFree(name); - *p_desktop = win; - return win; - } - - if(name) - XFree(name); - } - } - - DEBUG_MSG("Desktop Window Not found\n"); - return 0; -} - -static void usage (void) { - fprintf(stderr, "%s v%s- Modified by Shantanu Goel. Visit http://tech.shantanugoel.com for updates, queries and feature requests\n", NAME, VERSION); - fprintf (stderr, "\nUsage: %s [-g {w}x{h}+{x}+{y}] [-ni] [-argb] [-fs] [-s] [-st] [-sp] [-a] " - "[-b] [-nf] [-o OPACITY] [-sh SHAPE] [-ov]-- COMMAND ARG1...\n", NAME); - fprintf (stderr, "Options:\n \ - -g - Specify Geometry (w=width, h=height, x=x-coord, y=y-coord. ex: -g 640x480+100+100)\n \ - -ni - Ignore Input\n \ - -d - Desktop Window Hack. Provide name of the \"Desktop\" window as parameter \ - -argb - RGB\n \ - -fs - Full Screen\n \ - -s - Sticky\n \ - -st - Skip Taskbar\n \ - -sp - Skip Pager\n \ - -a - Above\n \ - -b - Below\n \ - -nf - No Focus\n \ - -o - Opacity value between 0 to 1 (ex: -o 0.20)\n \ - -sh - Shape of window (choose between rectangle, circle or triangle. Default is rectangle)\n \ - -ov - Set override_redirect flag (For seamless desktop background integration in non-fullscreenmode)\n \ - -debug - Enable debug messages\n"); -} - -static void sigHandler (int sig) { kill(pid, sig); } - -int main (int argc, char **argv) { - Display *dpy; - Window win; - Window root; - Window p_desktop = 0; - int screen; - XSizeHints xsh; - XWMHints xwmh; - char widArg[256]; - char *widArgv[] = { widArg }; - char *endArg = NULL; - int i; - int status = 0; - unsigned int opacity = OPAQUE; - int x = 0; - int y = 0; - unsigned int width = WIDTH; - unsigned int height = HEIGHT; - int argb = 0; - int fullscreen = 0; - int noInput = 0; - int noFocus = 0; - Atom state[256]; - int nState = 0; - int override = 0; - win_shape shape = SHAPE_RECT; - Pixmap mask; - GC mask_gc; - XGCValues xgcv; - - - dpy = XOpenDisplay (NULL); - if (!dpy) { - fprintf (stderr, "%s: Error: couldn't open display\n", argv[0]); - return 1; - } - - screen = DefaultScreen (dpy); - root = RootWindow (dpy, screen); - strcpy(desktop_window_name, DEFAULT_DESKTOP_WINDOW_NAME); - - for (i = 1; i < argc; i++) { - if (strcmp(argv[i], "-g") == 0) { - if (++i < argc) - XParseGeometry (argv[i], &x, &y, &width, &height); - } else if (strcmp(argv[i], "-ni") == 0) { - noInput = 1; - } else if (strcmp(argv[i], "-d") == 0) { - ++i; - strcpy(desktop_window_name, argv[i]); - } else if (strcmp(argv[i], "-argb") == 0) { - argb = 1; - } else if (strcmp(argv[i], "-fs") == 0) { - state[nState++] = XInternAtom (dpy, "_NET_WM_STATE_FULLSCREEN", 0); - fullscreen = 1; - } else if (strcmp(argv[i], "-s") == 0) { - state[nState++] = XInternAtom (dpy, "_NET_WM_STATE_STICKY", 0); - } else if (strcmp(argv[i], "-st") == 0) { - state[nState++] = XInternAtom (dpy, "_NET_WM_STATE_SKIP_TASKBAR", 0); - } else if (strcmp(argv[i], "-sp") == 0) { - state[nState++] = XInternAtom (dpy, "_NET_WM_STATE_SKIP_PAGER", 0); - } else if (strcmp(argv[i], "-a") == 0) { - state[nState++] = XInternAtom (dpy, "_NET_WM_STATE_ABOVE", 0); - } else if (strcmp(argv[i], "-b") == 0) { - state[nState++] = XInternAtom (dpy, "_NET_WM_STATE_BELOW", 0); - } else if (strcmp(argv[i], "-nf") == 0) { - noFocus = 1; - } else if (strcmp(argv[i], "-o") == 0) { - if (++i < argc) - opacity = (unsigned int) (atof (argv[i]) * OPAQUE); - } else if (strcmp(argv[i], "-sh") == 0) { - if (++i < argc) { - if(strcasecmp(argv[i], "circle") == 0) { - shape = SHAPE_CIRCLE; - } else if(strcasecmp(argv[i], "triangle") == 0) { - shape = SHAPE_TRIG; - } - } - } else if (strcmp(argv[i], "-ov") == 0) { - override = 1; - } else if (strcmp(argv[i], "-debug") == 0) { - debug = 1; - } else if (strcmp(argv[i], "--") == 0) { - break; - } else { - usage (); - return 1; - } - } - - for (i = i + 1; i < argc; i++) { - if (strcmp(argv[i], "WID") == 0) - addArguments (widArgv, 1); - else - addArguments (&argv[i], 1); - } - - if (!nChildArgv) { - fprintf (stderr, "%s: Error: couldn't create command line\n", argv[0]); - usage (); - return 1; - } - - addArguments (&endArg, 1); - - if (fullscreen) { - xsh.flags = PSize | PPosition; - xsh.width = DisplayWidth (dpy, screen); - xsh.height = DisplayHeight (dpy, screen); - } else { - xsh.flags = PSize; - xsh.width = width; - xsh.height = height; - } - - xwmh.flags = InputHint; - xwmh.input = !noFocus; - - if (argb) { - XSetWindowAttributes attr; - Visual *visual; - - visual = findArgbVisual (dpy, screen); - if (!visual) { - fprintf (stderr, "%s: Error: couldn't find argb visual\n", argv[0]); - return 1; - } - - attr.background_pixel = 0; - attr.border_pixel = 0; - attr.colormap = XCreateColormap (dpy, root, visual, AllocNone); - - win = XCreateWindow (dpy, root, 0, 0, xsh.width, xsh.height, 0, 32, - InputOutput, visual, - CWBackPixel | CWBorderPixel | CWColormap, &attr); - } else { - XSetWindowAttributes attr; - attr.override_redirect = override; - - if( override && find_desktop_window(dpy, screen, &root, &p_desktop) ) { - win = XCreateWindow (dpy, p_desktop, x, y, xsh.width, xsh.height, 0, - CopyFromParent, InputOutput, CopyFromParent, - CWOverrideRedirect, &attr); - } else { - win = XCreateWindow (dpy, root, x, y, xsh.width, xsh.height, 0, - CopyFromParent, InputOutput, CopyFromParent, - CWOverrideRedirect, &attr); - } - } - - XSetWMProperties (dpy, win, NULL, NULL, argv, argc, &xsh, &xwmh, NULL); - - if (opacity != OPAQUE) - setWindowOpacity (dpy, win, opacity); - - if (noInput) { - Region region; - - region = XCreateRegion (); - if (region) { - XShapeCombineRegion (dpy, win, ShapeInput, 0, 0, region, ShapeSet); - XDestroyRegion (region); - } - } - - if (nState) - XChangeProperty (dpy, win, XInternAtom (dpy, "_NET_WM_STATE", 0), - XA_ATOM, 32, PropModeReplace, (unsigned char *) state, nState); - - if (shape) { - mask = XCreatePixmap(dpy, win, width, height, 1); - mask_gc = XCreateGC(dpy, mask, 0, &xgcv); - - switch(shape) { - //Nothing special to be done if it's a rectangle - case SHAPE_CIRCLE: - /* fill mask */ - XSetForeground(dpy, mask_gc, 0); - XFillRectangle(dpy, mask, mask_gc, 0, 0, width, height); - - XSetForeground(dpy, mask_gc, 1); - XFillArc(dpy, mask, mask_gc, 0, 0, width, height, 0, 23040); - break; - - case SHAPE_TRIG: - { - XPoint points[3] = { {0, height}, - {width/2, 0}, - {width, height} }; - - XSetForeground(dpy, mask_gc, 0); - XFillRectangle(dpy, mask, mask_gc, 0, 0, width, height); - - XSetForeground(dpy, mask_gc, 1); - XFillPolygon(dpy, mask, mask_gc, points, 3, Complex, CoordModeOrigin); - } - break; - default: - break; - } - /* combine */ - XShapeCombineMask(dpy, win, ShapeBounding, 0, 0, mask, ShapeSet); - } - - XMapWindow (dpy, win); - - if(p_desktop == 0) - XLowerWindow(dpy, win); - - XSync (dpy, win); - sprintf (widArg, "0x%x", (int) win); - pid = fork (); - - switch (pid) { - case -1: - perror ("fork"); - return 1; - case 0: - execvp (childArgv[0], childArgv); - perror (childArgv[0]); - exit (2); - break; - default: - break; - } - - signal (SIGTERM, sigHandler); - signal (SIGINT, sigHandler); - - for (;;) { - if (waitpid (pid, &status, 0) != -1) { - if (WIFEXITED (status)) - fprintf (stderr, "%s died, exit status %d\n", childArgv[0], - WEXITSTATUS (status)); - break; - } - } - - XDestroyWindow (dpy, win); - XCloseDisplay (dpy); - return 0; -} diff --git a/src/versions/0.0.1/compileBin.sh b/src/versions/0.0.1/compileBin.sh deleted file mode 100755 index fdd8222..0000000 --- a/src/versions/0.0.1/compileBin.sh +++ /dev/null @@ -1,6 +0,0 @@ -#!/bin/bash - -function main() { - gcc -no-pie -s gwinwrap_exec_bin.cpp -o gwinwrap -} -main; diff --git a/src/versions/0.0.1/gwinwrap_exec_bin.cpp b/src/versions/0.0.1/gwinwrap_exec_bin.cpp deleted file mode 100644 index 81978ec..0000000 --- a/src/versions/0.0.1/gwinwrap_exec_bin.cpp +++ /dev/null @@ -1,10 +0,0 @@ -#include -#include -#include -using namespace std; - -int main() { - chdir("/opt/GWinWrap/"); - system("python3 ."); -return 0; -} diff --git a/src/versions/0.0.2/GWinWrap/__builtins__.py b/src/versions/0.0.2/GWinWrap/__builtins__.py index 287a5fb..e0cffce 100644 --- a/src/versions/0.0.2/GWinWrap/__builtins__.py +++ b/src/versions/0.0.2/GWinWrap/__builtins__.py @@ -1,73 +1,42 @@ -import builtins - # Python imports import builtins +import threading # Lib imports # Application imports -from signal_classes import IPCServerMixin +from utils.event_system import EventSystem +from utils.endpoint_registry import EndpointRegistry +from utils.keybindings import Keybindings +from utils.settings import Settings -class Builtins(IPCServerMixin): - """Docstring for __builtins__ extender""" - def __init__(self): - # NOTE: The format used is list of [type, target, data] - # Where data may be any kind of data - self._gui_events = [] - self._fm_events = [] - self.is_ipc_alive = False - self.ipc_authkey = b'GWinWrap-ipc' - self.ipc_address = '127.0.0.1' - self.ipc_port = 8888 - self.ipc_timeout = 15.0 +# NOTE: Threads WILL NOT die with parent's destruction. +def threaded_wrapper(fn): + def wrapper(*args, **kwargs): + threading.Thread(target=fn, args=args, kwargs=kwargs, daemon=False).start() + return wrapper - # Makeshift fake "events" type system FIFO - def _pop_gui_event(self): - if len(self._gui_events) > 0: - return self._gui_events.pop(0) - return None +# NOTE: Threads WILL die with parent's destruction. +def daemon_threaded_wrapper(fn): + def wrapper(*args, **kwargs): + threading.Thread(target=fn, args=args, kwargs=kwargs, daemon=True).start() + return wrapper - def _pop_fm_event(self): - if len(self._fm_events) > 0: - return self._fm_events.pop(0) - return None - - - def push_gui_event(self, event): - if len(event) == 3: - self._gui_events.append(event) - return None - - raise Exception("Invald event format! Please do: [type, target, data]") - - def push_fm_event(self, event): - if len(event) == 3: - self._fm_events.append(event) - return None - - raise Exception("Invald event format! Please do: [type, target, data]") - - def read_gui_event(self): - return self._gui_events[0] - - def read_fm_event(self): - return self._fm_events[0] - - def consume_gui_event(self): - return self._pop_gui_event() - - def consume_fm_event(self): - return self._pop_fm_event() # NOTE: Just reminding myself we can add to builtins two different ways... # __builtins__.update({"event_system": Builtins()}) builtins.app_name = "GWinWrap" -builtins.event_system = Builtins() -builtins.event_sleep_time = 0.2 -builtins.debug = False -builtins.trace_debug = False +builtins.keybindings = Keybindings() +builtins.event_system = EventSystem() +builtins.endpoint_registry = EndpointRegistry() +builtins.settings = Settings() +builtins.logger = settings.get_logger() + +builtins.threaded = threaded_wrapper +builtins.daemon_threaded = daemon_threaded_wrapper +builtins.event_sleep_time = 0.05 diff --git a/src/versions/0.0.2/GWinWrap/__init__.py b/src/versions/0.0.2/GWinWrap/__init__.py index 56356ba..90dc8da 100644 --- a/src/versions/0.0.2/GWinWrap/__init__.py +++ b/src/versions/0.0.2/GWinWrap/__init__.py @@ -1,50 +1,3 @@ -# Python imports -import os, inspect, time - -# Lib imports - -# Application imports -from utils import Settings -from signal_classes import Controller -from __builtins__ import Builtins - - - - -class Main(Builtins): - def __init__(self, args, unknownargs): - if not debug: - event_system.create_ipc_server() - - time.sleep(0.2) - if not trace_debug: - if not event_system.is_ipc_alive: - if unknownargs: - for arg in unknownargs: - if os.path.isdir(arg): - message = f"FILE|{arg}" - event_system.send_ipc_message(message) - - raise Exception("IPC Server Exists: Will send data to it and close...") - - - settings = Settings() - settings.create_window() - - controller = Controller(settings, args, unknownargs) - if not controller: - raise Exception("Controller exited and doesn't exist...") - - # Gets the methods from the classes and sets to handler. - # Then, builder from settings will connect to any signals it needs. - classes = [controller] - handlers = {} - for c in classes: - methods = None - try: - methods = inspect.getmembers(c, predicate=inspect.ismethod) - handlers.update(methods) - except Exception as e: - print(repr(e)) - - settings.get_builder().connect_signals(handlers) +""" + Start of package. +""" diff --git a/src/versions/0.0.2/GWinWrap/__main__.py b/src/versions/0.0.2/GWinWrap/__main__.py index dc06b1a..abdc793 100644 --- a/src/versions/0.0.2/GWinWrap/__main__.py +++ b/src/versions/0.0.2/GWinWrap/__main__.py @@ -1,38 +1,50 @@ #!/usr/bin/python3 - # Python imports -import argparse, faulthandler, traceback +import argparse +import faulthandler +import traceback from setproctitle import setproctitle import tracemalloc tracemalloc.start() - # Lib imports import gi gi.require_version('Gtk', '3.0') from gi.repository import Gtk # Application imports -from __init__ import Main +from __builtins__ import * +from app import Application + + if __name__ == "__main__": - try: - # import web_pdb - # web_pdb.set_trace() + ''' Set process title, get arguments, and create GTK main thread. ''' - setproctitle('GWinWrap') + try: + setproctitle(f'{app_name}') faulthandler.enable() # For better debug info + parser = argparse.ArgumentParser() # Add long and short arguments + parser.add_argument("--debug", "-d", default="false", help="Do extra console messaging.") + parser.add_argument("--trace-debug", "-td", default="false", help="Disable saves, ignore IPC lock, do extra console messaging.") parser.add_argument("--file", "-f", default="default", help="JUST SOME FILE ARG.") # Read arguments (If any...) args, unknownargs = parser.parse_known_args() - Main(args, unknownargs) + if args.debug == "true": + settings.set_debug(True) + + if args.trace_debug == "true": + settings.set_trace_debug(True) + + settings.do_dirty_start_check() + Application(args, unknownargs) Gtk.main() except Exception as e: traceback.print_exc() diff --git a/src/versions/0.0.2/GWinWrap/app.py b/src/versions/0.0.2/GWinWrap/app.py new file mode 100644 index 0000000..6880502 --- /dev/null +++ b/src/versions/0.0.2/GWinWrap/app.py @@ -0,0 +1,40 @@ +# Python imports +import os +import time + +# Lib imports + +# Application imports +from utils.ipc_server import IPCServer +from core.window import Window + + + + +class AppLaunchException(Exception): + ... + +class ControllerStartExceptiom(Exception): + ... + + +class Application(IPCServer): + ''' Create Settings and Controller classes. Bind signal to Builder. Inherit from Builtins to bind global methods and classes.''' + + def __init__(self, args, unknownargs): + super(Application, self).__init__() + if not settings.is_trace_debug(): + try: + self.create_ipc_listener() + except Exception: + ... + + if not self.is_ipc_alive: + for arg in unknownargs + [args.new_tab,]: + if os.path.isdir(arg): + message = f"FILE|{arg}" + self.send_ipc_message(message) + + raise AppLaunchException(f"{app_name} IPC Server Exists: Will send path(s) to it and close...") + + Window(args, unknownargs) diff --git a/src/versions/0.0.2/GWinWrap/core/__init__.py b/src/versions/0.0.2/GWinWrap/core/__init__.py new file mode 100644 index 0000000..90cfadc --- /dev/null +++ b/src/versions/0.0.2/GWinWrap/core/__init__.py @@ -0,0 +1,3 @@ +""" + Gtk Bound Signal Module +""" diff --git a/src/versions/0.0.2/GWinWrap/core/controller.py b/src/versions/0.0.2/GWinWrap/core/controller.py new file mode 100644 index 0000000..d80b76a --- /dev/null +++ b/src/versions/0.0.2/GWinWrap/core/controller.py @@ -0,0 +1,123 @@ +# Python imports +import os + +# Lib imports +import gi +gi.require_version('Gtk', '3.0') +gi.require_version('Gdk', '3.0') +from gi.repository import Gtk +from gi.repository import GLib +from gi.repository import Gdk + +# Application imports +from .mixins import * +from .controller_data import Controller_Data + + + +class Controller(ThumbnailMixin, ImageViewerMixin, DrawAreaMixin, GridMixin, Controller_Data): + def __init__(self, args, unknownargs, _window): + self.window = _window + + self._setup_styling() + self._setup_signals() + self._subscribe_to_events() + self._load_glade_file() + + self.setup_controller_data() + self.retrieve_settings() + + + def _setup_styling(self): + ... + + def _setup_signals(self): + ... + + def _subscribe_to_events(self): + event_system.subscribe("handle_file_from_ipc", self.handle_file_from_ipc) + + def handle_file_from_ipc(self, path: str) -> None: + print(f"Path From IPC: {path}") + + def _load_glade_file(self): + self.builder = Gtk.Builder() + self.builder.add_from_file(settings.get_glade_file()) + settings.set_builder(self.builder) + self.core_widget = self.builder.get_object("core_widget") + + settings.register_signals_to_builder([self, self.core_widget]) + + def get_core_widget(self): + return self.core_widget + + def tear_down(self, widget=None, eve=None): + if self.demo_area_pid: + self.close_demo_popup() + + self.close_image_popup() + + def close_program(self, widget, data=None): + event_system.emit("close_gwinwrap") + + + def apply_settings(self, widget, data=None): + os.system("killall xwinwrap &") + user_home = settings.get_home_path() + + if self.apply_type == 1: + files = os.listdir(user_home) + for file in files: + fPath = f"{user_home}/{file}" + if os.path.isfile(fPath) and "animatedBGstarter" in file: + os.system(f"bash -c '~/{file}' &") + else: + os.system("nitrogen --restore &") + + self.help_label.set_markup(self.appliedLabel) + + + def toggle_xscreen_list(self, widget=None, eve=None): + use_xscreensvr = self.builder.get_object("useXScrnList") + if use_xscreensvr.get_active(): + self.builder.get_object("xScreenSvrList").set_sensitive(True) + else: + self.builder.get_object("xScreenSvrList").set_sensitive(False) + + def show_settings_popup(self, widget): + self.builder.get_object("settingsWindow").popup() + + + def preview_xscreensaver(self, widget, eve): + if eve.type == Gdk.EventType.DOUBLE_BUTTON_PRESS: + demoXscrnSaver = self.xscreensavers + self.xscreen_value + xid = self.getXID() + command = [demoXscrnSaver, "-window-id", str(xid)] + self.run_demo_in_draw_area(command) + + def pass_xscreen_value(self, widget): + row = widget.get_cursor() + path = Gtk.TreePath(row.path) + treeiter = self.xscreen_store.get_iter(path[0]) + self.xscreen_value = self.xscreen_store.get_value(treeiter, 0) + + def kill_xwinwrap(self, widget, data=None): + os.system("killall xwinwrap &") + self.help_label.set_markup(self.stoppedLabel) + + def set_selected_eve_box(self, eveBox): + if self.selected_eve_box: + color = Gdk.RGBA(0.0, 0.0, 0.0, 0.0) + self.selected_eve_box.override_background_color(Gtk.StateType.NORMAL, color) + + color = Gdk.RGBA(0.9, 0.7, 0.4, 0.74) + eveBox.override_background_color(Gtk.StateType.NORMAL, color) + self.selected_eve_box = eveBox + + def mouse_over(self, widget, eve, args): + hand_cursor = Gdk.Cursor(Gdk.CursorType.HAND2) + self.window.get_window().set_cursor(hand_cursor) + + def mouse_out(self, widget, eve, args): + watch_cursor = Gdk.Cursor(Gdk.CursorType.LEFT_PTR) + self.window.get_window().set_cursor(watch_cursor) diff --git a/src/versions/0.0.2/GWinWrap/core/controller_data.py b/src/versions/0.0.2/GWinWrap/core/controller_data.py new file mode 100644 index 0000000..c4f62b9 --- /dev/null +++ b/src/versions/0.0.2/GWinWrap/core/controller_data.py @@ -0,0 +1,120 @@ +# Python imports +from os import listdir +from os.path import isfile +from os.path import join + +# Lib imports +from gi.repository import GLib + +# Application imports +from .save_state_to_xwinwarp import SaveStateToXWinWarp + + + +class Controller_Data: + def has_method(self, obj, name): + return callable(getattr(obj, name, None)) + + def setup_controller_data(self): + self.state_saver = SaveStateToXWinWarp() + self.logger = settings.get_logger() + + self.home_path = settings.get_home_path() + self.success_color = settings.get_success_color() + self.warning_color = settings.get_warning_color() + self.error_color = settings.get_error_color() + self.vids_filter = settings.get_vids_filter() + self.imgs_filter = settings.get_images_filter() + + self.image_grid = self.builder.get_object("imageGrid") + self.grid_label = self.builder.get_object("gridLabel") + self.help_label = self.builder.get_object("helpLabel") + self.xscreen_store = self.builder.get_object("XScreensaverStore") + + self.defaultLabel = "Note: Double click an image to view the video or image." + self.savedLabel = f"Saved settings..." + self.appliedLabel = f"Running xwinwrap..." + self.stoppedLabel = f"Stopped xwinwrap..." + + # Add filter to allow only folders to be selected + dialog = self.builder.get_object("selectedDirDialog") + file_filter = self.builder.get_object("Folders") + dialog.add_filter(file_filter) + + self.xscreensavers = settings.get_xscreensavers() + list = [f for f in listdir(self.xscreensavers) if isfile(join(self.xscreensavers , f))] + list.sort() + for file in list: + self.xscreen_store.append((file,)) + + self.selected_eve_box = None + self.start_path = None + self.default_player = None + self.default_img_viewer = None + self.demo_area_pid = None + + self.apply_type = 1 # 1 is XWinWrap and 2 is Nitrogen + self.xscreen_value = None + self.to_be_background = None # Global file path and type for saving to file + + self.set_monitor_offset_data() + self.retrieve_settings() + + + def retrieve_settings(self): + self.start_path = settings.get_start_path() + self.default_player = settings.get_default_player() + self.default_img_viewer = settings.get_default_img_viewer() + + self.builder.get_object("customStartPath").set_text(self.start_path) + self.builder.get_object("customVideoPlayer").set_text(self.default_player) + self.builder.get_object("customImgViewer").set_text(self.default_img_viewer) + self.builder.get_object("selectedDirDialog").set_filename(self.start_path) + + if self.start_path: + self.load_path(None, self.start_path) + + def set_monitor_offset_data(self): + monitors = settings.get_monitor_data(self.window) + monitorOffsetData = self.builder.get_object("monitorOffsetData") + + for monitor in monitors: + if monitor.x >= 0 and monitor.y >= 0: + monitorOffsetData.append_text("+" + str(monitor.x) + "+" + str(monitor.y)) + elif monitor.x <= 0 and monitor.y <= 0: + monitorOffsetData.append_text(str(monitor.x) + str(monitor.y)) + elif monitor.x >= 0 and monitor.y <= 0: + monitorOffsetData.append_text("+" + str(monitor.x) + str(monitor.y)) + elif monitor.x <= 0 and monitor.y >= 0: + monitorOffsetData.append_text(str(monitor.x) + "+" + str(monitor.y)) + + monitorOffsetData.set_active(0) + + def save_to_settings_file(self, widget=None): + settings.save_settings() + + def update_start_path(self, widget=None, eve=None): + start_path = self.builder.get_object("customStartPath").get_text().strip() + settings.set_start_path(start_path) + + def update_default_player(self, widget=None, eve=None): + default_player = self.builder.get_object("customVideoPlayer").get_text().strip() + settings.set_default_player(default_player) + + def update_default_img_viewer(self, widget=None, eve=None): + default_img_viewer = self.builder.get_object("customImgViewer").get_text().strip() + settings.set_default_img_viewer(default_img_viewer) + + def save_to_file(self, widget=None, eve=None): + save_location = self.builder.get_object("saveLoc").get_active_text() + use_xscreensvr = self.builder.get_object("useXScrnList").get_active() + playBackRes = self.builder.get_object("playbackResolution") + monitorOffset = self.builder.get_object("monitorOffsetData") + resolution = playBackRes.get_active_text() + monitorOffset.get_active_text() + self.apply_type = self.state_saver.save_to_file(self.to_be_background, resolution, save_location, use_xscreensvr, self.xscreen_value, self.default_player) + + if self.apply_type == -1: + self.help_label.set_markup("Nothing saved...") + return + + self.help_label.set_markup(self.savedLabel) diff --git a/src/versions/0.0.2/GWinWrap/signal_classes/mixins/DrawAreaMixin.py b/src/versions/0.0.2/GWinWrap/core/mixins/DrawAreaMixin.py similarity index 93% rename from src/versions/0.0.2/GWinWrap/signal_classes/mixins/DrawAreaMixin.py rename to src/versions/0.0.2/GWinWrap/core/mixins/DrawAreaMixin.py index 833d3ae..4c3f290 100644 --- a/src/versions/0.0.2/GWinWrap/signal_classes/mixins/DrawAreaMixin.py +++ b/src/versions/0.0.2/GWinWrap/core/mixins/DrawAreaMixin.py @@ -1,7 +1,10 @@ # Python imports -import os, subprocess, signal, time +import os +import subprocess +import signal +import time -# Gtk imports +# Lib imports import gi gi.require_version('Gdk', '3.0') from gi.repository import Gdk @@ -9,11 +12,12 @@ from gi.repository import Gdk # Application imports + class DrawAreaMixin: """docstring for DrawAreaMixin""" def close_demo_popup(self, widget=None, data=None): - os.kill(self.demo_area_pid, signal.SIGTERM) #or signal.SIGKILL + os.kill(self.demo_area_pid, signal.SIGTERM) # or signal.SIGKILL self.demo_area_pid = None time.sleep(.200) self.builder.get_object("demoPreviewPopWindow").popdown() diff --git a/src/versions/0.0.2/GWinWrap/signal_classes/mixins/GridMixin.py b/src/versions/0.0.2/GWinWrap/core/mixins/GridMixin.py similarity index 72% rename from src/versions/0.0.2/GWinWrap/signal_classes/mixins/GridMixin.py rename to src/versions/0.0.2/GWinWrap/core/mixins/GridMixin.py index 513d7b1..a172c3f 100644 --- a/src/versions/0.0.2/GWinWrap/signal_classes/mixins/GridMixin.py +++ b/src/versions/0.0.2/GWinWrap/core/mixins/GridMixin.py @@ -1,26 +1,19 @@ # Python imports -import threading, hashlib +import hashlib from os import listdir -from os.path import isfile, join +from os.path import isfile +from os.path import join # Gtk imports import gi gi.require_version('Gtk', '3.0') -from gi.repository import Gtk, GLib +from gi.repository import Gtk +from gi.repository import GLib # Application imports - - -def threaded(fn): - def wrapper(*args, **kwargs): - threading.Thread(target=fn, args=args, kwargs=kwargs).start() - - return wrapper - - class GridMixin: """docstring for GridMixin.""" @@ -36,8 +29,8 @@ class GridMixin: col = 0 for file in list: - if file.lower().endswith(self.settings.get_vids_filter() + \ - self.settings.get_images_filter()): + if file.lower().endswith(settings.get_vids_filter() + \ + settings.get_images_filter()): files.append(file) # fractionTick = 1.0 / 1.0 if len(files) == 0 else len(files) @@ -46,7 +39,7 @@ class GridMixin: self.image_grid.remove_column(0) # self.loadProgress.set_text("Loading...") # self.loadProgress.set_fraction(0.0) - self.help_label.set_markup(f"{path.strip(self.settings.get_home_path())}") + self.help_label.set_markup(f"{path.strip(settings.get_home_path())}") for file in files: self.porocess_file(path, file, col, row) @@ -59,13 +52,13 @@ class GridMixin: @threaded def porocess_file(self, path, file, col, row): - fPath = f"{path}/{file}" - eveBox = Gtk.EventBox() - thumbnl = Gtk.Image() + fPath = f"{path}/{file}" + eveBox = Gtk.EventBox() + thumbnl = Gtk.Image() - if file.lower().endswith(self.settings.get_vids_filter()): - fileHash = hashlib.sha256(str.encode(fPath)).hexdigest() - hashImgPath = f"{self.settings.get_home_path()}/.thumbnails/normal/{fileHash}.png" + if file.lower().endswith(self.vids_filter): + fileHash = self.fast_hash(str.encode(fPath)) + hashImgPath = f"{settings.get_home_path()}/.thumbnails/normal/{fileHash}.png" if isfile(hashImgPath) == False: self.generate_thumbnail(fPath, hashImgPath) @@ -73,7 +66,7 @@ class GridMixin: eveBox.connect("button_press_event", self.run_mplayer_process, (fPath, file, eveBox,)) eveBox.connect("enter_notify_event", self.mouse_over, ()) eveBox.connect("leave_notify_event", self.mouse_out, ()) - elif file.lower().endswith(self.settings.get_images_filter()): + elif file.lower().endswith(self.imgs_filter): thumbnl = self.create_gtk_image(fPath, [310, 310]) eveBox.connect("button_press_event", self.run_image_viewer_process, (fPath, file, eveBox,)) eveBox.connect("enter_notify_event", self.mouse_over, ()) @@ -82,7 +75,7 @@ class GridMixin: print("Not a video or image file.") return - GLib.idle_add(self.pre_grid_setup, (eveBox, thumbnl, )) + self.pre_grid_setup((eveBox, thumbnl,)) GLib.idle_add(self.add_to_grid, (self.image_grid, eveBox, col, row,)) # tickCount = tickCount + fractionTick # self.loadProgress.set_fraction(tickCount) @@ -114,3 +107,19 @@ class GridMixin: self.xscreen_value = None self.to_be_background = None self.apply_type = 1 + + def fast_hash(self, filename, hash_factory=hashlib.md5, chunk_num_blocks=128, i=1): + h = hash_factory() + with open(filename,'rb') as f: + f.seek(0, 2) + mid = int(f.tell() / 2) + f.seek(mid, 0) + + while chunk := f.read(chunk_num_blocks*h.block_size): + h.update(chunk) + if (i == 12): + break + + i += 1 + + return h.hexdigest() diff --git a/src/versions/0.0.2/GWinWrap/signal_classes/mixins/ImageViewerMixin.py b/src/versions/0.0.2/GWinWrap/core/mixins/ImageViewerMixin.py similarity index 94% rename from src/versions/0.0.2/GWinWrap/signal_classes/mixins/ImageViewerMixin.py rename to src/versions/0.0.2/GWinWrap/core/mixins/ImageViewerMixin.py index e4dd1b6..8e7aa08 100644 --- a/src/versions/0.0.2/GWinWrap/signal_classes/mixins/ImageViewerMixin.py +++ b/src/versions/0.0.2/GWinWrap/core/mixins/ImageViewerMixin.py @@ -1,7 +1,7 @@ # Python imports import subprocess -# Gtk imports +# Lib imports import gi gi.require_version('Gdk', '3.0') from gi.repository import Gdk @@ -20,7 +20,7 @@ class ImageViewerMixin: def run_image_viewer_process(self, widget, eve, params): image, file, eveBox = params - self.set_selected(eveBox) + self.set_selected_eve_box(eveBox) if eve.type == Gdk.EventType.DOUBLE_BUTTON_PRESS: previewWindow = self.builder.get_object("previewWindow") diff --git a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/mixins/ThumbnailMixin.py b/src/versions/0.0.2/GWinWrap/core/mixins/ThumbnailMixin.py similarity index 99% rename from src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/mixins/ThumbnailMixin.py rename to src/versions/0.0.2/GWinWrap/core/mixins/ThumbnailMixin.py index e067732..2560e2c 100644 --- a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/mixins/ThumbnailMixin.py +++ b/src/versions/0.0.2/GWinWrap/core/mixins/ThumbnailMixin.py @@ -1,7 +1,7 @@ # Python imports import subprocess -# Gtk imports +# Lib imports import gi gi.require_version('Gtk', '3.0') from gi.repository import Gtk @@ -10,6 +10,7 @@ from gi.repository import GdkPixbuf # Application imports + class ThumbnailMixin: """docstring for ThumbnailMixin""" diff --git a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/mixins/__init__.py b/src/versions/0.0.2/GWinWrap/core/mixins/__init__.py similarity index 86% rename from src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/mixins/__init__.py rename to src/versions/0.0.2/GWinWrap/core/mixins/__init__.py index f482286..8509626 100644 --- a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/mixins/__init__.py +++ b/src/versions/0.0.2/GWinWrap/core/mixins/__init__.py @@ -1,3 +1,6 @@ +""" + Mixins Module +""" from .ThumbnailMixin import ThumbnailMixin from .DrawAreaMixin import DrawAreaMixin from .ImageViewerMixin import ImageViewerMixin diff --git a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/SaveStateToXWinWarp.py b/src/versions/0.0.2/GWinWrap/core/save_state_to_xwinwarp.py similarity index 73% rename from src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/SaveStateToXWinWarp.py rename to src/versions/0.0.2/GWinWrap/core/save_state_to_xwinwarp.py index 14ff763..e0e9d23 100644 --- a/src/debs/gwinwrap-0-0-2-x64/opt/GWinWrap/signal_classes/SaveStateToXWinWarp.py +++ b/src/versions/0.0.2/GWinWrap/core/save_state_to_xwinwarp.py @@ -1,13 +1,21 @@ +# Python imports +import os +import subprocess + +# Lib imports + +# Application imports + + class SaveStateToXWinWarp: - def __init__(self, _settings): - self.settings = _settings - self.user_home = self.settings.get_home_path() + def __init__(self): + self.user_home = settings.get_home_path() self._file_writer = None self._to_be_background = None self._use_xscreensvr = None - self._xscreen_value = None + self._xscreen_value = None self._save_file_target = None self._resolution = None self._player = None @@ -24,7 +32,7 @@ class SaveStateToXWinWarp: # Saves to file with selected and needed settings if to_be_background: - if to_be_background.lower().endswith(self.settings.get_images_filter()): + if to_be_background.lower().endswith(settings.get_images_filter()): self._save_file_target = f"{self.user_home}/.config/nitrogen/bg-saved.cfg" else: self._save_file_target = f"{self.user_home}/{save_location}" @@ -48,15 +56,21 @@ class SaveStateToXWinWarp: # GIF elif self._to_be_background.lower().endswith(('.gif')): output = f"xwinwrap -ov -g {self._resolution} -st -sp -b -nf -s -ni -- gifview -a -w WID {self._to_be_background}"; - # Standard images using nitrogen + # Standard images using nitrogen elif self._to_be_background.lower().endswith(('.png', 'jpg', '.jpeg')): output = f"[xin_0] \nfile={self._to_be_background}\nmode=0 \nbgcolor=#000000\n\n[xin_1] \nfile={self._to_be_background}\nmode=0 \nbgcolor=#000000"; applyType = 2; # VIDEO else: output = f"xwinwrap -ov -g {self._resolution} -st -sp -b -nf -s -ni -- {self._player} -wid WID -really-quiet -ao null -loop 0 '{self._to_be_background}'"; - pass + self.write_to_launch_file(output) + self.set_as_executable() + + return applyType; + + + def write_to_launch_file(self, output): try: if self._file_writer: self._file_writer.write(output) @@ -65,4 +79,12 @@ class SaveStateToXWinWarp: print(":: Write failed! ::") print(e) - return applyType; + def set_as_executable(self): + os.access(self._save_file_target, os.X_OK) + try: + command = ["chmod", "764", self._save_file_target] + with subprocess.Popen(command, stdout=subprocess.PIPE) as proc: + result = proc.stdout.read().decode("UTF-8").strip() + except Exception as e: + print(f"Couldn't chmod\nFile: {properties.file_uri}") + print( repr(e) ) diff --git a/src/versions/0.0.2/GWinWrap/core/window.py b/src/versions/0.0.2/GWinWrap/core/window.py new file mode 100644 index 0000000..b372a74 --- /dev/null +++ b/src/versions/0.0.2/GWinWrap/core/window.py @@ -0,0 +1,83 @@ +# Python imports +import time +import signal + +# Lib imports +import gi +import cairo +gi.require_version('Gtk', '3.0') +gi.require_version('Gdk', '3.0') +from gi.repository import Gtk +from gi.repository import Gdk +from gi.repository import GLib + +# Application imports +from core.controller import Controller + + + + +class Window(Gtk.ApplicationWindow): + """docstring for Window.""" + + def __init__(self, args, unknownargs): + super(Window, self).__init__() + + self.controller = None + + self._set_window_data() + self._setup_styling() + self._setup_signals() + self._subscribe_to_events() + self._load_widgets(args, unknownargs) + + self.show_all() + + + def _setup_styling(self): + self.set_default_size(950, 600) + self.set_title(f"{app_name}") + self.set_icon_from_file( settings.get_window_icon() ) + self.set_gravity(5) # 5 = CENTER + self.set_position(1) # 1 = CENTER, 4 = CENTER_ALWAYS + + def _setup_signals(self): + self.connect("delete-event", self._tear_down) + GLib.unix_signal_add(GLib.PRIORITY_DEFAULT, signal.SIGINT, self._tear_down) + + def _subscribe_to_events(self): + event_system.subscribe("close_gwinwrap", self._tear_down) + + def _load_widgets(self, args, unknownargs): + self.controller = Controller(args, unknownargs, self) + self.add( self.controller.get_core_widget() ) + + def _set_window_data(self) -> None: + screen = self.get_screen() + visual = screen.get_rgba_visual() + + if visual != None and screen.is_composited(): + self.set_visual(visual) + self.set_app_paintable(True) + self.connect("draw", self._area_draw) + + # bind css file + cssProvider = Gtk.CssProvider() + cssProvider.load_from_path( settings.get_css_file() ) + screen = Gdk.Screen.get_default() + styleContext = Gtk.StyleContext() + styleContext.add_provider_for_screen(screen, cssProvider, Gtk.STYLE_PROVIDER_PRIORITY_USER) + + def _area_draw(self, widget: Gtk.ApplicationWindow, cr: cairo.Context) -> None: + cr.set_source_rgba(0, 0, 0, 0.54) + cr.set_operator(cairo.OPERATOR_SOURCE) + cr.paint() + cr.set_operator(cairo.OPERATOR_OVER) + + + def _tear_down(self, widget=None, eve=None): + self.controller.tear_down() + + settings.clear_pid() + time.sleep(event_sleep_time) + Gtk.main_quit() diff --git a/src/versions/0.0.2/GWinWrap/signal_classes/Controller.py b/src/versions/0.0.2/GWinWrap/signal_classes/Controller.py deleted file mode 100644 index adcb743..0000000 --- a/src/versions/0.0.2/GWinWrap/signal_classes/Controller.py +++ /dev/null @@ -1,151 +0,0 @@ -# Python imports -import threading, signal, subprocess, inspect, os, time - -# Gtk imports -import gi -gi.require_version('Gtk', '3.0') -gi.require_version('Gdk', '3.0') -from gi.repository import Gtk, GLib, Gdk - -# Application imports -from .mixins import * -from . import Controller_Data - - -def threaded(fn): - def wrapper(*args, **kwargs): - threading.Thread(target=fn, args=args, kwargs=kwargs).start() - - return wrapper - - -class Controller(ThumbnailMixin, ImageViewerMixin, DrawAreaMixin, GridMixin, Controller_Data): - def __init__(self, _settings, args, unknownargs): - self.setup_controller_data(_settings) - self.window.show() - self.retrieve_settings() - - - def tear_down(self, widget=None, eve=None): - event_system.send_ipc_message("close server") - if self.demo_area_pid: - self.close_demo_popup() - - self.close_image_popup() - time.sleep(event_sleep_time) - Gtk.main_quit() - - def close_program(self, widget, data=None): - self.tear_down() - - - @threaded - def gui_event_observer(self): - while True: - time.sleep(event_sleep_time) - event = event_system.consume_gui_event() - if event: - try: - type, target, data = event - method = getattr(self.__class__, type) - GLib.idle_add(method, (self, data,)) - except Exception as e: - print(repr(e)) - - - - def apply_settings(self, widget, data=None): - os.system("killall xwinwrap &") - user_home = self.settings.get_home_path() - - if self.apply_type == 1: - files = os.listdir(user_home) - for file in files: - fPath = f"{user_home}/{file}" - if os.path.isfile(fPath) and "animatedBGstarter" in file: - os.system(f"bash -c '~/{file}' &") - elif self.apply_type == 2: - os.system("nitrogen --restore &") - else: - os.system("nitrogen --restore &") - - self.help_label.set_markup(self.appliedLabel) - - def save_to_settings_file(self, widget): - self.start_path = self.builder.get_object("customStartPath").get_text().strip() - self.default_player = self.builder.get_object("customVideoPlayer").get_text().strip() - self.default_img_viewer = self.builder.get_object("customImgViewer").get_text().strip() - - self.settings_saver.save_settings(self.start_path, self.default_player, self.default_img_viewer) - - def save_to_file(self, widget, data=None): - save_location = self.builder.get_object("saveLoc").get_active_text() - use_xscreensvr = self.builder.get_object("useXScrnList").get_active() - playBackRes = self.builder.get_object("playbackResolution") - monitorOffset = self.builder.get_object("monitorOffsetData") - resolution = playBackRes.get_active_text() + monitorOffset.get_active_text() - self.apply_type = self.state_saver.save_to_file(self.to_be_background, resolution, save_location, use_xscreensvr, self.xscreen_value, self.default_player) - - if self.apply_type == -1: - self.help_label.set_markup("Nothing saved...") - return - - self.help_label.set_markup(self.savedLabel) - - - def toggle_xscreen_list(self, widget, data=None): - use_xscreensvr = self.builder.get_object("useXScrnList") - if use_xscreensvr.get_active(): - self.builder.get_object("xScreenSvrList").set_sensitive(True) - else: - self.builder.get_object("xScreenSvrList").set_sensitive(False) - - def show_settings_popup(self, widget): - self.builder.get_object("settingsWindow").popup() - - - def preview_xscreensaver(self, widget, eve): - if eve.type == Gdk.EventType.DOUBLE_BUTTON_PRESS: - demoXscrnSaver = self.xscreensavers + self.xscreen_value - xid = self.getXID() - command = [demoXscrnSaver, "-window-id", str(xid)] - self.run_demo_in_draw_area(command) - - def pass_xscreen_value(self, widget): - row = widget.get_cursor() - path = Gtk.TreePath(row.path) - treeiter = self.xscreen_store.get_iter(path[0]) - self.xscreen_value = self.xscreen_store.get_value(treeiter, 0) - - def kill_xwinwrap(self, widget, data=None): - os.system("killall xwinwrap &") - self.help_label.set_markup(self.stoppedLabel) - - def set_selected_eve_box(self, eveBox): - if self.selected_eve_box: - color = Gdk.RGBA(0.0, 0.0, 0.0, 0.0) - self.selected_eve_box.override_background_color(Gtk.StateType.NORMAL, color) - - color = Gdk.RGBA(0.9, 0.7, 0.4, 0.74) - eveBox.override_background_color(Gtk.StateType.NORMAL, color) - self.selected_eve_box = eveBox - - def mouse_over(self, widget, eve, args): - hand_cursor = Gdk.Cursor(Gdk.CursorType.HAND2) - self.window.get_window().set_cursor(hand_cursor) - - def mouse_out(self, widget, eve, args): - watch_cursor = Gdk.Cursor(Gdk.CursorType.LEFT_PTR) - self.window.get_window().set_cursor(watch_cursor) - - def get_clipboard_data(self): - proc = subprocess.Popen(['xclip','-selection', 'clipboard', '-o'], stdout=subprocess.PIPE) - retcode = proc.wait() - data = proc.stdout.read() - return data.decode("utf-8").strip() - - def set_clipboard_data(self, data): - proc = subprocess.Popen(['xclip','-selection','clipboard'], stdin=subprocess.PIPE) - proc.stdin.write(data) - proc.stdin.close() - retcode = proc.wait() diff --git a/src/versions/0.0.2/GWinWrap/signal_classes/Controller_Data.py b/src/versions/0.0.2/GWinWrap/signal_classes/Controller_Data.py deleted file mode 100644 index e651a46..0000000 --- a/src/versions/0.0.2/GWinWrap/signal_classes/Controller_Data.py +++ /dev/null @@ -1,102 +0,0 @@ -# Python imports -import signal -from os import listdir -from os.path import isfile, join - -# Lib imports -from gi.repository import GLib - -# Application imports -from . import SaveStateToXWinWarp, SaveGWinWrapSettings - - - -class Controller_Data: - def has_method(self, obj, name): - return callable(getattr(obj, name, None)) - - def setup_controller_data(self, _settings): - self.settings = _settings - self.state_saver = SaveStateToXWinWarp(_settings) - self.settings_saver = SaveGWinWrapSettings(_settings) - - - self.builder = self.settings.get_builder() - self.window = self.settings.get_main_window() - self.logger = self.settings.get_logger() - - self.home_path = self.settings.get_home_path() - self.success_color = self.settings.get_success_color() - self.warning_color = self.settings.get_warning_color() - self.error_color = self.settings.get_error_color() - - - self.image_grid = self.builder.get_object("imageGrid") - self.grid_label = self.builder.get_object("gridLabel") - self.help_label = self.builder.get_object("helpLabel") - self.xscreen_store = self.builder.get_object("XScreensaverStore") - - self.defaultLabel = "Note: Double click an image to view the video or image." - self.savedLabel = f"Saved settings..." - self.appliedLabel = f"Running xwinwrap..." - self.stoppedLabel = f"Stopped xwinwrap..." - - # Add filter to allow only folders to be selected - dialog = self.builder.get_object("selectedDirDialog") - file_filter = self.builder.get_object("Folders") - dialog.add_filter(file_filter) - - self.xscreensavers = self.settings.get_xscreensavers() - list = [f for f in listdir(self.xscreensavers) if isfile(join(self.xscreensavers , f))] - list.sort() - for file in list: - self.xscreen_store.append((file,)) - - - self.selected_eve_box = None - self.start_path = None - self.default_player = None - self.default_img_viewer = None - self.demo_area_pid = None - - self.apply_type = 1 # 1 is XWinWrap and 2 is Nitrogen - self.xscreen_value = None - self.to_be_background = None # Global file path and type for saving to file - - - self.window.connect("delete-event", self.tear_down) - GLib.unix_signal_add(GLib.PRIORITY_DEFAULT, signal.SIGINT, self.tear_down) - - self.set_monitor_offset_data() - self.retrieve_settings() - - - def set_monitor_offset_data(self): - monitors = self.settings.get_monitor_data() - monitorOffsetData = self.builder.get_object("monitorOffsetData") - - for monitor in monitors: - if monitor.x >= 0 and monitor.y >= 0: - monitorOffsetData.append_text("+" + str(monitor.x) + "+" + str(monitor.y)) - elif monitor.x <= 0 and monitor.y <= 0: - monitorOffsetData.append_text(str(monitor.x) + str(monitor.y)) - elif monitor.x >= 0 and monitor.y <= 0: - monitorOffsetData.append_text("+" + str(monitor.x) + str(monitor.y)) - elif monitor.x <= 0 and monitor.y >= 0: - monitorOffsetData.append_text(str(monitor.x) + "+" + str(monitor.y)) - - monitorOffsetData.set_active(0) - - def retrieve_settings(self): - data = self.settings_saver.retrieve_settings() - self.start_path = data[0] - self.default_player = data[1] - self.default_img_viewer = data[2] - - self.builder.get_object("customStartPath").set_text(self.start_path) - self.builder.get_object("customVideoPlayer").set_text(self.default_player) - self.builder.get_object("customImgViewer").set_text(self.default_img_viewer) - self.builder.get_object("selectedDirDialog").set_filename(self.start_path) - - if self.start_path: - self.load_path(None, self.start_path) diff --git a/src/versions/0.0.2/GWinWrap/signal_classes/IPCServerMixin.py b/src/versions/0.0.2/GWinWrap/signal_classes/IPCServerMixin.py deleted file mode 100644 index be92ace..0000000 --- a/src/versions/0.0.2/GWinWrap/signal_classes/IPCServerMixin.py +++ /dev/null @@ -1,64 +0,0 @@ -# Python imports -import threading, socket, time -from multiprocessing.connection import Listener, Client - -# Lib imports - -# Application imports - - -def threaded(fn): - def wrapper(*args, **kwargs): - threading.Thread(target=fn, args=args, kwargs=kwargs, daemon=True).start() - return wrapper - - - - -class IPCServerMixin: - - @threaded - def create_ipc_server(self): - listener = Listener((self.ipc_address, self.ipc_port), authkey=self.ipc_authkey) - self.is_ipc_alive = True - while True: - conn = listener.accept() - start_time = time.time() - - print(f"New Connection: {listener.last_accepted}") - while True: - msg = conn.recv() - if debug: - print(msg) - - if "FILE|" in msg: - file = msg.split("FILE|")[1].strip() - if file: - event_system.push_gui_event(["create_tab_from_ipc", None, file]) - - conn.close() - break - - - if msg == 'close connection': - conn.close() - break - if msg == 'close server': - conn.close() - break - - # NOTE: Not perfect but insures we don't lockup the connection for too long. - end_time = time.time() - if (end - start) > self.ipc_timeout: - conn.close() - - listener.close() - - - def send_ipc_message(self, message="Empty Data..."): - try: - conn = Client((self.ipc_address, self.ipc_port), authkey=self.ipc_authkey) - conn.send(message) - conn.send('close connection') - except Exception as e: - print(repr(e)) diff --git a/src/versions/0.0.2/GWinWrap/signal_classes/SaveGWinWrapSettings.py b/src/versions/0.0.2/GWinWrap/signal_classes/SaveGWinWrapSettings.py deleted file mode 100644 index 38025a1..0000000 --- a/src/versions/0.0.2/GWinWrap/signal_classes/SaveGWinWrapSettings.py +++ /dev/null @@ -1,49 +0,0 @@ -#!/usr/bin/env python - -import os, json - -class SaveGWinWrapSettings: - def __init__(self, settings): - self.config_file = settings.get_config_file() - - if os.path.isfile(self.config_file) == False: - open(self.config_file, 'a').close() - - - def save_settings(self, start_path, default_player, default_img_viewer): - data = {} - data['settings'] = [] - - data['settings'].append({ - 'start_path': start_path, - 'default_player': default_player, - 'default_img_viewer': default_img_viewer - }) - - with open(self.config_file, 'w') as outfile: - json.dump(data, outfile, separators=(',', ':'), indent=4) - - - def retrieve_settings(self): - data = [] - - with open(self.config_file) as infile: - try: - _data = json.load(infile) - for obj in _data['settings']: - data = [obj['start_path'], obj['default_player'], obj['default_img_viewer']] - except Exception as e: - print(repr(e)) - data = ['', 'mplayer', 'xdg-open'] - - - if data[0] == '': - data[0] = '' - - if data[1] == '': - data[1] = 'mplayer' - - if data[2] == '': - data[2] = 'xdg-open' - - return data diff --git a/src/versions/0.0.2/GWinWrap/signal_classes/SaveStateToXWinWarp.py b/src/versions/0.0.2/GWinWrap/signal_classes/SaveStateToXWinWarp.py deleted file mode 100644 index 14ff763..0000000 --- a/src/versions/0.0.2/GWinWrap/signal_classes/SaveStateToXWinWarp.py +++ /dev/null @@ -1,68 +0,0 @@ - -class SaveStateToXWinWarp: - def __init__(self, _settings): - self.settings = _settings - self.user_home = self.settings.get_home_path() - - self._file_writer = None - self._to_be_background = None - self._use_xscreensvr = None - self._xscreen_value = None - self._save_file_target = None - self._resolution = None - self._player = None - - - def save_to_file(self, to_be_background, resolution, save_location, - use_xscreensvr, xscreen_value, player): - - self._to_be_background = to_be_background - self._use_xscreensvr = use_xscreensvr - self._xscreen_value = xscreen_value - self._resolution = resolution - self._player = player - - # Saves to file with selected and needed settings - if to_be_background: - if to_be_background.lower().endswith(self.settings.get_images_filter()): - self._save_file_target = f"{self.user_home}/.config/nitrogen/bg-saved.cfg" - else: - self._save_file_target = f"{self.user_home}/{save_location}" - elif use_xscreensvr and xscreen_value: - self._save_file_target = f"{self.user_home}/{save_location}" - else: - return -1 - - if self._save_file_target: - self._file_writer = open(self._save_file_target, "w") - - return self.save() - - def save(self): - applyType = 1 - output = None - - # XSCREENSAVER - if self._use_xscreensvr: - output = f"xwinwrap -ov -g {self._resolution} -st -sp -b -nf -s -ni -- /usr/lib/xscreensaver/{self._xscreen_value} -window-id WID -root"; - # GIF - elif self._to_be_background.lower().endswith(('.gif')): - output = f"xwinwrap -ov -g {self._resolution} -st -sp -b -nf -s -ni -- gifview -a -w WID {self._to_be_background}"; - # Standard images using nitrogen - elif self._to_be_background.lower().endswith(('.png', 'jpg', '.jpeg')): - output = f"[xin_0] \nfile={self._to_be_background}\nmode=0 \nbgcolor=#000000\n\n[xin_1] \nfile={self._to_be_background}\nmode=0 \nbgcolor=#000000"; - applyType = 2; - # VIDEO - else: - output = f"xwinwrap -ov -g {self._resolution} -st -sp -b -nf -s -ni -- {self._player} -wid WID -really-quiet -ao null -loop 0 '{self._to_be_background}'"; - pass - - try: - if self._file_writer: - self._file_writer.write(output) - self._file_writer.close() - except Exception as e: - print(":: Write failed! ::") - print(e) - - return applyType; diff --git a/src/versions/0.0.2/GWinWrap/signal_classes/__init__.py b/src/versions/0.0.2/GWinWrap/signal_classes/__init__.py deleted file mode 100644 index 97a8b3b..0000000 --- a/src/versions/0.0.2/GWinWrap/signal_classes/__init__.py +++ /dev/null @@ -1,9 +0,0 @@ -""" - Gtk Bound Signal Module -""" -from .mixins import * -from .SaveStateToXWinWarp import SaveStateToXWinWarp -from .SaveGWinWrapSettings import SaveGWinWrapSettings -from .IPCServerMixin import IPCServerMixin -from .Controller_Data import Controller_Data -from .Controller import Controller diff --git a/src/versions/0.0.2/GWinWrap/signal_classes/mixins/ThumbnailMixin.py b/src/versions/0.0.2/GWinWrap/signal_classes/mixins/ThumbnailMixin.py deleted file mode 100644 index e067732..0000000 --- a/src/versions/0.0.2/GWinWrap/signal_classes/mixins/ThumbnailMixin.py +++ /dev/null @@ -1,56 +0,0 @@ -# Python imports -import subprocess - -# Gtk imports -import gi -gi.require_version('Gtk', '3.0') -from gi.repository import Gtk -from gi.repository import GdkPixbuf - -# Application imports - - -class ThumbnailMixin: - """docstring for ThumbnailMixin""" - - def create_gtk_image(self, path, wxh): - try: - pixbuf = GdkPixbuf.Pixbuf.new_from_file_at_scale( - filename = path, - width = wxh[0], - height = wxh[1], - preserve_aspect_ratio = True) - return Gtk.Image.new_from_pixbuf(pixbuf) - except Exception as e: - print(repr(e)) - - return Gtk.Image() - - def generate_thumbnail(self, fullPathFile, hashImgpth): - # Stream duration - command = ["ffprobe", "-v", "error", "-select_streams", "v:0", "-show_entries", "stream=duration", "-of", "default=noprint_wrappers=1:nokey=1", fullPathFile] - data = subprocess.run(command, stdout=subprocess.PIPE) - duration = data.stdout.decode('utf-8') - - # Format (container) duration - if "N/A" in duration: - command = ["ffprobe", "-v", "error", "-show_entries", "format=duration", "-of", "default=noprint_wrappers=1:nokey=1", fullPathFile] - data = subprocess.run(command , stdout=subprocess.PIPE) - duration = data.stdout.decode('utf-8') - - # Stream duration type: image2 - if "N/A" in duration: - command = ["ffprobe", "-v", "error", "-select_streams", "v:0", "-f", "image2", "-show_entries", "stream=duration", "-of", "default=noprint_wrappers=1:nokey=1", fullPathFile] - data = subprocess.run(command, stdout=subprocess.PIPE) - duration = data.stdout.decode('utf-8') - - # Format (container) duration type: image2 - if "N/A" in duration: - command = ["ffprobe", "-v", "error", "-f", "image2", "-show_entries", "format=duration", "-of", "default=noprint_wrappers=1:nokey=1", fullPathFile] - data = subprocess.run(command , stdout=subprocess.PIPE) - duration = data.stdout.decode('utf-8') - - # Get frame roughly 35% through video - grabTime = str( int( float( duration.split(".")[0] ) * 0.35) ) - command = ["ffmpeg", "-ss", grabTime, "-i", fullPathFile, "-an", "-vframes", "1", "-s", "320x180", "-q:v", "2", hashImgpth] - subprocess.call(command) diff --git a/src/versions/0.0.2/GWinWrap/signal_classes/mixins/__init__.py b/src/versions/0.0.2/GWinWrap/signal_classes/mixins/__init__.py deleted file mode 100644 index f482286..0000000 --- a/src/versions/0.0.2/GWinWrap/signal_classes/mixins/__init__.py +++ /dev/null @@ -1,4 +0,0 @@ -from .ThumbnailMixin import ThumbnailMixin -from .DrawAreaMixin import DrawAreaMixin -from .ImageViewerMixin import ImageViewerMixin -from .GridMixin import GridMixin diff --git a/src/versions/0.0.2/GWinWrap/utils/Logger.py b/src/versions/0.0.2/GWinWrap/utils/Logger.py deleted file mode 100644 index 06eed47..0000000 --- a/src/versions/0.0.2/GWinWrap/utils/Logger.py +++ /dev/null @@ -1,56 +0,0 @@ -# Python imports -import os, logging - -# Application imports - - -class Logger: - def __init__(self, config_path): - self._CONFIG_PATH = config_path - - def get_logger(self, loggerName = "NO_LOGGER_NAME_PASSED", createFile = True): - """ - Create a new logging object and return it. - :note: - NOSET # Don't know the actual log level of this... (defaulting or literally none?) - Log Levels (From least to most) - Type Value - CRITICAL 50 - ERROR 40 - WARNING 30 - INFO 20 - DEBUG 10 - :param loggerName: Sets the name of the logger object. (Used in log lines) - :param createFile: Whether we create a log file or just pump to terminal - - :return: the logging object we created - """ - - globalLogLvl = logging.DEBUG # Keep this at highest so that handlers can filter to their desired levels - chLogLevel = logging.CRITICAL # Prety musch the only one we change ever - fhLogLevel = logging.DEBUG - log = logging.getLogger(loggerName) - log.setLevel(globalLogLvl) - - # Set our log output styles - fFormatter = logging.Formatter('[%(asctime)s] %(pathname)s:%(lineno)d %(levelname)s - %(message)s', '%m-%d %H:%M:%S') - cFormatter = logging.Formatter('%(pathname)s:%(lineno)d] %(levelname)s - %(message)s') - - ch = logging.StreamHandler() - ch.setLevel(level=chLogLevel) - ch.setFormatter(cFormatter) - log.addHandler(ch) - - if createFile: - folder = self._CONFIG_PATH - file = f"{folder}/application.log" - - if not os.path.exists(folder): - os.mkdir(folder) - - fh = logging.FileHandler(file) - fh.setLevel(level=fhLogLevel) - fh.setFormatter(fFormatter) - log.addHandler(fh) - - return log diff --git a/src/versions/0.0.2/GWinWrap/utils/Settings.py b/src/versions/0.0.2/GWinWrap/utils/Settings.py deleted file mode 100644 index 0bf6325..0000000 --- a/src/versions/0.0.2/GWinWrap/utils/Settings.py +++ /dev/null @@ -1,112 +0,0 @@ -# Python imports -import os - -# Gtk imports -import gi, cairo -gi.require_version('Gtk', '3.0') -gi.require_version('Gdk', '3.0') - -from gi.repository import Gtk -from gi.repository import Gdk - - -# Application imports -from . import Logger - - - -class Settings: - def __init__(self): - self._SCRIPT_PTH = os.path.dirname(os.path.realpath(__file__)) - self._USER_HOME = os.path.expanduser('~') - self._CONFIG_PATH = f"{self._USER_HOME}/.config/{app_name.lower()}" - self._GLADE_FILE = f"{self._CONFIG_PATH}/Main_Window.glade" - self._CSS_FILE = f"{self._CONFIG_PATH}/stylesheet.css" - self._DEFAULT_ICONS = f"{self._CONFIG_PATH}/icons" - self._WINDOW_ICON = f"{self._DEFAULT_ICONS}/{app_name.lower()}.png" - self._USR_PATH = f"/usr/share/{app_name.lower()}" - self._CONFIG_FILE = f"{self._CONFIG_PATH}/settings.json" - self._XSCREEN_SAVERS = "/usr/lib/xscreensaver/" - - - self._logger = Logger(self._CONFIG_PATH).get_logger() - self._builder = Gtk.Builder() - self._main_window = None - - # '_filters' - self._vids_filter = ('.mkv', '.avi', '.flv', '.mov', '.m4v', '.mpg', '.wmv', '.mpeg', '.mp4', '.webm') - self._images_filter = ('.png', '.jpg', '.jpeg', '.gif') - - self._success_color = "#88cc27" - self._warning_color = "#ffa800" - self._error_color = "#ff0000" - - if not os.path.exists(self._GLADE_FILE): - self._GLADE_FILE = f"{self._USR_PATH}/Main_Window.glade" - if not os.path.exists(self._CSS_FILE): - self._CSS_FILE = f"{self._USR_PATH}/stylesheet.css" - if not os.path.exists(self._WINDOW_ICON): - self._WINDOW_ICON = f"{self._USR_PATH}/icons/{app_name.lower()}.png" - if not os.path.exists(self._DEFAULT_ICONS): - self.DEFAULT_ICONS = f"{self._USR_PATH}/icons" - - self._builder.add_from_file(self._GLADE_FILE) - - - - def create_window(self): - # Get window and connect signals - self._main_window = self._builder.get_object("Main_Window") - self.set_window_data() - - def set_window_data(self): - self._main_window.set_icon_from_file(self._WINDOW_ICON) - screen = self._main_window.get_screen() - visual = screen.get_rgba_visual() - - if visual != None and screen.is_composited(): - self._main_window.set_visual(visual) - self._main_window.set_app_paintable(True) - self._main_window.connect("draw", self.draw_area) - - # bind css file - cssProvider = Gtk.CssProvider() - cssProvider.load_from_path(self._CSS_FILE) - screen = Gdk.Screen.get_default() - styleContext = Gtk.StyleContext() - styleContext.add_provider_for_screen(screen, cssProvider, Gtk.STYLE_PROVIDER_PRIORITY_USER) - - def get_monitor_data(self): - screen = self._builder.get_object("Main_Window").get_screen() - monitors = [] - for m in range(screen.get_n_monitors()): - monitors.append(screen.get_monitor_geometry(m)) - - for monitor in monitors: - print("{}x{}|{}+{}".format(monitor.width, monitor.height, monitor.x, monitor.y)) - - return monitors - - def draw_area(self, widget, cr): - cr.set_source_rgba(0, 0, 0, 0.54) - cr.set_operator(cairo.OPERATOR_SOURCE) - cr.paint() - cr.set_operator(cairo.OPERATOR_OVER) - - - - - def get_builder(self): return self._builder - def get_logger(self): return self._logger - def get_main_window(self): return self._main_window - def get_home_path(self): return self._USER_HOME - def get_config_file(self): return self._CONFIG_FILE - def get_xscreensavers(self): return self._XSCREEN_SAVERS - - # Filter returns - def get_vids_filter(self): return self._vids_filter - def get_images_filter(self): return self._images_filter - - def get_success_color(self): return self._success_color - def get_warning_color(self): return self._warning_color - def get_error_color(self): return self._error_color diff --git a/src/versions/0.0.2/GWinWrap/utils/__init__.py b/src/versions/0.0.2/GWinWrap/utils/__init__.py index 15fcd01..a8e5edd 100644 --- a/src/versions/0.0.2/GWinWrap/utils/__init__.py +++ b/src/versions/0.0.2/GWinWrap/utils/__init__.py @@ -1,2 +1,3 @@ -from .Logger import Logger -from .Settings import Settings +""" + Utils module +""" diff --git a/src/versions/0.0.2/GWinWrap/utils/endpoint_registry.py b/src/versions/0.0.2/GWinWrap/utils/endpoint_registry.py new file mode 100644 index 0000000..15ffa9e --- /dev/null +++ b/src/versions/0.0.2/GWinWrap/utils/endpoint_registry.py @@ -0,0 +1,22 @@ +# Python imports + +# Lib imports + +# Application imports + + + + +class EndpointRegistry(): + def __init__(self): + self._endpoints = {} + + def register(self, rule, **options): + def decorator(f): + self._endpoints[rule] = f + return f + + return decorator + + def get_endpoints(self): + return self._endpoints diff --git a/src/versions/0.0.2/GWinWrap/utils/event_system.py b/src/versions/0.0.2/GWinWrap/utils/event_system.py new file mode 100644 index 0000000..b2d4a71 --- /dev/null +++ b/src/versions/0.0.2/GWinWrap/utils/event_system.py @@ -0,0 +1,48 @@ +# Python imports +from collections import defaultdict + +# Lib imports + +# Application imports + + + + +class EventSystem: + """ Create event system. """ + + def __init__(self): + self.subscribers = defaultdict(list) + + + def subscribe(self, event_type, fn): + self.subscribers[event_type].append(fn) + + def unsubscribe(self, event_type, fn): + self.subscribers[event_type].remove(fn) + + def unsubscribe_all(self, event_type): + self.subscribers.pop(event_type, None) + + def emit(self, event_type, data = None): + if event_type in self.subscribers: + for fn in self.subscribers[event_type]: + if data: + if hasattr(data, '__iter__') and not type(data) is str: + fn(*data) + else: + fn(data) + else: + fn() + + def emit_and_await(self, event_type, data = None): + """ NOTE: Should be used when signal has only one listener and vis-a-vis """ + if event_type in self.subscribers: + for fn in self.subscribers[event_type]: + if data: + if hasattr(data, '__iter__') and not type(data) is str: + return fn(*data) + else: + return fn(data) + else: + return fn() diff --git a/src/versions/0.0.2/GWinWrap/utils/ipc_server.py b/src/versions/0.0.2/GWinWrap/utils/ipc_server.py new file mode 100644 index 0000000..8226247 --- /dev/null +++ b/src/versions/0.0.2/GWinWrap/utils/ipc_server.py @@ -0,0 +1,105 @@ +# Python imports +import os +import threading +import time +from multiprocessing.connection import Client +from multiprocessing.connection import Listener + +# Lib imports + +# Application imports + + + + +class IPCServer: + """ Create a listener so that other {app_name} instances send requests back to existing instance. """ + def __init__(self, ipc_address: str = '127.0.0.1', conn_type: str = "socket"): + self.is_ipc_alive = False + self._ipc_port = 4848 + self._ipc_address = ipc_address + self._conn_type = conn_type + self._ipc_authkey = b'' + bytes(f'{app_name}-ipc', 'utf-8') + self._ipc_timeout = 15.0 + + if conn_type == "socket": + self._ipc_address = f'/tmp/{app_name}-ipc.sock' + elif conn_type == "full_network": + self._ipc_address = '0.0.0.0' + elif conn_type == "full_network_unsecured": + self._ipc_authkey = None + self._ipc_address = '0.0.0.0' + elif conn_type == "local_network_unsecured": + self._ipc_authkey = None + + self._subscribe_to_events() + + def _subscribe_to_events(self): + event_system.subscribe("post_file_to_ipc", self.send_ipc_message) + + + def create_ipc_listener(self) -> None: + if self._conn_type == "socket": + if os.path.exists(self._ipc_address) and settings.is_dirty_start(): + os.unlink(self._ipc_address) + + listener = Listener(address=self._ipc_address, family="AF_UNIX", authkey=self._ipc_authkey) + elif "unsecured" not in self._conn_type: + listener = Listener((self._ipc_address, self._ipc_port), authkey=self._ipc_authkey) + else: + listener = Listener((self._ipc_address, self._ipc_port)) + + + self.is_ipc_alive = True + self._run_ipc_loop(listener) + + @daemon_threaded + def _run_ipc_loop(self, listener) -> None: + while True: + conn = listener.accept() + start_time = time.perf_counter() + self._handle_ipc_message(conn, start_time) + + listener.close() + + def _handle_ipc_message(self, conn, start_time) -> None: + while True: + msg = conn.recv() + if settings.is_debug(): + print(msg) + + if "FILE|" in msg: + file = msg.split("FILE|")[1].strip() + if file: + event_system.emit("handle_file_from_ipc", file) + + conn.close() + break + + + if msg in ['close connection', 'close server']: + conn.close() + break + + # NOTE: Not perfect but insures we don't lock up the connection for too long. + end_time = time.perf_counter() + if (end_time - start_time) > self._ipc_timeout: + conn.close() + break + + + def send_ipc_message(self, message: str = "Empty Data...") -> None: + try: + if self._conn_type == "socket": + conn = Client(address=self._ipc_address, family="AF_UNIX", authkey=self._ipc_authkey) + elif "unsecured" not in self._conn_type: + conn = Client((self._ipc_address, self._ipc_port), authkey=self._ipc_authkey) + else: + conn = Client((self._ipc_address, self._ipc_port)) + + conn.send(message) + conn.close() + except ConnectionRefusedError as e: + print("Connection refused...") + except Exception as e: + print(repr(e)) diff --git a/src/versions/0.0.2/GWinWrap/utils/keybindings.py b/src/versions/0.0.2/GWinWrap/utils/keybindings.py new file mode 100644 index 0000000..790c963 --- /dev/null +++ b/src/versions/0.0.2/GWinWrap/utils/keybindings.py @@ -0,0 +1,128 @@ +# Python imports +import re + +# Lib imports +import gi +gi.require_version('Gdk', '3.0') +from gi.repository import Gdk + +# Application imports + + + + +def err(log = ""): + """Print an error message""" + print(log) + + +class KeymapError(Exception): + """Custom exception for errors in keybinding configurations""" + +MODIFIER = re.compile('<([^<]+)>') +class Keybindings: + """Class to handle loading and lookup of Terminator keybindings""" + + modifiers = { + 'ctrl': Gdk.ModifierType.CONTROL_MASK, + 'control': Gdk.ModifierType.CONTROL_MASK, + 'primary': Gdk.ModifierType.CONTROL_MASK, + 'shift': Gdk.ModifierType.SHIFT_MASK, + 'alt': Gdk.ModifierType.MOD1_MASK, + 'super': Gdk.ModifierType.SUPER_MASK, + 'hyper': Gdk.ModifierType.HYPER_MASK, + 'mod2': Gdk.ModifierType.MOD2_MASK + } + + empty = {} + keys = None + _masks = None + _lookup = None + + def __init__(self): + self.keymap = Gdk.Keymap.get_default() + self.configure({}) + + def configure(self, bindings): + """Accept new bindings and reconfigure with them""" + self.keys = bindings + self.reload() + + def reload(self): + """Parse bindings and mangle into an appropriate form""" + self._lookup = {} + self._masks = 0 + + for action, bindings in list(self.keys.items()): + if isinstance(bindings, list): + bindings = (*bindings,) + elif not isinstance(bindings, tuple): + bindings = (bindings,) + + + for binding in bindings: + if not binding or binding == "None": + continue + + try: + keyval, mask = self._parsebinding(binding) + # Does much the same, but with poorer error handling. + #keyval, mask = Gtk.accelerator_parse(binding) + except KeymapError as e: + err ("keybinding reload failed to parse binding '%s': %s" % (binding, e)) + else: + if mask & Gdk.ModifierType.SHIFT_MASK: + if keyval == Gdk.KEY_Tab: + keyval = Gdk.KEY_ISO_Left_Tab + mask &= ~Gdk.ModifierType.SHIFT_MASK + else: + keyvals = Gdk.keyval_convert_case(keyval) + if keyvals[0] != keyvals[1]: + keyval = keyvals[1] + mask &= ~Gdk.ModifierType.SHIFT_MASK + else: + keyval = Gdk.keyval_to_lower(keyval) + + self._lookup.setdefault(mask, {}) + self._lookup[mask][keyval] = action + self._masks |= mask + + def _parsebinding(self, binding): + """Parse an individual binding using Gtk's binding function""" + mask = 0 + modifiers = re.findall(MODIFIER, binding) + + if modifiers: + for modifier in modifiers: + mask |= self._lookup_modifier(modifier) + + key = re.sub(MODIFIER, '', binding) + if key == '': + raise KeymapError('No key found!') + + keyval = Gdk.keyval_from_name(key) + + if keyval == 0: + raise KeymapError("Key '%s' is unrecognised..." % key) + return (keyval, mask) + + def _lookup_modifier(self, modifier): + """Map modifier names to gtk values""" + try: + return self.modifiers[modifier.lower()] + except KeyError: + raise KeymapError("Unhandled modifier '<%s>'" % modifier) + + def lookup(self, event): + """Translate a keyboard event into a mapped key""" + try: + _found, keyval, _egp, _lvl, consumed = self.keymap.translate_keyboard_state( + event.hardware_keycode, + Gdk.ModifierType(event.get_state() & ~Gdk.ModifierType.LOCK_MASK), + event.group) + except TypeError: + err ("Keybinding lookup failed to translate keyboard event: %s" % dir(event)) + return None + + mask = (event.get_state() & ~consumed) & self._masks + return self._lookup.get(mask, self.empty).get(keyval, None) diff --git a/src/versions/0.0.2/GWinWrap/utils/logger.py b/src/versions/0.0.2/GWinWrap/utils/logger.py new file mode 100644 index 0000000..6ca2add --- /dev/null +++ b/src/versions/0.0.2/GWinWrap/utils/logger.py @@ -0,0 +1,61 @@ +# Python imports +import os +import logging + +# Lib imports + +# Application imports + + + + +class Logger: + """ + Create a new logging object and return it. + :note: + NOSET # Don't know the actual log level of this... (defaulting or literally none?) + Log Levels (From least to most) + Type Value + CRITICAL 50 + ERROR 40 + WARNING 30 + INFO 20 + DEBUG 10 + :param loggerName: Sets the name of the logger object. (Used in log lines) + :param createFile: Whether we create a log file or just pump to terminal + + :return: the logging object we created + """ + + def __init__(self, config_path: str, _ch_log_lvl = logging.CRITICAL, _fh_log_lvl = logging.INFO): + self._CONFIG_PATH = config_path + self.global_lvl = logging.DEBUG # Keep this at highest so that handlers can filter to their desired levels + self.ch_log_lvl = _ch_log_lvl # Prety much the only one we ever change + self.fh_log_lvl = _fh_log_lvl + + def get_logger(self, loggerName: str = "NO_LOGGER_NAME_PASSED", createFile: bool = True) -> logging.Logger: + log = logging.getLogger(loggerName) + log.setLevel(self.global_lvl) + + # Set our log output styles + fFormatter = logging.Formatter('[%(asctime)s] %(pathname)s:%(lineno)d %(levelname)s - %(message)s', '%m-%d %H:%M:%S') + cFormatter = logging.Formatter('%(pathname)s:%(lineno)d] %(levelname)s - %(message)s') + + ch = logging.StreamHandler() + ch.setLevel(level=self.ch_log_lvl) + ch.setFormatter(cFormatter) + log.addHandler(ch) + + if createFile: + folder = self._CONFIG_PATH + file = f"{folder}/application.log" + + if not os.path.exists(folder): + os.mkdir(folder) + + fh = logging.FileHandler(file) + fh.setLevel(level=self.fh_log_lvl) + fh.setFormatter(fFormatter) + log.addHandler(fh) + + return log diff --git a/src/versions/0.0.2/GWinWrap/utils/settings.py b/src/versions/0.0.2/GWinWrap/utils/settings.py new file mode 100644 index 0000000..f0517a4 --- /dev/null +++ b/src/versions/0.0.2/GWinWrap/utils/settings.py @@ -0,0 +1,173 @@ +# Python imports +import os +import json +import inspect + +# Lib imports +import gi +gi.require_version('Gtk', '3.0') +from gi.repository import Gtk + +# Application imports +from .logger import Logger + + + + +class Settings: + def __init__(self): + self._SCRIPT_PTH = os.path.dirname(os.path.realpath(__file__)) + self._USER_HOME = os.path.expanduser('~') + self._USR_PATH = f"/usr/share/{app_name.lower()}" + self._USR_PATH_CONFIG = f"{self._USR_PATH}/settings.json" + self._CONFIG_PATH = f"{self._USER_HOME}/.config/{app_name.lower()}" + self._GLADE_FILE = f"{self._CONFIG_PATH}/Main_Window.glade" + self._CSS_FILE = f"{self._CONFIG_PATH}/stylesheet.css" + self._DEFAULT_ICONS = f"{self._CONFIG_PATH}/icons" + self._PID_FILE = f"{self._CONFIG_PATH}/{app_name.lower()}.pid" + self._WINDOW_ICON = f"{self._DEFAULT_ICONS}/{app_name.lower()}.png" + self._CONFIG_FILE = f"{self._CONFIG_PATH}/settings.json" + + if not os.path.exists(self._CONFIG_PATH): + os.mkdir(self._CONFIG_PATH) + + if not os.path.exists(self._CONFIG_FILE): + import shutil + try: + shutil.copyfile(self._USR_PATH_CONFIG, self._CONFIG_FILE) + except Exception as e: + raise + + if not os.path.exists(self._GLADE_FILE): + self._GLADE_FILE = f"{self._USR_PATH}/Main_Window.glade" + if not os.path.exists(self._CSS_FILE): + self._CSS_FILE = f"{self._USR_PATH}/stylesheet.css" + if not os.path.exists(self._DEFAULT_ICONS): + self.DEFAULT_ICONS = f"{self._USR_PATH}/icons" + if not os.path.exists(self._WINDOW_ICON): + self._WINDOW_ICON = f"{self.DEFAULT_ICONS}/{app_name.lower()}.png" + + + self._logger = Logger(self._CONFIG_PATH).get_logger() + self._builder = Gtk.Builder() + self._builder.add_from_file(self._GLADE_FILE) + + self._debug = False + self._trace_debug = False + self._dirty_start = False + + self._settings = None + self._config = None + self._theming = None + + self.load_settings() + + + def is_trace_debug(self) -> str: return self._trace_debug + def is_debug(self) -> str: return self._debug + def is_dirty_start(self) -> bool: return self._dirty_start + def clear_pid(self): self._clean_pid() + + def do_dirty_start_check(self): + if not os.path.exists(self._PID_FILE): + self._write_new_pid() + else: + with open(self._PID_FILE, "r") as _pid: + pid = _pid.readline().strip() + if pid not in ("", None): + self._check_alive_status(int(pid)) + else: + self._write_new_pid() + + """ Check For the existence of a unix pid. """ + def _check_alive_status(self, pid): + print(f"PID Found: {pid}") + try: + os.kill(pid, 0) + except OSError: + print(f"{app_name} is starting dirty...") + self._dirty_start = True + self._write_new_pid() + return + + print("PID is alive... Let downstream errors (sans debug args) handle app closure propigation.") + + def _write_new_pid(self): + pid = os.getpid() + self._write_pid(pid) + + def _clean_pid(self): + os.unlink(self._PID_FILE) + + def _write_pid(self, pid): + with open(self._PID_FILE, "w") as _pid: + _pid.write(f"{pid}") + + def register_signals_to_builder(self, classes=None): + handlers = {} + + for c in classes: + methods = None + try: + methods = inspect.getmembers(c, predicate=inspect.ismethod) + handlers.update(methods) + except Exception as e: + print(repr(e)) + + self._builder.connect_signals(handlers) + + def get_monitor_data(self, window): + screen = window.get_screen() + monitors = [] + for m in range(screen.get_n_monitors()): + monitors.append(screen.get_monitor_geometry(m)) + + for monitor in monitors: + print("{}x{}|{}+{}".format(monitor.width, monitor.height, monitor.x, monitor.y)) + + return monitors + + def get_builder(self) -> any: return self._builder + def get_config_file(self) -> str: return self._CONFIG_FILE + def get_glade_file(self) -> str: return self._GLADE_FILE + def get_logger(self) -> Logger: return self._logger + def get_icon_theme(self) -> str: return self._ICON_THEME + def get_css_file(self) -> str: return self._CSS_FILE + def get_window_icon(self) -> str: return self._WINDOW_ICON + def get_home_path(self) -> str: return self._USER_HOME + + def get_success_color(self) -> str: return self._theming["success_color"] + def get_warning_color(self) -> str: return self._theming["warning_color"] + def get_error_color(self) -> str: return self._theming["error_color"] + + def get_xscreensavers(self) -> str: return self._config["xscreensaver_path"] + def get_start_path(self) -> str: return self._config["start_path"] + def get_default_player(self) -> str: return self._config["default_player"] + def get_default_img_viewer(self) -> str: return self._config["default_img_viewer"] + + def get_vids_filter(self) -> tuple: return tuple(self._settings["filters"]["videos"]) + def get_images_filter(self) -> tuple: return tuple(self._settings["filters"]["images"]) + + + + def set_builder(self, builder): self._builder = builder + def set_start_path(self, path): self._config["start_path"] = path + def set_default_player(self, player): self._config["default_player"] = player + def set_default_img_viewer(self, viewer): self._config["default_img_viewer"] = viewer + + def set_trace_debug(self, trace_debug): + self._trace_debug = trace_debug + + def set_debug(self, debug): + self._debug = debug + + + def load_settings(self): + with open(self._CONFIG_FILE) as f: + self._settings = json.load(f) + self._config = self._settings["config"] + self._theming = self._settings["theming"] + + def save_settings(self): + with open(self._CONFIG_FILE, 'w') as outfile: + json.dump(self._settings, outfile, separators=(',', ':'), indent=4) diff --git a/src/versions/0.0.2/compileBin.sh b/src/versions/0.0.2/compileBin.sh deleted file mode 100755 index fdd8222..0000000 --- a/src/versions/0.0.2/compileBin.sh +++ /dev/null @@ -1,6 +0,0 @@ -#!/bin/bash - -function main() { - gcc -no-pie -s gwinwrap_exec_bin.cpp -o gwinwrap -} -main; diff --git a/src/versions/0.0.2/gwinwrap_exec_bin.cpp b/src/versions/0.0.2/gwinwrap_exec_bin.cpp deleted file mode 100644 index 81978ec..0000000 --- a/src/versions/0.0.2/gwinwrap_exec_bin.cpp +++ /dev/null @@ -1,10 +0,0 @@ -#include -#include -#include -using namespace std; - -int main() { - chdir("/opt/GWinWrap/"); - system("python3 ."); -return 0; -} diff --git a/user_config/bin/gwinwrap b/user_config/bin/gwinwrap new file mode 100755 index 0000000..6b4c244 --- /dev/null +++ b/user_config/bin/gwinwrap @@ -0,0 +1,28 @@ +#!/bin/bash + +# . CONFIG.sh + +# set -o xtrace ## To debug scripts +# set -o errexit ## To exit on error +# set -o errunset ## To exit if a variable is referenced but not set + + +function main() { + call_path=`pwd` + path="" + + if [[ ! "${1::1}" == /* ]]; then + path="${call_path}/${1}" + else + path="${1}" + fi + + if [ ! -d "${path}" ]; then + echo "GWinWrap: Path given not a directory..." + exit 1 + fi + + cd "/opt/" + python ./gwinwrap.zip "${path}" +} +main "$@"; diff --git a/user_config/usr/applications/gwinwrap.desktop b/user_config/usr/applications/gwinwrap.desktop new file mode 100755 index 0000000..4451f4a --- /dev/null +++ b/user_config/usr/applications/gwinwrap.desktop @@ -0,0 +1,9 @@ +[Desktop Entry] +Encoding=UTF-8 +Name=GWinWrap +Comment=Glade GUI with python controls for XWinWrap +Exec=/bin/gwinwrap %f +Icon=/usr/share/gwinwrap/icons/gwinwrap.png +Terminal=false +Type=Application +Categories=Accessories;System;Settings; diff --git a/user_config/usr/share/gwinwrap/Main_Window.glade b/user_config/usr/share/gwinwrap/Main_Window.glade index 41e0e23..f26f25a 100644 --- a/user_config/usr/share/gwinwrap/Main_Window.glade +++ b/user_config/usr/share/gwinwrap/Main_Window.glade @@ -1,5 +1,5 @@ - + @@ -31,6 +31,11 @@ gtk-cancel 3 + + True + False + gtk-close + True False @@ -68,90 +73,45 @@ gtk-media-stop 3 - - 950 - 600 + + True False - GWinWrap - center - 950 - 600 - icons/GWinWrap.png - center - + True False + 15 + 15 + 15 + vertical True False - 15 - 15 - 15 - vertical + 5 - + True False - 5 - - - True - False - 15 - Note: Double click an image to view the video or image. - - - True - True - 0 - - - - - True - False - Chose Dream Scene / Image Directory - select-folder - False - Folders - Dream Scene / Image Dir - - - - False - True - 1 - - - - - True - True - True - settingsImage - True - - - - False - True - 2 - - + 15 + Note: Double click an image to view the video or image. - False + True True 0 - + True False - True + Chose Dream Scene / Image Directory + select-folder + False + Folders + Dream Scene / Image Dir + False @@ -159,64 +119,191 @@ 1 + + + True + True + True + settingsImage + True + + + + False + True + 2 + + + + + False + True + 0 + + + + + True + False + True + + + False + True + 1 + + + + + True + True + in + + + True + False + + + + True + False + vertical + 10 + 10 + True + True + + + 640 + 525 + True + False + Choose Image/Video Directory... + + + + + + 0 + 0 + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + True + True + 2 + + + + + Clear + True + True + True + clearImage + True + + + + False + True + 3 + + + + + True + True + 0 + + + + + 300 + True + False + 10 + 15 + 15 + 15 + False + vertical + + + True + False + vertical + + + Use XScreenSaver + True + True + False + center + 5 + True + + + + False + True + 0 + + True True in - + True - False + False + True + XScreensaverStore + False + + + + + - - - True - False - vertical - 10 - 10 - True - True + + XScreensaves - - 640 - 525 - True - False - Choose Image/Video Directory... - - - - - - 0 - 0 - - - - - - - - - - - - - - - - - - - - - - - - - + + + 0 + @@ -226,23 +313,7 @@ True True - 2 - - - - - Clear - True - True - True - clearImage - True - - - - False - True - 3 + 1 @@ -254,14 +325,9 @@ - 300 True False - 10 - 15 - 15 - 15 - False + False vertical @@ -269,15 +335,37 @@ False vertical - - Use XScreenSaver + True - True - False - center - 5 - True - + False + + + True + False + 10 + 10 + Playback Resolutions + + + True + True + 0 + + + + + True + False + 10 + 10 + Position Offset + + + True + True + 1 + + False @@ -286,35 +374,85 @@ - + True - True - in + False - + True - False - True - XScreensaverStore - False - - - - - - - - XScreensaves - - - - 0 - - - - + False + 3 + + 7680x4320 + 3840x2160 + 2048x1080 + 1920x1080 + 1440x720 + 1600x900 + 1280x720 + 800x600 + + + True + True + 0 + + + + True + False + + + True + True + 1 + + + + + False + True + 1 + + + + + False + True + 0 + + + + + True + False + vertical + + + True + False + 10 + 5 + Save Path + + + True + True + 0 + + + + + True + False + 0 + + .animatedBGstarter.sh + .animatedBGstarter2.sh + .animatedBGstarter3.sh + True @@ -324,267 +462,121 @@ - True + False True - 0 + 1 - + + True False - False - vertical - + + Save True - False - vertical - - - True - False - - - True - False - 10 - 10 - Playback Resolutions - - - True - True - 0 - - - - - True - False - 10 - 10 - Position Offset - - - True - True - 1 - - - - - False - True - 0 - - - - - True - False - - - True - False - 3 - - 7680x4320 - 3840x2160 - 2048x1080 - 1920x1080 - 1440x720 - 1600x900 - 1280x720 - 800x600 - - - - True - True - 0 - - - - - True - False - - - True - True - 1 - - - - - False - True - 1 - - + True + True + True + True + saveImage + True + - False - True - 0 + 1 + 0 - + + (Re)Start True - False - vertical - - - True - False - 10 - 5 - Save Path - - - True - True - 0 - - - - - True - False - 0 - - .animatedBGstarter.sh - .animatedBGstarter2.sh - .animatedBGstarter3.sh - - - - True - True - 1 - - + True + True + True + True + startImage + True + - False - True - 1 + 0 + 0 - - + + Stop True - False - - - Save - True - True - True - True - True - saveImage - True - - - - 1 - 0 - - - - - (Re)Start - True - True - True - True - True - startImage - True - - - - 0 - 0 - - - - - Stop - True - True - True - True - True - stopImage - True - - - - 0 - 1 - - - - - Close - True - True - True - True - True - closeImage - True - - - - 1 - 1 - - - - - - - - - - - - - - - - - + True + True + True + True + stopImage + True + - False - True - 2 + 0 + 1 + + + Close + True + True + True + True + True + closeImage + True + + + + 1 + 1 + + + + + + + + + + + + + + + + + False - False - end - 1 + True + 2 False - True - 1 + False + end 1 + + False + True + 1 + 1 + @@ -691,6 +683,7 @@ True True True + closePopupImage2 True @@ -770,6 +763,7 @@ True Set Custom Default Path Set Custom Start Path + True @@ -808,6 +802,7 @@ True Set Custom Video Player Set Custom Video Player + True @@ -846,6 +841,7 @@ True Set Custom Image Viewer Set Custom Image Viewer + False diff --git a/user_config/usr/share/gwinwrap/settings.json b/user_config/usr/share/gwinwrap/settings.json index 596ddd2..b373664 100644 --- a/user_config/usr/share/gwinwrap/settings.json +++ b/user_config/usr/share/gwinwrap/settings.json @@ -1,9 +1,36 @@ { - "settings":[ - { - "start_path":"/home/abaddon/LazyShare/Movies-TV-Music/Dream Scenes/Games/Halo", - "default_player":"mpv", - "default_img_viewer":"mirage" - } - ] -} \ No newline at end of file + "config":{ + "start_path":"", + "xscreensaver_path":"/usr/lib/xscreensaver/", + "default_player":"mpv", + "default_img_viewer":"mirage" + }, + "filters":{ + "videos":[ + ".mkv", + ".mp4", + ".webm", + ".avi", + ".mov", + ".m4v", + ".mpg", + ".mpeg", + ".wmv", + ".flv" + ], + "images":[ + ".png", + ".jpg", + ".jpeg", + ".gif", + ".ico", + ".tga", + ".webp" + ] + }, + "theming":{ + "success_color":"#88cc27", + "warning_color":"#ffa800", + "error_color":"#ff0000" + } +}