#encoding: utf-8
#Viper - Video In Python Editing Reptile, a video editor
-#Copyright 2009 - 2010 Paul Hänsch
+#Copyright 2009 - 2011 Paul Hänsch
#This file is part of Viper.
call named_save_project() if no
project directory is set yet
"""
-
- self.named_save_project()
+ if self.subgets['timeline'].get_basedir() == None:
+ self.named_save_project()
+ else:
+ savedir = self.subgets['timeline'].get_basedir()
+ try: os.unlink(savedir + '/description.sqlite')
+ except: pass
+
+ dbcon = sqlite.connect(savedir + '/description.sqlite')
+ dbcur = dbcon.cursor()
+ dbcur.execute('CREATE TABLE chunks (iorder INTEGER PRIMARY KEY, filename TEXT, start REAL, frames INTEGER, played INTEGER, marked BOOLEAN);')
+ dbcur.execute('CREATE TABLE filters (iorder INTEGER PRIMARY KEY, chunk INTEGER, FOREIGN KEY (chunk) REFERENCES chunks (iorder));')
+ dbcur.execute('CREATE TABLE filter_lines (iorder INTEGER PRIMARY KEY, line TEXT, filter INTEGER, FOREIGN KEY (filter) REFERENCES filters (iorder));')
+ for chunk in self.subgets['timeline'].chunks:
+ chunk.store(dbcur)
+
+ dbcur.close()
+ dbcon.commit()
+ dbcon.close()
def named_save_project(self):
"""
Ask for directory to save to (and save project)
"""
-
savedir = tkFileDialog.asksaveasfilename(filetypes = [('Viper Project Directory', '*.vpd')])
os.makedirs(savedir)
- dbcon = sqlite.connect(savedir + '/description.sqlite')
- dbcur = dbcon.cursor()
- dbcur.execute('CREATE TABLE chunks (iorder INTEGER PRIMARY KEY, filename TEXT, start REAL, frames INTEGER, played INTEGER, marked BOOLEAN);')
- dbcur.execute('CREATE TABLE filters (iorder INTEGER PRIMARY KEY, chunk INTEGER, FOREIGN KEY (chunk) REFERENCES chunks (iorder));')
- dbcur.execute('CREATE TABLE filter_lines (iorder INTEGER PRIMARY KEY, line TEXT, filter INTEGER, FOREIGN KEY (filter) REFERENCES filters (iorder));')
- for chunk in self.subgets['timeline'].chunks:
- chunk.store(dbcur)
-
- dbcur.close()
- dbcon.commit()
- dbcon.close()
+ self.subgets['timeline'].set_basedir(savedir)
+ self.save_project()
def open_project(self):
"""
"""
opendir = tkFileDialog.askopenfilename(filetypes = [('Project Description', '*/description.sqlite')])
+ self.subgets['timeline'].set_basedir(opendir[0:-19])
for chunk in self.subgets['timeline'].chunks: chunk.delete()
--- /dev/null
+#encoding: utf-8
+#Copyright 2011 Paul Hänsch
+
+#This file is part of Viper.
+
+#Viper 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 3 of the License, or
+#(at your option) any later version.
+
+#Viper 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 Viper. If not, see <http://www.gnu.org/licenses/>
+
+from Tkinter import *
+import Pmw
+from flic import *
+
+class VFrameset(LabelFrame, Flic):
+ """
+ Visual frameset widget
+
+ This widget represents a set of frames and provides controls for manipulating
+ and positioning it.
+
+ Properties are:
+ schedule (string) - commands to the owning object, values can be
+ mv left : move this chunk left
+ mv right: move this chunk right
+ copy : double this chunk
+ apply : realize new video properties
+ delete : remove this chunk
+
+ subgets - dictionary of widgets forming this
+ complex widget
+ played (Tk.Boolean) - indicates status of the play checkbox (use ...play.get())
+ marked (Tk.Boolean) - indicates status of the mark checkbox (use ...mark.get())
+ """
+
+ def __init__(self, master = None, vurl = '', play = True):
+ """
+ Constructor
+
+ master - the holding widget
+ """
+ self.vurl = vurl
+ self.subgets = {}
+ self.schedule = ''
+ self.animate = play
+ self.played = BooleanVar(value = True)
+ self.marked = BooleanVar(value = True)
+
+ tooltips = Pmw.Balloon()
+
+ Flic.__init__(self)
+ LabelFrame.__init__(self, master = master, text = vurl.split('/')[-1])
+ self.subgets['video'] = Frame(self, height=90, width=120, bg = '#000000')
+ self.subgets['video'].grid(column=0, row=0, rowspan=4, sticky=W)
+
+ self.subgets['b_edit'] = Button(self, text = 'Edit', command = self.edit)
+ self.subgets['b_edit'].grid(column = 1, row=1, columnspan = 4, rowspan = 2)
+ tooltips.bind(self.subgets['b_edit'], 'Select and remove single frames from frameset.')
+
+ self.subgets['b_mvbw'] = Button(self, text = '<-', command=self.mvbw)
+ self.subgets['b_mvbw'].grid(column = 1, row = 3, rowspan = 1, columnspan = 2, sticky=E)
+ tooltips.bind(self.subgets['b_mvbw'],
+ 'Swap this chunk with its left neighbour (move it left).')
+
+ self.subgets['b_copy'] = Button(self, text = 'Copy', command=self.copy)
+ self.subgets['b_copy'].grid(column = 3, columnspan = 2, row = 3, rowspan = 1)
+ tooltips.bind(self.subgets['b_copy'],
+ 'Create another chunk with the same properties as this one.')
+
+ self.subgets['b_mvfw'] = Button(self, text = '->', command=self.mvfw)
+ self.subgets['b_mvfw'].grid(column = 5, row = 3, rowspan = 1, sticky=W)
+ tooltips.bind(self.subgets['b_mvfw'],
+ 'Swap this chunk with its right neighbour (move it right).')
+
+ self.subgets['c_play'] = Checkbutton(self, text='Play', offvalue=False,
+ onvalue=True, variable = self.played)
+# self.subgets['c_play'].select()
+ self.subgets['c_play'].grid(column=1, columnspan = 2, row=0)
+ tooltips.bind(self.subgets['c_play'],
+ 'Mark this chunk for playback in main window.')
+
+ self.subgets['c_mark'] = Checkbutton(self, text='Mark', offvalue=False,
+ onvalue=True, variable = self.marked)
+# self.subgets['c_mark'].select()
+ self.subgets['c_mark'].grid(column=3, columnspan = 2, row=0)
+ tooltips.bind(self.subgets['c_mark'],
+ 'Mark this chunk for application of choosen filters and effects.')
+
+ self.subgets['b_del'] = Button(self, text='Del', command = self.delete)
+ self.subgets['b_del'].grid(column=5, row=0, sticky=NE)
+ tooltips.bind(self.subgets['b_del'],
+ 'Remove this chunk from the project.')
+ self.schedule = 'apply'
+
+ def load_filters(self, dbcur, num):
+ """
+ Load filter list from database
+
+ db - sqlite database cursor
+ num - database primary key id of this chunk
+ """
+
+ dbcur.execute('SELECT iorder FROM filters ' +
+ 'WHERE chunk = ' + str(num) + ' ORDER BY iorder')
+ for filter in dbcur.fetchall():
+ dbcur.execute('SELECT line FROM filter_lines WHERE filter = ' +
+ str(filter[0]) + ' ORDER BY iorder')
+ line = []
+ for item in dbcur.fetchall():
+ line.append(item[0])
+ self.add_filter(line)
+
+ def delete(self):
+ """
+ Scheduler for internal use
+ """
+ self.schedule = 'delete'
+
+ def mvbw(self):
+ """
+ Scheduler for internal use
+ """
+ self.schedule = 'mv left'
+
+ def mvfw(self):
+ """
+ Scheduler for internal use
+ """
+ self.schedule = 'mv right'
+
+ def copy(self):
+ """
+ Scheduler for internal use
+ """
+ self.schedule = 'copy'
+
+ def store(self, dbcur):
+ """
+ Store chunk to database
+
+ The tables "chunks", "filters" and "filter_lines"
+ must be prepared in database.
+
+ dbcur - sqlite database cursor
+ """
+ if self.played.get(): played = '1'
+ else: played = '0'
+ if self.marked.get(): marked = '1'
+ else: marked = '0'
+ dbcur.execute('INSERT INTO chunks (filename, start, frames, played, marked) ' +
+ 'VALUES ("' + self.vurl + '", 0, 0, ' + played + ', ' + marked + ');')
+
+ dbcur.execute('SELECT last_insert_rowid();')
+ chunk_id = str(dbcur.fetchone()[0])
+
+ for filter in self.filters:
+ dbcur.execute('INSERT INTO filters (chunk) VALUES (' + chunk_id + ');')
+ dbcur.execute('SELECT last_insert_rowid();')
+ filter_id = str(dbcur.fetchone()[0])
+ for line in filter:
+ dbcur.execute('INSERT INTO filter_lines (line, filter) ' +
+ 'VALUES ("' + line + '", ' + filter_id + ')')
+ def slave_video(self):
+ return [self.vurl]
+
+ def edit(self):
+ self.schedule = 'apply'
+
+ def play(self):
+ Flic.play(self, self.subgets['video'].winfo_id(), width=120, height=90)