优化submenu(10000数据量不卡)
This commit is contained in:
parent
db3f0b2445
commit
ad0dbc33a7
|
@ -2,35 +2,15 @@ import json
|
|||
import tkinter
|
||||
import sys
|
||||
from tkinter import ttk
|
||||
from tkinter import font as tkfont
|
||||
try:
|
||||
import color_tmpl
|
||||
except ImportError:
|
||||
from magictk import color_tmpl
|
||||
try:
|
||||
import photoload
|
||||
except ImportError:
|
||||
from magictk import photoload
|
||||
|
||||
from magictk import color_tmpl
|
||||
from magictk import photoload
|
||||
from magictk import fontconfig
|
||||
|
||||
transcolor = "#41342F"
|
||||
usetrans = sys.platform.startswith('win')
|
||||
|
||||
|
||||
def set_font():
|
||||
global use_font
|
||||
font_family = ["Helvetica Neue", "Helvetica", "PingFang SC", "Hiragino Sans GB",
|
||||
"Microsoft YaHei",
|
||||
"微软雅黑",
|
||||
"Arial", "sans-serif"]
|
||||
t_family = tkfont.families(root=None, displayof=None)
|
||||
for i in font_family:
|
||||
if i in t_family:
|
||||
use_font = i
|
||||
break
|
||||
else:
|
||||
print("Unknown font")
|
||||
|
||||
|
||||
class MenuObjs:
|
||||
def __init__(self):
|
||||
self.menu_lst = []
|
||||
|
@ -60,6 +40,7 @@ class Menu:
|
|||
__y_move = 0
|
||||
___last_move = 1
|
||||
___last_highlight = 0
|
||||
__load_y_size = 10
|
||||
ht = 12
|
||||
lt = 22
|
||||
ft = 34
|
||||
|
@ -102,7 +83,8 @@ class Menu:
|
|||
n += 1
|
||||
self.___last_move = self.__y_move
|
||||
n = 0
|
||||
for i in self.menuobj.menu_effect:
|
||||
for i_tmp in range((-self.__real_y_move+self.__y_move)//self.ft, min((-self.__real_y_move+self.__y_move)//self.ft+len(self.__items), len(self.menuobj.menu_effect))):
|
||||
i = self.menuobj.menu_effect[i_tmp]
|
||||
if (len(i) != 0):
|
||||
self.canvas.itemconfigure(
|
||||
self.__itemsf[n], justify=tkinter.LEFT, **i)
|
||||
|
@ -119,29 +101,35 @@ class Menu:
|
|||
y = event.y
|
||||
self.__last_highlight = max(
|
||||
-1, min(len(self.__items), int((y-self.ht-self.__y_move)//self.ft)))
|
||||
if (self.__last_highlight == -1 or self.__last_highlight >= len(self.__items)):
|
||||
if (self.___last_highlight != -2):
|
||||
self.canvas.itemconfig(
|
||||
self.__items[self.___last_highlight], fill=self.color["background"])
|
||||
self.___last_highlight = -2
|
||||
elif (self.___last_highlight != self.__last_highlight):
|
||||
for i in self.__items:
|
||||
self.canvas.itemconfig(
|
||||
self.__items[self.__last_highlight], fill=self.color["placeholder_light"])
|
||||
self.canvas.itemconfig(
|
||||
self.__items[self.___last_highlight], fill=self.color["background"])
|
||||
self.___last_highlight = self.__last_highlight
|
||||
i, fill=self.color["background"])
|
||||
self.canvas.itemconfig(
|
||||
self.__items[self.__last_highlight], fill=self.color["placeholder_light"])
|
||||
|
||||
def close(self, *args):
|
||||
self.__close_mode = 1
|
||||
if sys.platform.startswith('win'):
|
||||
self.toplevel.unbind_all("<MouseWheel>")
|
||||
elif sys.platform.startswith('darwin'):
|
||||
self.toplevel.unbind_all("<MouseWheel>")
|
||||
else:
|
||||
self.toplevel.unbind_all(
|
||||
"<Button-4>")
|
||||
self.toplevel.unbind_all(
|
||||
"<Button-5>")
|
||||
if (self.__closecallback is not None):
|
||||
self.__closecallback(self)
|
||||
|
||||
def __init__(self, root, menuobj: MenuObjs, w=200, h=300, x=100, y=300, color_list: None | dict = None, closeonleave=True, fontsize=10, closecallback=None):
|
||||
set_font()
|
||||
global use_font
|
||||
use_font = fontconfig.getfont()
|
||||
self.__closecallback = closecallback
|
||||
self.font = (use_font, fontsize)
|
||||
self.__items = []
|
||||
self.__itemsf = []
|
||||
self.__itemsid = []
|
||||
self.__real_y_move = 0
|
||||
self.menuobj = menuobj
|
||||
self.w = w
|
||||
self.h = h
|
||||
|
@ -177,11 +165,13 @@ class Menu:
|
|||
|
||||
def __draw_menu(self):
|
||||
n = 0
|
||||
for i in self.menuobj.menu_lst:
|
||||
for i_tmp in range(0, min(self.__load_y_size, len(self.menuobj.menu_lst))):
|
||||
i = self.menuobj.menu_lst[i_tmp]
|
||||
self.__items.append(self.canvas.create_rectangle(
|
||||
2, n*self.ft+self.ht, self.w, (n+1)*self.ft+self.ht, fill=self.color["background"], width=0))
|
||||
self.__itemsf.append(self.canvas.create_text(
|
||||
10, n*self.ft+self.ht, text=i, font=self.font, justify=tkinter.LEFT, fill=self.color["regular_text"]))
|
||||
self.__itemsid.append(n)
|
||||
n += 1
|
||||
|
||||
def __draw_corner(self, r_x, r_y, x, y, **kwargs):
|
||||
|
@ -234,6 +224,8 @@ class Menu:
|
|||
|
||||
def __bind_scroll(self):
|
||||
def scrollwheel(event: tkinter.Event, setdelta=None):
|
||||
if (len(self.menuobj.menu_lst) <= 8):
|
||||
return
|
||||
if (setdelta is None):
|
||||
delta = event.delta
|
||||
else:
|
||||
|
@ -241,10 +233,33 @@ class Menu:
|
|||
if sys.platform.startswith('win'):
|
||||
delta //= 120
|
||||
if delta > 0:
|
||||
self.__y_move = min(0, self.__y_move+delta)
|
||||
if (self.__real_y_move != 0):
|
||||
self.__y_move += delta
|
||||
self.__real_y_move = min(0, self.__real_y_move+delta)
|
||||
else:
|
||||
self.__y_move = max(
|
||||
-max(0, len(self.__items)*self.ft+self.ht-self.h), self.__y_move+delta)
|
||||
if (self.__real_y_move != -(len(self.menuobj.menu_lst)*self.ft-self.h+8)):
|
||||
self.__y_move += delta
|
||||
self.__real_y_move = max(self.__real_y_move+delta,
|
||||
-(len(self.menuobj.menu_lst)*self.ft-self.h+8))
|
||||
|
||||
if (self.__y_move > 0):
|
||||
self.__y_move -= self.ft
|
||||
self.__items.insert(0, self.__items.pop())
|
||||
self.__itemsf.insert(0, self.__itemsf.pop())
|
||||
self.__itemsid.insert(0, self.__itemsid.pop()-10)
|
||||
self.__mouse_move(event)
|
||||
if (self.__itemsid[0] >= 0):
|
||||
self.canvas.itemconfigure(
|
||||
self.__itemsf[0], text=self.menuobj.menu_lst[self.__itemsid[0]])
|
||||
elif (self.__y_move < -self.ft+1):
|
||||
self.__y_move += self.ft
|
||||
self.__items.append(self.__items.pop(0))
|
||||
self.__itemsf.append(self.__itemsf.pop(0))
|
||||
self.__itemsid.append(self.__itemsid.pop(0)+10)
|
||||
self.__mouse_move(event)
|
||||
if (self.__itemsid[-1] < len(self.menuobj.menu_lst)):
|
||||
self.canvas.itemconfigure(
|
||||
self.__itemsf[-1], text=self.menuobj.menu_lst[self.__itemsid[-1]])
|
||||
|
||||
if sys.platform.startswith('win'):
|
||||
self.toplevel.bind_all("<MouseWheel>", scrollwheel)
|
||||
|
@ -258,8 +273,8 @@ class Menu:
|
|||
|
||||
def __click(self, event):
|
||||
click_item = max(
|
||||
-1, min(len(self.__items), int((event.y-self.ht-self.__y_move)//self.ft)))
|
||||
if (click_item == -1 or self.__last_highlight >= len(self.__items)):
|
||||
-1, min(len(self.menuobj.menu_func), int((event.y-self.ht-self.__real_y_move)//self.ft)))
|
||||
if (click_item == -1 or self.__last_highlight >= len(self.menuobj.menu_func)):
|
||||
return
|
||||
self.close()
|
||||
self.menuobj.menu_func[click_item](self, click_item)
|
||||
|
|
Loading…
Reference in New Issue