aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--components/__base__.py38
-rw-r--r--components/color.py7
-rw-r--r--components/image.py6
-rw-r--r--components/original.py10
-rw-r--r--components/text.py11
-rw-r--r--components/video.py6
-rw-r--r--core.py87
-rw-r--r--mainwindow.py26
-rw-r--r--presetmanager.py32
9 files changed, 175 insertions, 48 deletions
diff --git a/components/__base__.py b/components/__base__.py
index 3ccb5dc..b32c120 100644
--- a/components/__base__.py
+++ b/components/__base__.py
@@ -1,9 +1,15 @@
-from PyQt4 import QtGui
+from PyQt4 import QtGui, QtCore
+class Component(QtCore.QObject):
+ '''A base class for components to inherit from'''
-class Component:
- def __init__(self):
+ # modified = QtCore.pyqtSignal(int, bool)
+
+ def __init__(self, moduleIndex, compPos):
+ super().__init__()
self.currentPreset = None
+ self.moduleIndex = moduleIndex
+ self.compPos = compPos
def __str__(self):
return self.__doc__
@@ -13,12 +19,27 @@ class Component:
return 1
def cancel(self):
- # make sure your component responds to these variables in frameRender()
+ # please stop any lengthy process in response to this variable
self.canceled = True
def reset(self):
self.canceled = False
+ def update(self):
+ self.modified.emit(self.compPos, True)
+ # use super().update() then read your widget values here
+
+ def loadPreset(self, presetDict, presetName):
+ '''Children should take (presetDict, presetName=None) as args'''
+
+ # Use super().loadPreset(presetDict, presetName)
+ # Then update your widgets using the preset dict
+ self.currentPreset = presetName \
+ if presetName != None else presetDict['preset']
+
+ def savePreset(self):
+ return {}
+
def preFrameRender(self, **kwargs):
for var, value in kwargs.items():
exec('self.%s = value' % var)
@@ -62,7 +83,7 @@ class Component:
return page
def update(self):
- # read widget values
+ super().update()
self.parent.drawPreview()
def previewRender(self, previewWorker):
@@ -77,13 +98,6 @@ class Component:
image = Image.new("RGBA", (width, height), (0,0,0,0))
return image
- def loadPreset(self, presetDict, presetName=None):
- self.currentPreset = presetName
- # update widgets using a preset dict
-
- def savePreset(self):
- return {}
-
def cancel(self):
self.canceled = True
diff --git a/components/color.py b/components/color.py
index 11c1b19..b6105c8 100644
--- a/components/color.py
+++ b/components/color.py
@@ -7,6 +7,9 @@ from . import __base__
class Component(__base__.Component):
'''Color'''
+
+ modified = QtCore.pyqtSignal(int, bool)
+
def widget(self, parent):
self.parent = parent
page = uic.loadUi(os.path.join(
@@ -45,6 +48,7 @@ class Component(__base__.Component):
return page
def update(self):
+ super().update()
self.color1 = self.RGBFromString(self.page.lineEdit_color1.text())
self.color2 = self.RGBFromString(self.page.lineEdit_color2.text())
self.x = self.page.spinBox_x.value()
@@ -70,7 +74,8 @@ class Component(__base__.Component):
return Image.new("RGBA", (width, height), (r, g, b, 255))
def loadPreset(self, pr, presetName=None):
- self.currentPreset = presetName if presetName else pr['preset']
+ super().loadPreset(pr, presetName)
+
self.page.lineEdit_color1.setText('%s,%s,%s' % pr['color1'])
self.page.lineEdit_color2.setText('%s,%s,%s' % pr['color2'])
diff --git a/components/image.py b/components/image.py
index 441e0e1..ed5f243 100644
--- a/components/image.py
+++ b/components/image.py
@@ -6,6 +6,9 @@ from . import __base__
class Component(__base__.Component):
'''Image'''
+
+ modified = QtCore.pyqtSignal(int, bool)
+
def widget(self, parent):
self.parent = parent
self.settings = parent.settings
@@ -22,6 +25,7 @@ class Component(__base__.Component):
return page
def update(self):
+ super().update()
self.imagePath = self.page.lineEdit_image.text()
self.parent.drawPreview()
@@ -49,7 +53,7 @@ class Component(__base__.Component):
return frame
def loadPreset(self, pr, presetName=None):
- self.currentPreset = presetName if presetName else pr['preset']
+ super().loadPreset(pr, presetName)
self.page.lineEdit_image.setText(pr['image'])
def savePreset(self):
diff --git a/components/original.py b/components/original.py
index 7873f43..f3f578d 100644
--- a/components/original.py
+++ b/components/original.py
@@ -1,9 +1,8 @@
import numpy
from PIL import Image, ImageDraw
-from PyQt4 import uic, QtGui
+from PyQt4 import uic, QtGui, QtCore
from PyQt4.QtGui import QColor
import os
-import random
from . import __base__
import time
from copy import copy
@@ -11,6 +10,9 @@ from copy import copy
class Component(__base__.Component):
'''Original Audio Visualization'''
+
+ modified = QtCore.pyqtSignal(int, bool)
+
def widget(self, parent):
self.parent = parent
self.visColor = (255, 255, 255)
@@ -33,12 +35,14 @@ class Component(__base__.Component):
return page
def update(self):
+ super().update()
self.layout = self.page.comboBox_visLayout.currentIndex()
self.visColor = self.RGBFromString(self.page.lineEdit_visColor.text())
self.parent.drawPreview()
def loadPreset(self, pr, presetName=None):
- self.currentPreset = presetName if presetName else pr['preset']
+ super().loadPreset(pr, presetName)
+
self.page.lineEdit_visColor.setText('%s,%s,%s' % pr['visColor'])
btnStyle = "QPushButton { background-color : %s; outline: none; }" \
% QColor(*pr['visColor']).name()
diff --git a/components/text.py b/components/text.py
index e8fb3d5..a40e2a9 100644
--- a/components/text.py
+++ b/components/text.py
@@ -9,8 +9,11 @@ from . import __base__
class Component(__base__.Component):
'''Title Text'''
- def __init__(self):
- super().__init__()
+
+ modified = QtCore.pyqtSignal(int, bool)
+
+ def __init__(self, *args):
+ super().__init__(*args)
self.titleFont = QFont()
def widget(self, parent):
@@ -53,6 +56,7 @@ class Component(__base__.Component):
return page
def update(self):
+ super().update()
self.title = self.page.lineEdit_title.text()
self.alignment = self.page.comboBox_textAlign.currentIndex()
self.titleFont = self.page.fontComboBox_titleFont.currentFont()
@@ -79,7 +83,8 @@ class Component(__base__.Component):
return x, self.yPosition
def loadPreset(self, pr, presetName=None):
- self.currentPreset = presetName if presetName else pr['preset']
+ super().loadPreset(pr, presetName)
+
self.page.lineEdit_title.setText(pr['title'])
font = QFont()
font.fromString(pr['titleFont'])
diff --git a/components/video.py b/components/video.py
index bd1bf96..ff06329 100644
--- a/components/video.py
+++ b/components/video.py
@@ -86,6 +86,9 @@ class Video:
class Component(__base__.Component):
'''Video'''
+
+ modified = QtCore.pyqtSignal(int, bool)
+
def widget(self, parent):
self.parent = parent
self.settings = parent.settings
@@ -106,6 +109,7 @@ class Component(__base__.Component):
return page
def update(self):
+ super().update()
self.videoPath = self.page.lineEdit_video.text()
self.loopVideo = self.page.checkBox_loop.isChecked()
self.parent.drawPreview()
@@ -136,7 +140,7 @@ class Component(__base__.Component):
return self.video.frame(frameNo)
def loadPreset(self, pr, presetName=None):
- self.currentPreset = presetName if presetName else pr['preset']
+ super().loadPreset(pr, presetName)
self.page.lineEdit_video.setText(pr['video'])
self.page.checkBox_loop.setChecked(pr['loop'])
diff --git a/core.py b/core.py
index c47068c..5617c81 100644
--- a/core.py
+++ b/core.py
@@ -34,6 +34,7 @@ class Core():
self.findComponents()
self.selectedComponents = []
+ self.modifiedComponents = {}
def findComponents(self):
def findComponents():
@@ -50,24 +51,86 @@ class Core():
for name in findComponents()]
self.moduleIndexes = [i for i in range(len(self.modules))]
+ def componentListChanged(self):
+ for i, component in enumerate(self.selectedComponents):
+ component.compPos = i
+ # print('Modified Components: ', self.modifiedComponents)
+
def insertComponent(self, compPos, moduleIndex):
if compPos < 0:
compPos = len(self.selectedComponents) -1
+
+ component = self.modules[moduleIndex].Component(
+ moduleIndex, compPos)
self.selectedComponents.insert(
compPos,
- self.modules[moduleIndex].Component()
- )
+ component)
+
+ newDict = {}
+ for i, val in self.modifiedComponents.items():
+ if i >= compPos:
+ newDict[i+1] = bool(val)
+ else:
+ newDict[i] = bool(val)
+ self.modifiedComponents.clear()
+ self.modifiedComponents = newDict
+
+ self.componentListChanged()
return compPos
def moveComponent(self, startI, endI):
+ def insert(target, comp):
+ self.selectedComponents.insert(target, comp)
+
comp = self.selectedComponents.pop(startI)
- self.selectedComponents.insert(endI, comp)
+ insert(endI, comp)
+
+ try:
+ oldModified = self.modifiedComponents.pop(startI)
+ if endI in self.modifiedComponents:
+ self.modifiedComponents[startI] = \
+ self.modifiedComponents.pop(endI)
+ self.modifiedComponents[endI] = oldModified
+ except KeyError:
+ pass
+
+ self.componentListChanged()
return endI
+ def removeComponent(self, i):
+ self.selectedComponents.pop(i)
+ try:
+ self.modifiedComponents.pop(i)
+ except KeyError:
+ pass
+
+ newDict = {}
+ for index, val in self.modifiedComponents.items():
+ if index >= i:
+ newDict[index-1] = bool(val)
+ else:
+ newDict[index] = bool(val)
+ self.modifiedComponents.clear()
+ self.modifiedComponents = newDict
+
+ self.componentListChanged()
+
def updateComponent(self, i):
# print('updating %s' % self.selectedComponents[i])
self.selectedComponents[i].update()
+ def componentModified(self, i):
+ '''Triggered by mainwindow.updateComponentTitle()
+ Tracks temporary state of whether components are modified or not
+ for retrieval upon loading a project file'''
+ self.modifiedComponents[i] = True
+
+ def componentUnmodified(self, i):
+ try:
+ self.modifiedComponents.pop(i)
+ except KeyError:
+ pass
+
def moduleIndexFor(self, compName):
compNames = [mod.Component.__doc__ for mod in self.modules]
index = compNames.index(compName)
@@ -78,11 +141,17 @@ class Core():
which implements an insertComponent method'''
errcode, data = self.parseAvFile(filepath)
if errcode == 0:
- for name, vers, preset in data['Components']:
+ for i, tup in enumerate(data['Components']):
+ name, vers, preset = tup
loader.insertComponent(
self.moduleIndexFor(name), -1)
self.selectedComponents[-1].loadPreset(
preset)
+ if data['Modified'][i] == True:
+ self.componentModified(i)
+ loader.updateComponentTitle(i, True)
+ else:
+ loader.updateComponentTitle(i)
elif errcode == 1:
typ, value, _ = data
if typ.__name__ == KeyError:
@@ -105,7 +174,7 @@ class Core():
with open(filepath, 'r') as f:
def parseLine(line):
'''Decides if a given avp or avl line is a section header'''
- validSections = ('Components')
+ validSections = ('Components', 'Modified')
line = line.strip()
newSection = ''
@@ -138,6 +207,8 @@ class Core():
lastCompPreset)
)
i = 0
+ if line and section == 'Modified':
+ data[section].append(eval(line))
return 0, data
except:
return 1, sys.exc_info()
@@ -223,6 +294,12 @@ class Core():
f.write('%s\n' % str(comp))
f.write('%s\n' % str(comp.version()))
f.write('%s\n' % Core.presetToString(saveValueStore))
+ f.write('[Modified]\n')
+ for i in range(len(self.selectedComponents)):
+ if i in self.modifiedComponents:
+ f.write('%s\n' % repr(True))
+ else:
+ f.write('%s\n' % repr(False))
return True
except:
return False
diff --git a/mainwindow.py b/mainwindow.py
index 42105d1..2a04a4a 100644
--- a/mainwindow.py
+++ b/mainwindow.py
@@ -235,13 +235,21 @@ class MainWindow(QtCore.QObject):
self.previewThread.wait()
self.autosave()
- def updateComponentTitle(self, pos):
+ @QtCore.pyqtSlot(int, bool)
+ def updateComponentTitle(self, pos, modified=False):
+ #print(pos, modified)
if pos < 0:
pos = len(self.core.selectedComponents)-1
title = str(self.core.selectedComponents[pos])
if self.core.selectedComponents[pos].currentPreset:
title += ' - %s' % self.core.selectedComponents[pos].currentPreset
+ if modified:
+ title += '*'
self.window.listWidget_componentList.item(pos).setText(title)
+ if modified:
+ self.core.componentModified(pos)
+ else:
+ self.core.componentUnmodified(pos)
def updateCodecs(self):
containerWidget = self.window.comboBox_videoContainer
@@ -344,9 +352,6 @@ class MainWindow(QtCore.QObject):
self.showMessage(
msg="You must select an audio file and output filename.")
- def progressBarUpdated(self, value):
- self.window.progressBar_createVideo.setValue(value)
-
def changeEncodingStatus(self, status):
if status:
self.window.pushButton_createVideo.setEnabled(False)
@@ -385,6 +390,9 @@ class MainWindow(QtCore.QObject):
self.window.pushButton_presets.setEnabled(True)
self.window.listWidget_componentList.setEnabled(True)
+ def progressBarUpdated(self, value):
+ self.window.progressBar_createVideo.setValue(value)
+
def progressBarSetText(self, value):
self.window.progressBar_createVideo.setFormat(value)
@@ -420,6 +428,10 @@ class MainWindow(QtCore.QObject):
self.core.selectedComponents[index].__doc__)
componentList.setCurrentRow(index)
+ # connect to signal that adds an asterisk when modified
+ self.core.selectedComponents[index].modified.connect(
+ self.updateComponentTitle)
+
self.pages.insert(index, self.core.selectedComponents[index].widget(self))
stackedWidget.insertWidget(index, self.pages[index])
stackedWidget.setCurrentIndex(index)
@@ -433,7 +445,7 @@ class MainWindow(QtCore.QObject):
index = componentList.row(selected)
self.window.stackedWidget.removeWidget(self.pages[index])
componentList.takeItem(index)
- self.core.selectedComponents.pop(index)
+ self.core.removeComponent(index)
self.pages.pop(index)
self.changeComponentWidget()
self.drawPreview()
@@ -533,10 +545,6 @@ class MainWindow(QtCore.QObject):
# actually load the project using core method
self.core.openProject(self, filepath)
- for i in range(self.window.listWidget_componentList.count()):
- # update listwidget titles to indicate loaded presets
- self.updateComponentTitle(i)
-
def showMessage(self, **kwargs):
parent = kwargs['parent'] if 'parent' in kwargs else self.window
msg = QtGui.QMessageBox(parent)
diff --git a/presetmanager.py b/presetmanager.py
index 91dc373..4300ce1 100644
--- a/presetmanager.py
+++ b/presetmanager.py
@@ -105,14 +105,14 @@ class PresetManager(QtGui.QDialog):
def openSavePresetDialog(self):
'''Functions on mainwindow level from the context menu'''
window = self.parent.window
- self.selectedComponents = self.parent.core.selectedComponents
+ selectedComponents = self.parent.core.selectedComponents
componentList = self.parent.window.listWidget_componentList
if componentList.currentRow() == -1:
return
while True:
index = componentList.currentRow()
- currentPreset = self.selectedComponents[index].currentPreset
+ currentPreset = selectedComponents[index].currentPreset
newName, OK = QtGui.QInputDialog.getText(
self.parent.window,
'Audio Visualizer',
@@ -127,30 +127,35 @@ class PresetManager(QtGui.QDialog):
if newName:
if index != -1:
saveValueStore = \
- self.selectedComponents[index].savePreset()
- componentName = str(self.selectedComponents[index]).strip()
- vers = self.selectedComponents[index].version()
+ selectedComponents[index].savePreset()
+ componentName = str(selectedComponents[index]).strip()
+ vers = selectedComponents[index].version()
self.createNewPreset(
- componentName, vers, newName, saveValueStore)
- self.selectedComponents[index].currentPreset = newName
- self.findPresets()
- self.drawPresetList()
+ componentName, vers, newName,
+ saveValueStore, window=self.parent.window)
+ selectedComponents[index].currentPreset = newName
+ #self.findPresets()
+ #self.drawPresetList()
+ self.parent.updateComponentTitle(index)
break
- def createNewPreset(self, compName, vers, filename, saveValueStore):
+ def createNewPreset(
+ self, compName, vers, filename, saveValueStore, **kwargs):
path = os.path.join(self.presetDir, compName, str(vers), filename)
- if self.presetExists(path):
+ if self.presetExists(path, **kwargs):
return
self.core.createPresetFile(compName, vers, filename, saveValueStore)
- def presetExists(self, path):
+ def presetExists(self, path, **kwargs):
if os.path.exists(path):
+ window = self.window \
+ if 'window' not in kwargs else kwargs['window']
ch = self.parent.showMessage(
msg="%s already exists! Overwrite it?" %
os.path.basename(path),
showCancel=True,
icon=QtGui.QMessageBox.Warning,
- parent=self.window)
+ parent=window)
if not ch:
# user clicked cancel
return True
@@ -204,6 +209,7 @@ class PresetManager(QtGui.QDialog):
os.remove(filepath)
def warnMessage(self, window=None):
+ print(window)
self.parent.showMessage(
msg='Preset names must contain only letters, '
'numbers, and spaces.',