diff --git a/.github/workflows/on-pr-open.yml b/.github/workflows/on-pr-open.yml index 4415b4c25..436d3b0c3 100644 --- a/.github/workflows/on-pr-open.yml +++ b/.github/workflows/on-pr-open.yml @@ -15,6 +15,7 @@ on: jobs: good-pr-title: + permissions: write-all name: Ensure Conventional PR Title runs-on: ubuntu-latest steps: @@ -24,13 +25,14 @@ jobs: success-state: Conventional commits compliant title detected. failure-state: Pull request title is not conventional commits compliant! env: - GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} + GITHUB_TOKEN: ${{ secrets.RAMSTK_PAT }} pr-labeler: + permissions: write-all name: Label Pull Request from Branch Name runs-on: ubuntu-latest steps: - name: Apply Labels to PR uses: TimonVS/pr-labeler-action@v4 env: - GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} + GITHUB_TOKEN: ${{ secrets.RAMSTK_PAT }} diff --git a/setup.cfg b/setup.cfg deleted file mode 100644 index fa7f378b4..000000000 --- a/setup.cfg +++ /dev/null @@ -1,38 +0,0 @@ -[compile_catalog] -domain = ramstk -directory = locale - -[extract_messages] -input_dirs = src/ramstk/ -output_file = locale/rtk.pot - -[pycodestyle] -count = True -exclude = - .git, - .tox, - *.pyc, - *.pyo, - build, - dist, - *.egg-info - config, - docs, - locale, - tests, - tools -format = pylint -ignore = - C326, - C330 - E121, - E123, - E126, - E133, - E242, - E265, - E402, - W503, - W504 -max-line-length = 88 -statistics = True diff --git a/src/ramstk/models/dbrecords/programdb_revision_record.py b/src/ramstk/models/dbrecords/programdb_revision_record.py index 100c3e7a1..f452c1d31 100644 --- a/src/ramstk/models/dbrecords/programdb_revision_record.py +++ b/src/ramstk/models/dbrecords/programdb_revision_record.py @@ -244,6 +244,11 @@ class RAMSTKRevisionRecord(RAMSTK_BASE, RAMSTKBaseRecord): # type: ignore backref="revision", passive_deletes=True, ) + matrix: relationship = relationship( + "RAMSTKMatrixRecord", + backref="revision", + passive_deletes=True, + ) def get_attributes(self): """Retrieve current values of the RAMSTKRevision data model attributes. diff --git a/src/ramstk/models/dbtables/basetable.py b/src/ramstk/models/dbtables/basetable.py index d4b2872e0..5214ae059 100644 --- a/src/ramstk/models/dbtables/basetable.py +++ b/src/ramstk/models/dbtables/basetable.py @@ -6,7 +6,9 @@ # Copyright since 2007 Doyle "weibullguy" Rowland doyle.rowland reliaqual com """Metaclass for the database table models.""" + # Standard Library Imports +import contextlib from datetime import date from typing import Any, Callable, Dict, List, Type, Union @@ -216,9 +218,10 @@ def do_insert( """ try: _record = self.do_get_new_record(attributes) + attributes.pop(self.pkey) for _id in self._lst_id_columns: - attributes.pop(_id) - + with contextlib.suppress(KeyError): + attributes.pop(_id) _record.set_attributes(attributes) # type: ignore _identifier = self.last_id + 1 @@ -242,6 +245,7 @@ def do_insert( logger_name="DEBUG", message=str(_error.msg), ) + except NodeIDAbsentError as _error: pub.sendMessage( "do_log_debug_msg", @@ -324,7 +328,7 @@ def do_set_attributes( :param node_id: the ID of the record in the RAMSTK Program database table whose attributes are to be set. - :param package: the key:value pair of the attribute to set. + :param package: the key:value pair for the attribute to set. :return: None :rtype: None """ @@ -342,12 +346,11 @@ def do_set_attributes( ) _attributes = {} + with contextlib.suppress(KeyError): + _attributes.pop(self.pkey) for _field in self._lst_id_columns: - try: + with contextlib.suppress(KeyError): _attributes.pop(_field) - except KeyError: - pass - if _key in _attributes: _attributes[_key] = _value @@ -455,9 +458,7 @@ def _do_remove_tree_node(self, node_id: int) -> None: :return: None :rtype: None """ - try: + with contextlib.suppress(NodeIDAbsentError): for _node in self.tree.children(node_id): self.dao.do_delete(self.do_select(_node.identifier)) self.tree.remove_node(node_id) - except NodeIDAbsentError: - pass diff --git a/src/ramstk/models/dbtables/programdb_validation_table.py b/src/ramstk/models/dbtables/programdb_validation_table.py index f211b41c4..555aa52f0 100644 --- a/src/ramstk/models/dbtables/programdb_validation_table.py +++ b/src/ramstk/models/dbtables/programdb_validation_table.py @@ -64,13 +64,14 @@ def __init__(self, **kwargs: Dict[Any, Union[float, int, str]]) -> None: # Subscribe to PyPubSub messages. pub.subscribe(self.do_calculate_plan, "request_calculate_plan") - pub.subscribe(self._do_calculate_task, "request_calculate_validation_task") + pub.subscribe(self._do_calculate_task, + "request_calculate_validation_task") pub.subscribe( self._do_calculate_all_tasks, "request_calculate_all_validation_tasks", ) - # pylint: disable=method-hidden + # pylint: disable=method-hidden, invalid-name def do_get_new_record( self, attributes: Dict[str, Union[date, float, int, str]] ) -> RAMSTKValidationRecord: @@ -81,12 +82,12 @@ def do_get_new_record( :return: None :rtype: None """ - _new_record = self._record() - _new_record.revision_id = attributes["revision_id"] - _new_record.validation_id = self.last_id + 1 - _new_record.name = "New Validation Task" + _new_record_obj = self._record() + _new_record_obj.revision_id = attributes["revision_id"] + _new_record_obj.validation_id = self.last_id + 1 + _new_record_obj.name = f"New Validation Task {self.last_id + 1}" - return _new_record + return _new_record_obj def do_calculate_plan(self) -> None: """Calculate the planned burndown of the overall validation effort. @@ -99,47 +100,47 @@ def do_calculate_plan(self) -> None: :return: _planned; the pandas DataFrame() containing the planned burndown hours for the entire validation effort. """ - _dic_planned = {} # type: ignore - _time_ll = 0.0 - _time_mean = 0.0 - _time_ul = 0.0 - _start_date = date.today() + _planned_dic = {} # type: ignore + _time_ll_flt = 0.0 + _time_mean_flt = 0.0 + _time_ul_flt = 0.0 + _start_date_obj = date.today() - for _node in self.tree.all_nodes()[1:]: + for _node_obj in self.tree.all_nodes()[1:]: # Calculate the three times if the mean task time is zero. - if _node.data["validation"].time_mean <= 0.0: - _node.data["validation"].calculate_task_time() + if _node_obj.data["validation"].time_mean <= 0.0: + _node_obj.data["validation"].calculate_task_time() # Keep a running total of the three times and the earliest task # start date. The earliest start date will be assigned the # total number of hours in the validation program. - _start_date = min( - _start_date, - pd.to_datetime(_node.data["validation"].date_start), + _start_date_obj = min( + _start_date_obj, + pd.to_datetime(_node_obj.data["validation"].date_start), ) - _time_ll += _node.data["validation"].time_ll - _time_mean += _node.data["validation"].time_mean - _time_ul += _node.data["validation"].time_ul + _time_ll_flt += _node_obj.data["validation"].time_ll + _time_mean_flt += _node_obj.data["validation"].time_mean + _time_ul_flt += _node_obj.data["validation"].time_ul # Calculate the sum of task hours for each, unique end date. - _end_date = _node.data["validation"].date_end + _end_date_obj = _node_obj.data["validation"].date_end try: # Update the end date's times. - _dic_planned[pd.to_datetime(_end_date)][0] += _node.data[ + _planned_dic[pd.to_datetime(_end_date_obj)][0] += _node_obj.data[ "validation" ].time_ll - _dic_planned[pd.to_datetime(_end_date)][1] += _node.data[ + _planned_dic[pd.to_datetime(_end_date_obj)][1] += _node_obj.data[ "validation" ].time_mean - _dic_planned[pd.to_datetime(_end_date)][2] += _node.data[ + _planned_dic[pd.to_datetime(_end_date_obj)][2] += _node_obj.data[ "validation" ].time_ul except KeyError: # Add the first time to the end date. - _dic_planned[pd.to_datetime(_end_date)] = [ - _node.data["validation"].time_ll, - _node.data["validation"].time_mean, - _node.data["validation"].time_ul, + _planned_dic[pd.to_datetime(_end_date_obj)] = [ + _node_obj.data["validation"].time_ll, + _node_obj.data["validation"].time_mean, + _node_obj.data["validation"].time_ul, ] # Create a pandas DataFrame() of the task times sorted by date in @@ -148,26 +149,27 @@ def do_calculate_plan(self) -> None: # the validation effort, not the total task hours planned to # complete on each day. # noinspection PyTypeChecker - _planned = pd.DataFrame( - _dic_planned.values(), - index=_dic_planned.keys(), + _planned_df = pd.DataFrame( + _planned_dic.values(), + index=_planned_dic.keys(), columns=["lower", "mean", "upper"], ).sort_index(ascending=False) # Calculate the total task time remaining on each planned end date # and then sort the DataFrame() by date in ascending order. - _planned = _planned.cumsum() - _planned - _planned.loc[_start_date] = [_time_ll, _time_mean, _time_ul] - _planned = _planned.sort_index() + _planned_df = _planned_df.cumsum() - _planned_df + _planned_df.loc[_start_date_obj] = [ + _time_ll_flt, _time_mean_flt, _time_ul_flt] + _planned_df = _planned_df.sort_index() - _dic_plan = { - "plan": _planned, + _planned_dic = { + "plan": _planned_df, "assessed": self._do_select_assessment_targets(), } pub.sendMessage( "succeed_calculate_verification_plan", - attributes=_dic_plan, + attributes=_planned_dic, ) def _do_calculate_all_tasks(self) -> None: @@ -180,17 +182,17 @@ def _do_calculate_all_tasks(self) -> None: :return: None :rtype: None """ - _program_cost_remaining = 0.0 - _program_time_remaining = 0.0 + _program_cost_remaining_flt = 0.0 + _program_time_remaining_flt = 0.0 - for _node in self.tree.all_nodes()[1:]: - self._do_calculate_task(_node.identifier) + for _node_obj in self.tree.all_nodes()[1:]: + self._do_calculate_task(_node_obj.identifier) - _program_cost_remaining += _node.data["validation"].cost_average * ( - 1.0 - _node.data["validation"].status / 100.0 + _program_cost_remaining_flt += _node_obj.data["validation"].cost_average * ( + 1.0 - _node_obj.data["validation"].status / 100.0 ) - _program_time_remaining += _node.data["validation"].time_average * ( - 1.0 - _node.data["validation"].status / 100.0 + _program_time_remaining_flt += _node_obj.data["validation"].time_average * ( + 1.0 - _node_obj.data["validation"].status / 100.0 ) pub.sendMessage( @@ -199,8 +201,8 @@ def _do_calculate_all_tasks(self) -> None: ) pub.sendMessage( "succeed_calculate_program_remaining", - cost_remaining=_program_cost_remaining, - time_remaining=_program_time_remaining, + cost_remaining=_program_cost_remaining_flt, + time_remaining=_program_time_remaining_flt, ) def _do_calculate_task(self, node_id: int) -> None: @@ -213,19 +215,19 @@ def _do_calculate_task(self, node_id: int) -> None: :return: None :rtype: None """ - _node = self.tree.get_node(node_id) + _node_obj = self.tree.get_node(node_id) - _node.data["validation"].calculate_task_time() - _node.data["validation"].calculate_task_cost() + _node_obj.data["validation"].calculate_task_time() + _node_obj.data["validation"].calculate_task_cost() - _attributes = _node.data["validation"].get_attributes() + _attribute_dic = _node_obj.data["validation"].get_attributes() self.do_set_attributes_all( - attributes=_attributes, + attributes=_attribute_dic, ) pub.sendMessage( "succeed_calculate_validation_task", - attributes=_attributes, + attributes=_attribute_dic, ) def _do_select_assessment_targets(self) -> pd.DataFrame: @@ -234,19 +236,19 @@ def _do_select_assessment_targets(self) -> pd.DataFrame: :return: _assessed; a pandas DataFrame() containing the assessment dates as the index and associated targets. """ - _dic_assessed = { - pd.to_datetime(_node.data["validation"].date_end): [ - _node.data["validation"].acceptable_minimum, - _node.data["validation"].acceptable_mean, - _node.data["validation"].acceptable_maximum, + _assessed_dic = { + pd.to_datetime(_node_obj.data["validation"].date_end): [ + _node_obj.data["validation"].acceptable_minimum, + _node_obj.data["validation"].acceptable_mean, + _node_obj.data["validation"].acceptable_maximum, ] - for _node in self.tree.all_nodes()[1:] - if _node.data["validation"].task_type == 5 + for _node_obj in self.tree.all_nodes()[1:] + if _node_obj.data["validation"].task_type == 5 } # noinspection PyTypeChecker return pd.DataFrame( - _dic_assessed.values(), - index=_dic_assessed.keys(), + _assessed_dic.values(), + index=_assessed_dic.keys(), columns=["lower", "mean", "upper"], ).sort_index() diff --git a/src/ramstk/views/gtk3/allocation/panel.py b/src/ramstk/views/gtk3/allocation/panel.py index 85654f81a..60d7df45f 100644 --- a/src/ramstk/views/gtk3/allocation/panel.py +++ b/src/ramstk/views/gtk3/allocation/panel.py @@ -188,11 +188,11 @@ def _do_set_sensitive(self, attributes: Dict[str, Union[float, int, str]]) -> No """ self.cmbAllocationGoal.set_sensitive(True) self.cmbAllocationGoal.do_update( - attributes["goal_measure_id"], signal="changed" + attributes["goal_measure_id"], ) self.cmbAllocationMethod.set_sensitive(True) self.cmbAllocationMethod.do_update( - attributes["allocation_method_id"], signal="changed" + attributes["allocation_method_id"], ) self.txtReliabilityGoal.set_sensitive(False) self.txtMTBFGoal.set_sensitive(False) @@ -202,19 +202,16 @@ def _do_set_sensitive(self, attributes: Dict[str, Union[float, int, str]]) -> No self.txtReliabilityGoal.set_sensitive(True) self.txtReliabilityGoal.do_update( attributes["reliability_goal"], - signal="changed", ) elif self._goal_id == 2: # Expressed as a hazard rate. self.txtHazardRateGoal.set_sensitive(True) self.txtHazardRateGoal.do_update( attributes["hazard_rate_goal"], - signal="changed", ) elif self._goal_id == 3: # Expressed as an MTBF. self.txtMTBFGoal.set_sensitive(True) self.txtMTBFGoal.do_update( attributes["mtbf_goal"], - signal="changed", ) def _on_goal_changed(self, combo: RAMSTKComboBox) -> None: diff --git a/src/ramstk/views/gtk3/books/modulebook.py b/src/ramstk/views/gtk3/books/modulebook.py index ac23fb889..b6a610cfb 100644 --- a/src/ramstk/views/gtk3/books/modulebook.py +++ b/src/ramstk/views/gtk3/books/modulebook.py @@ -21,7 +21,7 @@ from ramstk.views.gtk3.hardware import HardwareModuleView from ramstk.views.gtk3.requirement import RequirementModuleView from ramstk.views.gtk3.revision import RevisionModuleView -from ramstk.views.gtk3.validation import ValidationModuleView +from ramstk.views.gtk3.validation import RAMSTKValidationModuleView from ramstk.views.gtk3.widgets import RAMSTKBaseBook @@ -52,7 +52,7 @@ def __init__( "function": FunctionModuleView(configuration, logger), "requirement": RequirementModuleView(configuration, logger), "hardware": HardwareModuleView(configuration, logger), - "validation": ValidationModuleView(configuration, logger), + "validation": RAMSTKValidationModuleView(configuration, logger), } # Initialize private list attributes. diff --git a/src/ramstk/views/gtk3/books/workbook.py b/src/ramstk/views/gtk3/books/workbook.py index c49010a31..37327a150 100644 --- a/src/ramstk/views/gtk3/books/workbook.py +++ b/src/ramstk/views/gtk3/books/workbook.py @@ -6,7 +6,9 @@ # Copyright since 2007 Doyle "weibullguy" Rowland doyle.rowland reliaqual com """GTK3 Work Book.""" + # Standard Library Imports +import contextlib from typing import Dict, List # Third Party Imports @@ -35,7 +37,10 @@ from ramstk.views.gtk3.similar_item import SimilarItemWorkView from ramstk.views.gtk3.stakeholder import StakeholderWorkView from ramstk.views.gtk3.usage_profile import UsageProfileWorkView -from ramstk.views.gtk3.validation import ValidationGeneralDataView +from ramstk.views.gtk3.validation import ( + RAMSTKValidationGeneralDataView, + RAMSTKValidationMatrixView, +) from ramstk.views.gtk3.widgets import RAMSTKBaseBook, RAMSTKBaseView @@ -87,8 +92,9 @@ def __init__( PoFWorkView(configuration, logger), ], "validation": [ - ValidationGeneralDataView(configuration, logger), + RAMSTKValidationGeneralDataView(configuration, logger), ProgramStatusWorkView(configuration, logger), + RAMSTKValidationMatrixView(configuration, logger), ], } @@ -110,8 +116,6 @@ def _on_module_change(self, module: str = "") -> None: for _page in self.get_children(): self.remove(_page) - try: + with contextlib.suppress(KeyError): for _workspace in self.dic_work_views[module]: self.insert_page(_workspace, _workspace.hbx_tab_label, -1) - except KeyError: - pass diff --git a/src/ramstk/views/gtk3/design_electric/components/capacitor.py b/src/ramstk/views/gtk3/design_electric/components/capacitor.py index d248beeeb..759fb94f9 100644 --- a/src/ramstk/views/gtk3/design_electric/components/capacitor.py +++ b/src/ramstk/views/gtk3/design_electric/components/capacitor.py @@ -635,29 +635,36 @@ def do_load_comboboxes(self, subcategory_id: int) -> None: except KeyError: _quality = [] - self.cmbQuality.do_load_combo(_quality, signal="changed") + self.cmbQuality.do_load_combo( + _quality, + ) try: _specification: List[Any] = self._dic_specifications[self.subcategory_id] except KeyError: _specification = [] - self.cmbSpecification.do_load_combo(_specification, signal="changed") + self.cmbSpecification.do_load_combo( + _specification, + ) - self.cmbStyle.do_load_combo([], signal="changed") + self.cmbStyle.do_load_combo( + [], + ) self.cmbConfiguration.do_load_combo( - [[_("Fixed")], [_("Variable")]], signal="changed" + [[_("Fixed")], [_("Variable")]], ) - _construction: List[Any] = [ - [_("Slug, All Tantalum")], - [_("Foil, Hermetic")], - [_("Slug, Hermetic")], - [_("Foil, Non-Hermetic")], - [_("Slug, Non-Hermetic")], - ] - self.cmbConstruction.do_load_combo(_construction, signal="changed") + self.cmbConstruction.do_load_combo( + [ + [_("Slug, All Tantalum")], + [_("Foil, Hermetic")], + [_("Slug, Hermetic")], + [_("Foil, Non-Hermetic")], + [_("Slug, Non-Hermetic")], + ], + ) self._do_set_sensitive() @@ -674,7 +681,6 @@ def _do_set_reliability_attributes(self, attributes: Dict[str, Any]) -> None: self.cmbQuality.set_sensitive(True) self.cmbQuality.do_update( self._quality_id, - signal="changed", ) self._do_set_sensitive() @@ -696,7 +702,9 @@ def _do_load_styles(self, combo: RAMSTKComboBox) -> None: _styles = self._dic_styles[self.subcategory_id] except KeyError: _styles = [] - self.cmbStyle.do_load_combo(entries=_styles, signal="changed") + self.cmbStyle.do_load_combo( + entries_lst=_styles, + ) def _do_set_sensitive(self) -> None: """Set widget sensitivity as needed for the selected capacitor type. diff --git a/src/ramstk/views/gtk3/design_electric/components/connection.py b/src/ramstk/views/gtk3/design_electric/components/connection.py index 9ec5232f6..522941964 100644 --- a/src/ramstk/views/gtk3/design_electric/components/connection.py +++ b/src/ramstk/views/gtk3/design_electric/components/connection.py @@ -435,14 +435,18 @@ def do_load_comboboxes(self, subcategory_id: int) -> None: _data = self._dic_quality[self.subcategory_id] except KeyError: _data = [] - self.cmbQuality.do_load_combo(_data, signal="changed") + self.cmbQuality.do_load_combo( + _data, + ) # Load the connector type RAMSTKComboBox(). try: _data = self._dic_type[self.subcategory_id] except KeyError: _data = [] - self.cmbType.do_load_combo(_data, signal="changed") + self.cmbType.do_load_combo( + _data, + ) # Clear the remaining ComboBox()s. These are loaded dynamically # based on the selection made in other ComboBox()s. @@ -467,7 +471,9 @@ def _do_load_insert(self, combo: RAMSTKComboBox) -> None: _inserts = self._dic_insert[_type_id][_spec_id] except KeyError: _inserts = [] - self.cmbInsert.do_load_combo(entries=_inserts, signal="changed") + self.cmbInsert.do_load_combo( + entries_lst=_inserts, + ) def _do_load_specification(self, combo: RAMSTKComboBox) -> None: """Retrieve RAMSTKCombo() changes and assign to Connection attribute. @@ -482,7 +488,9 @@ def _do_load_specification(self, combo: RAMSTKComboBox) -> None: _specifications = self._dic_specification[_type_id] except KeyError: _specifications = [] - self.cmbSpecification.do_load_combo(entries=_specifications, signal="changed") + self.cmbSpecification.do_load_combo( + entries_lst=_specifications, + ) def _do_set_reliability_attributes(self, attributes: Dict[str, Any]) -> None: """Set the attributes when the reliability attributes are retrieved. @@ -497,7 +505,6 @@ def _do_set_reliability_attributes(self, attributes: Dict[str, Any]) -> None: self.cmbQuality.set_sensitive(True) self.cmbQuality.do_update( self._quality_id, - signal="changed", ) self._do_set_sensitive() diff --git a/src/ramstk/views/gtk3/design_electric/components/inductor.py b/src/ramstk/views/gtk3/design_electric/components/inductor.py index 01df2a894..a689e9fed 100644 --- a/src/ramstk/views/gtk3/design_electric/components/inductor.py +++ b/src/ramstk/views/gtk3/design_electric/components/inductor.py @@ -248,7 +248,7 @@ def do_load_comboboxes(self, subcategory_id: int) -> None: self.__do_load_specification_combobox() self.cmbConstruction.do_load_combo( - [[_("Fixed")], [_("Variable")]], signal="changed" + [[_("Fixed")], [_("Variable")]], ) self._do_set_sensitive() @@ -263,21 +263,25 @@ def _do_load_panel(self, attributes: Dict[str, Any]) -> None: """ super().do_load_common(attributes) - self.cmbFamily.do_update(attributes["family_id"], signal="changed") + self.cmbFamily.do_update( + attributes["family_id"], + ) if self._hazard_rate_method_id == 2: self.cmbSpecification.do_update( - attributes["specification_id"], signal="changed" + attributes["specification_id"], + ) + self.cmbInsulation.do_update( + attributes["insulation_id"], ) - self.cmbInsulation.do_update(attributes["insulation_id"], signal="changed") self.cmbConstruction.do_update( - attributes["construction_id"], signal="changed" + attributes["construction_id"], ) self.txtArea.do_update( - str(self.fmt.format(attributes["area"])), signal="changed" + str(self.fmt.format(attributes["area"])), ) self.txtWeight.do_update( - str(self.fmt.format(attributes["weight"])), signal="changed" + str(self.fmt.format(attributes["weight"])), ) # noqa def _do_set_reliability_attributes(self, attributes: Dict[str, Any]) -> None: @@ -293,7 +297,6 @@ def _do_set_reliability_attributes(self, attributes: Dict[str, Any]) -> None: self.cmbQuality.set_sensitive(True) self.cmbQuality.do_update( self._quality_id, - signal="changed", ) self._do_set_sensitive() @@ -351,7 +354,9 @@ def __do_load_family_combobox(self) -> None: [_("Power Transformer or Filter")], [_("RF Transformer")], ] - self.cmbFamily.do_load_combo(_data, signal="changed") + self.cmbFamily.do_load_combo( + _data, + ) def __do_load_insulation_combobox(self) -> None: """Load the insulation RAMSTKComboBox(). @@ -363,7 +368,9 @@ def __do_load_insulation_combobox(self) -> None: _data = self._dic_insulation[self.subcategory_id] except KeyError: _data = [] - self.cmbInsulation.do_load_combo(_data, signal="changed") + self.cmbInsulation.do_load_combo( + _data, + ) def __do_load_quality_combobox(self) -> None: """Load the quality RAMSTKComboBox(). @@ -382,7 +389,9 @@ def __do_load_quality_combobox(self) -> None: _data = self._dic_quality[self.subcategory_id] except KeyError: _data = [] - self.cmbQuality.do_load_combo(_data, signal="changed") + self.cmbQuality.do_load_combo( + _data, + ) def __do_load_specification_combobox(self) -> None: """Load the specification RAMSTKComboBox(). @@ -394,4 +403,6 @@ def __do_load_specification_combobox(self) -> None: _data = self._dic_specifications[self.subcategory_id] except KeyError: _data = [] - self.cmbSpecification.do_load_combo(_data, signal="changed") + self.cmbSpecification.do_load_combo( + _data, + ) diff --git a/src/ramstk/views/gtk3/design_electric/components/integrated_circuit.py b/src/ramstk/views/gtk3/design_electric/components/integrated_circuit.py index 87c016d8e..8934574b4 100644 --- a/src/ramstk/views/gtk3/design_electric/components/integrated_circuit.py +++ b/src/ramstk/views/gtk3/design_electric/components/integrated_circuit.py @@ -7,7 +7,9 @@ # Copyright since 2007 Doyle "weibullguy" Rowland doyle.rowland reliaqual com """Integrated Circuit Input Panel.""" + # Standard Library Imports +import contextlib from typing import Any, Dict, List # Third Party Imports @@ -430,7 +432,7 @@ def do_load_comboboxes(self, subcategory_id: int) -> None: # Load the Construction RAMSTKComboBox(). self.cmbConstruction.do_load_combo( - [["FLOTOX"], [_("Textured Poly")]], signal="changed" + [["FLOTOX"], [_("Textured Poly")]], ) # Load the error correction code RAMSTKComboBox(). @@ -440,12 +442,11 @@ def do_load_comboboxes(self, subcategory_id: int) -> None: [_("On-chip Hamming code")], [_("Two-Needs-One redundant cell approach")], ], - signal="changed", ) # Load the manufacturing process RAMSTKComboBox(). self.cmbManufacturing.do_load_combo( - [["QML or QPL"], ["Non-QML or non-QPL"]], signal="changed" + [["QML or QPL"], ["Non-QML or non-QPL"]], ) # Load the package RAMSTKComboBox(). @@ -461,7 +462,6 @@ def do_load_comboboxes(self, subcategory_id: int) -> None: [_("Nonhermetic Pin Grid Array (PGA)")], [_("Nonhermetic SMT")], ], - signal="changed", ) # Load the technology RAMSTKComboBox(). @@ -475,14 +475,18 @@ def do_load_comboboxes(self, subcategory_id: int) -> None: _data = self._dic_technology[subcategory_id] except KeyError: _data = [] - self.cmbTechnology.do_load_combo(_data, signal="changed") + self.cmbTechnology.do_load_combo( + _data, + ) # Load the device type RAMSTKComboBox(). try: _data = self._dic_types[subcategory_id] except KeyError: _data = [] - self.cmbType.do_load_combo(_data, signal="changed") + self.cmbType.do_load_combo( + _data, + ) self._do_set_sensitive() @@ -499,7 +503,6 @@ def _do_set_reliability_attributes(self, attributes: Dict[str, Any]) -> None: self.cmbQuality.set_sensitive(True) self.cmbQuality.do_update( self._quality_id, - signal="changed", ) self._do_set_sensitive() @@ -539,12 +542,9 @@ def _do_set_sensitive(self) -> None: 9: self.__do_set_gaas_sensitive, 10: self.__do_set_vhsic_vlsi_sensitive, } - try: + with contextlib.suppress(KeyError): # noinspection PyArgumentList _dic_method[self.subcategory_id]() - except KeyError: - pass - if self._hazard_rate_method_id == 2: # MIL-HDBK-217F, Part Stress self.cmbPackage.set_sensitive(True) self.txtNElements.set_sensitive(True) @@ -563,12 +563,10 @@ def _do_load_application_combo(self, attributes: Dict[str, Any]) -> None: [_("Driver and High Power (> 100mW)")], [_("Unknown")], ], - signal="changed", ) else: self.cmbApplication.do_load_combo( [[_("All digital devices")]], - signal="changed", ) def __do_set_dram_sensitive(self) -> None: diff --git a/src/ramstk/views/gtk3/design_electric/components/meter.py b/src/ramstk/views/gtk3/design_electric/components/meter.py index 3b8c3c21d..34d845ae6 100644 --- a/src/ramstk/views/gtk3/design_electric/components/meter.py +++ b/src/ramstk/views/gtk3/design_electric/components/meter.py @@ -163,11 +163,13 @@ def do_load_comboboxes(self, subcategory_id: int) -> None: _data = self._dic_quality[self.subcategory_id] except KeyError: _data = [] - self.cmbQuality.do_load_combo(_data, signal="changed") + self.cmbQuality.do_load_combo( + _data, + ) # Load the meter application RAMSTKComboBox(). self.cmbApplication.do_load_combo( - [[_("Ammeter")], [_("Voltmeter")], [_("Other")]], signal="changed" + [[_("Ammeter")], [_("Voltmeter")], [_("Other")]], ) # Load the meter type RAMSTKComboBox(). @@ -175,7 +177,9 @@ def do_load_comboboxes(self, subcategory_id: int) -> None: _data = self._dic_types[self.subcategory_id] except KeyError: _data = [] - self.cmbType.do_load_combo(_data, signal="changed") + self.cmbType.do_load_combo( + _data, + ) self._do_set_sensitive() @@ -192,7 +196,6 @@ def _do_set_reliability_attributes(self, attributes: Dict[str, Any]) -> None: self.cmbQuality.set_sensitive(True) self.cmbQuality.do_update( self._quality_id, - signal="changed", ) self._do_set_sensitive() diff --git a/src/ramstk/views/gtk3/design_electric/components/miscellaneous.py b/src/ramstk/views/gtk3/design_electric/components/miscellaneous.py index bff81c965..d469f07f8 100644 --- a/src/ramstk/views/gtk3/design_electric/components/miscellaneous.py +++ b/src/ramstk/views/gtk3/design_electric/components/miscellaneous.py @@ -7,7 +7,9 @@ # Copyright since 2007 Doyle "weibullguy" Rowland doyle.rowland reliaqual com """Miscellaneous Devices Input Panel.""" + # Standard Library Imports +import contextlib from typing import Any, Dict, List # Third Party Imports @@ -177,12 +179,13 @@ def do_load_comboboxes(self, subcategory_id: int) -> None: self.subcategory_id = subcategory_id # Load the quality level RAMSTKComboBox(). - self.cmbQuality.do_load_combo([["MIL-SPEC"], [_("Lower")]], signal="changed") + self.cmbQuality.do_load_combo( + [["MIL-SPEC"], [_("Lower")]], + ) # Load the application RAMSTKComboBox(). self.cmbApplication.do_load_combo( [[_("Incandescent, AC")], [_("Incandescent, DC")]], - signal="changed", ) # Load the type RAMSTKComboBox(). @@ -193,7 +196,6 @@ def do_load_comboboxes(self, subcategory_id: int) -> None: [_("Discrete LC Components")], [_("Discrete LC and Crystal Components")], ], - signal="changed", ) elif self._hazard_rate_method_id == 2: self.cmbType.do_load_combo( @@ -203,7 +205,6 @@ def do_load_comboboxes(self, subcategory_id: int) -> None: [_("MIL-F-18327 Discrete LC Components")], [_("MIL-F-18327 Discrete LC and Crystal Components")], ], - signal="changed", ) self._do_set_sensitive() @@ -231,7 +232,6 @@ def _do_set_reliability_attributes(self, attributes: Dict[str, Any]) -> None: self.cmbQuality.set_sensitive(True) self.cmbQuality.do_update( self._quality_id, - signal="changed", ) self._do_set_sensitive() @@ -252,10 +252,8 @@ def _do_set_sensitive(self) -> None: 2: self.__do_set_filter_sensitive, 4: self.__do_set_lamp_sensitive, } - try: + with contextlib.suppress(KeyError): _dic_method[self.subcategory_id]() - except KeyError: - pass def __do_set_crystal_sensitive(self) -> None: """Set the widget sensitivity as needed for a Crystal. diff --git a/src/ramstk/views/gtk3/design_electric/components/relay.py b/src/ramstk/views/gtk3/design_electric/components/relay.py index f8353c786..72046611d 100644 --- a/src/ramstk/views/gtk3/design_electric/components/relay.py +++ b/src/ramstk/views/gtk3/design_electric/components/relay.py @@ -367,9 +367,15 @@ def do_load_comboboxes(self, subcategory_id: int) -> None: self.__do_load_quality_combo() self.__do_load_type_combo() - self.cmbLoadType.do_load_combo(self._lst_technology, signal="changed") - self.cmbContactForm.do_load_combo(self._lst_contact_form, signal="changed") - self.cmbContactRating.do_load_combo(self._lst_contact_rating, signal="changed") + self.cmbLoadType.do_load_combo( + self._lst_technology, + ) + self.cmbContactForm.do_load_combo( + self._lst_contact_form, + ) + self.cmbContactRating.do_load_combo( + self._lst_contact_rating, + ) self._do_set_sensitive() @@ -386,7 +392,6 @@ def _do_set_reliability_attributes(self, attributes: Dict[str, Any]) -> None: self.cmbQuality.set_sensitive(True) self.cmbQuality.do_update( self._quality_id, - signal="changed", ) self._do_set_sensitive() @@ -454,7 +459,9 @@ def __do_load_application_combo(self) -> None: _data = self._dic_application[_contact_rating_id] except KeyError: _data = [] - self.cmbApplication.do_load_combo(_data, signal="changed") + self.cmbApplication.do_load_combo( + _data, + ) def __do_load_construction_combo(self) -> None: """Load the selections in the Relay construction RAMSTKComboBox(). @@ -468,7 +475,9 @@ def __do_load_construction_combo(self) -> None: _data = self._dic_construction[_contact_rating_id][_application_id] except KeyError: _data = [] - self.cmbConstruction.do_load_combo(_data, signal="changed") + self.cmbConstruction.do_load_combo( + _data, + ) def __do_load_quality_combo(self) -> None: """Load the selections in the Relay quality RAMSTKComboBox(). @@ -487,7 +496,9 @@ def __do_load_quality_combo(self) -> None: _data = self._dic_quality[self.subcategory_id] except KeyError: _data = [] - self.cmbQuality.do_load_combo(_data, signal="changed") + self.cmbQuality.do_load_combo( + _data, + ) def __do_load_type_combo(self) -> None: """Load the selections in the Relay type RAMSTKComboBox(). @@ -499,4 +510,6 @@ def __do_load_type_combo(self) -> None: _data = self._dic_pc_types[self.subcategory_id] except KeyError: _data = [] - self.cmbType.do_load_combo(_data, signal="changed") + self.cmbType.do_load_combo( + _data, + ) diff --git a/src/ramstk/views/gtk3/design_electric/components/resistor.py b/src/ramstk/views/gtk3/design_electric/components/resistor.py index b4ccc8fc9..dd988b29e 100644 --- a/src/ramstk/views/gtk3/design_electric/components/resistor.py +++ b/src/ramstk/views/gtk3/design_electric/components/resistor.py @@ -357,7 +357,6 @@ def _do_set_reliability_attributes(self, attributes: Dict[str, Any]) -> None: self.cmbQuality.set_sensitive(True) self.cmbQuality.do_update( self._quality_id, - signal="changed", ) self._do_set_sensitive() @@ -398,7 +397,6 @@ def __do_load_construction_combo(self) -> None: _data = [] self.cmbConstruction.do_load_combo( _data, - signal="changed", ) def __do_load_quality_combo(self) -> None: @@ -422,8 +420,7 @@ def __do_load_quality_combo(self) -> None: except KeyError: _quality = [[""]] self.cmbQuality.do_load_combo( - entries=_quality, - signal="changed", + _quality, ) def __do_load_specification_combo(self) -> None: @@ -438,7 +435,6 @@ def __do_load_specification_combo(self) -> None: _data = [] self.cmbSpecification.do_load_combo( _data, - signal="changed", ) def __do_load_style_combo(self) -> None: @@ -455,8 +451,7 @@ def __do_load_style_combo(self) -> None: except (KeyError, IndexError): _styles = [[""]] self.cmbStyle.do_load_combo( - entries=_styles, - signal="changed", + _styles, ) def __do_load_type_combo(self) -> None: @@ -473,8 +468,7 @@ def __do_load_type_combo(self) -> None: except KeyError: _types = [] self.cmbType.do_load_combo( - entries=_types, - signal="changed", + _types, ) def __do_set_construction_combo_sensitive(self) -> None: diff --git a/src/ramstk/views/gtk3/design_electric/components/semiconductor.py b/src/ramstk/views/gtk3/design_electric/components/semiconductor.py index cf1945142..c75f9cef3 100644 --- a/src/ramstk/views/gtk3/design_electric/components/semiconductor.py +++ b/src/ramstk/views/gtk3/design_electric/components/semiconductor.py @@ -427,7 +427,6 @@ def _do_set_reliability_attributes(self, attributes: Dict[str, Any]) -> None: self.cmbQuality.set_sensitive(True) self.cmbQuality.do_update( self._quality_id, - signal="changed", ) self._do_set_sensitive() @@ -468,7 +467,9 @@ def __do_load_application(self) -> None: _data = self._dic_applications[self.subcategory_id] except KeyError: _data = [] - self.cmbApplication.do_load_combo(_data, signal="changed") + self.cmbApplication.do_load_combo( + _data, + ) def __do_load_construction(self) -> None: """Load the construction RAMSTKComboBox() with selections. @@ -481,7 +482,6 @@ def __do_load_construction(self) -> None: [_("Metallurgically Bonded")], [_("Non-Metallurgically Bonded and Spring Loaded Contacts")], ], - signal="changed", ) def __do_load_matching(self) -> None: @@ -494,7 +494,9 @@ def __do_load_matching(self) -> None: _data = self._dic_matchings[self.subcategory_id] except KeyError: _data = [] - self.cmbMatching.do_load_combo(_data, signal="changed") + self.cmbMatching.do_load_combo( + _data, + ) def __do_load_quality(self) -> None: """Load the quality RAMSTKComboBox() with selections. @@ -522,7 +524,9 @@ def __do_load_quality(self) -> None: _data = self._dic_quality[self.subcategory_id] except KeyError: _data = [] - self.cmbQuality.do_load_combo(_data, signal="changed") + self.cmbQuality.do_load_combo( + _data, + ) def __do_load_type(self) -> None: """Load the type RAMSTKComboBox() with selections. @@ -541,7 +545,9 @@ def __do_load_type(self) -> None: _data = self._dic_types[self.subcategory_id] except KeyError: _data = [] - self.cmbType.do_load_combo(_data, signal="changed") + self.cmbType.do_load_combo( + _data, + ) def __do_set_application_sensitive(self) -> None: """Set the application RAMSTKComboBox() sensitive or not. diff --git a/src/ramstk/views/gtk3/design_electric/components/switch.py b/src/ramstk/views/gtk3/design_electric/components/switch.py index 4402efa11..5f5a2177c 100644 --- a/src/ramstk/views/gtk3/design_electric/components/switch.py +++ b/src/ramstk/views/gtk3/design_electric/components/switch.py @@ -224,14 +224,18 @@ def do_load_comboboxes(self, subcategory_id: int) -> None: self.subcategory_id = subcategory_id # Load the quality level RAMSTKComboBox(). - self.cmbQuality.do_load_combo([["MIL-SPEC"], [_("Lower")]], signal="changed") + self.cmbQuality.do_load_combo( + [["MIL-SPEC"], [_("Lower")]], + ) # Load the application RAMSTKComboBox(). try: _data = self._dic_applications[self.subcategory_id] except KeyError: _data = [] - self.cmbApplication.do_load_combo(_data, signal="changed") + self.cmbApplication.do_load_combo( + _data, + ) # Load the construction RAMSTKComboBox(). try: @@ -241,14 +245,18 @@ def do_load_comboboxes(self, subcategory_id: int) -> None: _data = self._dic_constructions[self.subcategory_id] except KeyError: _data = [] - self.cmbConstruction.do_load_combo(_data, signal="changed") + self.cmbConstruction.do_load_combo( + _data, + ) # Load the contact form RAMSTKComboBox(). try: _data = self._dic_contact_forms[self.subcategory_id] except KeyError: _data = [] - self.cmbContactForm.do_load_combo(_data, signal="changed") + self.cmbContactForm.do_load_combo( + _data, + ) self._do_set_sensitive() @@ -265,7 +273,6 @@ def _do_set_reliability_attributes(self, attributes: Dict[str, Any]) -> None: self.cmbQuality.set_sensitive(True) self.cmbQuality.do_update( self._quality_id, - signal="changed", ) self._do_set_sensitive() diff --git a/src/ramstk/views/gtk3/design_electric/panel.py b/src/ramstk/views/gtk3/design_electric/panel.py index bcff71b63..dae6fa410 100644 --- a/src/ramstk/views/gtk3/design_electric/panel.py +++ b/src/ramstk/views/gtk3/design_electric/panel.py @@ -187,7 +187,7 @@ def do_load_environment_active(self, environments: List[str]) -> None: :param environments: the list of active environments. :return: None """ - self.cmbActiveEnviron.do_load_combo(entries=environments) + self.cmbActiveEnviron.do_load_combo(entries_lst=environments) def do_load_environment_dormant(self, environments: List[str]) -> None: """Load the dormant environments RAMSTKComboBox(). @@ -195,7 +195,7 @@ def do_load_environment_dormant(self, environments: List[str]) -> None: :param environments: the list of dormant environments. :return: None """ - self.cmbDormantEnviron.do_load_combo(entries=environments) + self.cmbDormantEnviron.do_load_combo(entries_lst=environments) class DesignElectricStressInputPanel(RAMSTKFixedPanel): diff --git a/src/ramstk/views/gtk3/hardware/panel.py b/src/ramstk/views/gtk3/hardware/panel.py index 257ab1b1f..5bd8820b8 100644 --- a/src/ramstk/views/gtk3/hardware/panel.py +++ b/src/ramstk/views/gtk3/hardware/panel.py @@ -1163,8 +1163,7 @@ def do_load_categories(self, category: Dict[int, str]) -> None: _categories = [[value] for value in category.values()] self.cmbCategory.do_load_combo( - entries=_categories, - signal="changed", + _categories, ) def _do_load_subcategories(self, category_id: int) -> None: @@ -1178,7 +1177,9 @@ def _do_load_subcategories(self, category_id: int) -> None: if category_id > 0: _subcategories = SortedDict(self.dicSubcategories[category_id]) _subcategory = [[_subcategories[_key]] for _key in _subcategories] - self.cmbSubcategory.do_load_combo(entries=_subcategory, signal="changed") + self.cmbSubcategory.do_load_combo( + _subcategory, + ) def _do_set_comp_ref_des(self, comp_ref_des: str) -> None: """Set the value in the composite reference designator RAMSTKEntry(). @@ -1189,7 +1190,6 @@ def _do_set_comp_ref_des(self, comp_ref_des: str) -> None: """ self.txtCompRefDes.do_update( comp_ref_des, - signal="changed", ) def _request_load_component(self, combo: RAMSTKComboBox) -> None: @@ -1252,7 +1252,7 @@ def __init__(self) -> None: # Initialize widgets. self.cmbCostType: RAMSTKComboBox = RAMSTKComboBox() - self.cmbManufacturer: RAMSTKComboBox = RAMSTKComboBox(simple=False) + self.cmbManufacturer: RAMSTKComboBox = RAMSTKComboBox(simple_flag=False) self.txtCAGECode: RAMSTKEntry = RAMSTKEntry() self.txtCost: RAMSTKEntry = RAMSTKEntry() self.txtNSN: RAMSTKEntry = RAMSTKEntry() @@ -1401,8 +1401,8 @@ def do_load_manufacturers( """ _manufacturer = list(manufacturers.values()) self.cmbManufacturer.do_load_combo( - entries=_manufacturer, # type: ignore - simple=False, + _manufacturer, # type: ignore + simple_flag=False, ) def _do_load_cage_code(self, combo: RAMSTKComboBox) -> None: @@ -1420,7 +1420,9 @@ def _do_load_cage_code(self, combo: RAMSTKComboBox) -> None: except TypeError: _cage_code = "" - self.txtCAGECode.do_update(_cage_code, signal="changed") + self.txtCAGECode.do_update( + _cage_code, + ) pub.sendMessage( f"wvw_editing_{self._tag}", node_id=self._record_id, diff --git a/src/ramstk/views/gtk3/milhdbk217f/components/capacitor.py b/src/ramstk/views/gtk3/milhdbk217f/components/capacitor.py index 595f21709..da6cc3004 100644 --- a/src/ramstk/views/gtk3/milhdbk217f/components/capacitor.py +++ b/src/ramstk/views/gtk3/milhdbk217f/components/capacitor.py @@ -218,13 +218,10 @@ def _do_load_entries(self, attributes: Dict[str, Any]) -> None: self.lblModel.do_update(self._dic_part_stress[self.subcategory_id]) self.txtPiCV.do_update( str(self.fmt.format(attributes["piCV"])), - signal="changed", ) self.txtPiCF.do_update( str(self.fmt.format(attributes["piCF"])), - signal="changed", ) self.txtPiC.do_update( str(self.fmt.format(attributes["piC"])), - signal="changed", ) diff --git a/src/ramstk/views/gtk3/milhdbk217f/components/connection.py b/src/ramstk/views/gtk3/milhdbk217f/components/connection.py index 411cfc2c6..758bf7726 100644 --- a/src/ramstk/views/gtk3/milhdbk217f/components/connection.py +++ b/src/ramstk/views/gtk3/milhdbk217f/components/connection.py @@ -210,13 +210,10 @@ def _do_load_entries(self, attributes: Dict[str, Any]) -> None: self.txtPiC.do_update( str(self.fmt.format(attributes["piC"])), - signal="changed", ) self.txtPiK.do_update( str(self.fmt.format(attributes["piK"])), - signal="changed", ) self.txtPiP.do_update( str(self.fmt.format(attributes["piP"])), - signal="changed", ) diff --git a/src/ramstk/views/gtk3/milhdbk217f/components/inductor.py b/src/ramstk/views/gtk3/milhdbk217f/components/inductor.py index 92aef0974..1f39b2f45 100644 --- a/src/ramstk/views/gtk3/milhdbk217f/components/inductor.py +++ b/src/ramstk/views/gtk3/milhdbk217f/components/inductor.py @@ -162,5 +162,4 @@ def _do_load_entries(self, attributes: Dict[str, Any]) -> None: self.txtPiC.do_update( str(self.fmt.format(attributes["piC"])), - signal="changed", ) diff --git a/src/ramstk/views/gtk3/milhdbk217f/panel.py b/src/ramstk/views/gtk3/milhdbk217f/panel.py index 3dc21cb03..cea7d1076 100644 --- a/src/ramstk/views/gtk3/milhdbk217f/panel.py +++ b/src/ramstk/views/gtk3/milhdbk217f/panel.py @@ -101,15 +101,12 @@ def do_load_entries(self, attributes: Dict[str, Any]) -> None: self.txtLambdaB.do_update( str(self.fmt.format(self._lambda_b or 0.0)), - signal="changed", ) self.txtPiQ.do_update( str(self.fmt.format(attributes["piQ"] or 1.0)), - signal="changed", ) self.txtPiE.do_update( str(self.fmt.format(attributes["piE"] or 1.0)), - signal="changed", ) def _do_set_hardware_attributes(self, attributes: Dict[str, Any]) -> None: diff --git a/src/ramstk/views/gtk3/preferences/panel.py b/src/ramstk/views/gtk3/preferences/panel.py index bc576c738..045f23dd0 100644 --- a/src/ramstk/views/gtk3/preferences/panel.py +++ b/src/ramstk/views/gtk3/preferences/panel.py @@ -65,10 +65,10 @@ def __init__(self) -> None: _("RAMSTK Log Directory") ) - self.cmbModuleBookTabPosition: RAMSTKComboBox = RAMSTKComboBox(simple=True) - self.cmbWorkBookTabPosition: RAMSTKComboBox = RAMSTKComboBox(simple=True) - self.cmbListBookTabPosition: RAMSTKComboBox = RAMSTKComboBox(simple=True) - self.cmbReportSize: RAMSTKComboBox = RAMSTKComboBox(simple=True) + self.cmbModuleBookTabPosition: RAMSTKComboBox = RAMSTKComboBox() + self.cmbWorkBookTabPosition: RAMSTKComboBox = RAMSTKComboBox() + self.cmbListBookTabPosition: RAMSTKComboBox = RAMSTKComboBox() + self.cmbReportSize: RAMSTKComboBox = RAMSTKComboBox() self.txtFRMultiplier: RAMSTKEntry = RAMSTKEntry() self.txtDecimalPlaces: RAMSTKEntry = RAMSTKEntry() @@ -296,29 +296,25 @@ def _do_load_panel(self, configuration: RAMSTKUserConfiguration) -> None: self.cmbModuleBookTabPosition.do_update( _positions[self._configuration.RAMSTK_TABPOS["modulebook"].lower()], - signal="changed", ) self.cmbWorkBookTabPosition.do_update( _positions[self._configuration.RAMSTK_TABPOS["workbook"].lower()], - signal="changed", ) self.cmbListBookTabPosition.do_update( _positions[self._configuration.RAMSTK_TABPOS["listbook"].lower()], - signal="changed", ) self.cmbReportSize.do_update( _papersize[self._configuration.RAMSTK_REPORT_SIZE.lower()], - signal="changed", ) self.txtFRMultiplier.do_update( - str(self._configuration.RAMSTK_HR_MULTIPLIER), signal="changed" + str(self._configuration.RAMSTK_HR_MULTIPLIER), ) self.txtDecimalPlaces.do_update( - str(self._configuration.RAMSTK_DEC_PLACES), signal="changed" + str(self._configuration.RAMSTK_DEC_PLACES), ) self.txtMissionTime.do_update( - str(self._configuration.RAMSTK_MTIME), signal="changed" + str(self._configuration.RAMSTK_MTIME), ) self.btnConfDir.set_current_folder(self._configuration.RAMSTK_CONF_DIR) @@ -737,7 +733,7 @@ def __init__(self) -> None: super().__init__() # Initialize widgets. - self.cmbFormatFiles: RAMSTKComboBox = RAMSTKComboBox(simple=False) + self.cmbFormatFiles: RAMSTKComboBox = RAMSTKComboBox(simple_flag=False) self.tvwTreeView: RAMSTKTreeView = RAMSTKTreeView() # Initialize private dict instance attributes. @@ -791,7 +787,7 @@ def _do_load_comboboxes(self) -> None: [_("Usage Profile"), "usage_profile", ""], [_("Validation"), "validation", ""], ], - simple=False, + simple_flag=False, ) def _do_load_format(self, module: str) -> None: diff --git a/src/ramstk/views/gtk3/reliability/panel.py b/src/ramstk/views/gtk3/reliability/panel.py index ed7b4aef2..8276e0cce 100644 --- a/src/ramstk/views/gtk3/reliability/panel.py +++ b/src/ramstk/views/gtk3/reliability/panel.py @@ -298,7 +298,7 @@ def do_load_hr_distributions(self, distributions: List[str]) -> None: supports. :return: None """ - self.cmbFailureDist.do_load_combo(entries=distributions) + self.cmbFailureDist.do_load_combo(distributions) def do_load_hr_methods(self, methods: List[str]) -> None: """Load the hazard rate method RAMSTKComboBox(). @@ -312,7 +312,7 @@ def do_load_hr_methods(self, methods: List[str]) -> None: :param methods: the list of methods for assessing the hazard rate. :return: None """ - self.cmbHRMethod.do_load_combo(entries=methods) + self.cmbHRMethod.do_load_combo(methods) def do_load_hr_types(self, hr_types: List[str]) -> None: """Load the hazard rate type RAMSTKComboBox(). @@ -328,7 +328,7 @@ def do_load_hr_types(self, hr_types: List[str]) -> None: for a hardware item. :return: None """ - self.cmbHRType.do_load_combo(entries=hr_types) + self.cmbHRType.do_load_combo(hr_types) def _do_set_sensitive(self, attributes: Dict[str, Any]) -> None: """Set certain widgets sensitive or insensitive. @@ -808,43 +808,33 @@ def _do_load_entries_hazard_rate(self, attributes: Dict[str, Any]) -> None: """ self.txtActiveHt.do_update( str(self.fmt.format(attributes["hazard_rate_active"] or 0.0)), - signal="changed", ) self.txtActiveHtVar.do_update( str(self.fmt.format(attributes["hr_active_variance"] or 0.0)), - signal="changed", ) self.txtDormantHt.do_update( str(self.fmt.format(attributes["hazard_rate_dormant"] or 0.0)), - signal="changed", ) self.txtDormantHtVar.do_update( str(self.fmt.format(attributes["hr_dormant_variance"] or 0.0)), - signal="changed", ) self.txtSoftwareHt.do_update( str(self.fmt.format(attributes["hazard_rate_software"] or 0.0)), - signal="changed", ) self.txtLogisticsHt.do_update( str(self.fmt.format(attributes["hazard_rate_logistics"] or 0.0)), - signal="changed", ) self.txtLogisticsHtVar.do_update( str(self.fmt.format(attributes["hr_logistics_variance"] or 0.0)), - signal="changed", ) self.txtMissionHt.do_update( str(self.fmt.format(attributes["hazard_rate_mission"] or 0.0)), - signal="changed", ) self.txtMissionHtVar.do_update( str(self.fmt.format(attributes["hr_mission_variance"] or 0.0)), - signal="changed", ) self.txtPercentHt.do_update( str(self.fmt.format(attributes["hazard_rate_percent"] or 0.0)), - signal="changed", ) def _do_load_entries_mtbf(self, attributes: Dict[str, Any]) -> None: @@ -855,19 +845,15 @@ def _do_load_entries_mtbf(self, attributes: Dict[str, Any]) -> None: """ self.txtLogisticsMTBF.do_update( str(self.fmt.format(attributes["mtbf_logistics"] or 0.0)), - signal="changed", ) self.txtLogisticsMTBFVar.do_update( str(self.fmt.format(attributes["mtbf_logistics_variance"] or 0.0)), - signal="changed", ) self.txtMissionMTBF.do_update( str(self.fmt.format(attributes["mtbf_mission"] or 0.0)), - signal="changed", ) self.txtMissionMTBFVar.do_update( str(self.fmt.format(attributes["mtbf_mission_variance"] or 0.0)), - signal="changed", ) def _do_load_entries_reliability(self, attributes: Dict[str, Any]) -> None: @@ -878,19 +864,15 @@ def _do_load_entries_reliability(self, attributes: Dict[str, Any]) -> None: """ self.txtLogisticsRt.do_update( str(self.fmt.format(attributes["reliability_logistics"] or 1.0)), - signal="changed", ) self.txtLogisticsRtVar.do_update( str(self.fmt.format(attributes["reliability_log_variance"] or 0.0)), - signal="changed", ) self.txtMissionRt.do_update( str(self.fmt.format(attributes["reliability_mission"] or 1.0)), - signal="changed", ) self.txtMissionRtVar.do_update( str(self.fmt.format(attributes["reliability_miss_variance"] or 0.0)), - signal="changed", ) def __do_nudge_widgets(self) -> None: @@ -1145,19 +1127,15 @@ def _do_load_entries(self, attributes: Dict[str, Any]) -> None: """ self.txtLogisticsAt.do_update( str(self.fmt.format(attributes["availability_logistics"] or 1.0)), - signal="changed", ) self.txtLogisticsAtVar.do_update( str(self.fmt.format(attributes["avail_log_variance"] or 0.0)), - signal="changed", ) self.txtMissionAt.do_update( str(self.fmt.format(attributes["availability_mission"] or 1.0)), - signal="changed", ) self.txtMissionAtVar.do_update( str(self.fmt.format(attributes["avail_mis_variance"] or 0.0)), - signal="changed", ) def _do_load_entries_hardware(self, attributes: Dict[str, Any]) -> None: @@ -1171,19 +1149,15 @@ def _do_load_entries_hardware(self, attributes: Dict[str, Any]) -> None: """ self.txtTotalCost.do_update( str(locale.currency(attributes["total_cost"])), - signal="changed", ) self.txtCostFailure.do_update( str(locale.currency(attributes["cost_failure"])), - signal="changed", ) self.txtCostHour.do_update( str(locale.currency(attributes["cost_hour"])), - signal="changed", ) self.txtPartCount.do_update( str(f"{attributes['total_part_count']}"), - signal="changed", ) def __do_nudge_widgets(self) -> None: diff --git a/src/ramstk/views/gtk3/requirement/panel.py b/src/ramstk/views/gtk3/requirement/panel.py index 7e81694ca..b2f12de66 100644 --- a/src/ramstk/views/gtk3/requirement/panel.py +++ b/src/ramstk/views/gtk3/requirement/panel.py @@ -1046,7 +1046,9 @@ def __init__(self) -> None: ) self.cmbOwner: RAMSTKComboBox = RAMSTKComboBox() - self.cmbRequirementType: RAMSTKComboBox = RAMSTKComboBox(index=1, simple=False) + self.cmbRequirementType: RAMSTKComboBox = RAMSTKComboBox( + position_idx=1, simple_flag=False + ) self.cmbPriority: RAMSTKComboBox = RAMSTKComboBox() self.txtCode: RAMSTKEntry = RAMSTKEntry() @@ -1266,7 +1268,7 @@ def do_load_requirement_types( """ _requirement_types: List[Tuple[str]] = list(requirement_types.values()) - self.cmbRequirementType.do_load_combo(entries=_requirement_types, simple=False) + self.cmbRequirementType.do_load_combo(_requirement_types, simple_flag=False) def do_load_workgroups(self, workgroups: Dict[int, Tuple[str]]) -> None: """Load the workgroups RAMSTKComboBox(). @@ -1286,7 +1288,9 @@ def _do_load_code(self, requirement_code: int) -> None: :return: None :rtype: None """ - self.txtCode.do_update(str(requirement_code), signal="changed") + self.txtCode.do_update( + str(requirement_code), + ) @staticmethod def _do_select_date( diff --git a/src/ramstk/views/gtk3/similar_item/panel.py b/src/ramstk/views/gtk3/similar_item/panel.py index 0a359d2a6..4b8189000 100644 --- a/src/ramstk/views/gtk3/similar_item/panel.py +++ b/src/ramstk/views/gtk3/similar_item/panel.py @@ -93,7 +93,6 @@ def do_load_comboboxes(self) -> None: [_("Topic 633"), 0], [_("User-Defined"), 1], ], - signal="changed", ) def _do_set_sensitive(self, attributes: Dict[str, Union[int, float, str]]) -> None: @@ -106,7 +105,6 @@ def _do_set_sensitive(self, attributes: Dict[str, Union[int, float, str]]) -> No self.cmbSimilarItemMethod.set_sensitive(True) self.cmbSimilarItemMethod.do_update( attributes["similar_item_method_id"], - signal="changed", ) def _on_method_changed(self, combo: RAMSTKComboBox) -> None: @@ -1269,11 +1267,13 @@ def __init__(self) -> None: # Subscribe to PyPubSub messages. pub.subscribe(super().do_load_panel, "succeed_calculate_similar_item") - pub.subscribe(self._do_set_hardware_attributes, "succeed_get_hardware_tree") + pub.subscribe(self._do_set_hardware_attributes, + "succeed_get_hardware_tree") pub.subscribe( self._do_set_reliability_attributes, "succeed_get_reliability_tree" ) - pub.subscribe(self._on_method_changed, "succeed_change_similar_item_method") + pub.subscribe(self._on_method_changed, + "succeed_change_similar_item_method") pub.subscribe(self._on_select_hardware, "selected_hardware") # pylint: disable=unused-argument @@ -1326,11 +1326,16 @@ def do_refresh_functions(self, row: Gtk.TreeIter, function: List[str]) -> None: """ _model = self.tvwTreeView.get_model() - _model.set_value(row, self.tvwTreeView.position["function_1"], function[0]) - _model.set_value(row, self.tvwTreeView.position["function_2"], function[1]) - _model.set_value(row, self.tvwTreeView.position["function_3"], function[2]) - _model.set_value(row, self.tvwTreeView.position["function_4"], function[3]) - _model.set_value(row, self.tvwTreeView.position["function_5"], function[4]) + _model.set_value( + row, self.tvwTreeView.position["function_1"], function[0]) + _model.set_value( + row, self.tvwTreeView.position["function_2"], function[1]) + _model.set_value( + row, self.tvwTreeView.position["function_3"], function[2]) + _model.set_value( + row, self.tvwTreeView.position["function_4"], function[3]) + _model.set_value( + row, self.tvwTreeView.position["function_5"], function[4]) def _do_set_hardware_attributes(self, tree: treelib.Tree) -> None: """Set the attributes when the hardware tree is retrieved. @@ -1341,7 +1346,8 @@ def _do_set_hardware_attributes(self, tree: treelib.Tree) -> None: """ for _node in tree.all_nodes()[1:]: _hardware = _node.data["hardware"] - _row = self.tvwTreeView.do_get_row_by_value(1, _hardware.hardware_id) + _row = self.tvwTreeView.do_get_row_by_value( + 1, _hardware.hardware_id) if _row is not None: self.tvwTreeView.unfilt_model.set_value( _row, @@ -1358,7 +1364,8 @@ def _do_set_reliability_attributes(self, tree: treelib.Tree) -> None: """ for _node in tree.all_nodes()[1:]: _reliability = _node.data["reliability"] - _row = self.tvwTreeView.do_get_row_by_value(1, _reliability.hardware_id) + _row = self.tvwTreeView.do_get_row_by_value( + 1, _reliability.hardware_id) if _row is not None: self.tvwTreeView.unfilt_model.set_value( _row, @@ -1414,7 +1421,8 @@ def _on_select_hardware( """ self._parent_id = attributes["hardware_id"] self.tvwTreeView.filt_model.refilter() - pub.sendMessage("request_get_similar_item_attributes", node_id=self._parent_id) + pub.sendMessage("request_get_similar_item_attributes", + node_id=self._parent_id) def __do_load_similar_item(self, node: Any = "", row: Gtk.TreeIter = None) -> None: """Load the similar item RAMSTKTreeView(). diff --git a/src/ramstk/views/gtk3/validation/__init__.py b/src/ramstk/views/gtk3/validation/__init__.py index 9f01ca60c..7283dbccd 100644 --- a/src/ramstk/views/gtk3/validation/__init__.py +++ b/src/ramstk/views/gtk3/validation/__init__.py @@ -9,8 +9,13 @@ # RAMSTK Local Imports from .panel import ( - ValidationTaskDescriptionPanel, - ValidationTaskEffortPanel, - ValidationTreePanel, + RAMSTKValidationRequirementPanel, + RAMSTKValidationTaskDescriptionPanel, + RAMSTKValidationTaskEffortPanel, + RAMSTKValidationTreePanel, +) +from .view import ( + RAMSTKValidationGeneralDataView, + RAMSTKValidationMatrixView, + RAMSTKValidationModuleView, ) -from .view import ValidationGeneralDataView, ValidationModuleView diff --git a/src/ramstk/views/gtk3/validation/panel.py b/src/ramstk/views/gtk3/validation/panel.py index 36928a847..09c1599a8 100644 --- a/src/ramstk/views/gtk3/validation/panel.py +++ b/src/ramstk/views/gtk3/validation/panel.py @@ -6,7 +6,9 @@ # Copyright since 2007 Doyle "weibullguy" Rowland doyle.rowland reliaqual com """GTK3 Validation Panels.""" + # Standard Library Imports +import contextlib from datetime import date from typing import Dict, List, Tuple, Union @@ -22,13 +24,15 @@ RAMSTKDateSelect, RAMSTKEntry, RAMSTKFixedPanel, + RAMSTKMatrixPanel, RAMSTKSpinButton, RAMSTKTextView, RAMSTKTreePanel, + RAMSTKWidget, ) -class ValidationTreePanel(RAMSTKTreePanel): +class RAMSTKValidationTreePanel(RAMSTKTreePanel): """Panel to display flat list of validation tasks.""" # Define private dictionary class attributes. @@ -56,8 +60,8 @@ def __init__(self) -> None: } # Initialize private list class attributes. - self._lst_measurement_units: List[str] = [] - self._lst_verification_types: List[str] = [] + self._measurement_units: List[str] = [] + self._verification_types: List[str] = [] # Initialize private scalar class attributes. @@ -557,101 +561,110 @@ def __init__(self) -> None: ) def do_load_measurement_units( - self, measurement_unit: Dict[int, Tuple[str, str]] + self, measurement_unit_dic: Dict[int, Tuple[str, str]] ) -> None: """Load the verification task measurement unit list. - :param measurement_unit: the dict containing the units of measure. + :param measurement_unit_dic: the dict containing the units of measure. :return: None """ - self._lst_measurement_units = [""] + self._measurement_units = [""] - _cell = self.tvwTreeView.get_column( + _cell_obj = self.tvwTreeView.get_column( self.tvwTreeView.position["measurement_unit"] ).get_cells()[0] - _cell.set_property("has-entry", False) - _cellmodel = _cell.get_property("model") - _cellmodel.clear() - _cellmodel.append([""]) + _cell_obj.set_property("has-entry", False) + _cellmodel_obj = _cell_obj.get_property("model") + _cellmodel_obj.clear() + _cellmodel_obj.append([""]) # pylint: disable=unused-variable - for _key, value in measurement_unit.items(): - self._lst_measurement_units.append(measurement_unit[_key][1]) - _cellmodel.append([value[1]]) + for _unit_idx, _value_tpl in measurement_unit_dic.items(): + self._measurement_units.append(measurement_unit_dic[_unit_idx][1]) + _cellmodel_obj.append([_value_tpl[1]]) def do_load_verification_types( - self, verification_type: Dict[int, Tuple[str, str]] + self, verification_type_dic: Dict[int, Tuple[str, str]] ) -> None: """Load the verification task type list. - :param verification_type: the dict containing the verification task - types. + :param verification_type_dic: the dict containing the verification task types. :return: None """ - self._lst_verification_types = [""] + self._verification_types = [""] - _cell = self.tvwTreeView.get_column( + _cell_obj = self.tvwTreeView.get_column( self.tvwTreeView.position["task_type"] ).get_cells()[0] - _cell.set_property("has-entry", False) - _cellmodel = _cell.get_property("model") - _cellmodel.clear() - _cellmodel.append([""]) + _cell_obj.set_property("has-entry", False) + _cellmodel_obj = _cell_obj.get_property("model") + _cellmodel_obj.clear() + _cellmodel_obj.append([""]) # pylint: disable=unused-variable - for _key, value in verification_type.items(): - self._lst_verification_types.append(verification_type[_key][1]) - _cellmodel.append([value[1]]) + for _type_idx, _value_tpl in verification_type_dic.items(): + self._verification_types.append(verification_type_dic[_type_idx][1]) + _cellmodel_obj.append([_value_tpl[1]]) - def _on_module_switch(self, module: str = "") -> None: + def _on_module_switch( + self, + module: str = "", # pylint: disable=invalid-name + ) -> None: """Respond to change in selected Module View module (tab). - :param module: the name of the module that was just selected. + :param str module: the name of the module that was just selected. :return: None """ - _model, _row = self.tvwTreeView.selection.get_selected() + _model_obj, _row_obj = self.tvwTreeView.selection.get_selected() - if module == self._tag and _row is not None: - _code = _model.get_value(_row, self.tvwTreeView.position["validation_id"]) - _name = _model.get_value(_row, self.tvwTreeView.position["name"]) - _title = _(f"Analyzing Validation Task {_code}: {_name}") + if module == self._tag and _row_obj is not None: + _code_str = _model_obj.get_value( + _row_obj, self.tvwTreeView.position["validation_id"] + ) + _name_str = _model_obj.get_value( + _row_obj, self.tvwTreeView.position["name"] + ) + _title_str = _(f"Analyzing Validation Task {_code_str}: {_name_str}") - pub.sendMessage("request_set_title", title=_title) + pub.sendMessage("request_set_title", title=_title_str) - def _on_row_change(self, selection: Gtk.TreeSelection) -> None: + def _on_row_change(self, selection_obj: Gtk.TreeSelection) -> None: """Handle events for the Validation Module View RAMSTKTreeView(). This method is called whenever a Validation Module View RAMSTKTreeView() row is activated/changed. - :param selection: the Validation class Gtk.TreeSelection(). + :param selection_obj: the Validation class Gtk.TreeSelection(). :return: None """ - _attributes = super().on_row_change(selection) + _attribute_dic = super().on_row_change(selection_obj) - if _attributes: - self._record_id = _attributes["validation_id"] + if _attribute_dic: + self._record_id = _attribute_dic["validation_id"] - _attributes["measurement_unit"] = self._lst_measurement_units.index( - _attributes["measurement_unit"] + _attribute_dic["measurement_unit"] = self._measurement_units.index( + _attribute_dic["measurement_unit"] ) - _attributes["task_type"] = self._lst_verification_types.index( - _attributes["task_type"] + _attribute_dic["task_type"] = self._verification_types.index( + _attribute_dic["task_type"] ) - _title = _(f"Analyzing Verification Task {_attributes['name']}") + _title_str = _(f"Analyzing Verification Task {_attribute_dic['name']}") pub.sendMessage( "selected_validation", - attributes=_attributes, + attributes=_attribute_dic, ) pub.sendMessage( "request_set_title", - title=_title, + title=_title_str, ) + # pylint: disable=invalid-name def _on_workview_edit( - self, node_id: int, package: Dict[str, Union[bool, float, int, str]] + self, + node_id: int, + package: Dict[str, Union[bool, float, int, str]], ) -> None: """Update the module view RAMSTKTreeView() with attribute changes. @@ -663,87 +676,87 @@ def _on_workview_edit( :param package: the key:value for the data being updated. :return: None """ - [[_key, _value]] = package.items() + [[_key_str, _value_obj]] = package.items() - _column = self.tvwTreeView.get_column(self.tvwTreeView.position[_key]) - _cell = _column.get_cells()[-1] + _column_obj = self.tvwTreeView.get_column(self.tvwTreeView.position[_key_str]) + _cell_obj = _column_obj.get_cells()[-1] - if isinstance(_cell, Gtk.CellRendererCombo): - if _key == "measurement_unit": - package[_key] = self._lst_measurement_units[_value] - elif _key == "task_type": - package[_key] = self._lst_verification_types[_value] + if isinstance(_cell_obj, Gtk.CellRendererCombo): + if _key_str == "measurement_unit": + package[_key_str] = self._measurement_units[_value_obj] # type: ignore + elif _key_str == "task_type": + package[_key_str] = self._verification_types[_value_obj] # type: ignore super().do_refresh_tree(node_id, package) def __do_load_validation( - self, node: treelib.Node, row: Gtk.TreeIter + self, node_obj: treelib.Node, row_obj: Gtk.TreeIter ) -> Gtk.TreeIter: """Load a verification task into the RAMSTKTreeView(). :param node: the treelib Node() with the mode data to load. :param row: the parent row of the task to load into the validation tree. - :return: _new_row; the row that was just populated with validation data. + :return: _new_row_obj; the row that was just populated with validation data. :rtype: :class:`Gtk.TreeIter` """ - _new_row = None - _date_format = "%Y-%m-%d" + _new_row_obj = None + _date_format_str = "%Y-%m-%d" # pylint: disable=unused-variable - _entity = node.data["validation"] - - _attributes = [ - _entity.revision_id, - _entity.validation_id, - _entity.acceptable_maximum, - _entity.acceptable_mean, - _entity.acceptable_minimum, - _entity.acceptable_variance, - _entity.confidence, - _entity.cost_average, - _entity.cost_ll, - _entity.cost_maximum, - _entity.cost_mean, - _entity.cost_minimum, - _entity.cost_ul, - _entity.cost_variance, - _entity.date_end.strftime(_date_format), - _entity.date_start.strftime(_date_format), - _entity.description, - self._lst_measurement_units[_entity.measurement_unit], - _entity.name, - _entity.status, - _entity.task_specification, - self._lst_verification_types[_entity.task_type], - _entity.time_average, - _entity.time_ll, - _entity.time_maximum, - _entity.time_mean, - _entity.time_minimum, - _entity.time_ul, - _entity.time_variance, + _entity_obj = node_obj.data["validation"] + + _attribute_lst = [ + _entity_obj.revision_id, + _entity_obj.validation_id, + _entity_obj.acceptable_maximum, + _entity_obj.acceptable_mean, + _entity_obj.acceptable_minimum, + _entity_obj.acceptable_variance, + _entity_obj.confidence, + _entity_obj.cost_average, + _entity_obj.cost_ll, + _entity_obj.cost_maximum, + _entity_obj.cost_mean, + _entity_obj.cost_minimum, + _entity_obj.cost_ul, + _entity_obj.cost_variance, + _entity_obj.date_end.strftime(_date_format_str), + _entity_obj.date_start.strftime(_date_format_str), + _entity_obj.description, + self._measurement_units[_entity_obj.measurement_unit], + _entity_obj.name, + _entity_obj.status, + _entity_obj.task_specification, + self._verification_types[_entity_obj.task_type], + _entity_obj.time_average, + _entity_obj.time_ll, + _entity_obj.time_maximum, + _entity_obj.time_mean, + _entity_obj.time_minimum, + _entity_obj.time_ul, + _entity_obj.time_variance, ] try: - _new_row = self.tvwTreeView.unfilt_model.append(row, _attributes) + _new_row_obj = self.tvwTreeView.unfilt_model.append(row_obj, _attribute_lst) except (AttributeError, TypeError, ValueError): - _message = _( - f"An error occurred when loading verification task {node.identifier} " - f"into the verification tree. This might indicate it was missing it's " - f"data package, some of the data in the package was missing, or " - f"some of the data was the wrong type. Row data was: " - f"{_attributes}" + _message_str = _( + f"An error occurred when loading verification task " + f"{node_obj.identifier} into the verification tree. This might " + f"indicate it was missing it's data package, some of the data in the " + f"package was missing, or some of the data was the wrong type. Row " + f"data was: {_attribute_lst}" ) pub.sendMessage( "do_log_warning_msg", logger_name="WARNING", - message=_message, + message=_message_str, ) - return _new_row + return _new_row_obj -class ValidationTaskDescriptionPanel(RAMSTKFixedPanel): +class RAMSTKValidationTaskDescriptionPanel(RAMSTKFixedPanel): """Panel to display general data about the selected Validation task.""" # Define private dictionary class attributes. @@ -1028,11 +1041,11 @@ def __init__(self) -> None: # Subscribe to PyPubSub messages. def do_load_measurement_units( - self, measurement_unit: Dict[int, Tuple[str, str]] + self, measurement_unit_dic: Dict[int, Tuple[str, str]] ) -> None: """Load the measurement units RAMSTKComboBox(). - :param measurement_unit: the list of measurement units to load. The + :param measurement_unit_dic: the dict of measurement units to load. The key is an integer representing the ID field in the database. The value is a tuple with a unit abbreviation, unit name, and generic unit type. For example: @@ -1042,21 +1055,21 @@ def do_load_measurement_units( :return: None :rtype: None """ - _model = self.cmbMeasurementUnit.get_model() - _model.clear() + _model_obj = self.cmbMeasurementUnit.get_model() + _model_obj.clear() - _units = [] - for _index, _key in enumerate(measurement_unit): - self._dic_units[_index + 1] = measurement_unit[_key][1] - _units.append([measurement_unit[_key][1]]) - self.cmbMeasurementUnit.do_load_combo(entries=_units) + _unit_lst = [] + for _unit_idx, _key_str in enumerate(measurement_unit_dic): + self._dic_units[_unit_idx + 1] = measurement_unit_dic[_key_str][1] + _unit_lst.append([measurement_unit_dic[_key_str][1]]) + self.cmbMeasurementUnit.do_load_combo(_unit_lst) def do_load_validation_types( - self, validation_type: Dict[int, Tuple[str, str]] + self, validation_type_dic: Dict[int, Tuple[str, str]] ) -> None: """Load the validation task types RAMSTKComboBox(). - :param validation_type: a dict of validation task types. The key is an + :param validation_type_dic: a dict of validation task types. The key is an integer representing the ID field in the database. The value is a tuple with a task code, task name, and generic task type. For example: @@ -1066,19 +1079,19 @@ def do_load_validation_types( :return: None :rtype: None """ - _model = self.cmbTaskType.get_model() - _model.clear() - - _task_types = [] - for _index, _key in enumerate(validation_type): - self._dic_task_types[_index + 1] = [ - validation_type[_key][0], - validation_type[_key][1], + _model_obj = self.cmbTaskType.get_model() + _model_obj.clear() + + _task_type_lst = [] + for _type_idx, _key_str in enumerate(validation_type_dic): + self._dic_task_types[_type_idx + 1] = [ + validation_type_dic[_key_str][0], + validation_type_dic[_key_str][1], ] - _task_types.append([validation_type[_key][1]]) - self.cmbTaskType.do_load_combo(entries=_task_types) + _task_type_lst.append([validation_type_dic[_key_str][1]]) + self.cmbTaskType.do_load_combo(_task_type_lst) - def _do_make_task_code(self, combo: RAMSTKComboBox) -> None: + def _do_make_task_code(self, combo_obj: RAMSTKComboBox) -> None: """Create the validation task code. This method builds the task code based on the task type and the task @@ -1086,54 +1099,56 @@ def _do_make_task_code(self, combo: RAMSTKComboBox) -> None: task type 3-letter abbreviation-task ID - :param combo: the RAMSTKComboBox() that called this method. + :param combo_obj: the RAMSTKComboBox() that called this method. :return: None :rtype: None """ - try: - _index = combo.get_active() + with contextlib.suppress(AttributeError, KeyError): + _task_type_idx = combo_obj.get_active() - _task_type = self._dic_task_types[_index][0] - _task_code = f"{_task_type}-{self._record_id:04d}" + _task_type_str = self._dic_task_types[_task_type_idx][0] + _task_code_str = f"{_task_type_str}-{self._record_id:04d}" - self.txtCode.do_update(str(_task_code), signal="changed") + self.txtCode.do_update( + str(_task_code_str), + ) pub.sendMessage( "wvw_editing_validation", node_id=self._record_id, - package={"name": _task_code}, + package={"name": _task_code_str}, ) - except (AttributeError, KeyError): - pass @staticmethod def _do_select_date( - __button: RAMSTKButton, __event: Gdk.Event, entry: RAMSTKEntry + __button_obj: RAMSTKButton, + __event_obj: Gdk.Event, + entry_obj: RAMSTKEntry, ) -> str: """Request to launch a date selection dialog. This method is used to select the validation date for the Validation. - :param __button: the ramstk.RAMSTKButton() that called this method. - :type __button: :class:`ramstk.gui.gtk.ramstk.RAMSTKButton` - :param __event: the Gdk.Event() that called this method. - :type __event: :class:`Gdk.Event` - :param entry: the Gtk.Entry() that the new date should be displayed in. - :type entry: :class:`Gtk.Entry` + :param __button_obj: the ramstk.RAMSTKButton() that called this method. + :type __button_obj: :class:`ramstk.gui.gtk.ramstk.RAMSTKButton` + :param __event_obj: the Gdk.Event() that called this method. + :type __event_obj: :class:`Gdk.Event` + :param entry_obj: the Gtk.Entry() that the new date should be displayed in. + :type entry_obj: :class:`Gtk.Entry` :return: _date; the date in ISO-8601 (YYYY-mm-dd) format. :rtype: str """ - _dialog: RAMSTKDateSelect = RAMSTKDateSelect() + _dialog_obj: RAMSTKDateSelect = RAMSTKDateSelect() - _date = _dialog.do_run() - _dialog.do_destroy() + _date_obj = _dialog_obj.do_run() + _dialog_obj.do_destroy() - entry.set_text(str(_date)) + entry_obj.set_text(str(_date_obj)) - return _date + return _date_obj -class ValidationTaskEffortPanel(RAMSTKFixedPanel): +class RAMSTKValidationTaskEffortPanel(RAMSTKFixedPanel): """Panel to display effort data about the selected Validation task.""" # Define private dictionary class attributes. @@ -1368,11 +1383,11 @@ def __init__(self) -> None: pub.subscribe(self._on_calculate_task, "succeed_calculate_validation_task") def do_load_validation_types( - self, validation_type: Dict[int, Tuple[str, str]] + self, validation_type_dic: Dict[int, Tuple[str, str]] ) -> None: """Load the validation task types RAMSTKComboBox(). - :param validation_type: a dict of validation task types. The key is an + :param validation_type_dic: a dict of validation task types. The key is an integer representing the ID field in the database. The value is a tuple with a task code, task name, and generic task type. For example: @@ -1382,22 +1397,24 @@ def do_load_validation_types( :return: None :rtype: None """ - for _index, _key in enumerate(validation_type): - self._dic_task_types[_index + 1] = [ - validation_type[_key][0], - validation_type[_key][1], + for _task_type_idx, _key_str in enumerate(validation_type_dic): + self._dic_task_types[_task_type_idx + 1] = [ + validation_type_dic[_key_str][0], + validation_type_dic[_key_str][1], ] - def _do_load_code(self, task_code: int) -> None: + def _do_load_code(self, task_code_int: int) -> None: """Load the Validation code RAMSTKEntry(). - :param task_code: the Validation code to load. + :param task_code_int: the Validation code to load. :return: None :rtype: None """ - self.txtCode.do_update(str(task_code), signal="changed") + self.txtCode.do_update( + str(task_code_int), + ) - def _do_make_task_code(self, task_type: str) -> str: + def _do_make_task_code(self, task_type_str: str) -> str: """Create the validation task code. This method builds the task code based on the task type and the task @@ -1405,52 +1422,57 @@ def _do_make_task_code(self, task_type: str) -> str: task type 3-letter abbreviation-task ID - :param task_type: the three letter abbreviation for the task type. + :param task_type_str: the three letter abbreviation for the task type. :return: _code :rtype: str """ - _code = "" + _task_code_str = "" # pylint: disable=unused-variable - for __, _type in self._dic_task_types.items(): - if _type[1] == task_type: - _code = f"{_type[0]}-{self._record_id:04d}" + for _task_type_idx, _type_tpl in self._dic_task_types.items(): + if _type_tpl[1] == task_type_str: + _task_code_str = f"{_type_tpl[0]}-{self._record_id:04d}" pub.sendMessage( "wvw_editing_validation", node_id=self._record_id, - package={"name": _code}, + package={"name": _task_code_str}, ) - return _code + return _task_code_str @staticmethod def _do_select_date( - __button: RAMSTKButton, __event: Gdk.Event, entry: RAMSTKEntry + __button_obj: RAMSTKButton, + __event_obj: Gdk.Event, + entry_obj: RAMSTKEntry, ) -> str: """Request to launch a date selection dialog. This method is used to select the validation date for the Validation. - :param __button: the ramstk.RAMSTKButton() that called this method. - :type __button: :class:`ramstk.gui.gtk.ramstk.RAMSTKButton` - :param __event: the Gdk.Event() that called this method. - :type __event: :class:`Gdk.Event` - :param entry: the Gtk.Entry() that the new date should be displayed in. - :type entry: :class:`Gtk.Entry` - :return: _date; the date in ISO-8601 (YYYY-mm-dd) format. + :param __button_obj: the ramstk.RAMSTKButton() that called this method. + :type __button_obj: :class:`ramstk.gui.gtk.ramstk.RAMSTKButton` + :param __event_obj: the Gdk.Event() that called this method. + :type __event_obj: :class:`Gdk.Event` + :param entry_obj: the Gtk.Entry() that the new date should be displayed in. + :type entry_obj: :class:`Gtk.Entry` + :return: _date_str; the date in ISO-8601 (YYYY-mm-dd) format. :rtype: str """ - _dialog: RAMSTKDateSelect = RAMSTKDateSelect() + _dialog_obj: RAMSTKDateSelect = RAMSTKDateSelect() - _date = _dialog.do_run() - _dialog.do_destroy() + _date_str = _dialog_obj.do_run() + _dialog_obj.do_destroy() - entry.set_text(str(_date)) + entry_obj.set_text(str(_date_str)) - return _date + return _date_str - def _on_calculate_task(self, attributes: Dict[str, Union[float, int, str]]) -> None: + def _on_calculate_task( + self, + attributes: Dict[str, Union[float, int, str]], # pylint: disable=invalid-name + ) -> None: """Wrap _do_load_panel() on successful task calculation. :param attributes: the verification task attribute dict. @@ -1466,23 +1488,109 @@ def __do_adjust_widgets(self) -> None: :return: None :rtype: None """ - _fixed: Gtk.Fixed = self.get_children()[0].get_children()[0].get_children()[0] + _fixed_obj: Gtk.Fixed = ( + self.get_children()[0].get_children()[0].get_children()[0] + ) - _time_entry: RAMSTKEntry = _fixed.get_children()[9] - _cost_entry: RAMSTKEntry = _fixed.get_children()[21] + _time_entry_obj: RAMSTKWidget = _fixed_obj.get_children()[9] + _cost_entry_obj: RAMSTKWidget = _fixed_obj.get_children()[21] # We add the mean time and mean time UL to the same y position as # the mean time LL widget. - _x_pos: int = _fixed.child_get_property(_time_entry, "x") - _y_pos: int = _fixed.child_get_property(_time_entry, "y") - _fixed.move(self.txtMeanTimeLL, _x_pos, _y_pos) - _fixed.move(self.txtMeanTime, _x_pos + 175, _y_pos) - _fixed.move(self.txtMeanTimeUL, _x_pos + 350, _y_pos) + _x_pos_int: int = _fixed_obj.child_get_property(_time_entry_obj, "x") + _y_pos_int: int = _fixed_obj.child_get_property(_time_entry_obj, "y") + _fixed_obj.move(self.txtMeanTimeLL, _x_pos_int, _y_pos_int) + _fixed_obj.move(self.txtMeanTime, _x_pos_int + 175, _y_pos_int) + _fixed_obj.move(self.txtMeanTimeUL, _x_pos_int + 350, _y_pos_int) # We add the mean cost and mean cost UL to the same y position as # the mean cost LL widget. - _x_pos = _fixed.child_get_property(_cost_entry, "x") - _y_pos = _fixed.child_get_property(_cost_entry, "y") - _fixed.move(self.txtMeanCostLL, _x_pos, _y_pos) - _fixed.move(self.txtMeanCost, _x_pos + 175, _y_pos) - _fixed.move(self.txtMeanCostUL, _x_pos + 350, _y_pos) + _x_pos_int = _fixed_obj.child_get_property(_cost_entry_obj, "x") + _y_pos_int = _fixed_obj.child_get_property(_cost_entry_obj, "y") + _fixed_obj.move(self.txtMeanCostLL, _x_pos_int, _y_pos_int) + _fixed_obj.move(self.txtMeanCost, _x_pos_int + 175, _y_pos_int) + _fixed_obj.move(self.txtMeanCostUL, _x_pos_int + 350, _y_pos_int) + + +class RAMSTKValidationRequirementPanel(RAMSTKMatrixPanel): + """Panel to display effort data about the selected Validation task.""" + + # Define private dictionary class attributes. + + # Define private list class attributes. + + # Define private scalar class attributes. + _record_field = "validation_id" + _select_msg = "selected_validation" + _tag = "validation_requirement" + _title = _("Verification Task Effort") + + # Define public dictionary class attributes. + + # Define public list class attributes. + + # Define public scalar class attributes. + + def __init__(self) -> None: + """Initialize an instance of the Validation-Requirement Matrix panel.""" + super().__init__() + + # Initialize widgets. + + # Initialize private dict instance attributes. + + # Initialize private list instance attributes. + + # Initialize private scalar instance attributes. + + # Initialize public dict instance attributes. + + # Initialize public list instance attributes. + + # Initialize public scalar instance attributes. + + # super().do_set_properties() + super().do_make_panel() + # super().do_set_callbacks() + + # Subscribe to PyPubSub messages. + pub.subscribe(self._do_set_column_headers, "succeed_retrieve_all_requirement") + pub.subscribe(self._do_set_row_headers, "succeed_retrieve_all_validation") + + # pylint: disable=invalid-name + def _do_set_column_headers(self, tree: treelib.Tree) -> None: + """Set the column headings for the RAMSTKMatrixView(). + + :param tree: the Requirement tree. + :return: None + :rtype: None + """ + _column_name_lst = [ + ( + _node_obj.data["requirement"].requirement_code, + _node_obj.data["requirement"].description, + _node_obj.data["requirement"].requirement_id, + ) + for _node_obj in tree.all_nodes()[1:] + ] + + self.grdMatrixView.do_set_column_headings(_column_name_lst) + + # pylint: disable=invalid-name + def _do_set_row_headers(self, tree: treelib.Tree) -> None: + """Set the row headings for the RAMSTKMatrixView(). + + :param tree: the Validation & Verification task tree. + :return: None + :rtype: None + """ + _row_name_lst = [ + ( + _node_obj.data["validation"].name, + _node_obj.data["validation"].description, + _node_obj.data["validation"].validation_id, + ) + for _node_obj in tree.all_nodes()[1:] + ] + + self.grdMatrixView.do_set_row_headings(_row_name_lst) diff --git a/src/ramstk/views/gtk3/validation/panel.pyi b/src/ramstk/views/gtk3/validation/panel.pyi index 5557d230e..6cd7597e4 100644 --- a/src/ramstk/views/gtk3/validation/panel.pyi +++ b/src/ramstk/views/gtk3/validation/panel.pyi @@ -1,5 +1,5 @@ # Standard Library Imports -from typing import Any, Dict, Tuple +from typing import Dict, List, Tuple, Union # Third Party Imports import treelib @@ -13,89 +13,111 @@ from ramstk.views.gtk3.widgets import RAMSTKComboBox as RAMSTKComboBox from ramstk.views.gtk3.widgets import RAMSTKDateSelect as RAMSTKDateSelect from ramstk.views.gtk3.widgets import RAMSTKEntry as RAMSTKEntry from ramstk.views.gtk3.widgets import RAMSTKFixedPanel as RAMSTKFixedPanel +from ramstk.views.gtk3.widgets import RAMSTKMatrixPanel as RAMSTKMatrixPanel from ramstk.views.gtk3.widgets import RAMSTKSpinButton as RAMSTKSpinButton from ramstk.views.gtk3.widgets import RAMSTKTextView as RAMSTKTextView from ramstk.views.gtk3.widgets import RAMSTKTreePanel as RAMSTKTreePanel +from ramstk.views.gtk3.widgets import RAMSTKWidget as RAMSTKWidget -class ValidationTreePanel(RAMSTKTreePanel): +class RAMSTKValidationTreePanel(RAMSTKTreePanel): _select_msg: str _tag: str _title: str - _dic_row_loader: Any - _lst_measurement_units: Any - _lst_verification_types: Any - dic_attribute_widget_map: Any + _measurement_units: List[str] + _verification_types: List[str] + dic_attribute_widget_map: Dict[str, List[Union[bool, float, int, object, str]]] def __init__(self) -> None: ... def do_load_measurement_units( - self, measurement_unit: Dict[int, Tuple[str, str]] + self, measurement_unit_dic: Dict[int, Tuple[str, str]] ) -> None: ... def do_load_verification_types( - self, verification_type: Dict[int, Tuple[str, str]] + self, verification_type_dic: Dict[int, Tuple[str, str]] ) -> None: ... def _on_module_switch(self, module: str = ...) -> None: ... - _record_id: Any - def _on_row_change(self, selection: Gtk.TreeSelection) -> None: ... + _record_id: int + def _on_row_change(self, selection_obj: Gtk.TreeSelection) -> None: ... + def _on_workview_edit( + self, node_id: int, package: Dict[str, Union[bool, float, int, str]] + ) -> None: ... + def __do_load_validation( + self, node_obj: treelib.Node, row_obj: Gtk.TreeIter + ) -> Gtk.TreeIter: ... -class ValidationTaskDescriptionPanel(RAMSTKFixedPanel): +class RAMSTKValidationTaskDescriptionPanel(RAMSTKFixedPanel): _record_field: str _select_msg: str _tag: str - _title: Any - btnEndDate: Any - btnStartDate: Any - cmbTaskType: Any - cmbMeasurementUnit: Any - spnStatus: Any - txtTaskID: Any - txtCode: Any - txtMaxAcceptable: Any - txtMeanAcceptable: Any - txtMinAcceptable: Any - txtVarAcceptable: Any - txtSpecification: Any - txtTask: Any - txtEndDate: Any - txtStartDate: Any - _dic_task_types: Any - _dic_units: Any - dic_attribute_widget_map: Any + _title: str + btnEndDate: RAMSTKButton + btnStartDate: RAMSTKButton + cmbTaskType: RAMSTKComboBox + cmbMeasurementUnit: RAMSTKComboBox + spnStatus: RAMSTKSpinButton + txtTaskID: RAMSTKEntry + txtCode: RAMSTKEntry + txtMaxAcceptable: RAMSTKEntry + txtMeanAcceptable: RAMSTKEntry + txtMinAcceptable: RAMSTKEntry + txtVarAcceptable: RAMSTKEntry + txtSpecification: RAMSTKEntry + txtTask: RAMSTKEntry + txtEndDate: RAMSTKEntry + txtStartDate: RAMSTKEntry + _dic_task_types: Dict[int, List[str]] + _dic_units: Dict[int, str] + dic_attribute_widget_map: Dict[str, List[Union[bool, float, int, object, str]]] def __init__(self) -> None: ... def do_load_measurement_units( - self, measurement_unit: Dict[int, Tuple[str, str]] + self, measurement_unit_dic: Dict[int, Tuple[str, str]] ) -> None: ... def do_load_validation_types( - self, validation_type: Dict[int, Tuple[str, str]] + self, validation_type_dic: Dict[int, Tuple[str, str]] ) -> None: ... - def _do_make_task_code(self, combo: RAMSTKComboBox) -> None: ... + def _do_make_task_code(self, combo_obj: RAMSTKComboBox) -> None: ... @staticmethod def _do_select_date( - __button: RAMSTKButton, __event: Gdk.Event, entry: RAMSTKEntry + __button_obj: RAMSTKButton, __event_obj: Gdk.Event, entry_obj: RAMSTKEntry ) -> str: ... -class ValidationTaskEffortPanel(RAMSTKFixedPanel): +class RAMSTKValidationTaskEffortPanel(RAMSTKFixedPanel): _record_field: str _select_msg: str _tag: str - _title: Any - txtMinTime: Any - txtExpTime: Any - txtMaxTime: Any - txtMinCost: Any - txtExpCost: Any - txtMaxCost: Any - txtMeanTimeLL: Any - txtMeanTime: Any - txtMeanTimeUL: Any - txtMeanCostLL: Any - txtMeanCost: Any - txtMeanCostUL: Any - dic_attribute_widget_map: Any + _title: str + txtMinTime: RAMSTKEntry + txtExpTime: RAMSTKEntry + txtMaxTime: RAMSTKEntry + txtMinCost: RAMSTKEntry + txtExpCost: RAMSTKEntry + txtMaxCost: RAMSTKEntry + txtMeanTimeLL: RAMSTKEntry + txtMeanTime: RAMSTKEntry + txtMeanTimeUL: RAMSTKEntry + txtMeanCostLL: RAMSTKEntry + txtMeanCost: RAMSTKEntry + txtMeanCostUL: RAMSTKEntry + _dic_task_types: Dict[int, List[str]] + dic_attribute_widget_map: Dict[str, List[Union[bool, float, int, object, str]]] def __init__(self) -> None: ... - def _do_load_code(self, task_code: int) -> None: ... - def _do_make_task_code(self, task_type: str) -> str: ... + def do_load_validation_types( + self, validation_type_dic: Dict[int, Tuple[str, str]] + ) -> None: ... + def _do_load_code(self, task_code_int: int) -> None: ... + def _do_make_task_code(self, task_type_str: str) -> str: ... @staticmethod def _do_select_date( - __button: RAMSTKButton, __event: Gdk.Event, entry: RAMSTKEntry + __button_obj: RAMSTKButton, __event_obj: Gdk.Event, entry_obj: RAMSTKEntry ) -> str: ... - def _on_calculate_task(self, tree: treelib.Tree) -> None: ... + def _on_calculate_task( + self, attributes: Dict[str, Union[float, int, str]] + ) -> None: ... def __do_adjust_widgets(self) -> None: ... + +class RAMSTKValidationRequirementPanel(RAMSTKMatrixPanel): + _record_field: str + _select_msg: str + _tag: str + _title: str + def __init__(self) -> None: ... + def _do_set_column_headers(self, tree_obj: treelib.Tree) -> None: ... + def _do_set_row_headers(self, tree_obj: treelib.Tree) -> None: ... diff --git a/src/ramstk/views/gtk3/validation/view.py b/src/ramstk/views/gtk3/validation/view.py index f34ba1557..255f8fccc 100644 --- a/src/ramstk/views/gtk3/validation/view.py +++ b/src/ramstk/views/gtk3/validation/view.py @@ -7,7 +7,7 @@ """GTK3 Validation Views.""" # Standard Library Imports -from typing import Any, Dict +from typing import Dict, Union # Third Party Imports from pubsub import pub @@ -17,6 +17,7 @@ from ramstk.logger import RAMSTKLogManager from ramstk.views.gtk3 import Gtk, _ from ramstk.views.gtk3.widgets import ( + RAMSTKLabel, RAMSTKMessageDialog, RAMSTKModuleView, RAMSTKPanel, @@ -25,13 +26,14 @@ # RAMSTK Local Imports from . import ( - ValidationTaskDescriptionPanel, - ValidationTaskEffortPanel, - ValidationTreePanel, + RAMSTKValidationRequirementPanel, + RAMSTKValidationTaskDescriptionPanel, + RAMSTKValidationTaskEffortPanel, + RAMSTKValidationTreePanel, ) -class ValidationModuleView(RAMSTKModuleView): +class RAMSTKValidationModuleView(RAMSTKModuleView): """Display Validation attribute data in the RAMSTK Module Book. The Validation Module View displays all the Validations associated with the @@ -75,9 +77,9 @@ def __init__( super().__init__(configuration, logger) # Initialize private dictionary attributes. - self._dic_icons["tab"] = ( - self.RAMSTK_USER_CONFIGURATION.RAMSTK_ICON_DIR + "/32x32/validation.png" - ) + self._dic_icons[ + "tab" + ] = f"{self.RAMSTK_USER_CONFIGURATION.RAMSTK_ICON_DIR}/32x32/validation.png" # Initialize private list attributes. self._lst_mnu_labels = [ @@ -94,7 +96,7 @@ def __init__( ] # Initialize private scalar attributes. - self._pnlPanel = ValidationTreePanel() + self._pnlPanel = RAMSTKValidationTreePanel() # Initialize public dictionary attributes. @@ -107,36 +109,41 @@ def __init__( # Subscribe to PyPubSub messages. pub.subscribe(self._do_set_record_id, f"selected_{self._tag}") - def do_request_delete(self, __button: Gtk.ToolButton) -> None: + def do_request_delete(self, __button_obj: Gtk.ToolButton) -> None: """Request to delete selected record from the RAMSTKValidation table. - :param __button: the Gtk.ToolButton() that called this method. + :param __button_obj: the Gtk.ToolButton() that called this method. :return: None """ - _parent = self.get_parent().get_parent().get_parent().get_parent().get_parent() - _prompt = _( + _parent_obj = ( + self.get_parent().get_parent().get_parent().get_parent().get_parent() + ) + _prompt_str = _( "You are about to delete Validation {0:d} and all " "data associated with it. Is this really what " "you want to do?" ).format(self.dic_pkeys["record_id"]) - _dialog: RAMSTKMessageDialog = RAMSTKMessageDialog(parent=_parent) - _dialog.do_set_message(_prompt) - _dialog.do_set_message_type("question") + _dialog_obj: RAMSTKMessageDialog = RAMSTKMessageDialog(parent=_parent_obj) + _dialog_obj.do_set_message(_prompt_str) + _dialog_obj.do_set_message_type("question") - if _dialog.do_run() == Gtk.ResponseType.YES: + if _dialog_obj.do_run() == Gtk.ResponseType.YES: super().do_set_cursor_busy() pub.sendMessage( "request_delete_validation", node_id=self.dic_pkeys["record_id"], ) - _dialog.do_destroy() + _dialog_obj.do_destroy() - def _do_set_record_id(self, attributes: Dict[str, Any]) -> None: + # pylint: disable=invalid-name + def _do_set_record_id( + self, + attributes: Dict[str, Union[bool, float, int, str]], + ) -> None: """Set the Verification task's record ID. - :param attributes: the attribute dict for the selected Verification - task. + :param attributes: the attribute dict for the selected Verification task. :return: None :rtype: None """ @@ -165,7 +172,7 @@ def __make_ui(self) -> None: ) -class ValidationGeneralDataView(RAMSTKWorkView): +class RAMSTKValidationGeneralDataView(RAMSTKWorkView): """Display general Validation attribute data in the RAMSTK Work Book. The Validation Work View displays all the general data attributes for the @@ -246,8 +253,8 @@ def __init__( ] # Initialize private scalar attributes. - self._pnlTaskDescription: RAMSTKPanel = ValidationTaskDescriptionPanel() - self._pnlTaskEffort: RAMSTKPanel = ValidationTaskEffortPanel() + self._pnlTaskDescription: RAMSTKPanel = RAMSTKValidationTaskDescriptionPanel() + self._pnlTaskEffort: RAMSTKPanel = RAMSTKValidationTaskEffortPanel() # self._pnlProgramEffort: RAMSTKPanel = ProgramEffortPanel() # Initialize public dictionary attributes. @@ -266,10 +273,10 @@ def __init__( pub.subscribe(self._do_set_record_id, "selected_validation") - def _do_request_calculate(self, __button: Gtk.ToolButton) -> None: + def _do_request_calculate(self, __button_obj: Gtk.ToolButton) -> None: """Request to calculate the selected validation task. - :param __button: the Gtk.ToolButton() that called this method. + :param __button_obj: the Gtk.ToolButton() that called this method. :return: None :rtype: None """ @@ -279,10 +286,10 @@ def _do_request_calculate(self, __button: Gtk.ToolButton) -> None: node_id=self.dic_pkeys["record_id"], ) - def _do_request_calculate_all(self, __button: Gtk.ToolButton) -> None: + def _do_request_calculate_all(self, __button_obj: Gtk.ToolButton) -> None: """Request to calculate program cost and time. - :param __button: the Gtk.ToolButton() that called this method. + :param __button_obj: the Gtk.ToolButton() that called this method. :return: None :rtype: None """ @@ -291,7 +298,11 @@ def _do_request_calculate_all(self, __button: Gtk.ToolButton) -> None: "request_calculate_all_validation_tasks", ) - def _do_set_record_id(self, attributes: Dict[str, Any]) -> None: + # pylint: disable=invalid-name + def _do_set_record_id( + self, + attributes: Dict[str, Union[bool, float, int, str]], + ) -> None: """Set the Verification task record ID. :param attributes: the attribute dict for the selected Validation task. @@ -308,7 +319,7 @@ def __make_ui(self) -> None: :return: None :rtype: None """ - _hpaned, _vpaned_right = super().do_make_layout_lrr() + _hpaned_obj, _vpaned_right_obj = super().do_make_layout_lrr() self._pnlTaskDescription.fmt = self.fmt self._pnlTaskDescription.do_load_measurement_units( @@ -317,14 +328,165 @@ def __make_ui(self) -> None: self._pnlTaskDescription.do_load_validation_types( self.RAMSTK_USER_CONFIGURATION.RAMSTK_VALIDATION_TYPE ) - _hpaned.pack1(self._pnlTaskDescription, True, True) + _hpaned_obj.pack1(self._pnlTaskDescription, True, True) self._pnlTaskEffort.fmt = self.fmt self._pnlTaskEffort.do_load_validation_types( self.RAMSTK_USER_CONFIGURATION.RAMSTK_VALIDATION_TYPE ) # self._pnlProgramEffort.fmt = self.fmt - _vpaned_right.pack1(self._pnlTaskEffort, True, True) - # _vpaned_right.pack2(self._pnlProgramEffort, True, True) + _vpaned_right_obj.pack1(self._pnlTaskEffort, True, True) + # _vpaned_right_obj.pack2(self._pnlProgramEffort, True, True) + + self.show_all() + + +class RAMSTKValidationMatrixView(RAMSTKWorkView): + """Display general Validation attribute data in the RAMSTK Work Book. + + The Validation Work View displays all the general data attributes for the + selected Validation. The attributes of a Validation General Data Work View + are: + + :cvar dict _dic_keys: + :cvar list _lst_labels: the list of label text. + :cvar str _tag: the name of the module. + + :ivar list _lst_callbacks: the list of callback methods for the view's + toolbar buttons and pop-up menu. The methods are listed in the order + they appear on the toolbar and pop-up menu. + :ivar list _lst_icons: the list of icons for the view's toolbar buttons + and pop-up menu. The icons are listed in the order they appear on the + toolbar and pop-up menu. + :ivar list _lst_mnu_labels: the list of labels for the view's pop-up + menu. The labels are listed in the order they appear in the menu. + :ivar list _lst_tooltips: the list of tooltips for the view's + toolbar buttons and pop-up menu. The tooltips are listed in the + order they appear on the toolbar or pop-up menu. + """ + + # Define private dictionary class attributes. + + # Define private list class attributes. + + # Define private scalar class attributes. + _tag: str = "validation_requirement" + _tablabel: str = _("Requirements\nMatrix") + _tabtooltip: str = _( + "Displays general information for the selected Verification task." + ) + + # Define public dictionary class attributes. + + # Define public list class attributes. + + # Define public scalar class attributes. + + def __init__( + self, configuration_obj: RAMSTKUserConfiguration, logger_obj: RAMSTKLogManager + ) -> None: + """Initialize the Validation Work View general data page. + + :param configuration_obj: the RAMSTKUserConfiguration class instance. + :param logger_obj: the RAMSTKLogManager class instance. + """ + super().__init__(configuration_obj, logger_obj) + + # Initialize private dictionary attributes. + + # Initialize private list attributes. + self._lst_callbacks = [ + self._do_request_update_all, + ] + self._lst_icons = ["save-all"] + self._lst_mnu_labels = [ + _("Save All"), + ] + self._lst_tooltips = [ + _("Save changes to the Verification-Requirement matrix."), + ] + + # Initialize private scalar attributes. + self._pnlRequirementMatrix: RAMSTKValidationRequirementPanel = ( + RAMSTKValidationRequirementPanel() + ) + + # Initialize public dictionary attributes. + + # Initialize public list attributes. + + # Initialize public scalar attributes. + + self.__make_ui() + + # Subscribe to PyPubSub messages. + pub.subscribe(self._do_set_record_id, "selected_validation") + + def _do_request_update_all(self, __button_obj: Gtk.Button) -> None: + """Request to update matrix records to RAMSTK program database. + + :param __button: the Gtk.ToolButton() that called this method. + :return: None + """ + _correlation_int = 0 + _row_id = 0 + + self.do_set_cursor_busy() + + for _row_idx in range(2, self._pnlRequirementMatrix.grdMatrixView.n_rows + 1): + for _column_idx in range( + self._pnlRequirementMatrix.grdMatrixView.n_columns + ): + _obj = self._pnlRequirementMatrix.grdMatrixView.get_child_at( + _column_idx, + _row_idx, + ) + if isinstance(_obj, RAMSTKLabel): + _row_id = _obj.get_label() + else: + _correlation_int = _obj.get_value() + print(_row_id, _correlation_int) + + # pylint: disable=invalid-name + def _do_set_record_id( + self, + attributes: Dict[str, Union[bool, float, int, str]], + ) -> None: + """Set the Verification task record ID. + + :param attributes: the attribute dict for the selected Validation task. + :return: None + :rtype: None + """ + self.dic_pkeys["revision_id"] = attributes["revision_id"] + self.dic_pkeys["validation_id"] = attributes["validation_id"] + self.dic_pkeys["record_id"] = attributes["validation_id"] + + def __do_load_lists(self) -> None: + """Load panel lists and dictionaries. + + :return: None + :rtype: None + """ + self._pnlRequirementMatrix.grdMatrixView.icons_dic["none"] = self._dic_icons[ + "none" + ] + self._pnlRequirementMatrix.grdMatrixView.icons_dic["partial"] = self._dic_icons[ + "partial" + ] + self._pnlRequirementMatrix.grdMatrixView.icons_dic[ + "complete" + ] = self._dic_icons["complete"] + + def __make_ui(self) -> None: + """Build the user interface for the Validation General Data tab. + + :return: None + :rtype: None + """ + super().do_make_layout() + + self.__do_load_lists() + self.pack_start(self._pnlRequirementMatrix, True, True, 1) self.show_all() diff --git a/src/ramstk/views/gtk3/validation/view.pyi b/src/ramstk/views/gtk3/validation/view.pyi index 022320239..fb0c20422 100644 --- a/src/ramstk/views/gtk3/validation/view.pyi +++ b/src/ramstk/views/gtk3/validation/view.pyi @@ -1,5 +1,5 @@ # Standard Library Imports -from typing import Any, Dict +from typing import Callable, Dict, List, Union # RAMSTK Package Imports from ramstk.configuration import RAMSTKUserConfiguration as RAMSTKUserConfiguration @@ -12,40 +12,74 @@ from ramstk.views.gtk3.widgets import RAMSTKPanel as RAMSTKPanel from ramstk.views.gtk3.widgets import RAMSTKWorkView as RAMSTKWorkView # RAMSTK Local Imports -from . import ValidationTaskDescriptionPanel as ValidationTaskDescriptionPanel -from . import ValidationTaskEffortPanel as ValidationTaskEffortPanel -from . import ValidationTreePanel as ValidationTreePanel +from . import RAMSTKValidationRequirementPanel as RAMSTKValidationRequirementPanel +from . import ( + RAMSTKValidationTaskDescriptionPanel as RAMSTKValidationTaskDescriptionPanel, +) +from . import RAMSTKValidationTaskEffortPanel as RAMSTKValidationTaskEffortPanel +from . import RAMSTKValidationTreePanel as RAMSTKValidationTreePanel -class ValidationModuleView(RAMSTKModuleView): +class RAMSTKValidationModuleView(RAMSTKModuleView): _tag: str _tablabel: str _tabtooltip: str - _lst_mnu_labels: Any - _lst_tooltips: Any - _pnlPanel: Any + _lst_mnu_labels: List[str] + _lst_tooltips: List[str] + _pnlPanel: RAMSTKValidationTreePanel + def __init__( self, configuration: RAMSTKUserConfiguration, logger: RAMSTKLogManager ) -> None: ... def do_request_delete(self, __button: Gtk.ToolButton) -> None: ... - _record_id: Any - def _do_set_record_id(self, attributes: Dict[str, Any]) -> None: ... + _record_id: int + + def _do_set_record_id( + self, + attributes: Dict[str, Union[bool, int, float, str]], + ) -> None: ... def __make_ui(self) -> None: ... -class ValidationGeneralDataView(RAMSTKWorkView): +class RAMSTKValidationGeneralDataView(RAMSTKWorkView): _tag: str _tablabel: str _tabtooltip: str - _lst_callbacks: Any - _lst_icons: Any - _lst_mnu_labels: Any - _lst_tooltips: Any - _pnlTaskDescription: Any - _pnlTaskEffort: Any + _lst_callbacks: List[Callable] + _lst_icons: List[str] + _lst_mnu_labels: List[str] + _lst_tooltips: List[str] + _pnlTaskDescription: RAMSTKValidationTaskDescriptionPanel + _pnlTaskEffort: RAMSTKValidationTaskEffortPanel + def __init__( self, configuration: RAMSTKUserConfiguration, logger: RAMSTKLogManager ) -> None: ... def _do_request_calculate(self, __button: Gtk.ToolButton) -> None: ... def _do_request_calculate_all(self, __button: Gtk.ToolButton) -> None: ... - _record_id: Any - def _do_set_record_id(self, attributes: Dict[str, Any]) -> None: ... + _record_id: int + + def _do_set_record_id( + self, + attributes: Dict[str, Union[bool, float, int, str]], + ) -> None: ... + def __make_ui(self) -> None: ... + +class RAMSTKValidationMatrixView(RAMSTKWorkView): + _tag: str + _tablabel: str + _tabtooltip: str + _record_id: int + _lst_callbacks: List[Callable] + _lst_icons: List[str] + _lst_mnu_labels: List[str] + _lst_tooltips: List[str] + _pnlRequirementMatrix: RAMSTKValidationRequirementPanel + + def __init__( + self, configuration: RAMSTKUserConfiguration, logger: RAMSTKLogManager + ) -> None: ... + def _do_set_record_id( + self, + attributes: Dict[str, Union[bool, float, int, str]], + ) -> None: ... + def __do_load_lists(self) -> None: ... def __make_ui(self) -> None: ... diff --git a/src/ramstk/views/gtk3/widgets/button.py b/src/ramstk/views/gtk3/widgets/button.py index b827c2604..6de002bc3 100644 --- a/src/ramstk/views/gtk3/widgets/button.py +++ b/src/ramstk/views/gtk3/widgets/button.py @@ -175,17 +175,17 @@ def do_set_properties(self, **kwargs: Any) -> None: self.get_child().set_property("height-request", self.height) self.get_child().set_property("width-request", self.width) - def do_update(self, value: int, signal: str = "") -> None: + def do_update(self, value: int, signal_str: str = "") -> None: """Update the RAMSTK CheckButton with a new value. :param value: the information to update the RAMSTKCheckButton() to display. - :param str signal: the name of the signal whose handler ID the + :param str signal_str: the name of the signal whose handler ID the RAMSTKCheckButton() needs to block. :return: None :rtype: None """ - _handler_id = self.dic_handler_id[signal] + _handler_id = self.dic_handler_id[signal_str] self.handler_block(_handler_id) self.set_active(value) @@ -305,17 +305,17 @@ def do_set_properties(self, **kwargs: Any) -> None: self.set_snap_to_ticks(_snap_to_ticks) self.set_update_policy(Gtk.SpinButtonUpdatePolicy.IF_VALID) - def do_update(self, value: int, signal: str = "") -> None: + def do_update(self, value: int, signal_str: str = "") -> None: """Update the RAMSTK Spin Button with a new value. :param value: the information to update the RAMSTKSpinButton() to display. - :param str signal: the name of the signal whose handler ID the + :param str signal_str: the name of the signal whose handler ID the RAMSTKSpinButton() needs to block. :return: None :rtype: None """ - _handler_id = self.dic_handler_id[signal] + _handler_id = self.dic_handler_id[signal_str] self.handler_block(_handler_id) self.set_value(value) diff --git a/src/ramstk/views/gtk3/widgets/combo.py b/src/ramstk/views/gtk3/widgets/combo.py index 4a58db1c9..85d247c2b 100644 --- a/src/ramstk/views/gtk3/widgets/combo.py +++ b/src/ramstk/views/gtk3/widgets/combo.py @@ -25,12 +25,12 @@ class RAMSTKComboBox(Gtk.ComboBox, RAMSTKWidget): _default_height = 30 _default_width = 200 - def __init__(self, index: int = 0, simple: bool = True) -> None: + def __init__(self, position_idx: int = 0, simple_flag: bool = True) -> None: """Create RAMSTK ComboBox widgets. - :keyword int index: the index in the RAMSTKComboBox Gtk.ListView() to + :keyword position_idx: the index in the RAMSTKComboBox Gtk.ListView() to display. Default is 0. - :keyword bool simple: indicates whether to make a simple (one item) or + :keyword simple_flag: indicates whether to make a simple (one item) or complex (three item) RAMSTKComboBox. Default is True. """ RAMSTKWidget.__init__(self) @@ -40,64 +40,63 @@ def __init__(self, index: int = 0, simple: bool = True) -> None: # Initialize private list attributes. # Initialize private scalar attributes. - self._index: int = index + self._index: int = position_idx - _list = Gtk.ListStore() + _list_obj = Gtk.ListStore() # Initialize public dictionary attributes. # Initialize public list attributes. # Initialize public scalar attributes. - if not simple: - _list.set_column_types( + if not simple_flag: + _list_obj.set_column_types( [GObject.TYPE_STRING, GObject.TYPE_STRING, GObject.TYPE_STRING] ) else: - _list.set_column_types([GObject.TYPE_STRING]) - self.set_model(_list) + _list_obj.set_column_types([GObject.TYPE_STRING]) + self.set_model(_list_obj) - _cell = Gtk.CellRendererText() - self.pack_start(_cell, True) - self.add_attribute(_cell, "text", self._index) + _cell_obj = Gtk.CellRendererText() + self.pack_start(_cell_obj, True) + self.add_attribute(_cell_obj, "text", self._index) self.show() def do_get_options(self) -> Dict[int, Any]: """Retrieve all the options in the RAMSTK Combo. - :return: _options + :return: _options_dic :rtype: dict """ - _options = {} + _options_dic = {} - _model = self.get_model() - _iter = _model.get_iter_first() + _model_obj = self.get_model() + _iter_obj = _model_obj.get_iter_first() - i = 0 - while _iter is not None: - _options[i] = _model.get_value(_iter, self._index) - _iter = _model.iter_next(_iter) - i += 1 + _option_idx = 0 + while _iter_obj is not None: + _options_dic[_option_idx] = _model_obj.get_value(_iter_obj, self._index) + _iter_obj = _model_obj.iter_next(_iter_obj) + _option_idx += 1 - return _options + return _options_dic - # noinspection PyIncorrectDocstring def do_load_combo( self, - entries: List[List[Union[str, int]]], - signal: str = "", - simple: bool = True, + entries_lst: List[List[Union[str, int]]], + signal_str: str = "changed", + simple_flag: bool = True, ) -> None: """Load RAMSTK ComboBox widgets. - :param entries: the information to load into the Gtk.ComboBox(). + :param entries_lst: the information to load into the Gtk.ComboBox(). This is always a list of lists where each internal list contains the information to be displayed and there is one internal list for each RAMSTKComboBox line. - :param signal: the name of the signal whose handler ID the + :param signal_str: the name of the signal whose handler ID the RAMSTKComboBox() needs to block. - :param simple: indicates whether this is a simple (one item) or + :param simple_flag: indicates whether this is a simple (one item) or complex (three item) RAMSTKComboBox. A simple (default) RAMSTKComboBox contains and displays one field only. A 'complex' RAMSTKComboBox contains three str fields, but only displays the @@ -107,59 +106,58 @@ def do_load_combo( the other two fields might contain a code and an index. These could be extracted for use in the RAMSTK Views. :return: None + :rtype: None :raise: TypeError if attempting to load other than string values. """ - _model = self.get_model() - _model.clear() + _model_obj = self.get_model() + _model_obj.clear() try: - _handler_id = self.dic_handler_id[signal] + _handler_id = self.dic_handler_id[signal_str] self.handler_block(_handler_id) except KeyError: _handler_id = -1 - if not simple: - _model.append(["", "", ""]) - # pylint: disable=unused-variable - for _entry in entries: - _model.append(list(_entry)) + if not simple_flag: + _model_obj.append(["", "", ""]) + for _entry_obj in entries_lst: + _model_obj.append(list(_entry_obj)) else: - _model.append([""]) - # pylint: disable=unused-variable - for _entry in entries: - _model.append([_entry[self._index]]) + _model_obj.append([""]) + for _entry_obj in entries_lst: + _model_obj.append([_entry_obj[self._index]]) if _handler_id > 0: self.handler_unblock(_handler_id) - def do_update(self, value: int, signal: str = "") -> None: + def do_update(self, value_int: int, signal_str: str = "") -> None: """Update the RAMSTK Combo with a new value. - :param value: the information to update the RAMSTKCombo() to + :param value_int: the information to update the RAMSTKCombo() to display. - :param str signal: the name of the signal whose handler ID the + :param signal_str: the name of the signal whose handler ID the RAMSTKComboBox() needs to block. :return: None :rtype: None """ - _handler_id = self.dic_handler_id[signal] + _handler_id = self.dic_handler_id[signal_str] - _value = none_to_default(value, 0) + _value_int = none_to_default(value_int, 0) # type: ignore self.handler_block(_handler_id) - self.set_active(_value) + self.set_active(_value_int) self.handler_unblock(_handler_id) - def get_value(self, index: int = 0) -> str: + def get_value(self, column_idx: int = 0) -> str: """Return value in the RAMSTKComboBox() model at the index position. - :keyword int index: the column in the RAMSTKComboBox() model whose + :keyword column_idx: the column in the RAMSTKComboBox() model whose value is to be retrieved. Defaults to zero which will always read a 'simple' RAMSTKComboBox(). :return: _value :rtype: str """ - _model = self.get_model() - _row = self.get_active_iter() + _model_obj = self.get_model() + _row_obj = self.get_active_iter() - return _model.get_value(_row, index) + return _model_obj.get_value(_row_obj, column_idx) diff --git a/src/ramstk/views/gtk3/widgets/entry.py b/src/ramstk/views/gtk3/widgets/entry.py index 75578e895..d3632e29c 100644 --- a/src/ramstk/views/gtk3/widgets/entry.py +++ b/src/ramstk/views/gtk3/widgets/entry.py @@ -9,7 +9,7 @@ # Standard Library Imports from datetime import datetime -from typing import Any, Callable +from typing import Any, Callable, Union # RAMSTK Package Imports from ramstk.views.gtk3 import Gtk, Pango @@ -62,40 +62,43 @@ def do_set_properties(self, **kwargs: Any) -> None: """ super().do_set_properties(**kwargs) - _bold = kwargs.get("bold", False) - _editable = kwargs.get("editable", True) + _bold_flag = kwargs.get("bold", False) + _editable_flag = kwargs.get("editable", True) - self.set_property("editable", _editable) + self.set_property("editable", _editable_flag) - if _bold: - self.modify_font(Pango.FontDescription("bold")) + if _bold_flag: + self.override_font(Pango.FontDescription("bold")) - def do_update(self, value: Any, signal: str = "") -> None: + def do_update( + self, + value_obj: Union[bool, float, int, str], + signal_str: str = "changed", + ) -> None: """Update the RAMSTK Entry with a new value. - :param value: the information to update the RAMSTKEntry() to - display. - :keyword signal: the name of the signal whose handler ID the - RAMSTKEntry() needs to block. + :param value_obj: the information to update the RAMSTKEntry() to display. + :param signal_str: the name of the signal whose handler ID the RAMSTKEntry() + needs to block. :return: None :rtype: None """ try: - _value = datetime.strftime(value, "%Y-%m-%d") + _value_str = datetime.strftime(value_obj, "%Y-%m-%d") # type: ignore except TypeError: - _value = str(value) + _value_str = str(value_obj) # Sometimes there is no handler ID for the RAMSTKEntry(). This # usually happens when the widget is being used to display results # and has no associated callback method. try: - _handler_id = self.dic_handler_id[signal] + _handler_id = self.dic_handler_id[signal_str] self.handler_block(_handler_id) - self.set_text(_value) + self.set_text(_value_str) self.handler_unblock(_handler_id) except KeyError: - self.set_text(_value) + self.set_text(_value_str) class RAMSTKTextView(Gtk.TextView, RAMSTKWidget): @@ -105,47 +108,53 @@ class RAMSTKTextView(Gtk.TextView, RAMSTKWidget): _default_height = 100 _default_width = 200 - def __init__(self, txvbuffer: Gtk.TextBuffer) -> None: + def __init__(self, buffer_obj: Gtk.TextBuffer) -> None: """Create RAMSTK TextView() widgets. Returns a Gtk.TextView() embedded in a Gtk.ScrolledWindow(). - :param txvbuffer: the Gtk.TextBuffer() to associate with the - RAMSTKTextView(). + :param buffer_obj: the Gtk.TextBuffer() to associate with the RAMSTKTextView(). :return: None :rtype: None """ RAMSTKWidget.__init__(self) - self.set_buffer(txvbuffer) + self.set_buffer(buffer_obj) self.set_wrap_mode(Gtk.WrapMode.WORD) self.scrollwindow = Gtk.ScrolledWindow() self.scrollwindow.set_policy(Gtk.PolicyType.AUTOMATIC, Gtk.PolicyType.AUTOMATIC) self.scrollwindow.add_with_viewport(self) - self.tag_bold = txvbuffer.create_tag("bold", weight=Pango.Weight.BOLD) + self.tag_bold = buffer_obj.create_tag("bold", weight=Pango.Weight.BOLD) # pylint: disable=arguments-differ def connect( self, - signal: str, - callback: Callable, - index: int, - message: str, + signal_str: str, + callback_obj: Callable, + position_idx: int, + message_str: str, ) -> int: """Connect textview's buffer to a callback method or function. - :param signal: - :param callback: - :param index: - :param message: + :param signal_str: the name of the signal whose handler ID the Gtk.TextBuffer() + needs to block. + :param callback_obj: the function or method to handle RAMSTKTextView() edits. + :param position_idx: the index position in the view using the RAMSTKTextView(). + :param message_str: the pubsub message the RAMSTKTextView() responds to. """ - _buffer = self.do_get_buffer() - return _buffer.connect(signal, callback, index, message, self) + _buffer_obj = self.do_get_buffer() + return _buffer_obj.connect( + signal_str, + callback_obj, + position_idx, + message_str, + self, + ) def do_get_buffer(self) -> Gtk.TextBuffer: - """Return the Gtk.TextBuffer() emedded in the RAMSTK TextView. + """Return the Gtk.TextBuffer() emedded in the RAMSTKTextView(). :return: buffer; the embedded Gtk.TextBuffer() :rtype: :class:`Gtk.TextBuffer` @@ -158,9 +167,10 @@ def do_get_text(self) -> Any: :return: text; the text in the Gtk.TextBuffer(). :rtype: str """ - _buffer = self.do_get_buffer() + _buffer_obj = self.do_get_buffer() + _start_obj, _end_obj = _buffer_obj.get_bounds() - return _buffer.get_text(*_buffer.get_bounds(), True) + return _buffer_obj.get_text(_start_obj, _end_obj, True) def do_set_properties(self, **kwargs: Any) -> None: """Set the properties of the RAMSTK TextView. @@ -180,26 +190,29 @@ def do_set_properties(self, **kwargs: Any) -> None: self.scrollwindow.set_property("width-request", self.width) self.scrollwindow.set_shadow_type(Gtk.ShadowType.ETCHED_OUT) - def do_update(self, value: str, signal: str = "") -> None: + def do_update( + self, + value_str: str, + signal_str: str = "changed", + ) -> None: """Update the RAMSTK TextView with a new value. - :param value: the information to update the RAMSTKTextView() to - display. - :keyword str signal: the name of the signal whose handler ID the - RAMSTKTextView() needs to block. + :param value_str: the information to update the RAMSTKTextView() to display. + :param signal_str: the name of the signal whose handler ID the RAMSTKTextView() + needs to block. :return: None :rtype: None """ - _buffer = self.do_get_buffer() + _buffer_obj = self.do_get_buffer() # Sometimes there is no handler ID for the RAMSTKTextView(). This # usually happens when the widget is being used to display results # and has no associated callback method. try: - _handler_id = self.dic_handler_id[signal] + _handler_id = self.dic_handler_id[signal_str] - _buffer.handler_block(_handler_id) - _buffer.set_text(str(value)) - _buffer.handler_unblock(_handler_id) + _buffer_obj.handler_block(_handler_id) + _buffer_obj.set_text(value_str) + _buffer_obj.handler_unblock(_handler_id) except KeyError: - _buffer.set_text(str(value)) + _buffer_obj.set_text(value_str) diff --git a/src/ramstk/views/gtk3/widgets/label.py b/src/ramstk/views/gtk3/widgets/label.py index 1b599989c..7df99f4c1 100644 --- a/src/ramstk/views/gtk3/widgets/label.py +++ b/src/ramstk/views/gtk3/widgets/label.py @@ -31,7 +31,7 @@ def __init__(self, text: str) -> None: """ RAMSTKWidget.__init__(self) - self.set_markup("" + text + "") + self.set_markup(f"{text}") self.show_all() def get_attribute(self, attribute: str) -> Any: @@ -69,35 +69,38 @@ def do_set_properties(self, **kwargs: Any) -> None: """ super().do_set_properties(**kwargs) - _bold = kwargs.get("bold", True) - _justify = kwargs.get("justify", Gtk.Justification.LEFT) - _wrap = kwargs.get("wrap", False) + _angle_flt = kwargs.get("angle", 0.0) + _bold_flag = kwargs.get("bold", True) + _justify_int = kwargs.get("justify", Gtk.Justification.LEFT) + _selectable_flag = kwargs.get("selectable", False) + _wrap_flag = kwargs.get("wrap", False) - self.set_property("wrap", _wrap) - self.set_property("justify", _justify) - if _justify == Gtk.Justification.CENTER: + self.set_property("justify", _justify_int) + self.set_property("selectable", _selectable_flag) + self.set_property("wrap", _wrap_flag) + if _justify_int == Gtk.Justification.CENTER: self.set_xalign(0.5) - elif _justify == Gtk.Justification.LEFT: + elif _justify_int == Gtk.Justification.LEFT: self.set_xalign(0.05) else: self.set_xalign(0.99) self.set_yalign(0.5) - if _bold: - _text = self.get_property("label") - _text = "" + _text + "" - self.set_markup(_text) + if _bold_flag: + _label_str = self.get_property("label") + _label_str = f"{_label_str}" + self.set_markup(_label_str) # pylint: disable=unused-argument - def do_update(self, text: str, signal: str = "") -> None: + def do_update(self, text: str, signal_str: str = "") -> None: """Update the text displayed by the label. :param text: the information to update the RAMSTKLabel() to display. - :param signal: the name of the signal whose handler ID the RAMSTKLabel() + :param signal_str: the name of the signal whose handler ID the RAMSTKLabel() needs to block. Unused in this method, but required for compatibility. :return: None :rtype: None """ - self.set_markup("" + text + "") + self.set_markup(f"{text}") def do_make_label_group( diff --git a/src/ramstk/views/gtk3/widgets/treeview.py b/src/ramstk/views/gtk3/widgets/treeview.py index 8c670eabd..d376cf31a 100644 --- a/src/ramstk/views/gtk3/widgets/treeview.py +++ b/src/ramstk/views/gtk3/widgets/treeview.py @@ -7,9 +7,10 @@ # Copyright since 2007 Doyle "weibullguy" Rowland doyle.rowland reliaqual com """RAMSTKTreeView Module.""" + # Standard Library Imports -import datetime -from typing import Any, Callable, Dict, List, Tuple +import contextlib +from typing import Any, Callable, Dict, List, Tuple, Union # Third Party Imports # noinspection PyPackageRequirements @@ -17,93 +18,117 @@ import treelib # RAMSTK Package Imports -from ramstk.utilities import deprecated, string_to_boolean -from ramstk.views.gtk3 import Gdk, GdkPixbuf, GObject, Gtk, Pango +from ramstk.utilities import string_to_boolean +from ramstk.views.gtk3 import Gdk, GdkPixbuf, GObject, Gtk, Pango, _ # RAMSTK Local Imports from .label import RAMSTKLabel from .widget import RAMSTKWidget -def do_make_column(cells: List[object], **kwargs: Dict[str, Any]) -> Gtk.TreeViewColumn: +def do_make_column( + cells_lst: List[Gtk.CellRenderer], + **kwargs, +) -> Gtk.TreeViewColumn: """Make a Gtk.TreeViewColumn(). - :param list cells: list of Gtk.CellRenderer()s that are to be packed in - the column. - :return: _column + :param list cells_lst: list of Gtk.CellRenderer()s that are to be packed in the + column. + :return: _column_obj :rtype: :class:`Gtk.TreeViewColumn` """ - _heading = kwargs.get("heading", "") - _visible = kwargs.get("visible", True) - - _column = Gtk.TreeViewColumn("") - - for _cell in cells: - if isinstance(_cell, Gtk.CellRendererPixbuf): - _column.pack_start(_cell, False) + _header_str = kwargs.get("heading", "") + _tooltip_str = kwargs.get( + "tooltip", + _("Missing tooltip, please file a type:style issue to have one added."), + ) + _visible_flag = kwargs.get("visible", True) + + _column_obj: Gtk.TreeViewColumn = Gtk.TreeViewColumn("") + + for _cell_obj in cells_lst: + if isinstance(_cell_obj, Gtk.CellRendererPixbuf): + _column_obj.pack_start(_cell_obj, False) else: - _column.pack_start(_cell, True) - - _label = RAMSTKLabel(_heading) # type: ignore - _label.do_set_properties(width=-1, height=-1, justify=Gtk.Justification.CENTER) - _column.set_widget(_label) - _column.set_resizable(True) - _column.set_alignment(0.5) - _column.set_visible(_visible) - - return _column - - -def do_set_cell_properties(cell: object, properties: Dict[str, Any]) -> None: + _column_obj.pack_start(_cell_obj, True) + + _label_obj = RAMSTKLabel(_header_str) + _label_obj.do_set_properties( + height=-1, + justify=Gtk.Justification.CENTER, + tooltip=_tooltip_str, + width=-1, + ) + _column_obj.set_widget(_label_obj) + _column_obj.set_resizable(True) + _column_obj.set_alignment(0.5) + _column_obj.set_visible(_visible_flag) + + return _column_obj + + +def do_set_cell_properties( + cell_obj: Union[ + Gtk.CellRendererCombo, + Gtk.CellRendererSpin, + Gtk.CellRendererText, + Gtk.CellRendererToggle, + ], + property_dic: Dict[str, Union[bool, float, int, str]], +) -> None: """Set common properties of Gtk.CellRenderers(). - :param cell: the cell whose properties are to be set. - :param properties: the properties for the cell. + :param cell_obj: the Gtk.CellRenderer() object whose properties are to be set. + :param property_dic: the dictionary of properties for the cell. :return: None :rtype: None """ - _bg_color = properties.get("bg_color", "#FFFFFF") - _digits = properties.get("digits", 2) - _editable = properties.get("editable", False) - _fg_color = properties.get("fg_color", "#000000") - _lower = properties.get("lower", 1) - _step = properties.get("step", 1) - _upper = properties.get("upper", 10) - _visible = properties.get("visible", True) - _weight = properties.get("weight", 400) - _weight_set = properties.get("weight_set", False) - - if not _editable: - _color = Gdk.RGBA(255.0, 255.0, 255.0, 1.0) - _fg_color = "#000000" - cell.set_property("cell-background-rgba", _color) # type: ignore - - cell.set_property("visible", _visible) # type: ignore - cell.set_property("yalign", 0.1) # type: ignore - - if isinstance(cell, Gtk.CellRendererCombo): - _cellmodel = Gtk.ListStore(GObject.TYPE_STRING) - _cellmodel.append([""]) - cell.set_property("editable", _editable) - cell.set_property("has-entry", False) - cell.set_property("model", _cellmodel) - cell.set_property("text-column", 0) - elif isinstance(cell, Gtk.CellRendererSpin): - _adjustment = Gtk.Adjustment(lower=_lower, upper=_upper, step_incr=_step) - cell.set_property("adjustment", _adjustment) - cell.set_property("digits", _digits) - cell.set_property("editable", _editable) - elif isinstance(cell, Gtk.CellRendererText): - cell.set_property("background", _bg_color) - cell.set_property("editable", _editable) - cell.set_property("foreground", _fg_color) - cell.set_property("weight", _weight) - cell.set_property("weight-set", _weight_set) - cell.set_property("wrap-width", 250) - cell.set_property("wrap-mode", Pango.WrapMode.WORD) - elif isinstance(cell, Gtk.CellRendererToggle): - cell.set_property("activatable", _editable) - cell.set_property("cell-background", _bg_color) + _bg_color_str = property_dic.get("bg_color", "#FFFFFF") + _visible_digits_int = property_dic.get("digits", 2) + _editable_flag = property_dic.get("editable", False) + _fg_color_str = property_dic.get("fg_color", "#000000") + _lower_limit_int = property_dic.get("lower", 1) + _step_int = property_dic.get("step", 1) + _upper_limit_int = property_dic.get("upper", 10) + _visible_flag = property_dic.get("visible", True) + _font_weight_int = property_dic.get("weight", 400) + _weight_set_flag = property_dic.get("weight_set", False) + + if not _editable_flag: + _color_obj = Gdk.RGBA(255.0, 255.0, 255.0, 1.0) + _fg_color_str = "#000000" + cell_obj.set_property("cell-background-rgba", _color_obj) # type: ignore + + cell_obj.set_property("visible", _visible_flag) # type: ignore + cell_obj.set_property("yalign", 0.1) # type: ignore + + if isinstance(cell_obj, Gtk.CellRendererCombo): + _cellmodel_obj = Gtk.ListStore(GObject.TYPE_STRING) + _cellmodel_obj.append([""]) + cell_obj.set_property("editable", _editable_flag) + cell_obj.set_property("has-entry", False) + cell_obj.set_property("model", _cellmodel_obj) + cell_obj.set_property("text-column", 0) + elif isinstance(cell_obj, Gtk.CellRendererSpin): + _adjustment_obj = Gtk.Adjustment( + lower=_lower_limit_int, + upper=_upper_limit_int, + step_incr=_step_int, + ) + cell_obj.set_property("adjustment", _adjustment_obj) + cell_obj.set_property("digits", _visible_digits_int) + cell_obj.set_property("editable", _editable_flag) + elif isinstance(cell_obj, Gtk.CellRendererText): + cell_obj.set_property("background", _bg_color_str) + cell_obj.set_property("editable", _editable_flag) + cell_obj.set_property("foreground", _fg_color_str) + cell_obj.set_property("weight", _font_weight_int) + cell_obj.set_property("weight-set", _weight_set_flag) + cell_obj.set_property("wrap-width", 250) + cell_obj.set_property("wrap-mode", Pango.WrapMode.WORD) + elif isinstance(cell_obj, Gtk.CellRendererToggle): + cell_obj.set_property("activatable", _editable_flag) + cell_obj.set_property("cell-background", _bg_color_str) class RAMSTKTreeView(Gtk.TreeView, RAMSTKWidget): @@ -145,155 +170,148 @@ def __init__(self) -> None: def do_change_cell( self, - cell: Gtk.CellRenderer, - path: str, - new_row: Gtk.TreeIter, - position: int, - ) -> Any: - """Handle Gtk.CellRenderer() edits. - - :param cell: the Gtk.CellRenderer() that was edited. - :param path: the Gtk.TreeView() path of the Gtk.CellRenderer() that + cell_obj: Gtk.CellRendererCombo, + path_str: str, + new_row_obj: Gtk.TreeIter, + position_int: int, + ) -> int: + """Handle Gtk.CellRendererCombo() edits. + + :param cell_obj: the Gtk.CellRendererCombo() that was edited. + :param path_str: the Gtk.TreeView() path of the Gtk.CellRendererCombo() that was edited. - :param new_row: the new Gtk.TreeIter() selected in the + :param new_row_obj: the new Gtk.TreeIter() selected in the Gtk.CellRendererCombo(). This is relative to the cell renderer's model, not the RAMSTKTreeView() model. - :param position: the column position of the edited - Gtk.CellRenderer(). - :return: new_text; the value of the new text converted to the - correct data type for the attribute being edited. + :param position_int: the column position of the edited Gtk.CellRendererCombo(). + :return: _position_idx; the position in the Gtk.CellRenderCombo() list that + was selected. """ - _model = self.get_model() - _cell_model = cell.get_property("model") + _model_obj: Gtk.TreeModel = self.get_model() + _cell_model_obj: Gtk.TreeModel = cell_obj.get_property("model") - _new_text = _cell_model.get_value(new_row, 0) + _new_text_obj: GObject.Value = _cell_model_obj.get_value(new_row_obj, 0) + _iter_obj: Gtk.TreeIter = _cell_model_obj.get_iter_first() - _idx = 0 - _iter = _cell_model.get_iter_first() - while _iter is not None: - if _cell_model.get_value(_iter, 0) == _new_text: - _model[path][position] = _new_text + _selected_pos_idx: int = 0 + while _iter_obj is not None: + if _cell_model_obj.get_value(_iter_obj, 0) == _new_text_obj: + _model_obj[path_str][position_int] = _new_text_obj break - _iter = _cell_model.iter_next(_iter) - _idx += 1 + _iter_obj = _cell_model_obj.iter_next(_iter_obj) + _selected_pos_idx += 1 - return _idx + return _selected_pos_idx def do_edit_cell( - self, cell: Gtk.CellRenderer, path: str, new_text: Any, position: int - ) -> Any: + self, + cell_obj: Gtk.CellRenderer, + path_str: str, + new_text_obj: Union[bool, float, int, str], + position_int: int, + ) -> Union[bool, float, int, str]: """Handle Gtk.CellRenderer() edits. - :param cell: the Gtk.CellRenderer() that was edited. - :param path: the Gtk.TreeView() path of the Gtk.CellRenderer() that - was edited. - :param new_text: the new text in the edited Gtk.CellRenderer(). - :param position: the column position of the edited - Gtk.CellRenderer(). - :return: new_text; the value of the new text converted to the - correct data type for the attribute being edited. + :param cell_obj: the Gtk.CellRenderer() that was edited. + :param path_str: the Gtk.TreeView() path of the Gtk.CellRenderer() that was + edited. + :param new_text_obj: the new text in the edited Gtk.CellRenderer(). + :param position_int: the column position of the edited Gtk.CellRenderer(). + :return: new_text_obj; the value of the new text converted to the correct data + type for the attribute being edited. :rtype: Any """ - _model = self.get_model() - _convert = GObject.type_name(_model.get_column_type(position)) - - if isinstance(cell, Gtk.CellRendererToggle): - new_text = not cell.get_active() - elif _convert == "gchararray": - new_text = str(new_text) - elif _convert == "gint": + _model_obj: Gtk.TreeModel = self.get_model() + _col_data_type_str: str = GObject.type_name( + _model_obj.get_column_type(position_int) + ) + + if isinstance(cell_obj, Gtk.CellRendererToggle): + new_text_obj = not cell_obj.get_active() + elif _col_data_type_str == "gchararray": + new_text_obj = str(new_text_obj) + elif _col_data_type_str == "gint": try: - new_text = int(new_text) + new_text_obj = int(new_text_obj) except ValueError: - new_text = int(float(new_text)) - elif _convert == "gfloat": - new_text = float(new_text) - - _model[path][position] = new_text + new_text_obj = int(float(new_text_obj)) + elif _col_data_type_str == "gfloat": + new_text_obj = float(new_text_obj) - return new_text + _model_obj[path_str][position_int] = new_text_obj - @deprecated - def do_expand_tree(self) -> None: - """Expand the RAMSTKTreeView(). + return new_text_obj - Currently unused. Determine if it has value. - - :return: None - :rtype: None - """ - _model = self.get_model() - try: - _row = _model.get_iter_first() - except AttributeError: - _row = None - - self.expand_all() - if _row is not None: - _path = _model.get_path(_row) - _column = self.get_column(0) - self.set_cursor(_path, None, False) - self.row_activated(_path, _column) - - def do_get_row_by_value(self, search_col: int, value: Any) -> Gtk.TreeIter: + def do_get_row_by_value(self, search_col_int: int, value_obj: Any) -> Gtk.TreeIter: """Find the row in the RAMSTKTreeView() containing the passed value. - :param search_col: the column number to search for the desired value. - :param value: the value to match. - :return: _iter; the Gtk.TreeIter() for the matching row. + :param search_col_int: the column number to search for the desired value. + :param value_obj: the value to match. + :return: _row_obj; the Gtk.TreeIter() for the matching row. :rtype: :class:`Gtk.TreeIter` """ - _row = self.unfilt_model.get_iter_first() + _row_obj = self.unfilt_model.get_iter_first() while ( - _row is not None and self.unfilt_model.get_value(_row, search_col) != value + _row_obj is not None + and self.unfilt_model.get_value(_row_obj, search_col_int) != value_obj ): - _row = self.unfilt_model.iter_next(_row) + _row_obj = self.unfilt_model.iter_next(_row_obj) - return _row + return _row_obj - def do_insert_row(self, data: Dict[str, Any], prow: Gtk.TreeIter = None) -> None: + def do_insert_row( + self, data_dic: Dict[str, Any], prow_obj: Gtk.TreeIter = None + ) -> None: """Insert a new row in the treeview. - :param data: the data dictionary for the new row to insert. - :param prow: the parent row of the row to insert. + :param data_dic: the data dictionary for the new row to insert. + :param prow_obj: the parent row of the row to insert. :return: None :rtype: None """ - _model, _row = self.selection.get_selected() + _model_obj, _row_obj = self.selection.get_selected() - _data = [data[_key] for _key in self.position] + _data_obj = [data_dic[_position_idx] for _position_idx in self.position] - _row = _model.append(prow, _data) + _row_obj = _model_obj.append(prow_obj, _data_obj) - _path = _model.get_path(_row) - _column = self.get_column(0) - self.set_cursor(_path, None, False) - self.row_activated(_path, _column) + _path_str = _model_obj.get_path(_row_obj) + _column_obj = self.get_column(0) + self.set_cursor(_path_str, None, False) + self.row_activated(_path_str, _column_obj) - def do_load_combo_cell(self, index: int, items: List[str]) -> None: + def do_load_combo_cell(self, column_idx: int, item_lst: List[str]) -> None: """Load items into cell with combobox. - :param index: the index in the RAMSTKTreeView() model of the + :param column_idx: the index in the RAMSTKTreeView() model of the Gtk.CellRendererCombo() to load. - :param items: the list of entries to load into the Gtk.CellRendererCombo(). + :param item_lst: the list of entries to load into the Gtk.CellRendererCombo(). :return: None :rtype: None """ - _model = self.get_cell_model(index) - for _item in items: - _model.append([_item]) + _model_obj = self.get_cell_model(column_idx) + for _item_str in item_lst: + _model_obj.append([_item_str]) - def do_load_tree(self, tree: treelib.Tree, row: Gtk.TreeIter = None) -> None: - """Load the RAMSTKTreeView with the contents of the tree.""" - _row = None - _node = tree.get_node(tree.root) + def do_load_tree( + self, tree_obj: treelib.Tree, row_obj: Gtk.TreeIter = None + ) -> None: + """Load the RAMSTKTreeView() with the contents of the treelib Tree(). + + :param tree_obj: the treelib.Tree() to load into the RAMSTKTreeView. + :param row_obj: the current row to load. + :return: None + :rtype: None + """ + _row_obj = None + _node_obj = tree_obj.get_node(tree_obj.root) - if _node.data is not None: - _row = self.dic_row_loader[_node.tag](_node, row) + if _node_obj.data is not None: + _row_obj = self.dic_row_loader[_node_obj.tag](_node_obj, row_obj) - for _n in tree.children(_node.identifier): - self.do_load_tree(tree.subtree(_n.identifier), _row) + for _child_node_obj in tree_obj.children(_node_obj.identifier): + self.do_load_tree(tree_obj.subtree(_child_node_obj.identifier), _row_obj) def do_make_columns(self) -> None: """Make the columns for the RAMSTKTreeView(). @@ -301,42 +319,51 @@ def do_make_columns(self) -> None: :return: None :rtype: None """ - for _key, _position in self.position.items(): - _cell = self.widgets[_key] - _properties = { - "editable": self.editable[_key], - **self.cellprops[_key], + for _column_name_str, _position_int in self.position.items(): + _cell_obj = self.widgets[_column_name_str] + _property_dic: Dict[str, Union[bool, float, int, str]] = { + "editable": self.editable[_column_name_str], + **self.cellprops[_column_name_str], } + do_set_cell_properties( - _cell, - properties=_properties, + _cell_obj, + property_dic=_property_dic, ) + # If creating a RAMSTKTreeView() that displays icons and this is # the first column we're creating, add a Gtk.CellRendererPixbuf() # to go along with the data in the first column. - if self._has_pixbuf and _position == 0: - _pbcell = Gtk.CellRendererPixbuf() - _pbcell.set_property("xalign", 0.5) - _pbcell.set_property("cell-background", _properties["bg_color"]) - _column = do_make_column( - [_pbcell, _cell], + if self._has_pixbuf and _position_int == 0: + _pbcell_obj = Gtk.CellRendererPixbuf() + _pbcell_obj.set_property("xalign", 0.5) + _pbcell_obj.set_property("cell-background", _property_dic["bg_color"]) + _column_obj: Gtk.TreeViewColumn = do_make_column( + [_pbcell_obj, _cell_obj], heading="", # type: ignore visible=True, # type: ignore ) - _column.set_attributes(_pbcell, pixbuf=len(self.position.values())) + _column_obj.set_attributes( + _pbcell_obj, pixbuf=len(self.position.values()) + ) else: - _column = do_make_column( - [_cell], - heading=self.headings[_key], # type: ignore - visible=string_to_boolean(self.visible[_key]), # type: ignore + # noinspection PyTypeChecker + _column_obj = do_make_column( + [_cell_obj], + heading=self.headings[_column_name_str], # type: ignore + visible=string_to_boolean( # type: ignore + self.visible[_column_name_str], + ), ) - _column.set_cell_data_func( - _cell, self._do_format_cell, (_position, self.datatypes[_key]) + _column_obj.set_cell_data_func( + _cell_obj, + self._do_format_cell, + (_position_int, self.datatypes[_column_name_str]), ) - self._do_set_column_properties(_key, _column) - self.append_column(_column) + self._do_set_column_properties(_column_name_str, _column_obj) + self.append_column(_column_obj) def do_make_model(self) -> None: """Make the RAMSTKTreeView() data model. @@ -344,60 +371,75 @@ def do_make_model(self) -> None: :return: None :rtype: None """ - _types = [ - GObject.type_from_name(_datatype) - for __, _datatype in self.datatypes.items() + _data_type_lst = [ + GObject.type_from_name(_datatype_str) + for __, _datatype_str in self.datatypes.items() ] if self._has_pixbuf: - _types.append(GdkPixbuf.Pixbuf) + _data_type_lst.append(GdkPixbuf.Pixbuf) - self.unfilt_model = Gtk.TreeStore(*_types) + self.unfilt_model = Gtk.TreeStore(*_data_type_lst) self.set_model(self.unfilt_model) # noinspection PyTypeChecker - def do_parse_format(self, fmt_file: str) -> None: + def do_parse_format(self, fmt_file_path_str: str) -> None: """Parse the format file for the RAMSTKTreeView(). - :param fmt_file: the absolute path to the format file to read. + :param fmt_file_path_str: the absolute path to the format file to read. :return: None :rtype: None """ - _format = toml.load(fmt_file) + _format_dic = toml.load(fmt_file_path_str) - self._has_pixbuf = string_to_boolean(_format["pixbuf"]) + self._has_pixbuf = string_to_boolean(_format_dic["pixbuf"]) self.position = {} - _keys = sorted(_format["position"], key=_format["position"].get) - for _key in _keys: - self.position[_key] = _format["position"][_key] - self.editable[_key] = string_to_boolean(_format["editable"][_key]) - self.visible[_key] = string_to_boolean(_format["visible"][_key]) + _column_name_lst = sorted( + _format_dic["position"], key=_format_dic["position"].get + ) + for _column_name_str in _column_name_lst: + self.position[_column_name_str] = _format_dic["position"][_column_name_str] + self.editable[_column_name_str] = string_to_boolean( + _format_dic["editable"][_column_name_str] + ) + self.visible[_column_name_str] = string_to_boolean( + _format_dic["visible"][_column_name_str] + ) - self.headings = _format["usertitle"] + self.headings = _format_dic["usertitle"] - def do_set_editable_columns(self, method: object) -> None: + def do_set_editable_columns(self, edit_method_obj: object) -> None: """Set the treeview columns editable or read-only. - :param method: the callback method for the cell. + :param edit_method_obj: the callback method for the cell. :return: None """ - for _key in self.editable: - _column = self.get_column(self.position[_key]) + for _column_name_str in self.editable: + _column_obj = self.get_column(self.position[_column_name_str]) # Get the last cell so those columns containing a # Gtk.CellRendererPixBuf() will return the Gtk.CellRendererText() # that is packed with it. If there is only one cell renderer, # that is the one that will be returned. - _cell = _column.get_cells()[-1] - - if isinstance(self.widgets[_key], Gtk.CellRendererToggle): - _cell.connect("toggled", method, None, self.position[_key]) + _cell_obj = _column_obj.get_cells()[-1] + + if isinstance(self.widgets[_column_name_str], Gtk.CellRendererToggle): + _cell_obj.connect( + "toggled", + edit_method_obj, + None, + self.position[_column_name_str], + ) elif isinstance( - self.widgets[_key], + self.widgets[_column_name_str], (Gtk.CellRendererSpin, Gtk.CellRendererText), ): - _cell.connect("edited", method, self.position[_key]) + _cell_obj.connect( + "edited", + edit_method_obj, + self.position[_column_name_str], + ) def do_set_visible_columns(self) -> None: """Set the treeview columns visible or hidden. @@ -405,285 +447,120 @@ def do_set_visible_columns(self) -> None: :return: None :rtype: None """ - for _key, _visible in self.visible.items(): - _column = self.get_column(self.position[_key]) - _column.set_visible(_visible) - - def get_aggregate_attributes(self, entity: object) -> List[Any]: - """Get the attributes for aggregate work stream modules. - - :param entity: the RAMSTK Program database table whose attributes - are to be returned. - :return: _attributes; a list of the attributes values in the order - they will be displayed. - :rtype: list - """ - _attributes = [] - try: - for _key in self.position: - if _key == "dict": - _attributes.append(str(entity)) - else: - try: - if isinstance(entity[_key], datetime.date): # type: ignore - entity[_key] = entity[_key].strftime( # type: ignore - "%Y-%m-%d" - ) - entity[_key] = entity[_key].decode("utf-8") # type: ignore - except (AttributeError, KeyError): - pass - _attributes.append(entity[_key]) # type: ignore - except TypeError: - pass - - return _attributes - - def get_cell_model(self, column: int, clear: bool = True) -> Gtk.TreeModel: + for _column_name_str, _visible_flag in self.visible.items(): + _column_obj = self.get_column(self.position[_column_name_str]) + _column_obj.set_visible(_visible_flag) + + def get_cell_model(self, column_obj: int, clear_flag: bool = True) -> Gtk.TreeModel: """Retrieve the Gtk.TreeModel() from a Gtk.CellRendererCombo(). - :param column: the column number to retrieve the cell's model. - :param clear: whether to clear the Gtk.TreeModel(). Default is True. - :return: _model + :param column_obj: the column number to retrieve the cell's model. + :param clear_flag: whether to clear the Gtk.TreeModel(). Default is True. + :return: _model_obj :rtype: :class:`Gtk.TreeModel` """ - _column = self.get_column(column) - _cell = _column.get_cells()[0] - _model = _cell.get_property("model") - - if clear: - _model.clear() + _column_obj = self.get_column(column_obj) + _cell_obj = _column_obj.get_cells()[0] + _model_obj = _cell_obj.get_property("model") - return _model + if clear_flag: + _model_obj.clear() - def get_simple_attributes(self, entity: object) -> List[Any]: - """Get the attributes for simple work stream modules. - - :param entity: the RAMSTK Program database table whose attributes - are to be returned. - :return: _attributes; a list of the attributes values in the order - they will be displayed. - :rtype: list - """ - _attributes = [] - _temp = entity.get_attributes() # type: ignore - - for _key in self.position: - try: - if isinstance(_temp[_key], datetime.date): - _temp[_key] = _temp[_key].strftime("%Y-%m-%d") - _temp[_key] = _temp[_key].decode("utf-8") - except (AttributeError, KeyError): - pass - _attributes.append(_temp[_key]) - - return _attributes + return _model_obj @staticmethod def _do_format_cell( - __column: Gtk.TreeViewColumn, - cell: Gtk.CellRenderer, - model: Gtk.TreeModel, - row: Gtk.TreeIter, - data: Tuple[Any], + __column_obj: Gtk.TreeViewColumn, + cell_obj: Gtk.CellRenderer, + model_obj: Gtk.TreeModel, + row_obj: Gtk.TreeIter, + data_tpl: Tuple[Any], ) -> None: """Set the formatting of the Gtk.Treeview() Gtk.CellRenderers(). - :param __column: the Gtk.TreeViewColumn() containing the - Gtk.CellRenderer() to format. - :type __column: :class:`Gtk.TreeViewColumn` - :param cell: the Gtk.CellRenderer() to format. - :type cell: :class:`Gtk.CellRenderer` - :param model: the Gtk.TreeModel() containing the Gtk.TreeViewColumn(). - :type model: :class:`Gtk.TreeModel` - :param row: the Gtk.TreeIter() pointing to the row containing the + :param __column_obj: the Gtk.TreeViewColumn() containing the + Gtk.CellRenderer() to format. Unused in this method. + :type __column_obj: :class:`Gtk.TreeViewColumn` + :param cell_obj: the Gtk.CellRenderer() to format. + :type cell_obj: :class:`Gtk.CellRenderer` + :param model_obj: the Gtk.TreeModel() containing the Gtk.TreeViewColumn(). + :type model_obj: :class:`Gtk.TreeModel` + :param row_obj: the Gtk.TreeIter() pointing to the row containing the Gtk.CellRenderer() to format. - :type row: :class:`Gtk.TreeIter` - :param tuple data: a tuple containing the position and the data type. + :type row_obj: :class:`Gtk.TreeIter` + :param data_tpl: a tuple containing the position and the data type. + :return: None + :rtype: None """ - if data[1] == "gfloat": # type: ignore - fmt = "{0:0.6g}" - elif data[1] == "gint": # type: ignore - fmt = "{0:0d}" + if data_tpl[1] == "gfloat": # type: ignore + fmt_str = "{0:0.6g}" + elif data_tpl[1] == "gint": # type: ignore + fmt_str = "{0:0d}" else: return - val = model.get_value(row, data[0]) - try: - cell.set_property("text", fmt.format(val)) - except (TypeError, ValueError): # It's a Gtk.CellRendererToggle - pass + _value_flt = model_obj.get_value(row_obj, data_tpl[0]) + with contextlib.suppress(TypeError, ValueError): + cell_obj.set_property("text", fmt_str.format(_value_flt)) - def _do_set_column_properties(self, key: str, column: Gtk.TreeViewColumn) -> None: + def _do_set_column_properties( + self, + column_name_str: str, + column_obj: Gtk.TreeViewColumn, + ) -> None: """Set the properties of the RAMSTKTreeView() column. - :param key: the value of the key in the widgets and position dicts. - :param column: the Gtk.TreeViewColumn() to set properties. + :param column_name_str: the value of the key in the widgets and position dicts. + :param column_obj: the Gtk.TreeViewColumn() to set properties. :return: None :rtype: None """ - _cell = column.get_cells()[-1] + _cell_obj = column_obj.get_cells()[-1] - if isinstance(self.widgets[key], Gtk.CellRendererToggle): - column.set_attributes(_cell, active=self.position[key]) + if isinstance(self.widgets[column_name_str], Gtk.CellRendererToggle): + column_obj.set_attributes(_cell_obj, active=self.position[column_name_str]) elif isinstance( - self.widgets[key], + self.widgets[column_name_str], ( Gtk.CellRendererCombo, Gtk.CellRendererSpin, Gtk.CellRendererText, ), ): - column.set_attributes(_cell, text=self.position[key]) + column_obj.set_attributes(_cell_obj, text=self.position[column_name_str]) - if self.position[key] > 0: - column.set_reorderable(True) + if self.position[column_name_str] > 0: + column_obj.set_reorderable(True) @staticmethod def _resize_wrap( - column: Gtk.TreeViewColumn, __param, cell: Gtk.CellRenderer + column_obj: Gtk.TreeViewColumn, + __param_obj, + cell_obj: Gtk.CellRenderer, ) -> None: """Dynamically set wrap-width property for a Gtk.CellRenderer(). This is called whenever the column width in the Gtk.TreeView() is resized. - :param column: the Gtk.TreeViewColumn() being resized. - :param GParamInt __param: the triggering parameter. - :param cell: the Gtk.CellRenderer() that needs to be resized. + :param column_obj: the Gtk.TreeViewColumn() being resized. + :param GParamInt __param_obj: the triggering parameter. Unused in this method. + :param cell_obj: the Gtk.CellRenderer() that needs to be resized. :return: None :rtype: None """ - _width = column.get_width() + _width_int = column_obj.get_width() - if _width <= 0: - _width = 25 + if _width_int <= 0: + _width_int = 25 else: - _width += 10 - - try: - cell.set_property("wrap-width", _width) - except TypeError: # This is a Gtk.CellRendererToggle - cell.set_property("width", _width) - + _width_int += 10 -class CellRendererML(Gtk.CellRendererText): - """Create a multi-line cell renderer.""" - - def __init__(self) -> None: - """Initialize a CellRendererML instance.""" - GObject.GObject.__init__(self) - - self.textedit_window = None - self.selection = None - self.treestore = None - self.treeiter = None - - self.textedit = Gtk.TextView() - self.textbuffer = self.textedit.get_buffer() - - # pylint: disable=arguments-differ - def do_get_size(self, widget, cell_area): - """Get the size of the CellRendererML. - - :param widget: - :param cell_area: - """ - return Gtk.CellRendererText.do_get_size(self, widget, cell_area) - - # pylint: disable=arguments-differ,too-many-locals - def do_start_editing( - self, __event, treeview, path, __background_area, cell_area, __flags - ): - """Handle edits of the CellRendererML. - - :param __event: - :param treeview: - :param path: - :param __background_area: - :param cell_area: - :param __flags: - """ - if not self.get_property("editable"): - return - - self.selection = treeview.get_selection() - self.treestore, self.treeiter = self.selection.get_selected() - - self.textedit_window = Gtk.Dialog(parent=treeview.get_toplevel()) - self.textedit_window.action_area.hide() - self.textedit_window.set_decorated(False) - self.textedit_window.set_property("skip-taskbar-hint", True) - self.textedit_window.set_transient_for(None) - - self.textedit.set_editable(True) - self.textedit.set_property("visible", True) - self.textbuffer.set_property("text", self.get_property("text")) - - self.textedit_window.connect("key-press-event", self._keyhandler) - - scrolled_window = Gtk.ScrolledWindow() - scrolled_window.set_policy( - Gtk.PolicyType.AUTOMATIC, - Gtk.PolicyType.AUTOMATIC, - ) - scrolled_window.set_property("visible", True) - # self.textedit_window.vbox.pack_start(scrolled_window, True, True, 0) - - scrolled_window.add(self.textedit) - self.textedit_window.vbox.add(scrolled_window) - self.textedit_window.realize() - - # Position the popup below the edited cell (and try hard to keep the - # popup within the toplevel window) - (tree_x, tree_y) = treeview.get_bin_window().get_origin() - (tree_w, tree_h) = treeview.window.get_geometry()[2:4] - (t_w, t_h) = self.textedit_window.window.get_geometry()[2:4] - x_pos = tree_x + min( - cell_area.x, - tree_w - t_w + treeview.get_visible_rect().x, - ) - y_pos = tree_y + min( - cell_area.y, - tree_h - t_h + treeview.get_visible_rect().y, - ) - self.textedit_window.move(x_pos, y_pos) - self.textedit_window.resize(cell_area.width, cell_area.height) - - # Run the dialog, get response by tracking keypresses - response = self.textedit_window.run() - - if response == Gtk.ResponseType.OK: - self.textedit_window.destroy() - - (iter_first, iter_last) = self.textbuffer.get_bounds() - text = self.textbuffer.get_text(iter_first, iter_last) - - treeview.set_cursor(path, None, False) - - self.emit("edited", path, text) - - elif response == Gtk.ResponseType.CANCEL: - self.textedit_window.destroy() + if isinstance(cell_obj, Gtk.CellRendererToggle): + cell_obj.set_property("width", _width_int) else: - print(f"response {response} received") - self.textedit_window.destroy() - - def _keyhandler(self, __widget, event): - """Handle key-press-events on the Gtk.TextView(). - - :param __widget: the Gtk.TextView() that called this method. - :param event: the Gdk.Event() that called this method. - """ - _keyname = Gdk.keyval_name(event.keyval) - - if ( - event.get_state() - & (Gdk.ModifierType.SHIFT_MASK | Gdk.ModifierType.CONTROL_MASK) - and _keyname == "Return" - ): - self.textedit_window.response(Gtk.ResponseType.OK) + cell_obj.set_property("wrap-width", _width_int) # Register the new widget types. GObject.type_register(RAMSTKTreeView) -GObject.type_register(CellRendererML) diff --git a/src/ramstk/views/gtk3/widgets/treeview.pyi b/src/ramstk/views/gtk3/widgets/treeview.pyi index a08ca47cd..b614cd789 100644 --- a/src/ramstk/views/gtk3/widgets/treeview.pyi +++ b/src/ramstk/views/gtk3/widgets/treeview.pyi @@ -1,5 +1,5 @@ # Standard Library Imports -from typing import Any, Callable, Dict, List, Tuple +from typing import Any, Callable, Dict, List, Tuple, Union, overload # RAMSTK Package Imports from ramstk.utilities import deprecated as deprecated @@ -14,10 +14,23 @@ from ramstk.views.gtk3 import Pango as Pango from .label import RAMSTKLabel as RAMSTKLabel from .widget import RAMSTKWidget as RAMSTKWidget +@overload def do_make_column( - cells: List[object], **kwargs: Dict[str, Any] + cells_lst: List[Gtk.CellRenderer], **kwargs: Dict[str, int] ) -> Gtk.TreeViewColumn: ... -def do_set_cell_properties(cell: object, properties: Dict[str, Any]) -> None: ... +@overload +def do_make_column( + cells_lst: List[Gtk.CellRenderer], **kwargs: Dict[str, str] +) -> Gtk.TreeViewColumn: ... +def do_set_cell_properties( + cell_obj: Union[ + Gtk.CellRendererCombo, + Gtk.CellRendererSpin, + Gtk.CellRendererText, + Gtk.CellRendererToggle, + ], + property_dic: Dict[str, Union[bool, float, int, str]], +) -> None: ... class RAMSTKTreeView(Gtk.TreeView, RAMSTKWidget): _has_pixbuf: bool @@ -33,10 +46,20 @@ class RAMSTKTreeView(Gtk.TreeView, RAMSTKWidget): filt_model: Gtk.TreeModelFilter unfilt_model: Gtk.TreeModel def __init__(self) -> None: ... + def do_change_cell( + self, + cell: Gtk.CellRendererCombo, + path: str, + new_row: Gtk.TreeIter, + position: int, + ) -> int: ... def do_edit_cell( - self, cell: Gtk.CellRenderer, path: str, new_text: Any, position: int - ) -> Any: ... - def do_expand_tree(self) -> None: ... + self, + cell: Gtk.CellRenderer, + path: str, + new_text: Union[bool, float, int, str], + position: int, + ) -> Union[bool, float, int, str]: ... def do_get_row_by_value(self, search_col: int, value: Any) -> Gtk.TreeIter: ... def do_insert_row(self, data: Dict[str, Any], prow: Gtk.TreeIter = ...) -> None: ... def do_load_combo_cell(self, index: int, items: List[str]) -> None: ... @@ -45,9 +68,7 @@ class RAMSTKTreeView(Gtk.TreeView, RAMSTKWidget): def do_parse_format(self, fmt_file: str) -> None: ... def do_set_editable_columns(self, method: object) -> None: ... def do_set_visible_columns(self) -> None: ... - def get_aggregate_attributes(self, entity: object) -> List[Any]: ... def get_cell_model(self, column: int, clear: bool = ...) -> Gtk.TreeModel: ... - def get_simple_attributes(self, entity: object) -> List[Any]: ... @staticmethod def _do_format_cell( __column: Gtk.TreeViewColumn, diff --git a/src/ramstk/views/gtk3/widgets/widget.py b/src/ramstk/views/gtk3/widgets/widget.py index a9cde8160..115b132c9 100644 --- a/src/ramstk/views/gtk3/widgets/widget.py +++ b/src/ramstk/views/gtk3/widgets/widget.py @@ -57,7 +57,7 @@ def do_set_properties(self, **kwargs: Any) -> None: _height = kwargs.get("height", self._default_height) _tooltip = kwargs.get( "tooltip", - _("Missing tooltip, please file a quality type issue to have one added."), + _("Missing tooltip, please file a type:style issue to have one added."), ) _width = kwargs.get("width", self._default_width) diff --git a/tests/views/gtk3/widgets/test_combo.py b/tests/views/gtk3/widgets/test_combo.py index 6aec3d34f..4f54022aa 100644 --- a/tests/views/gtk3/widgets/test_combo.py +++ b/tests/views/gtk3/widgets/test_combo.py @@ -32,8 +32,9 @@ def test_create_entry(self): @pytest.mark.gui def test_create_combobox_not_simple(self): - """__init__() should create a RAMSTKComboBox with three columns when passed simple=False.""" - DUT = RAMSTKComboBox(index=2, simple=False) + """__init__() should create a RAMSTKComboBox with three columns when passed + simple=False.""" + DUT = RAMSTKComboBox(position_idx=2, simple_flag=False) assert isinstance(DUT, RAMSTKComboBox) assert DUT._index == 2 @@ -56,7 +57,8 @@ def test_set_properties(self): @pytest.mark.gui def test_set_properties_default_values(self): - """do_set_properties() should set the default properties of a RAMSTKComboBox when no keywords are passed to the method.""" + """do_set_properties() should set the default properties of a RAMSTKComboBox + when no keywords are passed to the method.""" DUT = RAMSTKComboBox() DUT.do_set_properties() @@ -68,7 +70,8 @@ def test_set_properties_default_values(self): @pytest.mark.gui def test_set_properties_zero_height(self): - """do_set_properties() should set the height to the default value if it is passed as zero.""" + """do_set_properties() should set the height to the default value if it is + passed as zero.""" DUT = RAMSTKComboBox() DUT.do_set_properties(height=0) @@ -76,7 +79,8 @@ def test_set_properties_zero_height(self): @pytest.mark.gui def test_set_properties_zero_width(self): - """do_set_properties() should set the width to the default value if it is passed as zero.""" + """do_set_properties() should set the width to the default value if it is + passed as zero.""" DUT = RAMSTKComboBox() DUT.do_set_properties(width=0) @@ -84,7 +88,8 @@ def test_set_properties_zero_width(self): @pytest.mark.gui def test_do_load_combo_simple(self): - """do_load_combo() should load a list of string values into a simple RAMSTKComboBox.""" + """do_load_combo() should load a list of string values into a simple + RAMSTKComboBox.""" _test_list = [ ["This"], ["is"], @@ -100,19 +105,21 @@ def test_do_load_combo_simple(self): @pytest.mark.gui def test_do_load_combo_not_simple(self): - """do_load_combo() should load a list of string values into a non-simple RAMSTKComboBox.""" + """do_load_combo() should load a list of string values into a non-simple + RAMSTKComboBox.""" _test_list = [ ["This", "is", "a"], ["test", "of", "the"], ["RAMSTKComboBox", "not", "simple"], ] - DUT = RAMSTKComboBox(index=1, simple=False) + DUT = RAMSTKComboBox(position_idx=1, simple_flag=False) - assert DUT.do_load_combo(_test_list, simple=False) is None + assert DUT.do_load_combo(_test_list, simple_flag=False) is None @pytest.mark.gui def test_do_load_combo_simple_not_string_list(self): - """do_load_combo() should raise a TypeError when passed a list of other than strings to load or a single non-string value.""" + """do_load_combo() should raise a TypeError when passed a list of other than + strings to load or a single non-string value.""" _test_list = [0, 1, 2, 3, 4] DUT = RAMSTKComboBox() @@ -123,7 +130,8 @@ def test_do_load_combo_simple_not_string_list(self): @pytest.mark.gui def test_do_get_options_simple(self): - """do_get_options() should return a dict of all the options available in a simple RAMSTKComboBox.""" + """do_get_options() should return a dict of all the options available in a + simple RAMSTKComboBox.""" _test_list = [ ["This"], ["is"], @@ -151,14 +159,15 @@ def test_do_get_options_simple(self): @pytest.mark.gui def test_do_get_options_not_simple(self): - """do_load_combo() should load a list of string values into a non-simple RAMSTKComboBox.""" + """do_load_combo() should load a list of string values into a non-simple + RAMSTKComboBox.""" _test_list = [ ["This", "is", "a"], ["test", "of", "the"], ["RAMSTKComboBox", "not", "simple"], ] - DUT = RAMSTKComboBox(index=1, simple=False) - DUT.do_load_combo(_test_list, simple=False) + DUT = RAMSTKComboBox(position_idx=1, simple_flag=False) + DUT.do_load_combo(_test_list, simple_flag=False) _options = DUT.do_get_options() assert isinstance(_options, dict)