Saturday, May 24, 2014

2. Binding Functions to Buttons

Two simple buttons are displayed and each has a bound method which is called if it is clicked.




Here we do the imports. BoxLayout, organizes the widgets, either vertically or horizontally. We use the App class and the Button class as in the first example. This example also uses the standard Python library time.




This is the overall structure of the program. The editor, we are using here, is Notepad++. The good thing about this editor is that you can collapse the code of the blocks, such as function definitions. We see that we have 2 classes. The class HelloWorld inherits from BoxLayout. It has three functions, the constructor, and the two binding functions, called after each button is clicked. The second class, HelloWorldApp, inherits from App, and thus is our application class. It has the build function, whose sole function, as we will define, is to call the subclassed BoxLayout class, where we define the widgets and behavior. Line 31 tests for the case our program is run directly, that is, not imported.




The constructor of any class is called when an instance of the class is created. We will see that the instance is created from within the second class. Whenever a constructor is called, its super function, BoxLayout in this case, must be called with the same arguments. The arguments are stored in a Python Dictionary structure. Line 13 creates a button btn1 with text of Hello. In Line 14, it binds the click (on_press) to function hello. On Line 15, the button is added to the BoxLayout. Further widgets will be added horizontally, the default, as we did not define the orientation. Lines 17 through 19, do the same for the second button with text World! and binding function world. Note, a function definition in Python does not have to have a return if nothing is returned. The way Python knows a function has ended, is the indentation level changes. You may write return if you really want to.




The two bound functions are then found in the first class. These merely print Hello, or World, as well as the time. The ctime function in time module is used to write a String. The %s inside the quotes is a String placeholder which will get the value after the rightmost percent symbol.




Here is the second class, and its only function. This class inherits from App, so it is our Application subclass. It then overwrites the build function of the App class and returns with instance to first class. Thus, now the constructor is called initializing the widgets and binding behaviors.




This is the main code. It is possible not to test this condition, since we know the program is going to be run directly anyway. However, with this, it is easier to see where is our main block. In Python, explicit is better. If we did not have the condition, the block will not be indented, and will not stand out. In this block, the App subclass is initiated. We do not used the constructor, but the build() function, which will be called at a little time after instance construction. A variable, myApp, is created to point to the application. This way we can inquire about its name. There are more application properties. Finally you run the application with the run() function.


# helloworld.py

from kivy.uix.boxlayout import BoxLayout
from kivy.app import App
from kivy.uix.button import Button

import time

class HelloWorld(BoxLayout):
    def __init__(self, **kwargs):
        super(HelloWorld, self).__init__(**kwargs)

        btn1 = Button(text="Hello")
        btn1.bind(on_press=self.hello)
        self.add_widget(btn1)

        btn2 = Button(text="World!")
        btn2.bind(on_press=self.world)
        self.add_widget(btn2)

    def hello(self, obj):
        print("--> Hello at time %s" % time.ctime())

    def world(self, obj):
        print("--> World! at time %s" % time.ctime())
   
class HelloWorldApp(App):
    def build(self):
        return HelloWorld()

if __name__ == "__main__":
    myApp = HelloWorldApp()
    print("myApp name is %s" % myApp.name)
    myApp.run()



If running inside IDLE, you can select Run menu and then Run Module submenu. You will get two buttons filling the application window. Also, you can see four printouts, after clicking on the buttons.




3 comments:

  1. great series - thank you !

    ReplyDelete
  2. Good Post! Thank you so much for sharing this pretty post, it was so good to read and useful to improve my knowledge as updated one, keep blogging.

    Python Training in electronic city

    ReplyDelete