mirror of https://github.com/python/cpython.git
139 lines
3.8 KiB
Python
139 lines
3.8 KiB
Python
|
# One or more ScrolledLists with HSeparators between them.
|
||
|
# There is a hierarchical relationship between them:
|
||
|
# the right list displays the substructure of the selected item
|
||
|
# in the left list.
|
||
|
|
||
|
import string
|
||
|
from Tkinter import *
|
||
|
from WindowList import ListedToplevel
|
||
|
from Separator import HSeparator
|
||
|
from ScrolledList import ScrolledList
|
||
|
|
||
|
class MultiScrolledLists:
|
||
|
|
||
|
def __init__(self, root, nlists=2):
|
||
|
assert nlists >= 1
|
||
|
self.root = root
|
||
|
self.nlists = nlists
|
||
|
self.path = []
|
||
|
# create top
|
||
|
self.top = top = ListedToplevel(root)
|
||
|
top.protocol("WM_DELETE_WINDOW", self.close)
|
||
|
top.bind("<Escape>", self.close)
|
||
|
self.settitle()
|
||
|
# create frames and separators in between
|
||
|
self.frames = []
|
||
|
self.separators = []
|
||
|
last = top
|
||
|
for i in range(nlists-1):
|
||
|
sepa = HSeparator(last)
|
||
|
self.separators.append(sepa)
|
||
|
frame, last = sepa.parts()
|
||
|
self.frames.append(frame)
|
||
|
self.frames.append(last)
|
||
|
# create labels and lists
|
||
|
self.labels = []
|
||
|
self.lists = []
|
||
|
for i in range(nlists):
|
||
|
frame = self.frames[i]
|
||
|
label = Label(frame, text=self.subtitle(i),
|
||
|
relief="groove", borderwidth=2)
|
||
|
label.pack(fill="x")
|
||
|
self.labels.append(label)
|
||
|
list = ScrolledList(frame, width=self.width(i),
|
||
|
height=self.height(i))
|
||
|
self.lists.append(list)
|
||
|
list.on_select = \
|
||
|
lambda index, i=i, self=self: self.on_select(index, i)
|
||
|
list.on_double = \
|
||
|
lambda index, i=i, self=self: self.on_double(index, i)
|
||
|
# fill leftmost list (rest get filled on demand)
|
||
|
self.fill(0)
|
||
|
# XXX one after_idle isn't enough; two are...
|
||
|
top.after_idle(self.call_pack_propagate_1)
|
||
|
|
||
|
def call_pack_propagate_1(self):
|
||
|
self.top.after_idle(self.call_pack_propagate)
|
||
|
|
||
|
def call_pack_propagate(self):
|
||
|
for frame in self.frames:
|
||
|
frame.pack_propagate(0)
|
||
|
|
||
|
def close(self, event=None):
|
||
|
self.top.destroy()
|
||
|
|
||
|
def settitle(self):
|
||
|
short = self.shorttitle()
|
||
|
long = self.longtitle()
|
||
|
if short and long:
|
||
|
title = short + " - " + long
|
||
|
elif short:
|
||
|
title = short
|
||
|
elif long:
|
||
|
title = long
|
||
|
else:
|
||
|
title = "Untitled"
|
||
|
icon = short or long or title
|
||
|
self.top.wm_title(title)
|
||
|
self.top.wm_iconname(icon)
|
||
|
|
||
|
def longtitle(self):
|
||
|
# override this
|
||
|
return "Multi Scrolled Lists"
|
||
|
|
||
|
def shorttitle(self):
|
||
|
# override this
|
||
|
return None
|
||
|
|
||
|
def width(self, i):
|
||
|
# override this
|
||
|
return 20
|
||
|
|
||
|
def height(self, i):
|
||
|
# override this
|
||
|
return 10
|
||
|
|
||
|
def subtitle(self, i):
|
||
|
# override this
|
||
|
return "Column %d" % i
|
||
|
|
||
|
def fill(self, i):
|
||
|
for k in range(i, self.nlists):
|
||
|
self.lists[k].clear()
|
||
|
self.labels[k].configure(text=self.subtitle(k))
|
||
|
list = self.lists[i]
|
||
|
l = self.items(i)
|
||
|
for s in l:
|
||
|
list.append(s)
|
||
|
|
||
|
def on_select(self, index, i):
|
||
|
item = self.lists[i].get(index)
|
||
|
del self.path[i:]
|
||
|
self.path.append(item)
|
||
|
if i+1 < self.nlists:
|
||
|
self.fill(i+1)
|
||
|
|
||
|
def items(self, i):
|
||
|
# override this
|
||
|
l = []
|
||
|
for k in range(10):
|
||
|
s = str(k)
|
||
|
if i > 0:
|
||
|
s = self.path[i-1] + "." + s
|
||
|
l.append(s)
|
||
|
return l
|
||
|
|
||
|
def on_double(self, index, i):
|
||
|
pass
|
||
|
|
||
|
|
||
|
def main():
|
||
|
root = Tk()
|
||
|
quit = Button(root, text="Exit", command=root.destroy)
|
||
|
quit.pack()
|
||
|
MultiScrolledLists(root, 4)
|
||
|
root.mainloop()
|
||
|
|
||
|
if __name__ == "__main__":
|
||
|
main()
|