Example #1
0
class WidgetsWrapper(object):
    def __init__(self):
        self.widgets = gtk.glade.XML('mpl_with_glade.glade')
        self.widgets.signal_autoconnect(GladeHandlers.__dict__)

        self['windowMain'].connect('destroy', lambda x: gtk.main_quit())
        self['windowMain'].move(10, 10)
        self.figure = Figure(figsize=(8, 6), dpi=72)
        self.axis = self.figure.add_subplot(111)

        t = arange(0.0, 3.0, 0.01)
        s = sin(2 * pi * t)
        self.axis.plot(t, s)
        self.axis.set_xlabel('time (s)')
        self.axis.set_ylabel('voltage')

        self.canvas = FigureCanvas(self.figure)  # a gtk.DrawingArea
        self.canvas.show()
        self.canvas.set_size_request(600, 400)
        self.canvas.set_events(gtk.gdk.BUTTON_PRESS_MASK
                               | gtk.gdk.KEY_PRESS_MASK
                               | gtk.gdk.KEY_RELEASE_MASK)
        self.canvas.set_flags(gtk.HAS_FOCUS | gtk.CAN_FOCUS)
        self.canvas.grab_focus()

        def keypress(widget, event):
            print('key press')

        def buttonpress(widget, event):
            print('button press')

        self.canvas.connect('key_press_event', keypress)
        self.canvas.connect('button_press_event', buttonpress)

        def onselect(xmin, xmax):
            print(xmin, xmax)

        span = SpanSelector(self.axis,
                            onselect,
                            'horizontal',
                            useblit=False,
                            rectprops=dict(alpha=0.5, facecolor='red'))

        self['vboxMain'].pack_start(self.canvas, True, True)
        self['vboxMain'].show()

        # below is optional if you want the navigation toolbar
        self.navToolbar = NavigationToolbar(self.canvas, self['windowMain'])
        self.navToolbar.lastDir = '/var/tmp/'
        self['vboxMain'].pack_start(self.navToolbar)
        self.navToolbar.show()

        sep = gtk.HSeparator()
        sep.show()
        self['vboxMain'].pack_start(sep, True, True)

        self['vboxMain'].reorder_child(self['buttonClickMe'], -1)

    def __getitem__(self, key):
        return self.widgets.get_widget(key)
Example #2
0
class WidgetsWrapper(object):
    def __init__(self):
        self.widgets = gtk.glade.XML('mpl_with_glade.glade')
        self.widgets.signal_autoconnect(GladeHandlers.__dict__)

        self['windowMain'].connect('destroy', lambda x: gtk.main_quit())
        self['windowMain'].move(10, 10)
        self.figure = Figure(figsize=(8, 6), dpi=72)
        self.axis = self.figure.add_subplot(111)

        t = arange(0.0, 3.0, 0.01)
        s = sin(2*pi*t)
        self.axis.plot(t, s)
        self.axis.set_xlabel('time (s)')
        self.axis.set_ylabel('voltage')

        self.canvas = FigureCanvas(self.figure)  # a gtk.DrawingArea
        self.canvas.show()
        self.canvas.set_size_request(600, 400)
        self.canvas.set_events(
            gtk.gdk.BUTTON_PRESS_MASK |
            gtk.gdk.KEY_PRESS_MASK |
            gtk.gdk.KEY_RELEASE_MASK
            )
        self.canvas.set_flags(gtk.HAS_FOCUS | gtk.CAN_FOCUS)
        self.canvas.grab_focus()

        def keypress(widget, event):
            print('key press')

        def buttonpress(widget, event):
            print('button press')

        self.canvas.connect('key_press_event', keypress)
        self.canvas.connect('button_press_event', buttonpress)

        def onselect(xmin, xmax):
            print(xmin, xmax)

        span = SpanSelector(self.axis, onselect, 'horizontal', useblit=False,
                            rectprops=dict(alpha=0.5, facecolor='red'))

        self['vboxMain'].pack_start(self.canvas, True, True)
        self['vboxMain'].show()

        # below is optional if you want the navigation toolbar
        self.navToolbar = NavigationToolbar(self.canvas, self['windowMain'])
        self.navToolbar.lastDir = '/var/tmp/'
        self['vboxMain'].pack_start(self.navToolbar)
        self.navToolbar.show()

        sep = gtk.HSeparator()
        sep.show()
        self['vboxMain'].pack_start(sep, True, True)

        self['vboxMain'].reorder_child(self['buttonClickMe'], -1)

    def __getitem__(self, key):
        return self.widgets.get_widget(key)
Example #3
0
class template:
    def __init__(self):
        self.builder = gtk.Builder()
        self.builder.add_from_file(os.path.splitext(__file__)[0]+".glade")
        self.window = self.builder.get_object("window")

        dic = {
            "on_toolbutton_refresh_clicked" : self.generate_testdata,
            "on_button1_clicked" : self.generate_testdata,
            "on_vboxMain_button_press_event" : self.button_press_event,
            "on_vboxMain_button_release_event" : self.button_release_event,
            "on_vboxMain_drag" : self.drag_begin,
            "on_vboxMain_motion_notify_event" : self.drag_begin,
            "on_toolbar_clear_clicked" : self.clear_selections,
            "on_toolbar_zoomin_clicked" : self.zoomin_time,
            "on_toolbar_zoomout_clicked" : self.zoomout_time,
            "on_go_back_clicked" : self.go_back,
            "on_go_forward_clicked" : self.go_forward,
            "on_toolbutton_preferences_clicked" : self.preferences_open,
            "on_button_pref_apply_activate" : self.pref_apply,
            "set_channel_groups" : self.set_channel_groups,

            }

        self.builder.connect_signals(dic)
        self.create_draw_frame('none')
        self.space = 0
        self.generate_testdata(None)

    def create_draw_frame(self,widget):
        self.fig = Figure(figsize=[100,100], dpi=72)
        self.canvas = FigureCanvas(self.fig)
        self.canvas.connect("scroll_event", self.scroll_event)
        #self.canvas.connect('button_press_event', self.button_press_event)
        self.canvas.show()
        self.figure = self.canvas.figure
        self.axes = self.fig.add_axes([0.045, 0.05, 0.93, 0.925], axisbg='#FFFFCC')

        self.vb = self.builder.get_object("vboxMain")
        self.vb.pack_start(self.canvas, gtk.TRUE, gtk.TRUE)
        self.vb.show()

    def preferences_open(self,widget):
        self.win_prefs = self.builder.get_object("window_prefs")
        self.win_prefs.show()
        self.channel_tree(None)

    def scroll_event(self, widget, event):
        if event.direction == gdk.SCROLL_UP:
            direction = 1
            self.space = self.space + .1*self.scalefact
        else:
            direction = -1
            self.space = self.space - .1*self.scalefact
        if self.space < 0:
            self.space = 0
        print 'space', self.space
        print (arange(0,size(self.data2plot,1))*(self.space))
        self.space_data()
        self.redraw(None)
        curpos = self.axes.get_position()
        l1 = curpos.x0
        b1 = curpos.y0
        w1 = curpos.x1
        h1 = curpos.y1

    def space_data(self):
        self.data2plot = self.data[self.tstart:self.tstop,self.chanind] + \
        (arange(0,size(self.data[self.tstart:self.tstop,self.chanind],1)) * \
        (self.space))



    def get_cursor_position(self,event):
        ap = self.axes.get_position()
        x,y = self.canvas.get_width_height()
        posx = ((event.x/x)-ap.x0)*(1/(ap.x1-ap.x0))
        posy = ((event.y/y)-(1-ap.y0))*(1/(ap.y0-ap.y1))
        self.sx = (posx*(self.time[-1]-self.time[0]))+self.time[0]
        self.sy = (posy*(self.data2plot.max()-self.data2plot.min()))+self.data2plot.min()
        print self.sx, self.sy

    def button_press_event(self,widget,event):
        self.get_cursor_position(event)
        print 'button pushed',event.button,event.type
        if event.type == gtk.gdk.BUTTON_PRESS:
            print "single click"
            if event.button == 1:
                #clicked line
                #self.axes.axvline(x=self.sx)
                self.xstart = self.sx
        elif event.type == gtk.gdk._2BUTTON_PRESS:
            print "double click"
            #highlight channel
            #self.axes.axhspan(self.sy-1, self.sy+1, xmin=0, xmax=1, color='yellow')

        elif event.type == gtk.gdk._3BUTTON_PRESS:
            print "triple click. ouch, you hurt your user."

        if event.type == gtk.gdk.BUTTON_PRESS and event.button == 2:
            print 'highlighting channel'
            self.axes.axhspan(self.sy-self.scalefact, \
            self.sy+self.scalefact, xmin=0, xmax=1, color='g')

        #refresh canvas
        self.canvas.draw()

    def button_release_event(self,widget,event):
        pass
        self.get_cursor_position(event)
        #print event#.button
        if event.type == gtk.gdk.BUTTON_RELEASE and event.button == 1:
            self.axes.axvspan(ymin=0, ymax=1, xmin=self.xstart, xmax=self.sx, color='b')
            try: self.selections = vstack((self.selections,[self.xstart,self.sx]))
            except AttributeError: self.selections = array([[self.xstart,self.sx]])
            print 'sels',self.selections
            self.canvas.draw()

    def clear_selections(self,widget):
        del self.selections
        self.redraw(None)

    def drag_begin(self,widget,event):
        pass
        #self.get_cursor_position(event)

    def redraw(self,widget):
        #print 'button press'
        print len(self.time),self.data2plot.shape
        self.color = 'black'
        self.axes.cla()
        self.axes = self.figure.axes[0]
        self.axes.plot(self.time, self.data2plot,color=self.color)
        self.axes.axis('tight')
        #self.axes.axis('off')
        try:
            print 'd',self.selections
            for i in self.selections:
                self.axes.axvspan(ymin=0, ymax=1, xmin=i[0], xmax=i[1], color='b')
        except:
            pass
        self.canvas.draw()

    def zoomin_time(self,widget):
        startind = self.tstart;
        stopind = self.tstop-((self.tstop-self.tstart)/2)
        self.check_scale(startind,stopind)

    def zoomout_time(self,widget):
        startind = self.tstart;
        stopind = self.tstop+((self.tstop-self.tstart)*2)
        self.check_scale(startind,stopind)

    def go_forward(self,widget):
        startind = ((self.tstop-self.tstart)/2)+self.tstart;
        stopind = ((self.tstop-self.tstart)/2)+self.tstop;
        self.check_scale(startind,stopind)

    def go_back(self,widget):
        startind = self.tstart-((self.tstop-self.tstart)/2);
        stopind = self.tstop-((self.tstop-self.tstart)/2);
        self.check_scale(startind,stopind)


    def check_scale(self,startind,stopind):
        print 'req',startind,stopind, self.tstart,self.tstop
        if startind < 0:
            startind = 0
            stopind = self.tstop
        if stopind > len(self.t):
            startind = self.tstart
            stopind = len(self.t)
        if stopind < 0:
            stopind = self.tstop
        print 'set',startind,stopind,self.tstart,self.tstop

        self.tstart = startind
        self.tstop = stopind
        self.time = self.t[self.tstart:self.tstop]
        self.data2plot = self.data[self.tstart:self.tstop,self.chanind]
        self.space_data()
        self.redraw(None)

    def page_down(self,widget):
        pass

    def channel_tree(self,widget):
        print('updating list')
        self.View = self.builder.get_object("treeview1")
        self.dataList = gtk.ListStore(str,str)
        self.AddListColumn('Number', 0)
        self.AddListColumn('Label', 1)

        for k in range(0,self.numchannels):
            iter = self.dataList.append([k,'label'+str(k)])

        self.View.set_model(self.dataList)
        print 'adding channels'

    def AddListColumn(self, title, columnId):
        column = gtk.TreeViewColumn(title, gtk.CellRendererText(), text=columnId)
        column.set_resizable(True)
        column.set_sort_column_id(columnId)
        self.View.append_column(column)
        self.View.get_selection().set_mode(gtk.SELECTION_MULTIPLE)


    def pref_apply(self, widget):
        liststore,iter = self.View.get_selection().get_selected_rows()
        self.chanind = []
        for i in iter:
            print i, liststore[i][1]
            self.chanind.append(int(liststore[i][0]))
            #print self.dataList.get_value(iter,0)
        print self.chanind
        self.space_data()
        self.redraw(None)

    def set_channel_groups(self,widget):
        print widget.get_label(), widget
        #for i in self.builder.get_object('vbox2').get_children():
            #if i.get_active() == True:
                #print(i)
                #print i.get_label()
        if widget.get_label() == 'meg' and widget.get_active() == True:
            #self.View.get_selection().select_all()
            #self.View.get_selection().select_all()
            self.View.get_selection().select_range(0,2)
        if widget.get_label() == 'Clear':
            self.View.get_selection().unselect_all()
        if widget.get_label() == 'all' and widget.get_active() == True:
            self.View.get_selection().select_all()





    def generate_testdata(self,widget):
        numpts = 10
        self.numchannels = 10
        self.t = arange(0,numpts, .01)
        self.data = zeros((len(self.t),self.numchannels))
        self.scalefact = 1e-9
        for i in arange(0,self.numchannels):
            r = random.randn()
            self.data[:,i] = float32((sin(2*0.32*pi*self.t*r) * sin(2*2.44*pi*self.t*r)))#+ self.space
        self.data = self.data * self.scalefact
        self.tstart = 0; self.tstop = len(self.t)
        self.time = copy(self.t[self.tstart:self.tstop])
        print self.tstart,self.tstop
        self.chanind = arange(0,self.numchannels)
        self.data2plot = self.data
        self.space_data()
        #self.time_view()
        self.redraw(None)




    def datahandler(data=None):
        pass
Example #4
0
class band_graph(gtk.VBox):
	def init(self):

		toolbar = gtk.Toolbar()

		toolbar.set_style(gtk.TOOLBAR_ICONS)
		toolbar.set_size_request(-1, 50)
		self.pack_start(toolbar, False, False, 0)

		tool_bar_pos=0
		save = gtk.ToolButton(gtk.STOCK_SAVE)
		save.connect("clicked", self.callback_save_image)
		toolbar.insert(save, tool_bar_pos)
		toolbar.show_all()
		tool_bar_pos=tool_bar_pos+1

		self.my_figure=Figure(figsize=(5,4), dpi=100)
		self.canvas = FigureCanvas(self.my_figure)  # a gtk.DrawingArea
		self.canvas.figure.patch.set_facecolor('white')
		self.canvas.set_size_request(600, 400)
		self.canvas.show()
		self.pack_start(self.canvas, False, False, 0)

		self.canvas.connect('key_press_event', self.on_key_press_event)

		self.show_all()

	def on_key_press_event(self,widget, event):
		keyname = gtk.gdk.keyval_name(event.keyval)
		if keyname == "c":
			if event.state == gtk.gdk.CONTROL_MASK:
				self.do_clip()

		self.canvas.draw()

	def do_clip(self):
		print "doing clip"
		snap = self.my_figure.canvas.get_snapshot()
		pixbuf = gtk.gdk.pixbuf_get_from_drawable(None, snap, snap.get_colormap(),0,0,0,0,snap.get_size()[0], snap.get_size()[1])
		clip = gtk.Clipboard()
		clip.set_image(pixbuf)

	def callback_save_image(self, widget):
		dialog = gtk.FileChooserDialog("Save plot",
                               None,
                               gtk.FILE_CHOOSER_ACTION_SAVE,
                               (gtk.STOCK_CANCEL, gtk.RESPONSE_CANCEL,
                                gtk.STOCK_SAVE, gtk.RESPONSE_OK))
		dialog.set_default_response(gtk.RESPONSE_OK)
		dialog.set_action(gtk.FILE_CHOOSER_ACTION_CREATE_FOLDER)

		filter = gtk.FileFilter()
		filter.set_name("png")
		filter.add_pattern("*.png")
		dialog.add_filter(filter)

		response = dialog.run()
		if response == gtk.RESPONSE_OK:
			self.my_figure.savefig(dialog.get_filename())

		elif response == gtk.RESPONSE_CANCEL:
		    print 'Closed'
		dialog.destroy()

	def set_data_file(self,file):
		self.optical_mode_file=os.path.join(os.getcwd(),"light_dump",file)

	def draw_graph(self):
		self.layer_end=[]
		self.layer_name=[]

		n=0
		self.my_figure.clf()
		ax1 = self.my_figure.add_subplot(111)
		ax2 = ax1.twinx()
		x_pos=0.0
		layer=0
		color =['r','g','b','y','o','r','g','b','y','o']
		start=0.0

		for i in range(0,epitaxy_get_layers()):
			if epitaxy_get_electrical_layer(i)=="none":
				start=start-epitaxy_get_width(i)
			else:
				break
		print "START=",start
		start=start*1e9

		x_pos=start
		for i in range(0,epitaxy_get_layers()):

			label=epitaxy_get_mat_file(i)
			layer_ticknes=epitaxy_get_width(i)
			layer_material=epitaxy_get_mat_file(i)

			delta=float(layer_ticknes)*1e9
			if epitaxy_get_electrical_layer(i)=="none":
				mat_file=os.path.join(os.getcwd(),'materials',layer_material,'mat.inp')
				myfile = open(mat_file)
				self.mat_file_lines = myfile.readlines()
				myfile.close()
			
				for ii in range(0, len(self.mat_file_lines)):
					self.mat_file_lines[ii]=self.mat_file_lines[ii].rstrip()

				lumo=-float(self.mat_file_lines[1])
				Eg=float(self.mat_file_lines[3])
			else:
				lines=[]
				if inp_load_file(lines,epitaxy_get_electrical_layer(i)+".inp")==True:
					lumo=-float(inp_search_token_value(lines, "#Xi"))
					Eg=float(inp_search_token_value(lines, "#Eg"))

			x = [x_pos,x_pos+delta,x_pos+delta,x_pos]

			lumo_delta=lumo-0.1
			h**o=lumo-Eg
			homo_delta=h**o-0.1
			if Eg==0.0:
				lumo_delta=-7.0
				h**o=0.0
			lumo_shape = [lumo,lumo,lumo_delta,lumo_delta]
			x_pos=x_pos+delta
			self.layer_end.append(x_pos)
			self.layer_name.append(layer_material)
			ax2.fill(x,lumo_shape, color[layer],alpha=0.4)
			ax2.text(x_pos-delta/1.5, lumo-0.4, epitaxy_get_name(i))

			if h**o!=0.0:
				homo_shape = [h**o,h**o,homo_delta,homo_delta]
				ax2.fill(x,homo_shape, color[layer],alpha=0.4)

			layer=layer+1

			n=n+1

		state=plot_state()
		get_plot_file_info(state,self.optical_mode_file)
		#summary="<big><b>"+self.store[path[0]][0]+"</b></big>\n"+"\ntitle: "+state.title+"\nx axis: "+state.x_label+" ("+latex_to_pygtk_subscript(state.x_units)+")\ny axis: "++" ("+latex_to_pygtk_subscript(state.y_units)+")\n\n<big><b>Double click to open</b></big>"

		print "ROD!!!!",state.y_label,self.optical_mode_file
		ax1.set_ylabel(state.y_label)
		ax1.set_xlabel('Position (nm)')
		ax2.set_ylabel('Energy (eV)')
		ax2.set_xlim([start, x_pos])
		#ax2.axis(max=)#autoscale(enable=True, axis='x', tight=None)
		loaded=False

		if os.path.isfile("light_dump.zip"):
			zf = zipfile.ZipFile("light_dump.zip", 'r')
			lines = zf.read(self.optical_mode_file).split("\n")
			zf.close()
			loaded=True
		elif os.path.isfile(self.optical_mode_file):
			print "I want to load",self.optical_mode_file
			f = open(self.optical_mode_file)
			lines = f.readlines()
			f.close()
			loaded=True
		
		if loaded==True:
			xx=[]
			yy=[]
			zz=[]
			lines_to_xyz(xx,yy,zz,lines)
			t = asarray(xx)
			s = asarray(yy)

			t=t*1e9
			ax1.plot(t,s, 'black', linewidth=3 ,alpha=0.5)

			

		self.my_figure.tight_layout()
class Gtk_NetworkCanvas:
    """Gtk_NetworkCanvas class.
    This class contains the canvas to draw the topology. It implements event listener and zoom.

    Parameters
    ----------
    canvas : the gtk canvas to draw
    adjustement : used for zoom scroll bar
    zoom_scale : a scroll bar to zoom
    redraw : a button to redraw the graph
    popup : a popup for interaction on right click
    bRefresh : bool. if True enable refresh with do_refresh function
    corners : the limit of the canvas drawing area
    press : bool. True if mouse click on canvas (used for zoom)
    x_old, y_old : position for zoom
    """

    def __init__(self):
        fig = plt.figure(num=None, facecolor='w', edgecolor='k')
        plt.axis('off')
        plt.subplots_adjust(left=0., right=1., bottom=0., top=1., wspace=0.2, hspace=0.2)
        self.canvas = FigureCanvas(fig)
        self.canvas.add_events(
            gtk.gdk.EXPOSURE_MASK | gtk.gdk.LEAVE_NOTIFY_MASK | gtk.gdk.BUTTON_PRESS_MASK | gtk.gdk.POINTER_MOTION_MASK | gtk.gdk.POINTER_MOTION_HINT_MASK | gtk.gdk.BUTTON_RELEASE_MASK)
        self.canvas.connect("motion_notify_event", self.on_motion)
        self.canvas.connect("button-press-event", self.on_click)
        self.canvas.connect("button-release-event", self.on_release)
        self.canvas.connect("scroll-event", self.on_scroll)
        self.canvas.connect("leave-notify-event", self.on_lose_focus)

        self.adjustement = gtk.Adjustment(0.0, 0.0, 100.0, 1.0, 1.0, 1.0)
        self.adjustement_signal = self.adjustement.connect("value-changed", self.on_zoom_changed)
        self.zoom_scale = gtk.HScale(self.adjustement)
        self.zoom_scale.set_draw_value(False)
        self.zoom_value = 0.0

        self.redraw = gtk.Button("Redraw")
        self.redraw.connect("clicked", self.on_redraw)

        self.hbox = gtk.HBox()
        self.hbox.pack_start(self.zoom_scale, True, True, 0)
        self.hbox.pack_end(self.redraw, False, False, 0)

        self.vbox = gtk.VBox()
        self.vbox.pack_start(self.canvas, True, True, 0)
        self.vbox.pack_end(self.hbox, False, False, 0)

        self.popup = Gtk_NewtworkPopupMenu()
        self.bRefresh = True
        self.corners = None
        self.press = False
        self.x_old = 0
        self.y_old = 0

        self.bg_img = None

    def on_click(self, widget, event):
        """Event listener : click
        If double left click :
        - on edge, show edges rules
        - on firewall, show firewall conf
        - on interface, add note
        If left click :
        - on edge, show message
        - on firewall, show message interaction firewall
        - on interface, show message interaction interface
        - else move x/y limit drawing area
        If right click :
        - on edge, show edge menu
        - on firewall, show firewall menu
        - on interface, show interface menu
        - else show canvas menu
        """
        if event.button == 1 and event.type == gtk.gdk._2BUTTON_PRESS:
            dbl_click = False
            dbl_click |= self.on_dblclick_edge()
            dbl_click |= self.on_dblclick_node()
            if not dbl_click:
                Gtk_Main.Gtk_Main().lateral_pane.help_message.change_message(Gtk_Message.TOPOLOGY_MESSAGE)
        if event.button == 3 and event.type == gtk.gdk.BUTTON_PRESS:
            right_click = False
            right_click |= self.on_right_click_edge(event)
            right_click |= self.on_right_click_node(event)
            if not right_click:
                Gtk_Main.Gtk_Main().lateral_pane.help_message.change_message(Gtk_Message.ON_BACKGROUND_CLICK)
                self.popup.popup_clear(event)
        if event.button == 1 and event.type == gtk.gdk.BUTTON_PRESS:
            left_click = False
            left_click |= self.on_left_click_edge()
            left_click |= self.on_left_click_node()
            if not left_click:
                self.press = True
                self.x_old = event.x
                self.y_old = event.y
                Gtk_Main.Gtk_Main().lateral_pane.help_message.change_message(Gtk_Message.TOPOLOGY_MESSAGE)
        return True

    def on_dblclick_edge(self):
        """Show interface rules"""
        def get_firewall(x, y):
            if isinstance(x, Firewall):
                return x
            elif isinstance(y, Firewall):
                return y
            return None

        def get_ip(x, y):
            if isinstance(x, Ip):
                return x
            elif isinstance(y, Ip):
                return y
            return None

        g = NetworkGraph.NetworkGraph()
        for elem in g.graph.edges(data=True):
            edge = elem[2]['object']
            if edge.gtk_press:
                fw = get_firewall(elem[0], elem[1])
                ip = get_ip(elem[0], elem[1])
                result = []
                [result.append(acl) for acl in g.get_acl_list(src=ip, dst=None, firewall=fw)]
                [result.append(acl) for acl in g.get_acl_list(src=None, dst=ip, firewall=fw)]
                if not result:
                    Gtk_DialogBox("No rules found for this interface !")
                [Gtk_Main.Gtk_Main().notebook.add_interface_tab(acl) for acl in result]
                return True
        return False

    def on_dblclick_node(self):
        """Event listener, on double click node, if firewall show conf file else add note"""
        g = NetworkGraph.NetworkGraph()
        for k, v in g.graph.node.items():
            if v['object'].gtk_press and isinstance(v['object'].object, Firewall):
                Gtk_Main.Gtk_Main().notebook.add_conf_tab(v['object'].object.name, v['object'].object.hostname)
                return True
            if v['object'].gtk_press and isinstance(v['object'].object, Ip):
                self.popup.node = v['object']
                self.popup.on_add_note(None)
                return True
        return False

    def on_right_click_edge(self, event):
        """Event listener, on right click edge, popup menu showing acl list of related to this interface"""
        g = NetworkGraph.NetworkGraph()
        for elem in g.graph.edges(data=True):
            edge = elem[2]['object']
            if edge.gtk_press:
                self.popup.popup(elem, event, edge)
                edge.gtk_press = False
                return True
        return False

    def on_right_click_node(self, event):
        """Event listener, on right click node, show popup menu for node"""
        g = NetworkGraph.NetworkGraph()
        for k, v in g.graph.node.items():
            if v['object'].gtk_press:
                self.popup.popup(None, event, v['object'])
                v['object'].gtk_press = False
                return True
        return False

    def on_left_click_node(self):
        """Show node details"""
        g = NetworkGraph.NetworkGraph()
        for k, v in g.graph.node.items():
            if v['object'].gtk_press:
                Gtk_Main.Gtk_Main().lateral_pane.help_message.change_message(Gtk_Message.ON_CLICK_NODE)
                Gtk_Main.Gtk_Main().lateral_pane.details.clear()
                tmp_intf = [e[2]['object'].object for e in g.graph.edges(k, data=True)]
                for e in sorted(tmp_intf, key=lambda tmp_intf: tmp_intf.nameif):
                    message = "%s:\n- %s\n- %s" % (e.nameif, e.name, e.network.to_string())
                    for key, value in e.attributes.items():
                        message += "\n- %s : %s" % (key, value)
                    Gtk_Main.Gtk_Main().lateral_pane.details.add_row(message)
                    Gtk_Main.Gtk_Main().lateral_pane.focus_details()
                return True
        return False

    def on_left_click_edge(self):
        """If left click edge, show help message"""
        g = NetworkGraph.NetworkGraph()
        for edge in g.graph.edges():
            if g.graph[edge[0]][edge[1]]['object'].gtk_press:
                Gtk_Main.Gtk_Main().lateral_pane.help_message.change_message(Gtk_HelpMessage.Gtk_Message.ON_CLICK_EDGE)
                return True
        return False

    def on_motion(self, widget, event):
        """If not click node, then move axis"""
        if self.press and self.corners:
            xlim = list(plt.gca().get_xlim())
            ylim = list(plt.gca().get_ylim())
            x = (self.x_old - event.x) / (1. * self.canvas.window.get_size()[0] / (xlim[1] - xlim[0]))
            y = (event.y - self.y_old) / (1. * self.canvas.window.get_size()[1] / (ylim[1] - ylim[0]))
            self.x_old = event.x
            self.y_old = event.y
            self.axes_move(x, y, x, y)
        self.do_refresh()

    def refresh(self):
        """refresh function. This function is call periodically by do_refresh"""
        self.bRefresh = True

    def do_refresh(self):
        """Update the graph if bRefresh is True"""
        if self.bRefresh:
            self.bRefresh = False
            self.canvas.draw()
            gtk.timeout_add(30, self.refresh)

    def on_release(self, widget, event):
        """Event listener : release"""
        self.press = False

    def on_scroll(self, widget, event):
        """Event listener : scroll. Update zoom"""
        if event.direction == 0 and self.adjustement.get_value() < 99:
            self.adjustement.set_value(self.adjustement.get_value() + 1)
        elif event.direction == 1 and self.adjustement.get_value() > 0:
            self.adjustement.set_value(self.adjustement.get_value() - 1)

    def on_zoom_changed(self, widget):
        """Event listerner : HScale change. Update zoom"""
        if self.corners:
            im = None
            if self.bg_img:
                im = self.bg_img.get_children()[0]
            if widget.value != 0:
                zoom = (self.zoom_value - widget.value) * (self.corners[1][0] - self.corners[0][0]) / 200
                self.axes_zoom(-zoom, -zoom, zoom, zoom)
                if im:
                    dim = min(1. * self.canvas.window.get_size()[0] / len(im.properties()['data'][0]),
                              1. * self.canvas.window.get_size()[1] / len(im.properties()['data']))
                    corners = min(self.corners[1][0] - self.corners[0][0], self.corners[1][1] - self.corners[0][1])
                    im.set_zoom(im.get_zoom() - zoom * 2 * dim / corners)
            else:
                plt.gca().set_xlim((self.corners[0][0], self.corners[1][0]))
                plt.gca().set_ylim((self.corners[0][1], self.corners[1][1]))
                if im:
                    im.set_zoom(min(1. * self.canvas.window.get_size()[0] / len(im.properties()['data'][0]),
                                    1. * self.canvas.window.get_size()[1] / len(im.properties()['data'])))
            self.zoom_value = widget.value
            self.do_refresh()

    def on_lose_focus(self, widget, event):
        """Event listener : focus"""
        self.press = False
        NetworkGraph.NetworkGraph().node_click = False
        for node in NetworkGraph.NetworkGraph().graph.nodes(data=True):
            node[1]['object'].press = False
        for edge in NetworkGraph.NetworkGraph().graph.edges(data=True):
            edge[2]['object'].press = False
        self.do_refresh()

    def on_redraw(self, widget):
        """Event listener : button redraw"""
        self.draw()

    def axes_move(self, x0, y0, x1, y1):
        """Change axis position according to the drawing area limit.

        Parameters
        ----------
        x0 : float. x minimal value
        x1 : float. x maximal value
        y0 : float. y minimal value
        y1 : float. y maximal value
        """
        if self.corners:
            x = list(plt.gca().get_xlim())
            y = list(plt.gca().get_ylim())
            if ((x0 < 0 and x[0] + x0 >= self.corners[0][0]) or (x0 > 0 and x[0] + x0 < x[1])) and \
                    ((x1 > 0 and x[1] + x1 <= self.corners[1][0]) or (x1 < 0 and x[1] + x1 > x[0])):
                x[0] += x0
                x[1] += x1
            if ((y0 < 0 and y[0] + y0 >= self.corners[0][1]) or (y0 > 0 and y[0] + y0 < y[1])) and \
                    ((y1 > 0 and y[1] + y1 <= self.corners[1][1]) or (y1 < 0 and y[1] + y1 > y[0])):
                y[0] += y0
                y[1] += y1
            plt.gca().set_xlim((x[0], x[1]))
            plt.gca().set_ylim((y[0], y[1]))

    def axes_zoom(self, x0, y0, x1, y1):
        """Zoom axis position according to the drawing area limit.

        Parameters
        ----------
        x0 : float. x minimal value
        x1 : float. x maximal value
        y0 : float. y minimal value
        y1 : float. y maximal value
        """
        if self.corners:
            x = list(plt.gca().get_xlim())
            y = list(plt.gca().get_ylim())
            if (x0 < 0 and x[0] >= self.corners[0][0]) or (x0 > 0 and x[0] + x0 < x[1]):
                x[0] += x0
            if (x1 > 0 and x[1] <= self.corners[1][0]) or (x1 < 0 and x[1] - x1 > x[0]):
                x[1] += x1
            if (y0 < 0 and y[0] >= self.corners[0][1]) or (y0 > 0 and y[0] + y0 < y[1]):
                y[0] += y0
            if (y1 > 0 and y[1] <= self.corners[1][1]) or (y1 < 0 and y[1] - y1 > y[0]):
                y[1] += y1
            plt.gca().set_xlim((x[0], x[1]))
            plt.gca().set_ylim((y[0], y[1]))

    def background_image(self, file):
        """Set the file image as background image"""
        if self.bg_img:
            self.bg_img.remove()

        datafile = get_sample_data(file)
        img = plt.imread(datafile)
        im = OffsetImage(img)
        im.set_zoom(min(1. * self.canvas.window.get_size()[0] / len(im.properties()['data'][0]),
                        1. * self.canvas.window.get_size()[1] / len(im.properties()['data'])))
        self.bg_img = AnnotationBbox(im, (0.5, 0.5), xycoords='data', frameon=False)
        self.bg_img.set_zorder(-1)
        plt.gca().add_artist(self.bg_img)
        self.do_refresh()

    def draw(self):
        """Draw the netowrk graph and set limit corners"""
        g = NetworkGraph.NetworkGraph()
        g.layout_graph()
        g.draw(self.canvas)

        self.corners = (-0.05, -0.05), (1.05, 1.05)
        plt.gca().set_xlim((-0.05, 1.05))
        plt.gca().set_ylim((-0.05, 1.05))

        self.do_refresh()
class _Matplotlib:
  def __init__ (self, pp, progressbar):
    self.pp = pp
    self.pb = progressbar
    self.figure = pylab.figure ()
    self.canvas = FigureCanvas (self.figure)
    self.toolbar = NavigationToolbar (self.canvas, pp ["MainWindow"])
    self.pp ["BoxPlotArea"].pack_start (self.toolbar, expand = False, fill = False) 
    self.pp ["BoxPlotArea"].pack_start (self.canvas , expand = True, fill = True) 
    self.canvas.connect ("button_press_event", self.on_button_press_event)

    self.l = 0
    self.dataAreOld = True
    self.pathLength = None
    self.pathId = None
    self.dl = None

  def get_x_cursor_position(self,event):
    gca = self.figure.gca ()
    ap = gca.get_position ()
    xmin, xmax = gca.get_xbound ()
    x,y = self.canvas.get_width_height()
    posx = ((event.x/x)-ap.x0)*(1/(ap.x1-ap.x0))
    sx = (posx*(xmax - xmin)) + xmin
    return sx

  def on_button_press_event (self, w, event):
    if   not event.type == gtk.gdk._2BUTTON_PRESS \
      or not event.button == 1:
      return False
    l = self.get_x_cursor_position(event)
    self.pp ["PathScale"].set_value (l)
    return True

  def selectData (self, x, ys):
    self.x = x
    self.ys = ys
    if   not self.pathLength == self.pp.pathLength \
      or not self.pathId     == self.pp.pathId \
      or not self.dl         == self.pp.dl:
      self.dataAreOld = True
      self.pathId = self.pp.pathId
      self.pathLength = self.pp.pathLength
      self.dl = self.pp.dl
      self.l = 0
      self.datas = list ()
    else:
      self.dataAreOld = False

  def init_pulse (self):
    if self.dataAreOld:
      self.pb.set_text ("Generating datas...")
      self.pb.set_fraction (0)
      glib.idle_add (self.getData_pulse)
    else:
      glib.idle_add (self.genPlot_pulse)
    return False

  def getData_pulse (self):
    d = [ self.l, ]
    d.extend (self.pp.client.problem.configAtParam (self.pathId, self.l))
    self.datas.append (d)
    self.l += self.dl
    if self.l < self.pathLength:
      self.pb.set_fraction (self.l / self.pathLength)
      return True
    else:
      self.pb.set_fraction (1)
      glib.idle_add (self.genPlot_pulse)
      return False

  def genPlot_pulse (self):
    self.pb.set_text ("Generating plots...")
    self.npdatas = np.matrix (self.datas)
    self.figure.clf ()
    gca = pylab.gca ()
    for elt in self.ys:
      pylab.plot (self.npdatas [:,self.x[1]], self.npdatas [:,elt[1]], label=elt[0])
    gca.set_xlabel (self.x[0])
    pylab.legend (loc='best')
    self.canvas.draw ()
    self.pb.set_text ("Idle")
    return False
Example #7
0
class Gtk_NetworkCanvas:
    """Gtk_NetworkCanvas class.
    This class contains the canvas to draw the topology. It implements event listener and zoom.

    Parameters
    ----------
    canvas : the gtk canvas to draw
    adjustement : used for zoom scroll bar
    zoom_scale : a scroll bar to zoom
    redraw : a button to redraw the graph
    popup : a popup for interaction on right click
    bRefresh : bool. if True enable refresh with do_refresh function
    corners : the limit of the canvas drawing area
    press : bool. True if mouse click on canvas (used for zoom)
    x_old, y_old : position for zoom
    """
    def __init__(self):
        fig = plt.figure(num=None, facecolor='w', edgecolor='k')
        plt.axis('off')
        plt.subplots_adjust(left=0.,
                            right=1.,
                            bottom=0.,
                            top=1.,
                            wspace=0.2,
                            hspace=0.2)
        self.canvas = FigureCanvas(fig)
        self.canvas.add_events(gtk.gdk.EXPOSURE_MASK
                               | gtk.gdk.LEAVE_NOTIFY_MASK
                               | gtk.gdk.BUTTON_PRESS_MASK
                               | gtk.gdk.POINTER_MOTION_MASK
                               | gtk.gdk.POINTER_MOTION_HINT_MASK
                               | gtk.gdk.BUTTON_RELEASE_MASK)
        self.canvas.connect("motion_notify_event", self.on_motion)
        self.canvas.connect("button-press-event", self.on_click)
        self.canvas.connect("button-release-event", self.on_release)
        self.canvas.connect("scroll-event", self.on_scroll)
        self.canvas.connect("leave-notify-event", self.on_lose_focus)

        self.adjustement = gtk.Adjustment(0.0, 0.0, 100.0, 1.0, 1.0, 1.0)
        self.adjustement_signal = self.adjustement.connect(
            "value-changed", self.on_zoom_changed)
        self.zoom_scale = gtk.HScale(self.adjustement)
        self.zoom_scale.set_draw_value(False)
        self.zoom_value = 0.0

        self.redraw = gtk.Button("Redraw")
        self.redraw.connect("clicked", self.on_redraw)

        self.hbox = gtk.HBox()
        self.hbox.pack_start(self.zoom_scale, True, True, 0)
        self.hbox.pack_end(self.redraw, False, False, 0)

        self.vbox = gtk.VBox()
        self.vbox.pack_start(self.canvas, True, True, 0)
        self.vbox.pack_end(self.hbox, False, False, 0)

        self.popup = Gtk_NewtworkPopupMenu()
        self.bRefresh = True
        self.corners = None
        self.press = False
        self.x_old = 0
        self.y_old = 0

        self.bg_img = None
        self.i = 1

    def on_click(self, widget, event):
        """Event listener : click
        If double left click :
        - on edge, show edges rules
        - on firewall, show firewall conf
        - on interface, add note
        If left click :
        - on edge, show message
        - on firewall, show message interaction firewall
        - on interface, show message interaction interface
        - else move x/y limit drawing area
        If right click :
        - on edge, show edge menu
        - on firewall, show firewall menu
        - on interface, show interface menu
        - else show canvas menu
        """
        if event.button == 1 and event.type == gtk.gdk._2BUTTON_PRESS:
            dbl_click = False
            dbl_click |= self.on_dblclick_edge()
            dbl_click |= self.on_dblclick_node()
            if not dbl_click:
                Gtk_Main.Gtk_Main().lateral_pane.help_message.change_message(
                    Gtk_Message.TOPOLOGY_MESSAGE)
        if event.button == 3 and event.type == gtk.gdk.BUTTON_PRESS:
            right_click = False
            right_click |= self.on_right_click_edge(event)
            right_click |= self.on_right_click_node(event)
            if not right_click:
                Gtk_Main.Gtk_Main().lateral_pane.help_message.change_message(
                    Gtk_Message.ON_BACKGROUND_CLICK)
                self.popup.popup_clear(event)
        if event.button == 1 and event.type == gtk.gdk.BUTTON_PRESS:
            left_click = False
            left_click |= self.on_left_click_edge()
            left_click |= self.on_left_click_node()
            if not left_click:
                self.press = True
                self.x_old = event.x
                self.y_old = event.y
                Gtk_Main.Gtk_Main().lateral_pane.help_message.change_message(
                    Gtk_Message.TOPOLOGY_MESSAGE)
        return True

    def on_dblclick_edge(self):
        """Show interface rules"""
        def get_firewall(x, y):
            if isinstance(x, Firewall):
                return x
            elif isinstance(y, Firewall):
                return y
            return None

        def get_ip(x, y):
            if isinstance(x, Ip):
                return x
            elif isinstance(y, Ip):
                return y
            return None

        g = NetworkGraph.NetworkGraph()
        for elem in g.graph.edges(data=True):
            edge = elem[2]['object']
            if edge.gtk_press:
                fw = get_firewall(elem[0], elem[1])
                ip = get_ip(elem[0], elem[1])
                result = []
                [
                    result.append(acl)
                    for acl in g.get_acl_list(src=ip, dst=None, firewall=fw)
                ]
                [
                    result.append(acl)
                    for acl in g.get_acl_list(src=None, dst=ip, firewall=fw)
                ]
                if not result:
                    Gtk_DialogBox("No rules found for this interface !")
                [
                    Gtk_Main.Gtk_Main().notebook.add_interface_tab(acl)
                    for acl in result
                ]
                return True
        return False

    def on_dblclick_node(self):
        """Event listener, on double click node, if firewall show conf file else add note"""
        g = NetworkGraph.NetworkGraph()
        for k, v in g.graph.node.items():
            if v['object'].gtk_press and isinstance(v['object'].object,
                                                    Firewall):
                Gtk_Main.Gtk_Main().notebook.add_conf_tab(
                    v['object'].object.name, v['object'].object.hostname)
                return True
            if v['object'].gtk_press and isinstance(v['object'].object, Ip):
                self.popup.node = v['object']
                self.popup.on_add_note(None)
                return True
        return False

    def on_right_click_edge(self, event):
        """Event listener, on right click edge, popup menu showing acl list of related to this interface"""
        g = NetworkGraph.NetworkGraph()
        for elem in g.graph.edges(data=True):
            edge = elem[2]['object']
            if edge.gtk_press:
                self.popup.popup(elem, event, edge)
                edge.gtk_press = False
                return True
        return False

    def on_right_click_node(self, event):
        """Event listener, on right click node, show popup menu for node"""
        g = NetworkGraph.NetworkGraph()
        for k, v in g.graph.node.items():
            if v['object'].gtk_press:
                self.popup.popup(None, event, v['object'])
                v['object'].gtk_press = False
                return True
        return False

    def on_left_click_node(self):
        """Show node details"""
        g = NetworkGraph.NetworkGraph()
        for k, v in g.graph.node.items():
            if v['object'].gtk_press:
                Gtk_Main.Gtk_Main().lateral_pane.help_message.change_message(
                    Gtk_Message.ON_CLICK_NODE)
                Gtk_Main.Gtk_Main().lateral_pane.details.clear()
                tmp_intf = [
                    e[2]['object'].object for e in g.graph.edges(k, data=True)
                ]
                if isinstance(tmp_intf, Interface):
                    for e in sorted(tmp_intf,
                                    key=lambda tmp_intf: tmp_intf.nameif):
                        message = "%s:\n- %s\n- %s" % (e.nameif, e.name,
                                                       e.network.to_string())
                        for key, value in e.attributes.items():
                            message += "\n- %s : %s" % (key, value)
                        Gtk_Main.Gtk_Main().lateral_pane.details.add_row(
                            message)
                        Gtk_Main.Gtk_Main().lateral_pane.focus_details()
                    return True
                if isinstance(v['object'].object, Route_info):
                    lateral_pane = Gtk_Main.Gtk_Main().lateral_pane
                    notebook_routes = Gtk_Main.Gtk_Main(
                    ).lateral_pane.notebook_routes
                    treeview_routes = Gtk_Main.Gtk_Main(
                    ).lateral_pane.routes_tab_treeview
                    scrolled_window = lateral_pane.routes_tab_treeview.scrolled_window
                    data = v['object'].object.data
                    notebook_routes.notebook.set_tab_label(
                        scrolled_window,
                        gtk.Label('Networks reached by ' +
                                  v['object'].object.iface.nameif))
                    treeview_routes.clear()

                    for gateway, networks in data.iteritems():
                        parent = treeview_routes.add_row(None,
                                                         gateway,
                                                         foreground='black',
                                                         background='grey')
                        for network in networks:
                            treeview_routes.add_row(parent, network)

                    if lateral_pane.vpane.get_child1(
                    ) == lateral_pane.notebook_path.notebook:
                        lateral_pane.vpane.remove(
                            lateral_pane.notebook_path.notebook)
                    elif lateral_pane.vpane.get_child1(
                    ) == lateral_pane.notebook_details.notebook:
                        lateral_pane.vpane.remove(
                            lateral_pane.notebook_details.notebook)
                    lateral_pane.vpane.pack1(
                        lateral_pane.notebook_routes.notebook, True, False)
                    lateral_pane.vpane.pack2(lateral_pane.help_message.eb,
                                             True, False)
                    Gtk_Main.Gtk_Main().hpaned.set_position(
                        4 * Gtk_Main.Gtk_Main().window.get_size()[0] / 5)
                    lateral_pane.vpane.show_all()

        return False

    def on_left_click_edge(self):
        """If left click edge, show help message"""
        g = NetworkGraph.NetworkGraph()
        for edge in g.graph.edges():
            if g.graph[edge[0]][edge[1]]['object'].gtk_press:
                Gtk_Main.Gtk_Main().lateral_pane.help_message.change_message(
                    Gtk_HelpMessage.Gtk_Message.ON_CLICK_EDGE)
                return True
        return False

    def on_motion(self, widget, event):
        """If not click node, then move axis"""
        if self.press and self.corners:
            xlim = list(plt.gca().get_xlim())
            ylim = list(plt.gca().get_ylim())
            x = (self.x_old -
                 event.x) / (1. * self.canvas.window.get_size()[0] /
                             (xlim[1] - xlim[0]))
            y = (event.y -
                 self.y_old) / (1. * self.canvas.window.get_size()[1] /
                                (ylim[1] - ylim[0]))
            self.x_old = event.x
            self.y_old = event.y
            self.axes_move(x, y, x, y)
        self.do_refresh()

    def refresh(self):
        """refresh function. This function is call periodically by do_refresh"""
        self.bRefresh = True

    def do_refresh(self):
        """Update the graph if bRefresh is True"""
        if self.bRefresh:
            self.bRefresh = False
            self.canvas.draw()
            gtk.timeout_add(30, self.refresh)

    def on_release(self, widget, event):
        """Event listener : release"""
        self.press = False

    def on_scroll(self, widget, event):
        """Event listener : scroll. Update zoom"""
        if event.direction == 0 and self.adjustement.get_value() < 99:
            self.adjustement.set_value(self.adjustement.get_value() + 1)
        elif event.direction == 1 and self.adjustement.get_value() > 0:
            self.adjustement.set_value(self.adjustement.get_value() - 1)

    def on_zoom_changed(self, widget):
        """Event listerner : HScale change. Update zoom"""
        if self.corners:
            im = None
            if self.bg_img:
                im = self.bg_img.get_children()[0]
            if widget.value != 0:
                zoom = (self.zoom_value - widget.value) * (
                    self.corners[1][0] - self.corners[0][0]) / 200
                self.axes_zoom(-zoom, -zoom, zoom, zoom)
                if im:
                    dim = min(
                        1. * self.canvas.window.get_size()[0] /
                        len(im.properties()['data'][0]),
                        1. * self.canvas.window.get_size()[1] /
                        len(im.properties()['data']))
                    corners = min(self.corners[1][0] - self.corners[0][0],
                                  self.corners[1][1] - self.corners[0][1])
                    im.set_zoom(im.get_zoom() - zoom * 2 * dim / corners)
            else:
                plt.gca().set_xlim((self.corners[0][0], self.corners[1][0]))
                plt.gca().set_ylim((self.corners[0][1], self.corners[1][1]))
                if im:
                    im.set_zoom(
                        min(
                            1. * self.canvas.window.get_size()[0] /
                            len(im.properties()['data'][0]),
                            1. * self.canvas.window.get_size()[1] /
                            len(im.properties()['data'])))
            self.zoom_value = widget.value
            self.do_refresh()

    def on_lose_focus(self, widget, event):
        """Event listener : focus"""
        self.press = False
        NetworkGraph.NetworkGraph().node_click = False
        for node in NetworkGraph.NetworkGraph().graph.nodes(data=True):
            node[1]['object'].press = False
        for edge in NetworkGraph.NetworkGraph().graph.edges(data=True):
            edge[2]['object'].press = False
        self.do_refresh()

    def on_redraw(self, widget):
        """Event listener : button redraw"""
        self.draw()

    def axes_move(self, x0, y0, x1, y1):
        """Change axis position according to the drawing area limit.

        Parameters
        ----------
        x0 : float. x minimal value
        x1 : float. x maximal value
        y0 : float. y minimal value
        y1 : float. y maximal value
        """
        if self.corners:
            x = list(plt.gca().get_xlim())
            y = list(plt.gca().get_ylim())
            if ((x0 < 0 and x[0] + x0 >= self.corners[0][0]) or (x0 > 0 and x[0] + x0 < x[1])) and \
                    ((x1 > 0 and x[1] + x1 <= self.corners[1][0]) or (x1 < 0 and x[1] + x1 > x[0])):
                x[0] += x0
                x[1] += x1
            if ((y0 < 0 and y[0] + y0 >= self.corners[0][1]) or (y0 > 0 and y[0] + y0 < y[1])) and \
                    ((y1 > 0 and y[1] + y1 <= self.corners[1][1]) or (y1 < 0 and y[1] + y1 > y[0])):
                y[0] += y0
                y[1] += y1
            plt.gca().set_xlim((x[0], x[1]))
            plt.gca().set_ylim((y[0], y[1]))

    def axes_zoom(self, x0, y0, x1, y1):
        """Zoom axis position according to the drawing area limit.

        Parameters
        ----------
        x0 : float. x minimal value
        x1 : float. x maximal value
        y0 : float. y minimal value
        y1 : float. y maximal value
        """
        if self.corners:
            x = list(plt.gca().get_xlim())
            y = list(plt.gca().get_ylim())
            if (x0 < 0
                    and x[0] >= self.corners[0][0]) or (x0 > 0
                                                        and x[0] + x0 < x[1]):
                x[0] += x0
            if (x1 > 0
                    and x[1] <= self.corners[1][0]) or (x1 < 0
                                                        and x[1] - x1 > x[0]):
                x[1] += x1
            if (y0 < 0
                    and y[0] >= self.corners[0][1]) or (y0 > 0
                                                        and y[0] + y0 < y[1]):
                y[0] += y0
            if (y1 > 0
                    and y[1] <= self.corners[1][1]) or (y1 < 0
                                                        and y[1] - y1 > y[0]):
                y[1] += y1
            plt.gca().set_xlim((x[0], x[1]))
            plt.gca().set_ylim((y[0], y[1]))

    def background_image(self, file):
        """Set the file image as background image"""
        if self.bg_img:
            self.bg_img.remove()

        datafile = get_sample_data(file)
        img = plt.imread(datafile)
        im = OffsetImage(img)
        im.set_zoom(
            min(
                1. * self.canvas.window.get_size()[0] /
                len(im.properties()['data'][0]),
                1. * self.canvas.window.get_size()[1] /
                len(im.properties()['data'])))
        self.bg_img = AnnotationBbox(im, (0.5, 0.5),
                                     xycoords='data',
                                     frameon=False)
        self.bg_img.set_zorder(-1)
        plt.gca().add_artist(self.bg_img)
        self.do_refresh()

    def draw(self):
        """Draw the netowrk graph and set limit corners"""
        g = NetworkGraph.NetworkGraph()
        g.layout_graph()
        g.draw(self.canvas)

        self.corners = (-0.05, -0.05), (1.05, 1.05)
        plt.gca().set_xlim((-0.05, 1.05))
        plt.gca().set_ylim((-0.05, 1.05))

        self.do_refresh()
class _Matplotlib:
    def __init__(self, pp, progressbar):
        self.pp = pp
        self.pb = progressbar
        self.figure = pylab.figure()
        self.canvas = FigureCanvas(self.figure)
        self.toolbar = NavigationToolbar(self.canvas, pp["MainWindow"])
        self.pp["BoxPlotArea"].pack_start(self.toolbar,
                                          expand=False,
                                          fill=False)
        self.pp["BoxPlotArea"].pack_start(self.canvas, expand=True, fill=True)
        self.canvas.connect("button_press_event", self.on_button_press_event)

        self.l = 0
        self.dataAreOld = True
        self.pathLength = None
        self.pathId = None
        self.dl = None

    def get_x_cursor_position(self, event):
        gca = self.figure.gca()
        ap = gca.get_position()
        xmin, xmax = gca.get_xbound()
        x, y = self.canvas.get_width_height()
        posx = ((event.x / x) - ap.x0) * (1 / (ap.x1 - ap.x0))
        sx = (posx * (xmax - xmin)) + xmin
        return sx

    def on_button_press_event(self, w, event):
        if   not event.type == gtk.gdk._2BUTTON_PRESS \
          or not event.button == 1:
            return False
        l = self.get_x_cursor_position(event)
        self.pp["PathScale"].set_value(l)
        return True

    def selectData(self, x, ys):
        self.x = x
        self.ys = ys
        if   not self.pathLength == self.pp.pathLength \
          or not self.pathId     == self.pp.pathId \
          or not self.dl         == self.pp.dl:
            self.dataAreOld = True
            self.pathId = self.pp.pathId
            self.pathLength = self.pp.pathLength
            self.dl = self.pp.dl
            self.l = 0
            self.datas = list()
        else:
            self.dataAreOld = False

    def init_pulse(self):
        if self.dataAreOld:
            self.pb.set_text("Generating datas...")
            self.pb.set_fraction(0)
            glib.idle_add(self.getData_pulse)
        else:
            glib.idle_add(self.genPlot_pulse)
        return False

    def getData_pulse(self):
        d = [
            self.l,
        ]
        d.extend(self.pp.client.problem.configAtParam(self.pathId, self.l))
        self.datas.append(d)
        self.l += self.dl
        if self.l < self.pathLength:
            self.pb.set_fraction(self.l / self.pathLength)
            return True
        else:
            self.pb.set_fraction(1)
            glib.idle_add(self.genPlot_pulse)
            return False

    def genPlot_pulse(self):
        self.pb.set_text("Generating plots...")
        self.npdatas = np.matrix(self.datas)
        self.figure.clf()
        gca = pylab.gca()
        for elt in self.ys:
            pylab.plot(self.npdatas[:, self.x[1]],
                       self.npdatas[:, elt[1]],
                       label=elt[0])
        gca.set_xlabel(self.x[0])
        pylab.legend(loc='best')
        self.canvas.draw()
        self.pb.set_text("Idle")
        return False
Example #9
0
class Plot(gtk.HBox):
    """ Base class for LivePlots. This class is an abstract class. In addition
    to inheriting from this class it is also required to take the following
    actions to achieve a functioning plot:
    Bla bla bla
    """
    
    def __init__(self, dpi=100, x_pixel_size=500, y_pixel_size=400):
        gtk.HBox.__init__(self)
        # If the class is being reinitialized, we need to remove the old plot
        [self.remove(child) for child in self.get_children()]
        self.vbox = gtk.VBox()
        self.pack_start(self.vbox)
        # this is bad with labels, I have to figure out why
        self.connect('size_allocate', self._full_update)

        self.fig = Figure(figsize=(float(x_pixel_size)/dpi,
                                   float(y_pixel_size)/dpi),
                          dpi=dpi)
        self.fig.set_facecolor('white')
        self.canvas = FigureCanvasGTKAgg(self.fig)
        self.ax = self.fig.add_subplot(111)
        self.vbox.pack_end(self.canvas)
        self.canvas.connect('button_press_event', self._on_mouse_click)

        self.first_update = True
        self.settings = {}
        self.n_lines = None
        #self.line_styles = None
        #self.line_colors = None
        self.lines = None
        self.saved_window_size = None
        self.background = None
        self.auto_x_scale = False
        self.auto_y_scale = False

    def _change_settings_common(self, number_of_lines, **kw):
        """ Change the subset of settings that are common for all plots """
        self.settings.update(kw)
        self.n_lines = number_of_lines
        self.line_styles = kw['line_styles'] if kw.has_key('line_styles')\
            else ['']*self.n_lines
        self.line_colors = kw['line_colors'] if kw.has_key('line_colors')\
            else self._get_colors(self.n_lines)
        self.lines = None
        self.background = None

        if self.settings['legends'] is not None:
            c = matplotlib.colors.ColorConverter()
            colors = [matplotlib.colors.rgb2hex(c.to_rgb(color))
                      for color in self.line_colors]
            self.legends = Legends(self.settings['legends'],
                                   colors,
                                   self.settings['legend_placement'],
                                   self.settings['legend_cols'])
            if self.settings['legend_placement'] == 'top':
                self.vbox.pack_end(self.legends, expand=False)
            else:
                self.pack_end(self.legends, expand=False)


    def _on_mouse_click(self, widget, event):
        if event.type == gtk.gdk.BUTTON_PRESS and event.button == 3:
            b1 = gtk.MenuItem("A button")
            b2 = gtk.MenuItem("Another")
            menu = gtk.Menu()
            menu.append(b1)
            menu.append(b2)
            b1.show()
            b2.show()
            menu.popup(None, None, None, event.button, event.time)

    def _update_bounds(self):
        return self._update_x_bounds() or self._update_y_bounds()

    def _update_x_bounds(self):
        if not self.auto_x_scale:
            return False

    def _update_y_bounds(self):
        modified = False
        if not self.auto_y_scale:
            return modified

        # Combine data (double loop), sort out None and get min/max
        y_min = min([inner for outer in self.y for inner in outer\
                         if inner is not None])
        y_max = max([inner for outer in self.y for inner in outer\
                         if inner is not None])
        delta = y_max - y_min
        if delta < 1E-10:
            return modified

        br = 0.2
        if y_min < self.settings['y_bounds'][0]:
            self.settings['y_bounds'] =\
                (y_min-br*delta, self.settings['y_bounds'][1])
            modified = True
        elif y_min > self.settings['y_bounds'][0] + br*delta:
            self.settings['y_bounds'] =\
                (y_min, self.settings['y_bounds'][1])
            modified = True

        if y_max > self.settings['y_bounds'][1]:
            self.settings['y_bounds'] =\
                (self.settings['y_bounds'][0], y_max+br*delta)
            modified = True
        elif y_max < self.settings['y_bounds'][1] - br*delta:
            self.settings['y_bounds'] =\
                (self.settings['y_bounds'][0], y_max)
            modified = True

        return modified

    def update_legends(self):
        if self.settings['legends'] is not None:
            for n in range(self.n_lines):
                point = self.y[n][-1]
                self.legends.set_legend_text(n, point)

    def _quick_update(self):
        if self.first_update:
            self._full_update()
            self.first_update = False
        self.canvas.restore_region(self.background)
        [line.set_ydata(y_data) for line, y_data in zip(self.lines, self.y)]
        [self.ax.draw_artist(line) for line in self.lines]
        # just redraw the axes rectangle
        self.canvas.blit(self.ax.bbox)

    def _full_update(self, widget=None, size=None):
        # This does not work properly, FIXME
        if widget is not None:
            if [size.width, size.height] != self.saved_window_size:
                self.saved_window_size = [size.width, size.height]
            else:
                return
        # Plot
        if self.first_update:
            plot = self.ax.semilogy if self.settings['logscale'] else self.ax.plot
            self.lines = [plot(x, y, style, color=color, animated=True)[0]
                          for x, y, color, style in
                          zip(self.x, self.y, self.line_colors, self.line_styles)]
            # Title and axis labels
            if self.settings['title'] is not None:
                self.ax.set_title(self.settings['title'])
            if self.settings['x_label'] is not None:
                self.ax.set_xlabel(self.settings['x_label'])
            if self.settings['y_label'] is not None:
                self.ax.set_ylabel(self.settings['y_label'])
            self.fig.subplots_adjust(left=0.25, bottom=0.15)
        else:
            [line.set_ydata(y_data) for line, y_data in zip(self.lines, self.y)]

        # Get or set boundaries
        if self.first_update:
            if self.settings['x_bounds'] is None:
                self.settings['x_bounds'] = self.ax.get_xlim()
            if self.settings['y_bounds'] is None:
                self.settings['y_bounds'] = self.ax.get_ylim()
        else:
            self.ax.set_xlim(*self.settings['x_bounds'])
            self.ax.set_ylim(*self.settings['y_bounds'])

        # Get the background for later use
        self.canvas.draw()
        self.background = self.canvas.copy_from_bbox(self.ax.bbox)
        # First draw update
        [line.set_animated(False) for line in self.lines]
        self.canvas.draw()
        [line.set_animated(True) for line in self.lines]

    def _get_colors(self, n):
        """ Generate colors for the lines if they are not provided. First use
        6 of the standard colors and then generate random colors

        Parameters:
            n -- the number of colors requested
        """
        standard = ['r', 'g', 'b', 'c', 'm', 'k']
        if n <= len(standard):
            out = standard[:n]
        else:
            out = standard
        if n > len(standard):
            for i in range(len(standard), n):
                out.append((random.random(), random.random(), random.random()))
        return out
Example #10
0
class setup_gui:
    def __init__(self):
        self.builder = gtk.Builder()
        self.builder.add_from_file(os.path.splitext(__file__)[0]+".glade")
        self.window = self.builder.get_object("window")

        dic = {
            "on_toolbutton_refresh_clicked" : self.generate_testdata,
            "on_button1_clicked" : self.generate_testdata,
            "on_vboxMain_button_press_event" : self.button_press_event,
            "on_vboxMain_button_release_event" : self.button_release_event,
            "on_vboxMain_drag" : self.drag_begin,
            "on_vboxMain_motion_notify_event" : self.drag_begin,
            "on_toolbar_clear_clicked" : self.clear_selections,
            "on_toolbar_zoomin_clicked" : self.zoomin_time,
            "on_toolbar_zoomout_clicked" : self.zoomout_time,
            "on_go_back_clicked" : self.page_back,
            "on_go_forward_clicked" : self.page_forward,
            "on_toolbutton_setup_toggled" : self.preferences_open,
            "on_button_channel_apply_clicked" : self.channel_selection_apply,
            "set_channel_groups" : self.set_channel_groups,
            "showpopupmenu" : self.showpopupmenu,
            "on_toolbar_plot_clicked" : self.plot_contour,
            "on_plot_contour_activate" : self.plot_contour,
            "on_button_delete_selection_clicked" : self.event_selection_delete,
            "gtk_widget_hide" : self.hideinsteadofdelete,
            "on_button_display_apply_clicked": self.display_apply,
            "on_go_up_clicked" : self.page_up,
            "on_go_down_clicked" : self.page_down,
            "on_toolbutton_load_clicked" : self.load_data,
            "on_menu_offset_correct_clicked" : self.offset_correct,
            "on_button_epoch_clicked" : self.add_selections_to_event_process,
            "on_store_event_clicked" : self.store_event,
            "on_menu_save_noise_activate" : self.store_noise,
            "on_menu_save_event_activate" : self.store_event,
            "on_key_press_event" : self.key_press_event,

            }

        self.builder.connect_signals(dic)
        try: self.prefs = readwrite.readdata(os.getenv('HOME')+'/.pymeg.pym')
        except IOError: self.prefs = {}; readwrite.writedata(self.prefs, os.getenv('HOME')+'/.pymeg')
        try:
            self.line_r,self.line_g,self.line_b = self.prefs['LineColor'][0],self.prefs['LineColor'][1],self.prefs['LineColor'][2]
            self.back_r,self.back_g,self.back_b = self.prefs['BackColor'][0],self.prefs['BackColor'][1],self.prefs['BackColor'][2]
        except:
            self.line_r,self.line_g,self.line_b = 1.,1.,1.
            self.back_r,self.back_g,self.back_b = .9,.9,.9
        self.color = (self.line_r,self.line_g,self.line_b)
        self.create_draw_frame('none')
        self.create_spec_frame('none')
        self.create_csd_frame('none')
        self.space = 0
        #self.generate_testdata(None)
        self.preferences_open(None)

    def printtest(self,widget):
        print 'something'

    def store_noise(self,widget):
        print widget,'wid',widget.get_parent().get_name()
        self.callback(widget)

    def store_event(self,widget):
        print widget,'wid',widget.get_parent().get_name()
        self.callback(widget)

    def create_draw_frame(self,widget):
        self.fig = Figure(figsize=[100,100], dpi=40)
        self.canvas = FigureCanvas(self.fig)
        self.canvas.connect("scroll_event", self.scroll_event)
        self.canvas.connect("key-press-event", self.key_press_event)
        #self.canvas.connect('button_press_event', self.button_press_event)
        self.canvas.show()
        self.figure = self.canvas.figure
        self.axes = self.fig.add_axes([0.045, 0.05, 0.93, 0.925], \
        axisbg=(self.back_r,self.back_g,self.back_b))
        #axisbg='#FFFFCC')

        self.vb = self.builder.get_object("vbox3")
        self.vb.pack_start(self.canvas, gtk.TRUE, gtk.TRUE)
        self.vb.show()

    def create_spec_frame(self,widget):
        self.specfig = Figure(figsize=[10,10], dpi=40)
        self.specfig.text(0.25,0.5,'Middle Click Channel for Specgram',\
        fontsize=20)
        self.speccanvas = FigureCanvas(self.specfig)
        self.speccanvas.show()
        self.specfigure = self.speccanvas.figure
        self.specaxes = self.specfig.add_axes([0.045, 0.05, 0.93, 0.925], \
        axisbg=(self.back_r,self.back_g,self.back_b))
        #self.specaxes.axis('off')
        self.vb2 = self.builder.get_object("vbox8")
        self.vb2.pack_end(self.speccanvas, gtk.TRUE, gtk.TRUE)
        self.vb2.show()

    def create_csd_frame(self,widget):
        self.csdfig = Figure(figsize=[10,10], dpi=40)
        self.csdfig.text(0.25,0.5,'Middle Click Channel for CSD',fontsize=20)
        self.csdcanvas = FigureCanvas(self.csdfig)
        self.csdcanvas.show()
        self.csdfigure = self.csdcanvas.figure
        self.csdaxes = self.csdfig.add_axes([0.045, 0.05, 0.93, 0.925], \
        axisbg=(self.back_r,self.back_g,self.back_b))
        #self.csdaxes.axis('off')
        self.vb3 = self.builder.get_object("vbox9")
        self.vb3.pack_end(self.csdcanvas, gtk.TRUE, gtk.TRUE)
        self.vb3.show()

    def data_loaded_setup(self):
        self.channel_tree(None)
        self.builder.get_object("spinbutton1").set_range(0,self.numchannels)
        self.builder.get_object("spinbutton1").set_value(self.numchannels)
        self.builder.get_object("spinbutton2").set_range(self.t[0],self.t[-1])
        self.builder.get_object("spinbutton2").set_value(self.t[0])
        self.builder.get_object("spinbutton3").set_range(self.t[0],self.t[-1])
        #if self.t[-1] - self.t[0] > 1: #alot of time, save time in plotting and set low
        if len(self.t) > 1000:
            self.builder.get_object("spinbutton3").set_value(self.t[1000])
            print '.....reducing time var'
        else:
            print '.....showing all time'
            self.builder.get_object("spinbutton3").set_value(self.t[-1])
        #self.builder.get_object("spinbutton3").set_value(self.t[-1])
        #self.builder.get_object("spinbutton5").set_value(self.scalefact)
        self.builder.get_object("entry1").set_text(str(self.space))
        self.builder.get_object("entry2").set_text(str(self.scalefact))

    def preferences_open(self,widget):
        self.win_prefs = self.builder.get_object("window_prefs")
        #try: self.prefs = readwrite.readdata(os.getenv('HOME')+'/.pymeg.pym')
        #except IOError: self.prefs = {}; readwrite.writedata(self.prefs, os.getenv('HOME')+'/.pymeg')
        try:
            #r,g,b = self.prefs['LineColor'][0],self.prefs['LineColor'][1],self.prefs['LineColor'][2]
            self.builder.get_object("colorbutton1").set_color(color=gtk.gdk.Color(self.line_r,self.line_g,self.line_b))
            self.builder.get_object("colorbutton2").set_color(color=gtk.gdk.Color(self.back_r,self.back_g,self.back_b))
        except IOError:
            pass
        #print 'color',self.builder.get_object("colorbutton1").get_color()
        
        #self.builder.get_object("colorbutton1").set_color(color=gtk.gdk.Color(111))
        #print 'color',self.builder.get_object("colorbutton1").get_color()
        
        if self.builder.get_object('toolbutton12').get_active() == True:
            self.win_prefs.show()
        else:
            self.win_prefs.hide()
        self.selections_tree(None)


    def key_press_event(self, widget, event):
        print event.keyval

    def scroll_event(self, widget, event):
        if event.direction == gdk.SCROLL_UP:
            direction = 1
            self.space = self.space + 2*self.scalefact
            print 'sf',self.scalefact
        else:
            direction = -1
            self.space = self.space - 2*self.scalefact
            print 'sf',self.scalefact
        if self.space < 0:
            self.space = 0
        print 'space', self.space
        #print (arange(0,size(self.data2plot,1))*(self.space))
        self.space_data()
        self.redraw(None)

    def space_data(self,space=None):
        self.data2plot = self.data[self.tstart:self.tstop,self.chanind2plot]+\
        (arange(0,size(self.data[self.tstart:self.tstop,self.chanind2plot],1))*\
        (self.space))

    def get_cursor_position(self,event):
        ap = self.axes.get_position()
        x,y = self.canvas.get_width_height()
        posx = ((event.x/x)-ap.x0)*(1/(ap.x1-ap.x0))
        posy = ((event.y/y)-(1-ap.y0))*(1/(ap.y0-ap.y1))
        self.sx = (posx*(self.time[-1]-self.time[0]))+self.time[0]
        self.sy = (posy*(self.data2plot.max()-self.data2plot.min())) + \
        self.data2plot.min()
        #print self.sx, self.sy

    def button_press_event(self,widget,event):
        self.get_cursor_position(event)
        #print 'button pushed',event.button,event.type
        if event.type == gtk.gdk.BUTTON_PRESS:
            print "single click"
            if event.button == 1:
                self.xstart = self.sx
        #elif event.type == gtk.gdk._2BUTTON_PRESS:
            #print "double click"
        #elif event.type == gtk.gdk._3BUTTON_PRESS:
            #print "triple click. ouch, you hurt your user."

        if event.type == gtk.gdk.BUTTON_PRESS and event.button == 2:
            closest_data = nearest.nearest(self.data2plot[0,:],self.sy)
            print 'nearest',closest_data
            print 'highlighting channel'
            self.axes.axhspan(self.data2plot[:,closest_data].min(), \
            self.data2plot[:,closest_data].max(), xmin=0, xmax=1, color='g',\
            alpha=0.2)
            self.canvas.draw()
            self.specaxes.cla()
            NFFT = 1024
            Fs = self.srate #(1/self.srate)
            print NFFT,int(Fs),'d'

            self.specaxes.specgram(
            self.data2plot[:,closest_data[0]], NFFT=NFFT, Fs=Fs,noverlap=900)
            #self.specaxes.axis('off')
            self.speccanvas.draw()

            self.csdaxes.csd(self.time,
            self.data2plot[:,closest_data[0]], NFFT=NFFT, Fs=Fs)
            #, noverlap=Noverlap,
            #cmap=cm.jet)#, xextent=xextent)
            #self.csdaxes.axis('off')
            self.csdcanvas.draw()

    def button_release_event(self,widget,event):
        self.get_cursor_position(event)
        if event.type == gtk.gdk.BUTTON_RELEASE and event.button == 1:
            self.axes.axvspan(ymin=0, ymax=1, xmin=self.xstart, xmax=self.sx, \
            color='b',alpha=0.4)
            if self.xstart > self.sx: #selection going from later to earlier
                tmp = copy(self.sx)
                self.sx = copy(self.xstart)
                self.xstart = tmp

            try: self.selections = vstack((self.selections,\
            [self.xstart,self.sx]))
            except AttributeError: self.selections = \
            array([[self.xstart,self.sx]])
            print 'sels',self.selections
            self.canvas.draw()
            self.selections_tree(None)

    def clear_selections(self,widget):
        del self.selections
        self.redraw(None)

    def drag_begin(self,widget,event):
        pass

    def redraw(self,widget):
        print len(self.time),self.data2plot.shape
        #self.color = 'black'
        self.axes.cla()
        self.axes = self.figure.axes[0]
        print 'cur color', self.color
        self.axes.plot(self.time, self.data2plot,color=self.color)
        self.axes.axis('tight')
        try:
            print 'current selections',self.selections
            for i in self.selections:
                self.axes.axvspan(ymin=0,ymax=1,xmin=i[0],xmax=i[1],color='b',\
                alpha=.4)
        except:
            pass
        self.axes.yaxis.set_ticks((arange(0,size(self.data2plot,1)) * \
        (self.space)))
        self.axes.yaxis.set_ticklabels(self.chanlabels2plot, fontsize=17)
        self.canvas.draw()
        ion()

    def zoomin_time(self,widget):
        startind = self.tstart;
        stopind = self.tstop-((self.tstop-self.tstart)/2)
        self.check_scale(startind,stopind)
        self.redraw(None)

    def zoomout_time(self,widget):
        startind = self.tstart;
        stopind = self.tstop+((self.tstop-self.tstart)*2)
        self.check_scale(startind,stopind)
        self.redraw(None)

    def page_forward(self,widget):
        startind = ((self.tstop-self.tstart)/2)+self.tstart;
        stopind = ((self.tstop-self.tstart)/2)+self.tstop;
        self.check_scale(startind,stopind)
        self.redraw(None)

    def page_back(self,widget):
        startind = self.tstart-((self.tstop-self.tstart)/2);
        stopind = self.tstop-((self.tstop-self.tstart)/2);
        self.check_scale(startind,stopind)
        self.redraw(None)

    def page_up(self,widget):
        self.curchannel = self.curchannel+self.numofch
        if self.curchannel >= len(self.chanind):
            self.curchannel = len(self.chanind)-self.numofch

        self.chanind2plot = \
        self.chanind[self.curchannel:self.curchannel+self.numofch]
        self.chanlabels2plot = \
        self.chanlabels[self.curchannel:self.curchannel+self.numofch]
        self.check_scale(self.tstart,self.tstop)
        self.redraw(None)#self.display_apply(None)

    def page_down(self,widget):
        self.curchannel = self.curchannel-self.numofch
        if self.curchannel < 0:
            self.curchannel = 0

        self.chanind2plot = \
        self.chanind[self.curchannel:self.curchannel+self.numofch]
        self.chanlabels2plot = \
        self.chanlabels[self.curchannel:self.curchannel+self.numofch]
        self.check_scale(self.tstart,self.tstop)
        self.redraw(None)#self.display_apply(None)

    def display_apply(self,widget):
        color = self.builder.get_object('colorbutton1')
        r = color.get_color().red_float
        g = color.get_color().green_float
        b = color.get_color().blue_float
        self.line_color = self.color = (r,g,b)
        self.prefs['LineColor'] = self.line_color
        color = self.builder.get_object('colorbutton2')
        r = color.get_color().red_float
        g = color.get_color().green_float
        b = color.get_color().blue_float
        self.back_color = (r,g,b)
        self.prefs['BackColor'] = self.back_color
        readwrite.writedata(self.prefs, os.getenv('HOME')+'/.pymeg')
        
        self.numofch = int(self.builder.get_object("spinbutton1").get_value())
        self.chanind2plot = \
        self.chanind[self.curchannel:self.curchannel+self.numofch]
        self.chanlabels2plot = \
        self.chanlabels[self.curchannel:self.curchannel+self.numofch]
        
        st = float(self.builder.get_object("spinbutton2").get_value())
        ed = float(self.builder.get_object("spinbutton3").get_value())
        self.space = float(self.builder.get_object("entry1").get_text())
        self.scalefact = float(self.builder.get_object("entry2").get_text())
        #print 'se',st,ed, self.t
        startind = nearest.nearest(self.t,st)[0]
        stopind = nearest.nearest(self.t,ed)[0]
        print 'se',startind,stopind
        self.check_scale(startind,stopind)
        self.space_data()
        self.redraw(None)

    def check_scale(self,startind,stopind):
        print 'req',startind,stopind, self.tstart,self.tstop
        if startind < 0:
            startind = 0
            stopind = self.tstop
        if stopind > len(self.t):
            startind = self.tstart
            stopind = len(self.t)
        if stopind < 0:
            stopind = self.tstop
        print 'set',startind,stopind,self.tstart,self.tstop

        self.tstart = startind
        self.tstop = stopind
        self.time = self.t[self.tstart:self.tstop]
        self.data2plot = self.data[self.tstart:self.tstop,self.chanind2plot]
        self.space_data()
        #self.redraw(None)


    def channel_tree(self,widget):
        print('updating list')
        self.View = self.builder.get_object("treeview1")
        self.dataList = gtk.ListStore(int,str)
        self.AddListColumn('Number', 0, self.View)
        self.AddListColumn('Label', 1, self.View)

        for k in range(0,self.numchannels):
            iter = self.dataList.append([k,self.chanlabels[k]])

        self.View.set_model(self.dataList)
        print 'adding channels'

    def AddListColumn(self, title, columnId, viewtype):
        column = gtk.TreeViewColumn(title,gtk.CellRendererText(),text=columnId)
        column.set_resizable(True)
        column.set_sort_column_id(columnId)
        viewtype.append_column(column)
        viewtype.get_selection().set_mode(gtk.SELECTION_MULTIPLE)


    def channel_selection_apply(self, widget):
        liststore,iter = self.View.get_selection().get_selected_rows()
        self.chanind = [];
        self.chanlabels = [];
        for i in iter:
            self.chanind.append(int(liststore[i][0]))
            self.chanlabels.append(liststore[i][1])
        print self.chanlabels

        self.chanind2plot = self.chanind
        self.chanlabels2plot = self.chanlabels
        self.space_data()
        self.redraw(None)

    def set_channel_groups(self,widget):
        l = self.View.get_model()
        i = l.get_iter_first()
        v = []
        while ( i != None ):
            v.append(l.get_value(i,1))
            i = l.iter_next(i)

        print widget.get_label(), widget
        if widget.get_label() == 'meg' and widget.get_active() == True:
            for i in range(0,len(v)):
                if v[i].startswith('A'):
                    self.View.get_selection().select_path(i)
        if widget.get_label() == 'De-Select All':
            self.View.get_selection().unselect_all()
        if widget.get_label() == 'Select All':
            self.View.get_selection().select_all()
        if widget.get_label() == 'reference' and widget.get_active() == True:
            for i in range(0,len(v)):
                if v[i].startswith('M') or v[i].startswith('G'):
                    self.View.get_selection().select_path(i)
        if widget.get_label() == 'trigger' and widget.get_active() == True:
            for i in range(0,len(self.chanlabels)):
                if v[i].startswith('TRIGG'):
                    self.View.get_selection().select_path(i)
        if widget.get_label() == 'response' and widget.get_active() == True:
            for i in range(0,len(v)):
                if v[i].startswith('RESP'):
                    self.View.get_selection().select_path(i)


    def selections_tree(self,widget):
        try:
            if self.win_prefs.get_property('visible') == True:
                print('updating selections')
                self.SelView = self.builder.get_object("treeview2")
                self.selectionList = gtk.ListStore(int,str)

                if self.SelView.get_columns() == []:
                    self.AddListColumn('Event Number', 0,self.SelView)
                    self.AddListColumn('Selection', 1,self.SelView)

                for k in range(0,len(self.selections)):
                    iter=self.selectionList.append([k,str(self.selections[k])])
                self.SelView.set_model(self.selectionList)
                print 'adding selections'

        except AttributeError:
            pass #window not initiated yet

    def event_selection_delete(self, widget):
        liststore,iter = self.SelView.get_selection().get_selected_rows()
        #self.selections = delete(self.selections,iter,axis=0)
        del_ind = []
        for i in iter:
            print 'deleting event:',liststore[i][0]
            del_ind.append(liststore[i][0])
        self.selections = delete(self.selections,del_ind,axis=0)
        self.selections_tree(None)
        self.redraw(None)

    def showpopupmenu(self,widget,event):
        print('button ',event.button)
        if event.button == 3:
            m = self.builder.get_object("menufunctions")
            print(widget, event)
            m.show_all()
            m.popup(None,None,None,3,0)

    def get_time_selection(self,widget,current=True):
        print 'name',widget.get_parent().get_name()
        sel_ind = []
        sel_onset_ind = []
        def selection_to_ind(sels,sele,inc):
            print 'getting sel'
            if sele == sels: #only one point selected
                sele = sels+inc

            nearest.nearest(self.t,arange(sels,sele,inc))
            sel_ind = nearest.nearest(self.t,arange(sels,sele,inc))
            return sel_ind
        if widget.get_parent().get_name() == 'GtkMenu' and current == True: #call from editor menu
            print 'call from right click menu'
            try:
                self.sel_ind = selection_to_ind(self.selections[-1][0],\
                self.selections[-1][1],self.t[1]-self.t[0])
            except AttributeError:
                print 'no selections yet'
                return -1

        else: #call from selector
            print 'call from selector window'
            liststore,iter = self.SelView.get_selection().get_selected_rows()
            for i in iter:
                j = int(liststore[i][0])
                sel_ind.extend(selection_to_ind(self.selections[j][0],\
                self.selections[j][1],self.t[1]-self.t[0]))
                sel_onset_ind.extend(selection_to_ind(self.selections[j][0],\
                self.selections[j][0],self.t[1]-self.t[0]))
            self.sel_ind = sel_ind
            self.sel_onset_ind = sel_onset_ind

    def plot_contour(self,widget):
        if size(self.data,1) < 4:
            self.builder.get_object("messagedialog1").format_secondary_text\
            ('Contour Plot Requires at least 4 Channels')
            self.builder.get_object("messagedialog1").show()
            return -1
        print widget.get_parent().get_name()
        if self.get_time_selection(widget) == -1: #no selections
            self.builder.get_object("messagedialog1").format_secondary_text\
            ('No Selection Made Yet')
            self.builder.get_object("messagedialog1").show()
            return -1
        try:
            print 'state',self.mc.window.get_property('visible')
            if self.mc.window.get_property('visible') == False:
                #someone closed the window
                self.mc.window.show()
            print 'done replotting'
        except AttributeError: #first call. setup
            print 'first plot'
            self.mc = contour_gtk.setup_gui()
            self.mc.window.show()

        self.mc.fig.clf()
        self.mc.display(self.data[self.sel_ind,:],self.channels, subplot='on', labels=self.chanlabels)

    def generate_testdata(self,widget):
        self.quick_load_pdf_script()
        #numpts = 100
        #self.numchannels = 10
        #self.t = arange(0,numpts, .01)
        #self.data = zeros((len(self.t),self.numchannels))
        #self.scalefact = 1e-9
        #for i in arange(0,self.numchannels):
            #r = random.randn()
            #self.data[:,i] = float32((sin(2*0.32*pi*self.t*r) * \
            #sin(2*2.44*pi*self.t*r)))#+ self.space
        #self.data[:,0] = random.randn((len(self.t)))
        #self.data = self.data * self.scalefact
        #self.tstart = 0; self.tstop = len(self.t)
        #self.time = copy(self.t[self.tstart:self.tstop])
        #print self.tstart,self.tstop
        #self.chanind = arange(0,self.numchannels)
        #self.chanlabels = arange(0,self.numchannels)
        self.data2plot = self.data
        self.display_apply(None)
        #self.space_data()
        #self.redraw(None)

    def quick_load_pdf_script(self):
        from pdf2py import pdf
        datapath = '/home/danc/programming/python/data/'
        p = pdf.read(datapath+'test/e,rfhp1.0Hz,ra')
        #p = pdf.read(datapath+'0611/0611piez/e,rfhp1.0Hz')
        #p = pdf.read(datapath+'data/0611/drawing3/01%01%01@01:01/2/c,rfDC')
        p.data.setchannels('meg')
        #p.data.setchannellabels(['A1','A69','A130'])#meg')
        #p.data.setchannellabels(['A178'])
        p.data.getdata(0,p.data.pnts_in_file)
        self.numchannels = size(p.data.data_block,1)
        self.t = p.data.wintime #eventtime
        self.data = p.data.data_block
        self.tstart = 0; self.tstop = len(self.t)
        self.time = copy(self.t[self.tstart:self.tstop])
        self.chanind = arange(self.numchannels)
        self.chanlabels = p.data.channels.labellist
        self.scalefact = (p.data.data_block.min()+p.data.data_block.max())/2
        self.channels = p.data.channels.chanlocs
        self.srate = p.hdr.header_data.sample_period
        self.data_loaded_setup()
        self.curchannel = 0

    def hideinsteadofdelete(self,widget, ev=None):
        widget.hide()
        return True

    def load_data(self,widget):
        from gui.gtk import filechooser
        fn = filechooser.open()
        try: #pdf load method
            self.data_assist = meg_assistant.setup(path = fn[0], \
            callback=self.load_data_callback)

        except:
            print 'something wrong with load'
            return -1

    def load_data_callback(self, widget):
        print 'DONE!'
        p = self.data_assist.pdfdata #4D MEG file format
        input_dict = {'data_block':p.data.data_block,'srate':p.data.srate,'wintime':p.data.wintime,'labellist':p.data.channels.labellist,'chanlocs':p.data.channels.chanlocs}
        self.data_handler(widget, input_dict)


    def data_handler(self, widget, input_dict, callback=None):
        '''
        datahandler(data,srate,wintime,chanlabels,chanlocs)
        -
        data = 2D array
        srate = type(float or int)
        wintime = type(list or array) of same length as first dimension of data
        chanlabels = type(list of strings) of same length as
            second dimension of data
        chanlocs = shape is 2Xnumber of channels, ie, (2,248) and contains page
            coordinates for each channel. Position of X and Y is between -.5
            and .5
        '''
        ####!!!!!!!
        '''should rerwite the following as well as the filechooser method to make simple and compatible with dictionary based load and read'''
        data = input_dict['data_block']
        srate = input_dict['srate']
        wintime = input_dict['wintime']
        chanlabels = input_dict['labellist']
        chanlocs = input_dict['chanlocs']

        print type(data),srate,type(wintime),type(chanlabels),type(chanlocs)
        print len(chanlabels),size(data,1),len(wintime),size(data,0),\
        size(chanlocs,1)
        if len(chanlabels) != size(data,1) or len(wintime) != size(data,0):
        #or size(chanlocs,1) != size(data,1):
            print 'error matching wintime or chlabels or chanlocs with data'
            #self.builder.get_object("messagedialog1").format_secondary_text\
            #('error matching wintime or chlabels or chanlocs with data')
            #self.builder.get_object("messagedialog1").show()
            #raise RuntimeError

        self.data = data
        self.srate = srate
        self.chanlabels = chanlabels
        self.t = array(wintime)
        self.tstart = 0; self.tstop = len(self.t)
        self.time = copy(self.t[self.tstart:self.tstop])
        self.numchannels = size(data,1)
        self.chanind = arange(self.numchannels)
        self.scalefact = (data.min()+data.max())/2
        print 'scalefact', self.scalefact
        self.channels = chanlocs
        self.curchannel = 0
        self.tstart = 0; self.tstop = len(self.t)

        self.data_loaded_setup()
        self.data2plot = self.data
        self.display_apply(None)


        try: callback(widget); self.callback = callback
        except TypeError, NameError: print('no callback')


    def offset_correct(self,widget):
        print self.get_time_selection(widget)
        if self.get_time_selection(widget) == -1: #no selections
            ###self.builder.get_object("messagedialog1").format_secondary_text\
            ###('No Selection Made Yet')
            ###self.builder.get_object("messagedialog1").show()
            print('no selections detected')
            return -1
        self.data = self.data - average(self.data[self.sel_ind,:],axis=0)
        print 'Data offset corrected, now trying to replot'
        self.display_apply(None)
        print widget,'wid:',widget.get_label()
        self.callback(widget)

    def add_selections_to_event_process(self,widget):
        try:
            if self.ed.window.get_property('visible') == False:
                #self.ed = event_process.setup_gui()
                self.ed.window.show()
        except AttributeError: #first call. setup
                self.ed = event_process.setup_gui()
                self.ed.window.show()
        if self.get_time_selection(widget) == -1:
            print('no selections detected')
            return -1

        print('passing selection indices',self.sel_onset_ind)
        self.ed.set_selected_events_passed(None,self.data,self.sel_onset_ind,self.t)
        self.ed.builder.get_object("button1").set_sensitive(False)