mirror of https://github.com/stella-emu/stella.git
Playfield.
This commit is contained in:
parent
2d76b7fb98
commit
cdafe8d0a4
|
@ -0,0 +1,142 @@
|
||||||
|
//============================================================================
|
||||||
|
//
|
||||||
|
// 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-2016 by Bradford W. Mott, Stephen Anthony
|
||||||
|
// and the Stella Team
|
||||||
|
//
|
||||||
|
// See the file "License.txt" for information on usage and redistribution of
|
||||||
|
// this file, and for a DISCLAIMER OF ALL WARRANTIES.
|
||||||
|
//
|
||||||
|
// $Id$
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
#include "Playfield.hxx"
|
||||||
|
|
||||||
|
namespace TIA6502tsCore {
|
||||||
|
|
||||||
|
Playfield::Playfield(uInt32 collisionMask)
|
||||||
|
: myCollisionMask(collisionMask)
|
||||||
|
{
|
||||||
|
reset();
|
||||||
|
}
|
||||||
|
|
||||||
|
void Playfield::reset()
|
||||||
|
{
|
||||||
|
myPattern = 0;
|
||||||
|
myReflected = false;
|
||||||
|
myRefp = false;
|
||||||
|
|
||||||
|
myPf0 = 0;
|
||||||
|
myPf1 = 0;
|
||||||
|
myPf2 = 0;
|
||||||
|
|
||||||
|
myColor = 0;
|
||||||
|
myColorP0 = 0;
|
||||||
|
myColorP1 = 0;
|
||||||
|
myColorMode = ColorMode::normal;
|
||||||
|
|
||||||
|
collision = 0;
|
||||||
|
|
||||||
|
applyColors();
|
||||||
|
}
|
||||||
|
|
||||||
|
void Playfield::pf0(uInt8 value)
|
||||||
|
{
|
||||||
|
myPattern = (myPattern & 0x000FFFF0) | ((value & 0xF0) >> 4);
|
||||||
|
}
|
||||||
|
|
||||||
|
void Playfield::pf1(uInt8 value)
|
||||||
|
{
|
||||||
|
myPattern = (myPattern & 0x000FF00F)
|
||||||
|
| ((value & 0x80) >> 3)
|
||||||
|
| ((value & 0x40) >> 1)
|
||||||
|
| ((value & 0x20) << 1)
|
||||||
|
| ((value & 0x10) << 3)
|
||||||
|
| ((value & 0x08) << 5)
|
||||||
|
| ((value & 0x04) << 7)
|
||||||
|
| ((value & 0x02) << 9)
|
||||||
|
| ((value & 0x01) << 11);
|
||||||
|
}
|
||||||
|
|
||||||
|
void Playfield::pf2(uInt8 value)
|
||||||
|
{
|
||||||
|
myPattern = (myPattern & 0x00000FFF) | ((value & 0xFF) << 12);
|
||||||
|
}
|
||||||
|
|
||||||
|
void Playfield::ctrlpf(uInt8 value)
|
||||||
|
{
|
||||||
|
myReflected = (value & 0x01) > 0;
|
||||||
|
myColorMode = (value & 0x06) == 0x02 ? ColorMode::score : ColorMode::normal;
|
||||||
|
applyColors();
|
||||||
|
}
|
||||||
|
|
||||||
|
void Playfield::setColor(uInt8 color)
|
||||||
|
{
|
||||||
|
myColor = color;
|
||||||
|
applyColors();
|
||||||
|
}
|
||||||
|
|
||||||
|
void Playfield::setColorP0(uInt8 color)
|
||||||
|
{
|
||||||
|
myColorP0 = color;
|
||||||
|
applyColors();
|
||||||
|
}
|
||||||
|
|
||||||
|
void Playfield::setColorP1(uInt8 color)
|
||||||
|
{
|
||||||
|
myColorP1 = color;
|
||||||
|
applyColors();
|
||||||
|
}
|
||||||
|
|
||||||
|
void Playfield::tick(uInt32 x)
|
||||||
|
{
|
||||||
|
myX = x;
|
||||||
|
|
||||||
|
if (myX == 80 || myX == 0) myRefp = myReflected;
|
||||||
|
|
||||||
|
if (x & 0x03) return;
|
||||||
|
|
||||||
|
uInt32 currentPixel;
|
||||||
|
|
||||||
|
if (myPattern == 0) {
|
||||||
|
currentPixel = 0;
|
||||||
|
} else if (x < 80) {
|
||||||
|
currentPixel = myPattern & (1 << (x >> 2));
|
||||||
|
} else if (myRefp) {
|
||||||
|
currentPixel = myPattern & (1 << (39 - (x >> 2)));
|
||||||
|
} else {
|
||||||
|
currentPixel = myPattern & (1 << ((x >> 2) - 20));
|
||||||
|
}
|
||||||
|
|
||||||
|
collision = currentPixel ? 0 : myCollisionMask;
|
||||||
|
}
|
||||||
|
|
||||||
|
uInt8 Playfield::getPixel(uInt8 colorIn) const
|
||||||
|
{
|
||||||
|
if (!collision) return myX < 80 ? myColorLeft : myColorRight;
|
||||||
|
|
||||||
|
return colorIn;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Playfield::applyColors()
|
||||||
|
{
|
||||||
|
switch (myColorMode) {
|
||||||
|
case ColorMode::normal:
|
||||||
|
myColorLeft = myColorRight = myColor;
|
||||||
|
break;
|
||||||
|
|
||||||
|
case ColorMode::score:
|
||||||
|
myColorLeft = myColorP0;
|
||||||
|
myColorRight = myColorP1;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace TIA6502tsCore
|
|
@ -0,0 +1,99 @@
|
||||||
|
//============================================================================
|
||||||
|
//
|
||||||
|
// 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-2016 by Bradford W. Mott, Stephen Anthony
|
||||||
|
// and the Stella Team
|
||||||
|
//
|
||||||
|
// See the file "License.txt" for information on usage and redistribution of
|
||||||
|
// this file, and for a DISCLAIMER OF ALL WARRANTIES.
|
||||||
|
//
|
||||||
|
// $Id$
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
#ifndef TIA_6502TS_CORE_PLAYFIELD
|
||||||
|
#define TIA_6502TS_CORE_PLAYFIELD
|
||||||
|
|
||||||
|
#include "bspf.hxx"
|
||||||
|
|
||||||
|
namespace TIA6502tsCore {
|
||||||
|
|
||||||
|
class Playfield {
|
||||||
|
|
||||||
|
public:
|
||||||
|
|
||||||
|
Playfield(uInt32 collisionMask);
|
||||||
|
|
||||||
|
public:
|
||||||
|
|
||||||
|
void reset();
|
||||||
|
|
||||||
|
void pf0(uInt8 value);
|
||||||
|
|
||||||
|
void pf1(uInt8 value);
|
||||||
|
|
||||||
|
void pf2(uInt8 value);
|
||||||
|
|
||||||
|
void ctrlpf(uInt8 value);
|
||||||
|
|
||||||
|
void setColor(uInt8 color);
|
||||||
|
|
||||||
|
void setColorP0(uInt8 color);
|
||||||
|
|
||||||
|
void setColorP1(uInt8 color);
|
||||||
|
|
||||||
|
void tick(uInt32 x);
|
||||||
|
|
||||||
|
uInt8 getPixel(uInt8 colorIn) const;
|
||||||
|
|
||||||
|
public:
|
||||||
|
|
||||||
|
uInt32 collision;
|
||||||
|
|
||||||
|
private:
|
||||||
|
|
||||||
|
enum ColorMode {normal, score};
|
||||||
|
|
||||||
|
private:
|
||||||
|
|
||||||
|
void applyColors();
|
||||||
|
|
||||||
|
private:
|
||||||
|
|
||||||
|
uInt8 myColorLeft;
|
||||||
|
uInt8 myColorRight;
|
||||||
|
uInt8 myColorP0;
|
||||||
|
uInt8 myColorP1;
|
||||||
|
uInt8 myColor;
|
||||||
|
ColorMode myColorMode;
|
||||||
|
|
||||||
|
uInt32 myPattern;
|
||||||
|
bool myRefp;
|
||||||
|
bool myReflected;
|
||||||
|
|
||||||
|
uInt8 myPf0;
|
||||||
|
uInt8 myPf1;
|
||||||
|
uInt8 myPf2;
|
||||||
|
|
||||||
|
uInt32 myX;
|
||||||
|
|
||||||
|
uInt32 myCollisionMask;
|
||||||
|
|
||||||
|
private:
|
||||||
|
|
||||||
|
Playfield() = delete;
|
||||||
|
Playfield(const Playfield&) = delete;
|
||||||
|
Playfield(Playfield&&) = delete;
|
||||||
|
Playfield& operator=(const Playfield&) = delete;
|
||||||
|
Playfield& operator=(Playfield&&) = delete;
|
||||||
|
};
|
||||||
|
|
||||||
|
} // namespace TIA6502tsCore
|
||||||
|
|
||||||
|
#endif // TIA_6502TS_CORE_PLAYFIELD
|
|
@ -21,13 +21,23 @@
|
||||||
#include "TIATypes.hxx"
|
#include "TIATypes.hxx"
|
||||||
#include "M6502.hxx"
|
#include "M6502.hxx"
|
||||||
|
|
||||||
|
enum CollisionMask : uInt32 {
|
||||||
|
player0 = 0b0111110000000000,
|
||||||
|
player1 = 0b0100001111000000,
|
||||||
|
missile0 = 0b0010001000111000,
|
||||||
|
missile1 = 0b0001000100100110,
|
||||||
|
ball = 0b0000100010010101,
|
||||||
|
playfield = 0b0000010001001011
|
||||||
|
};
|
||||||
|
|
||||||
namespace TIA6502tsCore {
|
namespace TIA6502tsCore {
|
||||||
|
|
||||||
TIA::TIA(Console& console, Sound& sound, Settings& settings)
|
TIA::TIA(Console& console, Sound& sound, Settings& settings)
|
||||||
: myConsole(console),
|
: myConsole(console),
|
||||||
mySound(sound),
|
mySound(sound),
|
||||||
mySettings(settings),
|
mySettings(settings),
|
||||||
myDelayQueue(10, 20)
|
myDelayQueue(10, 20),
|
||||||
|
myPlayfield(CollisionMask::playfield)
|
||||||
{
|
{
|
||||||
myFrameManager.setHandlers(
|
myFrameManager.setHandlers(
|
||||||
[this] () {onFrameStart();},
|
[this] () {onFrameStart();},
|
||||||
|
@ -56,6 +66,8 @@ void TIA::reset()
|
||||||
|
|
||||||
myLastCycle = 0;
|
myLastCycle = 0;
|
||||||
|
|
||||||
|
myPlayfield.reset();
|
||||||
|
|
||||||
mySound.reset();
|
mySound.reset();
|
||||||
myDelayQueue.reset();
|
myDelayQueue.reset();
|
||||||
myFrameManager.reset();
|
myFrameManager.reset();
|
||||||
|
@ -135,6 +147,49 @@ bool TIA::poke(uInt16 address, uInt8 value)
|
||||||
case AUDC1:
|
case AUDC1:
|
||||||
mySound.set(address, value, mySystem->cycles());
|
mySound.set(address, value, mySystem->cycles());
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case COLUP0:
|
||||||
|
myLinesSinceChange = 0;
|
||||||
|
myPlayfield.setColorP0(value & 0xFE);
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case COLUP1:
|
||||||
|
myLinesSinceChange = 0;
|
||||||
|
myPlayfield.setColorP1(value & 0xFE);
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case CTRLPF:
|
||||||
|
myLinesSinceChange = 0;
|
||||||
|
myPriority = (value & 0x04) ? Priority::inverted : Priority::normal;
|
||||||
|
myPlayfield.ctrlpf(value);
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case COLUPF:
|
||||||
|
myLinesSinceChange = 0;
|
||||||
|
myPlayfield.setColor(value & 0xFE);
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case PF0:
|
||||||
|
myLinesSinceChange = 0;
|
||||||
|
myPlayfield.pf0(value);
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case PF1:
|
||||||
|
myLinesSinceChange = 0;
|
||||||
|
myPlayfield.pf1(value);
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case PF2:
|
||||||
|
myLinesSinceChange = 0;
|
||||||
|
myPlayfield.pf2(value);
|
||||||
|
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
|
@ -354,7 +409,7 @@ void TIA::tickHframe()
|
||||||
|
|
||||||
myCollisionUpdateRequired = lineNotCached;
|
myCollisionUpdateRequired = lineNotCached;
|
||||||
|
|
||||||
// TODO: playfield tick
|
myPlayfield.tick(x);
|
||||||
|
|
||||||
// TODO: render sprites
|
// TODO: render sprites
|
||||||
|
|
||||||
|
@ -387,7 +442,11 @@ void TIA::renderPixel(uInt32 x, uInt32 y, bool lineNotCached)
|
||||||
if (lineNotCached) {
|
if (lineNotCached) {
|
||||||
uInt8 color = 0;
|
uInt8 color = 0;
|
||||||
|
|
||||||
// TODO: determine color from sprites
|
if (myPriority == Priority::normal) {
|
||||||
|
color = myPlayfield.getPixel(color);
|
||||||
|
} else {
|
||||||
|
color = myPlayfield.getPixel(color);
|
||||||
|
}
|
||||||
|
|
||||||
myCurrentFrameBuffer.get()[y * 160 + x] = myFrameManager.vblank() ? 0 : color;
|
myCurrentFrameBuffer.get()[y * 160 + x] = myFrameManager.vblank() ? 0 : color;
|
||||||
} else {
|
} else {
|
||||||
|
|
|
@ -17,8 +17,8 @@
|
||||||
// $Id$
|
// $Id$
|
||||||
//============================================================================
|
//============================================================================
|
||||||
|
|
||||||
#ifndef TIA_6502TS_CORE
|
#ifndef TIA_6502TS_CORE_TIA
|
||||||
#define TIA_6502TS_CORE
|
#define TIA_6502TS_CORE_TIA
|
||||||
|
|
||||||
#include "bspf.hxx"
|
#include "bspf.hxx"
|
||||||
#include "AbstractTIA.hxx"
|
#include "AbstractTIA.hxx"
|
||||||
|
@ -27,6 +27,7 @@
|
||||||
#include "TIATypes.hxx"
|
#include "TIATypes.hxx"
|
||||||
#include "DelayQueue.hxx"
|
#include "DelayQueue.hxx"
|
||||||
#include "FrameManager.hxx"
|
#include "FrameManager.hxx"
|
||||||
|
#include "Playfield.hxx"
|
||||||
|
|
||||||
class Console;
|
class Console;
|
||||||
|
|
||||||
|
@ -177,6 +178,8 @@ class TIA : public AbstractTIA {
|
||||||
BytePtr myCurrentFrameBuffer;
|
BytePtr myCurrentFrameBuffer;
|
||||||
BytePtr myPreviousFrameBuffer;
|
BytePtr myPreviousFrameBuffer;
|
||||||
|
|
||||||
|
Playfield myPlayfield;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
|
||||||
TIA() = delete;
|
TIA() = delete;
|
||||||
|
@ -189,4 +192,4 @@ class TIA : public AbstractTIA {
|
||||||
|
|
||||||
} // namespace TIA6502tsCore
|
} // namespace TIA6502tsCore
|
||||||
|
|
||||||
#endif // TIA_6502TS_CORE
|
#endif // TIA_6502TS_CORE_TIA
|
|
@ -4,7 +4,8 @@ MODULE_OBJS := \
|
||||||
src/emucore/tia/core_6502ts/TIA.o \
|
src/emucore/tia/core_6502ts/TIA.o \
|
||||||
src/emucore/tia/core_6502ts/DelayQueueMember.o \
|
src/emucore/tia/core_6502ts/DelayQueueMember.o \
|
||||||
src/emucore/tia/core_6502ts/DelayQueue.o \
|
src/emucore/tia/core_6502ts/DelayQueue.o \
|
||||||
src/emucore/tia/core_6502ts/FrameManager.o
|
src/emucore/tia/core_6502ts/FrameManager.o \
|
||||||
|
src/emucore/tia/core_6502ts/Playfield.o
|
||||||
|
|
||||||
|
|
||||||
MODULE_DIRS += \
|
MODULE_DIRS += \
|
||||||
|
|
Loading…
Reference in New Issue