【发布时间】:2021-10-30 08:56:10
【问题描述】:
有没有办法在排序后保持替代行着色?我的树视图有 2,000 多行,并且想知道除了每次对列进行排序时重新标记所有行之外是否有任何解决方案。当您单击任何列时,行颜色会混淆。
环境:Python 3.10.0 Windows 21H1
import tkinter as objTK
from tkinter import ttk as objTTK
from functools import partial
# Custom column sort for treeview
class MyTreeview(objTTK.Treeview):
def heading(self, column, sort_by=None, **kwargs):
if sort_by and not hasattr(kwargs, 'command'):
func = getattr(self, f"_sort_by_{sort_by}", None)
if func:
kwargs['command'] = partial(func, column, False)
# End of if
# End of if
return super().heading(column, **kwargs)
# End of heading()
def _sort(self, column, reverse, data_type, callback):
l = [(self.set(k, column), k) for k in self.get_children('')]
l.sort(key=lambda t: data_type(t[0]), reverse=reverse)
for index, (_, k) in enumerate(l):
self.move(k, '', index)
# End of for loop
self.heading(column, command=partial(callback, column, not reverse))
# End of _sort()
def _sort_by_name(self, column, reverse):
self._sort(column, reverse, str, self._sort_by_name)
# End of _sort_by_num()
# End of class MyTreeview
objWindow = objTK.Tk()
arrlbHeader = ["Type" , "Description"]
treeview = MyTreeview(columns=arrlbHeader, show="headings")
arrRows = [
["Expenses", "Gen"],
["Expenses", "Aug"],
["Expenses", "Aug"],
["Income", "Aug"],
["Expenses", "Aug"]
]
arrColWidth = [70, 80]
arrColAlignment = ["center", "e"]
# Column header and attributes
arrSortType = ["name", "name"]
for iCount in range(len(arrlbHeader)):
strHdr = arrlbHeader[iCount]
treeview.heading(strHdr, text=strHdr.title(), sort_by=arrSortType[iCount])
treeview.column(arrlbHeader[iCount], width=arrColWidth[iCount], stretch=True, anchor=arrColAlignment[iCount])
# End of for loop
treeview.pack()
# Row colouring tags
treeview.tag_configure("tgOddRow", background="white")
treeview.tag_configure("tgEvenRow", background="blue")
# Insert rows
for iCount in range(len(arrRows)):
if iCount % 2 == 0:
treeview.insert("", "end", values=arrRows[iCount], tags="tgEvenRow")
else:
treeview.insert("", "end", values=arrRows[iCount], tags="tgOddRow")
# End of for loop
objWindow.bind("<Escape>", lambda funcWinSer: objWindow.destroy())
objWindow.mainloop()
【问题讨论】:
-
重新标记似乎是唯一的解决方案,IMO
-
您可以使用您喜欢的值配置它们,而不是移动您的列。
-
为什么不想重新标记行?
-
@Atlas435 猜猜这和重新标记是一样的
-
@BryanOakley 除了重新标记之外,您建议如何解决我发布的问题?
标签: python-3.x tkinter