Использование декоратора для изменения возвращаемого значения метода - PullRequest
2 голосов
/ 02 августа 2020

У меня есть TextBox и Button. Когда пользователь нажимает Enter , я хочу, чтобы была нажата кнопка c, относящаяся к TextBox. TextBox и Button - классы. Я передаю экземпляр Button в TextBox, чтобы мы знали, что по одному нужно щелкнуть. Button - это класс с двумя методами click() и autoclick().

Я хочу, чтобы autoclick() проверял, нажата ли Enter клавиша и сделайте click() верните True, если это так. Я пробовал использовать декораторы и написал эту игрушечную программу, чтобы продемонстрировать именно то, что я пробовал.

class Button:
    def click(self):
        return False

    def autoclick(self, func, *args):
        def wrapper():
            func(*args)# This function needes events as it argumnet
            return True
        return wrapper

b = Button()
class TextBox:
    def __init__(self, button=None):
        self.button = button

    def box(self):
        if enterPressed:
            if self.button is not None:
                self.button.autoclick(self.button.click, events)()


tb = TextBox(button=b)
while True:
    tb.box()
    if b.click():
        print("this needs to be printed when user hits enter")

Я не получаю никаких ошибок, но это просто не работает.

Ответы [ 2 ]

1 голос
/ 02 августа 2020

Я думаю, что необходимо изменить следующую часть

class TextBox:
   def __init__(self, button=None):
       self.button = button

   def box(self):
       if enterPressed:
           if self.button is not None:
               self.button.autoclick(self.button.click, events)()

на что-то вроде:

class TextBox:
    def __init__(self, button=None):
        self.button = button

    def box(self):
        if enterPressed:
            if self.button is not None:
                self.button.click = self.button.autoclick(self.button.click)  # this line is changed

ОБНОВЛЕНИЕ

Думаю, может быть, вы должны иметь в виду что-то вроде следующего:

class Button:
    def _click(self):  # Maybe this method have events as parameters?
        return False

    def click(self):
        return self._click()

    def autoclick(self):
        def wrapper(*args):
            self._click(*args)  # This function needs events as it arguments
            self.click = self._click
            return True

        self.click = wrapper


class TextBox:
    def __init__(self, button=None):
        self.button = button

    def box(self):
        if enterPressed:
            if self.button is not None:
                self.button.autoclick()

Или, может быть, это? :

class Button:
    def _click(self):  # Maybe this method have events as parameters?
        return False

    def click(self):
        return self._click()

    def autoclick(self):
        def wrapper(*args):
            result = self._click(*args)  # This function needs events as it arguments
            if enterPressed:
                return True
            return result

        self.click = wrapper


class TextBox:
    def __init__(self, button=None):
        self.button = button

    def box(self):
        if self.button is not None:
            self.button.autoclick()
1 голос
/ 02 августа 2020

Думаю, теперь я знаю, что ты хочешь делать.

Попробуй. Вот как мы обычно используем декораторы.

class Button:
    @autoclick # this is how decorators are used.
    def click(self):
        return False

    def autoclick(self, func):
        def wrapper(*args):
            func(*args)# This function needes events as it argumnet
            return True
        if enterPressed:
            return wrapper
        else:
            return func
...