Beispiel #1
0
        def render(self):
            self.config(height=40)
            seq_frame = Frame(self, **self.style.highlight)
            seq_frame.grid(row=0, column=0, sticky="nsew")
            seq_frame.pack_propagate(False)
            self.sequence = Entry(seq_frame, **self.style.input)
            self.sequence.place(x=0, y=0, relwidth=1, relheight=1, width=-40)
            self.sequence.set(self.value.sequence)
            self.sequence.configure(**self.style.no_highlight)
            self.sequence.focus_set()
            self.handler = Entry(self, **self.style.input)
            self.handler.grid(row=0, column=1, sticky="ew")
            self.handler.set(self.value.handler)
            self.handler.config(**self.style.highlight)
            self.add_arg = Checkbutton(self, **self.style.checkbutton)
            self.add_arg.grid(row=0, column=2, sticky="ew")
            self.add_arg.set(self.value.add)
            del_btn = Label(self,
                            **self.style.button,
                            image=get_icon_image("delete", 14, 14))
            del_btn.grid(row=0, column=3, sticky='nswe')
            del_btn.bind("<Button-1>", self._delete_entry)
            # set the first two columns to expand evenly
            for column in range(2):
                self.grid_columnconfigure(column, weight=1, uniform=1)

            for widget in (self.sequence, self.handler):
                widget.on_change(self._on_value_change)

            self.add_arg._var.trace("w", lambda *_: self._on_value_change())
Beispiel #2
0
class Anchor(Editor):
    def __init__(self, master, style_def):
        super().__init__(master, style_def)
        self.set_def(style_def)
        self.config(width=150, height=110)
        self.n = ToggleButton(self, text="N", width=20, height=20)
        self.n.grid(row=0, column=0, columnspan=3, sticky='ns')
        self.w = ToggleButton(self, text='W', width=20, height=20)
        self.w.grid(row=1, column=0, sticky='ew')
        self.pad = Frame(self,
                         width=60,
                         height=60,
                         **self.style.dark,
                         **self.style.dark_highlight_active)
        self.pad.grid(row=1, column=1, padx=1, pady=1)
        self.pad.grid_propagate(0)
        self.pad.grid_columnconfigure(0, minsize=60)
        self.pad.grid_rowconfigure(0, minsize=60)
        self.floating = Frame(self.pad,
                              **self.style.dark_on_hover,
                              width=20,
                              height=20)
        self.floating.grid(row=0, column=0, pady=1, padx=1)
        self.e = ToggleButton(self, text="E", width=20, height=20)
        self.e.grid(row=1, column=2, sticky='ew')
        self.s = ToggleButton(self, text='S', width=20, height=20)
        self.s.grid(row=2, column=0, columnspan=3, sticky='ns')
        self.anchors = {"n": self.n, "w": self.w, "e": self.e, "s": self.s}
        self._order = ("n", "s", "e", "w")
        self._selected = []
        self._exclusive_pairs = ({"n", "s"}, {"e", "w"})
        self._is_multiple = re.compile(r'(.*[ns].*[ns])|(.*[ew].*[ew])')
        for anchor in self.anchors:
            self.anchors[anchor].on_change(self._change, anchor)

    def _is_exclusive_of(self, anchor1, anchor2):
        return {anchor1, anchor2} in self._exclusive_pairs

    def _change(self, _, anchor):
        if not self.multiple:
            self._sanitize(anchor)
        self._adjust()
        if self._on_change:
            self._on_change(self.get())

    def _sanitize(self, anchor):
        ex_anchor = [i for i in self.get() if self._is_exclusive_of(i, anchor)]
        if len(ex_anchor):
            self.anchors.get(ex_anchor[0]).set(False)

    def _adjust(self):
        sticky = '' if self.get() == 'center' else self.get()
        self.floating.grid(row=0, column=0, pady=1, padx=1, sticky=sticky)

    def get(self):
        anchor = ''.join([i for i in self._order if self.anchors[i].get()])
        # No anchor means center but only when we are acting as an anchor editor
        # if self.multiple is True then we are a stickiness editor and an empty string will suffice
        if anchor == '':
            if not self.multiple:
                return 'center'
        return anchor

    def set(self, value):
        # bypass the special value 'center' before subjecting to validity check
        value = '' if value == 'center' else str(value)
        # Ignore invalid values
        if self._is_multiple.match(str(value)) and not self.multiple:
            return
        # Assume no anchor means center
        for anchor in self.anchors:
            self.anchors.get(anchor).set(anchor in value)

        self._adjust()

    def set_def(self, definition):
        # This flag determines whether multiple anchors are allowed at a time
        # set to True to obtain a sticky property editor
        self.multiple = definition.get("multiple", True)
        super().set_def(definition)