Too many changes to document here. The codebase is currently

heavily broken pending a rewrite of the Framebuffer class.


git-svn-id: svn://svn.code.sf.net/p/stella/code/trunk@198 8b62c5a3-ac7e-4cc8-8f21-d9a121418aba
This commit is contained in:
stephena 2003-10-17 18:02:16 +00:00
parent aa2a397b6c
commit c7233b35b0
14 changed files with 298 additions and 1585 deletions

View File

@ -13,7 +13,7 @@
## See the file "license" for information on usage and redistribution of
## this file, and for a DISCLAIMER OF ALL WARRANTIES.
##
## $Id: makefile,v 1.41 2003-09-26 00:32:00 stephena Exp $
## $Id: makefile,v 1.42 2003-10-17 18:02:15 stephena Exp $
##============================================================================
##============================================================================
@ -23,17 +23,37 @@
## Comment a line out to disable that option, remove comment to enable it.
##============================================================================
OPTIMIZATIONS = $(CXXFLAGS) -Wall -Wno-unused
OPTIMIZATIONS = $(CXXFLAGS) -Wall -Wunused
### which sound drivers to compile for the X11 and SDL versions
### which sound drivers to compile for the SDL version
### OSS is most compatible, SDL for platforms where OSS not available
### SDL sound not yet supported in the X11 version
### comment out all lines to completely disable sound
###
#SOUND_ALSA = 1
#SOUND_OSS = 1
#SOUND_SDL = 1
### to include OpenGL video support (SDL)
#DISPLAY_OPENGL = 1
### to include joystick support (SDL)
# JOYSTICK_SUPPORT = 1
### to include support for saving snapshots in png format
### (requires PNG library) FIXME
### Only SDL port supported for now FIXME
# SNAPSHOT_SUPPORT = 1
### comment this out if your system doesn't
### have the gettimeofday function
HAVE_GETTIMEOFDAY = 1
### to include support for game developers
### enables some extra commandline options that allow the user
### to override some emulation defaults
### Only SDL port supported for now
# DEVELOPER_SUPPORT = 1
### if your C++ compiler doesn't support the bool type
# BSPF_BOOL = 1
@ -43,25 +63,6 @@ OPTIMIZATIONS = $(CXXFLAGS) -Wall -Wno-unused
### you want a 6507 trace written to stdout
# DEBUG = 1
### to include joystick support in the X11 and SDL versions
JOYSTICK_SUPPORT = 1
### to include support for saving snapshots in png format
### (requires PNG library) FIXME
### Only X11 and SDL ports supported for now FIXME
SNAPSHOT_SUPPORT = 1
### comment this out if your system doesn't
### have the gettimeofday function
### Currently, the X11 version won't compile without it
HAVE_GETTIMEOFDAY = 1
### to include support for game developers
### enables some extra commandline options that allow the user
### to override some emulation defaults
### Only X11 and SDL ports supported for now
DEVELOPER_SUPPORT = 1
##============================================================================
## All done, type make to get a list of frontends
## No configurable options below this line ...
@ -73,11 +74,6 @@ LD = g++
LDFLAGS =
LDLIBS =
OBJS.X11 =
OPTS.X11 =
LIBS.X11 =
CFLAGS.X11 =
OBJS.SDL =
OPTS.SDL =
LIBS.SDL = `sdl-config --libs`
@ -88,78 +84,68 @@ OPTS.DOS = -DDOS=1
SRC = ..
CORE = $(SRC)/emucore
UI = $(SRC)/ui
COMMON = $(SRC)/ui/common
INCLUDES = -I. -I$(CORE) -I$(CORE)/m6502/src -I$(CORE)/m6502/src/bspf/src -I$(UI)/common
INCLUDES = -I. -I$(CORE) -I$(CORE)/m6502/src -I$(CORE)/m6502/src/bspf/src -I$(COMMON)
FLAGS = $(OPTIMIZATIONS) $(INCLUDES) $(SYS_INCLUDES)
## set the user-defined options
ifdef BSPF_BOOL
OPTS.X11 += -DBSPF_BOOL=1
OPTS.DOS += -DBSPF_BOOL=1
endif
ifdef SHOW_TIMING
OPTS.X11 += -DSHOW_TIMING=1
OPTS.SDL += -DSHOW_TIMING=1
OPTS.DOS += -DSHOW_TIMING=1
endif
ifdef DEBUG
OPTS.X11 += -DDEBUG=1
OPTS.SDL += -DDEBUG=1
OPTS.DOS += -DDEBUG=1
endif
ifdef JOYSTICK_SUPPORT
OPTS.X11 += -DHAVE_JOYSTICK=1
OPTS.SDL += -DHAVE_JOYSTICK=1
endif
ifdef SNAPSHOT_SUPPORT
OBJS.X11 += Snapshot.o
OPTS.X11 += -DSNAPSHOT_SUPPORT=1
LIBS.X11 += -lpng -lz
OBJS.SDL += Snapshot.o
OPTS.SDL += -DSNAPSHOT_SUPPORT=1
LIBS.SDL += -lpng -lz
endif
ifdef HAVE_GETTIMEOFDAY
OPTS.X11 += -DHAVE_GETTIMEOFDAY=1
OPTS.SDL += -DHAVE_GETTIMEOFDAY=1
endif
ifdef DEVELOPER_SUPPORT
OPTS.X11 += -DDEVELOPER_SUPPORT=1
OPTS.SDL += -DDEVELOPER_SUPPORT=1
OPTS.DOS += -DDEVELOPER_SUPPORT=1
endif
ifeq ($(SOUND_OSS), 1)
OPTS.X11 += -DSOUND_OSS=1
OBJS.X11 += SoundOSS.o
OPTS.SDL += -DSOUND_OSS=1
OBJS.SDL += SoundOSS.o
endif
ifeq ($(SOUND_SDL), 1)
# OPTS.X11 += -DSOUND_OSS=1
# OBJS.X11 += SoundOSS.o
OPTS.SDL += -DSOUND_SDL=1
OBJS.SDL += SoundSDL.o
endif
ifeq ($(SOUND_ALSA), 1)
OPTS.X11 += -DSOUND_ALSA=1
OBJS.X11 += SoundALSA.o
LIBS.X11 += -lasound
OPTS.SDL += -DSOUND_ALSA=1
OBJS.SDL += SoundALSA.o
LIBS.SDL += -lasound
endif
ifeq ($(DISPLAY_OPENGL), 1)
OPTS.SDL += -DDISPLAY_OPENGL=1
OBJS.SDL += DispGLSDL.o
LIBS.SDL += -lGL -lGLU
endif
default:
@echo ""
@ -169,11 +155,7 @@ default:
@echo "<version> is one of:"
@echo ""
@echo " dos DOS version using DJGPP"
@echo " unix-x Generic Unix X windows version"
@echo " linux-x Linux X windows version"
@echo " linux-sdl Linux SDL version"
@echo " bsdi-x BSD/OS 4.0 X Windows version"
@echo " solaris-x Solaris X windows version"
@echo ""
@echo "Hopefully new versions will be added soon!"
@echo ""
@ -189,32 +171,6 @@ dos:
LDLIBS="" \
OBJS="mainDOS.o PCJoys.o SndDOS.o dos_sb.o vga.o"
unix-x:
make stella.x11 \
INCLUDES="$(INCLUDES) -I$(UI)/x11 -I$(UI)/sound" \
SYS_INCLUDES="" \
OPTIONS="-DBSPF_UNIX=1 -DUNIX=1" \
OPTIONS+="$(OPTS.X11)" \
LDFLAGS="-L/usr/X11R6/lib" \
LDFLAGS+="$(CFLAGS.X11)" \
LDLIBS="-lX11 -lXext" \
LDLIBS+="$(LIBS.X11)" \
OBJS="mainX11.o SettingsUNIX.o"
OBJS+="$(OBJS.X11)"
linux-x:
make stella.x11 \
INCLUDES="$(INCLUDES) -I$(UI)/x11 -I$(UI)/sound" \
SYS_INCLUDES="" \
OPTIONS="-DBSPF_UNIX=1 -DUNIX=1" \
OPTIONS+="$(OPTS.X11)" \
LDFLAGS="-L/usr/X11R6/lib" \
LDFLAGS+="$(CFLAGS.X11)" \
LDLIBS="-lX11 -lXext" \
LDLIBS+="$(LIBS.X11)" \
OBJS="mainX11.o SettingsUNIX.o" \
OBJS+="$(OBJS.X11)"
linux-sdl:
make stella.sdl \
INCLUDES="$(INCLUDES) -I$(UI)/sdl -I$(UI)/sound" \
@ -225,35 +181,9 @@ linux-sdl:
LDFLAGS+="$(CFLAGS.SDL)" \
LDLIBS="-lX11 -lXext" \
LDLIBS+="$(LIBS.SDL)" \
OBJS="mainSDL.o RectList.o SettingsUNIX.o" \
OBJS="mainSDL.o FrameBufferSDL.o RectList.o SettingsUNIX.o" \
OBJS+="$(OBJS.SDL)"
bsdi-x:
make stella.x11 \
INCLUDES="$(INCLUDES) -I$(UI)/x11 -I$(UI)/sound" \
SYS_INCLUDES="-I/usr/X11R6/include" \
OPTIONS="-DBSPF_UNIX=1 -DUNIX=1" \
OPTIONS+="$(OPTS.X11)" \
LDFLAGS="-L/usr/X11R6/lib" \
LDFLAGS+="$(CFLAGS.X11)" \
LDLIBS="-lX11 -lXext" \
LDLIBS+="$(LIBS.X11)" \
OBJS="mainX11.o SettingsUNIX.o"
OBJS+="$(OBJS.X11)"
solaris-x:
make stella.x11 \
INCLUDES="$(INCLUDES) -I$(UI)/x11 -I$(UI)/sound" \
SYS_INCLUDES="-I/usr/openwin/include" \
OPTIONS="-DBSPF_UNIX=1 -DUNIX=1" \
OPTIONS+="$(OPTS.X11)" \
LDFLAGS="-L/usr/openwin/lib" \
LDFLAGS+="$(CFLAGS.X11)" \
LDLIBS="-lX11 -lXext" \
LDLIBS+="$(LIBS.X11)" \
OBJS="mainX11.o SettingsUNIX.o"
OBJS+="$(OBJS.X11)"
###############################################################################
## List of "core" object files
###############################################################################
@ -265,7 +195,7 @@ CORE_OBJS = Booster.o Cart.o Cart2K.o Cart3F.o Cart4K.o CartAR.o CartDPC.o \
CartMB.o Console.o Control.o Driving.o \
Event.o Joystick.o Keyboard.o M6532.o MD5.o MediaSrc.o Paddles.o \
Props.o PropsSet.o Random.o Sound.o Switches.o Settings.o TIA.o \
Serializer.o Deserializer.o TIASound.o EventHandler.o UserInterface.o \
Serializer.o Deserializer.o TIASound.o EventHandler.o FrameBuffer.o \
$(M6502_OBJS)
stella.exe: $(CORE_OBJS) $(OBJS)
@ -277,9 +207,6 @@ stella.exe: $(CORE_OBJS) $(OBJS)
del a
del a.exe
stella.x11: $(CORE_OBJS) $(OBJS)
$(LD) -o stella.x11 $(CORE_OBJS) $(OBJS) $(LDFLAGS) $(LDLIBS)
stella.sdl: $(CORE_OBJS) $(OBJS)
$(LD) -o stella.sdl $(CORE_OBJS) $(OBJS) $(LDFLAGS) $(LDLIBS)
@ -299,7 +226,7 @@ cleandos:
del M6502Hi.ins
clean:
rm -f *.o stella stella.x11 stella.sdl stella.exe core
rm -f *.o stella stella.sdl stella.exe core
cleanall: clean
rm -f M6502Low.ins M6502Hi.ins
@ -391,9 +318,6 @@ M6532.o: $(CORE)/M6532.cxx $(CORE)/M6532.hxx
TIA.o: $(CORE)/TIA.cxx $(CORE)/TIA.hxx
$(CXX) -c $(FLAGS) $(OPTIONS) $(CORE)/TIA.cxx
UserInterface.o: $(CORE)/UserInterface.cxx $(CORE)/UserInterface.hxx
$(CXX) -c $(FLAGS) $(OPTIONS) $(CORE)/UserInterface.cxx
TIASound.o: $(CORE)/TIASound.c $(CORE)/TIASound.h
$(CXX) -c -DWIN32 $(FLAGS) $(OPTIONS) $(CORE)/TIASound.c
@ -406,6 +330,9 @@ MD5.o: $(CORE)/MD5.cxx $(CORE)/MD5.hxx
MediaSrc.o: $(CORE)/MediaSrc.cxx $(CORE)/MediaSrc.hxx
$(CXX) -c $(FLAGS) $(OPTIONS) $(CORE)/MediaSrc.cxx
FrameBuffer.o: $(CORE)/FrameBuffer.cxx $(CORE)/FrameBuffer.hxx
$(CXX) -c $(FLAGS) $(OPTIONS) $(CORE)/FrameBuffer.cxx
PropsSet.o: $(CORE)/PropsSet.cxx $(CORE)/PropsSet.hxx
$(CXX) -c $(FLAGS) $(OPTIONS) $(CORE)/PropsSet.cxx
@ -430,8 +357,8 @@ Deserializer.o: $(CORE)/Deserializer.cxx $(CORE)/Deserializer.hxx
Settings.o: $(CORE)/Settings.cxx $(CORE)/Settings.hxx
$(CXX) -c $(FLAGS) $(OPTIONS) $(LDFLAGS) $(CORE)/Settings.cxx
SettingsUNIX.o: $(UI)/common/SettingsUNIX.cxx $(UI)/common/SettingsUNIX.hxx
$(CXX) -c $(FLAGS) $(OPTIONS) $(LDFLAGS) $(UI)/common/SettingsUNIX.cxx
SettingsUNIX.o: $(UI)/sdl/SettingsUNIX.cxx $(UI)/sdl/SettingsUNIX.hxx
$(CXX) -c $(FLAGS) $(OPTIONS) $(LDFLAGS) $(UI)/sdl/SettingsUNIX.cxx
Terminal.o: $(UI)/x11/Terminal.cxx $(UI)/x11/Terminal.hxx
$(CXX) -c $(FLAGS) $(OPTIONS) $(UI)/x11/Terminal.cxx
@ -469,6 +396,12 @@ mainSDL.o: $(UI)/sdl/mainSDL.cxx
RectList.o: $(UI)/sdl/RectList.cxx $(UI)/sdl/RectList.hxx
$(CXX) -c $(FLAGS) $(OPTIONS) $(LDFLAGS) $(UI)/sdl/RectList.cxx
FrameBufferSDL.o: $(UI)/sdl/FrameBufferSDL.cxx $(UI)/sdl/FrameBufferSDL.hxx
$(CXX) -c $(FLAGS) $(OPTIONS) $(LDFLAGS) $(UI)/sdl/FrameBufferSDL.cxx
FrameBufferGL.o: $(UI)/sdl/FrameBufferGL.cxx $(UI)/sdl/FrameBufferGL.hxx
$(CXX) -c $(FLAGS) $(OPTIONS) $(LDFLAGS) $(UI)/sdl/FrameBufferGL.cxx
Snapshot.o: $(UI)/common/Snapshot.cxx $(UI)/common/Snapshot.hxx
$(CXX) -c $(FLAGS) $(OPTIONS) $(LDFLAGS) $(UI)/common/Snapshot.cxx

View File

@ -13,7 +13,7 @@
// See the file "license" for information on usage and redistribution of
// this file, and for a DISCLAIMER OF ALL WARRANTIES.
//
// $Id: Console.cxx,v 1.17 2003-09-26 22:39:36 stephena Exp $
// $Id: Console.cxx,v 1.18 2003-10-17 18:02:16 stephena Exp $
//============================================================================
#include <assert.h>
@ -42,7 +42,7 @@
#include "Switches.hxx"
#include "System.hxx"
#include "TIA.hxx"
#include "UserInterface.hxx"
#include "FrameBuffer.hxx"
#ifdef SNAPSHOT_SUPPORT
#include "Snapshot.hxx"
@ -50,9 +50,11 @@
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Console::Console(const uInt8* image, uInt32 size, const char* filename,
Settings& rcsettings, PropertiesSet& propertiesSet, uInt32 sampleRate)
Settings& rcsettings, PropertiesSet& propertiesSet,
FrameBuffer& framebuffer, uInt32 sampleRate)
: mySettings(rcsettings),
myPropSet(propertiesSet)
myPropSet(propertiesSet),
myFrameBuffer(framebuffer)
{
myControllers[0] = 0;
myControllers[1] = 0;
@ -167,17 +169,19 @@ Console::Console(const uInt8* image, uInt32 size, const char* filename,
// Remember what my media source is
myMediaSource = tia;
// Create the graphical user interface to draw menus, text, etc.
myUserInterface = new UserInterface(this, myMediaSource);
// Reset, the system to its power-on state
mySystem->reset();
// Initialize the framebuffer interface.
// This must be done *after* a reset, since it needs updated values.
myFrameBuffer.init(this, myMediaSource);
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Console::Console(const Console& console)
: mySettings(console.mySettings),
myPropSet(console.myPropSet)
myPropSet(console.myPropSet),
myFrameBuffer(console.myFrameBuffer)
{
// TODO: Write this method
assert(false);
@ -191,7 +195,6 @@ Console::~Console()
delete myControllers[0];
delete myControllers[1];
delete myEventHandler;
delete myUserInterface;
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
@ -206,6 +209,12 @@ Settings& Console::settings() const
return mySettings;
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
FrameBuffer& Console::frameBuffer() const
{
return myFrameBuffer;
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Console& Console::operator = (const Console&)
{
@ -259,12 +268,12 @@ void Console::toggleFormat()
if(format == "NTSC")
{
myUserInterface->showMessage("PAL Mode");
myFrameBuffer->showMessage("PAL Mode");
myProperties.set("Display.Format", "PAL");
}
else if(format == "PAL")
{
myUserInterface->showMessage("NTSC Mode");
myFrameBuffer->showMessage("NTSC Mode");
myProperties.set("Display.Format", "NTSC");
}
}
@ -282,12 +291,12 @@ void Console::changeXStart(const uInt32 direction)
xstart += 4;
if(xstart > 80)
{
myUserInterface->showMessage("XStart at maximum");
myFrameBuffer->showMessage("XStart at maximum");
return;
}
else if((width + xstart) > 160)
{
myUserInterface->showMessage("XStart no effect");
myFrameBuffer->showMessage("XStart no effect");
return;
}
}
@ -296,7 +305,7 @@ void Console::changeXStart(const uInt32 direction)
xstart -= 4;
if(xstart < 0)
{
myUserInterface->showMessage("XStart at minimum");
myFrameBuffer->showMessage("XStart at minimum");
return;
}
}
@ -307,7 +316,7 @@ void Console::changeXStart(const uInt32 direction)
message = "XStart ";
message += strval.str();
myUserInterface->showMessage(message);
myFrameBuffer->showMessage(message);
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
@ -322,7 +331,7 @@ void Console::changeYStart(const uInt32 direction)
ystart++;
if(ystart > 64)
{
myUserInterface->showMessage("YStart at maximum");
myFrameBuffer->showMessage("YStart at maximum");
return;
}
}
@ -331,7 +340,7 @@ void Console::changeYStart(const uInt32 direction)
ystart--;
if(ystart < 0)
{
myUserInterface->showMessage("YStart at minimum");
myFrameBuffer->showMessage("YStart at minimum");
return;
}
}
@ -342,7 +351,7 @@ void Console::changeYStart(const uInt32 direction)
message = "YStart ";
message += strval.str();
myUserInterface->showMessage(message);
myFrameBuffer->showMessage(message);
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
@ -358,12 +367,12 @@ void Console::changeWidth(const uInt32 direction)
width += 4;
if((width > 160) || ((width % 4) != 0))
{
myUserInterface->showMessage("Width at maximum");
myFrameBuffer->showMessage("Width at maximum");
return;
}
else if((width + xstart) > 160)
{
myUserInterface->showMessage("Width no effect");
myFrameBuffer->showMessage("Width no effect");
return;
}
}
@ -372,7 +381,7 @@ void Console::changeWidth(const uInt32 direction)
width -= 4;
if(width < 80)
{
myUserInterface->showMessage("Width at minimum");
myFrameBuffer->showMessage("Width at minimum");
return;
}
}
@ -383,7 +392,7 @@ void Console::changeWidth(const uInt32 direction)
message = "Width ";
message += strval.str();
myUserInterface->showMessage(message);
myFrameBuffer->showMessage(message);
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
@ -398,7 +407,7 @@ void Console::changeHeight(const uInt32 direction)
height++;
if(height > 256)
{
myUserInterface->showMessage("Height at maximum");
myFrameBuffer->showMessage("Height at maximum");
return;
}
}
@ -407,7 +416,7 @@ void Console::changeHeight(const uInt32 direction)
height--;
if(height < 100)
{
myUserInterface->showMessage("Height at minimum");
myFrameBuffer->showMessage("Height at minimum");
return;
}
}
@ -418,7 +427,7 @@ void Console::changeHeight(const uInt32 direction)
message = "Height ";
message += strval.str();
myUserInterface->showMessage(message);
myFrameBuffer->showMessage(message);
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
@ -428,9 +437,9 @@ void Console::saveProperties(string filename, bool merge)
if(merge)
{
if(myPropSet.merge(myProperties, filename))
myUserInterface->showMessage("Properties merged");
myFrameBuffer->showMessage("Properties merged");
else
myUserInterface->showMessage("Properties not merged");
myFrameBuffer->showMessage("Properties not merged");
}
else // Save to the specified file directly
{
@ -440,11 +449,11 @@ void Console::saveProperties(string filename, bool merge)
{
myProperties.save(out);
out.close();
myUserInterface->showMessage("Properties saved");
myFrameBuffer->showMessage("Properties saved");
}
else
{
myUserInterface->showMessage("Properties not saved");
myFrameBuffer->showMessage("Properties not saved");
}
}
}

View File

@ -13,7 +13,7 @@
// See the file "license" for information on usage and redistribution of
// this file, and for a DISCLAIMER OF ALL WARRANTIES.
//
// $Id: Console.hxx,v 1.12 2003-09-25 16:20:33 stephena Exp $
// $Id: Console.hxx,v 1.13 2003-10-17 18:02:16 stephena Exp $
//============================================================================
#ifndef CONSOLE_HXX
@ -30,7 +30,7 @@ class Snapshot;
class Sound;
class Switches;
class System;
class UserInterface;
class FrameBuffer;
#include "bspf.hxx"
#include "Control.hxx"
@ -41,7 +41,7 @@ class UserInterface;
This class represents the entire game console.
@author Bradford W. Mott
@version $Id: Console.hxx,v 1.12 2003-09-25 16:20:33 stephena Exp $
@version $Id: Console.hxx,v 1.13 2003-10-17 18:02:16 stephena Exp $
*/
class Console
{
@ -59,7 +59,7 @@ class Console
*/
Console(const uInt8* image, uInt32 size, const char* filename,
Settings& rcsettings, PropertiesSet& propertiesSet,
uInt32 sampleRate);
FrameBuffer& framebuffer, uInt32 sampleRate);
/**
Create a new console object by copying another one
@ -84,16 +84,6 @@ class Console
return (jack == Controller::Left) ? *myControllers[0] : *myControllers[1];
}
/**
Get the media source of the console
@return The media source
*/
MediaSource& mediaSource() const
{
return *myMediaSource;
}
/**
Get the properties being used by the game
@ -108,6 +98,13 @@ class Console
*/
Settings& settings() const;
/**
Get the frame buffer of the console
@return The frame buffer
*/
FrameBuffer& frameBuffer() const;
/**
Get the console switches
@ -138,16 +135,6 @@ class Console
return *myEventHandler;
}
/**
Get the user interfacee of the console
@return The graphical user interface
*/
UserInterface& gui() const
{
return *myUserInterface;
}
public:
/**
Overloaded assignment operator
@ -255,12 +242,12 @@ class Console
// Reference to the PropertiesSet object
PropertiesSet& myPropSet;
// Reference to the FrameBuffer object
FrameBuffer& myFrameBuffer;
// Pointer to the EventHandler object
EventHandler* myEventHandler;
// Pointer to the UserInterface object
UserInterface* myUserInterface;
private:
// Default properties to use for properties objects
static Properties ourDefaultProperties;

View File

@ -13,7 +13,7 @@
// See the file "license" for information on usage and redistribution of
// this file, and for a DISCLAIMER OF ALL WARRANTIES.
//
// $Id: EventHandler.cxx,v 1.15 2003-09-30 01:22:45 stephena Exp $
// $Id: EventHandler.cxx,v 1.16 2003-10-17 18:02:16 stephena Exp $
//============================================================================
#include <algorithm>
@ -26,7 +26,7 @@
#include "Settings.hxx"
#include "StellaEvent.hxx"
#include "System.hxx"
#include "UserInterface.hxx"
#include "FrameBuffer.hxx"
#include "bspf.hxx"
#ifdef SNAPSHOT_SUPPORT
@ -88,13 +88,13 @@ void EventHandler::sendKeyEvent(StellaEvent::KeyCode key, Int32 state)
if(key == StellaEvent::KCODE_TAB && state == 1)
{
myMenuStatus = !myMenuStatus;
myConsole->gui().showMainMenu(myMenuStatus);
myConsole->frameBuffer().showMainMenu(myMenuStatus);
return;
}
// Determine where the event should be sent
if(myMenuStatus)
myConsole->gui().sendKeyEvent(key, state);
myConsole->frameBuffer().sendKeyEvent(key, state);
else
sendEvent(myKeyTable[key], state);
}
@ -105,7 +105,7 @@ void EventHandler::sendJoyEvent(StellaEvent::JoyStick stick,
{
// Determine where the event should be sent
if(myMenuStatus)
myConsole->gui().sendJoyEvent(stick, code, state);
myConsole->frameBuffer().sendJoyEvent(stick, code, state);
else
sendEvent(myJoyTable[stick*StellaEvent::LastJCODE + code], state);
}
@ -154,7 +154,7 @@ void EventHandler::sendEvent(Event::Type event, Int32 state)
}
if(ourMessageTable[event] != "")
myConsole->gui().showMessage(ourMessageTable[event]);
myConsole->frameBuffer().showMessage(ourMessageTable[event]);
}
// Otherwise, pass it to the emulation core
@ -372,7 +372,7 @@ void EventHandler::saveState()
else if(result == 3)
buf << "Invalid state " << myCurrentState << " file";
myConsole->gui().showMessage(buf.str());
myConsole->frameBuffer().showMessage(buf.str());
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
@ -387,7 +387,7 @@ void EventHandler::changeState()
ostringstream buf;
buf << "Changed to slot " << myCurrentState;
myConsole->gui().showMessage(buf.str());
myConsole->frameBuffer().showMessage(buf.str());
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
@ -407,7 +407,7 @@ void EventHandler::loadState()
else if(result == 3)
buf << "Invalid state " << myCurrentState << " file";
myConsole->gui().showMessage(buf.str());
myConsole->frameBuffer().showMessage(buf.str());
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
@ -416,11 +416,11 @@ void EventHandler::takeSnapshot()
#ifdef SNAPSHOT_SUPPORT
// Now save the snapshot file
string filename = myConsole->settings().snapshotFilename();
myConsole->snapshot().savePNG(filename, myConsole->mediaSource(),
myConsole->snapshot().savePNG(filename, myConsole->frameBuffer(),
myConsole->settings().getInt("zoom")); // FIXME - update zoom in resizewindow
myConsole->gui().showMessage("Snapshot saved");
myConsole->frameBuffer().showMessage("Snapshot saved");
#else
myConsole->gui().showMessage("Snapshots unsupported");
myConsole->frameBuffer().showMessage("Snapshots unsupported");
#endif
}

View File

@ -13,7 +13,7 @@
// See the file "license" for information on usage and redistribution of
// this file, and for a DISCLAIMER OF ALL WARRANTIES.
//
// $Id: UserInterface.cxx,v 1.9 2003-10-01 19:01:01 stephena Exp $
// $Id: FrameBuffer.cxx,v 1.1 2003-10-17 18:02:16 stephena Exp $
//============================================================================
#include <sstream>
@ -25,7 +25,7 @@
#include "StellaEvent.hxx"
#include "Settings.hxx"
#include "MediaSrc.hxx"
#include "UserInterface.hxx"
#include "FrameBuffer.hxx"
// Eventually, these may become variables
#define FGCOLOR 10 // A white color in NTSC and PAL mode
@ -46,10 +46,8 @@
#define RIGHTMARKER 16 // Indicates item being remapped
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
UserInterface::UserInterface(Console* console, MediaSource* mediasrc)
: myConsole(console),
myMediaSource(mediasrc),
myFrameRate(0),
FrameBuffer::FrameBuffer()
: myFrameRate(0),
myCurrentWidget(W_NONE),
myRemapEventSelectedFlag(false),
mySelectedEvent(Event::NoType),
@ -63,22 +61,23 @@ UserInterface::UserInterface(Console* console, MediaSource* mediasrc)
myRemapMenuMaxLines(0),
myMessageTime(0),
myMessageText(""),
myInfoMenuWidth(0)
myInfoMenuWidth(0),
isFullscreen(false) // FIXME
{
myFrameRate = myConsole->settings().getInt("framerate");
cerr << "FrameBuffer::FrameBuffer()\n";
}
myXStart = atoi(myConsole->properties().get("Display.XStart").c_str());
myWidth = atoi(myConsole->properties().get("Display.Width").c_str());
myYStart = atoi(myConsole->properties().get("Display.YStart").c_str());
myHeight = atoi(myConsole->properties().get("Display.Height").c_str());
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
FrameBuffer::~FrameBuffer(void)
{
cerr << "FrameBuffer::~FrameBuffer()\n";
}
// Make sure the starting x and width values are reasonable
if((myXStart + myWidth) > 160)
{
// Values are illegal so reset to default values
myXStart = 0;
myWidth = 160;
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void FrameBuffer::initBase(Console* console, MediaSource* mediasrc)
{
myConsole = console;
myMediaSource = mediasrc;
// Fill the properties info array with game information
ourPropertiesInfo[0] = myConsole->properties().get("Cartridge.Name");
@ -112,16 +111,13 @@ UserInterface::UserInterface(Console* console, MediaSource* mediasrc)
myConsole->eventHandler().getKeymapArray(&myKeyTable, &myKeyTableSize);
myConsole->eventHandler().getJoymapArray(&myJoyTable, &myJoyTableSize);
myFrameRate = myConsole->settings().getInt("framerate");
loadRemapMenu();
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
UserInterface::~UserInterface(void)
{
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void UserInterface::showMainMenu(bool show)
void FrameBuffer::showMainMenu(bool show)
{
myCurrentWidget = show ? MAIN_MENU : W_NONE;
myRemapEventSelectedFlag = false;
@ -129,14 +125,14 @@ void UserInterface::showMainMenu(bool show)
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void UserInterface::showMessage(const string& message)
void FrameBuffer::showMessage(const string& message)
{
myMessageText = message;
myMessageTime = myFrameRate << 1;
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void UserInterface::sendKeyEvent(StellaEvent::KeyCode key, Int32 state)
void FrameBuffer::sendKeyEvent(StellaEvent::KeyCode key, Int32 state)
{
if(myCurrentWidget == W_NONE || state != 1)
return;
@ -199,7 +195,7 @@ cerr << "'" << ourRemapMenu[myRemapMenuIndex].action << "' selected for remappin
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void UserInterface::sendJoyEvent(StellaEvent::JoyStick stick,
void FrameBuffer::sendJoyEvent(StellaEvent::JoyStick stick,
StellaEvent::JoyCode code, Int32 state)
{
if(myCurrentWidget == W_NONE || state != 1)
@ -245,51 +241,7 @@ cerr << "stick = " << stick << ", button = " << code << endl;
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void UserInterface::update()
{
switch(myCurrentWidget)
{
case W_NONE:
break;
case MAIN_MENU:
drawMainMenu();
break;
case REMAP_MENU:
drawRemapMenu();
break;
case INFO_MENU:
drawInfoMenu();
break;
case FONTS_MENU:
drawFontsMenu();
break;
default:
break;
}
// A message is a special case of interface element
// It can overwrite even a menu
if(myMessageTime > 0)
{
uInt32 width = myMessageText.length()*FONTWIDTH + FONTWIDTH;
uInt32 height = LINEOFFSET + FONTHEIGHT;
uInt32 x = (myWidth >> 1) - (width >> 1);
uInt32 y = myHeight - height - LINEOFFSET/2;
// Draw the bounded box and text
drawBoundedBox(x, y, width, height);
drawText(x + XBOXOFFSET/2, LINEOFFSET/2 + y, myMessageText);
myMessageTime--;
}
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
UserInterface::Widget UserInterface::currentSelectedWidget()
FrameBuffer::Widget FrameBuffer::currentSelectedWidget()
{
if(myMainMenuIndex >= 0 && myMainMenuIndex < myMainMenuItems)
return ourMainMenu[myMainMenuIndex].widget;
@ -298,7 +250,7 @@ UserInterface::Widget UserInterface::currentSelectedWidget()
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Event::Type UserInterface::currentSelectedEvent()
Event::Type FrameBuffer::currentSelectedEvent()
{
if(myRemapMenuIndex >= 0 && myRemapMenuIndex < myRemapMenuItems)
return ourRemapMenu[myRemapMenuIndex].event;
@ -307,7 +259,7 @@ Event::Type UserInterface::currentSelectedEvent()
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void UserInterface::moveCursorUp()
void FrameBuffer::moveCursorUp()
{
switch(myCurrentWidget)
{
@ -342,7 +294,7 @@ void UserInterface::moveCursorUp()
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void UserInterface::moveCursorDown()
void FrameBuffer::moveCursorDown()
{
switch(myCurrentWidget)
{
@ -377,7 +329,7 @@ void UserInterface::moveCursorDown()
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void UserInterface::movePageUp()
void FrameBuffer::movePageUp()
{
switch(myCurrentWidget)
{
@ -409,7 +361,7 @@ void UserInterface::movePageUp()
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void UserInterface::movePageDown()
void FrameBuffer::movePageDown()
{
switch(myCurrentWidget)
{
@ -441,185 +393,7 @@ void UserInterface::movePageDown()
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
inline void UserInterface::drawMainMenu()
{
uInt32 x, y, width, height, i, xpos, ypos;
width = 16*FONTWIDTH + 2*FONTWIDTH;
height = myMainMenuItems*LINEOFFSET + 2*FONTHEIGHT;
x = (myWidth >> 1) - (width >> 1);
y = (myHeight >> 1) - (height >> 1);
// Draw the bounded box and text, leaving a little room for arrows
xpos = x + XBOXOFFSET;
drawBoundedBox(x-2, y-2, width+3, height+3);
for(i = 0; i < myMainMenuItems; i++)
drawText(xpos, LINEOFFSET*i + y + YBOXOFFSET, ourMainMenu[i].action);
// Now draw the selection arrow around the currently selected item
ypos = LINEOFFSET*myMainMenuIndex + y + YBOXOFFSET;
drawChar(x, ypos, LEFTARROW);
drawChar(width - x, ypos, RIGHTARROW);
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
inline void UserInterface::drawRemapMenu()
{
uInt32 x, y, width, height, i, xpos, ypos;
width = 16*FONTWIDTH + 2*FONTWIDTH; // FIXME - change 16 to maximum in new framebuffer (~ 40)
height = myMaxLines*LINEOFFSET + 2*FONTHEIGHT;
x = (myWidth >> 1) - (width >> 1);
y = (myHeight >> 1) - (height >> 1);
// FIXME - change 100 to left bound of key strings in new frmaebuffer
// Draw the bounded box and text, leaving a little room for arrows
drawBoundedBox(x-2, y-2, width+3, height+3);
for(i = myRemapMenuLowIndex; i < myRemapMenuHighIndex; i++)
{
drawText(x + XBOXOFFSET, LINEOFFSET*(i-myRemapMenuLowIndex) + y + YBOXOFFSET,
ourRemapMenu[i].action);
drawText(x + XBOXOFFSET+100, LINEOFFSET*(i-myRemapMenuLowIndex) + y + YBOXOFFSET,
ourRemapMenu[i].key);
}
// Normally draw an arrow indicating the current line,
// otherwise highlight the currently selected item for remapping
if(!myRemapEventSelectedFlag)
{
ypos = LINEOFFSET*(myRemapMenuIndex-myRemapMenuLowIndex) + y + YBOXOFFSET;
drawChar(x, ypos, LEFTARROW);
drawChar(width - x, ypos, RIGHTARROW);
}
else
{
// FIXME - draw "<| |>" around key being changed
// Can't be done until the framebuffer has been updated and I know exactly
// where the item will be located on the line.
// cerr << "draw brackets around '" << ourRemapMenu[myRemapMenuIndex].key << "'\n";
drawText(x + 2, LINEOFFSET*(myRemapMenuIndex-myRemapMenuLowIndex) + y + YBOXOFFSET, ">");
}
// Finally, indicate that there are more items to the top or bottom
xpos = (width >> 1) - FONTWIDTH/2;
if(myRemapMenuHighIndex - myMaxLines > 0)
drawChar(xpos, y, UPARROW);
if(myRemapMenuLowIndex + myMaxLines < myRemapMenuItems)
drawChar(xpos, height - FONTWIDTH/2, DOWNARROW);
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
inline void UserInterface::drawInfoMenu()
{
uInt32 x, y, width, height, i, xpos, ypos;
width = myInfoMenuWidth*FONTWIDTH + 2*FONTWIDTH;
height = 6*LINEOFFSET + 2*FONTHEIGHT;
x = (myWidth >> 1) - (width >> 1);
y = (myHeight >> 1) - (height >> 1);
// Draw the bounded box and text
xpos = x + XBOXOFFSET;
drawBoundedBox(x, y, width, height);
for(i = 0; i < 6; i++)
drawText(xpos, LINEOFFSET*i + y + YBOXOFFSET, ourPropertiesInfo[i]);
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
inline void UserInterface::drawFontsMenu()
{
uInt32 xorig, yorig, width, height, xpos, ypos;
width = 16*FONTWIDTH + 2*FONTWIDTH;
height = myMaxLines*LINEOFFSET;
xorig = (myWidth >> 1) - (width >> 1);
yorig = (myHeight >> 1) - (height >> 1);
// Draw the bounded box and text
xpos = xorig + XBOXOFFSET;
ypos = yorig + YBOXOFFSET;
drawBoundedBox(xorig, yorig, width, height);
uInt8* buffer = myMediaSource->currentFrameBuffer();
for(uInt32 lines = 0; lines < 256; lines+=16)
{
for(uInt32 x = 0; x < 16; x++)
{
for(uInt32 y = 0; y < FONTHEIGHT; y++)
{
for(uInt32 z = 0; z < FONTWIDTH; z++)
{
uInt32 letter = lines + x;
if((ourFontData[(letter << 3) + y] >> z) & 1)
buffer[(y + ypos)*myWidth + (x<<3) + z + xpos] = FGCOLOR;
}
}
}
ypos += LINEOFFSET;
}
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void UserInterface::drawBoundedBox(uInt32 x, uInt32 y, uInt32 width, uInt32 height)
{
uInt8* buffer = myMediaSource->currentFrameBuffer();
for(uInt32 col = 0; col < width; ++col)
{
for(uInt32 row = 0; row < height; ++row)
{
uInt32 position = ((y + row) * myWidth) + col + x;
if((col == 0) || (col == width - 1) || (row == 0) || (row == height - 1))
buffer[position] = FGCOLOR;
else
buffer[position] = BGCOLOR;
}
}
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void UserInterface::drawText(uInt32 xorig, uInt32 yorig, const string& message)
{
uInt8* buffer = myMediaSource->currentFrameBuffer();
uInt8 length = message.length();
for(uInt32 x = 0; x < length; x++)
{
for(uInt32 y = 0; y < FONTHEIGHT; y++)
{
for(uInt32 z = 0; z < FONTWIDTH; z++)
{
char letter = message[x];
if((ourFontData[(letter << 3) + y] >> z) & 1)
buffer[(y + yorig)*myWidth + (x<<3) + z + xorig] = FGCOLOR;
}
}
}
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void UserInterface::drawChar(uInt32 xorig, uInt32 yorig, uInt32 c)
{
if(c >= 256 )
return;
uInt8* buffer = myMediaSource->currentFrameBuffer();
for(uInt32 y = 0; y < FONTHEIGHT; y++)
{
for(uInt32 z = 0; z < FONTWIDTH; z++)
{
if((ourFontData[(c << 3) + y] >> z) & 1)
buffer[(y + yorig)*myWidth + z + xorig] = FGCOLOR;
}
}
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void UserInterface::loadRemapMenu()
void FrameBuffer::loadRemapMenu()
{
// Fill the remap menu with the current key and joystick mappings
for(uInt32 i = 0; i < myRemapMenuItems; ++i)
@ -644,7 +418,29 @@ void UserInterface::loadRemapMenu()
ostringstream joyevent;
uInt32 stick = j / StellaEvent::LastJCODE;
uInt32 button = j % StellaEvent::LastJCODE;
joyevent << "Joy " << stick << " B" << button;
switch(button)
{
case StellaEvent::JAXIS_UP:
joyevent << "J" << stick << " UP";
break;
case StellaEvent::JAXIS_DOWN:
joyevent << "J" << stick << " DOWN";
break;
case StellaEvent::JAXIS_LEFT:
joyevent << "J" << stick << " LEFT";
break;
case StellaEvent::JAXIS_RIGHT:
joyevent << "J" << stick << " RIGHT";
break;
default:
joyevent << "J" << stick << " B" << (button-4);
break;
}
if(key == "")
key = key + joyevent.str();
@ -659,7 +455,7 @@ void UserInterface::loadRemapMenu()
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void UserInterface::addKeyBinding(Event::Type event, StellaEvent::KeyCode key)
void FrameBuffer::addKeyBinding(Event::Type event, StellaEvent::KeyCode key)
{
myKeyTable[key] = event;
@ -667,7 +463,7 @@ void UserInterface::addKeyBinding(Event::Type event, StellaEvent::KeyCode key)
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void UserInterface::addJoyBinding(Event::Type event,
void FrameBuffer::addJoyBinding(Event::Type event,
StellaEvent::JoyStick stick, StellaEvent::JoyCode code)
{
myJoyTable[stick * StellaEvent::LastJCODE + code] = event;
@ -676,7 +472,7 @@ void UserInterface::addJoyBinding(Event::Type event,
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void UserInterface::deleteBinding(Event::Type event)
void FrameBuffer::deleteBinding(Event::Type event)
{
for(uInt32 i = 0; i < myKeyTableSize; ++i)
if(myKeyTable[i] == event)
@ -690,7 +486,7 @@ void UserInterface::deleteBinding(Event::Type event)
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
const uInt8 UserInterface::ourFontData[2048] = {
const uInt8 FrameBuffer::ourFontData[2048] = {
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7e,0x81,0xa5,0x81,0xbd,0x99,0x81,0x7e,0x7e,0xff,0xdb,0xff,0xc3,0xe7,0xff,0x7e,0x36,0x7f,0x7f,0x7f,0x3e,0x1c,0x08,0x00,0x08,0x1c,0x3e,0x7f,0x3e,0x1c,0x08,0x00,0x1c,0x3e,0x1c,0x7f,0x7f,0x3e,0x1c,0x3e,0x08,0x08,0x1c,0x3e,0x7f,0x3e,0x1c,0x3e,0x00,0x00,0x18,0x3c,0x3c,0x18,0x00,0x00,0xff,0xff,0xe7,0xc3,0xc3,0xe7,0xff,0xff,0x00,0x3c,0x66,0x42,0x42,0x66,0x3c,0x00,0xff,0xc3,0x99,0xbd,0xbd,0x99,0xc3,0xff,0xf0,0xe0,0xf0,0xbe,0x33,0x33,0x33,0x1e,0x3c,0x66,0x66,0x66,0x3c,0x18,0x7e,0x18,0xfc,0xcc,0xfc,0x0c,0x0c,0x0e,0x0f,0x07,0xfe,0xc6,0xfe,0xc6,0xc6,0xe6,0x67,0x03,0x99,0x5a,0x3c,0xe7,0xe7,0x3c,0x5a,0x99,0x01,0x07,0x1f,0x7f,0x1f,0x07,0x01,0x00,0x40,0x70,0x7c,0x7f,0x7c,0x70,0x40,0x00,0x18,0x3c,0x7e,0x18,0x18,0x7e,0x3c,0x18,0x66,0x66,0x66,0x66,0x66,0x00,0x66,0x00,0xfe,0xdb,0xdb,0xde,0xd8,0xd8,0xd8,0x00,0x7c,0xc6,0x1c,0x36,0x36,0x1c,0x33,0x1e,0x00,0x00,0x00,0x00,0x7e,0x7e,0x7e,0x00,0x18,0x3c,0x7e,0x18,0x7e,0x3c,0x18,0xff,0x18,0x3c,0x7e,0x18,0x18,0x18,0x18,0x00,0x18,0x18,0x18,0x18,0x7e,0x3c,0x18,0x00,0x00,0x18,0x30,0x7f,0x30,0x18,0x00,0x00,0x00,0x0c,0x06,0x7f,0x06,0x0c,0x00,0x00,0x00,0x00,0x03,0x03,0x03,0x7f,0x00,0x00,0x00,0x24,0x66,0xff,0x66,0x24,0x00,0x00,0x00,0x18,0x3c,0x7e,0xff,0xff,0x00,0x00,0x00,0xff,0xff,0x7e,0x3c,0x18,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x0c,0x1e,0x1e,0x0c,0x0c,0x00,0x0c,0x00,0x36,0x36,0x36,0x00,0x00,0x00,0x00,0x00,0x36,0x36,0x7f,0x36,0x7f,0x36,0x36,0x00,0x0c,0x3e,0x03,0x1e,0x30,0x1f,0x0c,0x00,0x00,0x63,0x33,0x18,0x0c,0x66,0x63,0x00,0x1c,0x36,0x1c,0x6e,0x3b,0x33,0x6e,0x00,0x06,0x06,0x03,0x00,0x00,0x00,0x00,0x00,0x18,0x0c,0x06,0x06,0x06,0x0c,0x18,0x00,0x06,0x0c,0x18,0x18,0x18,0x0c,0x06,0x00,0x00,0x66,0x3c,0xff,0x3c,0x66,0x00,0x00,0x00,0x0c,0x0c,0x3f,0x0c,0x0c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x0c,0x0c,0x06,0x00,0x00,0x00,0x3f,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x0c,0x0c,0x00,0x60,0x30,0x18,0x0c,0x06,0x03,0x01,0x00,0x3e,0x63,0x73,0x7b,0x6f,0x67,0x3e,0x00,0x0c,0x0e,0x0c,0x0c,0x0c,0x0c,0x3f,0x00,0x1e,0x33,0x30,0x1c,0x06,0x33,0x3f,0x00,0x1e,0x33,0x30,0x1c,0x30,0x33,0x1e,0x00,0x38,0x3c,0x36,0x33,0x7f,0x30,0x78,0x00,0x3f,0x03,0x1f,0x30,0x30,0x33,0x1e,0x00,0x1c,0x06,0x03,0x1f,0x33,0x33,0x1e,0x00,0x3f,0x33,0x30,0x18,0x0c,0x0c,0x0c,0x00,0x1e,0x33,0x33,0x1e,0x33,0x33,0x1e,0x00,0x1e,0x33,0x33,0x3e,0x30,0x18,0x0e,0x00,0x00,0x0c,0x0c,0x00,0x00,0x0c,0x0c,0x00,0x00,0x0c,0x0c,0x00,0x00,0x0c,0x0c,0x06,0x18,0x0c,0x06,0x03,0x06,0x0c,0x18,0x00,0x00,0x00,0x3f,0x00,0x00,0x3f,0x00,0x00,0x06,0x0c,0x18,0x30,0x18,0x0c,0x06,0x00,0x1e,0x33,0x30,0x18,0x0c,0x00,0x0c,0x00,
0x3e,0x63,0x7b,0x7b,0x7b,0x03,0x1e,0x00,0x0c,0x1e,0x33,0x33,0x3f,0x33,0x33,0x00,0x3f,0x66,0x66,0x3e,0x66,0x66,0x3f,0x00,0x3c,0x66,0x03,0x03,0x03,0x66,0x3c,0x00,0x1f,0x36,0x66,0x66,0x66,0x36,0x1f,0x00,0x7f,0x46,0x16,0x1e,0x16,0x46,0x7f,0x00,0x7f,0x46,0x16,0x1e,0x16,0x06,0x0f,0x00,0x3c,0x66,0x03,0x03,0x73,0x66,0x7c,0x00,0x33,0x33,0x33,0x3f,0x33,0x33,0x33,0x00,0x1e,0x0c,0x0c,0x0c,0x0c,0x0c,0x1e,0x00,0x78,0x30,0x30,0x30,0x33,0x33,0x1e,0x00,0x67,0x66,0x36,0x1e,0x36,0x66,0x67,0x00,0x0f,0x06,0x06,0x06,0x46,0x66,0x7f,0x00,0x63,0x77,0x7f,0x7f,0x6b,0x63,0x63,0x00,0x63,0x67,0x6f,0x7b,0x73,0x63,0x63,0x00,0x1c,0x36,0x63,0x63,0x63,0x36,0x1c,0x00,0x3f,0x66,0x66,0x3e,0x06,0x06,0x0f,0x00,0x1e,0x33,0x33,0x33,0x3b,0x1e,0x38,0x00,0x3f,0x66,0x66,0x3e,0x36,0x66,0x67,0x00,0x1e,0x33,0x07,0x0e,0x38,0x33,0x1e,0x00,0x3f,0x2d,0x0c,0x0c,0x0c,0x0c,0x1e,0x00,0x33,0x33,0x33,0x33,0x33,0x33,0x3f,0x00,0x33,0x33,0x33,0x33,0x33,0x1e,0x0c,0x00,0x63,0x63,0x63,0x6b,0x7f,0x77,0x63,0x00,0x63,0x63,0x36,0x1c,0x1c,0x36,0x63,0x00,0x33,0x33,0x33,0x1e,0x0c,0x0c,0x1e,0x00,0x7f,0x63,0x31,0x18,0x4c,0x66,0x7f,0x00,0x1e,0x06,0x06,0x06,0x06,0x06,0x1e,0x00,0x03,0x06,0x0c,0x18,0x30,0x60,0x40,0x00,0x1e,0x18,0x18,0x18,0x18,0x18,0x1e,0x00,0x08,0x1c,0x36,0x63,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xff,
@ -702,14 +498,14 @@ const uInt8 UserInterface::ourFontData[2048] = {
};
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
UserInterface::MainMenuItem UserInterface::ourMainMenu[3] = {
FrameBuffer::MainMenuItem FrameBuffer::ourMainMenu[3] = {
{ REMAP_MENU, "Key Remapping" },
{ INFO_MENU, "Game Information" },
{ FONTS_MENU, "Character Set" }
};
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
UserInterface::RemapMenuItem UserInterface::ourRemapMenu[57] = {
FrameBuffer::RemapMenuItem FrameBuffer::ourRemapMenu[57] = {
{ Event::ConsoleSelect, "Select", "" },
{ Event::ConsoleReset, "Reset", "" },
{ Event::ConsoleColor, "Color TV", "" },
@ -787,7 +583,7 @@ UserInterface::RemapMenuItem UserInterface::ourRemapMenu[57] = {
lookups. So I do it this way instead.
*/
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
const char* UserInterface::ourEventName[StellaEvent::LastKCODE] = {
const char* FrameBuffer::ourEventName[StellaEvent::LastKCODE] = {
"A", "B", "C", "D", "E", "F", "G", "H", "I", "J", "K", "L", "M", "N", "O",
"P", "Q", "R", "S", "T", "U", "V", "W", "X", "Y", "Z",

View File

@ -13,41 +13,38 @@
// See the file "license" for information on usage and redistribution of
// this file, and for a DISCLAIMER OF ALL WARRANTIES.
//
// $Id: UserInterface.hxx,v 1.7 2003-10-01 19:01:02 stephena Exp $
// $Id: FrameBuffer.hxx,v 1.1 2003-10-17 18:02:16 stephena Exp $
//============================================================================
#ifndef USERINTERFACE_HXX
#define USERINTERFACE_HXX
#ifndef FRAMEBUFFER_HXX
#define FRAMEBUFFER_HXX
#include "bspf.hxx"
#include "Event.hxx"
#include "MediaSrc.hxx"
#include "StellaEvent.hxx"
class Console;
class MediaSource;
/**
This class implements a MAME-like user interface where Stella settings
can be changed.
can be changed. It also encapsulates the MediaSource.
@author Stephen Anthony
@version $Id: UserInterface.hxx,v 1.7 2003-10-01 19:01:02 stephena Exp $
@version $Id: FrameBuffer.hxx,v 1.1 2003-10-17 18:02:16 stephena Exp $
*/
class UserInterface
class FrameBuffer
{
public:
/**
Creates a new User Interface
@param console The Console object
@param mediasrc The MediaSource object to draw into
Creates a new Frame Buffer
*/
UserInterface(Console* console, MediaSource* mediasrc);
FrameBuffer();
/**
Destructor
*/
virtual ~UserInterface(void);
virtual ~FrameBuffer(void);
/**
Send a keyboard event to the user interface.
@ -67,18 +64,54 @@ class UserInterface
void sendJoyEvent(StellaEvent::JoyStick stick, StellaEvent::JoyCode code,
Int32 state);
public:
void showMainMenu(bool show);
void showMessage(const string& message);
void update();
private:
uInt32 width() { return myWidth; }
uInt32 height() { return myHeight; }
uInt16* pixels() const;
/**
Answers if the display is currently in fullscreen mode.
*/
bool fullScreen() { return isFullscreen; }
public:
/**
This routine should be called once the console is created to setup
the video system for us to use. Return false if any operation fails,
otherwise return true.
*/
virtual bool init(Console* console, MediaSource* mediasrc) = 0;
/**
This routine should be called anytime the display needs to be updated
*/
virtual void update() = 0;
/**
Toggles between fullscreen and windowed mode.
*/
virtual void toggleFullscreen() = 0;
protected:
// Enumeration representing the different types of user interface widgets
enum Widget { W_NONE, MAIN_MENU, REMAP_MENU, INFO_MENU, FONTS_MENU };
Widget currentSelectedWidget();
Event::Type currentSelectedEvent();
// Add binding between a StellaEvent key and a core event
void addKeyBinding(Event::Type event, StellaEvent::KeyCode key);
// Add binding between a StellaEvent joystick and a core event
void addJoyBinding(Event::Type event, StellaEvent::JoyStick stick,
StellaEvent::JoyCode code);
// Remove all bindings for this core event
void deleteBinding(Event::Type event);
// Move the cursor up 1 line, possibly scrolling the list of items
void moveCursorUp();
@ -91,42 +124,12 @@ class UserInterface
// Move the list down 1 page and put the cursor at the top
void movePageDown();
// Draw the main menu
void drawMainMenu();
// Draw the remap menu
void drawRemapMenu();
// Draw the info menu
void drawInfoMenu();
// Draw the fonts menu
void drawFontsMenu();
// Draw a bounded box at the specified coordinates
void drawBoundedBox(uInt32 x, uInt32 y, uInt32 width, uInt32 height);
// Draw message text at specified coordinates
void drawText(uInt32 x, uInt32 y, const string& message);
// Draw character 'c' at specified coordinates
void drawChar(uInt32 x, uInt32 y, uInt32 c);
// scan the mapping arrays and update the remap menu
void loadRemapMenu();
// Add binding between a StellaEvent key and a core event
void addKeyBinding(Event::Type event, StellaEvent::KeyCode key);
void initBase(Console* console, MediaSource* mediasrc);
// Add binding between a StellaEvent joystick and a core event
void addJoyBinding(Event::Type event, StellaEvent::JoyStick stick,
StellaEvent::JoyCode code);
// Remove all bindings for this core event
void deleteBinding(Event::Type event);
private:
protected:
// The Console for the system
Console* myConsole;
@ -208,6 +211,9 @@ class UserInterface
// Holds the number of items in the joytable array
uInt32 myJoyTableSize;
// Indicates whether the emulator is currently in fullscreen mode
bool isFullscreen; // FIXME - remove from here, its specific
};
#endif

View File

@ -1,43 +0,0 @@
//============================================================================
//
// SSSS tt lll lll
// SS SS tt ll ll
// SS tttttt eeee ll ll aaaa
// SSSS tt ee ee ll ll aa
// SS tt eeeeee ll ll aaaaa -- "An Atari 2600 VCS Emulator"
// SS SS tt ee ll ll aa aa
// SSSS ttt eeeee llll llll aaaaa
//
// Copyright (c) 1995-1998 by Bradford W. Mott
//
// See the file "license" for information on usage and redistribution of
// this file, and for a DISCLAIMER OF ALL WARRANTIES.
//
// $Id: Frontend.cxx,v 1.1 2003-09-05 18:02:58 stephena Exp $
//============================================================================
#include <assert.h>
#include "Frontend.hxx"
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Frontend::Frontend()
{
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Frontend::~Frontend()
{
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Frontend::Frontend(const Frontend&)
{
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Frontend& Frontend::operator = (const Frontend&)
{
assert(false);
return *this;
}

View File

@ -1,140 +0,0 @@
//============================================================================
//
// SSSS tt lll lll
// SS SS tt ll ll
// SS tttttt eeee ll ll aaaa
// SSSS tt ee ee ll ll aa
// SS tt eeeeee ll ll aaaaa -- "An Atari 2600 VCS Emulator"
// SS SS tt ee ll ll aa aa
// SSSS ttt eeeee llll llll aaaaa
//
// Copyright (c) 1995-1998 by Bradford W. Mott
//
// See the file "license" for information on usage and redistribution of
// this file, and for a DISCLAIMER OF ALL WARRANTIES.
//
// $Id: Frontend.hxx,v 1.5 2003-09-12 18:08:53 stephena Exp $
//============================================================================
#ifndef FRONTEND_HXX
#define FRONTEND_HXX
class Console;
#include "bspf.hxx"
/**
This class provides an interface for accessing frontend specific data.
@author Stephen Anthony
@version $Id: Frontend.hxx,v 1.5 2003-09-12 18:08:53 stephena Exp $
*/
class Frontend
{
public:
/**
Create a new frontend
*/
Frontend();
/**
Destructor
*/
virtual ~Frontend();
public:
/**
This method should be called when the emulation core sets
the console object.
*/
virtual void setConsole(Console* console) = 0;
/**
This method should be called when the emulation core receives
a QUIT event.
*/
virtual void setQuitEvent() = 0;
/**
This method determines whether the QUIT event has been received.
@return Boolean representing whether a QUIT event has been received
*/
virtual bool quit() = 0;
/**
This method should be called at when the emulation core receives
a PAUSE event.
*/
virtual void setPauseEvent() = 0;
/**
This method determines whether the PAUSE event has been received.
@return Boolean representing whether a PAUSE event has been received
*/
virtual bool pause() = 0;
/**
This method should be called to get the filename of a state file
given the md5 and state number.
@return String representing the full path of the state filename.
*/
virtual string stateFilename(string& md5, uInt32 state) = 0;
/**
This method should be called to get the filename of a snapshot.
@return String representing the full path of the snapshot filename.
*/
virtual string snapshotFilename() = 0;
/**
This method should be called to get the filename of the users
properties (stella.pro) file.
@return String representing the full path of the user properties filename.
*/
virtual string userPropertiesFilename() = 0;
/**
This method should be called to get the filename of the system
properties (stella.pro) file.
@return String representing the full path of the system properties filename.
*/
virtual string systemPropertiesFilename() = 0;
/**
This method should be called to get the filename of the users
config (stellarc) file.
@return String representing the full path of the users config filename.
*/
virtual string userConfigFilename() = 0;
/**
This method should be called to get the filename of the system
config (stellarc) file.
@return String representing the full path of the system config filename.
*/
virtual string systemConfigFilename() = 0;
/**
This method should be called to get the filename of the users
base home directory.
@return String representing the full path of the home directory.
*/
virtual string userHomeDir() = 0;
private:
// Copy constructor isn't supported by this class so make it private
Frontend(const Frontend&);
// Assignment operator isn't supported by this class so make it private
Frontend& operator = (const Frontend&);
};
#endif

View File

@ -13,7 +13,7 @@
// See the file "license" for information on usage and redistribution of
// this file, and for a DISCLAIMER OF ALL WARRANTIES.
//
// $Id: TIA.cxx,v 1.23 2003-09-26 22:39:36 stephena Exp $
// $Id: TIA.cxx,v 1.24 2003-10-17 18:02:16 stephena Exp $
//============================================================================
#include <cassert>
@ -28,7 +28,6 @@
#include "TIA.hxx"
#include "Serializer.hxx"
#include "Deserializer.hxx"
#include "UserInterface.hxx"
#include "TIASound.h"
#define HBLANK 68
@ -571,9 +570,6 @@ void TIA::update()
// Compute the number of scanlines in the frame
uInt32 totalClocks = (mySystem->cycles() * 3) - myClockWhenFrameStarted;
myScanlineCountForLastFrame = totalClocks / 228;
// Draw any pending user interface elements to the framebuffer
myConsole.gui().update();
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

View File

@ -1,193 +0,0 @@
//============================================================================
//
// SSSS tt lll lll
// SS SS tt ll ll
// SS tttttt eeee ll ll aaaa
// SSSS tt ee ee ll ll aa
// SS tt eeeeee ll ll aaaaa -- "An Atari 2600 VCS Emulator"
// SS SS tt ee ll ll aa aa
// SSSS ttt eeeee llll llll aaaaa
//
// Copyright (c) 1995-1999 by Bradford W. Mott
//
// See the file "license" for information on usage and redistribution of
// this file, and for a DISCLAIMER OF ALL WARRANTIES.
//
// $Id: SettingsUNIX.cxx,v 1.4 2003-09-23 00:58:31 stephena Exp $
//============================================================================
#include <cstdlib>
#include <sstream>
#include <fstream>
#include <unistd.h>
#include <sys/stat.h>
#include <sys/types.h>
#include "bspf.hxx"
#include "Console.hxx"
#include "EventHandler.hxx"
#include "StellaEvent.hxx"
#include "Settings.hxx"
#include "SettingsUNIX.hxx"
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
SettingsUNIX::SettingsUNIX()
{
// First set variables that the parent class needs
myBaseDir = getenv("HOME");
string stelladir = myBaseDir + "/.stella";
if(access(stelladir.c_str(), R_OK|W_OK|X_OK) != 0 )
mkdir(stelladir.c_str(), 0777);
myStateDir = stelladir + "/state/";
if(access(myStateDir.c_str(), R_OK|W_OK|X_OK) != 0 )
mkdir(myStateDir.c_str(), 0777);
myUserPropertiesFile = stelladir + "/stella.pro";
mySystemPropertiesFile = "/etc/stella.pro";
myUserConfigFile = stelladir + "/stellarc";
mySystemConfigFile = "/etc/stellarc";
// Set up the names of the input and output config files
mySettingsOutputFilename = myUserConfigFile;
if(access(myUserConfigFile.c_str(), R_OK) == 0)
mySettingsInputFilename = myUserConfigFile;
else
mySettingsInputFilename = mySystemConfigFile;
mySnapshotFile = "";
myStateFile = "";
// Now create UNIX specific settings
set("fullscreen", "false");
set("grabmouse", "false");
set("center", "false");
set("hidecursor", "false");
set("owncmap", "false");
set("accurate", "true");
set("volume", "-1");
set("sound", "oss");
set("joyleft", "0");
set("joyright", "1");
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
SettingsUNIX::~SettingsUNIX()
{
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void SettingsUNIX::usage(string& message)
{
cout << endl
<< message << endl
<< endl
<< "Valid options are:" << endl
<< endl
<< " -framerate <number> Display the given number of frames per second\n"
<< " -zoom <size> Makes window be 'size' times normal\n"
<< " -owncmap <0|1> Install a private colormap\n"
<< " -fullscreen <0|1> Play the game in fullscreen mode\n"
<< " -grabmouse <0|1> Keeps the mouse in the game window\n"
<< " -hidecursor <0|1> Hides the mouse cursor in the game window\n"
<< " -center <0|1> Centers the game window onscreen\n"
<< " -volume <number> Set the volume (0 - 100)\n"
#ifdef HAVE_JOYSTICK
<< " -paddle <0|1|2|3|real> Indicates which paddle the mouse should emulate\n"
<< " or that real Atari 2600 paddles are being used\n"
<< " -joyleft <number> The joystick number representing the left controller\n"
<< " -joyright <number> The joystick number representing the right controller\n"
#else
<< " -paddle <0|1|2|3> Indicates which paddle the mouse should emulate\n"
#endif
<< " -altpro <props file> Use the given properties file instead of stella.pro\n"
<< " -showinfo <0|1> Shows some game info\n"
<< " -accurate <0|1> Accurate game timing (uses more CPU)\n"
#ifdef SNAPSHOT_SUPPORT
<< " -ssdir <path> The directory to save snapshot files to\n"
<< " -ssname <name> How to name the snapshot (romname or md5sum)\n"
<< " -sssingle <0|1> Generate single snapshot instead of many\n"
#endif
<< endl
<< " -sound <type> Type is one of the following:\n"
<< " 0 Disables all sound generation\n"
#ifdef SOUND_ALSA
<< " alsa ALSA version 0.9 driver\n"
#endif
#ifdef SOUND_OSS
<< " oss Open Sound System driver\n"
#endif
<< endl
#ifdef DEVELOPER_SUPPORT
<< " DEVELOPER options (see Stella manual for details)\n"
<< " -Dformat Sets \"Display.Format\"\n"
<< " -Dxstart Sets \"Display.XStart\"\n"
<< " -Dwidth Sets \"Display.Width\"\n"
<< " -Dystart Sets \"Display.YStart\"\n"
<< " -Dheight Sets \"Display.Height\"\n"
<< " -mergeprops <0|1> Merge changed properties into properties file,\n"
<< " or save into a separate file\n"
#endif
<< endl;
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
string SettingsUNIX::stateFilename(uInt32 state)
{
if(!myConsole)
return "";
ostringstream buf;
buf << myStateDir << myConsole->properties().get("Cartridge.MD5")
<< ".st" << state;
myStateFile = buf.str();
return myStateFile;
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
string SettingsUNIX::snapshotFilename()
{
if(!myConsole)
return "";
string filename;
string path = getString("ssdir");
string theSnapshotName = getString("ssname");
if(theSnapshotName == "romname")
path = path + "/" + myConsole->properties().get("Cartridge.Name");
else if(theSnapshotName == "md5sum")
path = path + "/" + myConsole->properties().get("Cartridge.MD5");
// Replace all spaces in name with underscores
replace(path.begin(), path.end(), ' ', '_');
// Check whether we want multiple snapshots created
if(!getBool("sssingle"))
{
// Determine if the file already exists, checking each successive filename
// until one doesn't exist
filename = path + ".png";
if(access(filename.c_str(), F_OK) == 0 )
{
ostringstream buf;
for(uInt32 i = 1; ;++i)
{
buf.str("");
buf << path << "_" << i << ".png";
if(access(buf.str().c_str(), F_OK) == -1 )
break;
}
filename = buf.str();
}
}
else
filename = path + ".png";
mySnapshotFile = filename;
return mySnapshotFile;
}

View File

@ -1,70 +0,0 @@
//============================================================================
//
// SSSS tt lll lll
// SS SS tt ll ll
// SS tttttt eeee ll ll aaaa
// SSSS tt ee ee ll ll aa
// SS tt eeeeee ll ll aaaaa -- "An Atari 2600 VCS Emulator"
// SS SS tt ee ll ll aa aa
// SSSS ttt eeeee llll llll aaaaa
//
// Copyright (c) 1995-1999 by Bradford W. Mott
//
// See the file "license" for information on usage and redistribution of
// this file, and for a DISCLAIMER OF ALL WARRANTIES.
//
// $Id: SettingsUNIX.hxx,v 1.4 2003-09-23 00:58:31 stephena Exp $
//============================================================================
#ifndef SETTINGS_UNIX_HXX
#define SETTINGS_UNIX_HXX
#include "bspf.hxx"
class Console;
/**
This class defines UNIX-like OS's (Linux) system specific settings.
@author Stephen Anthony
@version $Id: SettingsUNIX.hxx,v 1.4 2003-09-23 00:58:31 stephena Exp $
*/
class SettingsUNIX : public Settings
{
public:
/**
Create a new UNIX settings object
*/
SettingsUNIX();
/**
Destructor
*/
virtual ~SettingsUNIX();
public:
/**
This method should be called to get the filename of a state file
given the state number.
@return String representing the full path of the state filename.
*/
virtual string stateFilename(uInt32 state);
/**
This method should be called to get the filename of a snapshot.
@return String representing the full path of the snapshot filename.
*/
virtual string snapshotFilename();
/**
Display the commandline settings for this UNIX version of Stella.
@param message A short message about this version of Stella
*/
virtual void usage(string& message);
};
#endif

View File

@ -13,7 +13,7 @@
// See the file "license" for information on usage and redistribution of
// this file, and for a DISCLAIMER OF ALL WARRANTIES.
//
// $Id: Snapshot.cxx,v 1.5 2003-09-12 18:08:54 stephena Exp $
// $Id: Snapshot.cxx,v 1.6 2003-10-17 18:02:16 stephena Exp $
//============================================================================
#include <png.h>
@ -21,6 +21,7 @@
#include <fstream>
#include "bspf.hxx"
#include "FrameBuffer.hxx"
#include "Snapshot.hxx"
@ -61,18 +62,20 @@ void Snapshot::png_user_error(png_structp ctx, png_const_charp str)
This routine saves the current frame buffer to a 256 color PNG file,
appropriately scaled by the amount specified in 'multiplier'.
*/
int Snapshot::savePNG(string filename, MediaSource& mediaSource, uInt32 multiplier)
int Snapshot::savePNG(string filename, FrameBuffer& frameBuffer, uInt32 multiplier)
{
#if 0
// FIXME
png_structp png_ptr = 0;
png_infop info_ptr = 0;
uInt8* pixels = mediaSource.currentFrameBuffer();
uInt8* pixels = frameBuffer.current();
// PNG and window dimensions will be different because of scaling
int picWidth = mediaSource.width() * 2 * multiplier;
int picHeight = mediaSource.height() * multiplier;
int width = mediaSource.width();
int height = mediaSource.height();
int picWidth = frameBuffer.width() * 2 * multiplier;
int picHeight = frameBuffer.height() * multiplier;
int width = frameBuffer.width();
int height = frameBuffer.height();
ofstream* out = new ofstream(filename.c_str());
if(!out)
@ -90,7 +93,7 @@ int Snapshot::savePNG(string filename, MediaSource& mediaSource, uInt32 multipli
return 0;
}
const uInt32* gamePalette = mediaSource.palette();
const uInt32* gamePalette = frameBuffer.palette();
for(uInt32 i = 0; i < 256; ++i)
{
palette[i].red = (uInt8) ((gamePalette[i] & 0x00ff0000) >> 16);
@ -169,6 +172,6 @@ int Snapshot::savePNG(string filename, MediaSource& mediaSource, uInt32 multipli
out->close();
delete out;
#endif
return 1;
}

View File

@ -13,7 +13,7 @@
// See the file "license" for information on usage and redistribution of
// this file, and for a DISCLAIMER OF ALL WARRANTIES.
//
// $Id: Snapshot.hxx,v 1.2 2003-09-12 18:08:54 stephena Exp $
// $Id: Snapshot.hxx,v 1.3 2003-10-17 18:02:16 stephena Exp $
//============================================================================
#ifndef SNAPSHOT_HXX
@ -22,7 +22,8 @@
#include <png.h>
#include "bspf.hxx"
#include "MediaSrc.hxx"
class FrameBuffer;
class Snapshot
{
@ -30,7 +31,7 @@ class Snapshot
Snapshot();
~Snapshot();
int savePNG(string filename, MediaSource& mediaSource, uInt32 multiplier = 1);
int savePNG(string filename, FrameBuffer& mediaSource, uInt32 multiplier = 1);
private:
static void png_write_data(png_structp ctx, png_bytep area, png_size_t size);

View File

@ -13,12 +13,11 @@
// See the file "license" for information on usage and redistribution of
// this file, and for a DISCLAIMER OF ALL WARRANTIES.
//
// $Id: mainSDL.cxx,v 1.54 2003-09-29 18:10:56 stephena Exp $
// $Id: mainSDL.cxx,v 1.55 2003-10-17 18:02:16 stephena Exp $
//============================================================================
#include <fstream>
#include <iostream>
#include <sstream>
#include <string>
#include <algorithm>
@ -28,18 +27,21 @@
#endif
#include <SDL.h>
#include <SDL_syswm.h>
#include "bspf.hxx"
#include "Console.hxx"
#include "Event.hxx"
#include "StellaEvent.hxx"
#include "EventHandler.hxx"
#include "MediaSrc.hxx"
#include "FrameBuffer.hxx"
#include "FrameBufferSDL.hxx"
#include "PropsSet.hxx"
#include "Sound.hxx"
#include "Settings.hxx"
#include "RectList.hxx"
#ifdef DISPLAY_OPENGL
#include "FrameBufferGL.hxx"
#endif
#ifdef SOUND_ALSA
#include "SoundALSA.hxx"
@ -57,44 +59,6 @@
#include "SettingsUNIX.hxx"
#endif
// Hack for SDL < 1.2.0
#ifndef SDL_ENABLE
#define SDL_ENABLE 1
#endif
#ifndef SDL_DISABLE
#define SDL_DISABLE 0
#endif
// function prototypes
// FIXME the following will be placed in a Display class eventually ...
static bool setupDisplay();
static bool createScreen();
static void recalculate8BitPalette();
static void setupPalette();
static void updateDisplay(MediaSource& mediaSource);
static void resizeWindow(int mode);
static void centerWindow();
static void showCursor(bool show);
static void grabMouse(bool grab);
static void toggleFullscreen();
static uInt32 maxWindowSizeForScreen();
// Globals for the SDL stuff
static SDL_Surface* screen = (SDL_Surface*) NULL;
static Uint32 palette[256];
static int bpp;
static Display* theX11Display = (Display*) NULL;
static Window theX11Window = 0;
static int theX11Screen = 0;
static int mouseX = 0;
static bool x11Available = false;
static SDL_SysWMinfo info;
static int sdlflags;
static RectList* rectList = (RectList*) NULL;
static uInt32 theWidth, theHeight, theMaxWindowSize, theWindowSize;
////////////////////////////////////////////
static void cleanup();
static bool setupJoystick();
static void handleEvents();
@ -119,21 +83,15 @@ static Sound* theSound = (Sound*) NULL;
// Pointer to the settings object or the null pointer
static Settings* theSettings = (Settings*) NULL;
// Pointer to the display object or the null pointer
static FrameBufferSDL* theDisplay = (FrameBufferSDL*) NULL;
// Indicates if the mouse should be grabbed
static bool theGrabMouseIndicator = false;
// Indicates if the mouse cursor should be hidden
static bool theHideCursorIndicator = false;
// Indicates if the entire frame should be redrawn
static bool theRedrawEntireFrameIndicator = true;
// Indicates whether the game is currently in fullscreen
static bool isFullscreen = false;
// Indicates whether the window is currently centered
static bool isCentered = false;
// Indicates the current paddle mode
static Int32 thePaddleMode;
@ -296,88 +254,6 @@ inline uInt32 getTicks()
#endif
/**
This routine should be called once the console is created to setup
the SDL window for us to use. Return false if any operation fails,
otherwise return true.
*/
bool setupDisplay()
{
Uint32 initflags = SDL_INIT_VIDEO | SDL_INIT_TIMER;
if(SDL_Init(initflags) < 0)
return false;
// Check which system we are running under
x11Available = false;
SDL_VERSION(&info.version);
if(SDL_GetWMInfo(&info) > 0)
if(info.subsystem == SDL_SYSWM_X11)
x11Available = true;
sdlflags = SDL_SWSURFACE;
sdlflags |= theConsole->settings().getBool("fullscreen") ? SDL_FULLSCREEN : 0;
sdlflags |= theConsole->settings().getBool("owncmap") ? SDL_HWPALETTE : 0;
// Get the desired width and height of the display
theWidth = theConsole->mediaSource().width();
theHeight = theConsole->mediaSource().height();
// Get the maximum size of a window for THIS screen
// Must be called after display and screen are known, as well as
// theWidth and theHeight
theMaxWindowSize = maxWindowSizeForScreen();
// Check to see if window size will fit in the screen
if((uInt32)theConsole->settings().getInt("zoom") > theMaxWindowSize)
theWindowSize = theMaxWindowSize;
else
theWindowSize = theConsole->settings().getInt("zoom");
// Set up the rectangle list to be used in updateDisplay
rectList = new RectList();
if(!rectList)
{
cerr << "ERROR: Unable to get memory for SDL rects" << endl;
return false;
}
// Set the window title and icon
ostringstream name;
name << "Stella: \"" << theConsole->properties().get("Cartridge.Name") << "\"";
SDL_WM_SetCaption(name.str().c_str(), "stella");
// Create the screen
if(!createScreen())
return false;
setupPalette();
// Make sure that theUseFullScreenFlag sets up fullscreen mode correctly
theGrabMouseIndicator = theConsole->settings().getBool("grabmouse");
theHideCursorIndicator = theConsole->settings().getBool("hidecursor");
if(theConsole->settings().getBool("fullscreen"))
{
grabMouse(true);
showCursor(false);
isFullscreen = true;
}
else
{
// Keep mouse in game window if grabmouse is selected
grabMouse(theGrabMouseIndicator);
// Show or hide the cursor depending on the 'hidecursor' argument
showCursor(!theHideCursorIndicator);
}
// Center the window if centering is selected and not fullscreen
if(theConsole->settings().getBool("center") &&
!theConsole->settings().getBool("fullscreen"))
centerWindow();
return true;
}
/**
This routine should be called once setupDisplay is called
to create the joystick stuff.
@ -427,421 +303,6 @@ bool setupJoystick()
}
/**
This routine is called whenever the screen needs to be recreated.
It updates the global screen variable. When this happens, the
8-bit palette needs to be recalculated.
*/
bool createScreen()
{
int w = theWidth * theWindowSize * 2;
int h = theHeight * theWindowSize;
screen = SDL_SetVideoMode(w, h, 0, sdlflags);
if(screen == NULL)
{
cerr << "ERROR: Unable to open SDL window: " << SDL_GetError() << endl;
return false;
}
bpp = screen->format->BitsPerPixel;
if(bpp == 8)
recalculate8BitPalette();
theRedrawEntireFrameIndicator = true;
return true;
}
/**
Recalculates palette of an 8-bit (256 color) screen.
*/
void recalculate8BitPalette()
{
if(bpp != 8)
return;
// Map 2600 colors to the current screen
const uInt32* gamePalette = theConsole->mediaSource().palette();
SDL_Color colors[256];
for(uInt32 i = 0; i < 256; ++i)
{
Uint8 r, g, b;
r = (Uint8) ((gamePalette[i] & 0x00ff0000) >> 16);
g = (Uint8) ((gamePalette[i] & 0x0000ff00) >> 8);
b = (Uint8) (gamePalette[i] & 0x000000ff);
colors[i].r = r;
colors[i].g = g;
colors[i].b = b;
}
SDL_SetColors(screen, colors, 0, 256);
// Now see which colors we actually got
SDL_PixelFormat* format = screen->format;
for(uInt32 i = 0; i < 256; ++i)
{
Uint8 r, g, b;
r = format->palette->colors[i].r;
g = format->palette->colors[i].g;
b = format->palette->colors[i].b;
palette[i] = SDL_MapRGB(format, r, g, b);
}
theRedrawEntireFrameIndicator = true;
}
/**
Set up the palette for a screen of any depth.
Calls recalculate8BitPalette if necessary.
*/
void setupPalette()
{
if(bpp == 8)
{
recalculate8BitPalette();
return;
}
// Make the palette be 75% as bright if pause is selected
float shade = 1.0;
if(theSettings->pause())
shade = 0.75;
const uInt32* gamePalette = theConsole->mediaSource().palette();
for(uInt32 i = 0; i < 256; ++i)
{
Uint8 r, g, b;
r = (Uint8) (((gamePalette[i] & 0x00ff0000) >> 16) * shade);
g = (Uint8) (((gamePalette[i] & 0x0000ff00) >> 8) * shade);
b = (Uint8) ((gamePalette[i] & 0x000000ff) * shade);
switch(bpp)
{
case 15:
palette[i] = ((r >> 3) << 10) | ((g >> 3) << 5) | (b >> 3);
break;
case 16:
palette[i] = ((r >> 3) << 11) | ((g >> 2) << 5) | (b >> 3);
break;
case 24:
case 32:
palette[i] = (r << 16) | (g << 8) | b;
break;
}
}
theRedrawEntireFrameIndicator = true;
}
/**
This routine is called when the user wants to resize the window.
A '1' argument indicates that the window should increase in size, while '0'
indicates that the windows should decrease in size. A '-1' indicates that
the window should be sized according to the current properties.
Can't resize in fullscreen mode. Will only resize up to the maximum size
of the screen.
*/
void resizeWindow(int mode)
{
// reset size to that given in properties
// this is a special case of allowing a resize while in fullscreen mode
if(mode == -1)
{
theWidth = theConsole->mediaSource().width();
theHeight = theConsole->mediaSource().height();
}
else if(mode == 1) // increase size
{
if(isFullscreen)
return;
if(theWindowSize == theMaxWindowSize)
theWindowSize = 1;
else
theWindowSize++;
}
else if(mode == 0) // decrease size
{
if(isFullscreen)
return;
if(theWindowSize == 1)
theWindowSize = theMaxWindowSize;
else
theWindowSize--;
}
if(!createScreen())
return;
// A resize may mean that the window is no longer centered
isCentered = false;
if(theConsole->settings().getBool("center"))
centerWindow();
}
/**
Centers the game window onscreen. Only works in X11 for now.
*/
void centerWindow()
{
if(!x11Available)
{
cerr << "Window centering only available under X11.\n";
return;
}
if(isFullscreen || isCentered)
return;
int x, y, w, h;
info.info.x11.lock_func();
theX11Display = info.info.x11.display;
theX11Window = info.info.x11.wmwindow;
theX11Screen = DefaultScreen(theX11Display);
w = DisplayWidth(theX11Display, theX11Screen);
h = DisplayHeight(theX11Display, theX11Screen);
x = (w - screen->w)/2;
y = (h - screen->h)/2;
XMoveWindow(theX11Display, theX11Window, x, y);
info.info.x11.unlock_func();
isCentered = true;
theRedrawEntireFrameIndicator = true;
}
/**
Toggles between fullscreen and window mode. Grabmouse and hidecursor
activated when in fullscreen mode.
*/
void toggleFullscreen()
{
isFullscreen = !isFullscreen;
if(isFullscreen)
sdlflags |= SDL_FULLSCREEN;
else
sdlflags &= ~SDL_FULLSCREEN;
if(!createScreen())
return;
if(isFullscreen) // now in fullscreen mode
{
grabMouse(true);
showCursor(false);
}
else // now in windowed mode
{
grabMouse(theGrabMouseIndicator);
showCursor(!theHideCursorIndicator);
if(theConsole->settings().getBool("center"))
centerWindow();
}
}
/**
Shows or hides the cursor based on the given boolean value.
*/
void showCursor(bool show)
{
if(show)
SDL_ShowCursor(SDL_ENABLE);
else
SDL_ShowCursor(SDL_DISABLE);
}
/**
Grabs or ungrabs the mouse based on the given boolean value.
*/
void grabMouse(bool grab)
{
if(grab)
SDL_WM_GrabInput(SDL_GRAB_ON);
else
SDL_WM_GrabInput(SDL_GRAB_OFF);
}
/**
This routine should be called anytime the display needs to be updated
*/
void updateDisplay(MediaSource& mediaSource)
{
uInt8* currentFrame = mediaSource.currentFrameBuffer();
uInt8* previousFrame = mediaSource.previousFrameBuffer();
uInt16 screenMultiple = (uInt16) theWindowSize;
uInt32 width = theWidth;
uInt32 height = theHeight;
struct Rectangle
{
uInt8 color;
uInt16 x, y, width, height;
} rectangles[2][160];
// Start a new reclist on each display update
rectList->start();
// This array represents the rectangles that need displaying
// on the current scanline we're processing
Rectangle* currentRectangles = rectangles[0];
// This array represents the rectangles that are still active
// from the previous scanlines we have processed
Rectangle* activeRectangles = rectangles[1];
// Indicates the number of active rectangles
uInt16 activeCount = 0;
// This update procedure requires theWidth to be a multiple of four.
// This is validated when the properties are loaded.
for(uInt16 y = 0; y < height; ++y)
{
// Indicates the number of current rectangles
uInt16 currentCount = 0;
// Look at four pixels at a time to see if anything has changed
uInt32* current = (uInt32*)(currentFrame);
uInt32* previous = (uInt32*)(previousFrame);
for(uInt16 x = 0; x < width; x += 4, ++current, ++previous)
{
// Has something changed in this set of four pixels?
if((*current != *previous) || theRedrawEntireFrameIndicator)
{
uInt8* c = (uInt8*)current;
uInt8* p = (uInt8*)previous;
// Look at each of the bytes that make up the uInt32
for(uInt16 i = 0; i < 4; ++i, ++c, ++p)
{
// See if this pixel has changed
if((*c != *p) || theRedrawEntireFrameIndicator)
{
// Can we extend a rectangle or do we have to create a new one?
if((currentCount != 0) &&
(currentRectangles[currentCount - 1].color == *c) &&
((currentRectangles[currentCount - 1].x +
currentRectangles[currentCount - 1].width) == (x + i)))
{
currentRectangles[currentCount - 1].width += 1;
}
else
{
currentRectangles[currentCount].x = x + i;
currentRectangles[currentCount].y = y;
currentRectangles[currentCount].width = 1;
currentRectangles[currentCount].height = 1;
currentRectangles[currentCount].color = *c;
currentCount++;
}
}
}
}
}
// Merge the active and current rectangles flushing any that are of no use
uInt16 activeIndex = 0;
for(uInt16 t = 0; (t < currentCount) && (activeIndex < activeCount); ++t)
{
Rectangle& current = currentRectangles[t];
Rectangle& active = activeRectangles[activeIndex];
// Can we merge the current rectangle with an active one?
if((current.x == active.x) && (current.width == active.width) &&
(current.color == active.color))
{
current.y = active.y;
current.height = active.height + 1;
++activeIndex;
}
// Is it impossible for this active rectangle to be merged?
else if(current.x >= active.x)
{
// Flush the active rectangle
SDL_Rect temp;
temp.x = active.x * 2 * screenMultiple;
temp.y = active.y * screenMultiple;
temp.w = active.width * 2 * screenMultiple;
temp.h = active.height * screenMultiple;
rectList->add(&temp);
SDL_FillRect(screen, &temp, palette[active.color]);
++activeIndex;
}
}
// Flush any remaining active rectangles
for(uInt16 s = activeIndex; s < activeCount; ++s)
{
Rectangle& active = activeRectangles[s];
SDL_Rect temp;
temp.x = active.x * 2 * screenMultiple;
temp.y = active.y * screenMultiple;
temp.w = active.width * 2 * screenMultiple;
temp.h = active.height * screenMultiple;
rectList->add(&temp);
SDL_FillRect(screen, &temp, palette[active.color]);
}
// We can now make the current rectangles into the active rectangles
Rectangle* tmp = currentRectangles;
currentRectangles = activeRectangles;
activeRectangles = tmp;
activeCount = currentCount;
currentFrame += width;
previousFrame += width;
}
// Flush any rectangles that are still active
for(uInt16 t = 0; t < activeCount; ++t)
{
Rectangle& active = activeRectangles[t];
SDL_Rect temp;
temp.x = active.x * 2 * screenMultiple;
temp.y = active.y * screenMultiple;
temp.w = active.width * 2 * screenMultiple;
temp.h = active.height * screenMultiple;
rectList->add(&temp);
SDL_FillRect(screen, &temp, palette[active.color]);
}
// Now update all the rectangles at once
SDL_UpdateRects(screen, rectList->numRects(), rectList->rects());
// The frame doesn't need to be completely redrawn anymore
theRedrawEntireFrameIndicator = false;
}
/**
This routine should be called regularly to handle events
*/
@ -868,31 +329,31 @@ void handleEvents()
if(mod & KMOD_ALT)
{
if(key == SDLK_EQUALS)
resizeWindow(1);
theDisplay->resize(1);
else if(key == SDLK_MINUS)
resizeWindow(0);
theDisplay->resize(0);
else if(key == SDLK_RETURN)
toggleFullscreen();
theDisplay->toggleFullscreen();
#ifdef DEVELOPER_SUPPORT
else if(key == SDLK_END) // Alt-End increases XStart
{
theConsole->changeXStart(1);
resizeWindow(-1);
theDisplay->resize(-1);
}
else if(key == SDLK_HOME) // Alt-Home decreases XStart
{
theConsole->changeXStart(0);
resizeWindow(-1);
theDisplay->resize(-1);
}
else if(key == SDLK_PAGEUP) // Alt-PageUp increases YStart
{
theConsole->changeYStart(1);
resizeWindow(-1);
theDisplay->resize(-1);
}
else if(key == SDLK_PAGEDOWN) // Alt-PageDown decreases YStart
{
theConsole->changeYStart(0);
resizeWindow(-1);
theDisplay->resize(-1);
}
#endif
}
@ -901,46 +362,46 @@ void handleEvents()
if(key == SDLK_g)
{
// don't change grabmouse in fullscreen mode
if(!isFullscreen)
if(!theDisplay->fullScreen())
{
theGrabMouseIndicator = !theGrabMouseIndicator;
grabMouse(theGrabMouseIndicator);
theDisplay->grabMouse(theGrabMouseIndicator);
}
}
else if(key == SDLK_h)
{
// don't change hidecursor in fullscreen mode
if(!isFullscreen)
if(!theDisplay->fullScreen())
{
theHideCursorIndicator = !theHideCursorIndicator;
showCursor(!theHideCursorIndicator);
theDisplay->showCursor(!theHideCursorIndicator);
}
}
#ifdef DEVELOPER_SUPPORT
else if(key == SDLK_f) // Ctrl-f toggles NTSC/PAL mode
{
theConsole->toggleFormat();
setupPalette();
theDisplay->setupPalette();
}
else if(key == SDLK_END) // Ctrl-End increases Width
{
theConsole->changeWidth(1);
resizeWindow(-1);
theDisplay->resize(-1);
}
else if(key == SDLK_HOME) // Ctrl-Home decreases Width
{
theConsole->changeWidth(0);
resizeWindow(-1);
theDisplay->resize(-1);
}
else if(key == SDLK_PAGEUP) // Ctrl-PageUp increases Height
{
theConsole->changeHeight(1);
resizeWindow(-1);
theDisplay->resize(-1);
}
else if(key == SDLK_PAGEDOWN) // Ctrl-PageDown decreases Height
{
theConsole->changeHeight(0);
resizeWindow(-1);
theDisplay->resize(-1);
}
else if(key == SDLK_s) // Ctrl-s saves properties to a file
{
@ -981,20 +442,20 @@ void handleEvents()
else if(event.type == SDL_MOUSEMOTION)
{
float fudgeFactor = 1000000.0;
Int32 resistance = 0, x = 0;
Int32 width = theWidth * theWindowSize * 2;
Int32 resistance = 0, x = 0, mouseX;
Int32 width = 640;//theWidth * theWindowSize * 2; FIXME
Event::Type type = Event::LastType;
// Grabmouse and hidecursor introduce some lag into the mouse movement,
// so we need to fudge the numbers a bit
if(theGrabMouseIndicator && theHideCursorIndicator)
{
mouseX = (int)((float)mouseX + (float)event.motion.xrel
* 1.5 * (float) theWindowSize);
// mouseX = (int)((float)mouseX + (float)event.motion.xrel
// * 1.5 * (float) theWindowSize); FIXME
}
else
{
mouseX = mouseX + event.motion.xrel * theWindowSize;
// mouseX = mouseX + event.motion.xrel * theWindowSize; FIXME
}
// Check to make sure mouseX is within the game window
@ -1101,49 +562,6 @@ void handleEvents()
}
/**
Calculate the maximum window size that the current screen can hold.
Only works in X11 for now. If not running under X11, always return 3.
*/
uInt32 maxWindowSizeForScreen()
{
if(!x11Available)
return 3;
// Otherwise, lock the screen and get the width and height
info.info.x11.lock_func();
theX11Display = info.info.x11.display;
theX11Window = info.info.x11.wmwindow;
theX11Screen = DefaultScreen(theX11Display);
info.info.x11.unlock_func();
int screenWidth = DisplayWidth(info.info.x11.display,
DefaultScreen(theX11Display));
int screenHeight = DisplayHeight(info.info.x11.display,
DefaultScreen(theX11Display));
uInt32 multiplier = screenWidth / (theWidth * 2);
bool found = false;
while(!found && (multiplier > 0))
{
// Figure out the desired size of the window
int width = theWidth * multiplier * 2;
int height = theHeight * multiplier;
if((width < screenWidth) && (height < screenHeight))
found = true;
else
multiplier--;
}
if(found)
return multiplier;
else
return 1;
}
/**
Setup the properties set by first checking for a user file
"$HOME/.stella/stella.pro", then a system-wide file "/etc/stella.pro".
@ -1208,6 +626,9 @@ void cleanup()
delete theSound;
}
if(theDisplay)
delete theDisplay;
if(SDL_WasInit(SDL_INIT_EVERYTHING))
{
#ifdef HAVE_JOYSTICK
@ -1318,20 +739,22 @@ int main(int argc, char* argv[])
// Get just the filename of the file containing the ROM image
const char* filename = (!strrchr(file, '/')) ? file : strrchr(file, '/') + 1;
// Create the 2600 game console
theConsole = new Console(image, size, filename, *theSettings, propertiesSet,
theSound->getSampleRate());
// Free the image since we don't need it any longer
delete[] image;
// Setup the SDL window and joystick
if(!setupDisplay())
#ifdef DISPLAY_OPENGL
bool useGL = theSettings->getBool("opengl");
if(useGL)
theDisplay = new FrameBufferGL();
else
#endif
theDisplay = new FrameBufferSDL();
if(!theDisplay)
{
cerr << "ERROR: Couldn't set up display.\n";
cleanup();
return 0;
}
if(!setupJoystick())
{
cerr << "ERROR: Couldn't set up joysticks.\n";
@ -1339,6 +762,13 @@ int main(int argc, char* argv[])
return 0;
}
// Create the 2600 game console
theConsole = new Console(image, size, filename, *theSettings, propertiesSet,
*theDisplay, theSound->getSampleRate());
// Free the image since we don't need it any longer
delete[] image;
// These variables are common to both timing options
// and are needed to calculate the overall frames per second.
uInt32 frameTime = 0, numberOfFrames = 0;
@ -1366,14 +796,13 @@ int main(int argc, char* argv[])
handleEvents();
if(theSettings->pause())
{
updateDisplay(theConsole->mediaSource());
theDisplay->update();
SDL_Delay(10);
continue;
}
theConsole->mediaSource().update();
updateDisplay(theConsole->mediaSource());
theSound->updateSound(theConsole->mediaSource());
theDisplay->update();
//FIXME theSound->updateSound(theConsole->mediaSource());
// Now, waste time if we need to so that we are at the desired frame rate
for(;;)
@ -1411,10 +840,9 @@ int main(int argc, char* argv[])
handleEvents();
if(!theSettings->pause())
{
theConsole->mediaSource().update();
theSound->updateSound(theConsole->mediaSource());
//FIXME theSound->updateSound(theConsole->mediaSource());
}
updateDisplay(theConsole->mediaSource());
theDisplay->update();
currentTime = getTicks();
virtualTime += timePerFrame;