Source code for xtb_step.tk_frequencies

# -*- coding: utf-8 -*-

"""The graphical part of an xTB Frequencies step.

Inherits from :class:`TkOptimization` to reuse the energy frame and
the optimization frame, since xtb's recommended frequency invocation
is ``--ohess`` (optimize-then-Hessian). Adds its own "frequencies
frame" below for the frequency / thermochemistry-specific parameters.
"""

import pprint  # noqa: F401
import tkinter as tk
import tkinter.ttk as ttk

import xtb_step  # noqa: F401, E999
from .tk_optimization import TkOptimization
from seamm_util import ureg, Q_, units_class  # noqa: F401, E999
import seamm_widgets as sw


[docs] class TkFrequencies(TkOptimization): """The graphical part of a Frequencies step in a flowchart. See Also -------- TkOptimization, TkEnergy, Frequencies, FrequenciesParameters """
[docs] def create_dialog(self, title="xTB Frequencies"): """Create the dialog: energy + optimization frames from parents, plus a frequencies frame. """ # Let parents build the energy and optimization frames. frame = super().create_dialog(title=title) P = self.node.parameters # Frequencies frame f_frame = self["frequencies frame"] = ttk.LabelFrame( frame, borderwidth=4, relief="sunken", text="Frequencies / Thermochemistry", labelanchor="n", padding=10, ) # Skip the parents' keys so we only create the frequencies-specific # widgets in this frame. parent_keys = set(xtb_step.OptimizationParameters.parameters) | set( xtb_step.EnergyParameters.parameters ) skip = parent_keys | {"results", "extra keywords", "create tables"} for key in xtb_step.FrequenciesParameters.parameters: if key in skip: continue self[key] = P[key].widget(f_frame) # Bind 'optimize first' so toggling it can hide the optimization # frame in future iterations. For v1 we just trigger reset_dialog # so any future logic gets called. if "optimize first" in self: of = self["optimize first"] if hasattr(of, "combobox"): of.combobox.bind("<<ComboboxSelected>>", self.reset_dialog) of.combobox.bind("<Return>", self.reset_dialog) of.combobox.bind("<FocusOut>", self.reset_dialog) # Note: do NOT call self.reset_dialog() here -- the seamm framework # does it after create_dialog returns. See TkEnergy for details. return frame
[docs] def reset_dialog(self, widget=None): """Layout: energy frame, optimization frame (parents), then ours.""" # Parents lay out energy (row 0) and optimization (row 1). row = super().reset_dialog() # Place our frequencies frame below. self["frequencies frame"].grid(row=row, column=0, sticky=tk.EW, pady=5) row += 1 self.reset_frequencies_frame() return row
[docs] def reset_frequencies_frame(self, widget=None): """Layout the widgets inside the frequencies frame.""" f_frame = self["frequencies frame"] for slave in f_frame.grid_slaves(): slave.grid_forget() row = 0 widgets = [] parent_keys = set(xtb_step.OptimizationParameters.parameters) | set( xtb_step.EnergyParameters.parameters ) skip = parent_keys | {"results", "extra keywords", "create tables"} for key in xtb_step.FrequenciesParameters.parameters: if key in skip: continue self[key].grid(row=row, column=0, sticky=tk.EW) widgets.append(self[key]) row += 1 sw.align_labels(widgets, sticky=tk.E) return row