tksheet 7.4.3__py3-none-any.whl → 7.4.5__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
tksheet/sheet.py CHANGED
@@ -4,6 +4,7 @@ import tkinter as tk
4
4
  from bisect import bisect_left
5
5
  from collections import deque
6
6
  from collections.abc import Callable, Generator, Hashable, Iterator, Sequence
7
+ from contextlib import suppress
7
8
  from itertools import accumulate, chain, filterfalse, islice, product, repeat
8
9
  from operator import attrgetter
9
10
  from timeit import default_timer
@@ -54,6 +55,7 @@ from .functions import (
54
55
  )
55
56
  from .main_table import MainTable
56
57
  from .other_classes import (
58
+ Box_nt,
57
59
  DotDict,
58
60
  EventDataDict,
59
61
  FontTuple,
@@ -66,6 +68,7 @@ from .other_classes import (
66
68
  )
67
69
  from .row_index import RowIndex
68
70
  from .sheet_options import new_sheet_options
71
+ from .sorting import fast_sort_key, natural_sort_key, version_sort_key # noqa: F401
69
72
  from .themes import (
70
73
  theme_black,
71
74
  theme_dark,
@@ -121,14 +124,14 @@ class Sheet(tk.Frame):
121
124
  header_align: str = "n",
122
125
  row_index_align: str | None = None,
123
126
  index_align: str = "n",
124
- displayed_columns: list[int] = [],
127
+ displayed_columns: list[int] | None = None,
125
128
  all_columns_displayed: bool = True,
126
- displayed_rows: list[int] = [],
129
+ displayed_rows: list[int] | None = None,
127
130
  all_rows_displayed: bool = True,
128
131
  to_clipboard_delimiter: str = "\t",
129
132
  to_clipboard_quotechar: str = '"',
130
133
  to_clipboard_lineterminator: str = "\n",
131
- from_clipboard_delimiters: list[str] | str = ["\t"],
134
+ from_clipboard_delimiters: list[str] | str = "\t",
132
135
  show_default_header_for_empty: bool = True,
133
136
  show_default_index_for_empty: bool = True,
134
137
  page_up_down_select_row: bool = True,
@@ -187,6 +190,7 @@ class Sheet(tk.Frame):
187
190
  table_wrap: Literal["", "w", "c"] = "c",
188
191
  index_wrap: Literal["", "w", "c"] = "c",
189
192
  header_wrap: Literal["", "w", "c"] = "c",
193
+ sort_key: Callable = natural_sort_key,
190
194
  # colors
191
195
  outline_thickness: int = 0,
192
196
  theme: str = "light blue",
@@ -731,10 +735,14 @@ class Sheet(tk.Frame):
731
735
  - "rc_delete_row", "end_rc_delete_row", "end_delete_rows", "delete_rows"
732
736
  - "begin_rc_delete_column", "begin_delete_columns"
733
737
  - "rc_delete_column", "end_rc_delete_column","end_delete_columns", "delete_columns"
734
- - "begin_rc_insert_column", "begin_insert_column", "begin_insert_columns", "begin_add_column","begin_rc_add_column", "begin_add_columns"
735
- - "rc_insert_column", "end_rc_insert_column", "end_insert_column", "end_insert_columns", "rc_add_column", "end_rc_add_column", "end_add_column", "end_add_columns", "add_columns"
736
- - "begin_rc_insert_row", "begin_insert_row", "begin_insert_rows", "begin_rc_add_row", "begin_add_row", "begin_add_rows"
737
- - "rc_insert_row", "end_rc_insert_row", "end_insert_row", "end_insert_rows", "rc_add_row", "end_rc_add_row", "end_add_row", "end_add_rows", "add_rows"
738
+ - "begin_rc_insert_column", "begin_insert_column", "begin_insert_columns", "begin_add_column",
739
+ "begin_rc_add_column", "begin_add_columns"
740
+ - "rc_insert_column", "end_rc_insert_column", "end_insert_column", "end_insert_columns", "rc_add_column",
741
+ "end_rc_add_column", "end_add_column", "end_add_columns", "add_columns"
742
+ - "begin_rc_insert_row", "begin_insert_row", "begin_insert_rows", "begin_rc_add_row", "begin_add_row",
743
+ "begin_add_rows"
744
+ - "rc_insert_row", "end_rc_insert_row", "end_insert_row", "end_insert_rows", "rc_add_row", "end_rc_add_row",
745
+ "end_add_row", "end_add_rows", "add_rows"
738
746
  - "row_height_resize"
739
747
  - "column_width_resize"
740
748
  - "cell_select"
@@ -1610,10 +1618,7 @@ class Sheet(tk.Frame):
1610
1618
  res = list(chain.from_iterable(res))
1611
1619
  elif span.ndim == 1:
1612
1620
  # flatten sublists
1613
- if len(res) == 1 and len(res[0]) == 1:
1614
- res = res[0]
1615
- else:
1616
- res = list(chain.from_iterable(res))
1621
+ res = res[0] if len(res) == 1 and len(res[0]) == 1 else list(chain.from_iterable(res))
1617
1622
  # if span.ndim == 2 res keeps its current
1618
1623
  # dimensions as a list of lists
1619
1624
  if span.convert is not None:
@@ -2205,10 +2210,7 @@ class Sheet(tk.Frame):
2205
2210
  c_ops=False,
2206
2211
  )
2207
2212
  numrows = len(data)
2208
- if self.MT.all_rows_displayed:
2209
- displayed_ins_idx = idx
2210
- else:
2211
- displayed_ins_idx = bisect_left(self.MT.displayed_rows, idx)
2213
+ displayed_ins_idx = idx if self.MT.all_rows_displayed else bisect_left(self.MT.displayed_rows, idx)
2212
2214
  event_data = self.MT.add_rows(
2213
2215
  *self.MT.get_args_for_add_rows(
2214
2216
  data_ins_row=idx,
@@ -2586,7 +2588,7 @@ class Sheet(tk.Frame):
2586
2588
 
2587
2589
  def sort(
2588
2590
  self,
2589
- boxes: AnyIter[Sequence[int, int, int, int]] | Span | None = None,
2591
+ *box: CreateSpanTypes,
2590
2592
  reverse: bool = False,
2591
2593
  row_wise: bool = False,
2592
2594
  validation: bool = True,
@@ -2596,20 +2598,15 @@ class Sheet(tk.Frame):
2596
2598
  """
2597
2599
  Sort the data within specified box regions in the table.
2598
2600
 
2599
- This method sorts the data within one or multiple box regions defined by their coordinates. Each box's columns are sorted independently.
2601
+ This method sorts the data within one or multiple box regions defined by their coordinates.
2602
+ Each box's columns are sorted independently.
2600
2603
 
2601
2604
  Args:
2602
- boxes (AnyIter[Sequence[int, int, int, int]] | Span | None): An iterable of box coordinates. Each box is defined by:
2603
- - From Row (inclusive)
2604
- - From Column (inclusive)
2605
- - Up To Row (exclusive)
2606
- - Up To Column (exclusive)
2607
- If None, it will sort the currently selected boxes or the entire table.
2608
- If Span, it will use the span coordinates.
2605
+ boxes (CreateSpanTypes): A type that can create a Span.
2609
2606
 
2610
2607
  reverse (bool): If True, sorts in descending order. Default is False (ascending).
2611
2608
 
2612
- row_wise (bool): if True sorts cells row-wise. Default is column-wise
2609
+ row_wise (bool): if True sorts cells row-wise. Default is column-wise.
2613
2610
 
2614
2611
  validation (bool): If True, checks if the new cell values are valid according to any restrictions
2615
2612
  (e.g., dropdown validations) before applying the sort. Default is True.
@@ -2620,25 +2617,28 @@ class Sheet(tk.Frame):
2620
2617
  Note: Performance might be slow with the natural sort for very large datasets.
2621
2618
 
2622
2619
  Returns:
2623
- EventDataDict: A dictionary containing information about the sorting event, including changes made to the table.
2620
+ EventDataDict: A dictionary containing information about the sorting event,
2621
+ including changes made to the table.
2624
2622
 
2625
2623
  Raises:
2626
2624
  ValueError: If the input boxes are not in the expected format or if the data cannot be sorted.
2627
2625
 
2628
2626
  Note:
2629
- - Sorting is performed column-wise within each box.
2630
2627
  - If validation is enabled, any cell content that fails validation will not be updated.
2631
2628
  - Any cell options attached to cells will not be moved. Event data can be used to re-locate them.
2632
2629
  """
2633
- if isinstance(boxes, Span):
2634
- boxes = [boxes.coords]
2635
2630
  return self.MT.sort_boxes(
2636
- boxes=boxes, reverse=reverse, row_wise=row_wise, validation=validation, key=key, undo=undo
2631
+ boxes={Box_nt(*self.span_from_key(*box).coords): "cells"},
2632
+ reverse=reverse,
2633
+ row_wise=row_wise,
2634
+ validation=validation,
2635
+ key=key,
2636
+ undo=undo,
2637
2637
  )
2638
2638
 
2639
2639
  def sort_rows(
2640
2640
  self,
2641
- rows: AnyIter[int] | Span | None = None,
2641
+ rows: AnyIter[int] | Span | int | None = None,
2642
2642
  reverse: bool = False,
2643
2643
  validation: bool = True,
2644
2644
  key: Callable | None = None,
@@ -2646,11 +2646,13 @@ class Sheet(tk.Frame):
2646
2646
  ) -> EventDataDict:
2647
2647
  if isinstance(rows, Span):
2648
2648
  rows = rows.rows
2649
+ elif isinstance(rows, int):
2650
+ rows = (rows,)
2649
2651
  return self.RI._sort_rows(rows=rows, reverse=reverse, validation=validation, key=key, undo=undo)
2650
2652
 
2651
2653
  def sort_columns(
2652
2654
  self,
2653
- columns: AnyIter[int] | Span | None = None,
2655
+ columns: AnyIter[int] | Span | int | None = None,
2654
2656
  reverse: bool = False,
2655
2657
  validation: bool = True,
2656
2658
  key: Callable | None = None,
@@ -2658,6 +2660,8 @@ class Sheet(tk.Frame):
2658
2660
  ) -> EventDataDict:
2659
2661
  if isinstance(columns, Span):
2660
2662
  columns = columns.columns
2663
+ elif isinstance(columns, int):
2664
+ columns = (columns,)
2661
2665
  return self.CH._sort_columns(columns=columns, reverse=reverse, validation=validation, key=key, undo=undo)
2662
2666
 
2663
2667
  def sort_rows_by_column(
@@ -2755,9 +2759,9 @@ class Sheet(tk.Frame):
2755
2759
  def dropdown(
2756
2760
  self,
2757
2761
  *key: CreateSpanTypes,
2758
- values: list = [],
2762
+ values: list[object] | None = None,
2759
2763
  edit_data: bool = True,
2760
- set_values: dict[tuple[int, int], object] = {},
2764
+ set_values: dict[tuple[int, int], object] | None = None,
2761
2765
  set_value: object = None,
2762
2766
  state: Literal["normal", "readonly", "disabled"] = "normal",
2763
2767
  redraw: bool = True,
@@ -2767,6 +2771,10 @@ class Sheet(tk.Frame):
2767
2771
  validate_input: bool = True,
2768
2772
  text: None | str = None,
2769
2773
  ) -> Span:
2774
+ if values is None:
2775
+ values = []
2776
+ if set_values is None:
2777
+ set_values = {}
2770
2778
  if not search_function:
2771
2779
  search_function = dropdown_search_function
2772
2780
  v = set_value if set_value is not None else values[0] if values else ""
@@ -2791,13 +2799,13 @@ class Sheet(tk.Frame):
2791
2799
  self.del_index_cell_options_dropdown_and_checkbox(r)
2792
2800
  add_to_options(self.RI.cell_options, r, "dropdown", d)
2793
2801
  if edit_data:
2794
- set_idata(r, value=set_values[r] if r in set_values else v)
2802
+ set_idata(r, value=set_values.get(r, v))
2795
2803
  if header:
2796
2804
  for c in cols:
2797
2805
  self.del_header_cell_options_dropdown_and_checkbox(c)
2798
2806
  add_to_options(self.CH.cell_options, c, "dropdown", d)
2799
2807
  if edit_data:
2800
- set_hdata(c, value=set_values[c] if c in set_values else v)
2808
+ set_hdata(c, value=set_values.get(c, v))
2801
2809
  if table:
2802
2810
  if span.kind == "cell":
2803
2811
  for r in rows:
@@ -2805,21 +2813,21 @@ class Sheet(tk.Frame):
2805
2813
  self.del_cell_options_dropdown_and_checkbox(r, c)
2806
2814
  add_to_options(self.MT.cell_options, (r, c), "dropdown", d)
2807
2815
  if edit_data:
2808
- set_tdata(r, c, value=set_values[(r, c)] if (r, c) in set_values else v)
2816
+ set_tdata(r, c, value=set_values.get((r, c), v))
2809
2817
  elif span.kind == "row":
2810
2818
  for r in rows:
2811
2819
  self.del_row_options_dropdown_and_checkbox(r)
2812
2820
  add_to_options(self.MT.row_options, r, "dropdown", d)
2813
2821
  if edit_data:
2814
2822
  for c in cols:
2815
- set_tdata(r, c, value=set_values[(r, c)] if (r, c) in set_values else v)
2823
+ set_tdata(r, c, value=set_values.get((r, c), v))
2816
2824
  elif span.kind == "column":
2817
2825
  for c in cols:
2818
2826
  self.del_column_options_dropdown_and_checkbox(c)
2819
2827
  add_to_options(self.MT.col_options, c, "dropdown", d)
2820
2828
  if edit_data:
2821
2829
  for r in rows:
2822
- set_tdata(r, c, value=set_values[(r, c)] if (r, c) in set_values else v)
2830
+ set_tdata(r, c, value=set_values.get((r, c), v))
2823
2831
  self.set_refresh_timer(redraw)
2824
2832
  return span
2825
2833
 
@@ -2999,11 +3007,13 @@ class Sheet(tk.Frame):
2999
3007
  def format(
3000
3008
  self,
3001
3009
  *key: CreateSpanTypes,
3002
- formatter_options: dict = {},
3010
+ formatter_options: dict | None = None,
3003
3011
  formatter_class: object = None,
3004
3012
  redraw: bool = True,
3005
3013
  **kwargs,
3006
3014
  ) -> Span:
3015
+ if formatter_options is None:
3016
+ formatter_options = {}
3007
3017
  span = self.span_from_key(*key)
3008
3018
  rows, cols = self.ranges_from_span(span)
3009
3019
  kwargs = fix_format_kwargs({"formatter": formatter_class, **formatter_options, **kwargs})
@@ -4031,7 +4041,7 @@ class Sheet(tk.Frame):
4031
4041
  column: int = 0,
4032
4042
  keep_yscroll: bool = False,
4033
4043
  keep_xscroll: bool = False,
4034
- bottom_right_corner: bool = False,
4044
+ bottom_right_corner: bool | None = None,
4035
4045
  check_cell_visibility: bool = True,
4036
4046
  redraw: bool = True,
4037
4047
  ) -> Sheet:
@@ -4050,7 +4060,11 @@ class Sheet(tk.Frame):
4050
4060
  return self.MT.cell_visible(r, c)
4051
4061
 
4052
4062
  def cell_completely_visible(self, r: int, c: int, seperate_axes: bool = False) -> bool:
4053
- return self.MT.cell_completely_visible(r, c, seperate_axes)
4063
+ if seperate_axes:
4064
+ d = self.MT.cell_visibility_info(r, c)
4065
+ return d["yvis"], d["xvis"]
4066
+ else:
4067
+ return self.MT.cell_completely_visible(r, c)
4054
4068
 
4055
4069
  def set_xview(self, position: None | float = None, option: str = "moveto") -> Sheet | tuple[float, float]:
4056
4070
  if position is not None:
@@ -4504,18 +4518,14 @@ class Sheet(tk.Frame):
4504
4518
  def unbind_key_text_editor(self, key: str) -> Sheet:
4505
4519
  if key == "all":
4506
4520
  for key in self.MT.text_editor_user_bound_keys:
4507
- try:
4521
+ with suppress(Exception):
4508
4522
  self.MT.text_editor.tktext.unbind(key)
4509
- except Exception:
4510
- pass
4511
4523
  self.MT.text_editor_user_bound_keys = {}
4512
4524
  else:
4513
4525
  if key in self.MT.text_editor_user_bound_keys:
4514
4526
  del self.MT.text_editor_user_bound_keys[key]
4515
- try:
4527
+ with suppress(Exception):
4516
4528
  self.MT.text_editor.tktext.unbind(key)
4517
- except Exception:
4518
- pass
4519
4529
  return self
4520
4530
 
4521
4531
  def get_text_editor_value(self) -> str | None:
@@ -4662,24 +4672,14 @@ class Sheet(tk.Frame):
4662
4672
  Also retrieves any row or column options
4663
4673
  impacting that cell
4664
4674
  """
4665
- if isinstance(column, str):
4666
- column = alpha2idx(column)
4667
- if key is not None:
4668
- return self.MT.get_cell_kwargs(
4669
- datarn=row,
4670
- datacn=column,
4671
- key=key,
4672
- cell=cellops,
4673
- row=rowops,
4674
- column=columnops,
4675
- )
4676
- if cellops and (row, column) in self.MT.cell_options:
4677
- return self.MT.cell_options[(row, column)]
4678
- if rowops and row in self.MT.row_options:
4679
- return self.MT.row_options[row]
4680
- if columnops and column in self.MT.col_options:
4681
- return self.MT.col_options[column]
4682
- return {}
4675
+ return self.MT.get_cell_kwargs(
4676
+ datarn=row,
4677
+ datacn=alpha2idx(column) if isinstance(column, str) else column,
4678
+ key=key,
4679
+ cell=cellops,
4680
+ row=rowops,
4681
+ column=columnops,
4682
+ )
4683
4683
 
4684
4684
  def index_props(
4685
4685
  self,
@@ -4690,12 +4690,10 @@ class Sheet(tk.Frame):
4690
4690
  Retrieve options (properties - props)
4691
4691
  from a cell in the index
4692
4692
  """
4693
- if key is not None:
4694
- return self.RI.get_cell_kwargs(
4695
- datarn=row,
4696
- key=key,
4697
- )
4698
- return self.RI.cell_options[row] if row in self.RI.cell_options else {}
4693
+ return self.RI.get_cell_kwargs(
4694
+ datarn=row,
4695
+ key=key,
4696
+ )
4699
4697
 
4700
4698
  def header_props(
4701
4699
  self,
@@ -4706,14 +4704,10 @@ class Sheet(tk.Frame):
4706
4704
  Retrieve options (properties - props)
4707
4705
  from a cell in the header
4708
4706
  """
4709
- if isinstance(column, str):
4710
- column = alpha2idx(column)
4711
- if key is not None:
4712
- return self.CH.get_cell_kwargs(
4713
- datacn=column,
4714
- key=key,
4715
- )
4716
- return self.CH.cell_options[column] if column in self.CH.cell_options else {}
4707
+ return self.CH.get_cell_kwargs(
4708
+ datacn=alpha2idx(column) if isinstance(column, str) else column,
4709
+ key=key,
4710
+ )
4717
4711
 
4718
4712
  def get_cell_options(
4719
4713
  self,
@@ -4990,9 +4984,9 @@ class Sheet(tk.Frame):
4990
4984
  columns=set(),
4991
4985
  )
4992
4986
  for tag in unpack(tags):
4993
- res.cells.update(self.MT.tagged_cells[tag] if tag in self.MT.tagged_cells else set())
4994
- res.rows.update(self.MT.tagged_rows[tag] if tag in self.MT.tagged_rows else set())
4995
- res.columns.update(self.MT.tagged_columns[tag] if tag in self.MT.tagged_columns else set())
4987
+ res.cells.update(self.MT.tagged_cells.get(tag, set()))
4988
+ res.rows.update(self.MT.tagged_rows.get(tag, set()))
4989
+ res.columns.update(self.MT.tagged_columns.get(tag, set()))
4996
4990
  return res
4997
4991
 
4998
4992
  # Treeview Mode
@@ -5086,10 +5080,7 @@ class Sheet(tk.Frame):
5086
5080
  """
5087
5081
  If used without args all items are opened
5088
5082
  """
5089
- if items := set(unpack(items)):
5090
- to_open = self._tree_open(items)
5091
- else:
5092
- to_open = self._tree_open(set(self.get_children()))
5083
+ to_open = self._tree_open(items) if (items := set(unpack(items))) else self._tree_open(set(self.get_children()))
5093
5084
  return self.show_rows(
5094
5085
  rows=to_open,
5095
5086
  redraw=redraw,
@@ -5116,10 +5107,7 @@ class Sheet(tk.Frame):
5116
5107
  """
5117
5108
  If used without args all items are closed
5118
5109
  """
5119
- if items:
5120
- to_close = self._tree_close(unpack(items))
5121
- else:
5122
- to_close = self._tree_close(self.get_children())
5110
+ to_close = self._tree_close(unpack(items)) if items else self._tree_close(self.get_children())
5123
5111
  return self.hide_rows(
5124
5112
  rows=to_close,
5125
5113
  redraw=redraw,
@@ -5177,13 +5165,10 @@ class Sheet(tk.Frame):
5177
5165
  self.RI.tree_rns[parent]
5178
5166
  + index
5179
5167
  + 1
5180
- + sum(
5181
- sum(1 for _ in self.RI.get_iid_descendants(cid))
5182
- for cid in islice(self.get_children(parent), index)
5183
- )
5168
+ + sum(self.RI.num_descendants(cid) for cid in islice(self.get_children(parent), index))
5184
5169
  )
5185
5170
  else:
5186
- datarn = self.RI.tree_rns[parent] + sum(1 for _ in self.RI.get_iid_descendants(parent)) + 1
5171
+ datarn = self.RI.tree_rns[parent] + self.RI.num_descendants(parent) + 1
5187
5172
  else:
5188
5173
  if isinstance(index, int):
5189
5174
  datarn = index
@@ -5219,10 +5204,7 @@ class Sheet(tk.Frame):
5219
5204
  datarn = self._get_id_insert_row(index=index, parent=parent)
5220
5205
  rns_to_add = {}
5221
5206
  for rn, r in enumerate(data, start=datarn):
5222
- if iid_column is None:
5223
- iid = self.RI.new_iid()
5224
- else:
5225
- iid = r[iid_column]
5207
+ iid = self.RI.new_iid() if iid_column is None else r[iid_column]
5226
5208
  new_node = Node(
5227
5209
  r[text_column] if isinstance(text_column, int) else text_column if isinstance(text_column, str) else "",
5228
5210
  iid,
@@ -5315,8 +5297,8 @@ class Sheet(tk.Frame):
5315
5297
  def itemrow(self, item: str) -> int:
5316
5298
  try:
5317
5299
  return self.RI.tree_rns[item]
5318
- except Exception:
5319
- raise ValueError(f"item '{item}' does not exist.")
5300
+ except ValueError as error:
5301
+ raise ValueError(f"item '{item}' does not exist.") from error
5320
5302
 
5321
5303
  def rowitem(self, row: int, data_index: bool = False) -> str | None:
5322
5304
  try:
@@ -5537,7 +5519,7 @@ class Sheet(tk.Frame):
5537
5519
  return self.set_refresh_timer(redraw)
5538
5520
 
5539
5521
  def selection_toggle(self, *items, redraw: bool = True) -> Sheet:
5540
- selected = set(self.MT._row_index[self.displayed_row_to_data(rn)].iid for rn in self.get_selected_rows())
5522
+ selected = {self.MT._row_index[self.displayed_row_to_data(rn)].iid for rn in self.get_selected_rows()}
5541
5523
  add = []
5542
5524
  remove = []
5543
5525
  for item in unpack(items):
@@ -5905,14 +5887,12 @@ class Sheet(tk.Frame):
5905
5887
 
5906
5888
  def readonly_rows(
5907
5889
  self,
5908
- rows: list | int = [],
5890
+ rows: list[int] | int,
5909
5891
  readonly: bool = True,
5910
5892
  redraw: bool = False,
5911
5893
  ) -> Sheet:
5912
5894
  if isinstance(rows, int):
5913
5895
  rows = [rows]
5914
- else:
5915
- rows = rows
5916
5896
  if not readonly:
5917
5897
  for r in rows:
5918
5898
  if r in self.MT.row_options and "readonly" in self.MT.row_options[r]:
@@ -5926,14 +5906,12 @@ class Sheet(tk.Frame):
5926
5906
 
5927
5907
  def readonly_columns(
5928
5908
  self,
5929
- columns: list | int = [],
5909
+ columns: list[int] | int,
5930
5910
  readonly: bool = True,
5931
5911
  redraw: bool = False,
5932
5912
  ) -> Sheet:
5933
5913
  if isinstance(columns, int):
5934
5914
  columns = [columns]
5935
- else:
5936
- columns = columns
5937
5915
  if not readonly:
5938
5916
  for c in columns:
5939
5917
  if c in self.MT.col_options and "readonly" in self.MT.col_options[c]:
@@ -5949,7 +5927,7 @@ class Sheet(tk.Frame):
5949
5927
  self,
5950
5928
  row: int = 0,
5951
5929
  column: int = 0,
5952
- cells: list = [],
5930
+ cells: list[tuple[int, int]] | None = None,
5953
5931
  readonly: bool = True,
5954
5932
  redraw: bool = False,
5955
5933
  ) -> Sheet:
@@ -5978,7 +5956,7 @@ class Sheet(tk.Frame):
5978
5956
 
5979
5957
  def readonly_header(
5980
5958
  self,
5981
- columns: list = [],
5959
+ columns: list[int],
5982
5960
  readonly: bool = True,
5983
5961
  redraw: bool = False,
5984
5962
  ) -> Sheet:
@@ -5987,7 +5965,7 @@ class Sheet(tk.Frame):
5987
5965
 
5988
5966
  def readonly_index(
5989
5967
  self,
5990
- rows: list = [],
5968
+ rows: list[int],
5991
5969
  readonly: bool = True,
5992
5970
  redraw: bool = False,
5993
5971
  ) -> Sheet:
@@ -5996,7 +5974,7 @@ class Sheet(tk.Frame):
5996
5974
 
5997
5975
  def dehighlight_rows(
5998
5976
  self,
5999
- rows: list[int] | Literal["all"] = [],
5977
+ rows: list[int] | Literal["all"],
6000
5978
  redraw: bool = True,
6001
5979
  ) -> Sheet:
6002
5980
  if isinstance(rows, int):
@@ -6011,19 +5989,15 @@ class Sheet(tk.Frame):
6011
5989
  del self.RI.cell_options[r]["highlight"]
6012
5990
  else:
6013
5991
  for r in rows:
6014
- try:
5992
+ with suppress(Exception):
6015
5993
  del self.MT.row_options[r]["highlight"]
6016
- except Exception:
6017
- pass
6018
- try:
5994
+ with suppress(Exception):
6019
5995
  del self.RI.cell_options[r]["highlight"]
6020
- except Exception:
6021
- pass
6022
5996
  return self.set_refresh_timer(redraw)
6023
5997
 
6024
5998
  def dehighlight_columns(
6025
5999
  self,
6026
- columns: list[int] | Literal["all"] = [],
6000
+ columns: list[int] | Literal["all"],
6027
6001
  redraw: bool = True,
6028
6002
  ) -> Sheet:
6029
6003
  if isinstance(columns, int):
@@ -6038,14 +6012,10 @@ class Sheet(tk.Frame):
6038
6012
  del self.CH.cell_options[c]["highlight"]
6039
6013
  else:
6040
6014
  for c in columns:
6041
- try:
6015
+ with suppress(Exception):
6042
6016
  del self.MT.col_options[c]["highlight"]
6043
- except Exception:
6044
- pass
6045
- try:
6017
+ with suppress(Exception):
6046
6018
  del self.CH.cell_options[c]["highlight"]
6047
- except Exception:
6048
- pass
6049
6019
  return self.set_refresh_timer(redraw)
6050
6020
 
6051
6021
  def highlight_rows(
@@ -6087,7 +6057,7 @@ class Sheet(tk.Frame):
6087
6057
  self,
6088
6058
  row: int | Literal["all"] = 0,
6089
6059
  column: int | Literal["all"] = 0,
6090
- cells: list[tuple[int, int]] = [],
6060
+ cells: list[tuple[int, int]] | None = None,
6091
6061
  canvas: Literal["table", "index", "header"] = "table",
6092
6062
  bg: bool | None | str = False,
6093
6063
  fg: bool | None | str = False,
@@ -6141,7 +6111,7 @@ class Sheet(tk.Frame):
6141
6111
  self,
6142
6112
  row: int | Literal["all"] = 0,
6143
6113
  column: int = 0,
6144
- cells: list[tuple[int, int]] = [],
6114
+ cells: list[tuple[int, int]] | None = None,
6145
6115
  canvas: Literal["table", "row_index", "index", "header"] = "table",
6146
6116
  all_: bool = False,
6147
6117
  redraw: bool = True,
@@ -6220,7 +6190,7 @@ class Sheet(tk.Frame):
6220
6190
  self,
6221
6191
  row: int = 0,
6222
6192
  column: int = 0,
6223
- cells: list = [],
6193
+ cells: list[tuple[int, int]] | dict[tuple[int, int], str] | None = None,
6224
6194
  align: str | None = "global",
6225
6195
  redraw: bool = True,
6226
6196
  ) -> Sheet:
@@ -6237,7 +6207,7 @@ class Sheet(tk.Frame):
6237
6207
 
6238
6208
  def align_rows(
6239
6209
  self,
6240
- rows: list | dict | int = [],
6210
+ rows: list[int] | dict[int, str] | int,
6241
6211
  align: str | None = "global",
6242
6212
  align_index: bool = False,
6243
6213
  redraw: bool = True,
@@ -6262,7 +6232,7 @@ class Sheet(tk.Frame):
6262
6232
 
6263
6233
  def align_columns(
6264
6234
  self,
6265
- columns: list | dict | int = [],
6235
+ columns: list[int] | dict[int, str] | int,
6266
6236
  align: str | None = "global",
6267
6237
  align_header: bool = False,
6268
6238
  redraw: bool = True,
@@ -6287,7 +6257,7 @@ class Sheet(tk.Frame):
6287
6257
 
6288
6258
  def align_header(
6289
6259
  self,
6290
- columns: list | dict | int = [],
6260
+ columns: list[int] | dict[int, str] | int,
6291
6261
  align: str | None = "global",
6292
6262
  redraw: bool = True,
6293
6263
  ) -> Sheet:
@@ -6304,7 +6274,7 @@ class Sheet(tk.Frame):
6304
6274
 
6305
6275
  def align_index(
6306
6276
  self,
6307
- rows: list | dict | int = [],
6277
+ rows: list[int] | dict[int, str] | int,
6308
6278
  align: str | None = "global",
6309
6279
  redraw: bool = True,
6310
6280
  ) -> Sheet:
@@ -6470,11 +6440,11 @@ class Sheet(tk.Frame):
6470
6440
  c: int | Literal["all"] = 0,
6471
6441
  ) -> None:
6472
6442
  if isinstance(r, str) and r.lower() == "all" and isinstance(c, int):
6473
- for r_, c_ in self.MT.cell_options:
6443
+ for r_, _ in self.MT.cell_options:
6474
6444
  if "checkbox" in self.MT.cell_options[(r_, c)]:
6475
6445
  self.del_cell_options_checkbox(r_, c)
6476
6446
  elif isinstance(c, str) and c.lower() == "all" and isinstance(r, int):
6477
- for r_, c_ in self.MT.cell_options:
6447
+ for _, c_ in self.MT.cell_options:
6478
6448
  if "checkbox" in self.MT.cell_options[(r, c_)]:
6479
6449
  self.del_cell_options_checkbox(r, c_)
6480
6450
  elif isinstance(r, str) and r.lower() == "all" and isinstance(c, str) and c.lower() == "all":
@@ -6725,11 +6695,11 @@ class Sheet(tk.Frame):
6725
6695
  c: int | Literal["all"] = 0,
6726
6696
  ) -> None:
6727
6697
  if isinstance(r, str) and r.lower() == "all" and isinstance(c, int):
6728
- for r_, c_ in self.MT.cell_options:
6698
+ for r_, _ in self.MT.cell_options:
6729
6699
  if "dropdown" in self.MT.cell_options[(r_, c)]:
6730
6700
  self.del_cell_options_dropdown(r_, c)
6731
6701
  elif isinstance(c, str) and c.lower() == "all" and isinstance(r, int):
6732
- for r_, c_ in self.MT.cell_options:
6702
+ for _, c_ in self.MT.cell_options:
6733
6703
  if "dropdown" in self.MT.cell_options[(r, c_)]:
6734
6704
  self.del_cell_options_dropdown(r, c_)
6735
6705
  elif isinstance(r, str) and r.lower() == "all" and isinstance(c, str) and c.lower() == "all":
@@ -6823,9 +6793,11 @@ class Sheet(tk.Frame):
6823
6793
  r: int = 0,
6824
6794
  c: int = 0,
6825
6795
  set_existing_dropdown: bool = False,
6826
- values: list[object] = [],
6796
+ values: list[object] | None = None,
6827
6797
  set_value: object = None,
6828
6798
  ) -> Sheet:
6799
+ if values is None:
6800
+ values = []
6829
6801
  if set_existing_dropdown:
6830
6802
  if self.MT.dropdown.open:
6831
6803
  r_, c_ = self.MT.dropdown.get_coords()
@@ -6848,9 +6820,11 @@ class Sheet(tk.Frame):
6848
6820
  self,
6849
6821
  c: int = 0,
6850
6822
  set_existing_dropdown: bool = False,
6851
- values: list[object] = [],
6823
+ values: list[object] | None = None,
6852
6824
  set_value: object = None,
6853
6825
  ) -> Sheet:
6826
+ if values is None:
6827
+ values = []
6854
6828
  if set_existing_dropdown:
6855
6829
  if self.CH.dropdown.open:
6856
6830
  c_ = self.CH.dropdown.get_coords()
@@ -6872,9 +6846,11 @@ class Sheet(tk.Frame):
6872
6846
  self,
6873
6847
  r: int = 0,
6874
6848
  set_existing_dropdown: bool = False,
6875
- values: list[object] = [],
6849
+ values: list[object] | None = None,
6876
6850
  set_value: object = None,
6877
6851
  ) -> Sheet:
6852
+ if values is None:
6853
+ values = []
6878
6854
  if set_existing_dropdown:
6879
6855
  if self.RI.current_dropdown_window is not None:
6880
6856
  r_ = self.RI.current_dropdown_window.r
@@ -6963,11 +6939,13 @@ class Sheet(tk.Frame):
6963
6939
  self,
6964
6940
  r: int | Literal["all"],
6965
6941
  c: int | Literal["all"],
6966
- formatter_options: dict = {},
6942
+ formatter_options: dict | None = None,
6967
6943
  formatter_class: object = None,
6968
6944
  redraw: bool = True,
6969
6945
  **kwargs,
6970
6946
  ) -> Sheet:
6947
+ if formatter_options is None:
6948
+ formatter_options = {}
6971
6949
  kwargs = fix_format_kwargs({"formatter": formatter_class, **formatter_options, **kwargs})
6972
6950
  if isinstance(r, str) and r.lower() == "all" and isinstance(c, int):
6973
6951
  for r_ in range(self.MT.total_data_rows()):
@@ -6996,11 +6974,11 @@ class Sheet(tk.Frame):
6996
6974
  clear_values: bool = False,
6997
6975
  ) -> Sheet:
6998
6976
  if isinstance(r, str) and r.lower() == "all" and isinstance(c, int):
6999
- for r_, c_ in self.MT.cell_options:
6977
+ for r_, _ in self.MT.cell_options:
7000
6978
  if "format" in self.MT.cell_options[(r_, c)]:
7001
6979
  self.MT.delete_cell_format(r_, c, clear_values=clear_values)
7002
6980
  elif isinstance(c, str) and c.lower() == "all" and isinstance(r, int):
7003
- for r_, c_ in self.MT.cell_options:
6981
+ for _, c_ in self.MT.cell_options:
7004
6982
  if "format" in self.MT.cell_options[(r, c_)]:
7005
6983
  self.MT.delete_cell_format(r, c_, clear_values=clear_values)
7006
6984
  elif isinstance(r, str) and r.lower() == "all" and isinstance(c, str) and c.lower() == "all":
@@ -7014,11 +6992,13 @@ class Sheet(tk.Frame):
7014
6992
  def format_row(
7015
6993
  self,
7016
6994
  r: AnyIter[int] | int | Literal["all"],
7017
- formatter_options: dict = {},
6995
+ formatter_options: dict | None = None,
7018
6996
  formatter_class: object = None,
7019
6997
  redraw: bool = True,
7020
6998
  **kwargs,
7021
6999
  ) -> Sheet:
7000
+ if formatter_options is None:
7001
+ formatter_options = {}
7022
7002
  kwargs = fix_format_kwargs({"formatter": formatter_class, **formatter_options, **kwargs})
7023
7003
  if isinstance(r, str) and r.lower() == "all":
7024
7004
  for r_ in range(len(self.MT.data)):
@@ -7056,11 +7036,13 @@ class Sheet(tk.Frame):
7056
7036
  def format_column(
7057
7037
  self,
7058
7038
  c: AnyIter[int] | int | Literal["all"],
7059
- formatter_options: dict = {},
7039
+ formatter_options: dict | None = None,
7060
7040
  formatter_class: object = None,
7061
7041
  redraw: bool = True,
7062
7042
  **kwargs,
7063
7043
  ) -> Sheet:
7044
+ if formatter_options is None:
7045
+ formatter_options = {}
7064
7046
  kwargs = fix_format_kwargs({"formatter": formatter_class, **formatter_options, **kwargs})
7065
7047
  if isinstance(c, str) and c.lower() == "all":
7066
7048
  for c_ in range(self.MT.total_data_cols()):
@@ -7112,7 +7094,7 @@ class Dropdown(Sheet):
7112
7094
  height: int | None = None,
7113
7095
  font: None | tuple[str, int, str] = None,
7114
7096
  outline_thickness: int = 2,
7115
- values: list[object] = [],
7097
+ values: list[object] | None = None,
7116
7098
  close_dropdown_window: Callable | None = None,
7117
7099
  search_function: Callable = dropdown_search_function,
7118
7100
  modified_function: None | Callable = None,
@@ -7170,7 +7152,7 @@ class Dropdown(Sheet):
7170
7152
  ops=ops,
7171
7153
  outline_color=outline_color,
7172
7154
  align=align,
7173
- values=values,
7155
+ values=[] if values is None else values,
7174
7156
  search_function=search_function,
7175
7157
  modified_function=modified_function,
7176
7158
  )
@@ -7258,10 +7240,7 @@ class Dropdown(Sheet):
7258
7240
  row = None
7259
7241
  elif event.keysym == "Return":
7260
7242
  row = self.get_selected_rows()
7261
- if not row:
7262
- row = None
7263
- else:
7264
- row = next(iter(row))
7243
+ row = None if not row else next(iter(row))
7265
7244
  else:
7266
7245
  row = self.identify_row(event, exclude_index=True, allow_end=False)
7267
7246
  if self.single_index:
@@ -7287,10 +7266,12 @@ class Dropdown(Sheet):
7287
7266
 
7288
7267
  def values(
7289
7268
  self,
7290
- values: list = [],
7269
+ values: list[object] | None = None,
7291
7270
  redraw: bool = True,
7292
7271
  width: int | None = None,
7293
7272
  ) -> None:
7273
+ if values is None:
7274
+ values = []
7294
7275
  self.set_sheet_data(
7295
7276
  [[v] for v in values],
7296
7277
  reset_col_positions=False,