Forum Archive

Add Arguments to method called from UI Scene buttons?

AddledBadger

Hi,

I’m struggling to find a way to re-factor the following code to have a single method which accepts arguments when called from a Scene UI button, rather than two very similar ones. Any suggestions very welcome! Thanks.

def show_view_A(sender):
    v = ui.View()
    v.background_color = ‘white’
    v.name = ‘A’
    global location
    location = 1 # used in another method to grab a url
    sender.navigation_view.push_view(v)
    message = get_html(page_info,location_info)
    scrollview(v,message)

def show_view_B(sender):
    v = ui.View()
    v.background_color = ‘white’
    v.name = ‘B’
    global location
    location = 2 # used in another method to grab a url
    sender.navigation_view.push_view(v)
    message = get_html(page_info,location_info)
    scrollview(v,message)

root_view = ui.View()
root_view.background_color = 'white'
root_view.name = 'Stuff'

A = ui.Button(title='A')
B = ui.Button(title='B')

A.action = show_view_A
B.action = show_view_B

root_view.add_subview(A)
root_view.add_subview(B)
dgelessus

The sender parameter is the view object on which the action happened, i. e. in this case the button that was tapped. Since you have the two buttons stored in global variables A and B, you should be able to use something like if sender == A: ... elif sender == B: ... to tell which button was tapped.

ccc

Alternatively you could set the location by looking at the sender title.

import ui

page_info = None
location_info = None


def get_html(*args):
    pass


def scrollview(*args):
    pass


def show_view(sender):
    global location
    if sender.title == 'A':
        location = 1  # used in another method to grab a url
    elif sender.title == 'B':
        location = 2
    view = ui.View(name=sender.title, bg_color='white')
    sender.navigation_view.push_view(view)
    scrollview(view, get_html(page_info, location_info))


root_view = ui.View(name='Stuff', bg_color='white')
root_view.add_subview(ui.Button(title='A', action=show_view))
root_view.add_subview(ui.Button(title='B', action=show_view))
AddledBadger

Excellent, thanks both, I can work with those.

Phuket2

@AddledBadger , not to upset the apple cart so to speak. But another way is to add your own custom attrs to the ui.Button once you have created them. In the below, I added an attr to the ui.Button called your 'username'. It's done just by making the assignment. In this case I assigned a string, but I could have assigned anything. A dict, list, int etc... look, I am still a newbie. I think this way is not considered the best way of doing things. But sometimes you do want to associate data with a ui element. For data I want to associate with an item, I normally use the attr name tag rather than dreaming up new names all the time to help keep it clear.

Anyway it's just another idea.

import ui

class MyClass(ui.View):
    def __init__(self, *args, **kwargs):
        super().__init__(*args, **kwargs)
        self.make_view()

    def make_view(self):
        A = ui.Button(title='A', action=self.show_view)
        A.AddledBadger = 'This is my A type personality'    # adding a attr to the btn at runtime

        B = ui.Button(title='B', action=self.show_view)
        B.x = A.width + 30
        B.AddledBadger = 'This is my B type personality'

        self.add_subview(A)
        self.add_subview(B)

        # you will notice your attr is print
        print(dir(A))

    def show_view(self, sender):
        print(sender.AddledBadger)
        return

        # if not all objects passed to this func may not have your new attr
        # you could do something like the below -
        if hasattr(sender, 'AddledBadger'):
            print('it has my custom attr')
        else:
            print('sender does not have my custom attr, i better do something else')

if __name__ == '__main__':
    f = (0, 0, 300, 400)
    v = MyClass(frame = f)
    v.present(style='sheet', animated=False)