Tutorials - Blender Game Engine
Beginning BGE Pythonby Social
WHO THIS TUTORIAL IS FOR:
This tutorial is intended for those of you who have been "messing around" with the BGE for some time, but have not yet found the time to tinker with the python scripting aspect. It is meant to serve as a solid foundation from which you can get a decent start in learning how to use python with the BGE.
START WITH WHAT YOU KNOW:
Because this is the very beginning of your PY-BGE experience, we will use Python to accomplish something that can already be done with logic bricks alone. Our goal here will be to construct a simple control scheme for an object in the gamespace. This way, we eliminate any confusion that could potentially arise from setting a goal that you may not yet be familiar with.
Just to establish our standing knowledge, we should probably start by taking a look at the logic brick only version first. So go ahead and open "Control_LBVER.blend". Take note of the simple logic brick setup for the "Player" object, then press P and give the scheme a try, just to see what it does and how it behaves.
SETTING THINGS UP FOR SCRIPTING:
I already set up the blender window arrangement for you. The 3D window is on the left, the text editor (where you write your code) is on the right, and the logic buttons window is on the bottom (where the logic bricks are of course). You can choose your own arrangement when you feel comfortable enough to do so, but for the time being the current window setup will do ok. All that's left for you to do now, is to simply delete all the "and controllers" along with all the actuators and save this file as: "Controls_PYVER.blend" (no quotes) somewhere on your system.
PYTHON NEEDS LOGIC BRICKS TOO:
Yep, we kept those sensors for a reason. There is a common misconception among beginners that python scripts work on the same principle as some C coded games, where you usually have a main(), under which everything else is programmed, taking logic bricks out of the equation. However, in the BGE Python initiates events by making calls to C functions, and it usually has to be used in conjunction with logic bricks for events to occur. So there is no main(), and you are basically programming a complex controller which will *usually* have to get it's input from sensor bricks, and project it's output to actuators which make things happen.
So in turn, any python script we write will also have to be represented by a logic brick (more specifically a controller).
ASSIGN A SCRIPT TO A CONTROLLER:
YOUR FIRST LINES (of code):
In the text editor window, on the first line type:
As you may have already speculated, "cont" is short for controller. It is simply an assignment
variable, for which you can choose any name you wish. Writing out "controller" instead of "cont"
would not be wrong here, just like any other name. However it should be noted that within the
BGE community "cont" is the most common naming standard used, so it would probably be best for
you to go with the flow and use "cont", so as to avoid any probable confusion in the future.
What we assign to "cont" is a function called "getCurrentController()" which returns the current controller (as the name implies) and gives us access to it, and various other functions. "GameLogic" has to be listed before "getCurrentController()", because "GameLogic" is the module containing all the functions available to us in the BGE.
Well, because if we didn't assign the "getCurrentController" function to "cont", the line above
would have to look like this:
As you can see, it's considerably longer, and nowhere near pretty, but it is the same exact
thing. We just saved ourselves some typing by making an assignment shortcut.
The "getOwner()" function gives us access to the owner, (in this case the "Player" object) and subsequent functions. To see a list of all available functions under it, you can do "print dir(own)" if you want, or better yet, you can get detailed info in the official blender documentation. In addition to the available functions, "getOwner()" is most commonly used to access properties, which you assign with the big "Add Property" button in the buttons window.
See a pattern? "#Sensors" as I'm sure you already know, is a comment (as is anything preceded
with a "#" in python). Here I'm just giving the code some organization by stating that what
follows are my sensor assignments. The basic routine to get a sensor is as you can plainly see:
cont.getSensor("yoursensorname"). That is, the name that your sensor brick carries. When
getting a sensor name you have to use quotes, and as with everything in python, this too is
case sensitive. So if you were to type: getSensor("up") instead of ("Up") you would get an
error (errors will show up in the blender command prompt). In order for things to work properly
the name in cont.getSensor("name") has to be exactly the same as the name on the sensor logic
brick, (only with quotes) and the sensor brick itself has to be connected to the python
controller. So on that note:
Pretty much the same thing as with the sensors. Here, the assignment name is the same as the
actuator name. Just to show you that you can do that (if you want to). Assignment names don't
have to be the same though (as I demonstrated with the sensors) as long as the right name is
called with .get.
Let's start with the variables at the top. These are here pretty much to hold the values we wish
to assign to the motion actuator depending on what keys we press. The "speed" and "rspeed" hold
the numbers that we want to assign to the "walk" and "turn" variables when we are pressing some
of the movement keys (weather they will be positive or negative values is determined by which
keys are currently active). "walk" and "turn" variables are the default assign when nothing is
happening (hence they are initially set to 0), so it is these variables that will be assigned
to the actuator. "speed" and "rspeed" will only be assigned to "walk" and "turn" when the
situation calls for it. Otherwise "walk" and "turn" are by default 0, and nothing happens.
NOTE: The variables that we have set here, are reset at every script pass (a pass/pulse is simply referring to when the "script is read", which is something that happens very fast, and many times during a games run). Meaning that any values that these variables might have held in a previous pass, will be replaced by default when the initial value assignments are re-read. So if you are looking to make a counter, or something along those lines, you should use a property, and call to it through "own.propertyname", because variables like the ones we are using here won't do in that case.
The "if" statements should be self explanatory "if sensorassigment.isPositive():" checks for weather or not a key is pressed, and if it is, the code below is run, and so "walk" and "turn" variables are set accordingly.
"motion.setLinearVelocity(0, walk, 0, 1)" is where the "walk" variable is assigned to the actuators Y axis exertion placeholder. The general input that setLinearVelocity will recieve is (X, Y, Z, L/G). L/G standing for weather or not the exerted velocity will be administered locally(1) or globally(0).
"motion.setDRot(0, 0, turn, 1)" functions on the same exact principle. Except this time we are using DRot as our translation method, and the "turn" value is applied to the Z axis placeholder, instead of the Y.
"GameLogic.addActiveActuator(motion, 1)" is simply used to activate the actuator, and get it to make movements according to the assigned values via motion.set[TranslationMethod](). The general input that the addActiveActuator will recieve is: (actuatorassigment, 0/1). 1 activates the actuator, 0 deactivates it.
If you did everything right, your script should look like this, in it's entirety:
If it looks good, give it a run. If it works *and* you feel like you understand most of it, you
have successfully completed this tutorial. If not, you didn't.
This was simply a presentation of the very basics. In order to further progress, you will have to study, and implement new features as you learn them. One of the best ways to do so is by looking over .blend files others did, and then tinkering with the python code there. Try to figure out what the code actually does, make your own modifications, try to add a new functionality etc.
For example: Try to add a jumping feature to the player object (via python) to the practice file used in this tutorial, and try to figure out how to make it so that you have to let go of the jump key, before you can jump again. Use this template to practice, and use the BGE API documentation. Don't be afraid to try new things. The worst thing that can happen is: blender crashes (and that's if you really mess up) in which case you can just start it up again.
Now, you may not see the benefit of scripting all that clearly in this situation, but just imagine that you have more than 4 keys, and 2 constant speeds. Changing one variable is a lot easier than going around all your logic bricks, and changing each and every individual actuator value. When a game starts reaching a considerable size, logic bricks in many cases are not even an option, you will have to go with Python sooner or later. There are also other benefits, like being able to change gravity on the fly, and many other things that just can't be done with logic bricks, but that's something that you can look up for yourselves.
I hope this tutorial helped you gain a general idea on how the BGE API works. Just remember: it's a great time to learn how to use the BGE to it's full extent. With the OGRE implementation on the way, and a load of great new features, learning the BGE is not a waste of time. So keep at it.
Back to the tutorials index...
Website design by Tony "blendenzo" DiRienzo. All content © Copyright Tony DiRienzo unless otherwise noted.