image source
Repository: Python, Open Source Repository
Software Requirements: For software download python 3.0 compatible with your OS here
What you will learn:
In this tutorial you will learn how to
Different ways to start up a kivy app with examples
Using the kivy.clock and kivy.animation class functions and why and when to use each
Making our block fall and stop at zero coordinates
Difficulty : Intermediate
Tutorial
In the last two of these series we went through the preliminaries of kivy development which included how to start up a new app and using a few basic concepts within our kivy file.
In this tutorial we would learn a few more concepts and apply them to the tetris game we have been developing throgh the series of this tutorials. First i would explain the Property which came with the newer versions of kivy and how it could help in development also covering its flaws which are poorly documented.
The Property is a function class that helps us add properties to our super classes in a way more easier fashion. This means that rather than creating a new __init__ function we can add properties to our super class with a simplified line of code. For example:
class A(Widget):
def__init__(self, **kwargs):
super(A, self).__init__(**kwargs)
self.new_value = 1
Instead of using the standard python format for adding new properties to our parent class, we could simply use this:
class A(Widget):
new_value= NumericProperty(1)
The event dispatcher also helps us add other properties such as StringProperties, BooleanProperties and even a ReferenceListProperty which could house multiple other properties.
Lets go back to our tetris game.
So far we have created two classes. Firstly the class for the board or where the game would be played.
class board(ScatterLayout):
pass
which is linked up to its .kv file
<board>:
canvas:
Rectangle:
size: 500, 500
And then our block class which is for our blocks which would fall in the game
class block1(Widget):
#This is using the standard python format
def __init__(self, **kwargs):
super(block1, self).__init__(**kwargs)
xpositions = (0, 50, 100, 150, 200, 250, 300, 350, 400)
self.bind(pos= self.fall)
self.pos_x = random.choice(xpositions)
self.pos_y = Window.height
self.pos = (self.pos_x,self.pos_y)
self.vel_x = 0
self.vel_y = -5
self.velocity =(self.vel_x,self.vel_y)
def fall(self, *args):
self.pos = Vector(*self.velocity) + self.pos
if self.pos[1]==0:
self.position[1] = 0
return self.pos
To explain our Properties even further, we could use an alternative to this code such as this
class block1(Widget):
pos = ReferenceListProperty((randint(0,500), Window.height)
#This piece of code helps us to add a new x position which is any random position between 0,500 and an y position which is the height of whatever window specification you may have specified.
The next thing we have covered is our fall function which we defined within our new class. Our fall function takes the position of our block and adds a velocity whenever the function is called.
A regular confusion is whether to use a similar function class called the kivy.Animation class which helps you to create simple animations by simply just defining the positions you would like the widget to move to and the time you would like it to take while moving through this distance. If we were to use this function class our code would have looked something like this .
#After importing our animation module from kivy.animation at the beginning our program
def fall():
x = Animation(pos_x, 0)#This would make our widget to move to down to the zero x position hence giving it a falling motion
Then within our build within the app class we would have added.
def build():
x = block1()
x.fall
This would have been a good alternative to the normal fall function we have above but here are the constraints we would have faced.
If you have started up kivy and looked throught the official documentation you would have come across a Pong Tutorial where it takes you through the steps of creating a new pong game. In this tutorial rather than using the animation function, the documentation uses the kivy.clock function class which is a method of repeating a function within a given period of time. The reason why the kivy.clock function is used way more is that it is better suited for applications where there is interactivity in the widget, so for instance a function that changes what happens when it reaches a certain position would be able to detect those changes and carry out the needed which would be an impossibility or rather complicated if you were to be using the kivy.animation function.
So by doing this in our widget class:
def fall(self, *args):
self.pos = Vector(*self.velocity) + self.pos
if self.pos[1]==0:
self.position[1] = 0
return self.pos
and this in our apps build function
a = block1()
x = Clock.schedule_interval(a.fall, 1/60)
We could manage how our block will react when it reaches a certain point.
i.e It is better to use the kivy.animation function class when dealing with simple graphics but better to use the kivy.clock in situations where there is widget interactivity and when you would like the animation to react differently to changes
Using this we see that our block falls when the program is run and stops at the bottom of the window which would not be possible if using the kivy.animation function class.
You can find my Proof of work in Github