Pygame wrapper: Difference between revisions

From OLPC
Jump to navigation Jump to search
(New page: The Pygame wrapper is called olpcgames. For a tutorial on how to use it, see Game development HOWTO. This is the reference manual. =Getting the wrapper= Eventually, the wrapper will ...)
 
m (Reverted edits by Rizwan1218 (Talk) to last revision by Quozl)
 
(56 intermediate revisions by 18 users not shown)
Line 1: Line 1:
{{Developers}}
The Pygame wrapper is called olpcgames. For a tutorial on how to use it, see [[Game development HOWTO]]. This is the reference manual.
<< [[API reference]]

{{Olpcboxtop|toptext=[[{{PAGENAME}}|OLPCGames]]}}
{{ OBX source dev|projects/games-misc}}
{{ OBX devtickets |olpc-games}}
{{ OBX team |[[User:Mcfletch|Mike Fletcher]]}}
[http://dev.laptop.org/git?p=projects/games-misc;a=tree;f=olpcgames-src/dist;hb=HEAD Download]
{{Olpcboxbottom}}

''(See also [http://wiki.sugarlabs.org/go/Development_Team/Sugargame Sugargame].)''

The [[Pygame]] wrapper for the OLPC [[Sugar]] platform is called OLPCGames. This page explores the differences between standard Pygame programming and OLPCGames-mediated Pygame programming.

The automatically generated [http://dev.laptop.org/~mcfletch/OLPCGames/pydoc/olpcgames.html Pydoc documentation for OLPCGames] is the canonical reference work for the documentation.

=Strategic Rationale=

The particular value of the OLPCGames wrapper is not, in fact, the ability to run Pygame games on the OLPC. The particular value is that by using Pygame for your game, and OLPCGames as your wrapper, you should not need to worry about the underlying details of the (rapidly changing, and rather breakage-prone) Sugar API.

Historically that changing API has forced each (PyGTK) developer to revise their activities time and again. OLPCGames, which is effectively the "Sugar" side of your Pygame activity, is shared among many projects, so that when it is fixed, all of the games using it are fixed along with it (generally only needing to replace the version of OLPCGames they are using and re-publishing the .xo file).

In addition, there are platforms where creating a working Sugar development environment is a non-trivial task. For those environments, it is often possible to set up a simple Pygame environment, write your game/Activity in that environment, and then port (or have someone port) the Activity to the XO in a matter of minutes.

=Tutorials=

* [http://www.vrplumber.com/olpc/pycon2008-handout.odt PyCon 2008 Tutorial] ([http://www.vrplumber.com/olpc/pycon2008.tar.gz Code]) -- Hello World, Participant Tracking in Games, Networked TicTacToe, Journal integration, SVG and Pango rendering
* [[Porting pygame games to the XO]] -- Phil Hassey's notes on porting two of his games to the XO. Much shorter and higher-level presentation, assumes you already have a working Pygame game, know your way around your game's code base, and just need to know what's different about OLPCGames under Sugar
* [[Game development HOWTO]] -- describes the process of building a new skeleton project
* [http://pygametutorials.wikidot.com OOP tutorial for PyGame]


=Getting the wrapper=
=Getting the wrapper=


You can either [http://dev.laptop.org/~mcfletch/OLPCGames/ download the wrapper] as a .zip or .tar.gz
Eventually, the wrapper will be a part of the standard build. Before then, you need to get it from Git:

wget http://dev.laptop.org/~mcfletch/OLPCGames/OLPCGames-1.6.zip

or you can check it out of the git repository on dev.laptop.org (note, do '''not''' attempt this on an XO or other space-constrained device, GIT downloads the entire history of the project, which is over 120MB in this case).

git clone git://dev.laptop.org/projects/games-misc
git clone git://dev.laptop.org/projects/games-misc


The 'olpcgames' directory is the package in question. Submodules you can access are activity, canvas, camera, and pangofont. The wrapper also replaces certain Python modules (python.event) with 'eventwrap' (which can also be imported separately), so we document those here too.
The 'olpcgames' directory is the package in question. Submodules you can access are activity, canvas, camera, mesh, and pangofont. The wrapper also replaces certain Python modules (e.g. pygame.event with 'eventwrap' (which can also be imported separately)), so we document those here too.


=Activities=
=Activity=


The following Activities use OLPCGames and can serve as example code, (note that some of these projects may not be finished yet):
The <code>olpcgames.activity</code> module encapsulates creation of a Pygame activity. Your Activity should inherit from this class. Simply setting some class attributes is all you need to do in a class inheriting from olpcgames.activity.PyGameActivity in order to get Pygame to work.


* [[Story Builder]] -- Environment for creating story modules to be used in [[MaMaMedia]], uses the PGU GUI library extensively
* [[Games/Productive|Productive]] -- A Real-time Strategy game written explicitly for the OLPC platform. Includes networking via the mesh module (and raw Telepathy primitives). Graphics are via raw Pygame coding.
* [[Games/FiftyTwo|FiftyTwo]] -- A set of card games
* [[Maze]] -- Maze navigation game

* [http://dev.laptop.org/git?p=projects/games-misc;a=blob;f=cameratest.activity/run.py;hb=HEAD Camera Test] -- example of using the <code>olpcgames.camera</code> module [http://dev.laptop.org/~mcfletch/testactivities/cameratest-1.xo XO]
* [http://dev.laptop.org/git?p=projects/games-misc;a=blob;f=soundtest.activity/run.py;hb=HEAD Sound Test] -- example showing simple multi-channel sound usage [http://dev.laptop.org/~mcfletch/testactivities/soundtest-1.xo XO]

* [http://dev.laptop.org/git?p=projects/games-misc;a=blob;f=svgspritetest.activity/run.py;hb=HEAD SVG Sprite Test] -- example showing use of the <code>olpcgames.svgsprite</code> module [http://dev.laptop.org/~mcfletch/testactivities/svgspritetest-1.xo XO]

* [http://dev.laptop.org/git?p=projects/games-misc;a=blob;f=videotest.activity/run.py;hb=HEAD Video Test] -- example showing use of the [[GStreamer]]-based <code>olpcgames.video</code> module [http://dev.laptop.org/~mcfletch/testactivities/videotest-2.xo XO]
* [http://drupal.ceibaljam.org/?q=node/235 Quinteti] -- Tic Tac Toe like game [http://drupal.ceibaljam.org/sites/default/files/Quinteti-1_0.xo XO]

=Differences from Pygame=

The SDL Pygame wrapper allows for nested Pygame windows using a separate thread. It forwards GTK events and converts them to Pygame events. Games under the wrapper may not work exactly the same way and porting is not completely seamless -- you should be aware of a few OLPC-specific caveats:

* You cannot set the display mode using pygame.display.set_mode. You must set it in the wrapper boilerplate instead (see [[Game development HOWTO]]).

* It is not recommended that you use the regular Pygame.font text drawing. You can use the wrapper to draw text using the 'olpcgames.pangofont' module instead which supports proper internationalization. See [http://dev.laptop.org/~mcfletch/OLPCGames/pydoc/olpcgames.pangofont.html Pangofont].

** ''NOTE'': If you are developing on an AMD64/EMT64 platform, there is a bug in Pygame 1.7.x which prevents it from working with the SVG or PangoFont modules. This bug has been fixed on the trunk of Pygame and should show up with the next release.

* The event module is shadowed by [http://dev.laptop.org/~mcfletch/OLPCGames/pydoc/olpcgames.eventwrap.html Eventwrap] and some methods may not work exactly the same. Certain methods in pygame.mouse and pygame.key are also shadowed.

* There's no CD-ROM on OLPC-XOs, so the 'cdrom' module isn't generally useful.

=Keyboard and Mouse=

Keyboard and mouse work approximately as they do under Pygame. We simulate repeated key-down events when a key is held down for a period in order to simulate Pygame's operation.

The "gamepad" buttons on the left and right of the screen come in as Numpad number keys (i.e., <code>pygame.K_KP1</code> through <code>pygame.K_KP9</code>):
<pre>
<pre>
D-Pad (left of screen) Gamepad (right of screen)
class PyGameActivity(activity.Activity):
8 9 O
game_name = None
4 6 7 1 [] V
game_title = 'PyGame Game'
2 3 X
game_handler = None
game_size = (units.grid_to_pixels(16),
units.grid_to_pixels(11))
pygame_mode = 'SDL'
</pre>
</pre>


The D-pad (directional pad) mappings make sense as the traditional arrow keys on the numeric keypad of 101-key keyboards. The gamepad mappings make sense when you realize that 9/3 are page-up/page-down and 7/1 are home/end. The d-pad has 8 directions of articulation. You detect the diagonals by looking for two keys pressed at the same time.
game_name: This is a string containing the name of the module and, optionally a colon followed by the name of the main method (example: "tictactoe:main"). If there's no main method specified it defaults to "main". In this example, the wrapper code will import the module named "tictactoe" and call main() on it. That is expected to enter a Pygame main loop (which makes some call into pygame.event periodically, see [[Pygame wrapper#Eventwrap]]).


When designing your interfaces keep in mind that an OLPC-XO in tablet mode only has the eight "keys" above available (as well as a resize-and-rotate key, but that's already mapped by the operating system).
game_title:


Keep in mind that your activities will need to be localized into many languages, so binding, for instance "p" to "produce" is sub-optimal. If possible provide a run-time configuration, or at least a localization-time configuration mechanism (such as a configuration file) that lets more natural keys be chosen for each language's keyboard.
=Canvas=


== OLPC-XO (B4) Hardware Notes ==


The D-Pad control is usable for general control operations, but it is not a precise/fast control device as seen on gaming console controllers. It often slips from a cardinal direction to the adjacent intermediate direction (i.e. from left to left+up). You should not expect a traditional "platformer" game to be played with this control without some heuristics to clean up the input.
=Eventwrap=


The checkmark button (K_KP1) is far easier to click than the X button, so "click" for "fire" should likely be the checkmark rather than the X. (Which makes sense to English users, at least). The Game pad buttons are small and close enough that asking a user to rapidly switch between them will likely result in a lot of multiple-button push events. Again, some heuristic code would be needed to clean up the input.


= Cursors =
=Camera=


See [[Sugar Standard Icons]] for instructions on how to create and use a standard Sugar cursor within Pygame-based games. The arrow and hand cursor there should likely be sufficient for most games.

= Antialiased Lines =

The bit-depth chosen by the wrapper (16 bit on OLPC-XOs, normally) tends to make antialiased lines fail. The reason this is so hasn't been extensively investigated, so it's not known whether this is a hard-and-fast limitation, or just an optimization hint.

= Journal Integration =

OLPCGames produces events to tell you about Journal save/restore requests:

*pygame.USEREVENT
**code = olpcgames.FILE_READ_REQUEST (OLPCGames 1.6+)
*** filename -- the filename to be read
*** metadata -- metadata object (dictionary like)
**code = olpcgames.FILE_WRITE_REQUEST (OLPCGames 1.6+)
*** filename -- the filename to be written
*** metadata -- metadata object (dictionary like)

which are generated to allow you to save/restore to/from the [[Journal]]/Datastore on the OLPC.

= Window Resizing =

Window resizing doesn't work yet (i.e., resizing windows via the screen rotate button), but we will try to get this working soon.

=Module Reference=

The [http://dev.laptop.org/~mcfletch/OLPCGames/pydoc/olpcgames.html pydoc-generated documentation] for the OLPCGames package serves as the canonical reference work at this point.

= Customizing the Toolbar =

If you want to add stuff to the standard toolbar you can override build_toolbar in your PyGameActivity subclass like this:

<pre>
import pygame
import olpcgames
from sugar.graphics.toolbutton import ToolButton
from gettext import gettext as _

...

def build_toolbar( self ):
"""Build our Activity toolbar for the Sugar system."""
toolbar = super( MyActivityClass, self ).build_toolbar()
# Add a button
mybutton = ToolButton('activity-mybutton') # put the icon file here: MyGame.activity/icons/activity-mybutton.svg
mybutton.set_tooltip(_('Something'))
mybutton.connect('clicked', self._mybutton_cb)
toolbar.insert(mybutton, 2)
mybutton.show()
return toolbar

def _ mybutton_cb(self, button):
pygame.event.post(olpcgames.eventwrap.Event(pygame.USEREVENT, action='mybutton'))
</pre>

Then in your event handler do this:

<pre>
if event.type == pygame.USEREVENT:
if event.action == 'mybutton':
self.dosomething()
else:
print "Unknown user event action:", event.action
</pre>


[[Category:Developing games]]
=Pangofont=
[[Category:Python]]

Latest revision as of 20:33, 25 July 2013

<< API reference

Trac print.png Tickets all - active - new

Download

(See also Sugargame.)

The Pygame wrapper for the OLPC Sugar platform is called OLPCGames. This page explores the differences between standard Pygame programming and OLPCGames-mediated Pygame programming.

The automatically generated Pydoc documentation for OLPCGames is the canonical reference work for the documentation.

Strategic Rationale

The particular value of the OLPCGames wrapper is not, in fact, the ability to run Pygame games on the OLPC. The particular value is that by using Pygame for your game, and OLPCGames as your wrapper, you should not need to worry about the underlying details of the (rapidly changing, and rather breakage-prone) Sugar API.

Historically that changing API has forced each (PyGTK) developer to revise their activities time and again. OLPCGames, which is effectively the "Sugar" side of your Pygame activity, is shared among many projects, so that when it is fixed, all of the games using it are fixed along with it (generally only needing to replace the version of OLPCGames they are using and re-publishing the .xo file).

In addition, there are platforms where creating a working Sugar development environment is a non-trivial task. For those environments, it is often possible to set up a simple Pygame environment, write your game/Activity in that environment, and then port (or have someone port) the Activity to the XO in a matter of minutes.

Tutorials

  • PyCon 2008 Tutorial (Code) -- Hello World, Participant Tracking in Games, Networked TicTacToe, Journal integration, SVG and Pango rendering
  • Porting pygame games to the XO -- Phil Hassey's notes on porting two of his games to the XO. Much shorter and higher-level presentation, assumes you already have a working Pygame game, know your way around your game's code base, and just need to know what's different about OLPCGames under Sugar
  • Game development HOWTO -- describes the process of building a new skeleton project
  • OOP tutorial for PyGame

Getting the wrapper

You can either download the wrapper as a .zip or .tar.gz

wget http://dev.laptop.org/~mcfletch/OLPCGames/OLPCGames-1.6.zip

or you can check it out of the git repository on dev.laptop.org (note, do not attempt this on an XO or other space-constrained device, GIT downloads the entire history of the project, which is over 120MB in this case).

git clone git://dev.laptop.org/projects/games-misc

The 'olpcgames' directory is the package in question. Submodules you can access are activity, canvas, camera, mesh, and pangofont. The wrapper also replaces certain Python modules (e.g. pygame.event with 'eventwrap' (which can also be imported separately)), so we document those here too.

Activities

The following Activities use OLPCGames and can serve as example code, (note that some of these projects may not be finished yet):

  • Story Builder -- Environment for creating story modules to be used in MaMaMedia, uses the PGU GUI library extensively
  • Productive -- A Real-time Strategy game written explicitly for the OLPC platform. Includes networking via the mesh module (and raw Telepathy primitives). Graphics are via raw Pygame coding.
  • FiftyTwo -- A set of card games
  • Maze -- Maze navigation game
  • Camera Test -- example of using the olpcgames.camera module XO
  • Sound Test -- example showing simple multi-channel sound usage XO

Differences from Pygame

The SDL Pygame wrapper allows for nested Pygame windows using a separate thread. It forwards GTK events and converts them to Pygame events. Games under the wrapper may not work exactly the same way and porting is not completely seamless -- you should be aware of a few OLPC-specific caveats:

  • You cannot set the display mode using pygame.display.set_mode. You must set it in the wrapper boilerplate instead (see Game development HOWTO).
  • It is not recommended that you use the regular Pygame.font text drawing. You can use the wrapper to draw text using the 'olpcgames.pangofont' module instead which supports proper internationalization. See Pangofont.
    • NOTE: If you are developing on an AMD64/EMT64 platform, there is a bug in Pygame 1.7.x which prevents it from working with the SVG or PangoFont modules. This bug has been fixed on the trunk of Pygame and should show up with the next release.
  • The event module is shadowed by Eventwrap and some methods may not work exactly the same. Certain methods in pygame.mouse and pygame.key are also shadowed.
  • There's no CD-ROM on OLPC-XOs, so the 'cdrom' module isn't generally useful.

Keyboard and Mouse

Keyboard and mouse work approximately as they do under Pygame. We simulate repeated key-down events when a key is held down for a period in order to simulate Pygame's operation.

The "gamepad" buttons on the left and right of the screen come in as Numpad number keys (i.e., pygame.K_KP1 through pygame.K_KP9):

D-Pad (left of screen)             Gamepad (right of screen)
  
      8                                    9       O
    4   6                                7   1   []  V
      2                                    3       X

The D-pad (directional pad) mappings make sense as the traditional arrow keys on the numeric keypad of 101-key keyboards. The gamepad mappings make sense when you realize that 9/3 are page-up/page-down and 7/1 are home/end. The d-pad has 8 directions of articulation. You detect the diagonals by looking for two keys pressed at the same time.

When designing your interfaces keep in mind that an OLPC-XO in tablet mode only has the eight "keys" above available (as well as a resize-and-rotate key, but that's already mapped by the operating system).

Keep in mind that your activities will need to be localized into many languages, so binding, for instance "p" to "produce" is sub-optimal. If possible provide a run-time configuration, or at least a localization-time configuration mechanism (such as a configuration file) that lets more natural keys be chosen for each language's keyboard.

OLPC-XO (B4) Hardware Notes

The D-Pad control is usable for general control operations, but it is not a precise/fast control device as seen on gaming console controllers. It often slips from a cardinal direction to the adjacent intermediate direction (i.e. from left to left+up). You should not expect a traditional "platformer" game to be played with this control without some heuristics to clean up the input.

The checkmark button (K_KP1) is far easier to click than the X button, so "click" for "fire" should likely be the checkmark rather than the X. (Which makes sense to English users, at least). The Game pad buttons are small and close enough that asking a user to rapidly switch between them will likely result in a lot of multiple-button push events. Again, some heuristic code would be needed to clean up the input.

Cursors

See Sugar Standard Icons for instructions on how to create and use a standard Sugar cursor within Pygame-based games. The arrow and hand cursor there should likely be sufficient for most games.

Antialiased Lines

The bit-depth chosen by the wrapper (16 bit on OLPC-XOs, normally) tends to make antialiased lines fail. The reason this is so hasn't been extensively investigated, so it's not known whether this is a hard-and-fast limitation, or just an optimization hint.

Journal Integration

OLPCGames produces events to tell you about Journal save/restore requests:

  • pygame.USEREVENT
    • code = olpcgames.FILE_READ_REQUEST (OLPCGames 1.6+)
      • filename -- the filename to be read
      • metadata -- metadata object (dictionary like)
    • code = olpcgames.FILE_WRITE_REQUEST (OLPCGames 1.6+)
      • filename -- the filename to be written
      • metadata -- metadata object (dictionary like)

which are generated to allow you to save/restore to/from the Journal/Datastore on the OLPC.

Window Resizing

Window resizing doesn't work yet (i.e., resizing windows via the screen rotate button), but we will try to get this working soon.

Module Reference

The pydoc-generated documentation for the OLPCGames package serves as the canonical reference work at this point.

Customizing the Toolbar

If you want to add stuff to the standard toolbar you can override build_toolbar in your PyGameActivity subclass like this:

import pygame
import olpcgames
from sugar.graphics.toolbutton import ToolButton
from gettext import gettext as _

...

    def build_toolbar( self ):
        """Build our Activity toolbar for the Sugar system."""
        toolbar = super( MyActivityClass, self ).build_toolbar()
        
        # Add a button
        mybutton = ToolButton('activity-mybutton')  # put the icon file here: MyGame.activity/icons/activity-mybutton.svg
        mybutton.set_tooltip(_('Something'))
        mybutton.connect('clicked', self._mybutton_cb)
        toolbar.insert(mybutton, 2)
        mybutton.show()
        
        return toolbar

    def _ mybutton_cb(self, button):
        pygame.event.post(olpcgames.eventwrap.Event(pygame.USEREVENT, action='mybutton'))

Then in your event handler do this:

    if event.type == pygame.USEREVENT:
        if event.action == 'mybutton':
            self.dosomething()
        else:
            print "Unknown user event action:", event.action