It's free to join Gamasutra!|Have a question? Want to know who runs this site? Here you go.|Targeting the game development market with your product or service? Get info on advertising here.||For altering your contact information or changing email subscription preferences.
Registered members can log in here.Back to the home page.

Search articles, jobs, buyers guide, and more.

By Mika Tammenkoski
[Author's Bio]

Gamasutra
December 17, 2003

Introduction

Coping With Device Fragmentation

Insights For The Future

Printer Friendly Version
   

 

Change Login/Pwd
Post A Job
Post A Project
Post Resume
Post An Event
Post A Contractor
Post A Product
Write An Article
Get In Art Gallery
Submit News

 


 


[Submit Letter]

[View All...]
  



Upcoming Events:
Workshop on Network and Systems Support for Games (NetGames 2009)
Paris, France
11.23.09

EVA 09 - Exposicion de Videojuegos Argentina
Buenos Aires, Argentina
12.04.09

Flash GAMM Kyiv 2009
Kyiv, Ukraine
12.05.09

Game Connect: Asia Pacific (GCAP)
Melbourne, Australia
12.06.09

ICIDS 2009 – Interactive Storytelling
Guimaraes, Portugal
12.09.09

[Submit Event]
[View All...]

 


[Enter Forums...]

Note: Discussion forums for Gamasutra are hosted by the IGDA, which is free to join.
 

 

 


Features

Dealing With A Fragmented Java Landscape For Mobile Game Development

Coping With Device Fragmentation

In the summer of 2001 we at Sumea realized that the number of platforms our games would have to support in the future would be vast. As such, we started to develop technology and tools to ease our daily work. We targeted five key areas for our efforts: reusable components, scalability, localization, profile management, and testing.

Reusable components. Development cycles for mobile games are short compared to traditional game development--currently development cycles range from three to six months. On the other hand, when comparing one mobile game to another, one can see that there are many components in common: The games have a certain menu structure, program flow, features such as sounds, vibration and high scores, instruction page, and so on. In figure 1, only the screen framed in yellow is unique to this specific game-all the other screens can be reused in other games. By reusing components we shorten the development time of the game significantly.

Figure 1. Game structure flowchart.

Reusing code is an obvious advantage. To take full advantage of these components, we defined an abstract interface between the game and the generic components. We call these generic components our "game toolkit" The game has access to the toolkit as well as to standard APIs such as MIDP and CLDC, and the toolkit takes care of interfacing with proprietary APIs. This interface makes it possible to develop the game once, and exchange the underlying implementation to support any handset or any third-party API (see figure 2). For any new device or high score interface that didn't exist at the time the game was originally created, we update only the toolkit part, and keep the game code intact.

Figure 2. Game toolkit structure.

Scalability. Making games scale to the capabilities of the various mobile devices is not always easy. Games cannot be developed for the lowest common denominator platform; we have to take advantage of the capabilities each platform provides. This means that the game should look top-notch on each platform. For example, in a racing game we may have raindrops and lightning effects for high-end devices, and leave them out for the low-end devices. Scalability means just this: to make a customized version of the game for a certain platform as cost-efficiently as possible.

Scalability covers static content, such as graphics and audio, game specific features, such as level of detail, and devicespecific features. A good example of device-specific features are game controls. The devices out in the shops have various different keypad configurations: Most of the devices have an ordinary 3×4 keypad, some have game controllers, some support multiple key presses, and some devices have exotic keypad layouts, such as the Nokia 3650.

In the case of static content, the problem is solved by using different sets of content. For graphics this means that we use different sets of game graphics, and full-screen images are be customized for each screen resolution (see figure 3). For audio, the situation is even simpler: Either the device does not support sounds, it supports MIDI, or uses some proprietary audio technology.

Figure 3. Screenshots from a game designed for three different resolutions.

On the coding side, the problem can be solved in a similar way: by introducing different sets of features. A feature can be, for example, a lightning effect, support for sounds, or extra levels. We solved this problem in two ways: developing features at the component level and at the function level.

Component-level features are easy: we define an interface for a component, and select the version of the component to be used at compile time. In figure 4 you can see a practical example of this: We have a static component Sounds, which is used to play sounds in a game. The interface will remain the same, but the component can be exchanged to contain any sound implementation. This way we will get rid of an extra file for an actual interface, and Java obfuscators can optimize a class containing only static functions.


public class Sounds
{
   public static void initialize( MIDlet mid )
   {
      try
      {
         sm_title = readSound( mid, "/title.ott" );

   :
}

public class Sounds
{
   public static void initialize( MIDlet mid )
   {
      try
      {
         sm_title = Manager.createPlayer(
            mid.getClass().getResourceAsStream(
            "/title.mid" ), "audio/midi" );
   :
}

Figure 4: Code example of sound component for Nokia proprietary mono-sounds and Mobile Media API MIDI-sounds

Function-level features are more complicated: applications for wireless devices have to be optimized for speed and memory as well as for size. This means, for example, that we cannot have numerous different files. That, in turn, means that we must forget about pure object-oriented programming for a moment, even when using compile-time interfaces. Component-level features are not sufficient, as we cannot divide the code into as many components as we would need to. To tackle this problem we developed code preprocessing tools: If a certain tag is defined, the code remains intact-otherwise it is removed. An extreme example of this method can be seen in figure 5. The example is taken from a game in which the player can collect coins. When a coin is collected, a sound effect is played. When all the coins have been collected, a bonus game is opened. We defined two features: whether sounds are used (USE_SOUNDS) and whether the bonus game is included (BONUS_GAME). Either one of these features can be enabled or disabled. In figure 6 you can see the preprocessed code, where sounds have been disabled and the bonus game is enabled.


// <IF_DEFINED> BONUS_GAME
if ( m_coinCnt == m_totalCoinCnt )
{
   m_bonusGameOpened[0] = 1;
   m_showBonusGameActivated = 2000;

   // <IF_DEFINED> USE_SOUNDS
   Sounds.playAllCoinsCollected();
   // </IF_DEFINED> USE_SOUNDS
}
// </IF_DEFINED> BONUS_GAME

// <IF_DEFINED> BONUS_GAME & USE_SOUNDS
else
// </IF_DEFINED> BONUS_GAME & USE_SOUNDS

// <IF_DEFINED> USE_SOUNDS
   Sounds.playCollectCoin();
// </IF_DEFINED> USE_SOUNDS

Figure 5: Code example of original source code



if ( m_coinCnt == m_totalCoinCnt )
{
   m_bonusGameOpened[0] = 1;
   m_showBonusGameActivated = 2000;
}

Figure 6: Code example of preprocessed source code

With these types of features, porting a game to new handsets becomes easier. It is a matter of selecting the features to use, and compiling the game. The process is a bit like playing with building blocks.

Localization. The most important reason to localize games is that localized games sell better. Usually all the text in a game is translated--in some special cases even the title screen is translated. From Sumea's point of view, the most exotic language our games have been localized to is Chinese. By default we support five languages (English, French, German, Italian, and Spanish), and the number is increasing.

Usually the localization process goes like this: we deliver text assets for a certain game to the party taking care of the localization, get the translated assets back, build the game, and then deliver it to our customer. In some cases the game bounces back from the distributor's QA team due to errors in the localized assets. In some cases the context is wrong: it might be that a device uses certain terminology for navigation, and using different terminology confuses the user. This is straightforward work, and usually solving the problem once is enough.

Another problem arises from the different platforms supported. For example, controls have to be customized for certain handsets due to different keypad layouts. The easiest way of solving this is to have parameterized text assets. This means that we define the text once, define device specific parts as parameters, and fill those in either at compile time or at run time. In figure 7 you can see some of the English text assets used in Yoyo Fighter.


Parameterized instructions for Yoyo Fighter:

Controls:
%0U, %1U - Run left and right
%2U - Jump left
%3U - Jump up
%4U - Jump right
%5U - Flick yo-yo
%6U - Enter doors, drop down a platform
%7U - Cycle between carried items

You can only hit a baddie when a red box surrounds them.

After you obtain more items, press %7U to switch between them.

Story:
A magical portal transports you [Yozo] to the World of Stone where you must defeat the Golem Boss and save your helpless friend Jaco. Your only weapon is your yo-yo!

Use your yo-yo wisely to slay energy-draining bats and rock monsters! Look out for Extra Lives and Power Ups that will make your mission easier. Walk over info boxes for extra hints and tips on what to do in a particular situation.

Jaco can only be saved once you have successfully defeated the hideous Golem Boss!

Have fun! But be very careful!

Parameters for Nokia 7210:

4, 6
1
2
3
5, Green dial key
8
* and #

Parameters for Nokia 3650:

Left, right
0
Up
1
Navi key, 5
Down
* and #

Figure 7: Some text assets used in Yoyo Fighter.

From an implementation point of view, the simplest way to localize content is to use standard components provided by MIDP. These components take care of all the different aspects you can encounter: length of text in various languages, different font sizes, reading direction, handset user interface, and so on. The drawback to using system components is that you lose control over the graphical appearance. For example, it might be disturbing to show a system text box in the middle of a hectic gaming session.

The solution is to implement text components of your own. There are two simple rules to follow: never embed text in an image, and be conscious of the restrictions when drawing text. The reason for the first rule is simple: text is easier to replace than images (and it takes up far less memory). The second rule is more complicated, and is not easily fulfilled with a generic implementation because of strict limitations. We have compromised on this rule: When we know the limitations exactly, we use components of our own. In other cases we rely on the system components.

Profile management. Because of strict filesize limitations we will have to build a game file of its own for each device or device platform. To make things more straightforward, we include text assets for one language into a single build. One game build consists of JAD and JAR files. In practice, this means that for a game which supports eleven different platforms and eight languages, we have 88 different game builds-176 separate files. In most cases both of these files contain device-specific information. Managing all these files can be a tedious task, but luckily the process can be automated.

At Sumea we call the parameters that define a devicespecific version of a game a "profile". The profile defines source code and resource files to be used in a certain build of the game, as well as all device-specific parameters. These parameters define general properties such as whether sounds are used, whether the build is a debug or release version, whether the game is a demo version, and which system components are used, as well as game-specific properties such as which game controls and text assets will be used. We have developed tools with which we can define the profiles to be compiled with certain text assets, using just a single command.

Testing. Almost every device manufacturer provides device emulators to ease application development. The problem is that these emulators provide (at best) only an approximation of the actual device. Therefore we cannot rely on the emulators; we have to test the game in the actual handset. As most of the devices don't support on-device debugging, we have had to implement a logging mechanism to make the testing process easier. This logging mechanism gives the developer a means to store text-based information in the persistent memory, then to view it later. A good practice is to test games in new device software releases: software is rarely bug-free, and it might be that there are new bugs in the device software, or functionality of a certain API has changed enough to reveal or cause a bug in your game.

Fortunately, though, the emulators are getting better. In the early days we often received a device and a piece of documentation stating which APIs the device supports. The rest we had to figure out ourselves. Now emulators are starting to be more accurate and the documentation is, in the best cases at least, more than sufficient. The base software in devices is getting more stable as well-this means that when a new handset with a proven base software is released, we don't have to necessarily test the game in this new device, but can generally rely on it working flawlessly.

______________________________________________________


join | contact us | advertise | write | my profile
news | features | companies | jobs | resumes | education | product guide | projects | store



Copyright © 2003 CMP Media LLC

privacy policy
| terms of service