Changes between Version 6 and Version 7 of documentation/tutorials/PythonEventSystem

Show
Ignore:
Author:
peterc (IP: 202.68.89.228)
Timestamp:
01/09/08 14:05:57 (10 years ago)
Comment:

--

Legend:

Unmodified
Added
Removed
Modified
  • documentation/tutorials/PythonEventSystem

    v6 v7  
    22= Python Event Tutorial = 
    33 
    4 The Python interface to Rocket exposes a DOM API in a very similar way to Javascript. Python code can be attached to any event in the RML definition which is turn can dynamically update any part of the document including open other documents. Full source code to the final PyInvaders application can be found in the samples folder once the Python plugin has been installed. 
     4The Python interface to Rocket exposes a DOM API in a very similar way to Javascript. Python code can be attached to any event in the RML definition which in turn can dynamically update any part of the document, including opening new documents. Full source code to the final PyInvaders application can be found in the samples folder once the Python plugin has been installed. 
    55 
    66== Step 1: Setting up the Python environment == 
    88Make sure you've got the required Python support packages installed. For more information, see [wiki:documentation/PythonManual/Overview this page]. 
    99 
    10 The first thing we need to do is initialise python in our application, once we have done this we can start executing scripts. We're going to make a PythonInterface class that will hide all the python intricacies. 
     10The first thing we need to do is initialise Python in our application. Once we have done this we can start executing scripts. We're going to make a PythonInterface class that will hide all the Python intricacies. 
    1111 
    1212{{{ 
    1313/** 
    14         Creates and maintains the python interface to Invaders. 
     14        Creates and maintains the Python interface to Invaders. 
    1515 */ 
    1616 
    3030We then implement these methods.  
    3131 
    32 ''NOTE: Its a good idea to forcibly import the rocket Python module, this ensures all boost bindings have been done and that you can proceed to expose your own classes that rely on these bindings having taken place.'' 
     32''NOTE: Its a good idea to forcibly import the libRocket Python module. This ensures all Boost bindings have been done and that you can proceed to expose your own classes that rely on these bindings having taken place.'' 
    3333 
    3434''NOTE: For more information Python initialisation and shutdown please see the Python documentation at [http://docs.python.org]'' 
    4040    Py_Initialize(); 
    4141 
    42     // Pull in the rocket python module. 
     42    // Pull in the Rocket Python module. 
    4343    Py_XDECREF(PyImport_ImportModule("rocket")); 
    4444    return true; 
    5151}}} 
    5252 
    53 PythonInterface::Initialise should be called before rocket is initialised, this ensures the Python bindings are available when rocket starts up. 
    54  
    55 PythonInterface::Shutdown should be called after you've released all contexts but before you call Rocket::Shutdown(). This ensures all python objects are released before rocket does its final cleanup. 
     53PythonInterface::Initialise should be called before Rocket is initialised. This ensures the Python bindings are available when Rocket starts up. 
     54 
     55PythonInterface::Shutdown should be called after you've released all contexts but before you call Rocket::Shutdown(). This ensures all Python objects are released before Rocket does its final cleanup. 
    5656 
    5757At this point you'll need to add the relevant Python and Boost::Python build paths to your project and then compile and link your project. 
    5959== Step 2: Replacing the Event System == 
    6060 
    61 We can now completely remove the exiting event system from ''RocketInvaders'' as the Python bindings will do all the EventManagement for us. Remove all source and header files that begin with Event. You'll also need to comment out some code in GameElement.cpp and Game.cpp that call the EventManager directly. We'll get back to those later. 
     61We can now completely remove the exiting event system from ''RocketInvaders'' as the Python bindings will do all the event management for us. Remove all source and header files that begin with Event. You'll also need to comment out some code in GameElement.cpp and Game.cpp that call the EventManager directly. We'll get back to those later. 
    6262 
    6363Also remove all the EventManager initialisation from main.cpp as we'll replace it with a new Python script. I suggest you name it ''autoexec.py'' and place it in a ''python'' subfolder. It should look something like this: 
    9494At this point the ''RocketInvaders'' will now run, however you'll get a script import error because ''autoexec'' cannot be found. To fix this we'll need to add the ''python'' folder to our Python search path. 
    9595 
    96 ''NOTE: On Windows this error will go to stdout, which will not be visible. I suggest you grab a copy of DoAllocConsole() from the pyinvaders sample and drop it into your project. Call DoAllocConsole() at the start of your main function and you'll get a console for reading python error messages.'' 
     96''NOTE: On Windows this error will go to stdout, which will not be visible. I suggest you grab a copy of DoAllocConsole() from the pyinvaders sample and drop it into your project. Call DoAllocConsole() at the start of your main function and you'll get a console for reading Python error messages.'' 
    9797 
    9898My PythonInterface::Initialise now looks like this: 
    118118}}} 
    119119 
    120 This will get us further, you should see the main menu load, however you'll notice a python error on your console when Python attempts to execute the old ''onload'' event in mainmenu.rml. Update the ''onload'' and ''onunload'' events to use Python script which will correctly display and hide the logo. 
     120This will get us further, you should see the main menu load, however you'll notice a Python error on your console when Python attempts to execute the old ''onload'' event in mainmenu.rml. Update the ''onload'' and ''onunload'' events to use Python script which will correctly display and hide the logo. 
    121121{{{ 
    122122<body template="window" onload="document.context.LoadDocument('data/logo.rml').Show()" onunload="document.context.logo.Close()"> 
    160160    PySys_SetPath(buffer); 
    161161 
    162     // Import rocket 
     162    // Import Rocket 
    163163    if (!Import("rocket")) 
    164164        return false; 
    195195} 
    196196}}} 
     197 
    197198== Step 4: Custom Elements == 
    198199 
    199200The next problem we'll hit when converting ''RocketInvaders'' is the ElementGame does not have a Python interface. Thus we can't give it focus when we start the game which means the defender cannot be moved until the user clicks the game with the mouse. To fix this, we need to define ElementGame to Python and register the Python instancer with Rocket::Factory instead of the C++ instancer. 
    200201 
    201 Lets define a static method on ElementGame to do this and call it from our game modules initialisation. 
     202Let's define a static method on ElementGame to do this and call it from our game module's initialisation. 
    202203 
    203204{{{ 
    217218== Step 5: Key and end game bindings == 
    218219 
    219 We can now get into the game, however the game will never finish as theres no key bindings for processing the ESCAPE key and nothing will make the game exit when the game is over. Fixing the key binding is easy, simply drop in a OnKeyDown handler and make it launch the pause menu. 
    220  
    221 OnGameOver is a bit more tricky, as the old Invaders would call EventManager::LoadWindow directly from C++. We're going to have to add a game_over flag to game and make the GameElement check this state every update and fire a custom OnGameOver event. 
     220We can now get into the game, however the game will never finish as there's no key bindings for processing the ESCAPE key and nothing will make the game exit when the game is over. Fixing the key binding is easy, simply drop in a 'onkeydown' handler and make it launch the pause menu. 
     221 
     222The game over event is a bit more tricky, as the old Invaders would call EventManager::LoadWindow directly from C++. We're going to have to add a game_over flag to game and make the GameElement check this state every update and fire a custom 'gameover' event. 
    222223 
    223224{{{ 
    234235== Step 6: Python Data Formatters == 
    235236 
    236 We're still using C++ data formatters for the high scores, these can be moved into python for simplicity. 
     237We're still using C++ data formatters for the high scores, these can be moved into Python for simplicity. 
    237238 
    238239Here's my name formatter: 
    259260}}} 
    260261 
    261 A lot more code could be moved from C++ into Python, for example the HighScore system. Its just a matter of taking the principles you have learnt here and applying them. 
     262A lot more code could be moved from C++ into Python, for example the HighScore system. Its just a matter of taking the principles described here and applying them.