def create_monitor(self): self.monitor_frame = LabelFrame(self, text="Monitor and Transport") this_cycle = Scale(self.monitor_frame, label='cycle_pos', orient=HORIZONTAL, from_=1, to=16, resolution=1) this_cycle.disable, this_cycle.enable = (None, None) this_cycle.ref = 'cycle_pos' this_cycle.grid(column=0, row=0, sticky=E + W) self.updateButton = Button(self.monitor_frame, text='Reload all Settings', command=self.request_update) self.updateButton.grid(row=1, sticky=E + W) self.ForceCaesuraButton = Button(self.monitor_frame, text='Force Caesura', command=self.force_caesura) self.ForceCaesuraButton.grid(row=2, sticky=E + W) self.saveBehaviourButton = Button(self.monitor_frame, text='Save current behaviour', command=self.request_saving_behaviour) self.saveBehaviourButton.grid(row=3, sticky=E + W) self.saveBehaviourNameEntry = Entry(self.monitor_frame) self.saveBehaviourNameEntry.grid(row=4, sticky=E + W) self.saveBehaviourNameEntry.bind('<KeyRelease>', self.request_saving_behaviour) self.selected_behaviour = StringVar() self.selected_behaviour.trace('w', self.new_behaviour_chosen) self.savedBehavioursMenu = OptionMenu(self.monitor_frame, self.selected_behaviour, None,) self.savedBehavioursMenu.grid(row=5, sticky=E + W) self.monitor_frame.grid(column=0, row=10, sticky=E + W)
class Tx(Tk.Frame): def __init__(self, master=None): Tk.Frame.__init__(self, master) self.tx_frame = Tk.Frame(self) self.gpio = [] for i in range(0,20): self.gpio.append(GPIO(i)) # GPIO LABEL self.gpio_hdr = Tk.Label(self.tx_frame,text="PORT%02d"%i, anchor=Tk.W) # GPIO Configure self.c_gpio_config = ttk.Combobox(self.tx_frame,value=["INPUT","OUTPUT","HIZ"], state="readonly") self.c_gpio_config.current(HIZ) self.c_gpio_config.bind("<<ComboboxSelected>>",self.gpio[i].config_change) self.gpio[i].set_combo(self.c_gpio_config) # GPIO scaler self.s_gpio_value = Scale(self.tx_frame,orient = 'h',showvalue = 0,from_ = 0, to = 1,command = self.gpio[i].value_change) self.gpio[i].set_scale(self.s_gpio_value) self.gpio_hdr.grid(row=i, column=0, padx=5, pady=0) self.c_gpio_config.grid(row=i, column=1, padx=5, pady=0) self.s_gpio_value.grid(row=i, column=2, padx=5, pady=0) self.tx_frame.pack()
"""Simple scale. Stand-alone example from Tk Assistant. By Steve Shammbles. stevepython.wordpress.com""" from tkinter import Button, HORIZONTAL, Scale, Tk root = Tk() root.title('Simple scale example') def final_setting(): """Display scale value setting if OK button clicked.""" scale_setting = scale_meter.get() print('Scale reads:', scale_setting) scale_meter = Scale(root, fg='green', from_=0, to=100, orient=HORIZONTAL) scale_meter.grid(padx=40, pady=10) ok_btn = Button(root, bg='gold', text='OK', command=final_setting) ok_btn.grid(pady=10) root.mainloop()
class singleColor_module(baseModule): def __init__(self, parent): baseModule.__init__(self, parent) self._hexColor = "#ffffff" self._V3_HSVColor = [0.0, 1.0, 1.0] self.mainFrame = Frame(parent) self.mainFrame.grid(sticky=(E, W)) self.populateInterface(self.mainFrame) def populateInterface(self, parent): """ populate the parent element with all SingleColor elements :param parent: the parent element of all subelements """ """#################### LUMINOSITY ####################""" self._SV_luminosity = StringVar(value="100") self._S_luminosity = Scale(parent, from_=0, to=100, orient=HORIZONTAL, variable=self._SV_luminosity) self._S_luminosity.grid(row=0, column=0, columnspan=2, sticky=(E, W)) """#################### COEF ####################""" self._SV_coefEnabled = StringVar(value="on") self._RB_coefs = self._createToggle(parent, "Disable Coef", "Enable Coef", self._SV_coefEnabled) self._RB_coefs[0].grid(row=1, column=0) self._RB_coefs[1].grid(row=1, column=1) """#################### STROBE ####################""" self._f_strobeValue = 1.0 self._d_strobeDirection = -1 self._SV_strobeEnabled = StringVar(value="off") self._RB_strobe = self._createToggle(parent, "Disable Strobe", "Enable Strobe", self._SV_strobeEnabled) self._RB_strobe[0].grid(row=2, column=0) self._RB_strobe[1].grid(row=2, column=1) _SV_strobeSpeed = StringVar(self._parent) _SV_strobeSpeed.set("25") self._S_strobeSpeed = Spinbox(parent, from_=2, to=350, textvariable=_SV_strobeSpeed) self._S_strobeSpeed.grid(row=3, column=0, columnspan=2, sticky=(E, W)) """#################### RAINBOW ####################""" self._SV_rainbowEnabled = StringVar(value="off") self._RB_rainbow = self._createToggle(parent, "Disable Rainbow", "Enable Rainbow", self._SV_rainbowEnabled) self._RB_rainbow[0].grid(row=4, column=0) self._RB_rainbow[1].grid(row=4, column=1) _SV_rainbowSpeed = StringVar(self._parent) _SV_rainbowSpeed.set("6") self._S_rainbowSpeed = Spinbox(parent, from_=1, to=3600, textvariable=_SV_rainbowSpeed) self._S_rainbowSpeed.grid(row=5, column=0, columnspan=2, sticky=(E, W)) """#################### COLOR PICKER ####################""" self._B_pickColor = Button(parent, command=self._pickColor, width=21, height=5) self._B_pickColor.configure(background=self._hexColor) self._B_pickColor.grid(row=6, column=0, columnspan=2) def _switchRainbow(self): if self._SV_rainbowEnabled.get() == "on": self._V3_HSVColor = [0.0, 1.0, 1.0] else: self._V3_HSVColor = [0.0, 0.0, 1.0] def _switchFlash(self): if self._SV_strobeEnabled.get() == "off": self._f_strobeValue = 1.0 self._d_strobeDirection = -1 def __updateRainbow(self): _rainbowValue = self._safeGetValueFromSlider(self._S_rainbowSpeed, 10, 0.6) self._V3_HSVColor[0] = (self._V3_HSVColor[0] + _rainbowValue) % 360 RGB = Color.fromHSV(*self._V3_HSVColor) self._hexColor = RGB.toHex() def __updateStrobe(self): _strobeValue = self._safeGetValueFromSlider(self._S_strobeSpeed, 1000, 0.025) self._f_strobeValue = self._f_strobeValue + _strobeValue * self._d_strobeDirection if (1 - _strobeValue < self._f_strobeValue) or (self._f_strobeValue < _strobeValue): self._d_strobeDirection *= -1 def _pickColor(self): if self._SV_rainbowEnabled.get() == "off": self._hexColor = askcolor()[1] def update(self): """ Update the leds from interface parametters """ """ Computer color if rainbow is enabled """ if self._SV_rainbowEnabled.get() == "on": self.__updateRainbow() """ Computer value if strobe is enabled """ if self._SV_strobeEnabled.get() == "on": self.__updateStrobe() """ Update color value with strobeValue """ _Color_RGB = Color.fromHex(self._hexColor) _Color_RGB *= self._f_strobeValue """ Update button color """ self._B_pickColor.configure(background=_Color_RGB.toHex()) """ Computer color luminosity from slider """ _Color_RGB *= int(self._S_luminosity.get()) / 100 """ Computer color coefs """ if self._SV_coefEnabled.get() == "on": _rgbList = _Color_RGB.enhance(gr=0.60, br=0.45, bg=0.25).toList() else: _rgbList = _Color_RGB.toList() """ Send colors to arduino and wait 60ms """ for n in range(self._controller.nbLeds): self._controller.buffer[n] = _rgbList self._controller.send()
def initLabelFrame(self, labels): # We init the frame: if self.labelFrame is not None: self.labelFrame.destroy() self.labelIds = [] self.labelEntries = [] self.labelFrame = Frame(self) self.labelFrame.grid(row=self.labelFrameRow, column=11, sticky="nsew") self.labelFrame.columnconfigure(0, weight=1) # We init the row counter: i = 0 # We make the head message: self.labelFrame.rowconfigure(i, weight=1) title = Message(self.labelFrame, text="Labels", **self.headMessagesOption) title.grid(row=i, column=0, sticky='nsew', pady=10) i += 1 # For each label: for id, label in labels.items(): try: # We make the message: currentMessage = None if label["type"] != LABEL_TYPE.checkbutton or dictContains( label, "shorttitle"): currentMessage = Message( self.labelFrame, text=label["title"], width=self.messageWidth, font=self.messageFont ) # bg="white", foreground="black" # According to the label type: if not dictContains( label, "type") or label["type"] == LABEL_TYPE.scale: # We make the entry: currentEntry = Scale\ ( self.labelFrame, from_=label["from"] if dictContains(label, "from") else 0.0, to=label["to"] if dictContains(label, "to") else 1.0, orient=HORIZONTAL, resolution=label["resolution"] if dictContains(label, "resolution") else 0.05, ) currentEntry.set(label["default"] if dictContains( label, "default") else 0.5) # We save the entry: self.labelEntries.append(currentEntry) elif label["type"] == LABEL_TYPE.checkbutton: var = BooleanVar() currentEntry = Checkbutton\ ( self.labelFrame, text=label["shorttitle"] if dictContains(label, "shorttitle") else label["title"], variable=var, ) if dictContains(label, "default") and label["default"]: currentEntry.select() # We save the entry: self.labelEntries.append(var) elif label["type"] == LABEL_TYPE.radiobutton: vals = [] etiqs = [] for k, v in label["options"].items(): vals.append(k) etiqs.append(v) var = IntVar() var.set(vals[1]) currentEntry = [] for i in range(len(vals)): currentEtiq = etiqs[i] currentVal = vals[i] c = Radiobutton\ ( self.labelFrame, text=currentEtiq, variable=var, value=currentVal, ) currentEntry.append(c) if dictContains( label, "default") and label["default"] == currentVal: c.select() self.labelEntries.append(var) # We save the id: self.labelIds.append(id) # We grid the message: if currentMessage is not None: self.labelFrame.rowconfigure(i, weight=1) currentMessage.grid(row=i, column=0, sticky="nsew") i += 1 # We grid the entry: self.labelFrame.rowconfigure(i, weight=1) if isinstance(currentEntry, list): for c in currentEntry: c.grid(row=i, column=0, sticky="nsw") i += 1 else: currentEntry.grid(row=i, column=0, sticky="nsew") i += 1 # We make a separator: self.labelFrame.rowconfigure(i, weight=1) sep = Separator(self.labelFrame, orient=HORIZONTAL) sep.grid(row=i, column=0, sticky='nsew', pady=10) i += 1 except Exception as e: logException(e, self)
class SettingsFrame(Frame): """ Settings frame class. """ def __init__(self, app, *args, **kwargs): """ Constructor. :param Frame app: reference to main tkinter application :param args: optional args to pass to Frame parent class :param kwargs: optional kwargs to pass to Frame parent class """ self.__app = app # Reference to main application class self.__master = self.__app.get_master() # Reference to root class (Tk) Frame.__init__(self, self.__master, *args, **kwargs) self._protocol = IntVar() self._raw = IntVar() self._autoscroll = IntVar() self._maxlines = IntVar() self._webmap = IntVar() self._mapzoom = IntVar() self._units = StringVar() self._format = StringVar() self._datalog = IntVar() self._logformat = StringVar() self._record_track = IntVar() self._show_zerosig = IntVar() self._show_legend = IntVar() self._validsettings = True self._in_filepath = None self._logpath = None self._trackpath = None self._img_conn = ImageTk.PhotoImage(Image.open(ICON_CONN)) self._img_disconn = ImageTk.PhotoImage(Image.open(ICON_DISCONN)) self._img_ubxconfig = ImageTk.PhotoImage(Image.open(ICON_UBXCONFIG)) self._img_dataread = ImageTk.PhotoImage(Image.open(ICON_LOGREAD)) self._body() self._do_layout() self._reset() def _body(self): """ Set up frame and widgets. """ for i in range(4): self.grid_columnconfigure(i, weight=1) self.grid_rowconfigure(0, weight=1) self.option_add("*Font", self.__app.font_sm) # serial port configuration panel self._frm_serial = SerialConfigFrame(self, preselect=KNOWNGPS, timeouts=TIMEOUTS, bpsrates=BPSRATES) # connection buttons self._frm_buttons = Frame(self) self._btn_connect = Button( self._frm_buttons, width=45, height=35, image=self._img_conn, command=lambda: self.__app.serial_handler.connect(), ) self._btn_disconnect = Button( self._frm_buttons, width=45, height=35, image=self._img_disconn, command=lambda: self.__app.serial_handler.disconnect(), state=DISABLED, ) self._btn_connect_file = Button( self._frm_buttons, width=45, height=35, image=self._img_dataread, command=lambda: self._on_data_stream(), ) self._lbl_status_preset = Label(self._frm_buttons, font=self.__app.font_md2, text="") # Other configuration options self._frm_options = Frame(self) self._lbl_protocol = Label(self._frm_options, text=LBLPROTDISP) self._rad_nmea = Radiobutton(self._frm_options, text="NMEA", variable=self._protocol, value=NMEA_PROTOCOL) self._rad_ubx = Radiobutton(self._frm_options, text="UBX", variable=self._protocol, value=UBX_PROTOCOL) self._rad_all = Radiobutton(self._frm_options, text="ALL", variable=self._protocol, value=MIXED_PROTOCOL) self._lbl_consoledisplay = Label(self._frm_options, text=LBLDATADISP) self._rad_parsed = Radiobutton(self._frm_options, text="Parsed", variable=self._raw, value=0) self._rad_raw = Radiobutton(self._frm_options, text="Raw", variable=self._raw, value=1) self._lbl_format = Label(self._frm_options, text="Degrees Format") self._spn_format = Spinbox( self._frm_options, values=(DDD, DMS, DMM), width=6, state=READONLY, readonlybackground=ENTCOL, wrap=True, textvariable=self._format, ) self._lbl_units = Label(self._frm_options, text="Units") self._spn_units = Spinbox( self._frm_options, values=(UMM, UIK, UI, UMK), width=13, state=READONLY, readonlybackground=ENTCOL, wrap=True, textvariable=self._units, ) self._chk_scroll = Checkbutton(self._frm_options, text="Autoscroll", variable=self._autoscroll) self._spn_maxlines = Spinbox( self._frm_options, values=("100", "200", "500", "1000", "2000"), width=6, readonlybackground=ENTCOL, wrap=True, textvariable=self._maxlines, state=READONLY, ) self._chk_webmap = Checkbutton( self._frm_options, text="Web Map Zoom", variable=self._webmap, command=lambda: self._on_webmap(), ) self._scl_mapzoom = Scale( self._frm_options, from_=1, to=20, orient=HORIZONTAL, relief="sunken", bg=ENTCOL, variable=self._mapzoom, ) self._chk_zerosig = Checkbutton(self._frm_options, text=LBLSHOWNULL, variable=self._show_zerosig) self._chk_legend = Checkbutton(self._frm_options, text=LBLLEGEND, variable=self._show_legend) self._chk_datalog = Checkbutton( self._frm_options, text=LBLDATALOG, variable=self._datalog, command=lambda: self._on_data_log(), ) self._spn_datalog = Spinbox( self._frm_options, values=("Raw", "Parsed", "Both"), width=7, readonlybackground=ENTCOL, wrap=True, textvariable=self._logformat, state=READONLY, ) self._chk_recordtrack = Checkbutton( self._frm_options, text=LBLTRACKRECORD, variable=self._record_track, command=lambda: self._on_record_track(), ) self._lbl_ubxconfig = Label(self._frm_options, text=LBLUBXCONFIG) self._btn_ubxconfig = Button( self._frm_options, width=45, height=35, text="UBX", image=self._img_ubxconfig, command=lambda: self._on_ubx_config(), state=DISABLED, ) def _do_layout(self): """ Position widgets in frame. """ self._frm_serial.grid(column=0, row=1, columnspan=4, padx=3, pady=3, sticky=(W, E)) ttk.Separator(self).grid(column=0, row=2, columnspan=4, padx=3, pady=3, sticky=(W, E)) self._frm_buttons.grid(column=0, row=3, columnspan=4, sticky=(W, E)) self._btn_connect.grid(column=0, row=0, padx=3, pady=3) self._btn_connect_file.grid(column=1, row=0, padx=3, pady=3) self._btn_disconnect.grid(column=3, row=0, padx=3, pady=3) ttk.Separator(self).grid(column=0, row=7, columnspan=4, padx=3, pady=3, sticky=(W, E)) self._frm_options.grid(column=0, row=8, columnspan=4, sticky=(W, E)) self._lbl_protocol.grid(column=0, row=0, padx=3, pady=3, sticky=(W)) self._rad_nmea.grid(column=1, row=0, padx=0, pady=0, sticky=(W)) self._rad_ubx.grid(column=2, row=0, padx=0, pady=0, sticky=(W)) self._rad_all.grid(column=3, row=0, padx=0, pady=0, sticky=(W)) self._lbl_consoledisplay.grid(column=0, row=1, padx=2, pady=3, sticky=(W)) self._rad_parsed.grid(column=1, row=1, padx=1, pady=3, sticky=(W)) self._rad_raw.grid(column=2, row=1, padx=2, pady=3, sticky=(W)) self._lbl_format.grid(column=0, row=2, padx=3, pady=3, sticky=(W)) self._spn_format.grid(column=1, row=2, padx=2, pady=3, sticky=(W)) self._lbl_units.grid(column=0, row=3, padx=3, pady=3, sticky=(W)) self._spn_units.grid(column=1, row=3, columnspan=3, padx=2, pady=3, sticky=(W)) self._chk_scroll.grid(column=0, row=4, padx=3, pady=3, sticky=(W)) self._spn_maxlines.grid(column=1, row=4, columnspan=3, padx=3, pady=3, sticky=(W)) self._chk_webmap.grid(column=0, row=5, padx=3, pady=3, sticky=(W)) self._scl_mapzoom.grid(column=1, row=5, columnspan=3, sticky=(W)) self._chk_legend.grid(column=0, row=6, padx=3, pady=3, sticky=(W)) self._chk_zerosig.grid(column=1, row=6, columnspan=2, padx=3, pady=3, sticky=(W)) self._chk_datalog.grid(column=0, row=7, padx=3, pady=3, sticky=(W)) self._spn_datalog.grid(column=1, row=7, padx=3, pady=3, sticky=(W)) self._chk_recordtrack.grid(column=0, row=8, columnspan=2, padx=3, pady=3, sticky=(W)) ttk.Separator(self._frm_options).grid(column=0, row=9, columnspan=4, padx=3, pady=3, sticky=(W, E)) self._lbl_ubxconfig.grid(column=0, row=10, padx=3, pady=3, sticky=(W)) self._btn_ubxconfig.grid(column=1, row=10, padx=3, pady=3, sticky=(W)) def _on_ubx_config(self, *args, **kwargs): # pylint: disable=unused-argument """ Open UBX configuration dialog panel. """ self.__app.ubxconfig() def _on_webmap(self): """ Reset webmap refresh timer """ self.__app.frm_mapview.reset_map_refresh() def _on_data_log(self): """ Start or stop data logger """ if self._datalog.get() == 1: self._logpath = self.__app.file_handler.set_logfile_path() if self._logpath is not None: self.__app.set_status("Data logging enabled: " + self._logpath, "green") else: self._datalog.set(False) else: self._logpath = None self._datalog.set(False) # self.__app.file_handler.close_logfile() self.__app.set_status("Data logging disabled", "blue") def _on_record_track(self): """ Start or stop track recorder """ if self._record_track.get() == 1: self._trackpath = self.__app.file_handler.set_trackfile_path() if self._trackpath is not None: self.__app.set_status( "Track recording enabled: " + self._trackpath, "green") else: self._record_track.set(False) else: self._trackpath = None self._record_track.set(False) # self.__app.file_handler.close_trackfile() self.__app.set_status("Track recording disabled", "blue") def _on_data_stream(self): """ Start data file streamer """ self._in_filepath = self.__app.file_handler.open_infile() if self._in_filepath is not None: self.__app.set_status("") self.__app.serial_handler.connect_file() def _reset(self): """ Reset settings to defaults. """ self._protocol.set(MIXED_PROTOCOL) self._format.set(DDD) self._units.set(UMM) self._autoscroll.set(1) self._maxlines.set(300) self._raw.set(False) self._webmap.set(False) self._mapzoom.set(10) self._show_legend.set(True) self._show_zerosig.set(False) self._datalog.set(False) self._record_track.set(False) def enable_controls(self, status: int): """ Public method to enable and disable those controls which depend on connection status. :param int status: connection status as integer (0=Disconnected, 1=Connected to serial, 2=Connected to file, 3=No serial ports available) """ self._frm_serial.set_status(status) self._btn_connect.config( state=(DISABLED if status in (CONNECTED, CONNECTED_FILE, NOPORTS) else NORMAL)) self._btn_disconnect.config( state=(DISABLED if status in (DISCONNECTED, NOPORTS) else NORMAL)) self._chk_datalog.config( state=(DISABLED if status in (CONNECTED, CONNECTED_FILE, NOPORTS) else NORMAL)) self._spn_datalog.config( state=(DISABLED if status in (CONNECTED, CONNECTED_FILE, NOPORTS) else READONLY)) self._chk_recordtrack.config( state=(DISABLED if status in (CONNECTED, CONNECTED_FILE) else NORMAL)) self._btn_connect_file.config( state=(DISABLED if status in (CONNECTED, CONNECTED_FILE) else NORMAL)) self._btn_ubxconfig.config( state=(DISABLED if status in (DISCONNECTED, CONNECTED_FILE, NOPORTS) else NORMAL)) self.__app.menu.options_menu.entryconfig( 0, state=(DISABLED if status in (CONNECTED_FILE, DISCONNECTED, NOPORTS) else NORMAL), ) def get_size(self) -> (int, int): """ Get current frame size. :return: (width, height) :rtype: tuple """ self.update_idletasks() # Make sure we know about any resizing return (self.winfo_width(), self.winfo_height()) def serial_settings(self) -> Frame: """ Return reference to common serial configuration panel :return: reference to serial form :rtype: Frame """ return self._frm_serial @property def protocol(self) -> int: """ Getter for displayed protocols :return: protocol displayed (0=NMEA, 1=UBX, 2=BOTH) :rtype: int """ return self._protocol.get() @property def raw(self) -> int: """ Getter for console display format :return: display format (0 - parsed, 1 = raw) :rtype: int """ return self._raw.get() @property def autoscroll(self) -> int: """ Getter for autoscroll flag :return: scroll setting (0 = no scroll, 1 = auto) :rtype: int """ return self._autoscroll.get() @property def maxlines(self) -> int: """ Getter for max console display lines :return: max lines in console display (default=300) :rtype: int """ return self._maxlines.get() @property def webmap(self) -> int: """ Getter for webmap flag :return: map type (0 = static map, 1 = dynamic web map) :rtype: int """ return self._webmap.get() @property def mapzoom(self) -> int: """ Getter for webmap zoom level :return: webmap zoom level (1-20) :rtype: int """ return self._mapzoom.get() @property def units(self) -> int: """ Getter for display units :return: "UMM" = metric m/s, "UMK" = metric kmph, "UI" = imperial mph, "UIK" = imperial knots :rtype: int """ return self._units.get() @property def format(self) -> str: """ Getter for degrees format :return: "DD.D" = decimal degrees, "DM.M" = degrees, decimal minutes, "D.M.S" = degrees, minutes, seconds :rtype: str """ return self._format.get() @property def infilepath(self) -> str: """ Getter for input file path :return: input file path :rtype: str """ return self._in_filepath @property def outfilepath(self) -> str: """ Getter for output file path :return: output file path :rtype: str """ return self._logpath @property def datalogging(self) -> int: """ Getter for datalogging flag :return: 0 = no log, 1 = record datalog :rtype: int """ return self._datalog.get() @property def logformat(self) -> str: """ Getter for datalogging format :return: "Raw", "Parsed", "Both" :rtype: str """ return self._logformat.get() @property def record_track(self) -> int: """ Getter for record track flag :return: 0 = no track, 1 = record track :rtype: int """ return self._record_track.get() @property def show_zero(self) -> int: """ Getter for zero signal flag :return: 0 = exclude, 1 = include :rtype: int """ return self._show_zerosig.get() @property def show_legend(self) -> int: """ Getter for graph legend flag :return: 0 = hide, 1 = show :rtype: int """ return self._show_legend.get()
def _make_angle_boxes(self, *args): menu = self._progparams['n_angles'] n = menu.get() # this is the value chosen for number of angles prevparams = [ ] # making an empty array for previous options, so you don't lose your settings on re-render if 'angleparams' in self._progparams.keys( ): # if there are user entered angle settings for box in self._progparams[ 'angleparams']: # for angle box in previous settings entry = [] # create entry tosave those settings to for i, widget in enumerate( box): # for each widget in previous settings if i == 0 or i == 2: # these are the indicies for the angle and curve amount variables entry.append( widget.get()) # add the values to the entry widget.grid_forget() # remove the old box from the frame prevparams.append( entry) # add the entry to the list of previous parameters # doing some cleanup from the last run of this method self._progparams['angleparams'] = [] if 'turncycle' in self._parameters.keys(): self._parameters['turncycle'].grid_forget() if 'jank' in self._parameters.keys(): self._parameters['jank'].grid_forget() self._progparams['anglevariables'] = [] for i in range(n): # n is the number of angles we are setting anglevar = StringVar() anglevar.trace('w', self.set_angles) anglebox = Entry(self._spacedarea, width=5, textvariable=anglevar) label1 = Label(self._spacedarea, text=f"angle {str(i + 1)}") curvevar = StringVar() curvevar.trace('w', self.set_angles) curvebox = Entry(self._spacedarea, width=5, textvariable=curvevar) label2 = Label(self._spacedarea, text=f"curve {str(i + 1)}") if len(prevparams) > i: anglevar.set(prevparams[i][0]) curvevar.set(prevparams[i][1]) else: if i == 0: anglevar.set(125) curvevar.set(5) else: anglevar.set(0) curvevar.set(0) if i == 1: turncycle = Scale(self._spacedarea, orient='horizontal', from_=0, to=5, label='turn cycle') turncycle.grid(row=9, column=100, rowspan=3) jank = Scale(self._spacedarea, orient='horizontal', from_=0, to=600, label="jank") jank.grid(row=12, column=100, rowspan=3) self._parameters['turncycle'] = turncycle self._parameters['jank'] = jank col = 20 * ( i + 1 ) # just so that I have flexibility in positioning things later if I make changes label1.grid(row=9, column=col, pady=10) anglebox.grid(row=10, column=col, padx=20) label2.grid(row=12, column=col, padx=20) curvebox.grid(row=14, column=col) self._progparams['angleparams'].append( [anglebox, label1, curvebox, label2]) self._progparams['anglevariables'].append([anglevar, curvevar]) self.set_angles()
class Application(Frame): def __init__(self, master=None): Frame.__init__(self, master) self.pack() self.createWidgets() def generate(self): n = int(self.menu_gen.get()) seed = self.inp_seed.get() self.output = Generator.convert(seed, n) if len(self.output) > 0: self.generated = True self.butt_draw.config( state= 'normal') self.chek_fullscrn.config(state= 'normal') self.clearOutput(self.output) def draw(self, n, step=False): p1, p2 = Draw.move(n) self.curr_canvas.create_line(p1[0], p1[1], p2[0], p2[1], fill= self.color, width= self.thick) if step: self.curr_canvas.update_idletasks() def do(self, action, step, rainbow): if len(action) > 1: p = action[1] else: p = 1.0 self.timebuff += step cmd = action[0].lower() if cmd == "draw": if rainbow: self.incColor() if self.incThickYN: self.incThick(self.reverseThick, False) elif self.incThickYN: self.incThick(self.reverseThick, True) if self.timebuff > 1.0: truncate = int(self.timebuff) self.after(truncate, self.draw(float(p), True)) self.timebuff -= truncate else: self.draw(float(p)) elif cmd == "turn": Draw.turn(float(p)) elif cmd == "skip": Draw.skip(float(p)) elif cmd == "back": Draw.back(float(p)) elif cmd == "color": if not rainbow: self.color = Color.getHexString(p) elif cmd == "thick": self.thick = int(p) else: print("Unknown command " + cmd) def drawAll(self, newWindow= True): if self.generated == True: self.butt_print.config(state= 'disabled') self.timebuff = 0.0 self.color = Color.white() self.thick = 2 l = float(self.slid_linesize.get()) a = float(self.slid_angle.get()) Draw.init(self.startingPoint, l, a) if self.fullScreen.get() == 1: if newWindow: self.curr_canvas = dc.BigCanvas(self).canvas self.canvas.delete("all") else: self.curr_canvas = self.canvas self.curr_canvas.delete("all") self.curr_canvas.config(bg= Color.getHexString(self.bgColor.get())) rainbow = self.rainbowCheck.get() == 1 if rainbow or self.incThickYN: self.incStep = 1.0/float(self.getDrawCount(self.output)) self.percent = 0.0 for c in self.output: if c == '[': Draw.push() elif c == ']': Draw.pop() else: for r in Rule.getDrawings(): if c == r[0]: if len(r) > 2: params = (r[1], r[2]) else: params = (r[1],) s = float(self.slid_timer.get()) self.do(params, s, rainbow) break self.butt_print.config(state= 'normal') def incColor(self): self.color = Color.getValueByPercent(self.percent) self.percent += self.incStep def incThick(self, reverse, incYN): maxthick = 5 minthick = 1 diff = maxthick - minthick if reverse: result = maxthick - int(diff * self.percent) else: result = minthick + int(diff * self.percent) self.thick = result if incYN: self.percent += self.incStep def getDrawCount(self, s): draw_commands = [] for r in Rule.getDrawings(): if r[1].lower() == "draw": draw_commands.append(r[0]) draw_count = 0; for c in s: for d in draw_commands: if c == d: draw_count += 1 break return draw_count def clearOutput(self, replacement=None): self.text_output.config(state= 'normal') self.text_output.delete(1.0, END) if replacement: self.text_output.insert(END, replacement) self.text_output.config(state= 'disabled') def formatRules(self, rules): ret = [] for r in rules: entry = r[0] + " | " + r[1] if len(r) > 2: entry += " " + r[2] ret.append(entry) return ret def getRuleFromFormatted(self, s): if s: rule = s.split('|') rule[0] = rule[0].strip() rule[1] = rule[1].strip() prod = rule[1].split(" ") if len(prod) == 1: return (rule[0], prod[0]) else: return (rule[0], prod[0], prod[1]) def RefreshLists(self): self.list_prod.delete(0, END) self.list_draw.delete(0, END) l = self.formatRules(Rule.getProductions()) for p in l: self.list_prod.insert(END, p) l = self.formatRules(Rule.getDrawings()) for d in l: self.list_draw.insert(END, d) def AddProductionRule(self, edit=None): rule = dp.AddProductionRuleDialog(self, edit).result if rule: if edit: Rule.removeProd(edit[0]) Rule.AddProduction(rule) self.RefreshLists() def AddDrawingRule(self, edit=None): rule = dd.AddDrawingRuleDialog(self, edit).result if rule: if edit: Rule.removeDraw(edit[0]) Rule.AddDrawing(rule) self.RefreshLists() def EditProductionRule(self): s = self.list_prod.curselection() if s: idx = s[0] rule = (idx,) + self.getRuleFromFormatted(self.list_prod.get(idx)) if rule: self.AddProductionRule(rule) def EditDrawingRule(self): s = self.list_draw.curselection() if s: idx = s[0] rule = (idx,) + self.getRuleFromFormatted(self.list_draw.get(idx)) if rule: self.AddDrawingRule(rule) def DeleteProductionRule(self): s = self.list_prod.curselection() if s: Rule.removeProd(s[0]) self.RefreshLists() def DeleteDrawingRule(self): s = self.list_draw.curselection() if s: Rule.removeDraw(s[0]) self.RefreshLists() def packOutput(self): ret = "" ret += self.packAxiom() ret += self.packProdRules() ret += self.packDrawRules() return ret def packAxiom(self): return "@" + str(self.inp_seed.get()).strip() def packRules(self, rules): ret = "@" for r in rules: ret += "$" + str(r[0]) + "|" + str(r[1]) if len(r) > 2: ret += ":" + str(r[2]) return ret def packProdRules(self): return self.packRules(Rule.getProductions()) def packDrawRules(self): return self.packRules(Rule.getDrawings()) def parseProdRules(self, raw): rules = raw.split('$') for rule in rules: if rule is not "": r = rule.split('|') Rule.AddProduction((r[0], r[1])) def parseDrawRules(self, raw): rules = raw.split('$') for rule in rules: if rule is not "": r = rule.split('|') p = r[1].split(':') if len(p) == 1: tup = (r[0], p[0]) else: tup = (r[0], p[0], p[1]) Rule.AddDrawing(tup) def parseSaveFile(self, s): Rule.wipe() settings = s.split('@') self.inp_seed.set(str(settings[1])) self.parseProdRules(settings[2]) self.parseDrawRules(settings[3]) self.RefreshLists() def save(self): try: filename = filedialog.asksaveasfilename(**self.file_options['txt']) if filename: f = open(filename, 'w') f.write(self.packOutput()) f.close() except Exception as e: print("File IO error in save\n", e) def load(self): try: filename = filedialog.askopenfilename(**self.file_options['txt']) if filename: f = open(filename, 'r') self.parseSaveFile(f.read()) f.close() self.slid_linesize.set(1.0) self.slid_timer.set(0.0) self.menu_gen.set(1) self.clearOutput() except Exception as e: print("File IO error in load\n" + e) def help(self): help.HelpDialog(self) def saveImage(self): filename = filedialog.asksaveasfilename(**self.file_options['ps']) self.curr_canvas.postscript(file=filename, colormode='color') def click(self, event): self.startingPoint = (event.x, event.y) def clickAndRedraw(self, event): self.click(event) self.drawAll(False) def fileOptions(self): self.file_options = {} txt_options = {} ps_options = {} txt_options['defaultextension'] = '.txt' txt_options['filetypes'] = [('Plaintext', '.txt')] txt_options['initialdir'] = 'Patterns' ps_options['defaultextension'] = '.ps' ps_options['filetypes'] = [('Postscript Image', '.ps')] ps_options['initialdir'] = 'Images' self.file_options['txt'] = txt_options self.file_options['ps'] = ps_options def makeMenuBar(self): self.menubar = Menu(self); self.menubar.add_command(label="Save", command= self.save) self.menubar.add_command(label="Load", command= self.load) self.menubar.add_command(label="Help", command= self.help) root.config(menu= self.menubar) def makeInputFrame(self): self.inp_seed = String() self.bgColor = String() self.gen_value = Int() self.rainbowCheck = Int() self.fram_input = Frame(self, bd= 2, relief= self.style, width= input_frame_width, height= input_frame_height) self.fram_seed = Frame(self.fram_input, bd= 1, relief= self.style) self.fram_prod = Frame(self.fram_input, bd= 1, relief= self.style) self.fram_draw = Frame(self.fram_input, bd= 1, relief= self.style) self.fram_drawParams = Frame(self.fram_input, bd= 1, relief= self.style) self.fram_gen = Frame(self.fram_input, bd= 1, relief= self.style) self.fram_output = Frame(self.fram_input, bd= 1, relief= self.style) self.menu_gen = DropDown(self.fram_gen, textvariable= self.gen_value, state= 'readonly') self.entr_seed = Input(self.fram_seed, textvariable= self.inp_seed) self.text_output = Output(self.fram_output, width= 35, height= 10) self.scrl_output = Scrollbar(self.fram_output) self.list_prod = List(self.fram_prod, selectmode= BROWSE, font= "Courier 8", height= 5) self.list_draw = List(self.fram_draw, selectmode= BROWSE, font= "Courier 8", height= 5) self.slid_linesize = Slider(self.fram_drawParams, from_= 0.1, to= 10.0, orient= HORIZONTAL, resolution= 0.1, length= 180) self.slid_timer = Slider(self.fram_drawParams, from_= 0, to= 2, orient= HORIZONTAL, resolution= 0.02, length= 180) self.slid_angle = Slider(self.fram_drawParams, from_= 0, to= 359, orient= HORIZONTAL, length= 180) self.entr_bgcolor = Input (self.fram_drawParams, textvariable= self.bgColor) self.butt_prodAdd = Button(self.fram_prod, text= "Add", width=8, command= self.AddProductionRule) self.butt_prodEdit = Button(self.fram_prod, text= "Edit", width=8, command= self.EditProductionRule) self.butt_prodDelete = Button(self.fram_prod, text= "Delete", width=8, command= self.DeleteProductionRule) self.butt_drawAdd = Button(self.fram_draw, text= "Add", width=8, command= self.AddDrawingRule) self.butt_drawEdit = Button(self.fram_draw, text= "Edit", width=8, command= self.EditDrawingRule) self.butt_drawDelete = Button(self.fram_draw, text= "Delete", width=8, command= self.DeleteDrawingRule) self.chek_incColor = CheckBox(self.fram_draw, text= "Rainbow", variable= self.rainbowCheck) Label(self.fram_seed, text= "Axiom:", width=8).grid (row=0, column=0) Label(self.fram_prod, text= "Production\nRules:", width=8).grid (row=0, column=0) Label(self.fram_draw, text= "Drawing\nRules:", width=8).grid (row=0, column=0) Label(self.fram_drawParams, text= "Line Size:").grid (row=0, column=0) Label(self.fram_drawParams, text= "Delay (ms):").grid (row=1, column=0) Label(self.fram_drawParams, text= "Starting Angle:").grid (row=2, column=0) Label(self.fram_drawParams, text= "Background Color:").grid (row=3, column=0) Label(self.fram_output, text= "Output:").grid (row=0, column=0) Label(self.fram_gen, text= "Generations:").grid (row=0, column=0) self.gen_value.set(1) self.menu_gen['values'] = tuple(range(1, 13)) self.slid_linesize.set(1.0) self.bgColor.set( Color.default() ) self.text_output.config(state='disabled', yscrollcommand= self.scrl_output.set) self.scrl_output.config(command=self.text_output.yview) self.fram_input.grid (row=0, column=0) self.fram_seed.grid (row=1, column=0, sticky= 'ew') self.fram_prod.grid (row=2, column=0, sticky= 'ew') self.fram_draw.grid (row=3, column=0, sticky= 'ew') self.fram_drawParams.grid (row=4, column=0, sticky= 'ew') self.fram_gen.grid (row=5, column=0, sticky= 'ew') self.fram_output.grid (row=6, column=0, sticky= 'ew') self.entr_seed.grid (row=0, column=1, sticky= 'ew') self.list_prod.grid (row=0, column=1, sticky= 'ew') self.butt_prodAdd.grid (row=1, column=0, sticky= 'ew') self.butt_prodEdit.grid (row=1, column=1, sticky= 'ew') self.butt_prodDelete.grid (row=1, column=2, sticky= 'ew') self.list_draw.grid (row=0, column=1) self.butt_drawAdd.grid (row=1, column=0, sticky= 'ew') self.butt_drawEdit.grid (row=1, column=1, sticky= 'ew') self.butt_drawDelete.grid (row=1, column=2, sticky= 'ew') self.chek_incColor.grid (row=0, column=2) self.slid_linesize.grid (row=0, column=1, sticky= 'ew') self.slid_timer.grid (row=1, column=1, sticky= 'ew') self.slid_angle.grid (row=2, column=1, sticky= 'ew') self.entr_bgcolor.grid (row=3, column=1, sticky= 'ew') self.menu_gen.grid (row=0, column=1, sticky= 'ew') self.text_output.grid (row=1, column=0) self.scrl_output.grid (row=1, column=1, sticky= 'ns') def makeCanvasFrame(self): self.fram_canvas = Frame(self, bd=10, relief=self.style) self.canvas = Canvas(self.fram_canvas, width= canvas_width, height= canvas_height) self.fram_canvas.grid(row=0, column=1, sticky='nesw') self.canvas.grid(sticky='nesw') self.canvas.bind("<Button-1>", self.click) self.curr_canvas = self.canvas def makeIgnitionFrame(self): self.fullScreen = Int() self.fram_ignition = Frame(self, bd=4, relief=self.style, width= ignition_frame_width, height= ignition_frame_height) self.butt_generate = Button(self.fram_ignition, text= " -- GENERATE -- ", width=111, command= self.generate) self.butt_draw = Button(self.fram_ignition, text= " -- DRAW -- ", width=100, command= self.drawAll, state= 'disabled') self.butt_print = Button(self.fram_ignition, text= "Save Image", command= self.saveImage, state= 'disabled') self.chek_fullscrn = CheckBox(self.fram_ignition, text= "Fullscreen", variable= self.fullScreen, state= 'disabled') self.fram_ignition.grid(row=1, column=0, columnspan=2) self.butt_generate.grid(row=0, column=0, columnspan=2) self.butt_draw.grid( row=1, column=0) self.butt_print.grid( row=0, column=2, rowspan= 2, sticky='ns') self.chek_fullscrn.grid(row=1, column=1) def createWidgets(self): self.incThickYN = False self.reverseThick = False self.style = RIDGE self.startingPoint = (20, 20) self.generated = False self.fileOptions() self.makeMenuBar() self.makeInputFrame() self.makeCanvasFrame() self.makeIgnitionFrame()
relief=FLAT, bg=BG, bd=0, orient=HORIZONTAL, sliderlength=20, sliderrelief=GROOVE, highlightthickness=0, length=300, fg="gray20", troughcolor=FIELD_BG, tickinterval=tick_interval, state=DISABLED, command=updateAmt, ) tweet_scale.grid(row=7, column=1) # RUN DETECTOR BUTTON run_detector_button = Button( root, text="Run detector", bg=BUTTON_DISABLED_BG, fg="snow", font=DEFAULTFONT, justify=CENTER, padx=10, pady=5, bd=0, state=DISABLED, command=runDetector, )
class View(): def __init__(self, master): self.width = 600 self.height = 600 self.root = master self.root.geometry("600x600") # self.root.bind('<ButtonPress-1>', self.TestEvent) self.left_frame = Frame(self.root, width=600) self.left_frame.pack_propagate(0) self.left_frame.pack(fill='both', side='left', expand='True') self.retrieval_frame = Frame(self.root, bg='snow3') self.retrieval_frame.pack_propagate(0) self.retrieval_frame.pack(fill='both', side='right', expand='True') self.bg_frame = Frame(self.left_frame, bg='snow3', height=600, width=600) self.bg_frame.pack_propagate(0) self.bg_frame.pack(fill='both', side='top', expand='True') # self.bg_frame.grid(row=0, column=0,padx=30, pady=30) self.command_frame = Frame(self.left_frame, bg='snow3') self.command_frame.pack_propagate(0) self.command_frame.pack(fill='both', side='bottom', expand='True') # self.command_frame.grid(row=1, column=0,padx=0, pady=0) self.bg = Canvas(self.bg_frame, width=self.width, height=self.height, bg='gray') self.bg.place(relx=0.5, rely=0.5, anchor='center') self.mani = Canvas(self.retrieval_frame, width=1024, height=1024, bg='gray') self.mani.grid(row=0, column=0, padx=0, pady=42) # print(self.bg.start.x,self.bg.start.y) self.SetCommand() def run(self): self.root.mainloop() # def TestEvent(self,event): # print(event.widget,event.x,event.y) def helloCallBack(self): category = self.set_category.get() # print('####',category) # box=self.bg.box # messagebox.showinfo( "Hello Python",str(box[0])) messagebox.showinfo("Hello Python", category) def SetCommand(self): # tmp = Label(self.command_frame, text="dataset", width=10,bg='snow3') # tmp.grid(row=0, column=0,padx=0, pady=0) # names=['None','ffhq','car','cat'] # self.set_category = ttk.Combobox(self.command_frame, # values=names,width=10) # self.set_category.current(0) # self.set_category.grid(row=0, column=2, padx=10, pady=10) tmp = Label(self.command_frame, text="neutral", width=10, bg='snow3') tmp.grid(row=1, column=0, padx=10, pady=10) tmp = Label(self.command_frame, text="a photo of a", width=10, bg='snow3') tmp.grid(row=1, column=1, padx=10, pady=10) self.neutral = Text(self.command_frame, height=2, width=30) self.neutral.grid(row=1, column=2, padx=10, pady=10) tmp = Label(self.command_frame, text="target", width=10, bg='snow3') tmp.grid(row=2, column=0, padx=10, pady=10) tmp = Label(self.command_frame, text="a photo of a", width=10, bg='snow3') tmp.grid(row=2, column=1, padx=10, pady=10) self.target = Text(self.command_frame, height=2, width=30) self.target.grid(row=2, column=2, padx=10, pady=10) # self.set_p = Button(self.command_frame, text="Set Parameters")#,command= self.helloCallBack) # self.set_p.grid(row=2, column=3, padx=10, pady=10) tmp = Label(self.command_frame, text="strength", width=10, bg='snow3') tmp.grid(row=3, column=0, padx=10, pady=10) self.alpha = Scale(self.command_frame, from_=-15, to=25, orient=HORIZONTAL, bg='snow3', length=250, resolution=0.01) self.alpha.grid(row=3, column=2, padx=10, pady=10) tmp = Label(self.command_frame, text="disentangle", width=10, bg='snow3') tmp.grid(row=4, column=0, padx=10, pady=10) self.beta = Scale(self.command_frame, from_=0.08, to=0.4, orient=HORIZONTAL, bg='snow3', length=250, resolution=0.001) self.beta.grid(row=4, column=2, padx=10, pady=10) self.reset = Button(self.command_frame, text='Reset') self.reset.grid(row=5, column=1, padx=10, pady=10) self.set_init = Button(self.command_frame, text='Accept') self.set_init.grid(row=5, column=2, padx=10, pady=10)
class MainGUI(): def __init__(self, parent, fileName): self.DotTracking = DotTracking(fileName) frame = Frame(parent) frame.pack() #HUE self.label1 = Label(frame, text="Hue Min:") self.label1.grid(row=0, column=1) self.Hue_min = Scale(frame, from_=0, to=180, orient=HORIZONTAL, command=self.sliderUpdateMin) self.Hue_min.set(45) self.Hue_min.grid(row=0, column=2) self.label2 = Label(frame, text="Hue Max:") self.label2.grid(row=1, column=1) self.Hue_max = Scale(frame, from_=0, to=180, orient=HORIZONTAL, command=self.sliderUpdateMax) self.Hue_max.set(85) self.Hue_max.grid(row=1, column=2) #SAT self.label3 = Label(frame, text="Sat Min:") self.label3.grid(row=2, column=1) self.Sat_min = Scale(frame, from_=0, to=255, orient=HORIZONTAL, command=self.sliderUpdateMin) self.Sat_min.set(80) self.Sat_min.grid(row=2, column=2) self.label4 = Label(frame, text="Sat Max:") self.label4.grid(row=3, column=1) self.Sat_max = Scale(frame, from_=0, to=255, orient=HORIZONTAL, command=self.sliderUpdateMax) self.Sat_max.set(255) self.Sat_max.grid(row=3, column=2) #VAL self.label5 = Label(frame, text="Val Min:") self.label5.grid(row=4, column=1) self.Val_min = Scale(frame, from_=0, to=255, orient=HORIZONTAL, command=self.sliderUpdateMin) self.Val_min.set(80) self.Val_min.grid(row=4, column=2) self.label6 = Label(frame, text="Val Max:") self.label6.grid(row=5, column=1) self.Val_max = Scale(frame, from_=0, to=255, orient=HORIZONTAL, command=self.sliderUpdateMax) self.Val_max.set(255) self.Val_max.grid(row=5, column=2) #SIZE self.label7 = Label(frame, text="Size:") self.label7.grid(row=6, column=1) self.Size_setting = Scale(frame, from_=1000, to=7000, orient=HORIZONTAL, command=self.updateSize) self.Size_setting.set(5000) self.Size_setting.grid(row=6, column=2) #Buttons self.TestButton = Button(frame, text="Test", command=self.runTest) self.TestButton.grid(row=7, column=1) self.StartButton = Button(frame, text="Run", command=self.runAnalyze) self.StartButton.grid(row=7, column=2) self.LiveButton = Button(frame, text="Live", command=self.LiveStream) self.LiveButton.grid(row=7, column=3) # start_thread = threading.Thread(target=self.DotTracking.Start) # start_thread.start() #self.DotTracking.Start() def sliderUpdateMax(self, *args): if self.Hue_max.get() < self.Hue_min.get(): self.Hue_max.set(self.Hue_min.get()) if self.Sat_max.get() < self.Sat_min.get(): self.Sat_max.set(self.Sat_min.get()) if self.Val_max.get() < self.Val_min.get(): self.Val_max.set(self.Val_min.get()) self.updateHSV() def sliderUpdateMin(self, *args): if self.Hue_min.get() > self.Hue_max.get(): self.Hue_min.set(self.Hue_max.get()) if self.Sat_min.get() > self.Sat_max.get(): self.Sat_min.set(self.Sat_max.get()) if self.Val_min.get() > self.Val_max.get(): self.Val_min.set(self.Val_max.get()) self.updateHSV() def runTest(self, *args): self.DotTracking.test = True start_thread = threading.Thread(target=self.DotTracking.Start) start_thread.start() def runAnalyze(self, *args): self.DotTracking.test = False self.DotTracking.user = simpledialog.askstring("Input", "Enter user name:", parent=parent) start_thread = threading.Thread(target=self.DotTracking.Start) start_thread.start() def updateSize(self, *args): self.DotTracking.min_contour_size = self.Size_setting.get() def updateHSV(self, *args): self.DotTracking.h_low = self.Hue_min.get() self.DotTracking.h_high = self.Hue_max.get() self.DotTracking.s_low = self.Sat_min.get() self.DotTracking.s_high = self.Sat_max.get() self.DotTracking.v_low = self.Val_min.get() self.DotTracking.v_high = self.Val_max.get() def LiveStream(self, *args): self.DotTracking.live = True start_thread = threading.Thread(target=self.DotTracking.Start) start_thread.start() self.DotTracking.live = False
class Application(tk.Frame): def __init__(self, master=None): super().__init__(master) self.master = master self.grid(padx=4, pady=0) self.window_width = 1850 self.window_height = 900 self._geom = '{x}x{y}+0+0'.format(x=self.window_width, y=self.window_height) self.master.geometry(self._geom) self.image_size = 450 self.canvases = dict() self.scale_value = DoubleVar() self.create_window() self.create_widgets() #fullscreen #pad = 3 #master.geometry("{0}x{1}+0+0".format( # master.winfo_screenwidth()-pad, master.winfo_screenheight()-pad)) #master.bind('<Escape>',self.toggle_geom) def create_widgets(self): self.create_buttons() #self.create_scroll_bar() self.create_canvases() self.create_parameters_box() self.create_progressbar() self.set_default_values() def create_buttons(self): #upload button self.upload_input_button = tk.Button(self, text="Wgraj obraz", command=self.upload_input_file, width=50, height=3, fg='white', bg='green') self.upload_input_button.grid(row=12, column=0, pady=15) #transform start button self.start_transform_button = tk.Button(self, text="Uruchom tomograf", command=start_radon_transform, width=50, height=3, fg='white', bg='green') self.start_transform_button.grid(row=13, column=0, pady=15) def create_window(self): self.frame = Frame(self.master, width=self.window_width, height=self.window_height) def upload_input_file(self): filename = filedialog.askopenfilename(filetypes=[('Image', 'jpg jpeg png gif')]) if filename == "": return load_input_file(filename) img = Image.open(filename) self.set_image_on_canvas(img, ImageType.INPUT_IMAGE) self.reconstruction_progress['value'] = 0 def set_image_on_canvas(self, img, image_type): canvas = self.canvases[image_type] if type(img) is np.ndarray: img = Image.frombytes('L', (img.shape[1], img.shape[0]), img.astype('b').tostring()) img = img.resize((canvas.winfo_width(), canvas.winfo_height()), Image.ANTIALIAS) self.canvases[image_type].image = ImageTk.PhotoImage(img) self.canvases[image_type].create_image(0, 0, image=canvas.image, anchor=tk.NW) self.update() def create_canvases(self): x = 0 for i in ImageType: self.canvases[i] = Canvas(self, width=self.image_size, height=self.image_size, bg='white') self.canvases[i].create_rectangle(2, 2, self.image_size, self.image_size) self.canvases[i].create_text(self.image_size // 2, self.image_size // 2, text=text_values[i]) if i == ImageType.GRAPH: continue #self.canvases[i].grid(row=1, column=2, rowspan=15) else: self.canvases[i].grid(row=0, column=x) x += 1 def create_scroll_bar(self): self.scale = Scale(self, from_=0, to_=150, tickinterval=10, length=self.image_size - 20, variable=self.scale_value, orient=tk.HORIZONTAL) self.scale.bind("<ButtonRelease-1>", method) self.scale.set(0) self.scale.grid(row=2, column=2) def create_parameters_box(self): default_font = ("Helvetica", 9) #error label self.error = tk.StringVar() tk.Label(self, textvariable=self.error, fg="red", font=("Helvetica", 16)).grid(row=2) tk.Label(self, text="Liczba emiterów", font=default_font).grid(row=3, sticky='w') self.detectors_number = tk.Entry(self, width=4, justify=tk.RIGHT) self.detectors_number.grid(row=3) tk.Label(self, text="Rozpiętość kątowa", font=default_font).grid(row=4, sticky='w') self.emission_angle = tk.Entry(self, width=4, justify=tk.RIGHT) self.emission_angle.grid(row=4) tk.Label(self, text="Obrót tomografu", font=default_font).grid(row=5, sticky='w') self.radon_angle = tk.Entry(self, width=4, justify=tk.RIGHT) self.radon_angle.grid(row=5) tk.Label(self, text="Krok", font=default_font).grid(row=6, sticky='w') self.step_angle = tk.Entry(self, width=4, justify=tk.RIGHT) self.step_angle.grid(row=6) self.sinogram_convolution = tkinter.IntVar(value=1) self.sinogram_convoltion_checkbox = tk.Checkbutton( self, text="Użyj splotu przy sinorgamie", variable=self.sinogram_convolution, command=self.update_options) self.sinogram_convoltion_checkbox.grid(row=7, sticky='w') self.use_parallel_rays = tkinter.IntVar(value=1) self.parallel_rays_checkbox = tk.Checkbutton( self, text="Użyj promieni równoległych", variable=self.use_parallel_rays, command=self.update_options) self.parallel_rays_checkbox.grid(row=8, sticky='w') self.use_fourier = tkinter.IntVar(value=1) self.fourier_checkbox = tk.Checkbutton( self, text="Użyj rekonstrukcji Fouriera", variable=self.use_fourier, command=self.update_options) self.fourier_checkbox.grid(row=9, sticky='w') self.use_convolution_at_end = tkinter.IntVar(value=1) self.convolution_end_checkbutton = tk.Checkbutton( self, text="Użyj splotu na wyjściu", variable=self.use_convolution_at_end, command=self.update_options) self.convolution_end_checkbutton.grid(row=10, sticky='w') def set_default_values(self): self.sinogram_convolution.set(1 if main.use_convolution_filter else 0) self.use_parallel_rays.set(1 if main.parallel_rays_mode else 0) self.use_convolution_at_end.set( 1 if main.use_convolution_in_output else 0) self.use_fourier.set(1 if main.use_fourier_reconstruction else 0) self.detectors_number.insert(tk.END, main.n_detectors) self.radon_angle.insert(tk.END, main.radon_angle) self.emission_angle.insert(tk.END, main.emission_angle) self.step_angle.insert(tk.END, main.step_angle) self.reset_progressbar() def update_options(self): main.use_convolution_in_output = False if self.use_convolution_at_end.get( ) == 0 else True main.use_fourier_reconstruction = False if self.use_fourier.get( ) == 0 else True main.use_convolution_filter = False if self.sinogram_convolution.get( ) == 0 else True main.parallel_rays_mode = False if self.use_parallel_rays.get( ) == 0 else True def create_progressbar(self): self.reconstruction_progress = ttk.Progressbar(self, orient="horizontal", length=self.image_size, mode="determinate") self.reconstruction_progress.grid(row=1, column=3, rowspan=2) def reset_progressbar(self): self.reconstruction_progress['value'] = 0 ratio = main.radon_angle // main.step_angle * main.step_angle self.reconstruction_progress['maximum'] = ratio
def main(): def switchFrame(current_frame, todisplay_frame): current_frame.grid_forget() todisplay_frame.grid(row = 0, column = 0, padx = 60, pady = 30) tk = Tk() tk.title("BaseConverter") tk.tk_setPalette(background="#FFFFFF") menu = Menu(master = tk, bg = "#DDDDDD", activebackground = "#999999") menu.add_command(label = "Switch to complete converter", command = lambda : [switchFrame((classicFrame if frameDisplayed.get() == 0 else completeFrame), (completeFrame if frameDisplayed.get() == 0 else classicFrame)), frameDisplayed.set((1 if frameDisplayed.get() == 0 else 0)), menu.entryconfig(index = 1, label = ("Switch to complete converter" if frameDisplayed.get() == 0 else "Switch to quick converter"))]) tk.config(menu = menu) frameDisplayed = BooleanVar() # 0 = classic, 1 = complete frameDisplayed.set(0) ##### classic frame ##### classicFrame = Frame(master = tk, background = "#FFFFFF") decimalVar = IntVar() entryDecimal = Entry(master = classicFrame, textvariable = decimalVar, background = "#F8F8F8") hexaVar = StringVar() entryHexa = Entry(master = classicFrame, textvariable = hexaVar, background = "#F8F8F8") binaryVar = StringVar() entryBinary = Entry(master = classicFrame, textvariable = binaryVar, background = "#F8F8F8") decimalLabel = Label(master = classicFrame, text = "Decimal") hexaLabel = Label(master = classicFrame, text = "Hexadecimal") binaryLabel = Label(master = classicFrame, text = "Binary") convertButton1 = Button(master = classicFrame, text = "Convert", command = lambda : conversion(decimalVar, hexaVar, binaryVar), relief = GROOVE) classicFrame.grid(row = 0, column = 0, padx = 60, pady = 30) decimalLabel.grid(row = 0, column = 0, pady = 10, padx = 5, sticky = W) entryDecimal.grid(row = 0, column = 1, pady = 10) hexaLabel.grid (row = 1, column = 0, pady = 10, padx = 5, sticky = W) entryHexa.grid (row = 1, column = 1, pady = 10) binaryLabel.grid (row = 2, column = 0, pady = 10, padx = 5, sticky = W) entryBinary.grid (row = 2, column = 1, pady = 10) convertButton1.grid(row = 3, column = 0, columnspan = 2, pady = 5) decimalVar.set(0) hexaVar.set(0) binaryVar.set(0) ######################### classic frame ##### complete Frame ##### completeFrame = Frame(master = tk) labelFrom = Label(completeFrame, text = "From base") fromBaseVar = IntVar() fromBaseVar.set(0) baseFrom = Scale(completeFrame, from_ = 2, to = 26, orient = HORIZONTAL, variable = fromBaseVar) fromVar = StringVar() fromVar.set("0") fromEntry = Entry(completeFrame, textvariable = fromVar) labelFrom.grid(row = 0, column = 0, pady = 10, padx = 5, sticky = W) baseFrom.grid (row = 0, column = 1, pady = 10, padx = 5) fromEntry.grid(row = 0, column = 2, pady = 10, padx = 5) labelTo = Label(completeFrame, text = "To base") toBaseVar = IntVar() toBaseVar.set(0) baseFrom = Scale(completeFrame, from_ = 2, to = 26, orient = HORIZONTAL, variable = toBaseVar) toVar = StringVar() toVar.set("0") toEntry = Entry(completeFrame, textvariable = toVar) labelTo.grid (row = 1, column = 0, pady = 10, padx = 5, sticky = W) baseFrom.grid(row = 1, column = 1, pady = 10, padx = 5) toEntry.grid (row = 1, column = 2, pady = 10, padx = 5) convertButton2 = Button(master = completeFrame, text = "Convert", command = lambda : toVar.set(convert(from_n = fromBaseVar.get(), to_m = toBaseVar.get(), number = fromVar.get())), relief = GROOVE) convertButton2.grid(row = 2, column = 0, columnspan = 3, pady = 10) ######################### complete frame tk.mainloop()
class Paint(object): DEFAULT_COLOR = "black" DEFAULT_LINE_SIZE = 1 ITEM_TOKEN = "primitive" def __init__(self): self.root = Tk() self.root.title("Paint") self.line_button = Button(self.root, text="Line", relief=SUNKEN, command=self.select_line) self.line_button.grid(row=0, column=0, padx=2, pady=2) self.rectangle_button = Button(self.root, text="Rectangle", command=self.select_rectangle) self.rectangle_button.grid(row=0, column=1, padx=2, pady=2) self.circle_button = Button(self.root, text="Circle", command=self.select_circle) self.circle_button.grid(row=0, column=2, padx=2, pady=2) self.undo_button = Button(self.root, text="Undo", state=DISABLED, command=self.undo_action) self.undo_button.grid(row=0, column=3, padx=2, pady=2) self.clear_button = Button(self.root, text="Clear", command=self.clear_canvas) self.clear_button.grid(row=0, column=4, padx=2, pady=2) self.color_button = Button(self.root, text="Choose color", command=self.choose_color) self.color_button.grid(row=0, column=5, padx=2, pady=2) self.line_size_scale = Scale(self.root, label="Line size", from_=1, to=10, orient=HORIZONTAL) self.line_size_scale.grid(row=0, column=6, padx=2, pady=2) self.canvas = Canvas(self.root, bg="white", width=600, height=500) self.canvas.grid(row=1, columnspan=7) self.drag_data = {"x": 0, "y": 0, "item": None} # Primitives moving self.canvas.tag_bind(self.ITEM_TOKEN, "<ButtonPress-1>", self.on_primitive_press) self.canvas.tag_bind(self.ITEM_TOKEN, "<ButtonRelease-1>", self.on_primitive_release) self.canvas.tag_bind(self.ITEM_TOKEN, "<B1-Motion>", self.on_primitive_motion) # Primitives editing with toolbox self.canvas.tag_bind(self.ITEM_TOKEN, "<ButtonPress-3>", self.on_primitive_second_edit) self.cords_toolbox = Frame(self.root) self.cords_toolbox.grid(row=1, column=7, sticky=N) self.x1_label = Label(self.cords_toolbox, text="x1") self.x1_label.grid(row=0, sticky=E) self.x1_entry = Entry(self.cords_toolbox) self.x1_entry.insert(END, "0") self.x1_entry.grid(row=0, column=1) self.y1_label = Label(self.cords_toolbox, text="y1") self.y1_label.grid(row=1, sticky=E) self.y1_entry = Entry(self.cords_toolbox) self.y1_entry.insert(END, "0") self.y1_entry.grid(row=1, column=1) self.x2_label = Label(self.cords_toolbox, text="x2") self.x2_label.grid(row=2, sticky=E) self.x2_entry = Entry(self.cords_toolbox) self.x2_entry.insert(END, "0") self.x2_entry.grid(row=2, column=1) self.y2_label = Label(self.cords_toolbox, text="y2") self.y2_label.grid(row=3, sticky=E) self.y2_entry = Entry(self.cords_toolbox) self.y2_entry.insert(END, "0") self.y2_entry.grid(row=3, column=1) self.reset_button = Button(self.cords_toolbox, text="Reset", command=self.reset_coords) self.reset_button.grid(row=5, column=1, sticky=W) self.draw_button = Button(self.cords_toolbox, text="Draw", command=self.draw_shape) self.draw_button.grid(row=5, column=1, sticky=E) self.last_action = None self.active_button = self.line_button self.color = self.DEFAULT_COLOR self.line_size = self.line_size_scale.get() self.x1, self.y1, self.x2, self.y2 = None, None, None, None self.root.mainloop() def set_common_toolbox(self): self.x1_label.config(text="x1") self.y1_label.config(text="y1") self.x2_label.config(text="x2") self.y2_label = Label(self.cords_toolbox, text="y2") self.y2_label.grid(row=3, sticky=E) self.y2_entry = Entry(self.cords_toolbox) self.y2_entry.insert(END, "0") self.y2_entry.grid(row=3, column=1) def set_circle_toolbox(self): self.x1_label.config(text="x") self.y1_label.config(text="y") self.x2_label.config(text="r") self.y2_label.grid_forget() self.y2_entry.grid_forget() def on_primitive_press(self, event): self.drag_data["x"] = event.x self.drag_data["y"] = event.y self.drag_data["item"] = self.canvas.find_closest(event.x, event.y)[0] def on_primitive_release(self, event): self.drag_data["x"] = 0 self.drag_data["y"] = 0 self.drag_data["item"] = None def on_primitive_motion(self, event): delta_x = event.x - self.drag_data["x"] delta_y = event.y - self.drag_data["y"] self.canvas.move(self.drag_data["item"], delta_x, delta_y) self.drag_data["x"] = event.x self.drag_data["y"] = event.y def on_primitive_second_edit(self, event): self.drag_data["item"] = self.canvas.find_closest(event.x, event.y)[0] self.clear_coords() self.insert_editing_primitive_coords() def select_line(self): self.activate_button(self.line_button) log_message("Line selected") def select_rectangle(self): self.activate_button(self.rectangle_button) log_message("Rectangle selected") def select_circle(self): self.activate_button(self.circle_button) log_message("Circle selected") def activate_button(self, button): # If active button is either line or rectangle and now user selects circle then change toolbox to circle if (self.active_button is self.line_button or self.rectangle_button) and button is self.circle_button: self.set_circle_toolbox() # If active button is circle and now user selects others then change toolbox to common elif self.active_button is self.circle_button and button is not self.circle_button: self.set_common_toolbox() self.active_button.config(relief=RAISED) button.config(relief=SUNKEN) self.active_button = button def clear_coords(self): self.x1_entry.delete("0", END) self.y1_entry.delete("0", END) self.x2_entry.delete("0", END) self.y2_entry.delete("0", END) def reset_coords(self): self.drag_data["item"] = None self.clear_coords() self.x1_entry.insert(END, "0") self.y1_entry.insert(END, "0") self.x2_entry.insert(END, "0") self.y2_entry.insert(END, "0") log_message("Coords reset") def insert_editing_primitive_coords(self): primitive = self.drag_data["item"] if primitive is not None: (x1, y1, x2, y2) = self.canvas.coords(primitive) self.x1_entry.insert(END, int(x1)) self.y1_entry.insert(END, int(y1)) self.x2_entry.insert(END, int(x2)) self.y2_entry.insert(END, int(y2)) def draw_shape(self): self.read_line_size() self.read_coords() primitive = self.drag_data["item"] if primitive is not None: self.canvas.coords(primitive, self.x1, self.y1, self.x2, self.y2) self.canvas.itemconfig(primitive, width=self.line_size) self.drag_data["item"] = None self.reset_coords() elif self.active_button is self.line_button: self.draw_line() elif self.active_button is self.rectangle_button: self.draw_rectangle() elif self.active_button is self.circle_button: self.draw_circle() def read_line_size(self): self.line_size = self.line_size_scale.get() def read_coords(self): self.x1 = self.x1_entry.get() self.y1 = self.y1_entry.get() self.x2 = self.x2_entry.get() self.y2 = self.y2_entry.get() def draw_line(self): line = self.canvas.create_line(self.x1, self.y1, self.x2, self.y2, fill=self.color, width=self.line_size, tags=self.ITEM_TOKEN) log_message("Line drawn") self.undo_button.config(state=NORMAL) self.last_action = line def draw_rectangle(self): rectangle = self.canvas.create_rectangle(self.x1, self.y1, self.x2, self.y2, fill=self.color, width=self.line_size, tags=self.ITEM_TOKEN) log_message("Rectangle drawn") self.undo_button.config(state=NORMAL) self.last_action = rectangle def draw_circle(self): x1_ = int(self.x1) - int(self.x2) y1_ = int(self.y1) - int(self.x2) x2_ = int(self.x1) + int(self.x2) y2_ = int(self.y1) + int(self.x2) circle = self.canvas.create_oval(x1_, y1_, x2_, y2_, fill=self.color, width=self.line_size, tags=self.ITEM_TOKEN) log_message("Circle drawn") self.undo_button.config(state=NORMAL) self.last_action = circle def choose_color(self): self.color = askcolor(color=self.color)[1] log_message("Color selected") def undo_action(self): self.canvas.delete(self.last_action) log_message("Undo action") self.undo_button.config(state=DISABLED) def clear_canvas(self): self.canvas.delete(ALL) log_message("Canvas cleared") self.undo_button.config(state=DISABLED)
def creeInterface(a_largeur=LARGEUR_FEN, a_hauteur=HAUTEUR_FEN): global Wroot, Wcanvas, Wlargeur, Whauteur, ValLargeur, ValHauteur, EntreeX, EntreeY, SortieX, SortieY, NewLargeur, NewHauteur global CoulEntreeLbl, CoulEntreeBtn, CoulSortieLbl, CoulSortieBtn, Main, Orient, Replay, DemarrerBtn # Fenêtre principale Wroot = Tk() # Titre de la fenêtre Wroot.title(TITRE + VERSION) # Initialisation de la largeur et hauteur du graphique (et de la sauvegarde utilisée pour resize) NewLargeur = Wlargeur = a_largeur NewHauteur = Whauteur = a_hauteur # Définition de la taille de la fenêtre principale Wroot.geometry( str(a_largeur) + "x" + str(a_hauteur + HAUTEUR_MENU) + "-10+10") # Fonction appelée pour le changement de taille de la fenêtre Wroot.bind('<Configure>', resizeWindow) # Fonction appelée pour le lacher du bouton souris (indique la fin du resize) Wroot.bind('<ButtonRelease>', leaveWindow) # Frame des données dataFrame = Frame(Wroot) # Partie 'Labyrinthe' labyFrame = LabelFrame(dataFrame, text='Labyrinthe') # Première ligne : largeur du labyrinthe Label(labyFrame, text='Largeur').grid(row=0, column=0) ValLargeur = StringVar(Wroot) ValLargeur.set(LARGEUR_DEF) Entry(labyFrame, textvariable=ValLargeur, width=2).grid(row=0, column=1) # Deuxième ligne : hauteur du labyrinthe Label(labyFrame, text='Hauteur').grid(row=1, column=0) ValHauteur = StringVar(Wroot) ValHauteur.set(HAUTEUR_DEF) Entry(labyFrame, textvariable=ValHauteur, width=2).grid(row=1, column=1) # Troisième ligne : bouton 'Créer' Button(labyFrame, text='Créer', command=creerLabyCmd).grid(row=2, column=0, columnspan=1) taille = Scale(labyFrame, from_=CELLULE_MIN, to=CELLULE_MAX, showvalue=False, orient='h', label='Taille hexa', command=largeurCmd) taille.set(CELLULE_INI) taille.grid(row=2, column=1) # Fin de la partie labyFrame labyFrame.grid(row=0, column=0, sticky=tkinter.N + tkinter.S) # Partie 'Entrée' entreeFrame = LabelFrame(dataFrame, text='Entrée') # Abscisse Label(entreeFrame, text="X").grid(row=0, column=0) EntreeX = Scale(entreeFrame, to=LARGEUR_DEF - 1, showvalue=False, orient='h', command=xEntreeCmd) EntreeX.grid(row=0, column=1) # Ordonnée Label(entreeFrame, text="Y").grid(row=1, column=0) EntreeY = Scale(entreeFrame, to=HAUTEUR_DEF - 1, showvalue=False, orient='h', command=yEntreeCmd) EntreeY.grid(row=1, column=1) # Label Couleur CoulEntreeLbl = Label(entreeFrame, text="Couleur", bg=CoulEntree) CoulEntreeLbl.grid(row=2, column=0) # Bouton Couleur CoulEntreeBtn = Button(entreeFrame, text=CoulEntree, bg=CoulEntree, command=coulEntreeCmd) CoulEntreeBtn.grid(row=2, column=1) # Fin de la partie entreeFrame entreeFrame.grid(row=0, column=1, sticky=tkinter.N + tkinter.S) # Partie 'Sortie' sortieFrame = LabelFrame(dataFrame, text='Sortie') # Abscisse Label(sortieFrame, text="X").grid(row=0, column=0) SortieX = Scale(sortieFrame, to=LARGEUR_DEF - 1, showvalue=False, orient='h', command=xSortieCmd) SortieX.grid(row=0, column=1) # Ordonnée Label(sortieFrame, text="Y").grid(row=1, column=0) SortieY = Scale(sortieFrame, to=HAUTEUR_DEF - 1, showvalue=False, orient='h', command=ySortieCmd) SortieY.grid(row=1, column=1) # Label Couleur CoulSortieLbl = Label(sortieFrame, text="Couleur", bg=CoulSortie) CoulSortieLbl.grid(row=2, column=0) # Bouton Couleur CoulSortieBtn = Button(sortieFrame, text=CoulSortie, bg=CoulSortie, command=coulSortieCmd) CoulSortieBtn.grid(row=2, column=1) # Fin de la partie sortieFrame sortieFrame.grid(row=0, column=2, sticky=tkinter.N + tkinter.S) # Partie 'Algo' algoFrame = LabelFrame(dataFrame, text='Algorithme') # Main Label(algoFrame, text='Main').grid(row=0, column=0) Main = StringVar(Wroot) Main.set(MAIN[0]) OptionMenu(algoFrame, Main, *MAIN, command=mainCmd).grid(row=0, column=1) # Orientation Label(algoFrame, text='Orientation').grid(row=1, column=0) Orient = StringVar(Wroot) Orient.set(ORIENTATION[0]) OptionMenu(algoFrame, Orient, *ORIENTATION, command=orientationCmd).grid(row=1, column=1) # Bouton 'Démarrer' DemarrerBtn = Button(algoFrame, text='Démarrer', command=demarrerCmd, state='disabled') DemarrerBtn.grid(row=2, column=0) # Scale 'Replay' Replay = Scale(algoFrame, showvalue=False, orient='h', label='Chemin', command=replayCmd) Replay.grid(row=2, column=1) # Vitesse Label(algoFrame, text='Vitesse').grid(row=0, column=2) Vitesse = StringVar(Wroot) Vitesse.set(VITESSE[1]) OptionMenu(algoFrame, Vitesse, *VITESSE, command=vitesseCmd).grid(row=1, column=2) # Fin de la partie algoFrame algoFrame.grid(row=0, column=3, sticky=tkinter.N + tkinter.S) # Fin de la partie dataFrame et affichage dataFrame.grid(row=0, column=0) # Fenêtre graphique (canvas) Wcanvas = Canvas(Wroot, background='white', width=a_largeur, height=a_hauteur) # Fin de la partie Wcanvas et affichage Wcanvas.grid(row=1, column=0) return
load_image_stop = tk.PhotoImage( file="C:/Users/Lepi/Desktop/CS425/PythonGUI/Pause.png") button_stop = tk.Button(master=frame_media, image=load_image_stop, command=pause_song) button_stop["bg"] = "white" button_stop["border"] = "0" # Generation Options - Time Slider slider_time = Scale(master=frame_options, bg="white", label="Song Length (seconds)", to=600, orient=tk.HORIZONTAL, length=300) slider_time.grid(row=0, column=0) time_value = IntVar() time_entry = Entry(master=frame_options, width=10, textvariable=time_value) time_entry.grid(row=0, column=1) time_button = tk.Button(master=frame_options, bg="white", text="Set", height=1, width=3, command=set_time) time_button.grid(row=0, column=2) # Generation Options - Instrument Selection radio_options = IntVar()
class fromFile_module(baseModule): def __init__(self, parent): baseModule.__init__(self, parent) self._s_fileName = "" self._b_fileLoaded = False self._s_fileType = "" self.__nbleds = 0 self.__nbframes = 0 self.__data = [] self.__colorSH = Color.zero() self.__rainbowHue = 0.0 self.__x = 0 self.mainFrame = Frame(parent) self.mainFrame.grid(sticky=(E, W)) self.populateInterface(self.mainFrame) def populateInterface(self, parent): """ populate interface """ """#################### Rainbow Speed ####################""" self._SV_rainbowSpeed = StringVar(value="30") self._S_rainbowSpeed = Scale(parent, from_=0, to=100, orient=HORIZONTAL, variable=self._SV_rainbowSpeed) self._S_rainbowSpeed.grid(row=0, column=0, columnspan=2, sticky=(E, W)) self._B_rainbowSpeed_Reset = Button(parent, command=self.resetRainbowSpeed, text="reset rainbow speed") self._B_rainbowSpeed_Reset.grid(row=0, column=2) """#################### Speed ####################""" self._SV_SPEED = StringVar(value="60") self._S_SPEED = Scale(parent, from_=10, to=500, orient=HORIZONTAL, variable=self._SV_SPEED) self._S_SPEED.grid(row=1, column=0, columnspan=2, sticky=(E, W)) self._B_SPEED_Reset = Button(parent, command=self.resetSpeed, text="Reset speed") self._B_SPEED_Reset.grid(row=1, column=2) """#################### File selecter ####################""" self._B_selectFile = Button(parent, command=self._selectFile, text="Select file") self._B_selectFile.grid(row=2, column=0) def resetRainbowSpeed(self): self._S_rainbowSpeed.set(30) def resetSpeed(self): self._S_SPEED.set(60) def __readPngFile(self): with open(self._s_file, "rb") as fs: _reader = Reader(file=fs) _data = _reader.read() _colorarray = [] for frame in list(_data[2]): framearray = list(frame) _colorarray.append([ framearray[x:x + 3] for x in range(0, len(framearray), 3) ]) self.__nbleds = _data[0] self.__nbframes = _data[1] self.__data = _colorarray def _selectFile(self): self._s_file = filedialog.askopenfilename(initialdir=".", title="Select file", filetypes=(("png files", "*.png"), )) self._s_fileType = self._s_file.split("_")[1].replace(".png", "") if self._s_fileType not in ["rnb", "fi", "sh"]: self._s_file = "" self._s_fileType = "" self._b_fileLoaded = False else: self.__readPngFile() self._controller.nbLeds = self.__nbleds self._b_fileLoaded = True self.__rainbowHue = 0.0 self.__x = 0 self._parent.resetSpeed() self._S_SPEED.set(int(self._parent.getSpeed())) def _updateRNB(self): self._controller.clear() color = Color.fromHSV(self.__rainbowHue, 1.0, 1.0).mul([1.0, 0.42, 0.3]) for y in range(self.__nbleds): col = color * Color.fromList(self.__data[self.__x][y]) self._controller.buffer[y] = col.toList() self.__rainbowHue += int(self._SV_rainbowSpeed.get()) / 10.0 self.__rainbowHue %= 360.0 self._controller.send() def _updateFI(self): self._controller.clear() for y in range(self.__nbleds): col = Color.fromList(self.__data[self.__x][y]) col.mul([1.0, 0.42, 0.3]) self._controller.buffer[y] = col.toList() self._controller.send() def _updateSH(self): if self.__x == 0: self.__colorSH = Color.randomColor().mul([1.0, 0.42, 0.3]) self._controller.clear() for y in range(self.__nbleds): col = self.__colorSH * Color.fromList(self.__data[self.__x][y]) self._controller.buffer[y] = col.toList() self._controller.send() def __wishedSpeed(self): return int(self._SV_SPEED.get()) def update(self): if self._b_fileLoaded: if self.__wishedSpeed() != self._parent.getSpeed(): self._parent.setSpeed(self.__wishedSpeed()) if self._s_fileType == "rnb": self._updateRNB() elif self._s_fileType == "fi": self._updateFI() elif self._s_fileType == "sh": self._updateSH() else: print("Error while trying to get file type.") self.__x = self.__x + 1 if (self.__x + 1 < self.__nbframes) else 0
class Window(object): """"This class creates a GUI using the built in python libary tkinter""" def __init__(self, window): self.window = window self.check = False self.animateval = False titlel = Label(window, text="Evolutionary Spatial Games", height=3) titlel.grid(row=0, column=0, rowspan=2) self.cellularAutomata = Canvas(window, height=600, width=600, background="blue") self.cellularAutomata.grid(row=2, column=0, rowspan="20") l2 = Label(window, text="Payoff matrix:", width=16) l2.grid(row=3, column=1) l3 = Label(window, text="Cell size: ", width=16) l3.grid(row=6, column=1) l8 = Label(window, text="Moore Neighbourhood: ", width=22) l8.grid(row=7, column=1) l9 = Label(window, text="Von Nuemann Neighbourhood: ", width=26) l9.grid(row=8, column=1) l4 = Label(window, text="Initial Distribution: ", width=16) l4.grid(row=10, column=1) l9 = Label(window, text="Fixed boundary (A): ", width=26) l9.grid(row=11, column=1) l9 = Label(window, text="Reflective boundary: ", width=26) l9.grid(row=12, column=1) l9 = Label(window, text="Periodic boundary: ", width=26) l9.grid(row=13, column=1) la = Label(window, text="Count (A|B|C): ", width=16) la.grid(row=16, column=1) l5 = Label(window, text="Iterations: ", width=16) l5.grid(row=17, column=1) b1 = Button(window, text="Draw", command=self.draw_command) b1.grid(row=19, column=1) self.b2 = Button(window, text="Start", command=self.begin_command) self.b2.grid(row=19, column=2) self.e1 = Scale( window, width=8, orient=HORIZONTAL, from_=2, to=3, label="Strategies" ) self.e1.grid(row=0, column=1) self.e1.bind("<ButtonRelease-1>", self.change_entry) self.li = Label(window, text="B invades A: ", width=16) self.li.grid(row=14, column=1) self.ival = IntVar() self.iv = Checkbutton(window, variable=self.ival) self.iv.grid(row=14, column=2) self.ld = Label(window, text="Dynamic", width=16) self.ld.grid(row=15, column=1) self.dyval = IntVar() self.dyval.set(1) self.dy = Checkbutton(window, variable=self.dyval) self.dy.grid(row=15, column=2) self.e2 = IntVar() self.e2 = Entry(window, textvariable=self.e2, width=6) self.e2.grid(row=3, column=2) self.e3 = IntVar() self.e3 = Entry(window, textvariable=self.e3, width=6) self.e3.grid(row=3, column=3) self.e4 = IntVar() self.e4 = Entry(window, textvariable=self.e4, width=6) self.e4.grid(row=4, column=2) self.e5 = IntVar() self.e5 = Entry(window, textvariable=self.e5, width=6) self.e5.grid(row=4, column=3) self.cellsize = IntVar() self.cellsize.set(8) self.cellsize = Entry(window, textvariable=self.cellsize, width=6) self.cellsize.grid(row=6, column=2) self.p1 = DoubleVar() self.p1 = Entry(window, textvariable=self.p1, width=6) self.p1.grid(row=10, column=2) self.p2 = DoubleVar() self.p2 = Entry(window, textvariable=self.p2, width=6) self.p2.grid(row=10, column=3) self.neighbourE = IntVar() self.neighbourE.set(1) self.moore = Radiobutton(window, variable=self.neighbourE, value=1) self.moore.grid(row=7, column=2) self.nuemann = Radiobutton(window, variable=self.neighbourE, value=2) self.nuemann.grid(row=8, column=2) self.boundaryvar = IntVar() self.boundaryvar.set(2) self.fixed = Radiobutton(window, variable=self.boundaryvar, value=1) self.fixed.grid(row=11, column=2) self.reflective = Radiobutton(window, variable=self.boundaryvar, value=2) self.reflective.grid(row=12, column=2) self.periodic = Radiobutton(window, variable=self.boundaryvar, value=3) self.periodic.grid(row=13, column=2) self.a1 = Listbox(window, width=4, height=1) self.a1.grid(row=16, column=2) self.a2 = Listbox(window, width=4, height=1) self.a2.grid(row=16, column=3) self.i1 = Listbox(window, width=4, height=1) self.i1.grid(row=17, column=2) def draw_command(self): self.cellularAutomata.delete("all") self.count = 0 self.i1.delete(0, END) self.i1.insert(END, self.count) try: self.b3.destroy() self.b2 = Button(window, text="Start", command=self.begin_command) self.b2.grid(row=19, column=2) except AttributeError: pass try: if self.e1.get() == 2: matrix = [ [self.e2.get(), self.e3.get()], [self.e4.get(), self.e5.get()], ] self.SpatialGame = spatialGame( 600, 600, self.cellsize.get(), [self.p1.get(), self.p2.get()], self.e1.get(), matrix, self.ival.get(), self.neighbourE.get(), self.boundaryvar.get(), self.dyval.get(), ) if self.e1.get() == 3: matrix = [ [self.e2.get(), self.e3.get(), self.e6.get()], [self.e4.get(), self.e5.get(), self.e7.get()], [self.e8.get(), self.e9.get(), self.e10.get()], ] self.SpatialGame = spatialGame( 600, 600, self.cellsize.get(), [self.p1.get(), self.p2.get(), self.p3.get()], self.e1.get(), matrix, self.ival.get(), self.neighbourE.get(), self.boundaryvar.get(), self.dyval.get(), ) self.cells = self.SpatialGame.cells for x in range(0, self.SpatialGame.width): for y in range(0, self.SpatialGame.height): if self.cells[x][y] == 2: square_coords = ( x * self.SpatialGame.cell_size, y * self.SpatialGame.cell_size, x * self.SpatialGame.cell_size + self.SpatialGame.cell_size, y * self.SpatialGame.cell_size + self.SpatialGame.cell_size, ) self.cellularAutomata.create_rectangle( square_coords, fill="red", outline="red" ) if self.SpatialGame.cells[x][y] == 3: square_coords = ( x * self.SpatialGame.cell_size, y * self.SpatialGame.cell_size, x * self.SpatialGame.cell_size + self.SpatialGame.cell_size, y * self.SpatialGame.cell_size + self.SpatialGame.cell_size, ) self.cellularAutomata.create_rectangle( square_coords, fill="pink", outline="pink" ) except ValueError: self.cellularAutomata.create_text( 300, 300, fill="White", font="Times 20 bold", text="Your probability distribution must add to 1.", ) def begin_command(self): self.animateval = True self.animate() def next(self): self.cellularAutomata.delete("all") self.SpatialGame.run_rules() self.cells = self.SpatialGame.cells self.count = self.count + 1 self.i1.delete(0, END) self.i1.insert(END, self.count) self.b2.destroy() self.b3 = Button(window, text="Stop", command=self.stop_command) self.b3.grid(row=19, column=2) self.animateval = True for x in range(0, self.SpatialGame.width): for y in range(0, self.SpatialGame.height): if self.cells[x][y] == 2: square_coords = ( x * self.SpatialGame.cell_size, y * self.SpatialGame.cell_size, x * self.SpatialGame.cell_size + self.SpatialGame.cell_size, y * self.SpatialGame.cell_size + self.SpatialGame.cell_size, ) self.cellularAutomata.create_rectangle( square_coords, fill="red", outline="red" ) if self.cells[x][y] == 4: square_coords = ( x * self.SpatialGame.cell_size, y * self.SpatialGame.cell_size, x * self.SpatialGame.cell_size + self.SpatialGame.cell_size, y * self.SpatialGame.cell_size + self.SpatialGame.cell_size, ) self.cellularAutomata.create_rectangle( square_coords, fill="green", outline="green" ) if self.cells[x][y] == 5: square_coords = ( x * self.SpatialGame.cell_size, y * self.SpatialGame.cell_size, x * self.SpatialGame.cell_size + self.SpatialGame.cell_size, y * self.SpatialGame.cell_size + self.SpatialGame.cell_size, ) self.cellularAutomata.create_rectangle( square_coords, fill="yellow", outline="yellow" ) if self.cells[x][y] == 3: square_coords = ( x * self.SpatialGame.cell_size, y * self.SpatialGame.cell_size, x * self.SpatialGame.cell_size + self.SpatialGame.cell_size, y * self.SpatialGame.cell_size + self.SpatialGame.cell_size, ) self.cellularAutomata.create_rectangle( square_coords, fill="pink", outline="pink" ) if self.cells[x][y] == 6: square_coords = ( x * self.SpatialGame.cell_size, y * self.SpatialGame.cell_size, x * self.SpatialGame.cell_size + self.SpatialGame.cell_size, y * self.SpatialGame.cell_size + self.SpatialGame.cell_size, ) self.cellularAutomata.create_rectangle( square_coords, fill="purple", outline="purple" ) self.a1.delete(0, END) self.a1.insert(END, self.SpatialGame.stratA) self.a2.delete(0, END) self.a2.insert(END, self.SpatialGame.stratB) try: self.a3.delete(0, END) self.a3.insert(END, self.SpatialGame.stratC) except: pass def change_entry(self, event): if self.e1.get() == 3 and self.check == False: self.check = True self.e6 = IntVar() self.e6 = Entry(window, textvariable=self.e6, width=6) self.e6.grid(row=3, column=4) self.e7 = IntVar() self.e7 = Entry(window, textvariable=self.e7, width=6) self.e7.grid(row=4, column=4) self.e8 = IntVar() self.e8 = Entry(window, textvariable=self.e8, width=6) self.e8.grid(row=5, column=2) self.e9 = IntVar() self.e9 = Entry(window, textvariable=self.e9, width=6) self.e9.grid(row=5, column=3) self.e10 = IntVar() self.e10 = Entry(window, textvariable=self.e10, width=6) self.e10.grid(row=5, column=4) self.p3 = DoubleVar() self.p3 = Entry(window, textvariable=self.p3, width=6) self.p3.grid(row=10, column=4) self.li.destroy() self.iv.destroy() self.ival = IntVar() self.ival.set(0) self.a3 = Listbox(window, width=4, height=1) self.a3.grid(row=16, column=4) elif self.e1.get() == 2 and self.check == True: self.li = Label(window, text="B invades A: ", width=16) self.li.grid(row=14, column=1) self.ival = IntVar() self.iv = Checkbutton(window, variable=self.ival) self.iv.grid(row=14, column=2) self.check = False self.e6.destroy() self.e7.destroy() self.e8.destroy() self.e9.destroy() self.e10.destroy() self.p3.destroy() self.a3.destroy() def stop_command(self): self.animateval = False self.b3.destroy() self.b2 = Button(window, text="Start", command=self.begin_command) self.b2.grid(row=19, column=2) def animate(self): while self.animateval == True: self.next() self.window.update() time.sleep(0.5)
class ScytheConfigEditor(): def __init__(self): global CURRENTCONFIG global MAXCONFIG global CF_MODE self.confighandler = ConfigHandler() self.confighandler.backupConf() tmpconfig= configparser.ConfigParser() self.confighandler.backupConfTo(tmpconfig) top = tk.Toplevel() top.title("Set configuration") nb = ttk.Notebook(top) b_config_ok = tk.Button(top, text="OK", command=top.destroy) b_config_ok.bind('<ButtonRelease-1>',self.onSetConfigOK) b_config_apply = tk.Button(top, text="Apply", command=self.onSetConfigApply) b_config_cancel = tk.Button(top, text="Cancel", command=top.destroy) b_config_cancel.bind('<ButtonRelease-1>',self.onSetConfigCancel()) fr_paths = tk.Frame(nb,width=200, height=100) fr_penalties = tk.Frame(nb,width=200, height=100) fr_mode = ttk.Frame(nb,width=200, height=100) fr_cleanup = ttk.Frame(nb,width=200, height=100) fr_run = ttk.Frame(nb,width=200, height=100) fr_algorithm = ttk.Frame(nb,width=200, height=100) fr_fastaheader = ttk.Frame(nb,width=200, height=100) #######labels######################## self.txt_sec=[] self.txt_subsec={} for section in MAXCONFIG.sections(): #print( "["+section +"]\n") self.txt_sec.append(section) for opt in MAXCONFIG.options(section): try: self.txt_subsec[section].append(opt) except KeyError as e: self.txt_subsec[section]=[opt] lab_sec=[] lab_subsec={} dd_subsec={} self.var_subsec={} for t in self.txt_sec: lab_sec.append(tk.Label(fr_paths,text = t)) for t in self.txt_subsec: #print(t,self.txt_subsec[t]) for u in self.txt_subsec[t]: if t == CF_MODE: fr = fr_mode elif t == CF_PATHS: fr = fr_paths elif t == CF_CLEANUP: fr = fr_cleanup elif t == CF_RUN: fr = fr_run elif t == CF_PENALTIES: fr = fr_penalties elif t == CF_ALGORITHM: fr = fr_algorithm elif t == CF_FASTAHEADER: fr = fr_fastaheader #print("fastaheader_fr") ################################ else: sys.stderr.write("No such section:",t) try: lab_subsec[t].append(tk.Label(fr,text = u)) self.var_subsec[t].append(tk.StringVar(fr)) if u in OPTIONS: dd_subsec[t].append(OptionMenu(fr,self.var_subsec[t][-1],*OPTIONS[u])) else: dd_subsec[t].append("") except KeyError as e: try: lab_subsec[t]=[tk.Label(fr,text = u)] self.var_subsec[t]=[tk.StringVar(fr)] if u in OPTIONS: dd_subsec[t] = [OptionMenu(fr,self.var_subsec[t][-1],*OPTIONS[u])] else: dd_subsec[t] = [""] except KeyError as e: sys.stderr.write(str(e)) dd_subsec[t].append("") for t in lab_subsec: r=0 c=0 for i in lab_subsec[t]: #print(i.cget("text")) i.grid(row=r,column=c, sticky=tk.E) r+=1 #print(r,i.cget("text")) for t in dd_subsec: c=1 r=0 for i in dd_subsec[t]: #print(i) if i is not "": i.grid(row=r,column=c,sticky=tk.N) r+=1 #print(r) ###################################### self.st_submat = tk.StringVar() self.st_fasta_header_delimiter = tk.StringVar() self.st_fasta_header_part = tk.StringVar() #cpu_count starts at 0 for one cpu self.sc_config_numthreads = Scale(fr_run, from_=1, to=multiprocessing.cpu_count(), orient=tk.HORIZONTAL) self.sc_config_numthreads.grid(row=0, column=1, sticky=tk.E) en_config_gapopen=tk.Entry(fr_penalties, textvariable=self.var_subsec[CF_PENALTIES][0]) en_config_gapextend=tk.Entry(fr_penalties,textvariable=self.var_subsec[CF_PENALTIES][1] ) self.en_config_fasta_header_delimiter= tk.Entry(fr_fastaheader,textvariable=self.st_fasta_header_delimiter,width=6 ) self.en_config_fasta_header_part= tk.Entry(fr_fastaheader,textvariable=self.st_fasta_header_part ,width=6 ) self.om_config_submat=tk.OptionMenu(fr_penalties, self.st_submat, *["EBLOSUM62","EDNAFULL"]) self.om_config_submat.grid(row=2,column=1 ) en_config_gapopen.grid(row=0, column=1) en_config_gapextend.grid(row=1, column=1) self.en_config_fasta_header_delimiter.grid(row=0, column=1) self.en_config_fasta_header_part.grid(row=1,column=1) nb.add(fr_penalties, text=CF_PENALTIES) nb.add(fr_cleanup, text=CF_CLEANUP) nb.add(fr_run, text=CF_RUN) nb.add(fr_algorithm, text=CF_ALGORITHM) nb.add(fr_fastaheader, text=CF_FASTAHEADER) nb.grid() b_config_cancel.grid(row=1, column=0, sticky=tk.E,padx=115) b_config_apply.grid(row=1, column=0, sticky=tk.E,padx=50) b_config_ok.grid(row=1, column=0, sticky=tk.E) self.setFieldsFromConfig() def onSetConfigApply(self): self.setConfigFromFields() def onSetConfigOK(self,event): self.setConfigFromFields() def onSetConfigCancel(self): self.confighandler.restoreConf() #print("RESTORED-->CURRENTCONF set") #print("Config CANCEL") def setConfigFromFields(self): tempconf = configparser.ConfigParser() self.confighandler.backupConfTo(tempconf) #get all values from fields #penalties tempconf.set(CF_PENALTIES,CF_PENALTIES_gap_open_cost,self.var_subsec[CF_PENALTIES][0].get() ) tempconf.set(CF_PENALTIES, CF_PENALTIES_gap_extend_cost,self.var_subsec[CF_PENALTIES][1].get()) tempconf.set(CF_PENALTIES, CF_PENALTIES_substitution_matrix,self.st_submat.get()) tempconf.set(CF_ALGORITHM, CF_ALGORITHM_use_global_max,self.var_subsec[CF_ALGORITHM][0].get()) tempconf.set(CF_ALGORITHM, CF_ALGORITHM_use_default,self.var_subsec[CF_ALGORITHM ][1].get()) tempconf.set(CF_ALGORITHM, CF_ALGORITHM_use_global_sum,self.var_subsec[CF_ALGORITHM][2].get()) tempconf.set(CF_RUN, CF_RUN_num_CPU,str(self.sc_config_numthreads.get())) #CLEANUP tempconf.set(CF_CLEANUP, CF_CLEANUP_clean_up_directories, self.var_subsec[CF_CLEANUP][0].get()) #Fasta header tempconf.set(CF_FASTAHEADER, CF_FASTAHEADER_delimiter, self.var_subsec[CF_FASTAHEADER][0].get()) tempconf.set(CF_FASTAHEADER, CF_FASTAHEADER_part, self.var_subsec[CF_FASTAHEADER][1].get()) tempconf.set(CF_FASTAHEADER, CF_FASTAHEADER_part,self.st_fasta_header_part.get()) tempconf.set(CF_FASTAHEADER, CF_FASTAHEADER_delimiter,self.st_fasta_header_delimiter.get()) self.confighandler.setCurrentConf(tempconf) def setFieldsFromConfig(self): #penalties self.var_subsec[CF_PENALTIES][0].set(CURRENTCONFIG.get(CF_PENALTIES,self.txt_subsec[CF_PENALTIES][0])) self.var_subsec[CF_PENALTIES][1].set(CURRENTCONFIG.get(CF_PENALTIES,self.txt_subsec[CF_PENALTIES][1])) self.st_submat.set(CURRENTCONFIG.get(CF_PENALTIES, CF_PENALTIES_substitution_matrix)) #output #cleanup self.var_subsec[CF_CLEANUP][0].set(CURRENTCONFIG.get(CF_CLEANUP,self.txt_subsec[CF_CLEANUP][0])) #run #slider #algo self.var_subsec[CF_ALGORITHM][0].set(CURRENTCONFIG.get(CF_ALGORITHM,self.txt_subsec[CF_ALGORITHM][0])) self.var_subsec[CF_ALGORITHM][1].set(CURRENTCONFIG.get(CF_ALGORITHM,self.txt_subsec[CF_ALGORITHM][1])) self.var_subsec[CF_ALGORITHM][2].set(CURRENTCONFIG.get(CF_ALGORITHM,self.txt_subsec[CF_ALGORITHM][2])) self.var_subsec[CF_FASTAHEADER][0].set(CURRENTCONFIG.get(CF_FASTAHEADER,self.txt_subsec[CF_FASTAHEADER][0])) self.var_subsec[CF_FASTAHEADER][1].set(CURRENTCONFIG.get(CF_FASTAHEADER,self.txt_subsec[CF_FASTAHEADER][1])) self.st_fasta_header_part.set(CURRENTCONFIG.get(CF_FASTAHEADER, CF_FASTAHEADER_part)) self.st_fasta_header_delimiter.set(CURRENTCONFIG.get(CF_FASTAHEADER, CF_FASTAHEADER_delimiter))
class KarelWindow(Frame): def geometry(self, height): # print "gemo " + str(self._oldHeight) + ' ' + str(height) self._oldHeight = self._height self._height = height self.__bottom = height - self._inset self.__left = self._inset self.__top = self._inset self.__right = height # self.__scaleFactor = ((self.__bottom - self.__top)*1.0/self.__streets) def __init__(self, streets, avenues, size=800, callback=None): # avenues is ignored in this version # self.__configControl = threading.Condition() self.__root = root = Tk( className=" Karel's World ") # , geometry='800x600+60+10' global _windowBottom _windowBottom = size geometryString = '820x' + str(_windowBottom + 65) + "+55+25" root.geometry(newGeometry=geometryString ) #'820x865+55+25') # placement of window on desktop # print str(root.tk_menuBar()) Frame.__init__(self, master=root, cnf={}) bar = Menu() def endProgram(menu): exit() fil = Menu() fil.add_command(label='Quit ^Q', command=lambda x='Quit': endProgram(x)) bar.add_cascade(label='File', menu=fil) root.config(menu=bar) self.bind_all('<Command-q>', exit) # Mac standard self.bind_all('<Control-q>', exit) # Windows self.__streets = streets self.__avenues = streets # sic Avenues ignored self.__gBeepers = {} #locations of the beeper imagess self.__contents = [] # , walls, beepers that need to move on a rescale self.__robots = [] self.__beeperControl = threading.Condition( ) # helps multi threaded programs avoid anomalies self.__walls = [ ] # all the basic visual elements (boundary, streets, street labels, etc. top = self.winfo_toplevel() top.rowconfigure(2, weight=1) top.columnconfigure(0, weight=1) self.rowconfigure(2, weight=1) self.columnconfigure(0, weight=1) root.rowconfigure(2, weight=1) root.columnconfigure(0, weight=1) speedLabel = Label(text="Speed") speedLabel.grid(row=0, column=0, sticky=N + W + E + S) if callback != None: # this makes the speed slider work. from tkinter import IntVar self.iv = IntVar() self.iv.trace('r', callback) self.scale = Scale(orient=HORIZONTAL, variable=self.iv) self.scale.set(20) self.scale.grid(row=1, column=0, sticky=N + S) # self.__callback = callback # global _windowRight global _inset # root.minsize(_windowBottom, _windowRight) self._height = self._oldHeight = _windowBottom self.__bottom = _windowBottom - _inset #770 self.__left = _inset #30 self.__top = _inset #30 self.__right = self._height #_windowRight - _inset #770 self._inset = _inset # print str(speedLabel.config()) # print str(self.scale.config()) self._canvas = Canvas(root, height=_windowBottom, width=_windowBottom, bg='white') self._canvas.grid(row=2, column=0, sticky=N + E + W + S) self.geometry(self._height) self.setSize(streets) # self._canvas.bind_all('<Expose>', self.expose) # self._canvas.bind('<Configure>', self.configure) # def expose(self, event): ## print 'expose ' + str(event.width)+ ' ' + str(event.height) # pass # def configure(self, event): ## print str(self._canvas.config()) ## print "config " + str(event.height) ## self.__configControl.acquire() # self.geometry(event.height) # delta = (self._oldHeight - self._height)*1.0/self._oldHeight # scale = self._height*1.0/self._oldHeight # self._canvas.scale('all', 0, 0, scale, scale) # self._canvas.move('all', delta, delta) ## print "config " + str(event.widget)+ ' ' +str(event.x)+ ' ' + str(event.y)+' ' + str(event.width)+ ' ' + str(event.height) ## self.__configControl.notify() ## self.__configControl.release() # pass def clear(self): for item in self.__contents + self.__robots: item.deleteAll() def setSize(self, streets): #streets can change self.__streets = streets for x in self.__walls: # boundary walls and street lines self._canvas.delete(x) self.makeStreetsAndAvenues() self.makeBoundaryWalls() self.labelStreetsAvenues() for item in self.__contents + self.__robots: #rebuild the contents of the world item.moveScale() def scaleFactor(self): self.geometry(self._height) # print "in scaler " + str(self.__bottom) + " " + str(self.__top) + ' ' + str(self.__streets) return ((self.__bottom - self.__top) * 1.0 / self.__streets ) #self.__scaleFactor class Beeper: bNumber = 0 def __init__(self, street, avenue, number, window): self._street = street self._avenue = avenue self._number = number self._scaler = window._scaleToPixels self.scaleFactor = window.scaleFactor self._canvas = window._canvas self.tag = "b" + str(KarelWindow.Beeper.bNumber) KarelWindow.Beeper.bNumber += 1 def place(self): sizeFactor = .5 #Change this to change beeper size. The others scale from it. placeFactor = .5 * sizeFactor val = str(self._number) if self._number < 0: val = "oo" (x, y) = self._scaler(self._street + placeFactor, self._avenue - placeFactor) # print 'beeper ' + str(x) + ' ' + str(y) # print 'factor ' + str(self.scaleFactor()) # # circular beepers # self._canvas.create_oval(x, y, x + self.__scaleFactor*sizeFactor, y + self.__scaleFactor*sizeFactor, fill= 'black', tags = self.tag) # triangular beepers where = [] where.append(self._scaler(self._street + sizeFactor, self._avenue)) where.append( self._scaler(self._street - placeFactor, self._avenue - placeFactor)) where.append( self._scaler(self._street - placeFactor, self._avenue + placeFactor)) self._canvas.create_polygon(where, fill="black", smooth=False, tags=self.tag) self._canvas.create_text(x + self.scaleFactor() * placeFactor, y + self.scaleFactor() * placeFactor, text=val, font=Font(size=int(-self.scaleFactor() * placeFactor)), fill='white', tags=self.tag) def deleteAll(self): self._canvas.delete(self.tag) def moveScale(self): self._canvas.delete(self.tag) self.place() class Wall: def __init__(self, street, avenue, isVertical, window): self._street = street self._avenue = avenue self._isVertical = isVertical self.scaleFactor = window.scaleFactor self._scaler = window._scaleToPixels self._canvas = window._canvas if self._isVertical: (x, y) = self._scaler(street - .5, avenue + .5) self._code = self._canvas.create_line(x, y, x, y - self.scaleFactor(), width=2) else: (x, y) = self._scaler(street + .5, avenue - .5) self._code = self._canvas.create_line(x, y, x + self.scaleFactor(), y, width=2) # _code identifies the wall segment image in the tk layer def moveScale(self): self._canvas.delete( self._code ) #erase the current figure in prep to draw a new one if self._isVertical: (x, y) = self._scaler(self._street - .5, self._avenue + .5) self._code = self._canvas.create_line(x, y, x, y - self.scaleFactor(), width=2) else: (x, y) = self._scaler(self._street + .5, self._avenue - .5) self._code = self._canvas.create_line(x, y, x + self.scaleFactor(), y, width=2) def deleteAll(self): self._canvas.delete(self._code) def placeBeeper(self, street, avenue, number): # self.__beeperControl.acquire() # sync was moved to tkworldadapter beeper = self.Beeper(street, avenue, number, self) beeper.place() self.__gBeepers[(street, avenue)] = beeper self.__contents.append(beeper) # self.__beeperControl.notify() # self.__beeperControl.release() # return beeper def deleteBeeper(self, beeperlocation): # self.__beeperControl.acquire() beeper = self.__gBeepers.get(beeperlocation, None) if beeper != None: beeper.deleteAll() self.__gBeepers.pop(beeperlocation) i = 0 for b in self.__contents: if b == beeper: break i += 1 self.__contents.pop(i) # self.__beeperControl.notify() # self.__beeperControl.release() def placeWallNorthOf(self, street, avenue): self.__contents.append(self.Wall(street, avenue, False, self)) def removeWallNorthOf(self, street, avenue): i = 0 for wall in self.__contents: if wall.__class__ is self.Wall and wall._street == street and wall._avenue == avenue and not wall._isVertical: wall.deleteAll() self.__contents.pop(i) # print 'h gone' break i += 1 def placeWallEastOf(self, street, avenue): self.__contents.append(self.Wall(street, avenue, True, self)) def removeWallEastOf(self, street, avenue): i = 0 for wall in self.__contents: if wall.__class__ is self.Wall and wall._street == street and wall._avenue == avenue and wall._isVertical: wall.deleteAll() self.__contents.pop(i) # print 'v gone' break i += 1 def makeBoundaryWalls(self): (x, y) = self._scaleToPixels(.5, .5) # hardcode ok. Half way between streets self.__walls.append(self._canvas.create_line( x, 0, x, y, width=2)) # should width depend on number of streets? global _inset self.__walls.append( self._canvas.create_line(x, y, self.__right + _inset, y, width=2)) def makeStreetsAndAvenues(self): for i in range(0, self.__streets): (x, y) = self._scaleToPixels(i + 1, .5) (tx, ty) = self._scaleToPixels(i + 1, self.__streets + .5) self.__walls.append( self._canvas.create_line(x, y, tx, ty, fill="red")) (x, y) = self._scaleToPixels(.5, i + 1) (tx, ty) = self._scaleToPixels(self.__streets + .5, i + 1) self.__walls.append( self._canvas.create_line(x, y, tx, ty, fill="red")) def labelStreetsAvenues(self): for i in range(self.__streets): (x, y) = self._scaleToPixels(i + 1, .25) self.__walls.append( self._canvas.create_text(x, y, fill='black', text=str(i + 1))) (x, y) = self._scaleToPixels(.25, i + 1) self.__walls.append( self._canvas.create_text(x, y, fill='black', text=str(i + 1))) def addRobot(self, street, avenue, direction, fill, outline): # fill and outline are colors, default to blue, black robot = RobotImage(street, avenue, direction, self, fill, outline) self.__robots.append(robot) return robot # the world matches these with the actual robot objects in the model. def moveRobot(self, robot, amount=-1): #If no amount is specified then it moves one block, Otherwise amount pixels, not blocks if amount < 0: amount = self.scaleFactor() robot.move(amount) def _scaleToPixels(self, street, avenue): # origin is at corner (0,0) outside the world scale = self.scaleFactor() return (self.__left + avenue * scale, self.__bottom - street * scale) def _scaleFromPixels(self, x, y): scale = self.scaleFactor() return (int(round( (self.__bottom - y) / scale)), int(round( (x - self.__left) / scale))) def _downScaleFromPixels(self, x, y): scale = self.scaleFactor() return (int((self.__bottom - y) / scale), int( (x - self.__left) / scale)) def run(self, task, *pargs): # this is the actual graphic main. mainThread = threading.Thread(target=task, args=pargs) mainThread.start() self.mainloop() def _test(self): pass
class ScytheConfigEditor(): def __init__(self): global CURRENTCONFIG global MAXCONFIG global CF_MODE self.confighandler = ConfigHandler() self.confighandler.backupConf() tmpconfig = configparser.ConfigParser() self.confighandler.backupConfTo(tmpconfig) top = tk.Toplevel() top.title("Set configuration") nb = ttk.Notebook(top) b_config_ok = tk.Button(top, text="OK", command=top.destroy) b_config_ok.bind('<ButtonRelease-1>', self.onSetConfigOK) b_config_apply = tk.Button(top, text="Apply", command=self.onSetConfigApply) b_config_cancel = tk.Button(top, text="Cancel", command=top.destroy) b_config_cancel.bind('<ButtonRelease-1>', self.onSetConfigCancel()) fr_paths = tk.Frame(nb, width=200, height=100) fr_penalties = tk.Frame(nb, width=200, height=100) fr_mode = ttk.Frame(nb, width=200, height=100) fr_cleanup = ttk.Frame(nb, width=200, height=100) fr_run = ttk.Frame(nb, width=200, height=100) fr_algorithm = ttk.Frame(nb, width=200, height=100) fr_fastaheader = ttk.Frame(nb, width=200, height=100) #######labels######################## self.txt_sec = [] self.txt_subsec = {} for section in MAXCONFIG.sections(): #print( "["+section +"]\n") self.txt_sec.append(section) for opt in MAXCONFIG.options(section): try: self.txt_subsec[section].append(opt) except KeyError as e: self.txt_subsec[section] = [opt] lab_sec = [] lab_subsec = {} dd_subsec = {} self.var_subsec = {} for t in self.txt_sec: lab_sec.append(tk.Label(fr_paths, text=t)) for t in self.txt_subsec: #print(t,self.txt_subsec[t]) for u in self.txt_subsec[t]: if t == CF_MODE: fr = fr_mode elif t == CF_PATHS: fr = fr_paths elif t == CF_CLEANUP: fr = fr_cleanup elif t == CF_RUN: fr = fr_run elif t == CF_PENALTIES: fr = fr_penalties elif t == CF_ALGORITHM: fr = fr_algorithm elif t == CF_FASTAHEADER: fr = fr_fastaheader #print("fastaheader_fr") ################################ else: sys.stderr.write("No such section:", t) try: lab_subsec[t].append(tk.Label(fr, text=u)) self.var_subsec[t].append(tk.StringVar(fr)) if u in OPTIONS: dd_subsec[t].append( OptionMenu(fr, self.var_subsec[t][-1], *OPTIONS[u])) else: dd_subsec[t].append("") except KeyError as e: try: lab_subsec[t] = [tk.Label(fr, text=u)] self.var_subsec[t] = [tk.StringVar(fr)] if u in OPTIONS: dd_subsec[t] = [ OptionMenu(fr, self.var_subsec[t][-1], *OPTIONS[u]) ] else: dd_subsec[t] = [""] except KeyError as e: sys.stderr.write(str(e)) dd_subsec[t].append("") for t in lab_subsec: r = 0 c = 0 for i in lab_subsec[t]: #print(i.cget("text")) i.grid(row=r, column=c, sticky=tk.E) r += 1 #print(r,i.cget("text")) for t in dd_subsec: c = 1 r = 0 for i in dd_subsec[t]: #print(i) if i is not "": i.grid(row=r, column=c, sticky=tk.N) r += 1 #print(r) ###################################### self.st_submat = tk.StringVar() self.st_fasta_header_delimiter = tk.StringVar() self.st_fasta_header_part = tk.StringVar() #cpu_count starts at 0 for one cpu self.sc_config_numthreads = Scale(fr_run, from_=1, to=multiprocessing.cpu_count(), orient=tk.HORIZONTAL) self.sc_config_numthreads.grid(row=0, column=1, sticky=tk.E) en_config_gapopen = tk.Entry( fr_penalties, textvariable=self.var_subsec[CF_PENALTIES][0]) en_config_gapextend = tk.Entry( fr_penalties, textvariable=self.var_subsec[CF_PENALTIES][1]) self.en_config_fasta_header_delimiter = tk.Entry( fr_fastaheader, textvariable=self.st_fasta_header_delimiter, width=6) self.en_config_fasta_header_part = tk.Entry( fr_fastaheader, textvariable=self.st_fasta_header_part, width=6) self.om_config_submat = tk.OptionMenu(fr_penalties, self.st_submat, *["EBLOSUM62", "EDNAFULL"]) self.om_config_submat.grid(row=2, column=1) en_config_gapopen.grid(row=0, column=1) en_config_gapextend.grid(row=1, column=1) self.en_config_fasta_header_delimiter.grid(row=0, column=1) self.en_config_fasta_header_part.grid(row=1, column=1) nb.add(fr_penalties, text=CF_PENALTIES) nb.add(fr_cleanup, text=CF_CLEANUP) nb.add(fr_run, text=CF_RUN) nb.add(fr_algorithm, text=CF_ALGORITHM) nb.add(fr_fastaheader, text=CF_FASTAHEADER) nb.grid() b_config_cancel.grid(row=1, column=0, sticky=tk.E, padx=115) b_config_apply.grid(row=1, column=0, sticky=tk.E, padx=50) b_config_ok.grid(row=1, column=0, sticky=tk.E) self.setFieldsFromConfig() def onSetConfigApply(self): self.setConfigFromFields() def onSetConfigOK(self, event): self.setConfigFromFields() def onSetConfigCancel(self): self.confighandler.restoreConf() #print("RESTORED-->CURRENTCONF set") #print("Config CANCEL") def setConfigFromFields(self): tempconf = configparser.ConfigParser() self.confighandler.backupConfTo(tempconf) #get all values from fields #penalties tempconf.set(CF_PENALTIES, CF_PENALTIES_gap_open_cost, self.var_subsec[CF_PENALTIES][0].get()) tempconf.set(CF_PENALTIES, CF_PENALTIES_gap_extend_cost, self.var_subsec[CF_PENALTIES][1].get()) tempconf.set(CF_PENALTIES, CF_PENALTIES_substitution_matrix, self.st_submat.get()) tempconf.set(CF_ALGORITHM, CF_ALGORITHM_use_global_max, self.var_subsec[CF_ALGORITHM][0].get()) tempconf.set(CF_ALGORITHM, CF_ALGORITHM_use_default, self.var_subsec[CF_ALGORITHM][1].get()) tempconf.set(CF_ALGORITHM, CF_ALGORITHM_use_global_sum, self.var_subsec[CF_ALGORITHM][2].get()) tempconf.set(CF_RUN, CF_RUN_num_CPU, str(self.sc_config_numthreads.get())) #CLEANUP tempconf.set(CF_CLEANUP, CF_CLEANUP_clean_up_directories, self.var_subsec[CF_CLEANUP][0].get()) #Fasta header tempconf.set(CF_FASTAHEADER, CF_FASTAHEADER_delimiter, self.var_subsec[CF_FASTAHEADER][0].get()) tempconf.set(CF_FASTAHEADER, CF_FASTAHEADER_part, self.var_subsec[CF_FASTAHEADER][1].get()) tempconf.set(CF_FASTAHEADER, CF_FASTAHEADER_part, self.st_fasta_header_part.get()) tempconf.set(CF_FASTAHEADER, CF_FASTAHEADER_delimiter, self.st_fasta_header_delimiter.get()) self.confighandler.setCurrentConf(tempconf) def setFieldsFromConfig(self): #penalties self.var_subsec[CF_PENALTIES][0].set( CURRENTCONFIG.get(CF_PENALTIES, self.txt_subsec[CF_PENALTIES][0])) self.var_subsec[CF_PENALTIES][1].set( CURRENTCONFIG.get(CF_PENALTIES, self.txt_subsec[CF_PENALTIES][1])) self.st_submat.set( CURRENTCONFIG.get(CF_PENALTIES, CF_PENALTIES_substitution_matrix)) #output #cleanup self.var_subsec[CF_CLEANUP][0].set( CURRENTCONFIG.get(CF_CLEANUP, self.txt_subsec[CF_CLEANUP][0])) #run #slider #algo self.var_subsec[CF_ALGORITHM][0].set( CURRENTCONFIG.get(CF_ALGORITHM, self.txt_subsec[CF_ALGORITHM][0])) self.var_subsec[CF_ALGORITHM][1].set( CURRENTCONFIG.get(CF_ALGORITHM, self.txt_subsec[CF_ALGORITHM][1])) self.var_subsec[CF_ALGORITHM][2].set( CURRENTCONFIG.get(CF_ALGORITHM, self.txt_subsec[CF_ALGORITHM][2])) self.var_subsec[CF_FASTAHEADER][0].set( CURRENTCONFIG.get(CF_FASTAHEADER, self.txt_subsec[CF_FASTAHEADER][0])) self.var_subsec[CF_FASTAHEADER][1].set( CURRENTCONFIG.get(CF_FASTAHEADER, self.txt_subsec[CF_FASTAHEADER][1])) self.st_fasta_header_part.set( CURRENTCONFIG.get(CF_FASTAHEADER, CF_FASTAHEADER_part)) self.st_fasta_header_delimiter.set( CURRENTCONFIG.get(CF_FASTAHEADER, CF_FASTAHEADER_delimiter))
def pipet(Window, ProtoWindow, temp_file): """ This program adds the pipeting instruction. Entry: Window(Frame): the protocol window ProtoWindow(Frame): the protocol frame temp_file(string): the name of the file """ protocole = Prot.ReadProtocolFile(temp_file) pos = protocole.index(['position']) a = protocole[:pos] if a == []: a = [['pip']] else: a = a + [['pip']] b = protocole[pos:] #Create the new window Window_option = Toplevel(Window) Window_option.title('Neurodrop - Pipette calibration') #Create the heading of the new window Heading = Create_Heading(Window_option) #Create the choices of solutions and the slider for the volume Solution = Create_Frame(Window_option, border_thickness=5, style_border='groove', back_colour=sty.Bkg_frm_blue, col=1, line=2, nblines=2, nbcolumns=8, form='wens') Create_text(Solution, 'Choose the solution', color=sty.Clr_txt_frames, Police=sty.Font_frames_title, back_colour=sty.Bkg_frm_blue, col=1, line=1, form='wens', nbcolumns=4, nblines=1) var = IntVar() for i in [1, 2, 3, 4]: R = Radiobutton(Solution, text="Solution " + str(i), variable=var, value=i, bg=sty.Bkg_frm_blue) R.grid(column=i, row=3, columnspan=1, rowspan=1, sticky='we') scale = IntVar() Volume = Create_Frame(Window_option, border_thickness=5, style_border='groove', back_colour=sty.Bkg_frm_blue, col=1, line=5, nblines=2, nbcolumns=8, form='wens') Create_text(Volume, 'Choose the volume (in nL)', color=sty.Clr_txt_frames, Police=sty.Font_frames_title, back_colour=sty.Bkg_frm_blue, col=1, line=1, form='wens', nbcolumns=1, nblines=1) volscale = Scale(Volume, from_=200, to=10000, resolution=50, variable=scale, showvalue=True, label='nL', orient='horizontal', bg=sty.Bkg_frm_blue, length=30) volscale.grid(column=1, row=3, columnspan=1, rowspan=1, sticky='we') Confirm = Create_Frame(Window_option, border_thickness=5, style_border='groove', back_colour=sty.Bkg_frm_blue, col=1, line=8, nblines=1, nbcolumns=8, form='wens') Create_text(Confirm, 'Save parameters', color=sty.Clr_txt_frames, Police=sty.Font_frames_title, back_colour=sty.Bkg_frm_blue, col=1, line=1, form='wens', nbcolumns=1, nblines=1) Create_button( Confirm, 'OK', partial(get_value_2, Window_option, scale, var, a + b, ProtoWindow)).grid(column=1, row=3, columnspan=1, rowspan=1, sticky='wens') #Configure the window W = [ Window_option, Window_option, Heading, Solution, Solution, Volume, Volume, Confirm, Confirm ] Lines = [[0, 2, 3, 4, 6, 7, 8], [1, 5, 9], [0], [0, 2, 4], [1, 3], [0, 2, 4], [1, 3], [0, 2, 4], [1, 3]] Columns = [[1, 2, 3, 4, 5, 6, 7, 8], [0, 9], [0, 1, 2, 3, 4, 5, 6, 7], [0, 5], [1, 2, 3, 4], [0, 2], [1], [0, 2], [1]] WC = [0, 1, 1, 1, 0, 1, 0, 1, 0] WL = [0, 1, 0, 1, 0, 1, 0, 1, 0] for i in range(len(W)): Auto_configure(W[i], lines=Lines[i], columns=Columns[i], min_size_col=10, min_size_row=10, weight_col=WC[i], weight_row=WL[i]) return 1
class BMIGUI(Tk): def __init__(self, parent=None): 'constructor' Tk.__init__(self, parent) self.title('BMI Calculator') self.make_widgets() def getBMIDescription(self, value): if value < 18.5: return 'Underweight' elif value == 18.5 and value < 25: return 'Normal Weight' elif value == 25 and value < 30: return 'Overweight' else: return 'Obese' def calculateBMI(self): hf = self.heightfeet.get() hi = self.heightinches.get() weight = self.slider.get() try: hf = float(hf) except ValueError: showinfo( title='BMI Calculation', message='Error. Incorrect value entered for height(feet).') return try: hi = float(hi) except ValueError: showinfo( title='BMI Calculation', message='Error. Incorrect value entered for height(inches).') return heightinches = (hf * 12) + hi bmi = (weight / (heightinches * heightinches)) * 703 self.lbupdater.config( text='{:.2f} {{}}'.format(bmi, self.getBMIDescription(bmi))) def make_widgets(self): Label(self, text='Body Mass Index Calculator').grid(row=0, column=0) Label(self, text='Your Height:').grid(row=1, column=0) Label(self, text='Your Weight:').grid(row=2, column=0) Label(self, text='BMI:').grid(row=5, column=0) Label(self, text='Pounds').grid(row=2, column=2) Label(self, text='Feet').grid(row=1, column=2) Label(self, text='Inches').grid(row=1, column=4) self.lbupdater = Label(self) self.lbupdater.grid(row=5, column=1) self.calcBTN = Button(self, text='Calculate BMI', command=lambda: self.calculateBMI()) self.calcBTN.grid(row=4, column=1) self.slider = Scale(self, from_=0, to=500, orient=HORIZONTAL, resolution=10) self.slider.grid(row=2, column=1) self.heightfeet = Entry(self, width=5) self.heightfeet.grid(row=1, column=1) self.heightinches = Entry(self, width=5) self.heightinches.grid(row=1, column=3)
def addScale(self, row, start, end, fieldLabel, settingKey): Label(self, text=fieldLabel + ":").grid(row=row, column=1) scale = Scale(self, from_=start, to=end, orient=HORIZONTAL, command=lambda value, settingKey=settingKey: self.settings.set(settingKey, str(value))) scale.set(self.settings.get(settingKey)) scale.grid(row=row, column=3)
class VisAnaGUI(tk.LabelFrame): #update levels, each level includes all lower ones NOTHING = 0 TIMELINE_SELECTION = 1 TIMELINE_DAYSINPLOT = 2 PLOT = 3 PLOT_DATA = 4 DATA_TIDYUP = 5 def __init__(self, master=None, ds=None): #self.dates = [] #for dt in rrule.rrule(rrule.DAILY, # dtstart=datetime(2014,1,1,0,0,0), # until=datetime(2015,1,1,0,0,0)): # self.dates.append(dt.date()) ## save data source self.ds = ds #type:datasource.DataSource self.ds.groupby("all_days", datasource.TIME_ATTR, "COUNT", "base", bydate=True) #self.ds.link("show") #self.df=ds.get_base_data().df() ## parameter variables for listboxes self.param_list = list(ds.get_data("base").get_attr_names( )) #["MasterTime", "Small", "Large", "OutdoorTemp","RelHumidity"] #print("params:") #print(self.param_list) #print(list(self.param_list)) #print(self.param_list[1]) self.param2 = self.param_list[1] self.param1 = self.param_list[2] self.aggregation_limit = 1 ## simple string to describe last action (for history) self.action_str = "Show base data" self.plot_tooltip = None self.select_rect = None self.draw_frame(master) self.mouse_pressed = None ## save time of last update to prevent too many ## updates when using sliders self.last_action = time() ## delay after last data update and action (in ms) self.UPDATE_DELAY = 500 ## was there an action triggering an update? # (0=no, 1=only the timeline, 2=axes and timeline, 3=with selection, 4 with tidyup) self.unprocessed_action = self.DATA_TIDYUP ## calls check_for_update() method after delay has passed self.after(self.UPDATE_DELAY, self.check_for_update) ## dummy variable to ignore first update. sliders trigger an ## event at startup, which would lead to redundant update of data self.ignore_start_trigger = True ## draw data at startup self.update_data() ####################### # UI CREATION def draw_frame(self, master): tk.LabelFrame.__init__(self, master, bg="red") root.columnconfigure(0, weight=1) root.rowconfigure(0, weight=1) root.title("Visual Analyser - Gui") self.grid(column=0, row=0, sticky=(tk.N, tk.W, tk.E, tk.S)) self.columnconfigure(1, weight=1) self.rowconfigure(3, weight=1) self.rowconfigure(2, minsize=100) self.configure(background="red") self.create_widgets() ## creates all GUI elements def create_widgets(self): self.toolbar = tk.LabelFrame(self) self.toolbar.grid(column=0, row=0, sticky=(tk.W, tk.N, tk.E), columnspan=5) self.QUIT = tk.Button(self.toolbar, text="QUIT", fg="red", command=root.destroy) self.QUIT.grid(column=0, row=0, sticky=(tk.W, tk.N)) self.reset_view_btn = tk.Button(self.toolbar) self.reset_view_btn["text"] = "Reset the View" self.reset_view_btn["command"] = self.reset_to_start self.reset_view_btn.grid(column=1, row=0, sticky=(tk.W, tk.N)) self.toggle_hist_btn = tk.Button(self.toolbar) self.toggle_hist_btn["text"] = "Toggle History" self.toggle_hist_btn["command"] = self.toggle_history self.toggle_hist_btn.grid(column=4, row=0, sticky=(tk.W, tk.N)) # self.tdvar = tk.StringVar(value="0") # self.tidy_up = tk.Checkbutton(self.toolbar, text='Tidy Up Data', command=self.handle_tidy_up, # variable=self.tdvar) # self.tidy_up.grid(column=2, row=0, sticky=(tk.W, tk.N)) self.rgvar = tk.StringVar(value="0") self.regression = tk.Checkbutton(self.toolbar, text='Draw Regression', command=self.handle_regression, variable=self.rgvar) self.regression.grid(column=3, row=0, sticky=(tk.W, tk.N)) self.left_sidebar = tk.Frame(self) self.left_sidebar.grid(column=0, row=3, sticky=(tk.N, tk.E, tk.W)) self.projector = self.create_listboxes(self.left_sidebar) self.projector.grid(column=0, row=0, sticky=(tk.N, tk.E, tk.W)) self.selector = Selector_old(self.left_sidebar, self.param_list, self.handle_view_change) self.selector.grid(column=0, row=1, sticky=(tk.N, tk.E, tk.W)) self.history_text = "::LOG::\n" self.create_history() self.create_plot() def create_history(self): self.history_shown = True self.history = tk.Text(self, width=45) self.history.grid(column=2, row=3, sticky=(tk.N, tk.E, tk.S), rowspan=2) self.history.insert('end', self.history_text) self.history.see("end") self.historyslider = tk.Scrollbar(self, orient=tk.VERTICAL, command=self.history.yview) self.historyslider.grid(column=3, row=3, sticky=(tk.N, tk.S), rowspan=2) self.history['yscrollcommand'] = self.historyslider.set def create_listboxes(self, parent) -> tk.LabelFrame: frame = tk.LabelFrame(parent, bg="red") self.paramlabel = tk.Label(frame, text="Choose Parameters") self.paramlabel.grid(column=0, row=0, sticky=(tk.N, tk.E, tk.W), columnspan=2) ## listboxes for parameter selection self.param1lbl = tk.Label(frame, text="X-Axis:") self.param1lbl.grid(column=0, row=1, sticky=(tk.N, tk.E, tk.W)) self.param1var = StringVar() self.param1var.set(self.param1) self.param1box = Combobox(frame, textvariable=self.param1var, state="readonly", width=15) self.param1box['values'] = self.param_list self.param1box.bind('<<ComboboxSelected>>', self.handle_paramsChanged) self.param1box.grid(column=1, row=1, sticky=(tk.N, tk.E, tk.W)) self.param1lbl = tk.Label(frame, text="Y-Axis:") self.param1lbl.grid(column=0, row=2, sticky=(tk.N, tk.E, tk.W)) self.param2var = StringVar() self.param2var.set(self.param2) self.param2box = Combobox(frame, textvariable=self.param2var, state="readonly", width=15) self.param2box['values'] = self.param_list self.param2box.bind('<<ComboboxSelected>>', self.handle_paramsChanged) self.param2box.grid(column=1, row=2, sticky=(tk.N, tk.E, tk.W)) # self.param2box = Listbox(self.projector, exportselection=0) # for item in self.param_list: # self.param2box.insert("end", item) # param2_index = self.param_list.index(self.param2) # self.param2box.select_set(param2_index) # self.param2box.bind('<<ComboboxSelected>>', self.handle_paramsChanged) # self.param2box.grid(column=0, row=2, sticky=(tk.N, tk.E, tk.W)) self.var = StringVar(frame) self.var.set(str(self.aggregation_limit)) self.noise_spin = Spinbox(frame, from_=1, to=1440, textvariable=self.var, width=4) self.noise_spin.grid(column=0, row=3, sticky=(tk.E, tk.W)) self.testbutton = tk.Button(frame) self.testbutton["text"] = "Aggregate values (minutes)" self.testbutton["command"] = self.handle_aggregate_btn self.testbutton.grid(column=1, row=3, sticky=(tk.W, tk.N)) return frame ## add sliders to GUI def create_sliders(self): ## init sliders #self.filter = tk.LabelFrame(self, bg="#0066ff") self.filter = tk.LabelFrame(self, bg="red") self.filter.grid(column=0, row=1, sticky=(tk.N, tk.E, tk.W), columnspan=5) self.filter.columnconfigure(1, weight=1) self.filter.columnconfigure(0, weight=0) self.startSlider = Scale(self.filter, from_=0, to=365, orient=HORIZONTAL, command=self.update_start) self.startSlider.set(0) self.endSlider = Scale(self.filter, from_=0, to=365, orient=HORIZONTAL, command=self.update_end) self.endSlider.set(365) ## add sliders and labels to GUI self.startSlider.grid(column=1, row=0, sticky=(tk.W, tk.N, tk.E)) self.startlabel = tk.Label(self.filter, text="FROM \tVALUE") self.startlabel.grid(column=0, row=0, sticky=(tk.W)) self.endSlider.grid(column=1, row=1, sticky=(tk.W, tk.S, tk.E)) self.endlabel = tk.Label(self.filter, text="TO \tVALUE") self.endlabel.grid(column=0, row=1, sticky=(tk.W)) #add an empty plot to the GUI def create_plot(self): self.fig = Figure(figsize=(5, 5), dpi=100) #type:Figure self.ax = self.fig.add_subplot(111) #type:Axes self.ax.grid(True) self.canvas = FigureCanvasTkAgg(self.fig, self) ##type:FigureCanvasTkAgg self.canvas.mpl_connect('motion_notify_event', self.handle_hover) self.canvas.mpl_connect('button_press_event', self.handle_mouse_down) self.canvas.mpl_connect('button_release_event', self.handle_mouse_up) #self.canvas.mpl_connect('pick_event', self.draw_tooltip) self.canvas.get_tk_widget().grid(column=1, row=3, sticky=(tk.N, tk.E, tk.W, tk.S)) # self.canvas_tb = NavigationToolbar2TkAgg(self.canvas, self.canvas.get_tk_widget()) #self.ctbwidget=tk.Frame(self) #self.ctbwidget.grid(column=1, row=4, sticky=(tk.N, tk.E, tk.W, tk.S)) #self.canvas_tb = NavigationToolbar2TkAgg(self.canvas, self.ctbwidget) util.zoom_factory(self.ax) ############################ # UI HANDLER ## dummy method def reset_to_start(self): analytics.create_distributions("base", "out", self.ds) analytics.calc_clusters(in_table="cluster_distr", out_table="clustered", datasource=self.ds, k=4) self.clean_tooltip(True) #self.param1box.select_set(self.param_list.index("Large")) #self.param2box.select_set(self.param_list.index("Small")) # self.startSlider.set(0) # self.endSlider.set(365) self.var.set("1") self.handle_aggregate_btn() #self.tdvar.set("0") self.unprocessed_action = self.DATA_TIDYUP self.add_to_history("reset to basedata") self.action_str = "Show base data" #print("hi there, everyone!") def toggle_history(self): if self.history_shown: self.destroy_history() else: self.create_history() def destroy_history(self): self.history_shown = False self.history.destroy() self.historyslider.destroy() #self.history_text = self.history. def handle_aggregate_btn(self): self.aggregation_limit = int(self.noise_spin.get()) self.action_str = "Aggregated values: " + str( self.aggregation_limit) + "min" self.trigger_update(level=self.PLOT_DATA) # def handle_tidy_up(self): # if self.tdvar.get() is "0": # self.action_str="show raw data" # else: # self.action_str="tidy up data, remove all points where:" \ # "\n OutdoorTemp>40 or Small<0 or Large<0 or " \ # "\n RelHumidity<0" # self.trigger_update(level=self.DATA_TIDYUP) def handle_regression(self): if self.rgvar.get() is "0": self.action_str = "hide regression" else: self.action_str = "draw regression" self.trigger_update(level=self.PLOT) def handle_view_change(self, ax=None): if ax is None: ax = self.ax self.handle_changed_axes() print("viewport changed to", ax.get_xlim(), ax.get_ylim()) ######### ## SLIDER METHODS ## we need separate update functions for the sliders, ## as we could otherwise not distinguish between changing ## the first or second slider ######### ## triggered by changing startslider value def update_start(self, event): fromVal = self.startSlider.get() endVal = self.endSlider.get() if endVal < fromVal: self.endSlider.set(fromVal) self.handle_slider_update() ## triggered by changing endslider value def update_end(self, event): fromVal = self.startSlider.get() endVal = self.endSlider.get() if endVal < fromVal: self.startSlider.set(endVal) self.handle_slider_update() ## handle data update event, i.e. a slider changed. #def handle_slider_update(self): # fromVal = self.startSlider.get() # endVal = self.endSlider.get() # self.startlabel["text"] = "FROM \t"+str(self.dates[fromVal]) # self.endlabel["text"] = "TO \t"+str(self.dates[endVal]) # self.trigger_update(level=self.PLOT_DATA) # self.last_action = time() # self.action_str = "New time interval: "+str(self.dates[fromVal])+" - "+str(self.dates[endVal]) ## a different parameter was chosen def handle_paramsChanged(self, e): #self.param1 = self.param_list[self.param1box.curselection()[0]] self.param1 = self.param1var.get() self.param1box.select_clear() self.param2 = self.param2var.get() self.param2box.select_clear() # self.param2 = self.param_list[self.param2box.curselection()[0]] self.action_str = "New parameters: " + self.param1 + " & " + self.param2 self.trigger_update(level=self.PLOT) ################### # PLOT-EVENT HANDLER def handle_changed_axes(self): self.clean_tooltip() xlim = self.ax.get_xlim() ylim = self.ax.get_xlim() text = "Focus changed to: x=[{:.1f};{:.1f}] and y=[{:.1f};{:.1f}]".format( xlim[0], xlim[1], ylim[0], ylim[1]) self.add_to_history(text) ## is called by the plot to confirm if the mouseevent was inside/on a plotted line or a marker def handle_pick(self, line, mouseevent): if mouseevent.button == 1: return self.handle_mouse_event(mouseevent) else: return False, dict() ## is called to to do something when the mouse hovers over the plot and has changed its position. ## if no mousebutton is pressed and no points were selected, a hover-tooltip is shown. ## if the left button is pressed, (re-)draw the selection indicator def handle_hover(self, mouseevent): if not mouseevent.button in [1, 3] and self.select_rect is None: isover, props = self.handle_mouse_event(mouseevent) if isover: self.draw_tooltip(mouseevent, props["ind"]) elif mouseevent.button in [1, 3]: ## handle case if mouse is outside the canvas if mouseevent.xdata == None: xmin = self.mouse_pressed[0] xmax = self.mouse_pressed[0] ymin = self.mouse_pressed[1] ymax = self.mouse_pressed[1] else: xmin = min(mouseevent.xdata, self.mouse_pressed[0]) xmax = max(mouseevent.xdata, self.mouse_pressed[0]) ymin = min(mouseevent.ydata, self.mouse_pressed[1]) ymax = max(mouseevent.ydata, self.mouse_pressed[1]) bbox = (xmin, ymin, xmax, ymax) self.clean_tooltip(True, emit=False) bbox2 = self.ax.transData.transform(bbox) c_height = self.canvas.figure.bbox.height bbox3 = (bbox2[0], c_height - bbox2[1], bbox2[2], c_height - bbox2[3]) self.select_rect = self.canvas.get_tk_widget().create_rectangle( bbox3, dash=".") ## is called whenever a mousebutton is clicked while the mouse is over the plot. ## if the left button is pushed, we begin to draw a selection area def handle_mouse_down(self, mouseevent): if mouseevent.button in [1, 3]: self.clean_tooltip(True) self.mouse_pressed = (mouseevent.xdata, mouseevent.ydata) ## is called whenever a mouse button is released while hovering over the plot ## if the left button was pressed and there are points within the selection area, select those points and show a ## tooltip containing information about those selected points. If not, clean up. def handle_mouse_up(self, mouseevent): if mouseevent.button in [1, 3]: ## handle case if mouse is outside the canvas if mouseevent.xdata == None: xmin = self.mouse_pressed[0] xmax = self.mouse_pressed[0] ymin = self.mouse_pressed[1] ymax = self.mouse_pressed[1] else: xmin = min(mouseevent.xdata, self.mouse_pressed[0]) xmax = max(mouseevent.xdata, self.mouse_pressed[0]) ymin = min(mouseevent.ydata, self.mouse_pressed[1]) ymax = max(mouseevent.ydata, self.mouse_pressed[1]) if xmin == xmax and ymin == ymax: self.clean_tooltip(True) else: if mouseevent.button == 1: if self.param1 == datasource.TIME_ATTR: xmin = mdates.num2date(xmin) xmax = mdates.num2date(xmax) if self.param2 == datasource.TIME_ATTR: ymin = mdates.num2date(ymin) ymax = mdates.num2date(ymax) self.ds.select("selected", self.param1, xmin, xmax, "show") self.ds.select("selected", self.param2, ymin, ymax, "selected") ind = self.df("selected").index.values if len(ind) > 0: self.action_str = "Selected area from ({:.1f}; {:.1f})\n\t to ({:.1f}; {:.1f})".format( xmin, ymin, xmax, ymax) #self.add_to_history(text) self.draw_tooltip(mouseevent, ind, True) self.trigger_update(level=self.TIMELINE_SELECTION) else: self.clean_tooltip(True) else: self.clean_tooltip(True, emit=False) self.ax.set_xlim((xmin, xmax)) self.ax.set_ylim((ymin, ymax)) self.canvas.draw() ## handle any mouse event where it has to be clarified whether there's a marker under the mouse or not. If so, ## return all index values of the concerning markers. def handle_mouse_event(self, mouseevent, radius=5): """ find the points within a certain radius from the mouse in data coords and attach the index numbers of the found elements which are the data points that were picked """ self.clean_tooltip() #print("PICKER") #print(mouseevent, vars(mouseevent)) if self.param1 == datasource.TIME_ATTR or self.param2 == datasource.TIME_ATTR: return False, dict() xydata = self.ax.transData.transform( self.df("show")[[self.param1, self.param2]]).transpose() try: mxy = self.ax.transData.transform( [mouseevent.xdata, mouseevent.ydata]) except ValueError: return False, dict() xdata = xydata[0] ydata = xydata[1] mousex = mxy[0] mousey = mxy[1] if mouseevent.xdata is None: return False, dict() d = pd.np.sqrt((xdata - mousex)**2. + (ydata - mousey)**2.) ind = self.df("show").index.values[pd.np.nonzero( pd.np.less_equal(d, radius))[0]] if len(ind) > 0: props = dict(ind=ind) return True, props else: return False, dict() ## draws a tooltip and generates the information it contains from an event with/and a list of index values def draw_tooltip(self, event, ind=None, selected=False): if ind is None: ind = event.ind event = event.mouseevent # Generate the Tooltip-String selstr = "" if selected: selstr = "selected " if len(ind) is 1: text = selstr + "value:" self.ds.select_ids("selected", ind, "show") for col, cdata in self.df("selected").iteritems(): text += '\n {}: \t{}'.format(col, cdata[ind[0]]) else: text = selstr + "%s values:" % len(ind) if not selected: self.ds.select_ids("selected", ind, "show") self.ds.aggregate("sel_aggremin", "MIN", in_table="selected") self.ds.aggregate("sel_aggremax", "MAX", in_table="selected") for col, cdata in self.df("sel_aggremin").iteritems(): text += '\n {}: \t{} to {}'.format( col, cdata[0], self.df("sel_aggremax")[col][0]) # Draw the box and write the string on it c_height = self.canvas.figure.bbox.height c_width = self.canvas.figure.bbox.width y = c_height - event.y x = event.x #get bounding box of a possible tooltip self.plot_tooltip = self.canvas.get_tk_widget().create_text( x + 2, y, anchor=tk.NW, text=text) bbox = self.canvas.get_tk_widget().bbox(self.plot_tooltip) self.canvas.get_tk_widget().delete(self.plot_tooltip) # print("bbox:", bbox) #make sure the tooltip is within bounds if bbox[2] > c_width: adj = -2 if bbox[3] > c_height: anchor = tk.SE else: anchor = tk.NE else: adj = 2 if bbox[3] > c_height: anchor = tk.SW else: anchor = tk.NW #get the new bounding box if anchor is not tk.NW: # =^= the anchor had to be modified self.plot_tooltip = self.canvas.get_tk_widget().create_text( x + adj, y, anchor=anchor, text=text) bbox = self.canvas.get_tk_widget().bbox(self.plot_tooltip) self.canvas.get_tk_widget().delete(self.plot_tooltip) self.plot_tooltip_rect = self.canvas.get_tk_widget().create_rectangle( bbox, fill="yellow") self.plot_tooltip = self.canvas.get_tk_widget().create_text( x + adj, y, anchor=anchor, text=text) # draws a timeline (as a plot) def draw_timeline(self): #df = self.df("show") ## create value for each day in data, ## depending on whether it is selected, shown etc. #shown_dates = self.build_contained_dict(df) selected_dates = [] if self.select_rect is not None: print("b", self.ds.exists("selected")) self.ds.groupby("selected_days", datasource.TIME_ATTR, "COUNT", "selected", bydate=True) selected_dates = self.df("selected_days").index.values shown_dates = self.df("shown_dates").index.values base_dates = self.df("all_days").index.values ## extract first and last date start_date = base_dates[0] end_date = base_dates[-1] #days_diff = ((end_date-start_date) / np.timedelta64(1, 'D')) ## prepare data for timeline days = [] values = [] for day in self.df("all_days").index.values: if self.df("all_days")[self.param1][day] > 0 and self.df( "all_days")[self.param2][day] > 0: days.append(day) ##if random() < 0.01: #if self.dates[self.startSlider.get()] <= day < self.dates[self.endSlider.get()]: if day in shown_dates: values.append("blue") if day in selected_dates: #if random() < 0.05: values.append("red") else: values.append("lightskyblue") #print("d:",days, values) ## plot timeline fig = Figure(figsize=(12, 1), dpi=75) ax = fig.add_subplot(111) ax.scatter(days, [1] * len(days), c=values, marker='|', s=300) #, fontsize=10) #fig.xt hfmt = mdates.DateFormatter("1. %b '%y") # fig.subplots_adjust(left=0.03, right=0.97, top=1) ax.xaxis.set_major_formatter(hfmt) fig.autofmt_xdate() #ax.set_xticklabels(ax.xaxis.get_minorticklabels(), rotation=0) #ax.set_xlim([datetime(2014,1,1,0,0,0), datetime(2015,1,1,0,0,0)]) ax.set_xlim([start_date, end_date]) ## everything after this is turning off stuff that's plotted by default ax.yaxis.set_visible(False) ax.spines['right'].set_visible(False) ax.spines['left'].set_visible(False) ax.spines['top'].set_visible(False) ax.xaxis.set_ticks_position('bottom') ax.get_yaxis().set_ticklabels([]) fig.tight_layout(pad=0) #print(fig.get_figheight()) #fig.subplots_adjust(top=1, right=0.99) ## add to GUI self.timeline = FigureCanvasTkAgg(fig, self) self.timeline.get_tk_widget().grid(column=0, row=2, sticky=(tk.N, tk.E, tk.W, tk.S), columnspan=5) #print("h:",self.timeline.figure.bbox.height) ##################### # UPDATE-FUNCTIONS ## is called regularly, after the given delay def check_for_update(self): ## if there is an unprocessed action older than ## the given delay, update data #self.check_listbox_changes() if self.unprocessed_action>self.NOTHING and \ (time() - self.last_action) > self.UPDATE_DELAY/1000: ## simply block the very first update... ## (there might be prettier solutions) if self.ignore_start_trigger: self.ignore_start_trigger = False else: ## update data self.update_data() #print("checking for updates...") self.after(self.UPDATE_DELAY, self.check_for_update) """ general data tasks: after_tidyup [-> apply sliders ->] time-limited [-> (don't) aggregate ->] show show [-> select ->] selected [-> get min and max ->] """ ## draw new data according to current positions of date sliders and the aggregation limit def update_data(self): #if self.unprocessed_action >= self.DATA_TIDYUP: #if self.tdvar.get() is "0": # self.ds.link("after_tidyup","base") #else: # self.ds.select("after_tidyup", "Large",a=0, in_table="base") # self.ds.select("after_tidyup", "OutdoorTemp",b=40, in_table="after_tidyup") # self.ds.select("after_tidyup", "RelHumidity",a=0, in_table="after_tidyup") # self.ds.select("after_tidyup", "Small",a=0, in_table="after_tidyup") #self.action_str = "tidy up data, remove all points where:" \ # "\n\tOutdoorTemp>40 or Small<0 or Large<0 or " \ # "\n\tRelHumidity<0 or RelHumidity>100" if self.unprocessed_action >= self.PLOT_DATA: #fromVal = self.startSlider.get() #endVal = self.endSlider.get() #self.ds.link("time-limited","after_tidyup") #self.ds.select(out_table="time-limited", attr_name=datasource.TIME_ATTR, # a=self.dates[fromVal], b=self.dates[endVal], in_table="after_tidyup") #self.df = self.ds.get_data("time_filter").df() if self.aggregation_limit == 1: self.ds.link("show", "base") else: self.ds.aggregate(out_table="show", mode="AVG", limit=self.aggregation_limit, in_table="base") self.ds.groupby("shown_dates", datasource.TIME_ATTR, "COUNT", "show", bydate=True) # try: if self.unprocessed_action >= self.PLOT: self.draw_plot() self.draw_timeline() #print("add_to_history:",self.action_str) if self.action_str is not None: self.add_to_history(self.action_str) # except: # pass self.unprocessed_action = self.NOTHING ## update view with specified data def draw_plot(self): #ax.plot(self.df[self.param1], self.df[self.param2], marker="o", linewidth=0, picker=self.line_picker) self.clean_tooltip(True) self.ax.clear() self.ax.grid(True) x = self.df("show")[self.param1] y = self.df("show")[self.param2] if self.param1 == datasource.TIME_ATTR or self.param2 == datasource.TIME_ATTR: self.plot = self.ax.plot( x, y, picker=self.handle_pick ) #, marker="o", linewidths=0,picker=self.handle_pick) else: self.plot = self.ax.scatter(x=x, y=y, marker="o", linewidths=0, picker=self.handle_pick) self.ax.set_xlabel(self.param1) self.ax.set_ylabel(self.param2) self.ax.set_xlim(x.min(), x.max(), emit=False) self.ax.set_ylim(y.min(), y.max(), emit=False) self.ax.callbacks.connect('xlim_changed', self.handle_view_change) self.ax.callbacks.connect('ylim_changed', self.handle_view_change) #self.canvas. self.fig.tight_layout(pad=0) if self.rgvar.get() is not "0" and not (self.param2 == datasource.TIME_ATTR): self.draw_regression() self.canvas.draw() def draw_regression(self): ## we need to remove rows with NaNs first completedf = self.df("show") completedf = completedf[pd.notnull(completedf[self.param1])] completedf = completedf[pd.notnull(completedf[self.param2])] if self.param1 == datasource.TIME_ATTR: completedf["delta_time"] = (completedf[datasource.TIME_ATTR] - completedf[datasource.TIME_ATTR].min() ) / np.timedelta64(1, "m") X = completedf["delta_time"].to_frame() else: X = completedf[self.param1].to_frame() y = completedf[self.param2].to_frame() lr = LinearRegression() lr.fit(X, y) print(lr.coef_) if self.param1 == datasource.TIME_ATTR: self.ax.plot(completedf[datasource.TIME_ATTR], lr.predict(X), color="red") else: self.ax.plot(X, lr.predict(X), color="red") ################# # helper-functions def df(self, name=None) -> pd.DataFrame: return self.ds.get_data(name).df() ## add line to history window def add_to_history(self, text): self.history_text += "\n" + text if self.history_shown: self.history.insert('end', "\n" + text) # + "\n") self.history.see("end") ## remove the tooltip if shown def clean_tooltip(self, with_select_rect=False, emit=True): if self.plot_tooltip is not None: self.canvas.get_tk_widget().delete(self.plot_tooltip) self.canvas.get_tk_widget().delete(self.plot_tooltip_rect) self.plot_tooltip = None if with_select_rect and self.select_rect is not None: self.canvas.get_tk_widget().delete(self.select_rect) self.select_rect = None if emit: self.action_str = None self.trigger_update(self.TIMELINE_SELECTION) def trigger_update(self, level): self.unprocessed_action = max(self.unprocessed_action, level)
class PlayerControlPanel(Frame, IPlayerStateListener): def __init__(self, parent): super().__init__(parent) self.trackNameLabel: Label = None self.volumeScale: Scale = None self.muted = False self.__initView() def __initView(self): self.configure(borderwidth=3, relief=RIDGE) self.configure(height=HEIGHT) ################################################################################### image = Image.open(PLAY_ICON) image = image.resize((32, 32), Image.ANTIALIAS) self.play_icon = PhotoImage(image=image) image = Image.open(PAUSE_ICON) image = image.resize((32, 32), Image.ANTIALIAS) self.pause_icon = PhotoImage(image=image) self.playPauseButton = Button(self, image=self.play_icon) self.playPauseButton.grid(row=0, column=0) ################################################################################### image = Image.open(NEXT_TRACK_ICON) image = image.resize((32, 32), Image.ANTIALIAS) self.next_track_icon = PhotoImage(image=image) self.nextTrackButton = Button(self, image=self.next_track_icon) self.nextTrackButton.grid(row=0, column=1) ################################################################################### image = Image.open(LINEAR_ICON) image = image.resize((32, 32), Image.ANTIALIAS) self.linear_icon = PhotoImage(image=image) image = Image.open(REPEAT_ICON) image = image.resize((32, 32), Image.ANTIALIAS) self.repeat_icon = PhotoImage(image=image) self.musicSelectionModeButton = Button(self, image=self.next_track_icon) self.musicSelectionModeButton.grid(row=0, column=2) ################################################################################### image = Image.open(MUTE_ICON) image = image.resize((32, 32), Image.ANTIALIAS) self.mute_icon = PhotoImage(image=image) image = Image.open(UNMUTE_ICON) image = image.resize((32, 32), Image.ANTIALIAS) self.unmute_icon = PhotoImage(image=image) self.muteButton = Button(self, image=self.mute_icon, command=self.__muteButtonPressed) self.muteButton.grid(row=0, column=3) ################################################################################### self.volumeScale = Scale(self, from_=0, to=100, orient=HORIZONTAL) self.volumeScale.set(50) self.volumeScale.grid(row=0, column=4) ################################################################################### self.trackProgressBar = Progressbar(self, orient=HORIZONTAL, length=300, mode='determinate', maximum=MAXIMUM) self.trackProgressBar.grid(row=0, column=5) ################################################################################### self.timeLabel = Label(self, text='--:--/--:--') self.timeLabel.grid(row=0, column=6) self.trackNameLabel = Label(self) self.trackNameLabel.grid(row=0, column=7) def onPlayerStateUpdated(self, state: PlayerState): self.trackNameLabel.configure(text=state.trackName) if state.trackType is TrackType.MUSIC: self.trackProgressBar.configure(value=int(MAXIMUM * state.trackPosition)) self.playPauseButton.configure(state=NORMAL) else: self.trackProgressBar.configure(value=0) self.playPauseButton.configure(state=DISABLED) if state.playbackState is PlaybackState.PLAYING: self.playPauseButton.configure(image=self.pause_icon) else: self.playPauseButton.configure(image=self.play_icon) if state.musicSelectionMode is MusicSelectionMode.LINEAR: self.musicSelectionModeButton.configure(image=self.linear_icon) else: self.musicSelectionModeButton.configure(image=self.repeat_icon) self.__displayTime(state) def __displayTime(self, state: PlayerState): trackMinutes = int(state.trackLength / 60) trackSeconds = state.trackLength % 60 played = int(state.trackPosition * state.trackLength) playedMinutes = int(played / 60) playedSeconds = played % 60 if state.trackType is not TrackType.MUSIC: self.timeLabel.configure(text='--:--/--:--') else: self.timeLabel.configure( text= f'{playedMinutes:02d}:{playedSeconds:02d}/{trackMinutes:02d}:{trackSeconds:02d}' ) def setPlayerController(self, playerController: IPlayerController): self.playerController = playerController self.volumeScale.configure(command=lambda v: self.__sendVolume()) self.__sendVolume() self.trackProgressBar.bind( "<Button-1>", lambda e: self.onProgressBarClicked(e, playerController)) self.playPauseButton.configure( command=playerController.onPlayPauseClicked) self.nextTrackButton.configure( command=playerController.nextTrackClicked) self.musicSelectionModeButton.configure( command=playerController.changeMusicSelectionModeClicked) def __sendVolume(self): if self.playerController is None: return if self.muted: self.playerController.onVolumeSelected(0) else: self.playerController.onVolumeSelected(self.volumeScale.get()) def __muteButtonPressed(self): self.muted = not self.muted if self.muted: self.muteButton.configure(image=self.unmute_icon) else: self.muteButton.configure(image=self.mute_icon) self.__sendVolume() def onProgressBarClicked(self, event, playerController: IPlayerController): percentage = event.x / event.widget.winfo_width() playerController.seekTo(percentage) def onPlayerEndReached(self): pass
dots = [] distances = [] widgets = [] colors = ["red", "orange", "green", "blue", "violet"] fen = Tk() fen.title('Project : The smallest enclosing ball') cv = Canvas(fen, width = 750, height = 600, bg = 'snow') cv.pack(side = 'left') commande = Frame(fen, width = 390, height = 560) commande.pack() # Initialize scroll widget. scale = Scale(commande, orient = 'horizontal', from_ = 3, to = 100, resolution = 1, length = 350, label = 'Number of dots') scale.grid(row = 1, column = 1) def create_points(): """Create n random dots on the canvas.""" global n, dots n = scale.get() dots = [(random.randint(220,500), random.randint(170,400)) for k in range(n)] for (x,y) in dots: cv.create_rectangle(x, y, x+3, y+3, fill ='blue') def triangle(liste, a, b, c, x_dot_1, x_dot_2, x_dot_3, y_dot_1, y_dot_2, y_dot_3): # Al-Kashi Theorem. angle_radian_u = acos((-a**2+b**2+c**2)/(2*b*c)) angle_degre_u = int((angle_radian_u*180)/pi) angle_radian_v = acos((-b**2+a**2+c**2)/(2*a*c)) angle_degre_v = int((angle_radian_v*180)/pi)
class hsvrgb_module(baseModule): def __init__(self, parent): baseModule.__init__(self, parent) self._color = Color(255, 0, 0) self.mainFrame = Frame(parent) self.mainFrame.grid(sticky=(E, W)) self.populateInterface(self.mainFrame) def populateInterface(self, parent): """ populate the parent element with all SingleColor elements :param parent: the parent element of all subelements """ """#################### COEF ####################""" self._SV_coefEnabled = StringVar(value="on") self._RB_coefs = self._createToggle(parent, "Disable Coef", "Enable Coef", self._SV_coefEnabled) self._RB_coefs[0].grid(row=0, column=0) self._RB_coefs[1].grid(row=0, column=1) """#################### HUE ####################""" self._SV_hue = StringVar(value="0") self._S_hue = Scale(parent, from_=0, to=360, orient=HORIZONTAL, variable=self._SV_hue, command=self._change_HSV) self._S_hue.grid(row=1, column=0, columnspan=2, sticky=(E, W)) """#################### SATURATION ####################""" self._SV_saturation = StringVar(value="100") self._S_saturation = Scale(parent, from_=0, to=100, orient=HORIZONTAL, variable=self._SV_saturation, command=self._change_HSV) self._S_saturation.grid(row=2, column=0, columnspan=2, sticky=(E, W)) """#################### LUMINOSITY ####################""" self._SV_value = StringVar(value="100") self._S_value = Scale(parent, from_=0, to=100, orient=HORIZONTAL, variable=self._SV_value, command=self._change_HSV) self._S_value.grid(row=3, column=0, columnspan=2, sticky=(E, W)) """#################### RED ####################""" self._SV_red = StringVar(value="255") self._S_red = Scale(parent, from_=0, to=255, orient=HORIZONTAL, variable=self._SV_red, command=self._change_RGB) self._S_red.grid(row=4, column=0, columnspan=2, sticky=(E, W)) """#################### GREEN ####################""" self._SV_green = StringVar(value="0") self._S_green = Scale(parent, from_=0, to=255, orient=HORIZONTAL, variable=self._SV_green, command=self._change_RGB) self._S_green.grid(row=5, column=0, columnspan=2, sticky=(E, W)) """#################### BLUE ####################""" self._SV_blue = StringVar(value="0") self._S_blue = Scale(parent, from_=0, to=255, orient=HORIZONTAL, variable=self._SV_blue, command=self._change_RGB) self._S_blue.grid(row=6, column=0, columnspan=2, sticky=(E, W)) def _getHSVTuple(self): return float(self._SV_hue.get()), float( self._SV_saturation.get()) / 100.0, float( self._SV_value.get()) / 100.0 def _getRGBTuple(self): return def _change_HSV(self, e=None): self._color = Color.fromHSV(float(self._SV_hue.get()), float(self._SV_saturation.get()) / 100.0, float(self._SV_value.get()) / 100.0) self._SV_red.set(self._color.red()) self._SV_green.set(self._color.green()) self._SV_blue.set(self._color.blue()) def _change_RGB(self, e=None): self._color = Color(int(self._SV_red.get()), int(self._SV_green.get()), int(self._SV_blue.get())) h, s, v = self._color.toHSV() self._SV_hue.set(h) self._SV_saturation.set(s * 100) self._SV_value.set(v * 100) def update(self): """ Update the leds from interface parametters """ coefColor = Color(*self._color.toList()) if self._SV_coefEnabled.get() == "on": coefColor.enhance(gr=0.60, br=0.45, bg=0.25) """ Update color """ self.mainFrame.configure(background=self._color.toHex()) """ Send colors to arduino and wait 60ms """ for n in range(self._controller.nbLeds): self._controller.buffer[n] = coefColor.toList() self._controller.send()
result2.delete('1.0', END) result3.delete('1.0', END) value_1 = int(scale.get()) #s = value_1 + 1 for i in range(1, value_1 + 1): if i % 2 == 0: print(i) result.insert(END, f"{i:5} \n") elif i % 3 == 0: result2.insert(END, f"{i:5} \n") elif i % 5 == 0: result3.insert(END, f"{i:5} \n") scale = Scale(win, from_=1, to_=100, showvalue=1, command=calculate) scale.grid(row=0, column=0, sticky="NS") #---------------------- result = Text(win) #雙數用 result.grid(row=0, column=1) #----------------------- scroll = Scrollbar(win) scroll.grid(row=0, column=2, sticky="NS") #------------------------ result2 = Text(win) #3的倍數用 result2.grid(row=0, column=3) #----------------------- scroll2 = Scrollbar(win) scroll2.grid(row=0, column=4, sticky="NS") result3 = Text(win) #5的倍數用 result3.grid(row=0, column=5)
command=lambda t: update(2, t), variable=int_vars[2]) # scales for 6 servos servos = [] for i in range(6): servo = (lambda i: Scale(root, from_=0, to_=180, orient=HORIZONTAL, length=600, command=lambda t: update(3 + i, t), variable=int_vars[3 + i]))(i) # closure servo.configure(background="white") servos.append(servo) servo.set(arm.position[i]) servo.grid(row=3 + i, column=1) sx.set(100) sy.set(100) sz.set(100) sx.configure(background="white") sy.configure(background="white") sz.configure(background="white") sx.grid(row=0, column=1) sy.grid(row=1, column=1) sz.grid(row=2, column=1) plt.show() root.mainloop()
stress_weight_label = Label(master, text="Stress weight:") stress_weight_label.grid(row=row_counter, column=0) def scale_changed(val): global compute_st compute_st = int(val) var = DoubleVar() scale = Scale(master, variable=var, from_=0, to=10, orient=HORIZONTAL, command=scale_changed) scale.grid(row=row_counter, column=1) row_counter += 1 metric_weight_label = Label(master, text="Metric weight:") metric_weight_label.grid(row=row_counter, column=0) def metric_weight_scale_changed(val): global weight_param weight_param = int(val) metric_weight_var = DoubleVar() metric_weight_scale = Scale(master, variable=metric_weight_var, from_=0, to=10, orient=HORIZONTAL,
time_range_labelA.grid(row=4, column=0) time_range_labelB.grid(row=4, column=2) from_year_select.grid(row=4, column=1) to_year_select.grid(row=4, column=3) # 第五行,对游戏评分做出要求 critical_score_scale = Scale(window, label='媒体评分高于', from_=0, to=100, orient=HORIZONTAL, length=400, showvalue=1, tickinterval=10, resolution=1) critical_score_scale.grid(row=5, column=0, columnspan=2) user_score_scale = Scale(window, label='大众评分高于', from_=0, to=10, orient=HORIZONTAL, length=400, showvalue=1, tickinterval=1, resolution=0.1) user_score_scale.grid(row=5, column=2, columnspan=2) # 第六行,确认提交所选游戏指标要求 submit_btn = Button(window, text='提交', font=('Microsoft YaHei', 15),
class SettingsDisplay(Dialog): """ Settings form User Interface""" def body(self, master): self.root_window = master.master.master # This is really gross. I'm sorry. self.logger = logging.getLogger(self.root_window.logger.name + '.SettingsDisplay') self.key_listener = KeybindManager(self, sticky=True) # Labels Label(master, text="Start Minimized?: ").grid(row=0, column=0) Label(master, text="Avg. Monitor Default: ").grid(row=1, column=0) Label(master, text="Smooth Transition Time (sec): ").grid(row=2, column=0) Label(master, text="Brightness Offset: ").grid(row=3, column=0) Label(master, text="Add Preset Color: ").grid(row=4, column=0) Label(master, text="Audio Input Source: ").grid(row=5, column=0) Label(master, text="Add keyboard shortcut").grid(row=6, column=0) # Widgets # Starting minimized self.start_mini = BooleanVar(master, value=config.getboolean("AppSettings", "start_minimized")) self.start_mini_check = Checkbutton(master, variable=self.start_mini) # Avg monitor color match self.avg_monitor = StringVar(master, value=config["AverageColor"]["DefaultMonitor"]) options = ['full', 'get_primary_monitor', *getDisplayRects()] # lst = getDisplayRects() # for i in range(1, len(lst) + 1): # els = [list(x) for x in itertools.combinations(lst, i)] # options.extend(els) self.avg_monitor_dropdown = OptionMenu(master, self.avg_monitor, *options) self.duration_scale = Scale(master, from_=0, to_=2, resolution=1 / 15, orient=HORIZONTAL) self.duration_scale.set(float(config["AverageColor"]["Duration"])) self.brightness_offset = Scale(master, from_=0, to_=65535, resolution=1, orient=HORIZONTAL) self.brightness_offset.set(int(config["AverageColor"]["brightnessoffset"])) # Custom preset color self.preset_color_name = Entry(master) self.preset_color_name.insert(END, "Enter color name...") self.preset_color_button = Button(master, text="Choose and add!", command=self.get_color) # Audio dropdown device_names = self.master.audio_interface.get_device_names() try: init_string = " " + config["Audio"]["InputIndex"] + " " + device_names[int(config["Audio"]["InputIndex"])] except ValueError: init_string = " None" self.audio_source = StringVar(master, init_string) # AudioSource index is grabbed from [1], so add a space at [0] as_choices = device_names.items() self.as_dropdown = OptionMenu(master, self.audio_source, *as_choices) # Add keybindings lightnames = list(self.root_window.lightsdict.keys()) self.keybind_bulb_selection = StringVar(master, value=lightnames[0]) self.keybind_bulb_dropdown = OptionMenu(master, self.keybind_bulb_selection, *lightnames) self.keybind_keys_select = Entry(master) self.keybind_keys_select.insert(END, "Add key-combo...") self.keybind_keys_select.config(state='readonly') self.keybind_keys_select.bind('<FocusIn>', self.on_keybind_keys_click) self.keybind_keys_select.bind('<FocusOut>', lambda *_: self.keybind_keys_select.config(state='readonly')) self.keybind_color_selection = StringVar(master, value="Color") self.keybind_color_dropdown = OptionMenu(master, self.keybind_color_selection, *self.root_window.framesdict[ self.keybind_bulb_selection.get()].default_colors, *( [*config["PresetColors"].keys()] if any( config["PresetColors"].keys()) else [None]) ) self.keybind_add_button = Button(master, text="Add keybind", command=lambda *_: self.register_keybinding( self.keybind_bulb_selection.get(), self.keybind_keys_select.get(), self.keybind_color_selection.get())) self.keybind_delete_button = Button(master, text="Delete keybind", command=self.delete_keybind) # Insert self.start_mini_check.grid(row=0, column=1) ttk.Separator(master, orient=HORIZONTAL).grid(row=0, sticky='esw', columnspan=100) self.avg_monitor_dropdown.grid(row=1, column=1) self.duration_scale.grid(row=2, column=1) self.brightness_offset.grid(row=3, column=1) ttk.Separator(master, orient=HORIZONTAL).grid(row=3, sticky='esw', columnspan=100) self.preset_color_name.grid(row=4, column=1) self.preset_color_button.grid(row=4, column=2) ttk.Separator(master, orient=HORIZONTAL).grid(row=4, sticky='esw', columnspan=100) self.as_dropdown.grid(row=5, column=1) ttk.Separator(master, orient=HORIZONTAL).grid(row=5, sticky='esw', columnspan=100) self.keybind_bulb_dropdown.grid(row=6, column=1) self.keybind_keys_select.grid(row=6, column=2) self.keybind_color_dropdown.grid(row=6, column=3) self.keybind_add_button.grid(row=6, column=4) self.mlb = MultiListbox(master, (('Bulb', 5), ('Keybind', 5), ('Color', 5))) for keypress, fnx in dict(config['Keybinds']).items(): label, color = fnx.split(':') self.mlb.insert(END, (label, keypress, color)) self.mlb.grid(row=7, columnspan=100, sticky='esw') self.keybind_delete_button.grid(row=8, column=0) def validate(self): config["AppSettings"]["start_minimized"] = str(self.start_mini.get()) config["AverageColor"]["DefaultMonitor"] = str(self.avg_monitor.get()) config["AverageColor"]["Duration"] = str(self.duration_scale.get()) config["AverageColor"]["BrightnessOffset"] = str(self.brightness_offset.get()) config["Audio"]["InputIndex"] = str(self.audio_source.get()[1]) # Write to config file with open('config.ini', 'w') as cfg: config.write(cfg) self.key_listener.shutdown() return 1 def get_color(self): """ Present user with color pallette dialog and return color in HSBK """ color = askcolor()[0] if color: # RGBtoHBSK sometimes returns >65535, so we have to clamp hsbk = [min(c, 65535) for c in RGBtoHSBK(color)] config["PresetColors"][self.preset_color_name.get()] = str(hsbk) def register_keybinding(self, bulb: str, keys: str, color: str): """ Get the keybind from the input box and pass the color off to the root window. """ try: color = self.root_window.framesdict[self.keybind_bulb_selection.get()].default_colors[color] except KeyError: # must be using a custom color color = str2list(config["PresetColors"][color], int) self.root_window.save_keybind(bulb, keys, color) config["Keybinds"][str(keys)] = str(bulb + ":" + str(color)) self.mlb.insert(END, (str(bulb), str(keys), str(color))) self.keybind_keys_select.config(state='normal') self.keybind_keys_select.delete(0, 'end') self.keybind_keys_select.insert(END, "Add key-combo...") self.keybind_keys_select.config(state='readonly') self.preset_color_name.focus_set() # Set focus to a dummy widget to reset the Entry def on_keybind_keys_click(self, event): """ Call when cursor is in key-combo entry """ self.update() self.update_idletasks() self.key_listener.restart() self.keybind_keys_select.config(state='normal') self.update() self.update_idletasks() while self.focus_get() == self.keybind_keys_select: self.keybind_keys_select.delete(0, 'end') self.keybind_keys_select.insert(END, self.key_listener.get_key_combo_code()) self.update() self.update_idletasks() def delete_keybind(self): """ Delete keybind currently selected in the multi-list box. """ _, keybind, _ = self.mlb.get(ACTIVE) self.mlb.delete(ACTIVE) self.root_window.delete_keybind(keybind) config.remove_option("Keybinds", keybind)
def create_voices(self): voice_ids = ['1', '2', '3', '4'] SCALES = OrderedDict([ ('pan_pos', {'min': -1, 'max': 1, 'start': 0.5, 'res': 0.001}), ('volume', {'min': 0, 'max': 1, 'start': 0.666, 'res': 0.001}), ('slide_duration_msecs', {'min': 0, 'max': 2000, 'start': 60, 'res': 1}), ('slide_duration_prop', {'min': 0, 'max': 2, 'start': 0.666, 'res': 0.001}), ('binaural_diff', {'min': 0, 'max': 66, 'start': 0.2, 'res': 0.01}) ]) for vid in voice_ids: counter = 0 for sca in SCALES: name = 'voice_' + vid + '_' + sca setattr(self, 'min_' + name, SCALES[sca]['min']) setattr(self, 'max_' + name, SCALES[sca]['max']) this_sca = Scale(self, label=sca, orient=HORIZONTAL, from_=getattr(self, 'min_' + name), to=getattr(self, 'max_' + name), resolution=SCALES[sca]['res']) this_sca.enable = ('enable' in list(SCALES[sca].keys()) and SCALES[sca]['enable'] or None) this_sca.disable = ('disable' in list(SCALES[sca].keys()) and SCALES[sca]['disable'] or None) this_sca.grid(column=int(2 + int(vid)), row=counter, sticky=E + W) this_sca.bind("<ButtonRelease>", self.scale_handler) this_sca.ref = name counter += 1 CHECK_BUTTONS = OrderedDict( [('mute', False), ('automate_binaural_diffs', True), ('automate_note_duration_prop', True), ('use_proportional_slide_duration', {'val': True, 'label': 'proportional slide'}), ('automate_pan', True), ('automate_wavetables', True)]) for vid in voice_ids: counter = 0 cb_frame = LabelFrame(self, text="Voice {0} - Automation".format(vid)) setattr(self, 'voice_' + vid + '_cb_frame', cb_frame) for cb in CHECK_BUTTONS: options = CHECK_BUTTONS[cb] name = 'voice_' + vid + '_' + cb if isinstance(options, dict) and 'label' in list(options.keys()): label = options['label'] else: label = cb[9:] if cb[:9] == 'automate_' else cb setattr(self, name, IntVar( value=type(options) == dict and options['val'] or options)) self.this_cb = Checkbutton(cb_frame, text=label, variable=getattr(self, name)) self.this_cb.bind('<Button-1>', self.check_boxes_handler) self.this_cb.disable = None self.this_cb.grid(sticky=W, column=0, row=counter) self.this_cb.ref = name counter += 1 # add trigger wavetable-button trigWavetableButton = Button(cb_frame, text='Next Wavetable') trigWavetableButton.bind('<Button-1>', self.trigger_waveform_handler) trigWavetableButton.ref = 'voice_' + vid + "_trigger_wavetable" trigWavetableButton.grid(row=counter) cb_frame.grid(column=int(vid) + 2, row=5, sticky=E + W + N, rowspan=8) for vid in voice_ids: generation_types = ["random", "random_harmonic", "harmonic"] partial_pools = ["even", "odd", "all"] prefix = 'voice_' + vid + '_' types_name = prefix + 'wavetable_generation_type' pools_name = prefix + 'partial_pool' setattr(self, types_name, StringVar()) getattr(self, types_name).set("random") setattr(self, pools_name, StringVar()) getattr(self, pools_name).set("all") target_frame = getattr(self, 'voice_' + vid + '_cb_frame') gen_typ_frame = LabelFrame(target_frame, text="type") gen_typ_frame.grid(row=len(target_frame.winfo_children()), sticky=W) for gen_t in generation_types: gen_t_entry = Radiobutton(gen_typ_frame, value=gen_t, text=gen_t, anchor=W, variable=getattr(self, types_name)) gen_t_entry.bind('<ButtonRelease-1>', self.wt_handler) gen_t_entry.ref = types_name gen_t_entry.grid(row=len(gen_typ_frame.winfo_children()), sticky=W) pp_frame = LabelFrame(target_frame, text="harmonics") for pp in partial_pools: pp_entry = Radiobutton(pp_frame, value=pp, text=pp, anchor=W, variable=getattr(self, pools_name)) pp_entry.bind('<ButtonRelease-1>', self.wt_handler) pp_entry.ref = pools_name pp_entry.grid(row=len(pp_frame.winfo_children()), sticky=E + W) this_num_partials = Scale(pp_frame, label='number of harmonics', orient=HORIZONTAL, from_=1, to=24, resolution=1) this_num_partials.ref = prefix + 'num_partials' this_num_partials.grid(column=0, row=len(pp_frame.winfo_children()), sticky=E + W) this_num_partials.bind("<ButtonRelease>", self.scale_handler) pp_frame.grid(row=len(target_frame.winfo_children()), sticky=E + W)
class HsvGui(tk.Frame): def __init__(self, master=None,): tk.Frame.__init__(self, master) self.root = master self.Webcam = G2.Webcamera() self.baseImage = self.Webcam.save_image(persist=False) self.baseImage = cv2.cvtColor(numpy.array(self.baseImage), cv2.COLOR_RGB2BGR) self.createWidgets() self.OnValueChange = event.Event() self.title = "Webcam" cv2.startWindowThread() cv2.namedWindow(self.title, cv2.WINDOW_NORMAL) cv2.imshow(self.title, self.baseImage) self.Funkify() def createWidgets(self): Label(self.root, text="Value:").grid(row=0, sticky=W) Label(self.root, text="H:").grid(row=1, sticky=W) Label(self.root, text="S:").grid(row=2, sticky=W) Label(self.root, text="V:").grid(row=3, sticky=W) Label(self.root, text="S:").grid(row=4, sticky=W) Label(self.root, text="V:").grid(row=5, sticky=W) Label(self.root, text="H:").grid(row=6, sticky=W) self.valueLabel = Label(self.root, text="000-000-000 to 000-000-000") self.valueLabel.grid(row=0, column=1, sticky=W) self.Hvalue = Scale(self.root, from_=0, to=255, orient=HORIZONTAL, command=self.__sliderCallback) self.Hvalue.grid(row=1, column=1) self.Hvalue.set(0) self.Svalue = Scale(self.root, from_=0, to=255, orient=HORIZONTAL, command=self.__sliderCallback) self.Svalue.grid( row=2, column=1) self.Svalue.set(90) self.Vvalue = Scale(self.root, from_=0, to=255, orient=HORIZONTAL, command=self.__sliderCallback) self.Vvalue.grid( row=3, column=1) self.Vvalue.set(0) self.HvalueMax = Scale(self.root, from_=0, to=255, orient=HORIZONTAL, command=self.__sliderCallback) self.HvalueMax.grid(row=4, column=1) self.HvalueMax.set(255) self.SvalueMax = Scale(self.root, from_=0, to=255, orient=HORIZONTAL, command=self.__sliderCallback) self.SvalueMax.grid(row=5, column=1) self.SvalueMax.set(255) self.VvalueMax = Scale(self.root, from_=0, to=255, orient=HORIZONTAL, command=self.__sliderCallback) self.VvalueMax.grid(row=6, column=1) self.VvalueMax.set(120) self.Go = tk.Button(self.root, text="Go!", fg="Green", command=self.Funkify) self.Go.grid(row=7, column=0) self.QUIT = tk.Button(self.root, text="QUIT", fg="red", command=self.root.destroy) self.QUIT.grid(row=7, column=1) def Funkify(self): H = int(self.Hvalue.get()) S = int(self.Svalue.get()) V = int(self.Vvalue.get()) lower = [H, S, V] Hmax = int(self.HvalueMax.get()) Smax = int(self.SvalueMax.get()) Vmax = int(self.VvalueMax.get()) upper= [Hmax, Smax, Vmax] #self.valueLabel['text'] = '{0}-{1}-{2} to {3}-{4}-{5}'.format(H, S, V, Hmax, Smax, Vmax) output, a = self.Webcam.funkyfy(colorrange=(lower, upper)) cv2.imshow(self.title, numpy.hstack([output, a])) def __sliderCallback(self, args): print('Sliding!!')
class Application(Frame): def __init__(self, master=None): Frame.__init__(self, master) self.sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM) self.send_sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM) self.sock.bind((host, port)) self.grid() self.columnconfigure(0, minsize=100) self.columnconfigure(1, minsize=200) self.columnconfigure(2, minsize=200) self.columnconfigure(3, minsize=150) self.columnconfigure(4, minsize=150) self.columnconfigure(5, minsize=150) self.columnconfigure(6, minsize=150) self.create_widgets() self.settables = self.assemble_settables() self.gui_logger = logging.getLogger('gui') self.request_update() def create_widgets(self): self.create_monitor() self.create_check_buttons() self.create_ranges() self.create_scales() self.create_radio_buttons() self.create_voices() self.quitButton = Button(self, text='Quit', command=self.quit) self.quitButton.grid(columnspan=7, sticky=E + W) def assemble_settables(self): settables = self.winfo_children() for w in settables: settables += w.winfo_children() return [w for w in settables if w.__class__.__name__ in ['Scale', 'Checkbutton']] def create_radio_buttons(self): # Scale related entries = ['DIATONIC', 'HARMONIC', 'MELODIC', 'PENTATONIC', 'PENTA_MINOR', 'GREEK_CHROMATIC', 'GREEK_ENHARMONIC'] self.scale = StringVar() self.scale.set('DIATONIC') self.rb_frame = Frame(self) for e in entries: rb = Radiobutton(self.rb_frame, value=e, text=e, anchor=W, command=self.send_scale, variable=self.scale) rb.grid(row=len(self.rb_frame.winfo_children()), sticky=W) self.rb_frame.grid(column=1, row=len(self.grid_slaves(column=1)), rowspan=3) def create_monitor(self): self.monitor_frame = LabelFrame(self, text="Monitor and Transport") this_cycle = Scale(self.monitor_frame, label='cycle_pos', orient=HORIZONTAL, from_=1, to=16, resolution=1) this_cycle.disable, this_cycle.enable = (None, None) this_cycle.ref = 'cycle_pos' this_cycle.grid(column=0, row=0, sticky=E + W) self.updateButton = Button(self.monitor_frame, text='Reload all Settings', command=self.request_update) self.updateButton.grid(row=1, sticky=E + W) self.ForceCaesuraButton = Button(self.monitor_frame, text='Force Caesura', command=self.force_caesura) self.ForceCaesuraButton.grid(row=2, sticky=E + W) self.saveBehaviourButton = Button(self.monitor_frame, text='Save current behaviour', command=self.request_saving_behaviour) self.saveBehaviourButton.grid(row=3, sticky=E + W) self.saveBehaviourNameEntry = Entry(self.monitor_frame) self.saveBehaviourNameEntry.grid(row=4, sticky=E + W) self.saveBehaviourNameEntry.bind('<KeyRelease>', self.request_saving_behaviour) self.selected_behaviour = StringVar() self.selected_behaviour.trace('w', self.new_behaviour_chosen) self.savedBehavioursMenu = OptionMenu(self.monitor_frame, self.selected_behaviour, None,) self.savedBehavioursMenu.grid(row=5, sticky=E + W) self.monitor_frame.grid(column=0, row=10, sticky=E + W) def request_update(self): self.send({'sys': 'update'}) def request_saving_behaviour(self, event=None): """callback for save behaviour button and textentry""" if event and event.widget == self.saveBehaviourNameEntry: if event.keysym == 'Return': name = self.saveBehaviourNameEntry.get() self.saveBehaviourNameEntry.delete(0, len(name)) else: return else: # button was pressed name = self.saveBehaviourNameEntry.get() if name: self.send({'sys': ['save_behaviour', name]}) def force_caesura(self): self.send({'force_caesura': True}) def create_voices(self): voice_ids = ['1', '2', '3', '4'] SCALES = OrderedDict([ ('pan_pos', {'min': -1, 'max': 1, 'start': 0.5, 'res': 0.001}), ('volume', {'min': 0, 'max': 1, 'start': 0.666, 'res': 0.001}), ('slide_duration_msecs', {'min': 0, 'max': 2000, 'start': 60, 'res': 1}), ('slide_duration_prop', {'min': 0, 'max': 2, 'start': 0.666, 'res': 0.001}), ('binaural_diff', {'min': 0, 'max': 66, 'start': 0.2, 'res': 0.01}) ]) for vid in voice_ids: counter = 0 for sca in SCALES: name = 'voice_' + vid + '_' + sca setattr(self, 'min_' + name, SCALES[sca]['min']) setattr(self, 'max_' + name, SCALES[sca]['max']) this_sca = Scale(self, label=sca, orient=HORIZONTAL, from_=getattr(self, 'min_' + name), to=getattr(self, 'max_' + name), resolution=SCALES[sca]['res']) this_sca.enable = ('enable' in list(SCALES[sca].keys()) and SCALES[sca]['enable'] or None) this_sca.disable = ('disable' in list(SCALES[sca].keys()) and SCALES[sca]['disable'] or None) this_sca.grid(column=int(2 + int(vid)), row=counter, sticky=E + W) this_sca.bind("<ButtonRelease>", self.scale_handler) this_sca.ref = name counter += 1 CHECK_BUTTONS = OrderedDict( [('mute', False), ('automate_binaural_diffs', True), ('automate_note_duration_prop', True), ('use_proportional_slide_duration', {'val': True, 'label': 'proportional slide'}), ('automate_pan', True), ('automate_wavetables', True)]) for vid in voice_ids: counter = 0 cb_frame = LabelFrame(self, text="Voice {0} - Automation".format(vid)) setattr(self, 'voice_' + vid + '_cb_frame', cb_frame) for cb in CHECK_BUTTONS: options = CHECK_BUTTONS[cb] name = 'voice_' + vid + '_' + cb if isinstance(options, dict) and 'label' in list(options.keys()): label = options['label'] else: label = cb[9:] if cb[:9] == 'automate_' else cb setattr(self, name, IntVar( value=type(options) == dict and options['val'] or options)) self.this_cb = Checkbutton(cb_frame, text=label, variable=getattr(self, name)) self.this_cb.bind('<Button-1>', self.check_boxes_handler) self.this_cb.disable = None self.this_cb.grid(sticky=W, column=0, row=counter) self.this_cb.ref = name counter += 1 # add trigger wavetable-button trigWavetableButton = Button(cb_frame, text='Next Wavetable') trigWavetableButton.bind('<Button-1>', self.trigger_waveform_handler) trigWavetableButton.ref = 'voice_' + vid + "_trigger_wavetable" trigWavetableButton.grid(row=counter) cb_frame.grid(column=int(vid) + 2, row=5, sticky=E + W + N, rowspan=8) for vid in voice_ids: generation_types = ["random", "random_harmonic", "harmonic"] partial_pools = ["even", "odd", "all"] prefix = 'voice_' + vid + '_' types_name = prefix + 'wavetable_generation_type' pools_name = prefix + 'partial_pool' setattr(self, types_name, StringVar()) getattr(self, types_name).set("random") setattr(self, pools_name, StringVar()) getattr(self, pools_name).set("all") target_frame = getattr(self, 'voice_' + vid + '_cb_frame') gen_typ_frame = LabelFrame(target_frame, text="type") gen_typ_frame.grid(row=len(target_frame.winfo_children()), sticky=W) for gen_t in generation_types: gen_t_entry = Radiobutton(gen_typ_frame, value=gen_t, text=gen_t, anchor=W, variable=getattr(self, types_name)) gen_t_entry.bind('<ButtonRelease-1>', self.wt_handler) gen_t_entry.ref = types_name gen_t_entry.grid(row=len(gen_typ_frame.winfo_children()), sticky=W) pp_frame = LabelFrame(target_frame, text="harmonics") for pp in partial_pools: pp_entry = Radiobutton(pp_frame, value=pp, text=pp, anchor=W, variable=getattr(self, pools_name)) pp_entry.bind('<ButtonRelease-1>', self.wt_handler) pp_entry.ref = pools_name pp_entry.grid(row=len(pp_frame.winfo_children()), sticky=E + W) this_num_partials = Scale(pp_frame, label='number of harmonics', orient=HORIZONTAL, from_=1, to=24, resolution=1) this_num_partials.ref = prefix + 'num_partials' this_num_partials.grid(column=0, row=len(pp_frame.winfo_children()), sticky=E + W) this_num_partials.bind("<ButtonRelease>", self.scale_handler) pp_frame.grid(row=len(target_frame.winfo_children()), sticky=E + W) def wt_handler(self, event): print(event.widget.tk) ref = event.widget.ref self.send({ref: getattr(self, ref).get()}) def create_check_buttons(self): self.cb_frame = LabelFrame(self, text="Global Settings") for cb in CHECK_BUTTONS: label = cb target_parent = self.cb_frame if isinstance(CHECK_BUTTONS[cb], dict) and 'sub_frame' in list(CHECK_BUTTONS[cb].keys()): target_parent = getattr(self, CHECK_BUTTONS[cb]['sub_frame']) setattr(self, cb, IntVar(value=type(CHECK_BUTTONS[cb]) == dict and CHECK_BUTTONS[cb]['val'] or CHECK_BUTTONS[cb])) self.this_cb = Checkbutton(target_parent, text=label, variable=getattr(self, cb)) self.this_cb.bind('<Button-1>', self.check_boxes_handler) self.this_cb.disable = (type(CHECK_BUTTONS[cb]) == dict and 'disable' in list(CHECK_BUTTONS[cb].keys())) self.this_cb.grid(sticky=W, column=0, row=len(target_parent.winfo_children())) self.this_cb.ref = cb for but in GLOBAL_BUTTONS: label = but ele = GLOBAL_BUTTONS[but] this_but = Button(self.cb_frame, text=but) this_but.bind('<ButtonRelease-1>', getattr(self, ele['handler'])) this_but.ref = but this_but.grid(sticky=W, column=0, row=len(self.cb_frame.winfo_children())) self.cb_frame.grid(column=0, row=0, rowspan=10, sticky=N) def new_behaviour_chosen(self, a, b, c): self.send({'sys': ['change_behaviour', self.selected_behaviour.get()]}) def set_value(self, name, val): '''sets a widget to the specified value various different widget types need custom setting functionality''' direct = ['scale', 'wavetable_generation_type', 'partial_pool'] if [x for x in direct if match("(voice_\d_|)" + x, name)]: self.gui_logger.info("setting: '{0}' to '{1}' in GUI".format(name, val)) getattr(self, name).set(val) return if name == 'saved_behaviours' and len(val): self.savedBehavioursMenu.destroy() self.savedBehavioursMenu = OptionMenu(self.monitor_frame, self.selected_behaviour, *sorted(val)) self.savedBehavioursMenu.grid(row=5, sticky=E + W) return for w in self.settables: typ = w.__class__.__name__ if w.ref == name: # print "setting '{0}' of type: '{1}' to: {2}".format(name, typ, val) if typ == 'Scale': w.set(val) elif typ == "Checkbutton": w.select() if val else w.deselect() def check_boxes_handler(self, event): '''handles checkbox events. shows and hides gui elements according to their enable/disable fields''' # print event.__dict__ # print event.widget.__dict__ ref = event.widget.ref val = not getattr(self, ref).get() # because is read before the var is changed self.send({ref: val}) # print ref, val # handle gui elements # enable/disable functionality temporarily(?) commented on: # Wed Aug 17 09:39:54 CEST 2011 # if event.widget.disable: # for w in self.children.values(): # # # this try clause is for debugging, remove when stable # try: # w.ref # #print w.ref # except: # pass # if (w.__class__.__name__ == 'Scale' and # (w.disable or w.enable)): # if w.disable == ref: # if val: # w.grid() # else: # w.grid_remove() # elif w.enable == ref: # if val: # w.grid_remove() # else: # w.grid() # #print w.disable, w.enable def create_scales(self): counter = 0 for sca in SCALES: label = SCALES[sca]['label'] if 'label' in list(SCALES[sca].keys()) else sca setattr(self, 'min_' + sca, SCALES[sca]['min']) setattr(self, 'max_' + sca, SCALES[sca]['max']) self.this_scale = Scale(self, label=label, orient=HORIZONTAL, from_=getattr(self, 'min_' + sca), to=getattr(self, 'max_' + sca), resolution=SCALES[sca]['res']) self.this_scale.set(SCALES[sca]['start']) self.this_scale.enable = ('enable' in list(SCALES[sca].keys()) and SCALES[sca]['enable'] or None) self.this_scale.disable = ('disable' in list(SCALES[sca].keys()) and SCALES[sca]['disable'] or None) if 'pos' in list(SCALES[sca].keys()): pos = SCALES[sca]['pos'] col = pos['c'] row = pos['r'] else: row = counter col = 1 counter += 1 self.this_scale.grid(column=col, row=row, sticky=E + W) self.this_scale.ref = sca self.this_scale.bind("<ButtonRelease>", self.scale_handler) def scale_handler(self, event): self.send({event.widget.ref: event.widget.get()}) self.gui_logger.info("handling scale: {0}, with new value: {1}".format( event.widget.ref, event.widget.get())) def trigger_waveform_handler(self, event): self.send({event.widget.ref: True}) # print event.widget.ref, "- triggering wavetable" def send_scale(self): do = {'scale': self.scale.get()} self.send(do) def send(self, msg): self.gui_logger.info("sending: {0}".format(msg)) self.send_sock.sendto(json.dumps(msg), (remote_host, send_port)) def create_ranges(self): counter = 0 for ran in RANGES: setattr(self, 'min_' + ran, RANGES[ran]['min']) setattr(self, 'max_' + ran, RANGES[ran]['max']) self.this_min_scale = Scale(self, label='min ' + ran, orient=HORIZONTAL, from_=getattr(self, 'min_' + ran), to=getattr(self, 'max_' + ran), resolution=RANGES[ran]['res']) self.this_max_scale = Scale(self, label='max ' + ran, orient=HORIZONTAL, from_=getattr(self, 'min_' + ran), to=getattr(self, 'max_' + ran), resolution=RANGES[ran]['res']) self.this_min_scale.set(RANGES[ran]['min_start']) self.this_max_scale.set(RANGES[ran]['max_start']) self.this_min_scale.enable = ('enable' in list(RANGES[ran].keys()) and RANGES[ran]['enable'] or None) self.this_min_scale.disable = ('disable' in list(RANGES[ran].keys()) and RANGES[ran]['disable'] or None) self.this_max_scale.enable = ('enable' in list(RANGES[ran].keys()) and RANGES[ran]['enable'] or None) self.this_max_scale.disable = ('disable' in list(RANGES[ran].keys()) and RANGES[ran]['disable'] or None) self.this_min_scale.grid(column=2, row=counter, sticky=E + W) self.this_max_scale.grid(column=2, row=counter + 1, sticky=E + W) self.this_min_scale.ref = 'min_' + ran self.this_max_scale.ref = 'max_' + ran self.this_min_scale.bind("<ButtonRelease>", self.scale_handler) self.this_max_scale.bind("<ButtonRelease>", self.scale_handler) counter += 2 def socket_read_handler(self, file, mask): data_object = json.loads(file.recv(1024)) do = list(data_object.items())[0] self.set_value(do[0], do[1])
class Fenetre(Tk): def __init__(self): Tk.__init__(self) self.tilt_val_init = 110 self.pan_val_init = 75 self.pan_min = 0 self.pan_max = 105 self.tilt_min = 35 self.tilt_max = 135 self.pas = 5 # Full Screen largeur, hauteur = self.winfo_screenwidth(), self.winfo_screenheight() self.overrideredirect(0) self.geometry("%dx%d" % (largeur, hauteur)) # TILT self.tilt_bar = Scale(self, from_=self.tilt_min, to=self.tilt_max, length=250, label='Tilt', sliderlength=20, orient=HORIZONTAL, command=self.update_tilt) self.tilt_bar.set((self.tilt_max + self.tilt_min) // 2) self.tilt_bar.grid(row=1, column=2) self.tilt_angle = StringVar() self.tilt_val = self.tilt_bar.get() # PAN self.pan_bar = Scale(self, from_=self.pan_min, to=self.pan_max, length=250, label='Pan', sliderlength=20, orient=HORIZONTAL, command=self.update_pan) self.pan_bar.set((self.pan_max + self.pan_min) // 2) self.pan_bar.grid(row=2, column=2) self.pan_angle = StringVar() self.pan_val = self.pan_bar.get() # PS3 Controller self.bind("<a>", self.pan_plus) self.bind("<d>", self.pan_moins) self.bind("<s>", self.tilt_plus) self.bind("<w>", self.tilt_moins) self.bind("<p>", self.lean_left) self.bind("<m>", self.lean_right) self.bind("<q>", self.initialiser_positon) self.bind("<j>", self.forward) self.bind("<u>", self.reverse) self.bind("<h>", self.left) self.bind("<k>", self.right) self.bind("<i>", self.break_motor) self.bind("<Button-2>", self.alarm) self.bind("<Button-3>", self.beep) # Motor self.gear = 0 self.speed_init = 5 self.speed = self.speed_init self.leds = [led_1, led_2, led_3] self.bind("<e>", self.shift_down) self.bind("<r>", self.shift_up) self.pwm = gpio.PWM(enable_pin, 50) # 50 is the frequency # Infos self.pas_label = Label(self, text=str(self.pas)) self.pas_label.grid(row=3) self.buzzer_state = 0 #--------Buzzer-------- def beep(self, event, time=100): self.buzzer_on() self.after(time, self.buzzer_off) def buzzer_on(self): gpio.output(buzzer, gpio.HIGH) self.buzzer_state = 1 def buzzer_off(self): gpio.output(buzzer, gpio.LOW) self.buzzer_state = 0 def alarm(self, event): if self.buzzer_state == 0: gpio.output(buzzer, gpio.HIGH) self.buzzer_state = 1 else: gpio.output(buzzer, gpio.LOW) self.buzzer_state = 0 #-------Camera------- #-------Motor------- def shift_up(self, event): if self.gear != 3: self.gear += 1 gpio.output(self.leds[self.gear - 1], gpio.HIGH) else: self.beep(event, time=70) if self.gear == 0: self.speed = self.speed_init elif self.gear == 1: self.speed = 33 elif self.gear == 2: self.speed = 66 elif self.gear == 3: self.speed = 100 def shift_down(self, event): if self.gear != 0: gpio.output(self.leds[self.gear - 1], gpio.LOW) self.gear -= 1 if self.gear == 0: self.speed = self.speed_init elif self.gear == 1: self.speed = 33 elif self.gear == 2: self.speed = 66 elif self.gear == 3: self.speed = 100 def forward(self, event): self.go("forward") def reverse(self, event): self.go("reverse") def right(self, event): self.go("right") def left(self, event): self.go("left") def lean_left(self, event): self.go('lean left') def lean_right(self, event): self.go('lean right') def break_motor(self, event): self.go("stop") def go(self, direction): gpio_reset_motor() if direction == "forward": print("forward") gpio.output(right_forward, gpio.HIGH) gpio.output(left_forward, gpio.HIGH) elif direction == "reverse": print("reverse") gpio.output(right_reverse, gpio.HIGH) gpio.output(left_reverse, gpio.HIGH) elif direction == "right": print("right") gpio.output(left_reverse, gpio.HIGH) gpio.output(right_forward, gpio.HIGH) elif direction == "left": print("left") gpio.output(right_reverse, gpio.HIGH) gpio.output(left_forward, gpio.HIGH) elif direction == 'lean left': gpio.output(left_reverse, gpio.HIGH) elif direction == 'lean right': gpio.output(right_reverse, gpio.HIGH) elif direction == 'stop': self.pwm.stop() self.pwm = gpio.PWM(enable_pin, 50) # 50 is the frequency else: pass self.pwm.start(self.speed) # a "speed" of 50, sends power exactly every second cycle #time.sleep(1) #direction = input('Enter next direction') #-------Servos------- def tilt_plus(self, event): if verif_angle(self.tilt_val + self.pas, self.tilt_min, self.tilt_max): self.tilt_val += self.pas self.tilt_bar.set(self.tilt_val) def tilt_moins(self, event): if verif_angle(self.tilt_val - self.pas, self.tilt_min, self.tilt_max): self.tilt_val -= self.pas self.tilt_bar.set(self.tilt_val) def pan_plus(self, event): if verif_angle(self.pan_val + self.pas, self.pan_min, self.pan_max): self.pan_val += self.pas self.pan_bar.set(self.pan_val) def pan_moins(self, event): if verif_angle(self.pan_val - self.pas, self.pan_min, self.pan_max): self.pan_val -= self.pas * 2 self.pan_bar.set(self.pan_val) def pas_plus(self, event): if self.pas + 1 < 21: self.pas += 1 self.update_window() def pas_moins(self, event): if self.pas - 1 > 0: self.pas -= 1 self.update_window() def update_tilt(self, x): if x == 0: pass set_servo(int(x), 0) self.tilt_val = int(x) def update_pan(self, x): if x == 0: pass set_servo(int(x), 1) self.pan_val = int(x) def update_window(self): self.pas_label['text'] = str(self.pas) def initialiser_positon(self, event): self.tilt_bar.set(self.tilt_val_init) self.pan_bar.set(self.pan_val_init)
class shades_module(baseModule): def __init__(self, parent): baseModule.__init__(self, parent) self._color = Color(255, 0, 0) self._colors = [Color() for _ in range(10)] self.mainFrame = Frame(parent) self.mainFrame.grid(sticky=(E, W)) self.mainFrame.configure(background=self._color.toHex()) self.populateInterface(self.mainFrame) self.iupdateCounter = 0 self.newColors = [] def populateInterface(self, parent): """ populate the parent element with all SingleColor elements :param parent: the parent element of all subelements """ """#################### HUE ####################""" self._LF_hue = LabelFrame(parent, text="H") self._LF_hue.grid(row=0, column=0, sticky=(E, W)) self._SV_hue = StringVar(value="0") self._S_hue = Scale(self._LF_hue, from_=0, to=360, orient=HORIZONTAL, variable=self._SV_hue, command=self._change_HSV) self._S_hue.grid(row=0, column=0, columnspan=2, sticky=E) self._SV_hueD = StringVar(value="60") self._S_hueD = Scale(self._LF_hue, from_=0, to=120, orient=HORIZONTAL, variable=self._SV_hueD) self._S_hueD.grid(row=1, column=0, columnspan=2, sticky=E) """#################### SATURATION ####################""" self._LF_saturation = LabelFrame(parent, text="S") self._LF_saturation.grid(row=1, column=0, sticky=(E, W)) self._SV_saturation = StringVar(value="100") self._S_saturation = Scale(self._LF_saturation, from_=0, to=100, orient=HORIZONTAL, variable=self._SV_saturation, command=self._change_HSV) self._S_saturation.grid(row=0, column=0, columnspan=2, sticky=E) self._SV_saturationD = StringVar(value="0") self._S_saturationD = Scale(self._LF_saturation, from_=0, to=100, orient=HORIZONTAL, variable=self._SV_saturationD) self._S_saturationD.grid(row=1, column=0, columnspan=2, sticky=E) """#################### LUMINOSITY ####################""" self._LF_value = LabelFrame(parent, text="V") self._LF_value.grid(row=2, column=0, sticky=(E, W)) self._SV_value = StringVar(value="100") self._S_value = Scale(self._LF_value, from_=0, to=100, orient=HORIZONTAL, variable=self._SV_value, command=self._change_HSV) self._S_value.grid(row=0, column=0, columnspan=2, sticky=E) self._SV_valueD = StringVar(value="0") self._S_valueD = Scale(self._LF_value, from_=0, to=100, orient=HORIZONTAL, variable=self._SV_valueD) self._S_valueD.grid(row=1, column=0, columnspan=2, sticky=E) """#################### Speed ####################""" self._LF_SPEED = LabelFrame(parent, text="T") self._LF_SPEED.grid(row=3, column=0, sticky=(E, W)) self._SV_SPEED = StringVar(value="60") self._S_SPEED = Scale(self._LF_SPEED, from_=10, to=500, orient=HORIZONTAL, variable=self._SV_SPEED) self._S_SPEED.grid(row=0, column=0, columnspan=2, sticky=E) self._B_SPEED_Reset = Button(self._LF_SPEED, command=self.resetSpeed, text="Reset speed") self._B_SPEED_Reset.grid(row=1, column=0, sticky=E) """#################### Interpolation ####################""" self._LF_INTERPO = LabelFrame(parent, text="I") self._LF_INTERPO.grid(row=4, column=0, sticky=(E, W)) self._SV_INTERPO = StringVar(value="100") self._S_INTERPO = Scale(self._LF_INTERPO, from_=10, to=100, orient=HORIZONTAL, variable=self._SV_INTERPO) self._S_INTERPO.grid(row=0, column=0, columnspan=2, sticky=E) def resetSpeed(self): self._S_SPEED.set(5) def _change_HSV(self, e=None): self._color = Color.fromHSV(float(self._SV_hue.get()), float(self._SV_saturation.get()) / 100.0, float(self._SV_value.get()) / 100.0) self.mainFrame.configure(background=self._color.toHex()) def update(self): #self._SV_SPEED.get()) != self._parent.getSpeed(): if int(self._parent.getSpeed()) != 5: self._parent.setSpeed(5) #int(self._SV_SPEED.get())) if self._controller.nbLeds is not None and self._controller.nbLeds > len( self._colors): self._colors = [Color() for _ in range(self._controller.nbLeds)] if self.iupdateCounter != 0: for i in range(self._controller.nbLeds): self._colors[i] = self.interpolate(self._colors[i], self.newColors[i], 0.05) tmp = Color.fromList(self._colors[i].toList()).enhance(gr=0.60, br=0.45, bg=0.25) self._controller.buffer[i] = tmp.toList() self._controller.send() self.iupdateCounter -= 1 else: hue = float(self._SV_hue.get()) hueD = float(self._SV_hueD.get()) HueValues = (hue, (hue - hueD) % 360) saturation = float(self._SV_saturation.get()) saturationD = float(self._SV_saturationD.get()) SatValues = (saturation, saturation - saturationD) value = float(self._SV_value.get()) valueD = float(self._SV_valueD.get()) ValValues = (value, value - valueD) self.newColors.clear() for i in range(self._controller.nbLeds): self.newColors.append( Color.fromHSV( randrange(min(*HueValues), max(*HueValues)), randrange(min(*SatValues), max(*SatValues)) / 100.0, randrange(min(*ValValues), max(*ValValues)) / 100.0)) self.iupdateCounter = int(self._SV_SPEED.get()) // 5
class Visual(Frame): '''Class that takes a world as argument and present it graphically on a tkinter canvas.''' def __init__(self): ''' Sets up a simulation GUI in tkinter. ''' Frame.__init__(self) self.master.title("The Schelling Segregation Model in Python") self.master.wm_resizable(0, 0) self.grid() self.movement_possible = True # --------------------------------------- # # --------- FRAMES FOR GUI -------------- # # --------------------------------------- # # The pane for user values self._entryPane = Frame(self, borderwidth=5, relief='sunken') self._entryPane.grid(row=0, column=0, sticky='n') # The buttons pane self._buttonPane = Frame(self, borderwidth=5) self._buttonPane.grid(row=1, column=0, sticky='n') # A temp pane where graph is located, just for cosmetic reasons width, height = 425, 350 self._graph = Canvas(self, width=width, height=height, background="black") self._graph.configure(relief='sunken', border=2) self._graph.grid(row=3, column=0) # The pane where the canvas is located self._animationPane = Frame(self, borderwidth=5, relief='sunken') self._animationPane.grid(row=0, column=1, rowspan=4, pady=10, sticky="n") # --------------------------------------- # # --------- FILLING THE FRAMES ---------- # # --------------------------------------- # self._canvas() # Create graphics canvas self._entry() # Create entry widgets self._buttons() # Create button widgets def _plot_setup(self, time): '''Method for crudely annotating the graph window.''' time = time # Main plot width, height = 425, 350 y0 = -time/10 self._graph = Canvas(self, width=width, height=height, background="black", borderwidth=5) self._graph.grid(row=3, column=0) self.trans = Plotcoords(width, height, y0, -0.2, time, 1.3) x, y = self.trans.screen(time // 2, 1.2) x1, y1 = self.trans.screen(time // 2, 1.13) self._graph.create_text(x, y, text="% Happy", fill="green", font="bold 12") self._graph.create_text(x1, y1, text="% Unhappy", fill="red", font="bold 12") # Line x-axis x, y = self.trans.screen((-5 * (time / 100)), -0.05) x1, y = self.trans.screen(time, -0.05) self._graph.create_line(x, y, x1, y, fill="white", width=1.5) # Text x-axis x_text, y_text = self.trans.screen(time / 2, -0.15) self._graph.create_text(x_text, y_text, text="Time", fill="white", font="bold 12") # Line y-axis x, y = self.trans.screen((-0.5 * (time / 100)), -0.05) x, y1 = self.trans.screen((-5 * (time / 100)), 1) self._graph.create_line(x, y, x, y1, fill="white", width=1.5) def _entry(self): '''Method for creating widgets for collecting user input.''' # N (no of turtles) dim = 30*30 self.fill_label = Label(self._entryPane, anchor='w', justify='left', text='Fill', relief='raised', width=12, height=1, font='italic 20') self.fill_label.grid(row=0, column=1, ipady=14) self.fill = Scale(self._entryPane, from_=0, to=1, resolution=0.01, bd=3, relief='sunken', orient='horizontal', length=235, tickinterval=20) self.fill.grid(row=0, column=2) self.fill.set(0.8) self._N_label = Label(self._entryPane, anchor='w', justify='left', text="N:", relief='raised', width=12, height=1, font="italic 20") self._N_label.grid(row=1, column=1, ipady=14) self._N = Scale(self._entryPane, from_=0, to=100, resolution=1, bd=3, relief='sunken', orient='horizontal', length=235, tickinterval=20) self._N.set(30) self._N.grid(row=1, column=2) # Ticks (length of simulation) self._Ticks_label = Label(self._entryPane, anchor='w', justify='left', text="Time:", relief='raised', width=12, height=1, font="bold 20") self._Ticks_label.grid(row=2, column=1, ipady=14) self._Ticks = Scale(self._entryPane, from_=10, to=1000, resolution=1, bd=3, relief='sunken', orient='horizontal', length=235, tickinterval=990) self._Ticks.set(500) self._Ticks.grid(row=2, column=2) # % similar wanted self._Similar_label = Label(self._entryPane, anchor='w', justify='left', text="Similar wanted:", relief='raised', width=12, height=1, font="bold 20") self._Similar_label.grid(row=3, column=1, ipady=14) self._Similar = Scale(self._entryPane, from_=0.0, to=1.0, resolution=0.01, bd=3, relief='sunken', orient='horizontal', length=235, tickinterval=0.5) self._Similar.set(0.76) self._Similar.grid(row=3, column=2) # Delay between steps self._delay_label = Label(self._entryPane, anchor='w', justify='left', text="Delay (s):", relief='raised', width=12, height=1, font="bold 20") self._delay_label.grid(row=4, column=1, ipady=14) self._delay = Scale(self._entryPane, from_=0.0, to=1.0, resolution=0.01, bd=3, relief='sunken', orient='horizontal', length=235, tickinterval=0.5) self._delay.set(0.15) self._delay.grid(row=4, column=2) def _buttons(self): '''Method for creating button widgets for setting up, running and plotting results from simulation.''' width = 7 height = 1 # The 'Setup' button self._setupButton = Button(self._buttonPane, text="Setup", command=self._setup, width=width, height=height, font="bold 30", relief='raised', borderwidth=5) self._setupButton.grid(row=0, column=0) # The 'Go' button self._goButton = Button(self._buttonPane, text="Go", command=self._go, width=width, height=height, font="bold 30", relief='raised', borderwidth=5) self._goButton.grid(row=0, column=1) # The 'Quit' button self._quitButton = Button(self._buttonPane, text="Quit", command=self._quit, width=width, height=height, font="bold 30", relief='raised', borderwidth=5) self._quitButton.grid(row=1, column=0, columnspan=2) def _canvas(self): '''Creates the canvas on which everything happens.''' # The tick counter information self._Tick_counter = Label(self._animationPane, anchor='w', justify='left', text="Time:", width=5, font="bold 20") self._Tick_counter.grid(row=0, column=0, sticky="e") self._Tick_counter1 = Label(self._animationPane, justify='center', text="", relief='raised', width=5, font="bold 20") self._Tick_counter1.grid(row=0, column=1, sticky='w') self.canvas_w, self.canvas_h = 750, 750 self.canvas = Canvas(self._animationPane, width=self.canvas_w, height=self.canvas_h, background="black") self.canvas.grid(row=1, column=0, columnspan=2) def _setup(self): '''Method for 'Setup' button.''' # Clearing the canvas and reset the go button self.canvas.delete('all') self._goButton['relief'] = 'raised' self.N = int(self._N.get()) self.Ticks = int(self._Ticks.get()) self.similar = float(self._Similar.get()) self.data = [] self.tick_counter = 0 self._Tick_counter1['text'] = str(self.tick_counter) self._plot_setup(self.Ticks) self.grid_size = self.N self.world = World(750, 750, self.grid_size) self.create_turtles() self.neighbouring_turtles() self.draw_turtles() def _go(self): '''Method for the 'Go' button, i.e. running the simulation.''' self._goButton['relief'] = 'sunken' if self.tick_counter <= self.Ticks: self._Tick_counter1['text'] = str(self.tick_counter) self.canvas.update() self._graph.update() self._graph.after(0) # Data collection turtles_unhappy = self.check_satisfaction() prop_happy, prop_unhappy = self.calc_prop_happy(self.tick_counter) self.data_collection(self.tick_counter, prop_happy, prop_unhappy) if self.tick_counter >= 1: # HAPPY values (%) x0 = self.tick_counter-1 x1 = self.tick_counter # Collecting values from stored data y0 = self.data[self.tick_counter-1][1] y1 = self.data[self.tick_counter][1] # Transforming to tkinter x1, y1 = self.trans.screen(x1, y1) x0, y0 = self.trans.screen(x0, y0) self._graph.create_line(x0, y0, x1, y1, fill="green", width=1.3, tag="happy") # Draw "happy lines # UNHAPPY values (%) x0 = self.tick_counter-1 x1 = self.tick_counter # Collecting values from stored data y0 = self.data[self.tick_counter-1][2] y1 = self.data[self.tick_counter][2] # Transforming to tkinter x1, y1 = self.trans.screen(x1, y1) x0, y0 = self.trans.screen(x0, y0) self._graph.create_line(x0, y0, x1, y1, fill="red", width=1.1, tag="unhappy") # Draw unhappy lines if prop_happy < 1: self.turtle_move(turtles_unhappy) time.sleep(self._delay.get()) self.update_neighbours() self.tick_counter += 1 self.canvas.after(0, self._go()) self._goButton['relief'] = 'raised' def _quit(self): '''Method for the 'Quit' button.''' self.master.destroy() # ------------------------------------------------------ # # ---------- FUNCTIONS CALLED AT EACH TICK ------------- # # ------------------------------------------------------ # def turtle_move(self, unhappy_turtles): '''Moves all the unhappy turtles (randomly).''' while unhappy_turtles: i = random.randint(0, len(unhappy_turtles)-1) turtle = unhappy_turtles.pop(i) turtle.move(self) def update_neighbours(self): '''Updates the turtles neigbour attributes. Called after all turtles have moved.''' for turtle in self.turtles: turtle.update_neighbours() def check_satisfaction(self): '''Checks to see if turtles are happy or not. Returns a list of unhappy turtles, i.e. turtles that should move. Called before the move method.''' for turtle in self.turtles: turtle.is_happy() unhappy_turtles = [] for element in self.turtles: if not element.happy: unhappy_turtles.append(element) return unhappy_turtles def calc_prop_happy(self, i): '''Calculates the proportion of happy turtles.''' happy = 0 unhappy = 0 for turtle in self.turtles: if turtle.happy: happy += 1 else: unhappy += 1 prop_happy = happy/len(self.turtles) prop_unhappy = unhappy/len(self.turtles) return prop_happy, prop_unhappy def data_collection(self, i, prop_happy, prop_unhappy): '''Method for collecting data at each tick.''' self.data.append((i, prop_happy, prop_unhappy)) # ------------------------------------------------------ # # ---------- INITIALISATION FUNCTIONS ------------------ # # ------------------------------------------------------ # def create_turtles(self): '''Method for creating a new list of turtles. Upon creation they are registered in the World object.''' if self.N*self.N <= self.grid_size*self.grid_size: counter = 0 self.turtles = [] while counter < self.N * self.N * self.fill.get(): s = "S"+str(counter) if counter <= int(self.N * self.N * self.fill.get() / 2): color = "green" else: color = "red" x = random.randint(0, self.grid_size-1) y = random.randint(0, self.grid_size-1) if not self.world.patch_list[x][y]: new_turtle = Schelling(world=self.world, x=x, y=y, s=s, color=color, similar_wanted=self.similar) self.world.register(new_turtle) counter += 1 self.turtles.append(new_turtle) else: print("Number of turtles exceeds world!") def draw_turtles(self): '''Method for drawing turtles on canvas. Calls each turtle's own method for drawing.''' for turtle in self.turtles: turtle.draw(self.canvas) def neighbouring_turtles(self): '''Method for updating turtles' neighbours. Calls on each turtle's own method for updating neighbours.''' for turtle in self.turtles: turtle.get_neighbouring_patches()
def initui(self): self.parent.title("Light pollution map") self.style = Style() self.style.theme_use("alt") self.grid(row=0, column=0) padding = {'padx':'5', 'pady':'5'} big_heading_font = ("Arial", 14, 'bold') small_heading_font = ("Arial", 10, 'bold') # Create frames. # There are three frames for settings - preprocessing, convolve, and contour. # Each also has an image frame underneath it. # Layout is as follows: # # -------------------------------------------------------------------------- # | | | | | # | | | | | # | import_body | process_body | contour_body | export_body | # | | | | | # | | | | | # -------------------------------------------------------------------------- # Settings frames top = self.winfo_toplevel() top.rowconfigure(0, weight=1) top.columnconfigure(0, weight=1) self.rowconfigure(0, weight=1) self.columnconfigure(0, weight=1) self.columnconfigure(1, weight=1) self.columnconfigure(2, weight=1) self.columnconfigure(3, weight=1) import_body = Frame(self, relief=RAISED, borderwidth=1) import_body.grid(row=0, column=0, sticky=N+S+E+W) process_body = Frame(self, relief=RAISED, borderwidth=1) process_body.grid(row=0, column=1, sticky=N+S+E+W) contour_body = Frame(self, relief=RAISED, borderwidth=1) contour_body.grid(row=0, column=2, sticky=N+S+E+W) export_body = Frame(self, relief=RAISED, borderwidth=1) export_body.grid(row=0, column=3, sticky=N+S+E+W) # ============================================================================================================= # # Contents of load_image_frame # # ============================================================================================================= # Heading processing_frame_header = Label(import_body, text="Import", font=big_heading_font) processing_frame_header.grid(row=0, column=0, sticky=N, **padding) filename_variable = StringVar() # Import image import_canvas = Canvas(import_body, width=canvas_size, height=canvas_size, background='black') import_canvas.grid(row=1, column=0, sticky=N, **padding) # Load file method def choosefile(): filename_variable.set(filedialog.askopenfilename(parent=import_body)) image = Image.open(filename_variable.get()) thumbnail = create_thumbnail(image, canvas_size) import_canvas.create_image(0, 0, image=thumbnail, anchor=NW) load_image_button = Button(import_body, text="Import image", command=choosefile) load_image_button.grid(row=2, column=0, columnspan=2, sticky=E+W+S, **padding) import_body.rowconfigure(2, weight=1) # ============================================================================================================= # # Contents of processing_frame # # ============================================================================================================= processing_frame_header = Label(process_body, text="Process", font=big_heading_font) processing_frame_header.grid(row=0, column=0, columnspan=2, sticky=N, **padding) clipping_variable = IntVar() constants_label = Label(process_body, text="Clipping", font=("Arial", 10, 'bold')) constants_label.grid(row=1, column=0, sticky=E, **padding) clipping_label = Label(process_body, text="Remove pixels with \n brightness under") clipping_label.grid(row=2, column=0, sticky=E, **padding) clipping_entry = Entry(process_body, textvariable=clipping_variable, width=4) clipping_entry.grid(row=2, column=1, sticky=W, **padding) clipping_variable.set(value=default_clipping_value) convolve_header = Label(process_body, text="Kernel", font=small_heading_font) convolve_header.grid(row=4, column=0, sticky=E, **padding) kernel_size_variable = IntVar() kernel_size_label = Label(process_body, text="Convolve kernel size", justify=RIGHT) kernel_size_label.grid(row=5, column=0, sticky=E, **padding) kernel_size_entry = Entry(process_body, textvariable=kernel_size_variable, width=4) kernel_size_entry.grid(row=5, column=1, sticky=W, **padding) kernel_size_variable.set(value=default_kernel_size) # Constants for convolve equation constants_label = Label(process_body, text="Falloff", font=("Arial", 10, 'bold')) constants_label.grid(row=6, column=0, sticky=E, **padding) constant_a_label = Label(process_body, text="Constant A:") constant_b_label = Label(process_body, text="Constant B:") constant_c_label = Label(process_body, text="Constant C:") constant_a_label.grid(row=7, column=0, sticky=E, **padding) constant_b_label.grid(row=8, column=0, sticky=E, **padding) constant_c_label.grid(row=9, column=0, sticky=E, **padding) constant_a_variable = DoubleVar() constant_b_variable = DoubleVar() constant_c_variable = DoubleVar() constant_a_entry = Entry(process_body, textvariable=constant_a_variable, width=4) constant_b_entry = Entry(process_body, textvariable=constant_b_variable, width=4) constant_c_entry = Entry(process_body, textvariable=constant_c_variable, width=4) constant_a_variable.set(default_constant_a) constant_b_variable.set(default_constant_b) constant_c_variable.set(default_constant_c) constant_a_entry.grid(row=7, column=1, **padding) constant_b_entry.grid(row=8, column=1, **padding) constant_c_entry.grid(row=9, column=1, **padding) constants_note = Label(process_body, text="Falloff equation is (Ax^B)-C", font=("Arial", 9)) constants_note.grid(row=10, column=0, columnspan=2, sticky=E, **padding) # Start button! def process(): print("Filename was " + filename_variable.get()) image_data = process_image(filename=filename_variable.get(), kernel_size=kernel_size_variable.get(), clipping_value=clipping_variable.get(), constant_a=constant_a_variable.get(), constant_b=constant_b_variable.get(), constant_c=constant_c_variable.get() ) image_data = Image.open("processed_image.png") thumbnail = create_thumbnail(image_data, canvas_size) export_canvas.create_image(0, 0, image=thumbnail, anchor=NW) start_button = Button(process_body, text="Process image", command=process) start_button.grid(row=11, column=0, columnspan=3, sticky=E+W+S, **padding) process_body.rowconfigure(11, weight=1) # ============================================================================================================= # # Contents of contour_frame # # ============================================================================================================= contour_header = Label(contour_body, text="Contour", font=big_heading_font) contour_header.grid(row=0, column=0, sticky=S, columnspan=2, **padding) contour_note = Label(contour_body, text="(optional)") contour_note.grid(row=1, column=0, sticky=S, columnspan=2) scale_options = {"width":"5", "length":"150"} slider_padding = {"padx":"2", "pady":"0"} scale_list = [] scale_values_list = [] default_scale_values = [5, 7, 10, 20, 30, 40, 60, 100, 200] for i in range(9): scale = Scale(contour_body, from_=0, to_=255, orient=HORIZONTAL, **scale_options) scale.grid(row=i+2, column=0, columnspan=2, sticky=S, **slider_padding) scale.set(default_scale_values[i]) scale_list.append(scale) for scale in scale_list: print(scale) print(type(scale)) #print(scale.get()) def contour(): scale_values_list.clear() for scale in scale_list: scale_values_list.append(scale.get()) contour_image(scale_values_list) image_data = Image.open("Contoured_image.png") thumbnail = create_thumbnail(image_data, canvas_size) export_canvas.create_image(0, 0, image=thumbnail, anchor=NW) contour_button = Button(contour_body, text="Contour image", command=contour) contour_button.grid(row=11, column=0, columnspan=2, sticky=E+S+W, **padding) contour_body.rowconfigure(11, weight=1) contour_body.columnconfigure(1, weight=1) # ============================================================================================================= # # Contents of export_body # # ============================================================================================================= filename_export_variable = StringVar() def export_file(): filename_options = {} filename_options['filetypes'] = [('PNG', '.png')] filename_options['initialfile'] = 'output.png' filename_options['parent'] = self filename_export_variable.set(filedialog.asksaveasfilename(**filename_options)) image_data = Image.open("Contoured_image.png") image_data.save(filename_export_variable.get()) export_header = Label(export_body, text="Export", font=big_heading_font) export_header.grid(row=0, column=0, sticky=N, **padding) export_canvas = Canvas(export_body, width=canvas_size, height=canvas_size, background='black') export_canvas.grid(row=1, column=0, **padding) export_button = Button(export_body, text="Export image", command=export_file) export_button.grid(row=2, column=0, columnspan=2, sticky=E+W+S, **padding) export_body.rowconfigure(2, weight=1)