Module sprit.sprit_tkinter_ui
This script contains all the functions, classes, etc. to create a tkinter app for graphical user interface.
Functions
def catch_errors(func)
def on_closing()
def reboot_app()
-
Restarts the current program. Note: this function does not return. Any cleanup action (like saving data) must be done before calling this function.
Classes
class SPRIT_App (master)
-
Expand source code
class SPRIT_App: global spritApp def __init__(self, master): self.master = master self.master.title("SPRIT") self.params = sprit_hvsr.HVSRData({'site':''}) # Set the theme self.darkthemepath = pathlib.Path(pkg_resources.resource_filename(__name__, "resources/themes/forest-dark.tcl")) self.lightthemepath = pathlib.Path(pkg_resources.resource_filename(__name__, "resources/themes/forest-light.tcl")) # Create the style object self.style = ttk.Style(master) # #self.style.theme_use('forest-light') self.create_menubar() self.create_tabs() self.master.rowconfigure(0, weight=1) self.master.columnconfigure(0, weight=1) if 'forest' in current_theme_name: if 'light' in current_theme_name: self.master.tk.call('source', self.lightthemepath) else: self.master.tk.call('source', self.darkthemepath) else: self.style.theme_use(current_theme_name) # Create the dark theme #self.style.theme_create("dark", parent="alt", settings={ # "TLabel": {"configure": {"background": "black", "foreground": "white"}}, # "TButton": {"configure": {"background": "black", "foreground": "white"}}, # # Add more options here to style other widgets #}) # Create the light theme #self.style.theme_create("light", parent="alt", settings={ # "TLabel": {"configure": {"background": "white", "foreground": "black"}}, # "TButton": {"configure": {"background": "white", "foreground": "black"}}, # # Add more options here to style other widgets #}) #Method to log error message def log_errorMsg(self, logMsg): self.log_text.insert('end', logMsg) self.tab_control.select(self.log_tab) #Not currently working def manual_label_update(self): for notebook in self.master.winfo_children(): if isinstance(notebook, ttk.Notebook): for tab_id in notebook.tabs(): tab_frame = notebook.nametowidget(tab_id) for frame in tab_frame.winfo_children(): if isinstance(frame, ttk.LabelFrame): for widget in frame.winfo_children(): if isinstance(widget, ttk.Label): # apply the updated style to the label self.style.layout('CustTLabel', [('Label.border', {'sticky': 'nswe', 'border': '1', 'children': [('Label.padding', {'sticky': 'nswe', 'children': [('Label.text', {'sticky': 'nswe'})]})]})]) self.style.configure('CustTLabel', background=self.style.lookup('style', 'background'), foreground=self.style.lookup('style', 'background')) self.style.map('CustTLabel', {'priority':[('CustTLabel',1)]}) widget.configure(style='CustTLabel') def create_menubar(self): self.menubar = tk.Menu(self.master) self.master.config(menu=self.menubar) self.sprit_menu = tk.Menu(self.menubar, tearoff=0) def on_theme_select(): # Set the theme based on the selected value self.style = ttk.Style() #Update the theme file so the new theme opens on reboot prev_theme = curr_gui_dict['theme_name'] curr_gui_dict['theme_name'] = self.theme_var.get() with open(gui_theme_file, 'w') as f: json.dump(curr_gui_dict, f) def apply_theme(): if 'forest' in self.theme_var.get(): if self.theme_var.get()=='forest-dark' and 'forest-dark' not in self.style.theme_names(): self.master.tk.call('source', self.darkthemepath) elif self.theme_var.get()=='forest-light' and 'forest-light' not in self.style.theme_names(): self.master.tk.call('source', self.lightthemepath) self.master.tk.call("ttk::style", "theme", "use", self.theme_var.get()) if curr_gui_dict['theme_name']=='forest-light' or curr_gui_dict['theme_name'] == 'forest-dark': do_reboot = messagebox.askyesno('App Restart Required', f"It is recommended to restart the SpRIT GUI at this time to apply this theme. If not, you may continue but theme errors may occur. Click No to retain current theme ({prev_theme}) \nReboot now?", ) print(do_reboot) if do_reboot: reboot_app() else: self.theme_var.set(prev_theme) else: apply_theme() """An attempt to get the backgrounds right def apply_to_all_children(widget, func): Recursively apply a function to all child widgets of a given widget children = widget.winfo_children() for child in children: func(child) apply_to_all_children(child, func) return def change_background_color(widget): if isinstance(widget, tk.Label): widget.option_clear() widget.configure(background=None, foreground=None) return apply_to_all_children(self.master, change_background_color) """ #self.master.tk.call("ttk::setTheme", self.theme_var.get()) #self.style.theme_use(self.theme_var.get()) #self.master.tk.call('source', self.lightthemepath) #self.style.theme_use(self.theme_var.get()) #self.style.configure("TLabel", background=self.style.lookup('TLabel', 'background'), foreground=self.style.lookup('TLabel', 'background')) def import_parameters(self): filepath = filedialog.askopenfilename() def export_parameters(self): filepath = filedialog.asksaveasfilename() self.theme_menu = tk.Menu(self.menubar, tearoff=0) self.theme_var = tk.StringVar(value=current_theme_name) self.theme_menu.add_radiobutton(label="Default", variable=self.theme_var, value="default", command=on_theme_select) self.theme_menu.add_radiobutton(label="Clam", variable=self.theme_var, value="clam", command=on_theme_select) self.theme_menu.add_radiobutton(label="Alt", variable=self.theme_var, value="alt", command=on_theme_select) self.theme_menu.add_radiobutton(label="Forest Light (buggy)", variable=self.theme_var, value="forest-light", command=on_theme_select) self.theme_menu.add_radiobutton(label="Forest Dark (buggy)", variable=self.theme_var, value="forest-dark", command=on_theme_select) self.sprit_menu.add_cascade(label="Theme", menu=self.theme_menu) self.sprit_menu.add_command(label="Import Parameters", command=import_parameters) self.sprit_menu.add_command(label="Export Parameters", command=export_parameters) self.sprit_menu.add_separator() self.sprit_menu.add_command(label="Exit", command=self.master.quit) self.settings_menu = tk.Menu(self.menubar, tearoff=0) self.instrument_menu = tk.Menu(self.settings_menu, tearoff=0) self.instrument_var = tk.StringVar(value="Raspberry Shake") self.instrument_menu.add_radiobutton(label="Raspberry Shake", variable=self.instrument_var, value="Raspberry Shake") self.instrument_menu.add_radiobutton(label="Tromino", variable=self.instrument_var, value="Tromino") self.instrument_menu.add_radiobutton(label="Other", variable=self.instrument_var, value="Other") self.settings_menu.add_cascade(label="Instrument", menu=self.instrument_menu) self.settings_menu.add_command(label="Processing Settings", command=lambda: self.tab_control.select(self.settings_tab)) self.menubar.add_cascade(label="SPRIT", menu=self.sprit_menu) self.menubar.add_cascade(label="Settings", menu=self.settings_menu) def create_tabs(self): self.style = ttk.Style(self.master) self.tab_control = ttk.Notebook(self.master) # INPUT TAB self.input_tab = ttk.Frame(self.tab_control) # Configure the row and column of the input_tab to have a non-zero weight hvsrFrame = ttk.LabelFrame(self.input_tab, text="Input Parameters") #hvsrFrame.rowconfigure(0, weight=1) hvsrFrame.columnconfigure(1, weight=1) # Logo and Site Name # Replace "logo.png" with the path to your logo image #self.logo = tk.PhotoImage(file="logo.png") #self.logo_label = ttk.Label(hvsrFrame, image=self.logo) #self.logo_label.grid(row=0, column=0) self.processingData = False def update_input_labels(hvsr_data): #Update labels for data preview tab self.input_data_label.configure(text=self.data_filepath_entry.get() + '\n' + str(hvsr_data['stream'])) self.obspySreamLabel_settings.configure(text=str(hvsr_data['stream'])) self.sensitivityLabelZ_settings.configure(text=hvsr_data['paz']['Z']['sensitivity']) self.gainLabelZ_settings.configure(text=hvsr_data['paz']['Z']['gain']) self.polesLabelZ_settings.configure(text=hvsr_data['paz']['Z']['poles']) self.zerosLabelZ_settings.configure(text=hvsr_data['paz']['Z']['zeros']) self.sensitivityLabelN_settings.configure(text=hvsr_data['paz']['N']['sensitivity']) self.gainLabelN_settings.configure(text=hvsr_data['paz']['N']['gain']) self.polesLabelN_settings.configure(text=hvsr_data['paz']['N']['poles']) self.zerosLabelN_settings.configure(text=hvsr_data['paz']['N']['zeros']) self.sensitivityLabelE_settings.configure(text=hvsr_data['paz']['E']['sensitivity']) self.gainLabelE_settings.configure(text=hvsr_data['paz']['E']['gain']) self.polesLabelE_settings.configure(text=hvsr_data['paz']['E']['poles']) self.zerosLabelE_settings.configure(text=hvsr_data['paz']['E']['zeros']) return self.data_read = False #Initialize #FUNCTION TO READ DATA @catch_errors def read_data(): update_progress_bars(prog_percent=0) #messagebox.showinfo(title="Reading Data", message='Reading Data...') self.log_text.insert('end', f'\n\nReading data [{datetime.datetime.now()}]\n\n') self.starttime, self.endtime = get_times() self.log_text.insert('end', f"{self.input_params_call['text']}\n\n") self.log_text.insert('end', f"{self.fetch_data_call['text']}\n\n") if self.file_source.get() == 'batch': batchType = self.batch_type.get() if isinstance(self.fpath, str): self.fpath = self.fpath elif isinstance(self.fpath, tuple) and len(self.fpath)==1: self.fpath = self.fpath[0] elif len(self.fpath) > 1: self.fpath = list(self.fpath) else: self.fpath = self.fpath[0] update_progress_bars(prog_percent=1) self.params = sprit_hvsr.input_params(input_data=self.fpath, metapath = self.meta_path.get(), site=self.site_name.get(), network=self.network.get(), station=self.station.get(), loc=self.location.get(), channels=[self.z_channel.get(), self.n_channel.get(), self.e_channel.get()], acq_date = self.starttime.date(), starttime = self.starttime, endtime = self.endtime, tzone = 'UTC', #Will always be converted to UTC before we get to this point when using gui xcoord = self.x.get(), ycoord = self.y.get(), elevation = self.z.get(), input_crs= self.input_crs.get(), output_crs= self.output_crs.get(), elev_unit= self.elev_unit.get(), instrument = self.instrumentSel.get(), hvsr_band = [self.hvsrBand_min.get(), self.hvsrBand_max.get()] ) if self.trim_dir.get()=='': trimDir=None else: trimDir=self.trim_dir.get() update_progress_bars(prog_percent=2) self.hvsr_data = sprit_hvsr.fetch_data(params=self.params, source=self.file_source.get(), trim_dir=trimDir, export_format=self.export_format.get(), detrend=self.detrend.get(), detrend_order=self.detrend_order.get()) update_progress_bars(prog_percent=10) self.site_options = self.hvsr_data.sites self.log_text.insert('end', f"{self.site_options}\n\n") firstSite = self.hvsr_data[list(self.hvsr_data.keys())[0]] update_input_labels(firstSite) update_site_dropdown() #Plot data in data preview tab self.fig_pre, self.ax_pre = sprit_hvsr.plot_stream(stream=firstSite['stream'], params=firstSite, fig=self.fig_pre, axes=self.ax_pre, return_fig=True) #Plot data in noise preview tab self.fig_noise, self.ax_noise = sprit_hvsr._plot_specgram_stream(stream=firstSite['stream'], params=firstSite, fig=self.fig_noise, ax=self.ax_noise, fill_gaps=0, component='Z', stack_type='linear', detrend='mean', dbscale=True, return_fig=True, cmap_per=[0.1,0.9]) select_windows(event=None, initialize=True) plot_noise_windows(self.hvsr_data) else: if isinstance(self.fpath, str): pass elif len(self.fpath) > 1: self.fpath = list(self.fpath) else: self.fpath = self.fpath[0] update_progress_bars(prog_percent=1) self.params = sprit_hvsr.input_params( input_data=self.fpath, metapath = self.meta_path.get(), site=self.site_name.get(), network=self.network.get(), station=self.station.get(), loc=self.location.get(), channels=[self.z_channel.get(), self.n_channel.get(), self.e_channel.get()], acq_date = self.starttime.date(), starttime = self.starttime, endtime = self.endtime, tzone = 'UTC', #Will always be converted to UTC before we get to this point when using gui xcoord = self.x.get(), ycoord = self.y.get(), elevation = self.z.get(), input_crs= self.input_crs.get(), output_crs= self.output_crs.get(), elev_unit= self.elev_unit.get(), instrument = self.instrumentSel.get(), hvsr_band = [self.hvsrBand_min.get(), self.hvsrBand_max.get()] ) self.hvsr_data = self.params if self.trim_dir.get()=='': trimDir=None else: trimDir=self.trim_dir.get() update_progress_bars(prog_percent=2) try: self.hvsr_data = sprit_hvsr.fetch_data(params=self.params, source=self.file_source.get(), trim_dir=trimDir, export_format=self.export_format.get(), detrend=self.detrend.get(), detrend_order=self.detrend_order.get()) except: traceback.print_exc() update_progress_bars(prog_percent=10) update_input_labels(self.hvsr_data) # Plot data in data preview tab self.fig_pre = sprit_hvsr.plot_stream(stream=self.hvsr_data['stream'], params=self.hvsr_data, fig=self.fig_pre, axes=self.ax_pre, return_fig=True) # Plot data in noise preview tab self.fig_noise = sprit_hvsr._plot_specgram_stream(stream=self.hvsr_data['stream'], params=self.hvsr_data, fig=self.fig_noise, ax=self.ax_noise, fill_gaps=0, component='Z', stack_type='linear', detrend='mean', dbscale=True, return_fig=True, cmap_per=[0.1,0.9]) select_windows(event=None, initialize=True) plot_noise_windows(self.hvsr_data) self.data_read = True if not self.processingData: update_progress_bars(prog_percent=100) self.tab_control.select(self.preview_data_tab) return self.hvsr_data def report_results(hvsr_results, azimuth='HV'): self.curveTest1ResultText.configure(text=hvsr_results['BestPeak'][azimuth]['Report']['Lw'][:-1]) self.curveTest1Result.configure(text=hvsr_results['BestPeak'][azimuth]['Report']['Lw'][-1]) self.curveTest2ResultText.configure(text=hvsr_results['BestPeak'][azimuth]['Report']['Nc'][:-1]) self.curveTest2Result.configure(text=hvsr_results['BestPeak'][azimuth]['Report']['Nc'][-1]) self.curveTest3ResultText.configure(text=hvsr_results['BestPeak'][azimuth]['Report']['σ_A(f)'][:-1]) self.curveTest3Result.configure(text=hvsr_results['BestPeak'][azimuth]['Report']['σ_A(f)'][-1]) curvePass = (hvsr_results['BestPeak'][azimuth]['PassList']['WindowLengthFreq.'] + hvsr_results['BestPeak'][azimuth]['PassList']['SignificantCycles']+ hvsr_results['BestPeak'][azimuth]['PassList']['LowCurveStDevOverTime']) > 2 if curvePass: self.totalCurveResult.configure(text=sprit_utils.check_mark(), font=("TkDefaultFont", 16, "bold"), foreground='green') else: self.totalCurveResult.configure(text=sprit_utils.x_mark(), font=("TkDefaultFont", 16, "bold"), foreground='red') self.peakTest1ResultText.configure(text=hvsr_results['BestPeak'][azimuth]['Report']['A(f-)'][:-1]) self.peakTest1Result.configure(text=hvsr_results['BestPeak'][azimuth]['Report']['A(f-)'][-1]) self.peakTest2ResultText.configure(text=hvsr_results['BestPeak'][azimuth]['Report']['A(f+)'][:-1]) self.peakTest2Result.configure(text=hvsr_results['BestPeak'][azimuth]['Report']['A(f+)'][-1]) self.peakTest3ResultText.configure(text=hvsr_results['BestPeak'][azimuth]['Report']['A0'][:-1]) self.peakTest3Result.configure(text=hvsr_results['BestPeak'][azimuth]['Report']['A0'][-1]) self.peakTest4ResultText.configure(text=hvsr_results['BestPeak'][azimuth]['Report']['P-'][:5] + ' and ' +hvsr_results['BestPeak'][azimuth]['Report']['P+'][:-1]) if hvsr_results['BestPeak'][azimuth]['PassList']['FreqStability']: self.peakTest4Result.configure(text=sprit_utils.check_mark()) else: self.peakTest4Result.configure(text=sprit_utils.x_mark()) self.peakTest5ResultText.configure(text=hvsr_results['BestPeak'][azimuth]['Report']['Sf'][:-1]) self.peakTest5Result.configure(text=hvsr_results['BestPeak'][azimuth]['Report']['Sf'][-1]) self.peakTest6ResultText.configure(text=hvsr_results['BestPeak'][azimuth]['Report']['Sa'][:-1]) self.peakTest6Result.configure(text=hvsr_results['BestPeak'][azimuth]['Report']['Sa'][-1]) peakPass = (hvsr_results['BestPeak'][azimuth]['PassList']['PeakProminenceBelow'] + hvsr_results['BestPeak'][azimuth]['PassList']['PeakProminenceAbove']+ hvsr_results['BestPeak'][azimuth]['PassList']['PeakAmpClarity']+ hvsr_results['BestPeak'][azimuth]['PassList']['FreqStability']+ hvsr_results['BestPeak'][azimuth]['PassList']['PeakStability_FreqStD']+ hvsr_results['BestPeak'][azimuth]['PassList']['PeakStability_AmpStD']) >= 5 if peakPass: self.totalPeakResult.configure(text=sprit_utils.check_mark(), font=("TkDefaultFont", 16, "bold"), foreground='green') else: self.totalPeakResult.configure(text=sprit_utils.x_mark(), font=("TkDefaultFont", 16, "bold"), foreground='red') if curvePass and peakPass: self.totalResult.configure(text=f'Pass {sprit_utils.check_mark()}', font=("TkDefaultFont", 22, "bold"), foreground='green') else: self.totalResult.configure(text=f'Fail {sprit_utils.x_mark()}', font=("TkDefaultFont", 22, "bold"), foreground='red') sprit_hvsr.plot_hvsr(hvsr_results, plot_type=get_kindstr(), fig=self.fig_results, ax=self.ax_results, use_subplots=True, clear_fig=False) #FUNCTION TO PROCESS DATA @catch_errors def process_data(): update_progress_bars(prog_percent=0) #messagebox.showinfo("Processing Data", 'Processing Data...') self.processingData = True #Set to true while data processing algorithm is being run if not self.data_read: self.hvsr_data = read_data() update_progress_bars(prog_percent=12) self.log_text.insert('end', f"\n\nProcessing Data [{datetime.datetime.now()}]\n\n") self.log_text.insert('end', f"{self.generate_ppsd_call['text']}\n\n") self.hvsr_data = sprit_hvsr.remove_noise(hvsr_data=self.hvsr_data, remove_method='auto', sat_percent=0.995, noise_percent=0.8, sta=2, lta=30, stalta_thresh=[0.5, 5], warmup_time=0, cooldown_time=0, min_win_size=1, remove_raw_noise=False) update_progress_bars(prog_percent=12) self.hvsr_data = plot_noise_windows(self.hvsr_data) update_progress_bars(prog_percent=15) self.hvsr_data = sprit_hvsr.generate_ppsds(hvsr_data=self.hvsr_data, remove_outliers=self.remove_outliers.get(), outlier_std=self.outlier_std.get(), ppsd_length=self.ppsd_length.get(), overlap=self.overlap.get(), period_step_octaves=self.perStepOct.get(), skip_on_gaps=self.skip_on_gaps.get(), db_bins=self.db_bins, period_limits=self.period_limits, period_smoothing_width_octaves=self.perSmoothWidthOct.get(), special_handling=special_handling#, verbose=True ) update_progress_bars(prog_percent=50) self.hvsr_data = sprit_hvsr.remove_outlier_curves(hvsr_data=self.hvsr_data, rmse_thresh=98, use_percentile=True, use_hv_curve = False, show_plot = False) update_progress_bars(prog_percent=60) self.log_text.insert('end', f"{self.procHVSR_call['text']}\n\n") self.hvsr_results = sprit_hvsr.process_hvsr(hvsr_data=self.hvsr_data, method=self.method_ind, smooth=self.hvsmooth_param, freq_smooth=self.freq_smooth.get(), f_smooth_width=self.fSmoothWidth.get(), resample=self.hvresample_int, outlier_curve_rmse_percentile=True) update_progress_bars(prog_percent=90) self.log_text.insert('end', f"{self.checkPeaks_Call['text']}\n\n") self.hvsr_results = sprit_hvsr.check_peaks(hvsr_data=self.hvsr_results, hvsr_band = [self.hvsrBand_min.get(), self.hvsrBand_max.get()], peak_freq_range=[self.peakFreqRange_min.get(), self.peakFreqRange_max.get()]) update_progress_bars(prog_percent=95) self.log_text.insert('end', f"{self.checkPeaks_Call['text']}\n\n") if isinstance(self.hvsr_results, sprit_hvsr.HVSRData): report_results(self.hvsr_results) self.results_siteSelectFrame.grid_forget() elif isinstance(self.hvsr_results, sprit_hvsr.HVSRBatch): self.results_siteSelectFrame.grid(row=0, column=0, columnspan=10, sticky='ew') report_results(self.hvsr_results[self.hvsr_results.sites[0]]) else: warnings.warn(f'Data is of type {type(self.hvsr_results)}; should be HVSRData or HVSRBatch type.') #Log results self.log_text.insert('end', f"Processing completed at [{datetime.datetime.now()}]\n\n") self.hvsr_results = sprit_hvsr.get_report(self.hvsr_results, report_format='print', no_output=True) if isinstance(self.hvsr_results, sprit_hvsr.HVSRData): #format data to be same as HVSRBatch hvsrResults = {'sitename_placeholder':self.hvsr_results} else: hvsrResults = self.hvsr_results for sitename in hvsrResults.keys(): self.log_text.insert('end', f"{hvsrResults[sitename]['Print_Report']}\n\n") self.processingData = False self.tab_control.select(self.results_tab) update_progress_bars(prog_percent=100) global update_progress_bars def update_progress_bars(prog_percent, process_name='Processing'): progBarListList = [[self.inputProgBar,(0,0), True], [self.prevProgBar,(0,0), True], [self.noiseProgBar,(0,0), True], [self.settingsProgBar_ppsd, (0, 0), True], [self.settingsProgBar_hvsr, (0,0), True], [self.settingsProgBar_plot,(0,0), True], [self.logProgBar,(0,11), False], [self.resultsProgBar,(0,26), False]] def prog_bar_update(progBarListList, progPercent, processName): for bar in progBarListList: progBar = bar[0] barLoc = bar[1] progBar['value'] = progPercent if progPercent==0: progBar.master.columnconfigure(0, weight=1) progBar.grid(row=barLoc[0],column=barLoc[1], sticky='ew') elif progPercent==100: progBar.grid_forget() progBar.update() threading.Thread(target=prog_bar_update(progBarListList=progBarListList, progPercent=prog_percent, processName=process_name)).start() #self.update_idletasks() def update_input_params_call(): prevCall = self.input_params_call.cget('text') self.input_params_call.configure(text="input_params( input_data='{}', metapath={}, site='{}', instrument='{}',\n\tnetwork='{}', station='{}', loc='{}', channels=[{}, {}, {}], \n\tacq_date='{}', starttime='{}', endttime='{}', tzone='{}', \n\txcoord={}, ycoord={}, elevation={}, input_crs='{}', output_crs='{}', elev_unit='{}', \n\thvsr_band=[{}, {}], peak_freq_range=[{}, {}])".format( self.data_path.get(), self.meta_path.get(), self.site_name.get(), self.instrumentSel.get(), self.network.get(), self.station.get(), self.location.get(), self.z_channel.get(), self.e_channel.get(), self.n_channel.get(), self.acq_date, self.starttime.time(), self.endtime.time(), self.tz, self.x.get(), self.y.get(), self.z.get(), self.input_crs.get(), self.output_crs.get(), self.elev_unit.get(), self.hvsrBand_min.get(), self.hvsrBand_max.get(), self.peakFreqRange_min.get(), self.peakFreqRange_max.get())) newCall = self.input_params_call.cget('text') if prevCall==newCall: self.data_read=True else: self.data_read = False #Specify site name siteLabel = ttk.Label(hvsrFrame, text="Site Name") siteLabel.grid(row=0, column=0, sticky='e', padx=5) self.site_name = tk.StringVar() self.site_name.set('HVSR Site') self.site_name_entry = ttk.Entry(hvsrFrame, textvariable=self.site_name, validate='focusout', validatecommand=update_input_params_call) self.site_name_entry.grid(row=0, column=1, columnspan=1, sticky='ew', padx=5) def on_source_select(): self.data_read = False try: str(self.file_source.get()) sourceLabel.configure(text="source='{}'".format(self.file_source.get())) update_fetch_call() if self.file_source.get() == 'raw' or self.file_source.get() == 'dir': self.browse_data_filepath_button.configure(text='Browse Folder') self.batch_options_frame.grid_forget() elif self.file_source.get() == 'batch': self.batch_options_frame.grid(row=11, column=0, columnspan=7, sticky='ew') self.browse_data_filepath_button.configure(text='Browse File(s)') else: self.browse_data_filepath_button.configure(text='Browse File(s)') self.batch_options_frame.grid_forget() return True except ValueError: return False sourceLabel = ttk.Label(master=hvsrFrame, text="source='file'") ttk.Label(master=hvsrFrame, text='Data Source Type [str]').grid(row=0, column=3, sticky='e', padx=5) sourcFrame= ttk.Frame(hvsrFrame) sourcFrame.grid(row=0, column=4, sticky='w', columnspan=3) self.file_source = tk.StringVar() self.file_source.set('file') ttk.Radiobutton(master=sourcFrame, text='File', variable=self.file_source, value='file', command=on_source_select).grid(row=0, column=0, sticky='w', padx=(5, 10)) ttk.Radiobutton(master=sourcFrame, text='Raw', variable=self.file_source, value='raw', command=on_source_select).grid(row=0, column=1, sticky='w', padx=(5, 10)) ttk.Radiobutton(master=sourcFrame, text='Batch', variable=self.file_source, value='batch', command=on_source_select).grid(row=0, column=2, sticky='w', padx=(5, 10)) ttk.Radiobutton(master=sourcFrame, text='Directory', variable=self.file_source, value='dir', command=on_source_select).grid(row=0, column=3, sticky='w', padx=(5, 10)) #Instrument select ttk.Label(hvsrFrame, text="Instrument").grid(row=0, column=6, sticky='e', padx=5) inst_options = ["Raspberry Shake", "Tromino", "Other"] def on_option_select(self, inst): update_input_params_call() if inst == "Raspberry Shake": self.network_entry.configure(state='normal') self.station_entry.configure(state='normal') self.location_entry.configure(state='normal') self.z_channel_entry.delete(0, 'end') self.e_channel_entry.delete(0, 'end') self.n_channel_entry.delete(0, 'end') self.z_channel_entry.insert(0,"EHZ") self.e_channel_entry.insert(0,"EHE") self.n_channel_entry.insert(0,"EHN") self.network_entry.delete(0, 'end') self.network_entry.insert(0,"AM") self.station_entry.delete(0, 'end') self.station_entry.insert(0,"RAC84") self.location_entry.delete(0, 'end') self.location_entry.insert(0,"00") else: self.network_entry.configure(state='disabled') self.station_entry.configure(state='disabled') self.location_entry.configure(state='disabled') self.instrumentSel = tk.StringVar(value=inst_options[0]) self.instrument_dropdown = ttk.OptionMenu(hvsrFrame, self.instrumentSel, inst_options[0], *inst_options, command=on_option_select) self.instrument_dropdown.config(width=20) self.instrument_dropdown.grid(row=0, column=7, columnspan=1, sticky='ew') # Data Filepath dataLabel= ttk.Label(hvsrFrame, text="Data Filepath") dataLabel.grid(row=1, column=0, sticky='e', padx=5, pady=(5,2.55)) #Function to set self.data_read False whenever the data_path is updated def on_data_path_change(data_path, index, trace_mode): #If our data path changes, data is registered as not having been read #This is primarily so that if just the Run button is pushed, it will know to first read the data self.data_read = False def filepath_update(): self.data_read = False self.fpath = self.data_path.get() self.data_read = False update_input_params_call() self.data_path = tk.StringVar() self.data_path.set('sample') self.fpath = self.data_path.get() self.data_path.trace_add('write', on_data_path_change) self.data_filepath_entry = ttk.Entry(hvsrFrame, textvariable=self.data_path, validate='focusout', validatecommand=filepath_update) self.data_filepath_entry.grid(row=1, column=1, columnspan=6, sticky='ew', padx=5, pady=(5,2.55)) def browse_data_filepath(): if self.file_source.get() == 'raw' or self.file_source.get() == 'dir': self.fpath = filedialog.askdirectory() if self.fpath: self.data_filepath_entry.delete(0, 'end') self.data_filepath_entry.insert(0, self.fpath) else: self.fpath = filedialog.askopenfilenames() #fpath will always be tuple self.no_data_files = len(self.fpath) if self.fpath: self.data_filepath_entry.delete(0, 'end') for f in self.fpath: self.data_filepath_entry.insert('end', self.fpath) update_input_params_call() buttonFrame = ttk.Frame(hvsrFrame) buttonFrame.grid(row=1, column=7, sticky='ew') self.browse_data_filepath_button = ttk.Button(buttonFrame, text="Browse File(s)", command=browse_data_filepath) #self.browse_data_filepath_button.grid(row=1, column=6, sticky='ew') self.browse_data_filepath_button.pack(side="left", fill="x", expand=True, padx=(0,2), pady=(5,2.55)) # Metadata Filepath ttk.Label(hvsrFrame, text="Metadata Filepath").grid(row=2, column=0, sticky='e', padx=5, pady=(2.5,5)) self.meta_path = tk.StringVar() self.meta_path.set('') self.metadata_filepath_entry = ttk.Entry(hvsrFrame, textvariable=self.meta_path, validate='focusout', validatecommand=update_input_params_call) self.metadata_filepath_entry.grid(row=2, column=1, columnspan=6, sticky='ew', padx=5, pady=(2.5,5)) def browse_metadata_filepath(): self.data_read = False #New file will not have been read, set to False filepath = filedialog.askopenfilename() if filepath: self.metadata_filepath_entry.delete(0, 'end') self.metadata_filepath_entry.insert(0, filepath) update_input_params_call() self.browse_metadata_filepath_button = ttk.Button(hvsrFrame, text="Browse", command=browse_metadata_filepath) self.browse_metadata_filepath_button.grid(row=2, column=7, sticky='ew', padx=0, pady=(2.5,5)) def update_acq_date(): aMonth = self.acq_month.get() if str(aMonth)[0]=='0': aMonth = str(aMonth)[-1] aDay = self.acq_day.get() if str(aDay)[0]=='0': aDay = str(aDay)[-1] self.acq_date = datetime.date(year=self.acq_year.get(), month=aMonth, day=aDay) self.day_of_year = self.acq_date.timetuple().tm_yday self.doy_label.configure(text=str(self.day_of_year)) update_input_params_call() # Date and Time dateFrame = ttk.Frame(hvsrFrame) dateFrame.grid(row=3, column=1, columnspan=2, sticky='e', padx=5) ttk.Label(dateFrame, text="Date").grid(row=1, column=1, sticky='e', padx=5) self.acq_year = tk.IntVar() self.acq_year.set(int(datetime.datetime.today().year)) self.acq_year_entry = ttk.Spinbox(dateFrame, from_=0, to=10000, width=7, textvariable=self.acq_year, validate='focusout', validatecommand=update_acq_date) self.acq_year_entry.grid(row=1, column=2, sticky='ew', padx=1) self.acq_month = tk.IntVar() self.acq_month.set(int(datetime.datetime.today().month)) self.acq_month_entry = ttk.Spinbox(dateFrame, from_=0, to=12, width=3, textvariable=self.acq_month, validate='focusout', validatecommand=update_acq_date) self.acq_month_entry.grid(row=1, column=3, sticky='ew', padx=1) self.acq_day = tk.IntVar() self.acq_day.set(int(datetime.datetime.today().day)) self.acq_day_entry = ttk.Spinbox(dateFrame, from_=0, to=31, width=3, textvariable=self.acq_day, validate='focusout', validatecommand=update_acq_date) self.acq_day_entry.grid(row=1, column=4, sticky='ew', padx=1) self.acq_date = datetime.date.today() sTimeFrame = ttk.Frame(hvsrFrame) sTimeFrame.grid(row=3, column=4, sticky='ew') def get_times(): #Format starttime as datetime object (in timezone as originally entered) self.acq_date = datetime.date(year=self.acq_year.get(), month=self.acq_month.get(), day=self.acq_day.get()) sHour = self.start_hour.get() if str(sHour)[0] == '0': sHour = int(str(sHour)[-1]) sMin = self.start_minute.get() if str(sMin)[0] == '0': sMin = int(str(sMin)[-1]) self.starttime = datetime.datetime(year = int(self.acq_date.year), month = int(self.acq_date.month), day = int(self.acq_date.day), hour = int(sHour), minute = int(sMin), tzinfo=self.tz) #Get duration, as originally entered hour_dur = self.end_hour.get() - self.start_hour.get() if hour_dur < 0: hour_dur = self.end_hour.get() + 24 - self.start_hour.get() min_dur = self.end_minute.get() - self.start_minute.get() #Convert starttime to utc #self.starttime = self.tz.normalize(self.tz.localize(self.starttime)).astimezone(pytz.utc) self.starttime = self.starttime.astimezone(datetime.timezone.utc) #Get endttime based on utc starttime and original duration self.endtime = self.starttime + datetime.timedelta(hours=hour_dur, minutes=min_dur) return self.starttime, self.endtime self.tz = datetime.timezone.utc def any_time_change(): self.data_read = False #New file will not have been read, set to False self.acq_date = datetime.date(year=self.acq_year.get(), month=self.acq_month.get(), day=self.acq_day.get()) self.starttime, self.endtime = get_times() update_input_params_call() ttk.Label(hvsrFrame, text="Start Time").grid(row=3, column=3, sticky='e', padx=5) colonLabel= ttk.Label(sTimeFrame, text=":")#.grid(row=3, column=4, padx=(20,0), sticky='w') self.start_hour = tk.IntVar() self.start_hour.set(00) self.start_time_hour_entry = ttk.Spinbox(sTimeFrame, from_=0, to=23, width=5, textvariable=self.start_hour, validate='focusout', validatecommand=any_time_change) self.start_time_hour_entry#.grid(row=3, column=4, sticky='w') self.start_minute = tk.DoubleVar() self.start_minute.set(00) self.start_time_min_entry = ttk.Spinbox(sTimeFrame, from_=0, to=59, width=5, textvariable=self.start_minute, validate='focusout', validatecommand=any_time_change) self.start_time_min_entry#.grid(row=3, column=4, padx=80, sticky='w') #sTLabel.pack(side="left", fill="x", expand=True) self.start_time_hour_entry.pack(side='left', expand=True) colonLabel.pack(side="left", fill="x") self.start_time_min_entry.pack(side='right', expand=True) eTimeFrame = ttk.Frame(hvsrFrame) eTimeFrame.grid(row=3, column=6, sticky='ew') ttk.Label(hvsrFrame, text="End Time").grid(row=3, column=5, sticky='e', padx=5) colonLabel = ttk.Label(eTimeFrame, text=":")#.grid(row=3, column=6, padx=(20,0), sticky='w') self.end_hour = tk.IntVar() self.end_hour.set(23) self.end_time_hour_entry = ttk.Spinbox(eTimeFrame, from_=0, to=23, width=5, textvariable=self.end_hour, validate='focusout', validatecommand=any_time_change) self.end_time_hour_entry#.grid(row=3, column=+, sticky='w') self.end_minute = tk.DoubleVar() self.end_minute.set(59) self.end_time_min_entry = ttk.Spinbox(eTimeFrame, from_=0, to=59, width=5, textvariable=self.end_minute, validate='focusout', validatecommand=any_time_change) self.end_time_min_entry#.grid(row=3, column=+, padx=80, sticky='w') #eTLabel.pack(side="left", fill="x", expand=True) self.end_time_hour_entry.pack(side='left', expand=True) colonLabel.pack(side="left", fill="x") self.end_time_min_entry.pack(side='right', expand=True) self.acq_date = datetime.date(year=self.acq_year.get(), month=self.acq_month.get(), day=self.acq_day.get()) self.starttime, self.endtime = get_times() def onTimezoneSelect(event): #Listbox "loses" selection and triggers an event sometimes, so need to check if that is just what happened if self.timezone_listbox.curselection(): #If it was an actual selection, update timezone self.tz = zoneinfo.ZoneInfo(self.timezone_listbox.get(self.timezone_listbox.curselection())) else: #If it was just the listbox losing the selection, don't change anything pass update_input_params_call() self.timezone_listbox = tk.Listbox(hvsrFrame, selectmode='browse', height=25) self.timezone_listbox.insert('end', 'UTC') self.timezone_listbox.insert('end', 'US/Central') for tz in zoneinfo.available_timezones():# pytz.all_timezones: if tz !='UTC': self.timezone_listbox.insert('end', tz) self.timezone_listbox.selection_set(0) self.timezone_listbox.bind('<<ListboxSelect>>', onTimezoneSelect) ttk.Label(hvsrFrame,text="Timezone").grid(row=3,column=7, sticky='w', padx=5) self.timezone_listbox.grid(row=4,column=7, rowspan=26, sticky='nsew', padx=5) # DOY self.day_of_year = self.acq_date.timetuple().tm_yday ttk.Label(hvsrFrame,text="Day of Year:").grid(row=4, column=1, sticky='e', padx=5, pady=10) self.doy_label = ttk.Label(hvsrFrame, text=str(self.day_of_year)) self.doy_label.grid(row=4, column=2, sticky='w') # UTC Time Output ttk.Label(hvsrFrame,text="UTC Time:").grid(row=4, column=3, sticky='e', padx=5, pady=10) self.utc_time_output_label = ttk.Label(hvsrFrame, text="") self.utc_time_output_label.grid(row=4, column=4) # Initialize as UTC self.tz = datetime.timezone.utc self.starttime, self.endtime = get_times() # X Y Z CRS Depth ttk.Label(hvsrFrame,text="X").grid(row=5,column=1, sticky='e', padx=5, pady=10) self.x = tk.DoubleVar() self.x.set(0) self.x_entry = ttk.Entry(hvsrFrame, textvariable=self.x, validate='focusout', validatecommand=update_input_params_call) self.x_entry.grid(row=5,column=2, sticky='w', padx=0) ttk.Label(hvsrFrame,text="Y").grid(row=5,column=3, sticky='e', padx=5, pady=10) self.y = tk.DoubleVar() self.y.set(0) self.y_entry = ttk.Entry(hvsrFrame, textvariable=self.y, validate='focusout', validatecommand=update_input_params_call) self.y_entry.grid(row=5, column=4, sticky='w', padx=0) ttk.Label(hvsrFrame,text="Z").grid(row=5,column=5, sticky='e', padx=5, pady=10) self.z = tk.DoubleVar() self.z.set(0) self.z_entry = ttk.Entry(hvsrFrame, textvariable=self.z, validate='focusout', validatecommand=update_input_params_call) self.z_entry.grid(row=5,column=6, sticky='w', padx=0) ttk.Label(hvsrFrame,text="Input CRS").grid(row=6,column=1, sticky='e', padx=5, pady=10) self.input_crs = tk.StringVar() self.input_crs.set('EPSG:4326') self.input_crs_entry = ttk.Entry(hvsrFrame, textvariable=self.input_crs, validate='focusout', validatecommand=update_input_params_call) self.input_crs_entry.grid(row=6,column=2, sticky='w', padx=0) ttk.Label(hvsrFrame,text="Output CRS").grid(row=6,column=3, sticky='e', padx=5, pady=10) self.output_crs = tk.StringVar() self.output_crs.set('EPSG:4326') self.output_crs_entry = ttk.Entry(hvsrFrame, textvariable=self.output_crs, validate='focusout', validatecommand=update_input_params_call) self.output_crs_entry.grid(row=6, column=4, sticky='w', padx=0) ttk.Label(master=hvsrFrame, text='Elevation Unit').grid(row=6, column=5, sticky='e', padx=5, pady=10) elevUnitFrame= ttk.Frame(hvsrFrame) elevUnitFrame.grid(row=6, column=6, sticky='w', columnspan=3) self.elev_unit = tk.StringVar() self.elev_unit.set('meters') ttk.Radiobutton(master=elevUnitFrame, text='Meters', variable=self.elev_unit, value='meters', command=update_input_params_call).grid(row=0, column=0, sticky='w', padx=(5, 10)) ttk.Radiobutton(master=elevUnitFrame, text='Feet', variable=self.elev_unit, value='feet', command=update_input_params_call).grid(row=0, column=1, sticky='w', padx=(5, 10)) # Network Station Location ttk.Label(hvsrFrame,text="Network").grid(row=7,column=1, sticky='e', padx=5, pady=10) self.network = tk.StringVar() self.network.set('AM') self.network_entry = ttk.Entry(hvsrFrame, textvariable=self.network, validate='focusout', validatecommand=update_input_params_call) self.network_entry.grid(row=7,column=2, sticky='w', padx=0) ttk.Label(hvsrFrame,text="Station").grid(row=7,column=3, sticky='e', padx=5, pady=10) self.station = tk.StringVar() self.station.set('RAC84') self.station_entry = ttk.Entry(hvsrFrame, textvariable=self.station, validate='focusout', validatecommand=update_input_params_call) self.station_entry.grid(row=7,column=4, sticky='w', padx=0) ttk.Label(hvsrFrame,text="Location").grid(row=7,column=5, sticky='e', padx=5, pady=10) self.location = tk.StringVar() self.location.set('00') self.location_entry = ttk.Entry(hvsrFrame, textvariable=self.location, validate='focusout', validatecommand=update_input_params_call) self.location_entry.grid(row=7,column=6, sticky='w', padx=0) # Z N E Channels ttk.Label(hvsrFrame,text="Z Channel").grid(row=8,column=1, sticky='e', padx=5, pady=10) self.z_channel = tk.StringVar() self.z_channel.set('EHZ') self.z_channel_entry = ttk.Entry(hvsrFrame, textvariable=self.z_channel, validate='focusout', validatecommand=update_input_params_call) self.z_channel_entry.grid(row=8,column=2, sticky='w', padx=0) ttk.Label(hvsrFrame,text="N Channel").grid(row=8,column=3, sticky='e', padx=5, pady=10) self.n_channel = tk.StringVar() self.n_channel.set('EHN') self.n_channel_entry = ttk.Entry(hvsrFrame, textvariable=self.n_channel, validate='focusout', validatecommand=update_input_params_call) self.n_channel_entry.grid(row=8,column=4, sticky='w', padx=0) ttk.Label(hvsrFrame,text="E Channel").grid(row=8,column=5, sticky='e', padx=5, pady=10) self.e_channel = tk.StringVar() self.e_channel.set('EHE') self.e_channel_entry = ttk.Entry(hvsrFrame, textvariable=self.e_channel, validate='focusout', validatecommand=update_input_params_call) self.e_channel_entry.grid(row=8,column=6, sticky='w', padx=0) # HVSR Band def on_hvsrband_update(): try: float(self.hvsrBand_min.get()) float(self.hvsrBand_max.get()) hvsrBandLabel.configure(text='hvsr_band=[{}, {}]'.format(self.hvsrBand_min.get(), self.hvsrBand_max.get())) update_check_peaks_call(self.checkPeaks_Call) update_input_params_call() return True except ValueError: return False ttk.Label(hvsrFrame,text="HVSR Band").grid(row=9,column=1, sticky='e', padx=10, pady=10) hvsrbandframe= ttk.Frame(hvsrFrame) hvsrbandframe.grid(row=9, column=2,sticky='w') self.hvsrBand_min = tk.DoubleVar() self.hvsrBand_min.set(0.4) hvsr_band_min_entry = ttk.Entry(hvsrbandframe, width=9, textvariable=self.hvsrBand_min, validate='focusout', validatecommand=on_hvsrband_update) hvsr_band_min_entry.grid(row=0, column=0, sticky='ew', padx=(0,2)) self.hvsrBand_max = tk.DoubleVar() self.hvsrBand_max.set(40) hvsr_band_max_entry = ttk.Entry(hvsrbandframe, width=9,textvariable=self.hvsrBand_max, validate='focusout', validatecommand=on_hvsrband_update) hvsr_band_max_entry.grid(row=0,column=1, sticky='ew', padx=(2,0)) # Peak Freq Range Band def on_peakFreqRange_update(): try: float(self.peakFreqRange_min.get()) float(self.peakFreqRange_max.get()) peakFreqRangeLabel.configure(text='peak_freq_range=[{}, {}]'.format(self.peakFreqRange_min.get(), self.peakFreqRange_max.get())) update_check_peaks_call(self.checkPeaks_Call) update_input_params_call() return True except ValueError: return False ttk.Label(hvsrFrame,text="Peak Freq. Range").grid(row=9,column=3, sticky='e', padx=10, pady=10) peakFreqRangeframe= ttk.Frame(hvsrFrame) peakFreqRangeframe.grid(row=9, column=4,sticky='w') self.peakFreqRange_min = tk.DoubleVar() self.peakFreqRange_min.set(0.4) peakFreqRange_min_entry = ttk.Entry(peakFreqRangeframe, width=9, textvariable=self.peakFreqRange_min, validate='focusout', validatecommand=on_peakFreqRange_update) peakFreqRange_min_entry.grid(row=0, column=0, sticky='ew', padx=(0,2)) self.peakFreqRange_max = tk.DoubleVar() self.peakFreqRange_max.set(40) peakFreqRange_max_entry = ttk.Entry(peakFreqRangeframe, width=9,textvariable=self.peakFreqRange_max, validate='focusout', validatecommand=on_peakFreqRange_update) peakFreqRange_max_entry.grid(row=0,column=1, sticky='ew', padx=(2,0)) #BATCH Section def update_batch_data_read_call(): self.batch_read_data_call.configure(text="batch_data_read(input_data, batch_type='{}', param_col={}, batch_params={})".format( self.batch_type.get(), self.param_col.get(), self.batch_params.get())) return def on_batch_type_select(): update_batch_data_read_call() return self.batch_options_frame = ttk.LabelFrame(hvsrFrame, text='Batch Options') ttk.Label(self.batch_options_frame, text="Batch Type").grid(row=0,column=0, sticky='e', padx=10, pady=10) batchTypeFrame= ttk.Frame(self.batch_options_frame) batchTypeFrame.grid(row=0, column=1, sticky='w', columnspan=3) self.batch_type = tk.StringVar() self.batch_type.set('table') ttk.Radiobutton(master=batchTypeFrame, text='Table', variable=self.batch_type, value='table', command=on_batch_type_select).grid(row=0, column=0, sticky='w', padx=(5, 10)) ttk.Radiobutton(master=batchTypeFrame, text='File list', variable=self.batch_type, value='filelist', command=on_batch_type_select).grid(row=0, column=1, sticky='w', padx=(5, 10)) ttk.Label(self.batch_options_frame,text="Parameter column name").grid(row=0,column=4, sticky='e', padx=5) self.param_col = tk.StringVar() self.param_col.set(None) self.param_col_entry = ttk.Entry(self.batch_options_frame, textvariable=self.param_col, validate='focusout', validatecommand=update_batch_data_read_call) self.param_col_entry.grid(row=0, column=5, sticky='w', padx=0) ttk.Label(self.batch_options_frame,text="For batch_type='table' with single parameter column only").grid(row=1,column=4, columnspan=2, sticky='w', padx=5) ttk.Label(self.batch_options_frame,text="Batch parameters").grid(row=0,column=6, sticky='e', padx=5) self.batch_params = tk.StringVar() self.batch_params.set(None) self.batch_params_entry = ttk.Entry(self.batch_options_frame, textvariable=self.batch_params, validate='focusout', validatecommand=update_batch_data_read_call, width=75) self.batch_params_entry.grid(row=0, column=7, columnspan=3, sticky='ew', padx=0) ttk.Label(self.batch_options_frame,text="To specify parameters used for reading in data").grid(row=1,column=6, columnspan=2, sticky='w', padx=5) self.batch_read_data_call = ttk.Label(self.batch_options_frame, text="batch_data_read(input_data, batch_type={}, param_col={}, batch_params={})".format( self.batch_type.get(), self.param_col.get(), self.batch_params.get() )) self.batch_read_data_call.grid(row=2,column=0, columnspan=10, sticky='w', padx=10, pady=10) self.batch_options_frame.grid(row=11, column=0, columnspan=7, sticky='ew') self.batch_options_frame.grid_forget() separator = ttk.Separator(hvsrFrame, orient='horizontal') separator.grid(row=12, column=0, columnspan=7, sticky='ew', padx=10) def update_fetch_call(): prevCall = self.input_params_call.cget('text') if self.trim_dir.get()=='': trim_dir = None else: trim_dir = self.trim_dir.get() self.data_read = False #New file will not have been read, set to False self.fetch_data_call.configure(text="fetch_data(params, source='{}', trim_dir={}, export_format='{}', detrend='{}', detrend_order={})" .format(self.file_source.get(), trim_dir, self.export_format.get(), self.detrend.get(), self.detrend_order.get())) newCall = self.input_params_call.cget('text') if prevCall==newCall: self.data_read=True else: self.data_read = False #export_format='.mseed' def on_obspyFormatSelect(self): update_fetch_call() ttk.Label(hvsrFrame, text="Data Format").grid(row=13, column=1, sticky='e', padx=5) obspyformats = ['AH', 'ALSEP_PSE', 'ALSEP_WTH', 'ALSEP_WTN', 'CSS', 'DMX', 'GCF', 'GSE1', 'GSE2', 'KINEMETRICS_EVT', 'KNET', 'MSEED', 'NNSA_KB_CORE', 'PDAS', 'PICKLE', 'Q', 'REFTEK130', 'RG16', 'SAC', 'SACXY', 'SEG2', 'SEGY', 'SEISAN', 'SH_ASC', 'SLIST', 'SU', 'TSPAIR', 'WAV', 'WIN', 'Y'] self.export_format = tk.StringVar(value=obspyformats[11]) self.data_format_dropdown = ttk.OptionMenu(hvsrFrame, self.export_format, obspyformats[11], *obspyformats, command=on_obspyFormatSelect) self.data_format_dropdown.grid(row=13, column=2, columnspan=3, sticky='ew') #detrend='spline' def on_detrend_select(): try: str(self.detrend.get()) update_fetch_call() return True except ValueError: return False sourceLabel = ttk.Label(master=hvsrFrame, text="source='raw'") ttk.Label(master=hvsrFrame, text='Detrend type [str]').grid(row=14, column=1, sticky='e', padx=5) detrendFrame= ttk.Frame(hvsrFrame) detrendFrame.grid(row=14, column=2, sticky='w', columnspan=3) self.detrend = tk.StringVar() self.detrend.set('spline') ttk.Radiobutton(master=detrendFrame, text='Spline', variable=self.detrend, value='spline', command=on_detrend_select).grid(row=0, column=0, sticky='w', padx=(5, 10)) ttk.Radiobutton(master=detrendFrame, text='Polynomial', variable=self.detrend, value='polynomial', command=on_detrend_select).grid(row=0, column=1, sticky='w', padx=(5, 10)) ttk.Radiobutton(master=detrendFrame, text='None', variable=self.detrend, value='none', command=on_detrend_select).grid(row=0, column=2, sticky='w', padx=(5, 10)) #detrend_order=2 def on_detrend_order(): try: int(self.detrend_order.get()) update_fetch_call() return True except ValueError: return False ttk.Label(hvsrFrame,text="Detrend Order [int]").grid(row=14,column=5, sticky='e', padx=5, pady=10) self.detrend_order = tk.IntVar() self.detrend_order.set(2) self.detrend_order_entry = ttk.Entry(hvsrFrame, textvariable=self.detrend_order, validate='focusout', validatecommand=on_detrend_order) self.detrend_order_entry.grid(row=14,column=6, sticky='w', padx=0) #trim_dir=False def on_trim_dir(): try: str(self.trim_dir.get()) update_fetch_call() return True except ValueError: return False ttk.Label(hvsrFrame, text="Output Directory (trimmed data)").grid(row=15, column=0, sticky='e', padx=5, pady=(2.5,5)) self.trim_dir = tk.StringVar() self.trim_dir_entry = ttk.Entry(hvsrFrame, textvariable=self.trim_dir, validate='focusout', validatecommand=on_trim_dir) self.trim_dir_entry.grid(row=15, column=1, columnspan=5, sticky='ew', padx=5, pady=(2.5,5)) def browse_trim_dir_filepath(): filepath = filedialog.askdirectory() if filepath: self.trim_dir_entry.delete(0, 'end') self.trim_dir_entry.insert(0, filepath) self.trim_dir_filepath_button = ttk.Button(hvsrFrame, text="Browse", command=browse_trim_dir_filepath) self.trim_dir_filepath_button.grid(row=15, column=6, sticky='ew', padx=0, pady=(2.5,5)) #self.starttime, self.endtime = get_times() input_params_LF = ttk.LabelFrame(master=self.input_tab, text='input_params() call') self.input_params_call = ttk.Label(master=input_params_LF, text="input_params( input_data='{}', metapath={}, site='{}', instrument='{}',\n\tnetwork='{}', station='{}', loc='{}', channels=[{}, {}, {}], \n\tacq_date='{}', starttime='{}', endttime='{}', tzone='{}', \n\txcoord={}, ycoord={}, elevation={}, input_crs='{}', output_crs='{}', elev_unit='{}', \n\thvsr_band=[{}, {}], peak_freq_range=[{}, {}])".format( self.data_path.get(), self.meta_path.get(), self.site_name.get(), self.instrumentSel.get(), self.network.get(), self.station.get(), self.location.get(), self.z_channel.get(), self.e_channel.get(), self.n_channel.get(), self.acq_date, self.starttime.time(), self.endtime.time(), self.tz, self.x.get(), self.y.get(), self.z.get(), self.input_crs.get(), self.output_crs.get(), self.elev_unit.get(), self.hvsrBand_min.get(), self.hvsrBand_max.get(), self.peakFreqRange_min.get(), self.peakFreqRange_max.get())) self.input_params_call.pack(anchor='w', expand=True, padx=20) #fetch_data() call fetch_data_LF = ttk.LabelFrame(master=self.input_tab, text='fetch_data() call') self.fetch_data_call = ttk.Label(master=fetch_data_LF, text="fetch_data(params, source={}, trim_dir={}, export_format={}, detrend={}, detrend_order={})" .format(self.file_source.get(), None, self.export_format.get(), self.detrend.get(), self.detrend_order.get())) self.fetch_data_call.pack(anchor='w', expand=True, padx=20) #Set up frame for reading and running runFrame_hvsr = ttk.Frame(self.input_tab) runFrame_hvsr.columnconfigure(0, weight=1) self.inputProgBar = ttk.Progressbar(runFrame_hvsr, orient='horizontal') self.inputProgBar.grid(row=0, column=0, sticky='ew')#.pack(fill='both',expand=True, side='left', anchor='sw') self.style.configure(style='Custom.TButton', background='#d49949') self.read_button = ttk.Button(runFrame_hvsr, text="Read Data", command=read_data, width=30, style='Custom.TButton') self.style.configure('Run.TButton', background='#8b9685', width=10, height=3) self.run_button = ttk.Button(runFrame_hvsr, text="Run", style='Run.TButton', command=process_data) self.run_button.grid(row=0, column=2, sticky='nsew', padx=2.5)#.pack(side='right', anchor='se', padx=(10,0)) self.read_button.grid(row=0, column=1, sticky='nsew', padx=2.5)#.pack(side='right', anchor='se') hvsrFrame.pack(fill='both', expand=True, side='top')#.grid(row=0, sticky="nsew") runFrame_hvsr.pack(fill='both', side='bottom') fetch_data_LF.pack(fill='x', side='bottom') input_params_LF.pack(fill='x', side='bottom') self.input_tab.pack(fill='both', expand=True) self.tab_control.add(self.input_tab, text="Input") #Data Preview Tab self.preview_data_tab = ttk.Frame(self.tab_control) # Configure the row and column of the input_tab to have a non-zero weight self.preview_data_tab.pack(expand=1) self.inputdataFrame = ttk.LabelFrame(self.preview_data_tab, text="Input Data Viewer") self.inputdataFrame.pack(expand=True, fill='both') self.inputInfoFrame = ttk.LabelFrame(self.inputdataFrame, text="Input Data Info") self.input_data_label = ttk.Label(self.inputInfoFrame, text=self.data_filepath_entry.get()) self.input_data_label.pack(anchor='w', fill='both', expand=True, padx=15) self.inputInfoFrame.pack(expand=True, fill='both', side='top') self.inputDataViewFrame = ttk.LabelFrame(self.inputdataFrame, text="Input Data Plot") ttk.Label(master=self.inputInfoFrame, text=self.data_filepath_entry.get()).pack()#.grid(row=0, column=0) #Set up plot #Reset axes, figure, and canvas widget self.fig_pre = plt.figure() prev_mosaic = [['Z'],['N'],['E']] self.ax_pre = self.fig_pre.subplot_mosaic(prev_mosaic, sharex=True) self.canvas_pre = FigureCanvasTkAgg(self.fig_pre, master=self.inputDataViewFrame) # A tk.DrawingArea. self.canvas_pre.draw() self.canvasPreWidget = self.canvas_pre.get_tk_widget()#.pack(side=tk.TOP, fill=tk.BOTH, expand=1) self.preview_toolbar = NavigationToolbar2Tk(self.canvas_pre, self.inputDataViewFrame, pack_toolbar=False) self.preview_toolbar.update() #self.canvas_pre.mpl_connect("button_release_event", select_windows) #Save preview figure savePrevFigFrame = ttk.Frame(master=self.inputDataViewFrame) ttk.Label(savePrevFigFrame, text="Export Figure").grid(row=0, column=0, sticky='ew', padx=5) self.previewFig_dir = tk.StringVar() self.previewFig_dir_entry = ttk.Entry(savePrevFigFrame, textvariable=self.previewFig_dir) self.previewFig_dir_entry.grid(row=0, column=1, columnspan=5, sticky='ew') def filepath_preview_fig(): filepath = filedialog.asksaveasfilename(defaultextension='.png', initialdir=pathlib.Path(self.data_path.get()).parent) if filepath: self.previewFig_dir_entry.delete(0, 'end') self.previewFig_dir_entry.insert(0, filepath) def save_preview_fig(): self.fig_pre.savefig(self.previewFig_dir.get()) self.browsePreviewFig = ttk.Button(savePrevFigFrame, text="Browse",command=filepath_preview_fig) self.browsePreviewFig.grid(row=0, column=7, sticky='ew', padx=2.5) self.savePreviewFig = ttk.Button(savePrevFigFrame, text="Save",command=save_preview_fig) self.savePreviewFig.grid(row=0, column=8, columnspan=2, sticky='ew', padx=2.5) savePrevFigFrame.columnconfigure(1, weight=1) savePrevFigFrame.pack(side='bottom', fill='both', expand=False) self.preview_toolbar.pack(side=tk.BOTTOM, fill=tk.X) self.canvasPreWidget.pack(fill='both', expand=True)#.grid(row=0, column=0, sticky='nsew') self.inputDataViewFrame.pack(expand=True, fill='both', side='bottom') #preview-Run button runFrame_dataPrev = ttk.Frame(self.preview_data_tab) runFrame_dataPrev.columnconfigure(0, weight=1) self.prevProgBar = ttk.Progressbar(runFrame_dataPrev, orient='horizontal') self.prevProgBar.grid(row=0, column=0, sticky='ew')#.pack(fill='both',expand=True, side='left', anchor='sw') self.run_button = ttk.Button(runFrame_dataPrev, text="Run", style='Run.TButton', command=process_data) self.run_button.grid(row=0, column=1, sticky='nsew', padx=2.5)#.pack(side='bottom', anchor='e')#.grid(row=2, column=9, columnspan=20, sticky='e') runFrame_dataPrev.pack(side='bottom', anchor='e', fill='both')#grid(row=1, sticky='e') self.tab_control.add(self.preview_data_tab, text="Data Preview") # NOISE TAB self.noise_tab = ttk.Frame(self.tab_control) self.canvasFrame_noise = ttk.LabelFrame(self.noise_tab, text='Noise Viewer') #Helper function for updating the canvas and drawing/deleted the boxes def __draw_windows(event, pathlist, ax_key, windowDrawn, winArtist, xWindows, fig, ax): """Helper function for updating the canvas and drawing/deleted the boxes""" for i, pa in enumerate(pathlist): for j, p in enumerate(pa): if windowDrawn[i][j]: pass else: patch = matplotlib.patches.PathPatch(p, facecolor='k', alpha=0.75) winArt = ax[ax_key].add_patch(patch) windowDrawn[i][j] = True winArtist[i][j] = winArt if event.button is MouseButton.RIGHT: fig.canvas.draw() #Helper function for manual window selection def __draw_boxes(event, clickNo, xWindows, pathList, windowDrawn, winArtist, lineArtist, x0, fig, ax): """Helper function for manual window selection to draw boxes to show where windows have been selected for removal""" #Create an axis dictionary if it does not already exist so all functions are the same if isinstance(ax, np.ndarray) or isinstance(ax, dict): ax = ax else: ax = {'a':ax} if len(ax) > 1: if type(ax) is not dict: axDict = {} for i, a in enumerate(ax): axDict[str(i)] = a ax = axDict #else: # ax = {'a':ax} #if event.inaxes!=ax: return #y0, y1 = ax.get_ylim() y0 = [] y1 = [] kList = [] for k in ax.keys(): kList.append(k) y0.append(ax[k].get_ylim()[0]) y1.append(ax[k].get_ylim()[1]) #else: # y0 = [ax.get_ylim()[0]] # y1 = [ax.get_ylim()[1]] if self.clickNo == 0: #y = np.linspace(ax.get_ylim()[0], ax.get_ylim()[1], 2) self.x0 = event.xdata self.clickNo = 1 self.lineArtist.append([]) winNums = len(self.xWindows) for i, k in enumerate(ax.keys()): linArt = ax[k].axvline(self.x0, 0, 1, color='k', linewidth=1, zorder=100) self.lineArtist[winNums].append([linArt, linArt]) #else: # linArt = plt.axvline(self.x0, y0[i], y1[i], color='k', linewidth=1, zorder=100) # self.lineArtist.append([linArt, linArt]) else: x1 = event.xdata self.clickNo = 0 windowDrawn.append([]) winArtist.append([]) pathList.append([]) winNums = len(self.xWindows) for i, key in enumerate(kList): path_data = [ (matplotlib.path.Path.MOVETO, (self.x0, y0[i])), (matplotlib.path.Path.LINETO, (x1, y0[i])), (matplotlib.path.Path.LINETO, (x1, y1[i])), (matplotlib.path.Path.LINETO, (self.x0, y1[i])), (matplotlib.path.Path.LINETO, (self.x0, y0[i])), (matplotlib.path.Path.CLOSEPOLY, (self.x0, y0[i])), ] codes, verts = zip(*path_data) path = matplotlib.path.Path(verts, codes) windowDrawn[winNums].append(False) winArtist[winNums].append(None) pathList[winNums].append(path) __draw_windows(event=event, pathlist=pathList, ax_key=key, windowDrawn=windowDrawn, winArtist=winArtist, xWindows=self.xWindows, fig=fig, ax=ax) linArt = ax[key].axvline(x1, 0, 1, color='k', linewidth=0.5, zorder=100) [self.lineArtist[winNums][i].pop(-1)] self.lineArtist[winNums][i].append(linArt) x_win = [self.x0, x1] x_win.sort() #Make sure they are in the right order self.xWindows.append(x_win) fig.canvas.draw() return self.clickNo, self.x0 #Helper function for manual window selection to draw boxes to deslect windows for removal def __remove_on_right(event, xWindows, pathList, windowDrawn, winArtist, lineArtist, fig, ax): """Helper function for manual window selection to draw boxes to deslect windows for removal""" if self.xWindows is not None: for i, xWins in enumerate(self.xWindows): if event.xdata > xWins[0] and event.xdata < xWins[1]: linArtists = self.lineArtist[i] pathList.pop(i) for j, a in enumerate(linArtists): winArtist[i][j].remove()#.pop(i) self.lineArtist[i][j][0].remove()#.pop(i)#[i].pop(j) self.lineArtist[i][j][1].remove() windowDrawn.pop(i) self.lineArtist.pop(i)#[i].pop(j) winArtist.pop(i)#[i].pop(j) self.xWindows.pop(i) fig.canvas.draw() def select_windows(event, input=None, initialize=False): """Function to manually select windows for exclusion from data. Parameters ---------- input : dict Dictionary containing all the hvsr information. Returns ------- self.xWindows : list List of two-item lists containing start and end times of windows to be removed. """ from matplotlib.backend_bases import MouseButton import matplotlib.pyplot as plt #self.fig_noise, self.ax_noise = sprit_hvsr._plot_specgram_stream(stream=input['stream'], params=input, fig=self.fig_noise, ax=self.ax_noise, component='Z', stack_type='linear', detrend='mean', fill_gaps=0, dbscale=True, return_fig=True, cmap_per=[0.1,0.9]) #self.fig_noise.canvas.draw() #if 'stream' in input.keys(): # self.fig_noise, self.ax_noise = sprit_hvsr._plot_specgram_stream(stream=self.params['stream'], params=self.params, fig=self.fig_noise, ax=self.ax_noise, component='Z', stack_type='linear', detrend='mean', fill_gaps=0, dbscale=True, return_fig=True, cmap_per=[0.1,0.9]) #else: # params = input.copy() # input = input['stream'] #if isinstance(input, obspy.core.stream.Stream): # fig, ax = sprit_hvsr._plot_specgram_stream(input, component=['Z']) #elif isinstance(input, obspy.core.trace.Trace): # fig, ax = sprit_hvsr._plot_specgram_stream(input) if initialize: self.lineArtist = [] self.winArtist = [] self.windowDrawn = [] self.pathList = [] self.xWindows = [] self.x0 = 0 self.clickNo = 0 if not initialize: __on_click(event) self.hvsr_data['xwindows_out'] = self.xWindows #self.fig_closed #fig_closed = False #while fig_closed is False: # #fig.canvas.mpl_connect('button_press_event', __on_click)#(self.clickNo, self.xWindows, pathList, windowDrawn, winArtist, lineArtist, self.x0, fig, ax)) # fig.canvas.mpl_connect('close_event', _on_fig_close)#(self.clickNo, self.xWindows, pathList, windowDrawn, winArtist, lineArtist, self.x0, fig, ax)) # plt.pause(0.5) #output['xwindows_out'] = self.xWindows #output['fig'] = fig #output['ax'] = ax noEvent = True return self.hvsr_data #Support function to help select_windows run properly def _on_fig_close(event): #self.fig_closed fig_closed = True return def __on_click(event): if event.button is MouseButton.RIGHT: __remove_on_right(event, self.xWindows, self.pathList, self.windowDrawn, self.winArtist, self.lineArtist, self.fig_noise, self.ax_noise) if event.button is MouseButton.LEFT: self.clickNo, self.x0 = __draw_boxes(event, self.clickNo, self.xWindows, self.pathList, self.windowDrawn, self.winArtist, self.lineArtist, self.x0, self.fig_noise, self.ax_noise) #if 'hvsr_data' not in dir(self): # self.hvsr_data = {'placeholder':None} def plot_noise_windows(hvsr_data={'placeholder':None}, initial_setup=False): if 'hvsr_data' in dir(self): hvsr_data = self.hvsr_data if isinstance(hvsr_data, sprit_hvsr.HVSRBatch): batch_data = hvsr_data.copy() hvsr_data = hvsr_data[list(hvsr_data.keys())[0]] else: batch_data = None if initial_setup: self.xWindows=[] else: #Clear everything for key in self.ax_noise: self.ax_noise[key].clear() self.fig_noise.clear() #Really make sure it's out of memory self.fig_noise = [] self.ax_noise = [] try: self.fig_noise.get_children() except: pass try: self.ax_noise.get_children() except: pass #Reset axes, figure, and canvas widget self.fig_noise = plt.figure() noise_mosaic = [['spec'],['spec'],['spec'], ['spec'],['spec'],['spec'], ['signalz'],['signalz'], ['signaln'], ['signale']] self.ax_noise = self.fig_noise.subplot_mosaic(noise_mosaic, sharex=True) if not initial_setup: self.noise_canvasWidget.destroy() self.noise_toolbar.destroy() self.fig_noise = sprit_hvsr._plot_specgram_stream(stream=hvsr_data['stream'], params=hvsr_data, fig=self.fig_noise, ax=self.ax_noise, component='Z', stack_type='linear', detrend='mean', fill_gaps=0, dbscale=True, return_fig=True, cmap_per=[0.1,0.9]) self.noise_canvas = FigureCanvasTkAgg(self.fig_noise, master=self.canvasFrame_noise) # A tk.DrawingArea. self.noise_canvas.draw() #self.noise_canvasWidget = self.noise_canvas.get_tk_widget()#.pack(side=tk.TOP, fill=tk.BOTH, expand=1) # pack_toolbar=False will make it easier to use a layout manager later on. self.noise_toolbar = NavigationToolbar2Tk(self.noise_canvas, self.canvasFrame_noise, pack_toolbar=False) self.noise_toolbar.update() self.noise_canvasWidget = self.noise_canvas.get_tk_widget()#.pack(side=tk.TOP, fill=tk.BOTH, expand=1) self.noise_canvas.mpl_connect("button_release_event", select_windows) self.noise_toolbar.pack(side=tk.BOTTOM, fill=tk.X) self.noise_canvasWidget.pack(fill='both')#.grid(row=0, column=0, sticky='nsew') if not initial_setup: if batch_data is None: hvsr_data = {'SITENAME':hvsr_data} else: hvsr_data = batch_data for i, (k, hv_data) in enumerate(hvsr_data.items()): #Reset edited data every time plot_noise_windows is run #v_data['stream'] = hv_data['input_stream'].copy() #Set initial input #input = hv_data#['input_stream'] if self.do_stalta.get(): hv_data = sprit_hvsr.remove_noise(hvsr_data=hv_data, remove_method='stalta', sta=self.sta.get(), lta=self.lta.get(), stalta_thresh=[self.stalta_thresh_low.get(), self.stalta_thresh_hi.get()]) if self.do_pctThresh.get(): hv_data = sprit_hvsr.remove_noise(hvsr_data=hv_data, remove_method='saturation', sat_percent=self.pct.get()) if self.do_noiseWin.get(): hv_data = sprit_hvsr.remove_noise(hvsr_data=hv_data, remove_method='noise', noise_percent=self.noise_amp_pct.get(), lta=self.lta_noise.get(), min_win_size=self.win_size_thresh.get()) if self.do_warmup.get(): hv_data = sprit_hvsr.remove_noise(hvsr_data=hv_data, remove_method='warmup', warmup_time=self.warmup_time.get(), cooldown_time=self.cooldown_time.get()) if i==0: self.fig_noise, self.ax_noise, self.noise_windows_line_artists, self.noise_windows_window_artists = sprit_hvsr._get_removed_windows(input=hv_data, fig=self.fig_noise, ax=self.ax_noise, existing_xWindows=self.xWindows, time_type='matplotlib') self.fig_noise.canvas.draw() if batch_data is None: hvsr_data = hvsr_data['SITENAME'] return hvsr_data self.fig_noise.canvas.draw() return plot_noise_windows({'placeholder':None}, initial_setup=True) self.canvasFrame_noise.pack(fill='both')#.grid(row=0, column=0, sticky="nsew") #noise_mosaic = [['spec'],['spec'],['spec'], # ['spec'],['spec'],['spec'], # ['signalz'],['signalz'], ['signaln'], ['signale']] #self.fig_noise, self.ax_noise = plt.subplot_mosaic(noise_mosaic, sharex=True) #self.canvasFrame_noise = ttk.LabelFrame(self.noise_tab, text='Noise Viewer') #self.canvasFrame_noise.pack(fill='both')#.grid(row=0, column=0, sticky="nsew") #self.noise_canvas = FigureCanvasTkAgg(self.fig_noise, master=self.canvasFrame_noise) #self.noise_canvas.draw() #self.noise_canvasWidget = self.noise_canvas.get_tk_widget()#.pack(side=tk.TOP, fill=tk.BOTH, expand=1) #self.noise_canvasWidget.pack(fill='both')#.grid(row=0, column=0, sticky='nsew') #Run button frame runFrame_noise = ttk.Frame(self.noise_tab) runFrame_noise.columnconfigure(0, weight=1) #Run area #Progress Bar self.noiseProgBar = ttk.Progressbar(runFrame_noise, orient='horizontal') self.noiseProgBar.grid(row=0, column=0, sticky='ew')#.pack(fill='both',expand=True, side='left', anchor='sw') #Update Noise Windows button self.style.configure(style='Noise.TButton', background='#86a5ba') self.noise_button = ttk.Button(runFrame_noise, text="Update Noise Windows", command=plot_noise_windows, width=30, style='Noise.TButton') self.noise_windows_line_artists = [] self.noise_windows_window_artists = [] self.style.configure('Run.TButton', background='#8b9685', width=10, height=3) self.run_button = ttk.Button(runFrame_noise, text="Run", style='Run.TButton', command=process_data) self.noise_button.grid(row=0, column=1, sticky='nsew', padx=2.5)#.pack(side='right', anchor='se') self.run_button.grid(row=0, column=2, sticky='nsew', padx=2.5)#.pack(side='right', anchor='se', padx=(10,0)) runFrame_noise.pack(fill='both',side='bottom', anchor='e') def update_remove_noise_call(): if 'prevAutoState' not in dir(self): self.prevAutoState=self.do_auto.get() if self.prevAutoState and not self.do_auto.get(): self.do_stalta.set(False) self.do_pctThresh.set(False) self.do_noiseWin.set(False) self.do_warmup.set(False) #Get method remMethDict = {'auto':self.do_auto.get(), 'stalta':self.do_stalta.get(), 'sat_per':self.do_pctThresh.get(), 'noise_per':self.do_noiseWin.get(), 'warmcool':self.do_warmup.get(), } remMethList = [] for k, v in remMethDict.items(): if v: if k=='auto': remMethList = ['auto'] break remMethList.append(k) if len(remMethList)==1: remMethList = remMethList[0] if remMethList=='auto': remMethList = 'auto' self.do_auto.set(True) set_auto() if len(remMethList)==0: remMethList=None self.remove_noise_call.configure(text="remove_noise(hvsr_data, remove_method={}, sat_percent={}, noise_percent={}, sta={}, lta={}, stalta_thresh=[{},{}], warmup_time={}, cooldown_time={}, min_win_size={}, remove_raw_noise={})".format( remMethList, self.pct.get(), self.noise_amp_pct.get(), self.sta.get(), self.lta.get(), self.stalta_thresh_low.get(), self.stalta_thresh_hi.get(), self.warmup_time.get(), self.cooldown_time.get(), self.win_size_thresh.get(),self.use_raw_data.get() )) self.prevAutoState = self.do_auto.get() #remove_noise Frame removeNoiseFrame = ttk.LabelFrame(self.noise_tab, text='remove_noise() call') self.remove_noise_call = ttk.Label(master=removeNoiseFrame, text="remove_noise(hvsr_data, remove_method='auto',sat_percent=0.995, noise_percent=0.80, sta=2, lta=30, stalta_thresh=[0.5,5], warmup_time=0, cooldown_time=0, min_win_size=1, remove_raw_noise=False)") self.remove_noise_call.grid(row=0, column=0, padx=5, pady=(0,5)) removeNoiseFrame.pack(fill='both', side='bottom')#.grid(row=0, column=1, sticky='nsew') noiseFrame = ttk.LabelFrame(self.noise_tab, text='Noise Removal') noiseFrame.pack(fill='both')#.grid(row=1, columnspan=2, sticky='nsew') #Options for doing stalta antitrigger for noise removal stltaremoveFrame = ttk.LabelFrame(noiseFrame, text='STA/LTA Antitrigger') stltaremoveFrame.grid(row=0, column=0, columnspan=1, sticky='nsew') self.do_stalta = tk.BooleanVar() staltaBool = ttk.Checkbutton(master=stltaremoveFrame, text="", variable=self.do_stalta, command=update_remove_noise_call) # create the Checkbutton widget staltaBool.grid(row=0, column=0, sticky='ew') ttk.Label(master=stltaremoveFrame, text="STA [s]").grid(row=0, column=1) self.sta = tk.DoubleVar() self.sta.set(5) staEntry = ttk.Entry(master=stltaremoveFrame, textvariable=self.sta, width=5, validate='focusout', validatecommand=update_remove_noise_call) # create the Entry widget staEntry.grid(row=0, column=2, sticky='ew', padx=(5,10)) ttk.Label(master=stltaremoveFrame, text="LTA [s]").grid(row=0, column=3) self.lta = tk.DoubleVar() self.lta.set(30) ltaEntry = ttk.Entry(master=stltaremoveFrame, textvariable=self.lta, width=5, validate='focusout', validatecommand=update_remove_noise_call) # create the Entry widget ltaEntry.grid(row=0, column=4, sticky='ew', padx=(5,10)) ttk.Label(master=stltaremoveFrame, text="STA/LTA Thresholds (Low, High)").grid(row=0, column=5) self.stalta_thresh_low = tk.DoubleVar() self.stalta_thresh_low.set(0.5) staltaLowEntry = ttk.Entry(master=stltaremoveFrame, textvariable=self.stalta_thresh_low, width=5, validate='focusout', validatecommand=update_remove_noise_call) # create the Entry widget staltaLowEntry.grid(row=0, column=6, sticky='ew', padx=(5,0)) self.stalta_thresh_hi = tk.DoubleVar() self.stalta_thresh_hi.set(5) staltaHiEntry = ttk.Entry(master=stltaremoveFrame, textvariable=self.stalta_thresh_hi, width=5, validate='focusout', validatecommand=update_remove_noise_call) # create the Entry widget staltaHiEntry.grid(row=0, column=7, sticky='ew') #Options for Percentage threshold removal pctThresFrame = ttk.LabelFrame(noiseFrame, text='Percentage Threshold') pctThresFrame.grid(row=1, column=0, sticky='nsew') self.do_pctThresh= tk.BooleanVar() pctBool = ttk.Checkbutton(master=pctThresFrame, text="", variable=self.do_pctThresh, command=update_remove_noise_call) # create the Checkbutton widget pctBool.grid(row=0, column=0, sticky='ew') ttk.Label(master=pctThresFrame, text="Max Saturation %").grid(row=0, column=1) self.pct = tk.DoubleVar() self.pct.set(0.995) pctEntry = ttk.Entry(master=pctThresFrame, textvariable=self.pct, width=10, validate='focusout', validatecommand=update_remove_noise_call) # create the Entry widget pctEntry.grid(row=0, column=2, sticky='ew', padx=(5,10)) ttk.Label(master=pctThresFrame, text="", width=27).grid(row=0, column=3, columnspan=2) #Options for noisy window noisyWindowFrame = ttk.LabelFrame(noiseFrame, text='Noisy Windows') noisyWindowFrame.grid(row=2, column=0, sticky='nsew') self.do_noiseWin = tk.BooleanVar() winNoiseBool = ttk.Checkbutton(master=noisyWindowFrame, text="", variable=self.do_noiseWin, command=update_remove_noise_call) # create the Checkbutton widget winNoiseBool.grid(row=0, column=0, sticky='ew') ttk.Label(master=noisyWindowFrame, text="Max Window %").grid(row=0, column=1) self.noise_amp_pct = tk.DoubleVar() self.noise_amp_pct.set(0.80) winamppctEntry = ttk.Entry(master=noisyWindowFrame, textvariable=self.noise_amp_pct, width=10, validate='focusout', validatecommand=update_remove_noise_call) # create the Entry widget winamppctEntry.grid(row=0, column=2, sticky='ew', padx=(5,10)) ttk.Label(master=noisyWindowFrame, text="Window Length [sec]").grid(row=0, column=3) self.lta_noise = tk.DoubleVar() self.lta_noise.set(30) winamppctEntry = ttk.Entry(master=noisyWindowFrame, textvariable=self.lta_noise, width=10, validate='focusout', validatecommand=update_remove_noise_call) # create the Entry widget winamppctEntry.grid(row=0, column=4, sticky='ew', padx=(5,10)) ttk.Label(master=noisyWindowFrame, text="Min. Window Size [sec]").grid(row=0, column=5) self.win_size_thresh = tk.DoubleVar() self.win_size_thresh.set(0) win_size_Entry = ttk.Entry(master=noisyWindowFrame, textvariable=self.win_size_thresh, width=10, validate='focusout', validatecommand=update_remove_noise_call) # create the Entry widget win_size_Entry.grid(row=0, column=6, sticky='e', padx=(5,10)) #Options for warmup warmupFrame = ttk.LabelFrame(noiseFrame, text='Warmup & Cooldown Time') warmupFrame.grid(row=0, column=1, sticky='nsew') self.do_warmup= tk.BooleanVar() warmupBool = ttk.Checkbutton(master=warmupFrame, text="", variable=self.do_warmup, command=update_remove_noise_call) # create the Checkbutton widget warmupBool.grid(row=0, column=0, sticky='ew') ttk.Label(master=warmupFrame, text="Warmup time [s]").grid(row=0, column=1) self.warmup_time = tk.DoubleVar() warmupEntry = ttk.Entry(master=warmupFrame, textvariable=self.warmup_time, width=10, validate='focusout', validatecommand=update_remove_noise_call) # create the Entry widget warmupEntry.grid(row=0, column=2, sticky='ew', padx=(5,10)) warmupEntry.delete(0, 'end') warmupEntry.insert(0, '0') ttk.Label(master=warmupFrame, text="Cooldown Time [s]").grid(row=0, column=3) self.cooldown_time = tk.DoubleVar() cooldownEntry = ttk.Entry(master=warmupFrame, textvariable=self.cooldown_time, width=10, validate='focusout', validatecommand=update_remove_noise_call) # create the Entry widget cooldownEntry.grid(row=0, column=5, sticky='ew', padx=(5,10)) cooldownEntry.delete(0, 'end') cooldownEntry.insert(0, '0') #Options for doing stdev noise removal stdremoveFrame = ttk.LabelFrame(noiseFrame, text='Standard Deviation Antitrigger (not yet implemented)') stdremoveFrame.grid(row=1, column=1, columnspan=1, sticky='nsew') self.do_stdev = tk.BooleanVar() stdBool = ttk.Checkbutton(master=stdremoveFrame, text="", variable=self.do_stdev, state='disabled', command=update_remove_noise_call) # create the Checkbutton widget stdBool.grid(row=0, column=0, sticky='ew') ttk.Label(master=stdremoveFrame, text="Std Deviation Ratio (moving stdev/total stdev)").grid(row=0, column=1) self.stdRatio = tk.DoubleVar() stdRatEntry = ttk.Entry(master=stdremoveFrame, textvariable=self.stdRatio, width=5, state='disabled', validate='focusout', validatecommand=update_remove_noise_call) # create the Entry widget stdRatEntry.grid(row=0, column=2, sticky='ew', padx=(5,10)) stdRatEntry.delete(0, 'end') stdRatEntry.insert(0, '1') ttk.Label(master=stdremoveFrame, text="Window Length [s]").grid(row=0, column=3) self.stdWinLen = tk.DoubleVar() stdWinLenEntry = ttk.Entry(master=stdremoveFrame, textvariable=self.stdWinLen, width=5, state='disabled',validate='focusout', validatecommand=update_remove_noise_call) # create the Entry widget stdWinLenEntry.grid(row=0, column=4, sticky='ew', padx=(5,10)) stdWinLenEntry.delete(0, 'end') stdWinLenEntry.insert(0, '5') #Quick set the auto #autoFrame = ttk.LabelFrame(noiseFrame, text='Auto Run') #autoFrame.grid(row=2, column=1, columnspan=1, sticky='nsew') def set_auto(): if self.do_auto.get(): self.do_stalta.set(True) self.do_stdev.set(True) self.do_warmup.set(True) self.do_noiseWin.set(True) self.do_pctThresh.set(True) else: self.do_stalta.set(False) self.do_stdev.set(False) self.do_warmup.set(False) self.do_noiseWin.set(False) self.do_pctThresh.set(False) pass #Additional options addOptionsFrame = ttk.LabelFrame(noiseFrame, text='') addOptionsFrame.grid(row=2, column=1, columnspan=1, sticky='nsew') self.do_auto= tk.BooleanVar() autoBool = ttk.Checkbutton(master=addOptionsFrame, text="Set Auto Run", variable=self.do_auto, command=update_remove_noise_call) # create the Checkbutton widget autoBool.grid(row=0, column=0, sticky='nsew', padx=5) self.use_raw_data= tk.BooleanVar() rawDataRemoveBool = ttk.Checkbutton(master=addOptionsFrame, text="Remove from raw data", variable=self.use_raw_data, command=update_remove_noise_call) # create the Checkbutton widget rawDataRemoveBool.grid(row=0, column=1, sticky='nsew', padx=5) #Export noise windows ttk.Label(noiseFrame, text="Export Figure").grid(row=4, column=0, sticky='ew', padx=5) self.results_noise_dir = tk.StringVar() self.results_noise_dir_entry = ttk.Entry(noiseFrame, textvariable=self.results_noise_dir) self.results_noise_dir_entry.grid(row=4, column=0, columnspan=5, sticky='ew', padx=(100,5)) def filepath_noise_fig(): filepath = filedialog.asksaveasfilename(defaultextension='png', initialdir=pathlib.Path(self.data_path.get()).parent, initialfile=self.params['site']+'_noisewindows.png') if filepath: self.results_noise_dir_entry.delete(4, 'end') self.results_noise_dir_entry.insert(4, filepath) def save_noise_fig(): self.fig_noise.savefig(self.results_noise_dir.get()) self.browse_noise_fig = ttk.Button(noiseFrame, text="Browse",command=filepath_noise_fig) self.browse_noise_fig.grid(row=4, column=7, sticky='ew', padx=2.5) self.save_noise_fig = ttk.Button(noiseFrame, text="Save",command=save_noise_fig) self.save_noise_fig.grid(row=4, column=8, columnspan=2, sticky='ew', padx=2.5) self.noise_tab.pack(expand=1) self.tab_control.add(self.noise_tab, text="Noise") # SETTINGS TAB self.settings_tab = ttk.Frame(self.tab_control) self.tab_control.add(self.settings_tab, text="Settings") # Create a new Notebook widget within the Settings tab settings_notebook = ttk.Notebook(self.settings_tab) # Create the tabs within the Settings tab #PPSD SETTINGS SUBTAB ppsd_settings_tab = ttk.Frame(settings_notebook) ppsdSettingsFrame = ttk.LabelFrame(ppsd_settings_tab, text='Input Settings')#.pack(fill='both') ppsdParamsFrame = ttk.LabelFrame(ppsd_settings_tab, text='PPSD Parameters')#.pack(fill='both') # ppsd_length=30.0 def on_ppsd_length(): try: float(self.ppsd_length.get()) ppsdLenLabel.configure(text='ppsd_length={}'.format(self.ppsd_length.get())) update_ppsd_call(self.ppsd_call) return True except ValueError: return False ppsdLenLabel = ttk.Label(master=ppsdParamsFrame, text='ppsd_length=30.0 ')#.grid(row=0, column=0) ppsdLenLabel.grid(row=0, column=0, sticky='w', pady=(6,6), padx=5) ttk.Label(master=ppsdSettingsFrame, text='PPSD Length (in seconds) [float]').grid(row=0, column=0, sticky='w', padx=5) self.ppsd_length = tk.DoubleVar() self.ppsd_length.set(30) ppsdLenEntry = ttk.Entry(master=ppsdSettingsFrame, textvariable=self.ppsd_length, width=10, validate='focusout', validatecommand=on_ppsd_length) ppsdLenEntry.grid(row=0, column=1, sticky='w', padx=(5, 10)) # overlap=0.5, def on_overlap(): try: overlap = float(self.overlap.get()) if overlap > 1: self.overlap.set(overlap/100) overlapLabel.configure(text='overlap={}'.format(self.overlap.get())) update_ppsd_call(self.ppsd_call) return True except ValueError: return False overlapLabel = ttk.Label(master=ppsdParamsFrame, text='overlap=0.5 ')#.grid(row=0, column=0) overlapLabel.grid(row=1, column=0, sticky='ew', pady=(6,6), padx=5) ttk.Label(master=ppsdSettingsFrame, text='Overlap % (0-1) [float]').grid(row=1, column=0, sticky='w', padx=5) self.overlap = tk.DoubleVar() self.overlap.set(0.5) overlapEntry = ttk.Entry(master=ppsdSettingsFrame, textvariable=self.overlap, width=10, validate='focusout', validatecommand=on_overlap) overlapEntry.grid(row=1, column=1, sticky='w', padx=(5, 10)) # period_step_octaves=0.0625, def on_per_step_oct(): try: float(self.perStepOct.get()) pStepOctLabel.configure(text='period_step_octaves={}'.format(self.perStepOct.get())) update_ppsd_call(self.ppsd_call) return True except ValueError: return False pStepOctLabel = ttk.Label(master=ppsdParamsFrame, text='period_step_octaves=0.0625')#.grid(row=0, column=0) pStepOctLabel.grid(row=2, column=0, sticky='ew', pady=(6,6), padx=5) ttk.Label(master=ppsdSettingsFrame, text='Period Step Octave [float]').grid(row=2, column=0, sticky='w', padx=5) self.perStepOct = tk.DoubleVar() self.perStepOct.set(0.0625) pStepOctEntry = ttk.Entry(master=ppsdSettingsFrame, textvariable=self.perStepOct, width=10, validate='focusout', validatecommand=on_per_step_oct) pStepOctEntry.grid(row=2, column=1, sticky='w', padx=(5, 10)) #skip_on_gaps def show_sog(): if self.skip_on_gaps.get(): sogLabel.configure(text ='skip_on_gaps=True') else: sogLabel.configure(text ='skip_on_gaps=False') update_ppsd_call(self.ppsd_call) self.skip_on_gaps = tk.BooleanVar() ttk.Label(master=ppsdSettingsFrame, text='Skip on Gaps [bool]: ', justify='left').grid(row=3, column=0, sticky='w', padx=5) sogCheckButton = ttk.Checkbutton(master=ppsdSettingsFrame, text='', variable=self.skip_on_gaps, command=show_sog) # create the Entry widget sogCheckButton.grid(row=3, column=1, sticky='ew', padx=(5,10)) sogLabel = ttk.Label(master=ppsdParamsFrame, text='skip_on_gaps=False') sogLabel.grid(row=3, column=0, sticky='ew', pady=(6,6), padx=5) # db_bins=(-200, -50, 1.0), def show_dbbins(): try: float(minDB.get()) float(maxDB.get()) float(dB_step.get()) dbbinsLabel.configure(text='db_bins=({}, {}, {})'.format( minDB.get(), maxDB.get(), dB_step.get())) self.db_bins = (minDB.get(), maxDB.get(), dB_step.get()) update_ppsd_call(self.ppsd_call) return True except ValueError: return False dbbinsLabel = ttk.Label(master=ppsdParamsFrame, text='db_bins=(-200, -50, 1.0)') dbbinsLabel.grid(row=4, column=0, sticky='ew', pady=(6,6), padx=5) ttk.Label(master=ppsdSettingsFrame, text='dB Bins (Y Axis) [tuple]', justify='left').grid(row=4, column=0, sticky='w', padx=5) ttk.Label(master=ppsdSettingsFrame, text='Min. dB').grid(row=4, column=1, sticky='e', padx=5) minDB = tk.DoubleVar() minDB.set(-200) minDBEntry = ttk.Entry(master=ppsdSettingsFrame, textvariable=minDB, validate="focusout", validatecommand=show_dbbins, width=10) minDBEntry.grid(row=4, column=2, sticky='w', padx=(5, 10)) ttk.Label(master=ppsdSettingsFrame, text='Max. dB').grid(row=4, column=3, sticky='e', padx=5) maxDB = tk.DoubleVar() maxDB.set(-50) maxDBEntry = ttk.Entry(master=ppsdSettingsFrame, textvariable=maxDB, validate="focusout", validatecommand=show_dbbins, width=10) maxDBEntry.grid(row=4, column=4, sticky='w', padx=(5, 10)) ttk.Label(master=ppsdSettingsFrame, text='dB Step').grid(row=4, column=5, sticky='e', padx=5) dB_step = tk.DoubleVar() dB_step.set(1.0) stepEntry = ttk.Entry(master=ppsdSettingsFrame, textvariable=dB_step, validate="focusout", validatecommand=(show_dbbins), width=10) stepEntry.grid(row=4, column=6, sticky='w', padx=(5, 10)) self.db_bins = (minDB.get(), maxDB.get(), dB_step.get()) # period_limits=None, def show_per_lims(): try: if minPerLim.get() == 'None': pass else: float(minPerLim.get()) if maxPerLim.get() == 'None': pass else: float(maxPerLim.get()) if minPerLim.get() == 'None' or maxPerLim.get() == 'None': perLimsLabel.configure(text='period_limits=None') else: perLimsLabel.configure(text='period_limits=[{}, {}]'.format(minPerLim.get(), maxPerLim.get())) self.period_limits = [float(minPerLim.get()), float(maxPerLim.get())] update_ppsd_call(self.ppsd_call) return True except ValueError: return False perLimsLabel = ttk.Label(master=ppsdParamsFrame, text='period_limits=None') perLimsLabel.grid(row=5, column=0, sticky='ew', pady=(6,6), padx=5) ttk.Label(master=ppsdSettingsFrame, text='Period Limits [list of floats or None]', justify='left').grid(row=5, column=0, sticky='w', padx=5) ttk.Label(master=ppsdSettingsFrame, text='Min. Period Limit').grid(row=5, column=1, sticky='e', padx=5) minPerLim = tk.StringVar() minPerLim.set(None) minPerLimEntry = ttk.Entry(master=ppsdSettingsFrame, textvariable=minPerLim, validate="focusout", validatecommand=(show_per_lims), width=10) minPerLimEntry.grid(row=5, column=2, sticky='w', padx=(5, 10)) ttk.Label(master=ppsdSettingsFrame, text='Max. Period Limit').grid(row=5, column=3, sticky='e', padx=5) maxPerLim = tk.StringVar() maxPerLim.set(None) maxPerLimEntry = ttk.Entry(master=ppsdSettingsFrame, textvariable=maxPerLim, validate="focusout", validatecommand=(show_per_lims), width=10) maxPerLimEntry.grid(row=5, column=4, sticky='w', padx=(5, 10)) if minPerLim.get() == 'None' or maxPerLim.get() == 'None': self.period_limits = None else: self.period_limits = [float(minPerLim.get()), float(maxPerLim.get())] # period_smoothing_width_octaves=1.0, def on_per_smoothwidth_oct(): try: float(self.perSmoothWidthOct.get()) pSmoothWidthLabel.configure(text='period_smoothing_width_octaves={}'.format(self.perSmoothWidthOct.get())) update_ppsd_call(self.ppsd_call) return True except ValueError: return False pSmoothWidthLabel = ttk.Label(master=ppsdParamsFrame, text='period_smoothing_width_octaves=1.0')#.grid(row=0, column=0) pSmoothWidthLabel.grid(row=6, column=0, sticky='ew', pady=(6,6), padx=5) ttk.Label(master=ppsdSettingsFrame, text='Period Smoothing Width (octaves) [float]').grid(row=6, column=0, sticky='w', padx=5) self.perSmoothWidthOct = tk.DoubleVar() self.perSmoothWidthOct.set(1.0) pSmoothWidthEntry = ttk.Entry(master=ppsdSettingsFrame, textvariable=self.perSmoothWidthOct, width=10, validate='focusout', validatecommand=on_per_smoothwidth_oct) pSmoothWidthEntry.grid(row=6, column=1, sticky='w', padx=(5, 10)) # special_handling=None, def on_special_handling(): try: str(self.special_handling.get()) if self.special_handling.get() == 'None': specialHandlingLabel.configure(text="special_handling={}".format(self.special_handling.get())) special_handling = None else: specialHandlingLabel.configure(text="special_handling='{}'".format(self.special_handling.get())) special_handling = self.special_handling.get() update_ppsd_call(self.ppsd_call) return True except ValueError: return False specialHandlingLabel = ttk.Label(master=ppsdParamsFrame, text="special_handling=None") specialHandlingLabel.grid(row=7, column=0, sticky='ew', pady=(6,6), padx=5) ttk.Label(master=ppsdSettingsFrame, text='Special Handling [str]').grid(row=7, column=0, sticky='w', padx=5) self.special_handling = tk.StringVar() self.special_handling.set('None') ttk.Radiobutton(master=ppsdSettingsFrame, text='None', variable=self.special_handling, value='None', command=on_special_handling).grid(row=7, column=1, sticky='w', padx=(5, 10)) ttk.Radiobutton(master=ppsdSettingsFrame, text='Ringlaser', variable=self.special_handling, value='ringlaser', command=on_special_handling).grid(row=7, column=2, sticky='w', padx=(5, 10)) ttk.Radiobutton(master=ppsdSettingsFrame, text='Hydrophone', variable=self.special_handling, value='hydrophone', command=on_special_handling).grid(row=7, column=3, sticky='w', padx=(5, 10)) if self.special_handling.get()=='None': special_handling = None else: special_handling = self.special_handling.get() separator = ttk.Separator(ppsdSettingsFrame, orient='horizontal') separator.grid(row=8, columnspan=8, sticky='ew', pady=10, padx=5) separator = ttk.Separator(ppsdParamsFrame, orient='horizontal') separator.grid(row=8, sticky='ew', pady=10, padx=5) #remove_outliers def show_rem_outliers(): if self.remove_outliers.get(): rem_outliers_Label.configure(text ='remove_outliers=True') else: rem_outliers_Label.configure(text ='remove_outliers=False') update_ppsd_call(self.ppsd_call) self.remove_outliers = tk.BooleanVar() self.remove_outliers.set(True) ttk.Label(master=ppsdSettingsFrame, text='Remove outlier curves [bool]: ', justify='left').grid(row=9, column=0, sticky='w', padx=5) rem_outliers_CheckButton = ttk.Checkbutton(master=ppsdSettingsFrame, text='', variable=self.remove_outliers, command=show_rem_outliers) # create the Entry widget rem_outliers_CheckButton.grid(row=9, column=1, sticky='ew', padx=(5,10)) rem_outliers_Label = ttk.Label(master=ppsdParamsFrame, text='remove_outliers=True') rem_outliers_Label.grid(row=9, column=0, sticky='ew', pady=(6,6), padx=5) # outlier_std=1.5, def on_outlier_std(): try: float(self.outlier_std.get()) outlier_std_Label.configure(text='outlier_std={}'.format(self.outlier_std.get())) update_ppsd_call(self.ppsd_call) return True except ValueError: return False outlier_std_Label = ttk.Label(master=ppsdParamsFrame, text='outlier_std=1.5')#.grid(row=0, column=0) outlier_std_Label.grid(row=10, column=0, sticky='ew', pady=(6,6), padx=5) ttk.Label(master=ppsdSettingsFrame, text='St. Dev. for Outliers [float]').grid(row=10, column=0, sticky='w', padx=5) self.outlier_std = tk.DoubleVar() self.outlier_std.set(1.5) outlier_std_Entry = ttk.Entry(master=ppsdSettingsFrame, textvariable=self.outlier_std, width=10, validate='focusout', validatecommand=on_outlier_std) outlier_std_Entry.grid(row=10, column=1, sticky='w', padx=(5, 10)) #PPSD Function Call ppsdCallFrame = ttk.LabelFrame(ppsd_settings_tab, text='sprit_hvsr.generate_ppsds() and obspy PPSD() call')#.pack(fill='both') self.ppsd_call = ttk.Label(master=ppsdCallFrame, text='obspy...PPSD({}, {}, {}, {}, {}, {}, \n\t{}, {}, {}, {})' .format('stats', 'metadata', ppsdLenLabel.cget('text'), overlapLabel.cget('text'), pStepOctLabel.cget('text'), sogLabel.cget('text'), dbbinsLabel.cget('text'), perLimsLabel.cget('text'), pSmoothWidthLabel.cget('text'), specialHandlingLabel.cget('text'))) self.ppsd_call.pack(side='bottom', anchor='w', padx=(25,0), pady=(10,10)) self.generate_ppsd_call = ttk.Label(master=ppsdCallFrame, text='generate_ppsds({}, remove_outliers={}, outlier_std={},...\n\t{}, {}, {}, {}, {}, \n\t{}, {}, {})' .format('hvsr_data', self.remove_outliers.get(), self.outlier_std.get(), ppsdLenLabel.cget('text'), overlapLabel.cget('text'), pStepOctLabel.cget('text'), sogLabel.cget('text'), dbbinsLabel.cget('text'), perLimsLabel.cget('text'), pSmoothWidthLabel.cget('text'), specialHandlingLabel.cget('text'))) self.generate_ppsd_call.pack(side='bottom', anchor='w', padx=(25,0), pady=(10,10)) def update_ppsd_call(ppsd_call): ppsd_call.configure(text='obspy...PPSD({}, {}, {}, {}, {}, {}, \n\t{}, {}, {}, {})'.format('stats', 'metadata', ppsdLenLabel.cget('text'), overlapLabel.cget('text'), pStepOctLabel.cget('text'), sogLabel.cget('text'), dbbinsLabel.cget('text'), perLimsLabel.cget('text'), pSmoothWidthLabel.cget('text'), specialHandlingLabel.cget('text'))) self.generate_ppsd_call.configure(text='generate_ppsds({}, remove_outliers={}, outlier_std={},...\n\t{}, {}, {}, {}, {}, \n\t{}, {}, {})' .format('hvsr_data', self.remove_outliers.get(), self.outlier_std.get(), ppsdLenLabel.cget('text'), overlapLabel.cget('text'), pStepOctLabel.cget('text'), sogLabel.cget('text'), dbbinsLabel.cget('text'), perLimsLabel.cget('text'), pSmoothWidthLabel.cget('text'), specialHandlingLabel.cget('text'))) #Stats from trace(s) obspyStatsFrame = ttk.LabelFrame(ppsd_settings_tab, text='Data Trace Stats')#.pack(fill='both') self.obspySreamLabel_settings = ttk.Label(obspyStatsFrame, text='Stats') self.obspySreamLabel_settings.pack(anchor='nw', padx=5) #Metadata (PAZ) obspyMetadataFrame = ttk.LabelFrame(ppsd_settings_tab, text='Metadata Poles and Zeros')#.pack(fill='both') self.metadataZ_settings = ttk.Label(obspyMetadataFrame, text='Z: ') self.metadataZ_settings.grid(row=1, column=0, padx=5) self.metadataZ_settings.configure(font=("TkDefaultFont", 10, 'underline', 'bold')) self.sensitivityLabelZ_settings = ttk.Label(obspyMetadataFrame, text='Sensitivity_Z') self.sensitivityLabelZ_settings.grid(row=1, column=1, padx=5) self.gainLabelZ_settings = ttk.Label(obspyMetadataFrame, text='Gain_Z') self.gainLabelZ_settings.grid(row=1, column=2, padx=5) self.polesLabelZ_settings = ttk.Label(obspyMetadataFrame, text='Poles_Z') self.polesLabelZ_settings.grid(row=1, column=3, padx=5) self.zerosLabelZ_settings = ttk.Label(obspyMetadataFrame, text='Zeros_Z') self.zerosLabelZ_settings.grid(row=1, column=4, padx=5) self.metadataN_settings = ttk.Label(obspyMetadataFrame, text='N: ') self.metadataN_settings.grid(row=2, column=0, padx=5) self.metadataN_settings.configure(font=("TkDefaultFont", 10, 'underline', 'bold')) self.sensitivityLabelN_settings = ttk.Label(obspyMetadataFrame, text='Sensitivity_N') self.sensitivityLabelN_settings.grid(row=2, column=1, padx=5) self.gainLabelN_settings = ttk.Label(obspyMetadataFrame, text='Gain_N') self.gainLabelN_settings.grid(row=2, column=2, padx=5) self.polesLabelN_settings = ttk.Label(obspyMetadataFrame, text='Poles_N') self.polesLabelN_settings.grid(row=2, column=3, padx=5) self.zerosLabelN_settings = ttk.Label(obspyMetadataFrame, text='Zeros_N') self.zerosLabelN_settings.grid(row=2, column=4, padx=5) self.metadataE_settings = ttk.Label(obspyMetadataFrame, text='E: ') self.metadataE_settings.grid(row=3, column=0, padx=5) self.metadataE_settings.configure(font=("TkDefaultFont", 10, 'underline', 'bold')) self.sensitivityLabelE_settings = ttk.Label(obspyMetadataFrame, text='Sensitivity_E') self.sensitivityLabelE_settings.grid(row=3, column=1) self.gainLabelE_settings = ttk.Label(obspyMetadataFrame, text='Gain_E') self.gainLabelE_settings.grid(row=3, column=2, padx=5) self.polesLabelE_settings = ttk.Label(obspyMetadataFrame, text='Poles_E') self.polesLabelE_settings.grid(row=3, column=3, padx=5) self.zerosLabelE_settings = ttk.Label(obspyMetadataFrame, text='Zeros_E') self.zerosLabelE_settings.grid(row=3, column=4, padx=5) self.metadata_sensitivity = ttk.Label(obspyMetadataFrame, text='Sensitivity') self.metadata_sensitivity.grid(row=0, column=1, padx=5) self.metadata_sensitivity.configure(font=("TkDefaultFont", 10, 'underline', 'bold')) self.metadata_gain = ttk.Label(obspyMetadataFrame, text='Gain') self.metadata_gain.grid(row=0, column=2, padx=5) self.metadata_gain.configure(font=("TkDefaultFont", 10, 'underline', 'bold')) self.metadata_poles = ttk.Label(obspyMetadataFrame, text='Poles') self.metadata_poles.grid(row=0, column=3, padx=5) self.metadata_poles.configure(font=("TkDefaultFont", 10, 'underline', 'bold')) self.metadata_zeros = ttk.Label(obspyMetadataFrame, text='Zeros') self.metadata_zeros.grid(row=0, column=4, padx=5) self.metadata_zeros.configure(font=("TkDefaultFont", 10, 'underline', 'bold')) #Run button frame runFrame_set_ppsd = ttk.Frame(ppsd_settings_tab) self.run_button = ttk.Button(runFrame_set_ppsd, text="Run", style='Run.TButton', command=process_data) self.run_button.grid(row=0, column=11, sticky='ew', padx=2.5) self.settingsProgBar_ppsd = ttk.Progressbar(runFrame_set_ppsd, orient='horizontal') self.settingsProgBar_ppsd.grid(row=0, column=0, columnspan=10, sticky='ew') runFrame_set_ppsd.columnconfigure(0, weight=1) runFrame_set_ppsd.pack(fill='both', side='bottom', anchor='e') obspyMetadataFrame.pack(fill='both', side='bottom',expand=True)#.grid(row=7, column=0, columnspan=6, sticky='nsew')#.pack(side='bottom', fill='both', anchor='n', expand=True) obspyStatsFrame.pack(fill='both', side='bottom',expand=True)#.grid(row=6, column=0, columnspan=6, sticky='nsew')#.pack(side='bottom', fill='both', anchor='n', expand=True) ppsdCallFrame.pack(fill='both', side='bottom',expand=True)#row=5, column=0, columnspan=6, sticky='nsew')#.pack(side='bottom', fill='both', anchor='n', expand=True) ppsdParamsFrame.pack(fill='both', side='right')#.grid(row=0, column=5, rowspan=4, sticky='nsew')#.pack(side='right',fill='both', anchor='n', expand=True) ppsdSettingsFrame.pack(fill='both', expand=True, side='top', anchor='w')#.grid(row=0, column=0, columnspan=4, rowspan=4, sticky='nsew')#.pack(side='left', fill='both', anchor='n', expand=True) ppsd_settings_tab.pack(fill='both', expand=True) settings_notebook.add(ppsd_settings_tab, text="PPSD") #HVSR SETTINGS SUBTAB hvsr_settings_tab = ttk.Frame(settings_notebook) hvsrSettingsFrame = ttk.LabelFrame(hvsr_settings_tab, text='H/V Processing Settings')#.pack(fill='both') hvsrParamsFrame = ttk.LabelFrame(hvsr_settings_tab, text='Process HVSR Parameters')#.pack(fill='both') #Method selection, method=4 ttk.Label(hvsrSettingsFrame, text="Horizontal Combine Method [int]").grid(row=0, column=0, padx=(5,0), sticky='w') method_options = ['', #Empty to make intuitive and match sprit_hvsr.py "1.Diffuse Field Assumption (not currently implemented)", "2. Arithmetic Mean H ≡ (N + E)/2", "3. Geometric Mean: H ≡ √(N · E) (recommended by SESEAME Project (2004))", "4. Vector Summation: H ≡ √(N^2 + E^2)", "5. Quadratic Mean: H ≡ √(N^2 + E^2)/2", "6. Maximum Horizontal Value: H ≡ max(N, E)" ] def on_method_select(meth, meth_opts=method_options): self.method_ind = meth_opts.index(meth) try: int(self.method_ind) hCombMethodLabel.configure(text="method={}".format(self.method_ind)) update_procHVSR_call(self.procHVSR_call) return True except ValueError: return False defaultMeth=3 hCombMethodLabel = ttk.Label(master=hvsrParamsFrame, text="method={}".format(defaultMeth), width=30) hCombMethodLabel.grid(row=0, column=0, sticky='ew', pady=(6,6), padx=5) self.method_sel = tk.StringVar(value=method_options[defaultMeth]) self.method_ind = method_options.index(self.method_sel.get()) self.method_dropdown = ttk.OptionMenu(hvsrSettingsFrame, self.method_sel, method_options[defaultMeth], *method_options, command=on_method_select) self.method_dropdown.config(width=50) self.method_dropdown.grid(row=0, column=1, columnspan=8, sticky='ew') #smooth=True, def curve_smooth(): try: int(self.hvsmooth.get()) bool(self.hvsmoothbool.get()) if not self.hvsmoothbool.get(): hvSmoothLabel.configure(text='smooth={}'.format(self.hvsmoothbool.get())) self.hvsmooth_param = False else: hvSmoothLabel.configure(text='smooth={}'.format(self.hvsmooth.get())) self.hvsmooth_param = self.hvsmooth.get() update_procHVSR_call(self.procHVSR_call) return True except ValueError: return False hvSmoothLabel = ttk.Label(master=hvsrParamsFrame, text="smooth=True", width=30) hvSmoothLabel.grid(row=1, column=0, sticky='ew', pady=(6,6), padx=5) ttk.Label(master=hvsrSettingsFrame, text='Smooth H/V Curve [bool]').grid(row=1, column=0, padx=(5,0), sticky='w') self.hvsmoothbool = tk.BooleanVar() self.hvsmoothbool.set(True) self.hvsmooth_param=True smoothCurveBool = ttk.Checkbutton(master=hvsrSettingsFrame, text="", compound='left', variable=self.hvsmoothbool, command=curve_smooth) # create the Checkbutton widget smoothCurveBool.grid(row=1, column=1, sticky='w') self.hvsmooth = tk.IntVar() self.hvsmooth.set(51) smoothCurveSamples = ttk.Entry(master=hvsrSettingsFrame, textvariable=self.hvsmooth, width=10, validate='focusout', validatecommand=curve_smooth) smoothCurveSamples.grid(row=1, column=2, sticky='w', padx=(5, 10)) ttk.Label(master=hvsrSettingsFrame, text='[int] # pts in smoothing window (default=51)').grid(row=1, column=3, padx=(0,0)) #freq_smooth='konno ohmachi', freqSmoothLabel = ttk.Label(master=hvsrParamsFrame, text="freq_smooth='konno ohmachi'", width=30) freqSmoothLabel.grid(row=2, column=0, sticky='w', pady=(16,16), padx=5) def on_freq_smooth(): try: str(self.freq_smooth.get()) freqSmoothLabel.configure(text="freq_smooth={}".format(self.freq_smooth.get())) update_procHVSR_call(self.procHVSR_call) return True except ValueError: return False self.freq_smooth = tk.StringVar() self.freq_smooth.set('konno ohmachi') ttk.Label(master=hvsrSettingsFrame, text='Frequency Smoothing [str]').grid(row=2, column=0, padx=(5,0), sticky='w') fsmoothOptFrame = ttk.LabelFrame(master=hvsrSettingsFrame, text='Frequency Smoothing Operations') fsmoothOptFrame.grid(row=2, column=1, columnspan=7, padx=5, sticky='nsew') ttk.Radiobutton(master=fsmoothOptFrame, text='Konno-Ohmachi', variable=self.freq_smooth, value='konno ohmachi', command=on_freq_smooth).grid(row=0, column=0, sticky='w', padx=(5, 10)) ttk.Radiobutton(master=fsmoothOptFrame, text='Constant', variable=self.freq_smooth, value='constant', command=on_freq_smooth).grid(row=0, column=1, sticky='w', padx=(5, 10)) ttk.Radiobutton(master=fsmoothOptFrame, text='Proportional', variable=self.freq_smooth, value='proportional', command=on_freq_smooth).grid(row=0, column=2, sticky='w', padx=(5, 10)) ttk.Radiobutton(master=fsmoothOptFrame, text='None', variable=self.freq_smooth, value='None', command=on_freq_smooth).grid(row=0, column=3, sticky='w', padx=(5, 10)) #f_smooth_width=40, fSmoothWidthlabel = ttk.Label(master=hvsrParamsFrame, text="f_smooth_width=40", width=30) fSmoothWidthlabel.grid(row=3, column=0, sticky='ew', pady=(6,6), padx=5) def on_smooth_width(): try: int(self.fSmoothWidth.get()) fSmoothWidthlabel.configure(text='f_smooth_width={}'.format(self.fSmoothWidth.get())) update_procHVSR_call(self.procHVSR_call) return True except ValueError: return False ttk.Label(master=hvsrSettingsFrame, text='Bandwidth of freq. smoothing [int]').grid(row=3, column=0, padx=(5,0), sticky='w') self.fSmoothWidth = tk.IntVar() self.fSmoothWidth.set(40) fSmoothWidthEntry = ttk.Entry(master=hvsrSettingsFrame, justify='left', textvariable=self.fSmoothWidth, validate='focusout', validatecommand=on_smooth_width, width=10) fSmoothWidthEntry.grid(row=3, column=1, sticky='w', padx=(5, 10)) #resample=True, resampleLabel = ttk.Label(master=hvsrParamsFrame, text="resample=True", width=30) resampleLabel.grid(row=4, column=0, sticky='ew', pady=(6,6), padx=5) def on_curve_resample(): try: if not self.resamplebool.get(): resampleLabel.configure(text='resample={}'.format(self.resamplebool.get())) self.hvresample_int=self.hvresample.get() else: resampleLabel.configure(text='resample={}'.format(self.hvresample.get())) self.hvresample_int=self.hvresample.get() update_procHVSR_call(self.procHVSR_call) return True except ValueError: return False self.resamplebool = tk.BooleanVar() self.resamplebool.set(True) ttk.Label(master=hvsrSettingsFrame, text='Resample H/V Curve [bool]').grid(row=4, column=0, padx=(5,0), sticky='w') resampleCurveBool = ttk.Checkbutton(master=hvsrSettingsFrame, text="", compound='left', variable=self.resamplebool, command=on_curve_resample) # create the Checkbutton widget resampleCurveBool.grid(row=4, column=1, sticky='w') self.hvresample = tk.IntVar() self.hvresample.set(1000) self.hvresample_int = self.hvresample.get() resampleCurveSamples = ttk.Entry(master=hvsrSettingsFrame, textvariable=self.hvresample, width=10, validate='focusout', validatecommand=on_curve_resample) resampleCurveSamples.grid(row=4, column=2, sticky='w', padx=(5, 10)) ttk.Label(master=hvsrSettingsFrame, text='[int] # pts in resampled curve (default=1000)').grid(row=4, column=3, padx=(0,0), sticky='w') #outlier_curve_std=1.75 outlierValLabel = ttk.Label(master=hvsrParamsFrame, text="outlier_curve_std=1.75", width=30) outlierValLabel.grid(row=5, column=0, sticky='ew', pady=(6,6), padx=5) ttk.Label(master=hvsrSettingsFrame, text='Outlier St. Dev. [float]').grid(row=6, column=0, columnspan=2, padx=(5,0), sticky='w') self.outlierRemStDev = tk.DoubleVar() self.outlierRemStDev.set(1.75) outlierRemStDev = ttk.Entry(master=hvsrSettingsFrame, textvariable=self.outlierRemStDev, width=10, validate='focusout', validatecommand=on_outlier_std) outlierRemStDev.grid(row=6, column=1, sticky='w', padx=(5, 10)) separator = ttk.Separator(hvsrSettingsFrame, orient='horizontal') separator.grid(row=7, columnspan=7, sticky='ew', pady=10) #hvsr_band=[0.4, 40] hvsrBandLabel = ttk.Label(master=hvsrParamsFrame, text="hvsr_band=[0.4,40]", width=30) hvsrBandLabel.grid(row=7, column=0, sticky='w', pady=(20,6), padx=5) ttk.Label(hvsrSettingsFrame,text="HVSR Band [Hz]").grid(row=8,column=0, sticky='w', padx=(5,0)) hvsr_band_min_settingsEntry = ttk.Entry(hvsrSettingsFrame, width=10, textvariable=self.hvsrBand_min, validate='focusout', validatecommand=on_hvsrband_update) hvsr_band_min_settingsEntry.grid(row=8,column=1, sticky='ew') hvsr_band_max_settingsEntry = ttk.Entry(hvsrSettingsFrame, width=10, textvariable=self.hvsrBand_max, validate='focusout', validatecommand=on_hvsrband_update) hvsr_band_max_settingsEntry.grid(row=8,column=2, sticky='ew') #peak_freq_range=[0.4, 40] peakFreqRangeLabel = ttk.Label(master=hvsrParamsFrame, text="peak_freq_range=[0.4,40]", width=30) peakFreqRangeLabel.grid(row=8, column=0, sticky='w', pady=(20,6), padx=5) ttk.Label(hvsrSettingsFrame,text="Peak Frequency Range [Hz]").grid(row=9,column=0, sticky='w', padx=(5,0)) hvsr_band_min_settingsEntry = ttk.Entry(hvsrSettingsFrame, width=10, textvariable=self.peakFreqRange_min, validate='focusout', validatecommand=on_peakFreqRange_update) hvsr_band_min_settingsEntry.grid(row=9,column=1, sticky='ew') hvsr_band_max_settingsEntry = ttk.Entry(hvsrSettingsFrame, width=10, textvariable=self.peakFreqRange_max, validate='focusout', validatecommand=on_peakFreqRange_update) hvsr_band_max_settingsEntry.grid(row=9,column=2, sticky='ew') #Process HVSR Function Call hvsrCallFrame = ttk.LabelFrame(hvsr_settings_tab, text='sprit_hvsr.process_hvsr() Call')#.pack(fill='both') self.procHVSR_call = ttk.Label(master=hvsrCallFrame, text='process_hvsr({}, {}, {}, {}, {}, \n\t{}, {}, {})' .format('hvsr_data', hCombMethodLabel.cget('text'), hvSmoothLabel.cget('text'), freqSmoothLabel.cget('text'), fSmoothWidthlabel.cget('text'), resampleLabel.cget('text'), outlierValLabel.cget('text'), hvsrBandLabel.cget('text'))) self.procHVSR_call.pack(anchor='w', padx=(25,0), pady=(10,10)) def update_procHVSR_call(procHVSR_call): procHVSR_call.configure(text='process_hvsr({}, {}, {}, {}, {}, \n\t{}, {}, {})' .format('hvsr_data', hCombMethodLabel.cget('text'), hvSmoothLabel.cget('text'), freqSmoothLabel.cget('text'), fSmoothWidthlabel.cget('text'), resampleLabel.cget('text'), outlierValLabel.cget('text'), hvsrBandLabel.cget('text'))) #Check Peaks Function Call checkPeaksCallFrame = ttk.LabelFrame(hvsr_settings_tab, text='sprit_hvsr.check_peaks() Call')#.pack(fill='both') self.checkPeaks_Call = ttk.Label(master=checkPeaksCallFrame, text='check_peaks({}, {}, {})' .format('hvsr_data', hvsrBandLabel.cget('text'), peakFreqRangeLabel.cget('text'))) self.checkPeaks_Call.pack(anchor='w', padx=(25,0), pady=(10,10)) #check_peaks(hvsr_dict, hvsr_band=[0.4, 40], peak_water_level=1.8) def update_check_peaks_call(checkPeaks_Call): checkPeaks_Call.configure(text='check_peaks({}, {}, {})' .format('hvsr_data', hvsrBandLabel.cget('text'), peakFreqRangeLabel.cget('text'))) #Run button frame runFrame_set_hvsr = ttk.Frame(hvsr_settings_tab) runFrame_set_hvsr.columnconfigure(0, weight=1) self.settingsProgBar_hvsr = ttk.Progressbar(runFrame_set_hvsr, orient='horizontal') self.settingsProgBar_hvsr.grid(row=0, column=0, sticky='nsew')#.pack(fill='both',expand=True, side='left', anchor='sw') self.run_button = ttk.Button(runFrame_set_hvsr, text="Run", style='Run.TButton', command=process_data) self.run_button.grid(row=0, column=1, sticky='nsew', padx=2.5)#.pack(side='bottom', anchor='e') #Pack tab runFrame_set_hvsr.pack(fill='both', side='bottom', anchor='e') checkPeaksCallFrame.pack(fill='both', expand=True, side='bottom')#.grid(row=10, column=0, columnspan=6, sticky='nsew')#.pack(side='bottom', fill='both', anchor='n', expand=True) hvsrCallFrame.pack(fill='both', expand=True, side='bottom')#.grid(row=9, column=0, columnspan=6, sticky='nsew')#.pack(side='bottom', fill='both', anchor='n', expand=True) hvsrParamsFrame.pack(fill='both', side='right')#.grid(row=0, column=6, rowspan=4, sticky='nsew')#.pack(side='right',fill='both', anchor='n', expand=True) hvsrSettingsFrame.pack(fill='both', expand=True, side='top')#.grid(row=0, column=0, columnspan=6, rowspan=4, sticky='nsew')#.pack(fill='both', expand=True) hvsr_settings_tab.pack(fill='both', expand=True) settings_notebook.add(hvsr_settings_tab, text="HVSR Settings") #PLOT SETTINGS TAB plot_settings_tab = ttk.Frame(settings_notebook) # Create the Plot Options LabelFrame plot_options_frame = ttk.LabelFrame(plot_settings_tab, text="Plot Options") def update_hvplot_call(): kindstr = get_kindstr() hvplot_label.configure(text="plot_hvsr({}, plot_type={}, xtype='{}', show_legend={}, {}, {})".format('hvsr_data', kindstr, self.x_type.get(), self.show_legend.get(), '[...]', 'kwargs')) # Create the Checkbuttons for the plot options ttk.Label(plot_options_frame, text='HVSR Plot', justify='center').grid(row=0, column=1, sticky='ew', padx=(5, 5)) ttk.Label(plot_options_frame, text='Components H/V Plot', justify='center').grid(row=0, column=2, sticky='ew', padx=(5, 5)) ttk.Label(plot_options_frame, text='Spectrogram Plot', justify='center').grid(row=0, column=3, sticky='ew', padx=(5, 5)) self.hvsr_chart_bool = tk.BooleanVar() self.hvsr_chart_bool.set(True) ttk.Checkbutton(plot_options_frame, text='', variable=self.hvsr_chart_bool, command=update_hvplot_call).grid(row=1, column=1, sticky='nsew', padx=15, pady=(5, 20)) self.ind_comp_chart_bool = tk.BooleanVar() self.ind_comp_chart_bool.set(True) ttk.Checkbutton(plot_options_frame, text='', variable=self.ind_comp_chart_bool, command=update_hvplot_call).grid(row=1, column=2, sticky='nsew', padx=50, pady=(5, 20)) self.spec_chart_bool = tk.BooleanVar() self.spec_chart_bool.set(True) ttk.Checkbutton(plot_options_frame, text='', variable=self.spec_chart_bool, command=update_hvplot_call).grid(row=1, column=3, sticky='nsew', padx=25, pady=(5, 20)) ttk.Separator(plot_options_frame, orient='horizontal').grid(row=2, columnspan=5, sticky='ew', pady=5) #Separate component chart: c+ ttk.Label(plot_options_frame, text='Show Components on same chart as H/V Curve:').grid(row=3, column=0, sticky='w', padx=5) def disable_comp_buttons(): if self.show_comp_with_hv.get(): self.annotate_best_peak_comp.set(False) self.show_best_peak_comp.set(False) bestPeakCompButton.config(state="disabled") bestPeakCompAnnButton.config(state='disabled') else: bestPeakCompButton.config(state="normal") bestPeakCompAnnButton.config(state='normal') update_hvplot_call() self.show_comp_with_hv = tk.BooleanVar() self.show_comp_with_hv.set(False) ttk.Checkbutton(plot_options_frame, text="", variable=self.show_comp_with_hv, command=disable_comp_buttons).grid(row=3, column=2, sticky="ew", padx=50) ttk.Separator(plot_options_frame, orient='horizontal').grid(row=4, columnspan=5, sticky='ew', pady=5) #Show Best Peak: p ttk.Label(plot_options_frame, text='Show Best Peak:').grid(row=5, column=0, sticky='w', padx=5) self.show_best_peak_hv = tk.BooleanVar() self.show_best_peak_hv.set(True) ttk.Checkbutton(plot_options_frame, text="", variable=self.show_best_peak_hv, command=update_hvplot_call).grid(row=5, column=1, sticky="ew", padx=15) self.show_best_peak_comp = tk.BooleanVar() self.show_best_peak_comp.set(True) bestPeakCompButton=ttk.Checkbutton(plot_options_frame, text="", variable=self.show_best_peak_comp, command=update_hvplot_call) bestPeakCompButton.grid(row=5, column=2, sticky="ew", padx=50) self.show_best_peak_spec = tk.BooleanVar() self.show_best_peak_spec.set(False) ttk.Checkbutton(plot_options_frame, text="", variable=self.show_best_peak_spec, command=update_hvplot_call).grid(row=5, column=3, sticky="ew", padx=25) ttk.Separator(plot_options_frame, orient='horizontal').grid(row=6, columnspan=5, sticky='ew') #Annotate Best Peak: ann ttk.Label(plot_options_frame, text='Annotate Best Peak:').grid(row=7, column=0, sticky='w', padx=5) self.annotate_best_peak_hv = tk.BooleanVar() self.annotate_best_peak_hv.set(True) ttk.Checkbutton(plot_options_frame, text="", variable=self.annotate_best_peak_hv, command=update_hvplot_call).grid(row=7, column=1, sticky="ew", padx=15) self.annotate_best_peak_comp = tk.BooleanVar() self.annotate_best_peak_comp.set(True) bestPeakCompAnnButton=ttk.Checkbutton(plot_options_frame, text="", variable=self.annotate_best_peak_comp, command=update_hvplot_call) bestPeakCompAnnButton.grid(row=7, column=2, sticky="ew", padx=50) self.annotate_best_peak_spec = tk.BooleanVar() self.annotate_best_peak_spec.set(True) ttk.Checkbutton(plot_options_frame, text="", variable=self.annotate_best_peak_spec, command=update_hvplot_call).grid(row=7, column=3, sticky="ew", padx=25) ttk.Separator(plot_options_frame, orient='horizontal').grid(row=8, columnspan=5, sticky='ew') #Show all peaks (main H/V curve): all ttk.Label(plot_options_frame, text='Show All Peaks (H/V Curve):').grid(row=9, column=0, sticky='w', padx=5) self.show_all_peaks_hv = tk.BooleanVar() self.show_all_peaks_hv.set(False) ttk.Checkbutton(plot_options_frame, text="", variable=self.show_all_peaks_hv, command=update_hvplot_call).grid(row=9, column=1, sticky="ew", padx=15) ttk.Separator(plot_options_frame, orient='horizontal').grid(row=10, columnspan=5, sticky='ew') #Show all curves: t ttk.Label(plot_options_frame, text='Show All H/V Curves:').grid(row=11, column=0, sticky='w', padx=5) self.show_ind_curves = tk.BooleanVar() self.show_ind_curves.set(False) ttk.Checkbutton(plot_options_frame, text="", variable=self.show_ind_curves, command=update_hvplot_call).grid(row=11, column=1, sticky="ew", padx=15) ttk.Separator(plot_options_frame, orient='horizontal').grid(row=12, columnspan=5, sticky='ew') #Show individual peaks (tp): tp ttk.Label(plot_options_frame, text='Show Individual Peaks:').grid(row=13, column=0, sticky='w', padx=5) self.show_ind_peaks = tk.BooleanVar() self.show_ind_peaks.set(False) ttk.Checkbutton(plot_options_frame, text="", variable=self.show_ind_peaks, command=update_hvplot_call).grid(row=13, column=1, sticky="ew", padx=15) ttk.Separator(plot_options_frame, orient='horizontal').grid(row=14, columnspan=5, sticky='ew') #Show individual peaks (tp): tp ttk.Label(plot_options_frame, text='Show Standard Deviation:').grid(row=15, column=0, sticky='w', padx=5) self.show_stDev_hv = tk.BooleanVar() self.show_stDev_hv.set(True) ttk.Checkbutton(plot_options_frame, text="", variable=self.show_stDev_hv, command=update_hvplot_call).grid(row=15, column=1, sticky="ew", padx=15) self.show_stDev_comp = tk.BooleanVar() self.show_stDev_comp.set(True) ttk.Checkbutton(plot_options_frame, text="", variable=self.show_stDev_comp, command=update_hvplot_call).grid(row=15, column=2, sticky="ew", padx=50) ttk.Separator(plot_options_frame, orient='horizontal').grid(row=16, columnspan=5, sticky='ew') ttk.Label(plot_options_frame, text='Show Legend:').grid(row=17, column=0, sticky='w', padx=5) self.show_legend = tk.BooleanVar() self.show_legend.set(False) ttk.Checkbutton(plot_options_frame, text="", variable=self.show_legend, command=update_hvplot_call).grid(row=17, column=2, sticky="ew", padx=50) #Specify X-Type ttk.Label(plot_options_frame, text='X Type:').grid(row=18, column=0, sticky='w', padx=5, pady=10) self.x_type = tk.StringVar() self.x_type.set('freq') ttk.Radiobutton(master=plot_options_frame, text='Frequency', variable=self.x_type, value='freq', command=update_hvplot_call).grid(row=18, column=1, sticky='w', padx=(5, 10), pady=10) ttk.Radiobutton(master=plot_options_frame, text='Period', variable=self.x_type, value='period', command=update_hvplot_call).grid(row=18, column=2, sticky='w', padx=(5, 10), pady=10) #kwargs ttk.Label(plot_options_frame, text='Matplotlib Keyword Arguments (not implemented):').grid(row=19, column=0, sticky='w', padx=5, pady=10) self.plot_kwargs = tk.StringVar() self.plot_kwargs.set("cmap='turbo'") ttk.Entry(plot_options_frame, textvariable=self.plot_kwargs).grid(row=19, column=1, columnspan=3, sticky="ew", pady=10) plot_options_frame.pack(fill='both', expand=True)#.grid(row=1, column=0, padx=10, pady=10, sticky="nsew") # Create the plot_hvsr Call LabelFrame hvplot_call_frame = ttk.LabelFrame(plot_settings_tab, text="plot_hvsr() Call") #HVSR def get_kindstr(): if self.hvsr_chart_bool.get(): kindstr_hv = 'HVSR' if self.show_best_peak_hv.get(): kindstr_hv = kindstr_hv + ' p' if self.annotate_best_peak_hv.get(): kindstr_hv = kindstr_hv + ' ann' if self.show_all_peaks_hv.get(): kindstr_hv = kindstr_hv + ' all' if self.show_ind_curves.get(): kindstr_hv = kindstr_hv + ' t' if self.show_ind_peaks.get(): kindstr_hv = kindstr_hv.replace('t', 'tp') if 'tp' not in kindstr_hv: kindstr_hv = kindstr_hv+ ' tp' if not self.show_stDev_hv.get(): kindstr_hv = kindstr_hv + ' -s' else: kindstr_hv = '' #Comp if self.ind_comp_chart_bool.get(): kindstr_c = 'c' if not self.show_comp_with_hv.get(): kindstr_c = kindstr_c + '+' if self.show_best_peak_comp.get(): kindstr_c = kindstr_c + ' p' if self.annotate_best_peak_comp.get(): kindstr_c = kindstr_c + ' ann' if not self.show_stDev_comp.get(): kindstr_c = kindstr_c + ' -s' else: kindstr_c = '' #Specgram if self.spec_chart_bool.get(): kindstr_spec = 'Spec' if self.show_best_peak_spec.get(): kindstr_spec = kindstr_spec + ' p' if self.annotate_best_peak_spec.get(): kindstr_spec = kindstr_spec + ' ann' else: kindstr_spec = '' kindstr = kindstr_hv + ' ' + kindstr_c + ' ' + kindstr_spec return kindstr # Add a Label widget to the plot_hvsr Call Label section hvplot_label = ttk.Label(hvplot_call_frame, text="plot_hvsr({}, remove_method='{}', xtype='{}', show_legend={}, {}, {})".format('hvsr_data', get_kindstr(), self.x_type.get(), self.show_legend.get(), '[...]', 'kwargs')) #Run button frame runFrame_set_plot = ttk.Frame(plot_settings_tab) runFrame_set_plot.columnconfigure(0, weight=1) self.settingsProgBar_plot = ttk.Progressbar(runFrame_set_plot, orient='horizontal') self.settingsProgBar_plot.grid(row=0, column=0, columnspan=10, sticky='ew')#.pack(fill='both',expand=True, side='left', anchor='sw') self.run_button = ttk.Button(runFrame_set_plot, text="Run", style='Run.TButton', command=process_data) def update_results_plot(): self.tab_control.select(self.results_tab) sprit_hvsr.plot_hvsr(self.hvsr_results, plot_type=get_kindstr(), fig=self.fig_results, ax=self.ax_results, show_legend=self.show_legend.get(), use_subplots=True, clear_fig=False) self.update_results_plot_button = ttk.Button(runFrame_set_plot, text="Update Plot", style='Noise.TButton', command=update_results_plot, width=30) self.update_results_plot_button.grid(row=0, column=11, padx=2.5)#pack(side='right', anchor='se') self.run_button.grid(row=0, column=12, padx=2.5)#(side='right', anchor='se', padx=(10,0)) runFrame_set_plot.pack(fill='both', side='bottom', anchor='e') hvplot_label.pack(fill='both', expand=True, padx=(10,0))#.grid(column=0, row=0, padx=10, pady=10, sticky="w") hvplot_call_frame.pack(fill='both', expand=True)#.grid(row=2, column=0, padx=10, pady=10, sticky="nsew") plot_settings_tab.pack(fill='both', expand=True) settings_notebook.add(plot_settings_tab, text="Plot Settings") # Pack the settings Notebook widget settings_notebook.pack(expand=True, fill='both') self.tab_control.add(self.settings_tab, text="Settings") # RESULTS TAB self.results_tab = ttk.Frame(self.tab_control) self.hvsr_results = {'site':''}#Just initialize for now # Create the Batch Site selection LabelFrame self.results_siteSelectFrame = ttk.LabelFrame(self.results_tab, text="HVSR Results") self.results_siteSelectLabel = ttk.Label(self.results_siteSelectFrame, text='Select Site ') def on_site_select(): sitename =self.selectedSite.get() try: report_results(self.hvsr_results[sitename]) except: if sitename=='': pass else: messagebox.showwarning(title='WARNING', message=f"Site {sitename} does not exist") if isinstance(self.hvsr_results, sprit_hvsr.HVSRBatch): sites = self.hvsr_results.sites else: sites = [self.hvsr_results['site']] self.site_options = sites self.selectedSite = tk.StringVar(value=sites[0]) self.site_dropdown = ttk.Combobox(self.results_siteSelectFrame, textvariable=self.selectedSite, values=self.site_options, validate='focusout', validatecommand=on_site_select) self.site_dropdown.config(width=30) self.results_siteSelectLabel.grid(row=0, column=0, columnspan=1, sticky='ew') self.site_dropdown.grid(row=0, column=1, columnspan=4, sticky='ew') self.browse_results_fig = ttk.Button(self.results_siteSelectFrame, text="Update site",command=on_site_select) self.browse_results_fig.grid(row=0, column=8, sticky='ew', padx=5) self.results_siteSelectFrame.columnconfigure(9, weight=1) def update_site_dropdown(): self.site_dropdown['values'] = self.site_options #lambda value=string: self.om_variable.set(value) # Create the plot_hvsr Call LabelFrame self.results_chartFrame = ttk.LabelFrame(self.results_tab, text="Data Plots") #Set up plot self.fig_results = plt.figure() results_mosaic = [['hvsr'],['comp'],['spec']] self.ax_results = self.fig_results.subplot_mosaic(results_mosaic) self.results_canvas = FigureCanvasTkAgg(self.fig_results, master=self.results_chartFrame) # A tk.DrawingArea. self.results_canvas.draw() self.results_canvasWidget = self.results_canvas.get_tk_widget() self.results_toolbar = NavigationToolbar2Tk(self.results_canvas, self.results_chartFrame, pack_toolbar=False) self.results_toolbar.update() self.results_toolbar.pack(fill=tk.X, side=tk.BOTTOM, expand=False) self.results_canvasWidget.pack(fill='both', expand=True) #Peak report self.results_peakInfoFrame = ttk.LabelFrame(self.results_tab, text="Peak Report") self.curveTitleLabel = ttk.Label(self.results_peakInfoFrame, text='Criteria for Reliable H/V Curve (all 3 must pass)') self.curveTest1Label = ttk.Label(self.results_peakInfoFrame, text='Window Length for Frequency') self.curveTest1ResultFrame = ttk.Frame(self.results_peakInfoFrame) self.curveTest1ResultText = ttk.Label(self.curveTest1ResultFrame, text='') self.curveTest1Result = ttk.Label(self.curveTest1ResultFrame, text='') self.curveTest2Label = ttk.Label(self.results_peakInfoFrame, text='Number of Significant Cycles') self.curveTest2ResultFrame = ttk.Frame(self.results_peakInfoFrame) self.curveTest2ResultText = ttk.Label(self.curveTest2ResultFrame, text='') self.curveTest2Result = ttk.Label(self.curveTest2ResultFrame, text='') self.curveTest3Label = ttk.Label(self.results_peakInfoFrame, text='Low Curve Standard Deviation for Frequencies Near Peak Over Time') self.curveTest3ResultFrame = ttk.Frame(self.results_peakInfoFrame) self.curveTest3ResultText = ttk.Label(self.curveTest3ResultFrame, text='') self.curveTest3Result = ttk.Label(self.curveTest3ResultFrame, text='') self.totalCurveResult = ttk.Label(self.results_peakInfoFrame, text='') self.peakTitleLabel = ttk.Label(self.results_peakInfoFrame, text='Criteria for a Clear H/V Peak (5/6 must pass)') self.peakTest1Label = ttk.Label(self.results_peakInfoFrame, text='H/V Amplitude is low Below Peak Frequency') self.peakTest1ResultFrame = ttk.Frame(self.results_peakInfoFrame) self.peakTest1ResultText = ttk.Label(self.peakTest1ResultFrame, text='') self.peakTest1Result = ttk.Label(self.peakTest1ResultFrame, text='') self.peakTest2Label = ttk.Label(self.results_peakInfoFrame, text='H/V Amplitude is low Above Peak Frequency') self.peakTest2ResultFrame = ttk.Frame(self.results_peakInfoFrame) self.peakTest2ResultText = ttk.Label(self.peakTest2ResultFrame, text='') self.peakTest2Result = ttk.Label(self.peakTest2ResultFrame, text='') self.peakTest3Label = ttk.Label(self.results_peakInfoFrame, text='Peak is Prominent') self.peakTest3ResultFrame = ttk.Frame(self.results_peakInfoFrame) self.peakTest3ResultText = ttk.Label(self.peakTest3ResultFrame, text='') self.peakTest3Result = ttk.Label(self.peakTest3ResultFrame, text='') self.peakTest4Label = ttk.Label(self.results_peakInfoFrame, text='Frequency of Peak is Stationary Over Time') self.peakTest4ResultFrame = ttk.Frame(self.results_peakInfoFrame) self.peakTest4ResultText = ttk.Label(self.peakTest4ResultFrame, text='') self.peakTest4Result = ttk.Label(self.peakTest4ResultFrame, text='') self.peakTest5Label = ttk.Label(self.results_peakInfoFrame, text='Standard Deviation of Peak Frequency is low ') self.peakTest5ResultFrame = ttk.Frame(self.results_peakInfoFrame) self.peakTest5ResultText = ttk.Label(self.peakTest5ResultFrame, text='') self.peakTest5Result = ttk.Label(self.peakTest5ResultFrame, text='') self.peakTest6Label = ttk.Label(self.results_peakInfoFrame, text='Standard Deviation of Peak Amplitude is low') self.peakTest6ResultFrame = ttk.Frame(self.results_peakInfoFrame) self.peakTest6ResultText = ttk.Label(self.peakTest6ResultFrame, text='') self.peakTest6Result = ttk.Label(self.peakTest6ResultFrame, text='') self.totalPeakResult = ttk.Label(self.results_peakInfoFrame, text='') self.totalResult = ttk.Label(self.results_peakInfoFrame, text='') self.curveTitleLabel.grid(row=0, sticky='w', padx=5, pady=2.5) self.curveTitleLabel.configure(font=("TkDefaultFont", 12, 'underline', 'bold')) self.curveTest1Label.grid(row=1, sticky='w', padx=5, pady=2.5) self.curveTest1ResultFrame.grid(row=2, sticky='ew', padx=5, pady=2.5) self.curveTest1ResultFrame.columnconfigure(0, weight=1) self.curveTest1ResultFrame.columnconfigure(1, weight=6) self.curveTest1ResultText.grid(row=0, column=0, sticky='e', padx=5, pady=2.5) self.curveTest1Result.grid(row=0, column=1, sticky='e', padx=5, pady=2.5) self.curveTest2Label.grid(row=3, sticky='w', padx=5, pady=2.5) self.curveTest2ResultFrame.grid(row=4, sticky='ew', padx=5, pady=2.5) self.curveTest2ResultFrame.columnconfigure(0, weight=1) self.curveTest2ResultFrame.columnconfigure(1, weight=6) self.curveTest2ResultText.grid(row=0, column=0, sticky='e', padx=5, pady=2.5) self.curveTest2Result.grid(row=0, column=1, sticky='e', padx=5, pady=2.5) self.curveTest3Label.grid(row=5, sticky='w', padx=5, pady=2.5) self.curveTest3ResultFrame.grid(row=6, sticky='ew', padx=5, pady=2.5) self.curveTest3ResultFrame.columnconfigure(0, weight=1) self.curveTest3ResultFrame.columnconfigure(1, weight=6) self.curveTest3ResultText.grid(row=0, column=0, sticky='e', padx=5, pady=2.5) self.curveTest3Result.grid(row=0, column=1, sticky='e', padx=5, pady=2.5) self.totalCurveResult.grid(row=7, sticky='e', padx=5, pady=10 ) ttk.Separator(self.results_peakInfoFrame).grid(row=8, sticky='ew', pady=5) self.peakTitleLabel.grid(row=9, sticky='w', padx=5, pady=2.5) self.peakTitleLabel.configure(font=("TkDefaultFont", 12, 'underline', 'bold')) self.peakTest1Label.grid(row=11, sticky='w', padx=5, pady=2.5) self.peakTest1ResultFrame.grid(row=12, sticky='ew', padx=5, pady=2.5) self.peakTest1ResultFrame.columnconfigure(0, weight=1) self.peakTest1ResultFrame.columnconfigure(1, weight=6) self.peakTest1ResultText.grid(row=0, column=0, sticky='e', padx=5, pady=2.5) self.peakTest1Result.grid(row=0, column=1, sticky='e', padx=5, pady=2.5) self.peakTest2Label.grid(row=13, sticky='w', padx=5, pady=2.5) self.peakTest2ResultFrame.grid(row=14, sticky='ew', padx=5, pady=2.5) self.peakTest2ResultFrame.columnconfigure(0, weight=1) self.peakTest2ResultFrame.columnconfigure(1, weight=6) self.peakTest2ResultText.grid(row=0, column=0, sticky='e', padx=5, pady=2.5) self.peakTest2Result.grid(row=0, column=1, sticky='e', padx=5, pady=2.5) self.peakTest3Label.grid(row=15, sticky='w', padx=5, pady=2.5) self.peakTest3ResultFrame.grid(row=16, sticky='ew', padx=5, pady=2.5) self.peakTest3ResultFrame.columnconfigure(0, weight=1) self.peakTest3ResultFrame.columnconfigure(1, weight=6) self.peakTest3ResultText.grid(row=0, column=0, sticky='e', padx=5, pady=2.5) self.peakTest3Result.grid(row=0, column=1, sticky='e', padx=5, pady=2.5) self.peakTest4Label.grid(row=17, sticky='w', padx=5, pady=2.5) self.peakTest4ResultFrame.grid(row=18, sticky='ew', padx=5, pady=2.5) self.peakTest4ResultFrame.columnconfigure(0, weight=1) self.peakTest4ResultFrame.columnconfigure(1, weight=6) self.peakTest4ResultText.grid(row=0, column=0, sticky='e', padx=5, pady=2.5) self.peakTest4Result.grid(row=0, column=1, sticky='e', padx=5, pady=2.5) self.peakTest5Label.grid(row=19, sticky='w', padx=5, pady=2.5) self.peakTest5ResultFrame.grid(row=20, sticky='ew', padx=5, pady=2.5) self.peakTest5ResultFrame.columnconfigure(0, weight=1) self.peakTest5ResultFrame.columnconfigure(1, weight=6) self.peakTest5ResultText.grid(row=0, column=0, sticky='e', padx=5, pady=2.5) self.peakTest5Result.grid(row=0, column=1, sticky='e', padx=5, pady=2.5) self.peakTest6Label.grid(row=21, sticky='w', padx=5, pady=2.5) self.peakTest6ResultFrame.grid(row=22, sticky='ew', padx=5, pady=2.5) self.peakTest6ResultFrame.columnconfigure(0, weight=1) self.peakTest6ResultFrame.columnconfigure(1, weight=6) self.peakTest6ResultText.grid(row=0, column=0, sticky='e', padx=5, pady=2.5) self.peakTest6Result.grid(row=0, column=1, sticky='e', padx=5, pady=2.5) self.totalPeakResult.grid(row=23, sticky='e', padx=5, pady=10 ) ttk.Separator(self.results_peakInfoFrame).grid(row=24, sticky='ew', pady=5) self.totalResult.grid(row=25, sticky='e', padx=5, pady=10 ) self.resultsProgBar = ttk.Progressbar(self.results_peakInfoFrame, orient='horizontal') self.resultsProgBar.grid(row=26, column=0, sticky='ew') #Export results self.results_export_Frame = ttk.LabelFrame(self.results_tab, text="Export Results") ttk.Label(self.results_export_Frame, text="Export Figure").grid(row=0, column=0, sticky='ew', padx=5) self.results_fig_dir = tk.StringVar() self.results_fig_dir_entry = ttk.Entry(self.results_export_Frame, textvariable=self.results_fig_dir) self.results_fig_dir_entry.grid(row=0, column=1, columnspan=5, sticky='ew') def filepath_results_fig(): filepath = filedialog.asksaveasfilename(defaultextension='png', initialdir=pathlib.Path(self.data_path.get()).parent, initialfile=self.params['site']+'_results.png') if filepath: self.results_fig_dir_entry.delete(0, 'end') self.results_fig_dir_entry.insert(0, filepath) def save_results_fig(): if not self.save_ind_subplots.get(): self.fig_results.savefig(self.results_fig_dir.get()) else: for key in self.ax_results.keys(): extent = self.ax_results[key].get_tightbbox(self.fig_results.canvas.renderer).transformed(self.fig_results.dpi_scale_trans.inverted()) self.fig_results.savefig(pathlib.Path(self.results_fig_dir.get()).parent.as_posix()+'/Subplot'+key+'.png', bbox_inches=extent) self.browse_results_fig = ttk.Button(self.results_export_Frame, text="Browse",command=filepath_results_fig) self.browse_results_fig.grid(row=0, column=7, sticky='ew', padx=2.5) self.save_results_fig = ttk.Button(self.results_export_Frame, text="Save",command=save_results_fig) self.save_results_fig.grid(row=0, column=8, columnspan=2, sticky='ew', padx=2.5) #Save subplots individually self.save_ind_subplots = tk.BooleanVar() self.save_ind_subplots.set(False) ttk.Checkbutton(self.results_export_Frame, text="Save ind. subplots", variable=self.save_ind_subplots).grid(row=0, column=10, sticky="ew", padx=5) #Export Peak Report ttk.Label(self.results_export_Frame, text="Export Peak Report").grid(row=1, column=0, sticky='ew', padx=5) self.results_report_dir = tk.StringVar() self.results_report_dir_entry = ttk.Entry(self.results_export_Frame, textvariable=self.results_report_dir) self.results_report_dir_entry.grid(row=1, column=1, columnspan=5, sticky='ew') def filepath_report_fig(): filepath = filedialog.asksaveasfilename(defaultextension='csv', initialdir=pathlib.Path(self.data_path.get()).parent, initialfile=self.params['site']+'_peakReport.csv') if filepath: self.results_report_dir_entry.delete(0, 'end') self.results_report_dir_entry.insert(0, filepath) def save_report_fig(): sprit_hvsr.get_report(self.hvsr_results, format='plot', export=self.results_report_dir.get()) self.browse_results_fig = ttk.Button(self.results_export_Frame, text="Browse",command=filepath_report_fig) self.browse_results_fig.grid(row=1, column=7, sticky='ew', padx=2.5) self.save_results_fig = ttk.Button(self.results_export_Frame, text="Save",command=save_report_fig) self.save_results_fig.grid(row=1, column=8, columnspan=2, sticky='ew', padx=2.5) self.results_export_Frame.columnconfigure(1, weight=1) self.results_siteSelectFrame.grid(row=0,column=0, columnspan=8, rowspan=2, sticky='ew') self.results_peakInfoFrame.grid(row=0, column=9, columnspan=2, rowspan=8, sticky='nsew')#.pack(side='right', fill='both') self.results_chartFrame.grid(row=2, column=0, columnspan=8, rowspan=6, sticky='nsew')#.pack(side='top', expand=True, fill='both') self.results_export_Frame.grid(row=9, column=0, columnspan=11,rowspan=2,sticky='nsew')#.pack(side='bottom', fill='x') self.results_tab.columnconfigure(0, weight=1) self.results_tab.rowconfigure(2, weight=1) # LOG TAB self.log_tab = ttk.Frame(self.tab_control) from tkinter import scrolledtext self.logFrame = ttk.LabelFrame(self.log_tab, text='Log') self.logFrame.columnconfigure(0, weight=1) self.logFrame.rowconfigure(0, weight=1) self.log_text = scrolledtext.ScrolledText(self.logFrame, wrap = tk.WORD)#, width=200, height=50) self.log_text.configure(font=("Courier", 11)) #text_area.grid(row=0, column=0, sticky='nsew') self.log_text.grid(row=0, rowspan=10, column=0, sticky='nsew')#.pack(fill='both', expand=True) self.logProgBar = ttk.Progressbar(self.logFrame, orient='horizontal') self.logProgBar.grid(row=11, column=0, sticky='nsew') introLogText = "Log of active session:\n" self.log_text.insert('end', introLogText) #log_text.configure(bg='black', fg='white') self.logFrame.pack(fill='both', expand=True)#.pack(fill='both', expand=True, side='top', anchor='nw') self.log_tab.pack(fill='both', expand=True, side='left', anchor='nw') # Add log tab to tab control self.tab_control.add(self.log_tab, text="Log") # Add result tab to tab control self.tab_control.add(self.results_tab, text="Results".center(11, ' ').center(13,'|')) # Pack tab control self.tab_control.pack(expand=True, fill="both")
Methods
def create_tabs(self)
def log_errorMsg(self, logMsg)
def manual_label_update(self)