[ROOT] --> Emulator
Space Invaders arcade machine emulator.
This class emulates in software the original Space Invaders arcade machine. It uses the I8080 emulator to emulate the CPU and extends the I8080Environment to provide the required functions to the CPU emulation.
For portability, this class does not make direct use of functions that may depend on a specific system, such as sound and video. However, it does provide access to all necessary information in a form that makes it much easier for a system-dependent layer to implement the required functionality.
For example, sound samples are not directly played but the getSounds() function provides information about what sounds the game is playing.
public InvadersMachine ( ) ;
Constructor.
public virtual ~ InvadersMachine ( ) ;
Destructor.
public enum Constants { ScreenWidth = 224, , ScreenHeight = 256 } ;
Machine-related definitions.
public enum Sounds { SoundUfo = 1 , SoundShot = 2 , SoundBaseHit = 4 , SoundInvaderHit = 8 , SoundUfoHit = 16, , SoundWalk1 = 32, , SoundWalk2 = 64, , SoundWalk3 = 128, , SoundWalk4 = 256 } ;
Sounds played by the machine.
public enum Events { KeyLeftDown = 0 , KeyLeftUp , KeyRightDown , KeyRightUp , KeyFireDown , KeyFireUp , KeyOnePlayerDown , KeyOnePlayerUp , KeyTwoPlayersDown , KeyTwoPlayersUp , CoinInserted } ;
Events accepted by the machine.
public void reset ( int ships = 3 , int easy = 0 ) ;
Resets the machine.
ships | number of ships per game (3 to 6) |
easy | enable easy play if non zero |
public void step ( ) ;
Executes the program until the next frame is ready.
public void fireEvent ( int event ) ;
Informs the machine that an event has occurred.
This function is used mainly to fire events related to the coin slots or the arcade input devices, such as joysticks and buttons.
event | event to fire (see the Events enumeration for a list of recognized events) |
public const unsigned char * getVideo ( ) const ;
Returns a pointer to the game video memory in normalized form (224x256, one byte per pixel).
The original machine uses a one bit per pixel monochrome video adapter, where a byte contains eight vertically aligned pixels. Since this format is not in use anymore, the emulator reorganizes video memory so that there is one byte per pixel, with scanlines arranged as usual: the first scanline starts at offset 0, the second at offset 224 and so on. This "wastes" some memory, but makes it much easier to render the video on current cards.
public unsigned getSounds ( ) const ;
Returns a bit array which describes what sounds the game has played during the last frame.
The original machine used custom analogic devices for sounds, controlled by a couple of I/O ports. Once activated each sound device would go on automatically and generate its own sound effect without requiring further control by the CPU. Because of that, the easiest and probably best approach for emulation is to sample the original sounds and then simply play them back when required. This is the approach that this class supports with the getSounds() function.
To simplify implementations, the emulator adopts an event based approach that keeps track of changes in the sound status. In fact, it is only useful to know when a sound is activated, because then it will play automatically and then go off all by itself. In fact, when step() is called, one of the first things it does is to reset the sound status. As the game runs, it may activate one or more sounds, which the emulator keeps track of. Eventually, on exit from the step() function, the updated sound status can be retrieved by calling getSounds().
The value returned by getSounds() is an array of bits where each bit corresponds to a sound. If a bit is set, it means that during the last step (or frame) the game has played the corresponding sound. Note that if a bit is not set that does not mean that the corresponding sound is turned off, but rather that it keeps it current status. A sound should be only turned off when the corresponding sample has been entirely played.
The only exception is represented by the UFO sound (the SoundUfo bit), which goes into a continuous loop when played. In this case the game explicitly turns on and off the sound, and so the corresponding bit by getSounds() actually reflects the sound status, playing when set and not playing when reset.
Assuming that the function PlaySound plays a sound once, and that PlayLoopedSound plays a sound that automatically loops, sounds could be handled like in the following code snippet.
... machine.step(); if( machine.getSounds() & InvadersMachine::SoundShot ) PlaySound( "SoundShot sample" ); ... if( machine.getSounds() & InvadersMachine::SoundUfo ) PlayLoopedSound( "SoundUfo sample" ); else StopLoopedSound( "SoundUfo sample" ); ...
public void setFrameRate ( unsigned fps ) ;
Sets the video frame rate.
fps | frames per second |
public unsigned getFrameRate ( ) const ;
Returns the current frame rate.
public void setROM ( const char * rom ) ;
Sets the machine ROM.
For this machine, the ROM is an 8K area that starts at address 0x0000.
Note: the ROM is copied to internal storage and the specified pointer is no longer used after this function returns.
rom | pointer to the ROM buffer |
This documentation was generated automatically by the ccdoc tool (version 0.7a).
Click here to submit a bug report or feature request.
Click here to return to the top of the page.