Mercurial > code > home > repos > light9
changeset 538:571d058c9838
vidref refactor, start gui layout
Ignore-this: 68728a495bdaaa1316e70fdddfbfc037
author | drewp@bigasterisk.com |
---|---|
date | Sun, 13 Jun 2010 07:57:29 +0000 |
parents | 1929e0e1053e |
children | 5cf326ef965a |
files | light9/vidref/main.py light9/vidref/replay.py light9/vidref/vidref.glade |
diffstat | 3 files changed, 343 insertions(+), 158 deletions(-) [+] |
line wrap: on
line diff
--- a/light9/vidref/main.py Sun Jun 13 07:57:00 2010 +0000 +++ b/light9/vidref/main.py Sun Jun 13 07:57:29 2010 +0000 @@ -10,23 +10,16 @@ pygst.require("0.10") import gst, gobject, time, jsonlib, restkit, logging, os, traceback from decimal import Decimal -from bisect import bisect_left -import pygtk import gtk from twisted.python.util import sibpath import Image from threading import Thread from Queue import Queue from light9 import networking +from light9.vidref.replay import ReplayViews log = logging.getLogger() -existingDir = "/tmp/vidref/play-_my_proj_light9_show_dance2010_music_07-jacksonmix-complete.wav-1276331148" -existingFrames = sorted([Decimal(f.split('.jpg')[0]) - for f in os.listdir(existingDir)]) - -otherPic = None - class MusicTime(object): """ fetch times from ascoltami in a background thread; return times @@ -44,6 +37,8 @@ """ dict with 't' and 'song', etc. """ + if not hasattr(self, 'position'): + return {'t' : 0, 'song' : None} pos = self.position.copy() if pos['playing']: pos['t'] = pos['t'] + (time.time() - self.positionFetchTime) @@ -56,26 +51,6 @@ self.positionFetchTime = time.time() self.position = position time.sleep(self.period) - -class ReplayFrames(object): - """ - supplies all the frames from disk for the replay videos - """ - def update(self, position): - inPic = self.findClosestFrame(position['t']+.2) - with gtk.gdk.lock: - otherPic.set_from_file(inPic) - if 0: - # force redraw of that widget - otherPic.queue_draw_area(0,0,320,240) - otherPic.get_window().process_updates(True) - - def findClosestFrame(self, t): - i = bisect_left(existingFrames, Decimal(str(t))) - if i >= len(existingFrames): - i = len(existingFrames) - 1 - return os.path.join(existingDir, "%08.03f.jpg" % existingFrames[i]) - class VideoRecordSink(gst.Element): _sinkpadtemplate = gst.PadTemplate ("sinkpadtemplate", @@ -109,7 +84,6 @@ t.start() def chainfunc(self, pad, buffer): - return gst.FLOW_OK global nextImageCb self.info("%s timestamp(buffer):%d" % (pad, buffer.timestamp)) @@ -160,25 +134,31 @@ class Main(object): def __init__(self): - global otherPic wtree = gtk.Builder() wtree.add_from_file(sibpath(__file__, "vidref.glade")) mainwin = wtree.get_object("MainWindow") - otherPic = wtree.get_object("liveVideo") mainwin.connect("destroy", gtk.main_quit) wtree.connect_signals(self) - # other sources: videotestsrc, v4l2src device=/dev/video0 - ## if 0: - ## source = makeElem("videotestsrc", "video") - ## else: - ## source = makeElem("v4l2src", "vsource") - ## source.set_property("device", "/dev/video0") + self.replayViews = ReplayViews(wtree.get_object("image1"))#"replayScroll")) + + mainwin.show_all() + self.liveVideoXid = wtree.get_object("vid3").window.xid + + self.setInput('dv') + + def getInputs(self): + return ['auto', 'dv', 'video0'] - dv = "dv1394src name=src1 ! dvdemux ! dvdec" - v4l = "v4l2src device=/dev/video0 ! hqdn3d" + def setInput(self, name): + sourcePipe = { + "auto": "autovideosrc name=src1", + "testpattern" : "videotestsrc name=src1", + "dv": "dv1394src name=src1 ! dvdemux ! dvdec", + "v4l": "v4l2src device=/dev/video0 name=src1 ! hqdn3d" , + }[name] - cam = (dv + " ! " + cam = (sourcePipe + " ! " "videorate ! video/x-raw-yuv,framerate=15/1 ! " "videoscale ! video/x-raw-yuv,width=320,height=240;video/x-raw-rgb,width=320,height=240 ! " "queue name=vid") @@ -191,8 +171,7 @@ return e sink = makeElem("xvimagesink") - replay = ReplayFrames() - recSink = VideoRecordSink(replay) + recSink = VideoRecordSink(self.replayViews) self.pipeline.add(recSink) tee = makeElem("tee") @@ -202,12 +181,8 @@ gst.element_link_many(self.pipeline.get_by_name("vid"), tee, sink) gst.element_link_many(tee, makeElem("ffmpegcolorspace"), caps, recSink) - - mainwin.show_all() - - sink.set_xwindow_id(wtree.get_object("vid3").window.xid) - - self.pipeline.set_state(gst.STATE_PLAYING) + sink.set_xwindow_id(self.liveVideoXid) + self.pipeline.set_state(gst.STATE_PLAYING) def on_liveVideoEnabled_toggled(self, widget): if widget.get_active():
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/light9/vidref/replay.py Sun Jun 13 07:57:29 2010 +0000 @@ -0,0 +1,62 @@ +import os, gtk +from bisect import bisect_left +from decimal import Decimal + +existingDir = "/tmp/vidref/play-_my_proj_light9_show_dance2010_music_01-chorusmix.wav-1276415052" +existingFrames = sorted([Decimal(f.split('.jpg')[0]) + for f in os.listdir(existingDir)]) + + +class ReplayViews(object): + """ + the whole list of replay windows. parent is the scrolling area for + these windows to be added + """ + def __init__(self, parent): + self.out = ReplayView(parent, Replay(existingDir)) + return + for x in range(1000): + lab = gtk.Label() + lab.set_text("hello") + parent.add_with_viewport(lab) + + def update(self, position): + """ + freshen all replay windows. We get called this about every + time there's a new live video frame. + + may be responsible for making new children if we change song + """ + self.out.updatePic(position) + +class Replay(object): + """ + model for one of the replay widgets + """ + def __init__(self, sourceDir): + self.sourceDir = sourceDir + + def findClosestFrame(self, t): + i = bisect_left(existingFrames, Decimal(str(t))) + if i >= len(existingFrames): + i = len(existingFrames) - 1 + return os.path.join(existingDir, "%08.03f.jpg" % existingFrames[i]) + +class ReplayView(object): + """ + one of the replay widgets + """ + def __init__(self, parent, replay): + self.replay = replay +# self.loadWindwos + self.picWidget = parent + + def updatePic(self, position): + inPic = self.replay.findClosestFrame(position['t']+.25) + with gtk.gdk.lock: + self.picWidget.set_from_file(inPic) + if 0: + # force redraw of that widget + self.picWidget.queue_draw_area(0,0,320,240) + self.picWidget.get_window().process_updates(True) +
--- a/light9/vidref/vidref.glade Sun Jun 13 07:57:00 2010 +0000 +++ b/light9/vidref/vidref.glade Sun Jun 13 07:57:29 2010 +0000 @@ -6,60 +6,286 @@ <property name="default_width">500</property> <property name="default_height">500</property> <child> - <object class="GtkFixed" id="fixed1"> + <object class="GtkHBox" id="hbox3"> <property name="visible">True</property> <child> - <object class="GtkFrame" id="frame1"> - <property name="width_request">336</property> - <property name="height_request">277</property> + <object class="GtkVBox" id="vbox3"> <property name="visible">True</property> - <property name="label_xalign">0</property> - <property name="shadow_type">out</property> <child> - <object class="GtkFixed" id="fixed2"> + <object class="GtkFrame" id="frame1"> + <property name="width_request">336</property> + <property name="height_request">277</property> + <property name="visible">True</property> + <property name="label_xalign">0</property> + <property name="shadow_type">out</property> + <child> + <object class="GtkAspectFrame" id="aspectframe2"> + <property name="visible">True</property> + <property name="label_xalign">0</property> + <property name="shadow_type">none</property> + <property name="ratio">1.3300000429153442</property> + <child> + <object class="GtkDrawingArea" id="vid3"> + <property name="width_request">320</property> + <property name="height_request">240</property> + <property name="visible">True</property> + </object> + </child> + </object> + </child> + <child type="label"> + <object class="GtkLabel" id="label2"> + <property name="visible">True</property> + <property name="label" translatable="yes"><b>Live view</b></property> + <property name="use_markup">True</property> + </object> + </child> + </object> + <packing> + <property name="expand">False</property> + <property name="position">0</property> + </packing> + </child> + <child> + <object class="GtkVBox" id="vbox4"> <property name="visible">True</property> <child> - <object class="GtkDrawingArea" id="vid3"> - <property name="width_request">320</property> - <property name="height_request">240</property> + <object class="GtkToggleButton" id="liveVideoEnabled"> + <property name="label" translatable="yes">Enabled</property> + <property name="width_request">110</property> + <property name="height_request">36</property> <property name="visible">True</property> + <property name="can_focus">True</property> + <property name="receives_default">True</property> + <property name="active">True</property> + <signal name="toggled" handler="on_liveVideoEnabled_toggled"/> </object> <packing> - <property name="x">7</property> - <property name="y">8</property> + <property name="expand">False</property> + <property name="position">0</property> + </packing> + </child> + <child> + <object class="GtkHBox" id="hbox4"> + <property name="visible">True</property> + <child> + <object class="GtkLabel" id="label1"> + <property name="width_request">75</property> + <property name="height_request">20</property> + <property name="visible">True</property> + <property name="label" translatable="yes">Frame rate</property> + </object> + <packing> + <property name="position">0</property> + </packing> + </child> + <child> + <object class="GtkSpinButton" id="liveFrameRate"> + <property name="width_request">52</property> + <property name="height_request">25</property> + <property name="visible">True</property> + <property name="can_focus">True</property> + <property name="invisible_char">●</property> + <property name="numeric">True</property> + </object> + <packing> + <property name="position">1</property> + </packing> + </child> + </object> + <packing> + <property name="expand">False</property> + <property name="position">1</property> + </packing> + </child> + <child> + <object class="GtkHBox" id="hbox5"> + <property name="visible">True</property> + <child> + <object class="GtkLabel" id="label4"> + <property name="width_request">85</property> + <property name="height_request">20</property> + <property name="visible">True</property> + <property name="label" translatable="yes">Input source</property> + </object> + <packing> + <property name="position">0</property> + </packing> + </child> + <child> + <object class="GtkComboBox" id="videoSource"> + <property name="width_request">100</property> + <property name="visible">True</property> + </object> + <packing> + <property name="position">1</property> + </packing> + </child> + </object> + <packing> + <property name="expand">False</property> + <property name="position">2</property> </packing> </child> </object> - </child> - <child type="label"> - <object class="GtkLabel" id="label2"> - <property name="visible">True</property> - <property name="label" translatable="yes"><b>Live view</b></property> - <property name="use_markup">True</property> - </object> + <packing> + <property name="expand">False</property> + <property name="position">1</property> + </packing> </child> </object> <packing> - <property name="x">15</property> - <property name="y">10</property> + <property name="expand">False</property> + <property name="position">0</property> </packing> </child> <child> - <object class="GtkFrame" id="frame2"> + <object class="GtkFrame" id="replayHalf"> <property name="width_request">336</property> <property name="height_request">259</property> <property name="visible">True</property> <property name="label_xalign">0</property> <property name="shadow_type">out</property> <child> - <object class="GtkAlignment" id="alignment1"> + <object class="GtkScrolledWindow" id="replayScrollWin"> + <property name="width_request">571</property> + <property name="height_request">367</property> <property name="visible">True</property> - <property name="left_padding">12</property> + <property name="can_focus">True</property> + <property name="hscrollbar_policy">automatic</property> + <property name="vscrollbar_policy">automatic</property> + <property name="shadow_type">out</property> <child> - <object class="GtkImage" id="liveVideo"> - <property name="width_request">320</property> - <property name="height_request">240</property> + <object class="GtkViewport" id="replayScroll"> <property name="visible">True</property> + <property name="resize_mode">queue</property> + <child> + <object class="GtkVBox" id="vbox1"> + <property name="visible">True</property> + <child> + <object class="GtkHandleBox" id="handlebox1"> + <property name="height_request">273</property> + <property name="visible">True</property> + <child> + <object class="GtkHBox" id="hbox1"> + <property name="visible">True</property> + <child> + <object class="GtkAspectFrame" id="aspectframe1"> + <property name="width_request">320</property> + <property name="height_request">240</property> + <property name="visible">True</property> + <property name="label_xalign">0</property> + <property name="shadow_type">out</property> + <property name="ratio">1.3300000429153442</property> + <child> + <object class="GtkImage" id="image1"> + <property name="width_request">320</property> + <property name="height_request">240</property> + <property name="visible">True</property> + <property name="stock">gtk-missing-image</property> + </object> + </child> + </object> + <packing> + <property name="position">0</property> + </packing> + </child> + <child> + <object class="GtkVBox" id="vbox2"> + <property name="visible">True</property> + <child> + <object class="GtkHBox" id="hbox2"> + <property name="visible">True</property> + <child> + <object class="GtkLabel" id="label5"> + <property name="visible">True</property> + <property name="label" translatable="yes">Started:</property> + </object> + <packing> + <property name="expand">False</property> + <property name="fill">False</property> + <property name="position">0</property> + </packing> + </child> + <child> + <object class="GtkEntry" id="entry1"> + <property name="visible">True</property> + <property name="can_focus">True</property> + <property name="editable">False</property> + <property name="invisible_char">●</property> + <property name="width_chars">12</property> + <property name="text" translatable="yes">Sat 14:22:25</property> + </object> + <packing> + <property name="expand">False</property> + <property name="fill">False</property> + <property name="position">1</property> + </packing> + </child> + </object> + <packing> + <property name="expand">False</property> + <property name="position">0</property> + </packing> + </child> + <child> + <object class="GtkToggleButton" id="togglebutton1"> + <property name="label" translatable="yes">Enabled</property> + <property name="visible">True</property> + <property name="can_focus">True</property> + <property name="receives_default">True</property> + </object> + <packing> + <property name="expand">False</property> + <property name="position">1</property> + </packing> + </child> + <child> + <object class="GtkButton" id="button1"> + <property name="label" translatable="yes">Delete</property> + <property name="visible">True</property> + <property name="can_focus">True</property> + <property name="receives_default">True</property> + <property name="image">image2</property> + </object> + <packing> + <property name="expand">False</property> + <property name="position">2</property> + </packing> + </child> + <child> + <object class="GtkCheckButton" id="checkbutton1"> + <property name="label" translatable="yes">Pin to top</property> + <property name="visible">True</property> + <property name="can_focus">True</property> + <property name="receives_default">False</property> + <property name="draw_indicator">True</property> + </object> + <packing> + <property name="expand">False</property> + <property name="position">3</property> + </packing> + </child> + </object> + <packing> + <property name="position">1</property> + </packing> + </child> + </object> + </child> + </object> + <packing> + <property name="position">0</property> + </packing> + </child> + <child> + <placeholder/> + </child> + <child> + <placeholder/> + </child> + </object> + </child> </object> </child> </object> @@ -73,92 +299,14 @@ </child> </object> <packing> - <property name="x">373</property> - <property name="y">23</property> - </packing> - </child> - <child> - <object class="GtkToggleButton" id="liveVideoEnabled"> - <property name="label" translatable="yes">Enabled</property> - <property name="width_request">110</property> - <property name="height_request">36</property> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="receives_default">True</property> - <property name="active">True</property> - <signal name="toggled" handler="on_liveVideoEnabled_toggled"/> - </object> - <packing> - <property name="x">20</property> - <property name="y">307</property> - </packing> - </child> - <child> - <object class="GtkSpinButton" id="liveFrameRate"> - <property name="width_request">52</property> - <property name="height_request">25</property> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="invisible_char">●</property> - <property name="numeric">True</property> - </object> - <packing> - <property name="x">96</property> - <property name="y">360</property> - </packing> - </child> - <child> - <object class="GtkLabel" id="label1"> - <property name="width_request">75</property> - <property name="height_request">20</property> - <property name="visible">True</property> - <property name="label" translatable="yes">Frame rate</property> - </object> - <packing> - <property name="x">16</property> - <property name="y">363</property> - </packing> - </child> - <child> - <object class="GtkComboBox" id="videoSource"> - <property name="width_request">100</property> - <property name="visible">True</property> - </object> - <packing> - <property name="x">114</property> - <property name="y">405</property> - </packing> - </child> - <child> - <object class="GtkLabel" id="label4"> - <property name="width_request">85</property> - <property name="height_request">20</property> - <property name="visible">True</property> - <property name="label" translatable="yes">Input source</property> - </object> - <packing> - <property name="x">20</property> - <property name="y">407</property> - </packing> - </child> - <child> - <object class="GtkScrolledWindow" id="scrolledwindow1"> - <property name="width_request">336</property> - <property name="height_request">310</property> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="hscrollbar_policy">automatic</property> - <property name="vscrollbar_policy">automatic</property> - <child> - <placeholder/> - </child> - </object> - <packing> - <property name="x">383</property> - <property name="y">323</property> + <property name="position">1</property> </packing> </child> </object> </child> </object> + <object class="GtkImage" id="image2"> + <property name="visible">True</property> + <property name="stock">gtk-delete</property> + </object> </interface>