What I’m trying to do:
I’ve got a 5x5 grid of buttons. I’d like to create an event handler that can dynamically check the name of the button clicked, and make changes to the appearance of the button that called the event.
I know that I could just add an event for each button from the properties menu, but it seems like there’s a better way.
What I’ve tried and what’s not working:
Code Sample:
# this is a formatted code snippet.
def a1_button_click(self, **event_args):
"""This method is called when the button is clicked"""
pass
def a2_button_click(self, **event_args):
"""This method is called when the button is clicked"""
pass
def a3_button_click(self, **event_args):
"""This method is called when the button is clicked"""
pass
def a4_button_click(self, **event_args):
"""This method is called when the button is clicked"""
pass
def a5_button_click(self, **event_args):
"""This method is called when the button is clicked"""
pass
# paste your code between ```
So when I print event_args[‘sender’] it just shows <anvil.Button object> no matter which button I press. I’m still not sure how to get the name of that sender
For that, @jhdrake, you don’t need the button’s name. You just need a variable that refers to the actual button object, exactly as @stefano.menci showed you. In his code, local variable button contains that reference. You can not only read the button’s properties, as Stefano showed, but you can also write to them:
And if you can’t determine which button is which based on a single or group of properties with enough certainty, you can create a dictionary with each button as a key and each value be a dictionary of properties you want to change, like so in the init function:
Ok I’m able to successfully manipulate the properties of the button that calls the event.
The next step of my game involves “highlighting” the buttons around the one I just clicked. So I’m still running into the problem of needing some type of identifier or label for the buttons that can be referenced by itself and other buttons.
Below, I’ve tried to create a function to assign tags to all 25 buttons, but I’m consistently getting a NameError. One of the buttons is called a1_button. And it’s tag after the tag function should be a1_button.tag = ‘a1’.
Any advice?
from ._anvil_designer import HomeTemplate
from anvil import *
ranks = [‘a’, ‘b’, ‘c’, ‘d’, ‘e’]
columns = [1, 2, 3, 4, 5]
spaces = []
for rank in ranks:
for column in columns:
spaces.append(str(rank)+str(column))
class Home(HomeTemplate):
def init(self, **properties):
# Set Form properties and Data Bindings.
self.init_components(**properties)
# Any code you write here will run when the form opens.
def tagButtons():
for space in spaces:
button_label = exec(space + '_button')
button_label.tag = space
tagButtons()
print(a1_button.tag)
There is likely no local or global variable named a1_button. However, from your description, it sounds like your Form has an attribute with that name, e.g., self.a1_button.
This is where a short trip to the Python standard library comes in handy. See the getattr() function.
However, you can also make a list of buttons without having to systematically assign them names. For example:
self.button_row = [ self.a1_button, self.a2_button, self.a3_button, ... ]
for button in self.button_row:
...
With this method, you could conceivably tag each button with its own list of its (relevant) neighbors…
Lots of possibilities here!
The visible behavior you mentioned sounds a bit like Minesweeper…?