For the moment I came up with this solution, which seems to work, however I am not very happy with it. I need to define an "anchor" variable to remember from where the selection started
class MyTreeview(ttk.Treeview): def __init__(self, master, *kw, **args): super().__init__(master, *kw, **args) self.bind("<B1-Motion>", self.b1motion) self.bind("<ButtonRelease-1>", self.release) self.bind("<Up>",self.up) self.bind("<Down>", self.down) self.bind("<Shift-Key-Up>", self.selectUp) self.bind("<Shift-Key-Down>",self.selectDown) self._anchor = "" # ---------------------------------------------------------------------- def b1motion(self, event): # If selected item is the last one focused # then ignore, otherwise Select is selecting everything if self.identify_row(event.y) == self.focus(): return self.tk.call("ttk::treeview::Select", self._w, event.x, event.y, "extend") # ---------------------------------------------------------------------- def release(self, event): self.tk.call("ttk::treeview::Release", self._w, event.x, event.y) self._anchor = self.focus() return "break" # ---------------------------------------------------------------------- def up(self, event): self.tk.call("ttk::treeview::Keynav", self._w, "up") self._anchor = self.focus() return "break" # ---------------------------------------------------------------------- def down(self, event): self.tk.call("ttk::treeview::Keynav", self._w, "down") self._anchor = self.focus() return "break" # ---------------------------------------------------------------------- def selectUp(self, event): if not self._anchor: self._anchor = self.focus() self.tk.call("ttk::treeview::Keynav", self._w, "up") if self.focus() != self._anchor: self.tk.call("ttk::treeview::SelectOp", self._w, self._anchor, "extend") return "break" # ---------------------------------------------------------------------- def selectDown(self, event): if not self._anchor: self._anchor = self.focus() self.tk.call("ttk::treeview::Keynav", self._w, "down") if self.focus() != self._anchor: self.tk.call("ttk::treeview::SelectOp", self._w, self._anchor, "extend") return "break" ________________________________ From: Tkinter-discuss [tkinter-discuss-bounces+vasilis.vlachoudis=cern...@python.org] on behalf of Vasilis Vlachoudis [vasilis.vlachou...@cern.ch] Sent: Tuesday, January 05, 2021 12:06 To: tkinter-discuss@python.org Subject: [Tkinter-discuss] Extend selection in ttk.Treeview Hi all, I am currently replacing some Listbox() with ttk.Treeview() however the Treeview doesn't have the "Shift-Up/Down" and "B1-Motion" capabilities to select with the keyboard multiple items and with the mouse by click and drag. Looking the treeview.tcl I've managed to add a binding for the B1-Motion which seems to work, however I failed to find a way to correctly replicate the Listbox behavior with the Shift-Up/Down This is one of my failed tries Any suggestion? class MyTreeview(ttk.TreeView): def __init__(self, master, *kw, **args): super().__init__(master, *kw, **args) self.bind("<B1-Motion>", self.b1motion) self.bind("<Shift-Key-Up>", self.selectUp) self.bind("<Shift-Key-Down>", self.selectDown) def b1motion(self, event): if self.identify_row(event.y) == self.focus(): return self.tk.call("ttk::treeview::Select", self._w, event.x, event.y, "extend") def selectDown(self, event): self.tk.call("ttk::treeview::Keynav", self._w, "down") item = self.focus() self.tk.call("ttk::treeview::SelectOp", self._w, item, "extend") return "break"
_______________________________________________ Tkinter-discuss mailing list Tkinter-discuss@python.org https://mail.python.org/mailman/listinfo/tkinter-discuss