Merge remote-tracking branch 'origin/late-hmove-experiments'

This commit is contained in:
Christian Speckner 2024-08-31 18:49:51 +02:00
commit 1dd364bc8a
15 changed files with 172 additions and 25 deletions

Binary file not shown.

Before

Width:  |  Height:  |  Size: 3.7 KiB

After

Width:  |  Height:  |  Size: 4.3 KiB

View File

@ -3694,7 +3694,7 @@
<td>When enabled, each external access (AtariVox/SaveKey EEPROM, PlusROM, Supercharger...) <td>When enabled, each external access (AtariVox/SaveKey EEPROM, PlusROM, Supercharger...)
is signalled by a message.</td> is signalled by a message.</td>
</tr><tr> </tr><tr>
<td><pre>-dev.tia.type &lt;standard|koolaidman|</br> cosmicark|pesco|quickstep|matchie|</br> indy500|heman|custom&gt;</pre></td> <td><pre>-dev.tia.type &lt;standard|koolaidman|</br> cosmicark|pesco|quickstep|matchie|</br> indy500|heman|flashmenu|custom&gt;</pre></td>
<td>Set emulated TIA type. Only with 'custom' the following TIA options become relevant.</td> <td>Set emulated TIA type. Only with 'custom' the following TIA options become relevant.</td>
</tr><tr> </tr><tr>
<td><pre>-dev.tia.plinvphase &lt;1|0&gt;</pre></td> <td><pre>-dev.tia.plinvphase &lt;1|0&gt;</pre></td>
@ -3705,6 +3705,15 @@
</tr><tr> </tr><tr>
<td><pre>-dev.tia.blinvphase &lt;1|0&gt;</pre></td> <td><pre>-dev.tia.blinvphase &lt;1|0&gt;</pre></td>
<td>Enable/disable inverted HMOVE clock phase for ball.</td> <td>Enable/disable inverted HMOVE clock phase for ball.</td>
</tr><tr>
<td><pre>-dev.tia.pllatehmove &lt;1|0&gt;</pre></td>
<td>Enable/disable short late HMOVE for players (Flashcart menu shifted right).</td>
</tr><tr>
<td><pre>-dev.tia.mslatehmove &lt;1|0&gt;</pre></td>
<td>Enable/disable short late HMOVE for missiles.</td>
</tr><tr>
<td><pre>-dev.tia.bllatehmove &lt;1|0&gt;</pre></td>
<td>Enable/disable short late HMOVE for ball.</td>
</tr><tr> </tr><tr>
<td><pre>-dev.tia.delaypfbits &lt;1|0&gt;</pre></td> <td><pre>-dev.tia.delaypfbits &lt;1|0&gt;</pre></td>
<td>Enable/disable playfield bits delayed by one color clock (stray playfield pixels in Pesco).</td> <td>Enable/disable playfield bits delayed by one color clock (stray playfield pixels in Pesco).</td>
@ -4615,6 +4624,9 @@
<tr><td>Inverted HMOVE clock...</td><td>Emulates the Kool-Aid Man <tr><td>Inverted HMOVE clock...</td><td>Emulates the Kool-Aid Man
collision and Cosmic Ark stars glitches for the given objects.</td> collision and Cosmic Ark stars glitches for the given objects.</td>
<td>-dev.tia.plinvphase</br>-dev.tia.msinvphase</br>-dev.tia.blinvphase</td></tr> <td>-dev.tia.plinvphase</br>-dev.tia.msinvphase</br>-dev.tia.blinvphase</td></tr>
<tr><td>Short late HMOVE</td><td>Emulates one pixel too short late HMOVEs for the given objects.
This causes e.g. shifted flashcart menues.</td>
<td>-dev.tia.pllatehmove</br>-dev.tia.mslatehmove</br>-dev.tia.bllatehmove</td></tr>
<tr><td>Delayed Playfield</td><td>Emulates playfield changes moved <tr><td>Delayed Playfield</td><td>Emulates playfield changes moved
by one color clock. This e.g. causes glitches in Pesco (stray playfield by one color clock. This e.g. causes glitches in Pesco (stray playfield
pixel), Quick Step! (colored step borders) and Matchie (vertical line at pixel 79).</td> pixel), Quick Step! (colored step borders) and Matchie (vertical line at pixel 79).</td>

View File

@ -70,6 +70,9 @@ void DevSettingsHandler::loadSettings(SettingsSet set)
myPlInvPhase[set] = devSettings ? settings.getBool("dev.tia.plinvphase") : false; myPlInvPhase[set] = devSettings ? settings.getBool("dev.tia.plinvphase") : false;
myMsInvPhase[set] = devSettings ? settings.getBool("dev.tia.msinvphase") : false; myMsInvPhase[set] = devSettings ? settings.getBool("dev.tia.msinvphase") : false;
myBlInvPhase[set] = devSettings ? settings.getBool("dev.tia.blinvphase") : false; myBlInvPhase[set] = devSettings ? settings.getBool("dev.tia.blinvphase") : false;
myPlLateHMove[set] = devSettings ? settings.getBool("dev.tia.pllatehmove") : false;
myMsLateHMove[set] = devSettings ? settings.getBool("dev.tia.mslatehmove") : false;
myBlLateHMove[set] = devSettings ? settings.getBool("dev.tia.bllatehmove") : false;
myPFBits[set] = devSettings ? settings.getBool("dev.tia.delaypfbits") : false; myPFBits[set] = devSettings ? settings.getBool("dev.tia.delaypfbits") : false;
myPFColor[set] = devSettings ? settings.getBool("dev.tia.delaypfcolor") : false; myPFColor[set] = devSettings ? settings.getBool("dev.tia.delaypfcolor") : false;
myPFScore[set] = devSettings ? settings.getBool("dev.tia.pfscoreglitch") : false; myPFScore[set] = devSettings ? settings.getBool("dev.tia.pfscoreglitch") : false;
@ -141,6 +144,9 @@ void DevSettingsHandler::saveSettings(SettingsSet set)
settings.setValue("dev.tia.plinvphase", myPlInvPhase[set]); settings.setValue("dev.tia.plinvphase", myPlInvPhase[set]);
settings.setValue("dev.tia.msinvphase", myMsInvPhase[set]); settings.setValue("dev.tia.msinvphase", myMsInvPhase[set]);
settings.setValue("dev.tia.blinvphase", myBlInvPhase[set]); settings.setValue("dev.tia.blinvphase", myBlInvPhase[set]);
settings.setValue("dev.tia.pllatehmove", myPlLateHMove[set]);
settings.setValue("dev.tia.mslatehmove", myMsLateHMove[set]);
settings.setValue("dev.tia.bllatehmove", myBlLateHMove[set]);
settings.setValue("dev.tia.delaypfbits", myPFBits[set]); settings.setValue("dev.tia.delaypfbits", myPFBits[set]);
settings.setValue("dev.tia.delaypfcolor", myPFColor[set]); settings.setValue("dev.tia.delaypfcolor", myPFColor[set]);
settings.setValue("dev.tia.pfscoreglitch", myPFScore[set]); settings.setValue("dev.tia.pfscoreglitch", myPFScore[set]);
@ -197,6 +203,9 @@ void DevSettingsHandler::applySettings(SettingsSet set)
myOSystem.console().tia().setPlInvertedPhaseClock(myPlInvPhase[set]); myOSystem.console().tia().setPlInvertedPhaseClock(myPlInvPhase[set]);
myOSystem.console().tia().setMsInvertedPhaseClock(myMsInvPhase[set]); myOSystem.console().tia().setMsInvertedPhaseClock(myMsInvPhase[set]);
myOSystem.console().tia().setBlInvertedPhaseClock(myBlInvPhase[set]); myOSystem.console().tia().setBlInvertedPhaseClock(myBlInvPhase[set]);
myOSystem.console().tia().setPlShortLateHMove(myPlLateHMove[set]);
myOSystem.console().tia().setMsShortLateHMove(myMsLateHMove[set]);
myOSystem.console().tia().setBlShortLateHMove(myBlLateHMove[set]);
myOSystem.console().tia().setPFBitsDelay(myPFBits[set]); myOSystem.console().tia().setPFBitsDelay(myPFBits[set]);
myOSystem.console().tia().setPFColorDelay(myPFColor[set]); myOSystem.console().tia().setPFColorDelay(myPFColor[set]);
myOSystem.console().tia().setPFScoreGlitch(myPFScore[set]); myOSystem.console().tia().setPFScoreGlitch(myPFScore[set]);

View File

@ -69,16 +69,19 @@ class DevSettingsHandler
std::array<bool, numSets> myThumbException{}; std::array<bool, numSets> myThumbException{};
std::array<int, numSets> myArmSpeed{}; std::array<int, numSets> myArmSpeed{};
// TIA sets // TIA sets
std::array<string, numSets> myTIAType{}; std::array<string, numSets> myTIAType;
std::array<bool, numSets> myPlInvPhase{}; std::array<bool, numSets> myPlInvPhase;
std::array<bool, numSets> myMsInvPhase{}; std::array<bool, numSets> myMsInvPhase;
std::array<bool, numSets> myBlInvPhase{}; std::array<bool, numSets> myBlInvPhase;
std::array<bool, numSets> myPFBits{}; std::array<bool, numSets> myPlLateHMove;
std::array<bool, numSets> myPFColor{}; std::array<bool, numSets> myMsLateHMove;
std::array<bool, numSets> myPFScore{}; std::array<bool, numSets> myBlLateHMove;
std::array<bool, numSets> myBKColor{}; std::array<bool, numSets> myPFBits;
std::array<bool, numSets> myPlSwap{}; std::array<bool, numSets> myPFColor;
std::array<bool, numSets> myBlSwap{}; std::array<bool, numSets> myPFScore;
std::array<bool, numSets> myBKColor;
std::array<bool, numSets> myPlSwap;
std::array<bool, numSets> myBlSwap;
// States sets // States sets
std::array<bool, numSets> myTimeMachine{}; std::array<bool, numSets> myTimeMachine{};
std::array<int, numSets> myStateSize{}; std::array<int, numSets> myStateSize{};

View File

@ -297,6 +297,9 @@ Settings::Settings()
setPermanent("dev.tia.plinvphase", "true"); setPermanent("dev.tia.plinvphase", "true");
setPermanent("dev.tia.msinvphase", "true"); setPermanent("dev.tia.msinvphase", "true");
setPermanent("dev.tia.blinvphase", "true"); setPermanent("dev.tia.blinvphase", "true");
setPermanent("dev.tia.pllatehmove", "true");
setPermanent("dev.tia.mslatehmove", "true");
setPermanent("dev.tia.bllatehmove", "true");
setPermanent("dev.tia.delaypfbits", "true"); setPermanent("dev.tia.delaypfbits", "true");
setPermanent("dev.tia.delaypfcolor", "true"); setPermanent("dev.tia.delaypfcolor", "true");
setPermanent("dev.tia.pfscoreglitch", "true"); setPermanent("dev.tia.pfscoreglitch", "true");
@ -811,11 +814,16 @@ void Settings::usage()
<< " koolaidman|\n" << " koolaidman|\n"
<< " cosmicark|pesco|\n" << " cosmicark|pesco|\n"
<< " quickstep|matchie|\n" << " quickstep|matchie|\n"
<< " indy500|heman|>\n" << " indy500|heman|\n"
<< " flashmenu>\n"
<< " -dev.tia.plinvphase <1|0> Enable inverted HMOVE clock phase for players\n" << " -dev.tia.plinvphase <1|0> Enable inverted HMOVE clock phase for players\n"
<< " -dev.tia.msinvphase <1|0> Enable inverted HMOVE clock phase for\n" << " -dev.tia.msinvphase <1|0> Enable inverted HMOVE clock phase for\n"
<< " missiles\n" << " missiles\n"
<< " -dev.tia.blinvphase <1|0> Enable inverted HMOVE clock phase for ball\n" << " -dev.tia.blinvphase <1|0> Enable inverted HMOVE clock phase for ball\n"
<< " -dev.tia.pllatehmove <1|0> Enable short late HMOVE for players\n"
<< " -dev.tia.mslatehmove <1|0> Enable short late HMOVE for\n"
<< " missiles\n"
<< " -dev.tia.bllatehmove <1|0> Enable short late HMOVE for ball\n"
<< " -dev.tia.delaypfbits <1|0> Enable extra delay cycle for PF bits access\n" << " -dev.tia.delaypfbits <1|0> Enable extra delay cycle for PF bits access\n"
<< " -dev.tia.delaypfcolor <1|0> Enable extra delay cycle for PF color\n" << " -dev.tia.delaypfcolor <1|0> Enable extra delay cycle for PF color\n"
<< " -dev.tia.pfscoreglitch <1|0> Enable PF score mode color glitch\n" << " -dev.tia.pfscoreglitch <1|0> Enable PF score mode color glitch\n"

View File

@ -45,6 +45,7 @@ void Ball::reset()
myRenderCounter = 0; myRenderCounter = 0;
myInvertedPhaseClock = false; myInvertedPhaseClock = false;
myUseInvertedPhaseClock = false; myUseInvertedPhaseClock = false;
myUseShortLateHMove = false;
} }
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
@ -153,6 +154,12 @@ void Ball::setInvertedPhaseClock(bool enable)
myUseInvertedPhaseClock = enable; myUseInvertedPhaseClock = enable;
} }
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void Ball::setShortLateHMove(bool enable)
{
myUseShortLateHMove = enable;
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void Ball::startMovement() void Ball::startMovement()
{ {

View File

@ -108,6 +108,7 @@ class Ball : public Serializable
Aid Man bug on some Jr. models. Aid Man bug on some Jr. models.
*/ */
void setInvertedPhaseClock(bool enable); void setInvertedPhaseClock(bool enable);
void setShortLateHMove(bool enable);
/** /**
Start movement --- this is triggered by strobing HMOVE. Start movement --- this is triggered by strobing HMOVE.
@ -167,7 +168,7 @@ class Ball : public Serializable
/** /**
Process a single movement tick. Inline for performance (implementation below). Process a single movement tick. Inline for performance (implementation below).
*/ */
FORCE_INLINE void movementTick(uInt32 clock, bool hblank); FORCE_INLINE void movementTick(uInt32 clock, uInt32 hclock, bool hblank);
/** /**
Tick one color clock. Inline for performance (implementation below). Tick one color clock. Inline for performance (implementation below).
@ -323,6 +324,8 @@ class Ball : public Serializable
*/ */
bool myUseInvertedPhaseClock{false}; bool myUseInvertedPhaseClock{false};
bool myUseShortLateHMove{false};
/** /**
TIA instance. Required for flushing the line cache and requesting collision updates. TIA instance. Required for flushing the line cache and requesting collision updates.
*/ */
@ -341,7 +344,7 @@ class Ball : public Serializable
// ############################################################################ // ############################################################################
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void Ball::movementTick(uInt32 clock, bool hblank) void Ball::movementTick(uInt32 clock, uInt32 hclock, bool hblank)
{ {
myLastMovementTick = myCounter; myLastMovementTick = myCounter;
@ -350,7 +353,7 @@ void Ball::movementTick(uInt32 clock, bool hblank)
// Stop movement once the number of clocks according to HMBL is reached // Stop movement once the number of clocks according to HMBL is reached
if (clock == myHmmClocks) if (clock == myHmmClocks)
isMoving = false; isMoving = false;
else else if (!myUseShortLateHMove || hclock != 0)
{ {
// Process the tick if we are in hblank. Otherwise, the tick is either masked // Process the tick if we are in hblank. Otherwise, the tick is either masked
// by an ordinary tick or merges two consecutive ticks into a single tick (inverted // by an ordinary tick or merges two consecutive ticks into a single tick (inverted

View File

@ -46,6 +46,7 @@ void Missile::reset()
collision = myCollisionMaskDisabled; collision = myCollisionMaskDisabled;
myInvertedPhaseClock = false; myInvertedPhaseClock = false;
myUseInvertedPhaseClock = false; myUseInvertedPhaseClock = false;
myUseShortLateHMove = false;
} }
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
@ -199,6 +200,12 @@ void Missile::setInvertedPhaseClock(bool enable)
myUseInvertedPhaseClock = enable; myUseInvertedPhaseClock = enable;
} }
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void Missile::setShortLateHMove(bool enable)
{
myUseShortLateHMove = enable;
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void Missile::updateEnabled() void Missile::updateEnabled()
{ {

View File

@ -60,6 +60,7 @@ class Missile : public Serializable
void applyColorLoss(); void applyColorLoss();
void setInvertedPhaseClock(bool enable); void setInvertedPhaseClock(bool enable);
void setShortLateHMove(bool enable);
void toggleCollisions(bool enabled); void toggleCollisions(bool enabled);
@ -127,6 +128,7 @@ class Missile : public Serializable
bool myInvertedPhaseClock{false}; bool myInvertedPhaseClock{false};
bool myUseInvertedPhaseClock{false}; bool myUseInvertedPhaseClock{false};
bool myUseShortLateHMove{false};
TIA *myTIA{nullptr}; TIA *myTIA{nullptr};
@ -149,7 +151,7 @@ void Missile::movementTick(uInt8 clock, uInt8 hclock, bool hblank)
// Stop movement once the number of clocks according to HMMx is reached // Stop movement once the number of clocks according to HMMx is reached
if(clock == myHmmClocks) if(clock == myHmmClocks)
isMoving = false; isMoving = false;
else else if (!myUseShortLateHMove || hclock != 0)
{ {
// Process the tick if we are in hblank. Otherwise, the tick is either masked // Process the tick if we are in hblank. Otherwise, the tick is either masked
// by an ordinary tick or merges two consecutive ticks into a single tick (inverted // by an ordinary tick or merges two consecutive ticks into a single tick (inverted

View File

@ -47,6 +47,7 @@ void Player::reset()
myDividerChangeCounter = -1; myDividerChangeCounter = -1;
myInvertedPhaseClock = false; myInvertedPhaseClock = false;
myUseInvertedPhaseClock = false; myUseInvertedPhaseClock = false;
myUseShortLateHMove = false;
myPattern = 0; myPattern = 0;
setDivider(1); setDivider(1);
@ -260,6 +261,12 @@ void Player::setInvertedPhaseClock(bool enable)
myUseInvertedPhaseClock = enable; myUseInvertedPhaseClock = enable;
} }
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void Player::setShortLateHMove(bool enable)
{
myUseShortLateHMove = enable;
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void Player::startMovement() void Player::startMovement()
{ {

View File

@ -60,6 +60,7 @@ class Player : public Serializable
void applyColorLoss(); void applyColorLoss();
void setInvertedPhaseClock(bool enable); void setInvertedPhaseClock(bool enable);
void setShortLateHMove(bool enable);
void startMovement(); void startMovement();
@ -88,7 +89,7 @@ class Player : public Serializable
bool save(Serializer& out) const override; bool save(Serializer& out) const override;
bool load(Serializer& in) override; bool load(Serializer& in) override;
FORCE_INLINE void movementTick(uInt32 clock, bool hblank); FORCE_INLINE void movementTick(uInt32 clock, uInt32 hclock, bool hblank);
FORCE_INLINE void tick(); FORCE_INLINE void tick();
@ -143,6 +144,7 @@ class Player : public Serializable
bool myIsDelaying{false}; bool myIsDelaying{false};
bool myInvertedPhaseClock{false}; bool myInvertedPhaseClock{false};
bool myUseInvertedPhaseClock{false}; bool myUseInvertedPhaseClock{false};
bool myUseShortLateHMove{false};
TIA* myTIA{nullptr}; TIA* myTIA{nullptr};
@ -158,14 +160,14 @@ class Player : public Serializable
// ############################################################################ // ############################################################################
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void Player::movementTick(uInt32 clock, bool hblank) void Player::movementTick(uInt32 clock, uInt32 hclock, bool hblank)
{ {
if(isMoving) if(isMoving)
{ {
// Stop movement once the number of clocks according to HMPx is reached // Stop movement once the number of clocks according to HMPx is reached
if (clock == myHmmClocks) if (clock == myHmmClocks)
isMoving = false; isMoving = false;
else else if (!myUseShortLateHMove || hclock != 0)
{ {
// Process the tick if we are in hblank. Otherwise, the tick is either masked // Process the tick if we are in hblank. Otherwise, the tick is either masked
// by an ordinary tick or merges two consecutive ticks into a single tick (inverted // by an ordinary tick or merges two consecutive ticks into a single tick (inverted

View File

@ -978,6 +978,11 @@ void TIA::applyDeveloperSettings()
? mySettings.getBool("dev.tia.msinvphase") ? mySettings.getBool("dev.tia.msinvphase")
: BSPF::equalsIgnoreCase("cosmicark", mySettings.getString("dev.tia.type"))); : BSPF::equalsIgnoreCase("cosmicark", mySettings.getString("dev.tia.type")));
setBlInvertedPhaseClock(custom ? mySettings.getBool("dev.tia.blinvphase") : false); setBlInvertedPhaseClock(custom ? mySettings.getBool("dev.tia.blinvphase") : false);
setPlShortLateHMove(custom
? mySettings.getBool("dev.tia.pllatehmove")
: BSPF::equalsIgnoreCase("flashmenu", mySettings.getString("dev.tia.type")));
setMsShortLateHMove(custom ? mySettings.getBool("dev.tia.mslatehmove") : false);
setBlShortLateHMove(custom ? mySettings.getBool("dev.tia.bllatehmove") : false);
setPFBitsDelay(custom setPFBitsDelay(custom
? mySettings.getBool("dev.tia.delaypfbits") ? mySettings.getBool("dev.tia.delaypfbits")
: BSPF::equalsIgnoreCase("pesco", mySettings.getString("dev.tia.type"))); : BSPF::equalsIgnoreCase("pesco", mySettings.getString("dev.tia.type")));
@ -1558,9 +1563,9 @@ FORCE_INLINE void TIA::tickMovement()
myMissile0.movementTick(movementCounter, myHctr, hblank); myMissile0.movementTick(movementCounter, myHctr, hblank);
myMissile1.movementTick(movementCounter, myHctr, hblank); myMissile1.movementTick(movementCounter, myHctr, hblank);
myPlayer0.movementTick(movementCounter, hblank); myPlayer0.movementTick(movementCounter, myHctr, hblank);
myPlayer1.movementTick(movementCounter, hblank); myPlayer1.movementTick(movementCounter, myHctr, hblank);
myBall.movementTick(movementCounter, hblank); myBall.movementTick(movementCounter, myHctr, hblank);
myMovementInProgress = myMovementInProgress =
myMissile0.isMoving || myMissile0.isMoving ||
@ -1900,6 +1905,27 @@ void TIA::setBlInvertedPhaseClock(bool enable)
myBall.setInvertedPhaseClock(enable); myBall.setInvertedPhaseClock(enable);
} }
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void TIA::setPlShortLateHMove(bool enable)
{
myPlayer0.setShortLateHMove(enable);
myPlayer1.setShortLateHMove(enable);
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void TIA::setMsShortLateHMove(bool enable)
{
myMissile0.setShortLateHMove(enable);
myMissile1.setShortLateHMove(enable);
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void TIA::setBlShortLateHMove(bool enable)
{
myBall.setShortLateHMove(enable);
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void TIA::delayedWrite(uInt8 address, uInt8 value) void TIA::delayedWrite(uInt8 address, uInt8 value)
{ {

View File

@ -523,6 +523,27 @@ class TIA : public Device
*/ */
void setBlInvertedPhaseClock(bool enable); void setBlInvertedPhaseClock(bool enable);
/**
Enables/disables short late HMOVE for players.
@param enable Whether to enable short late HMOVE for players
*/
void setPlShortLateHMove(bool enable);
/**
Enables/disables short late HMOVE for missiles.
@param enable Whether to enable short late HMOVE for missiles
*/
void setMsShortLateHMove(bool enable);
/**
Enables/disables short late HMOVE for ball.
@param enable Whether to enable short late HMOVE for ball
*/
void setBlShortLateHMove(bool enable);
/** /**
This method should be called to update the TIA with a new scanline. This method should be called to update the TIA with a new scanline.
*/ */

View File

@ -229,8 +229,8 @@ void DeveloperDialog::addEmulationTab(const GUI::Font& font)
myArmSpeedWidget = new SliderWidget(myTab, font, HBORDER + INDENT * 1, ypos - 1, myArmSpeedWidget = new SliderWidget(myTab, font, HBORDER + INDENT * 1, ypos - 1,
fontWidth * 10, lineHeight, "Limit ARM speed (*) ", fontWidth * 10, lineHeight, "Limit ARM speed (*) ",
0, kArmSpeedChanged, fontWidth * 9, " MIPS"); 0, kArmSpeedChanged, fontWidth * 9, " MIPS");
myArmSpeedWidget->setMinValue(CartridgeELF::MIPS_MIN); myArmSpeedWidget->setMinValue(CartridgeELF::MIPS_MIN);
myArmSpeedWidget->setMaxValue(CartridgeELF::MIPS_MAX); myArmSpeedWidget->setMaxValue(CartridgeELF::MIPS_MAX);
myArmSpeedWidget->setTickmarkIntervals((CartridgeELF::MIPS_MAX - CartridgeELF::MIPS_MIN) / 50); myArmSpeedWidget->setTickmarkIntervals((CartridgeELF::MIPS_MAX - CartridgeELF::MIPS_MIN) / 50);
myArmSpeedWidget->setStepValue(2); myArmSpeedWidget->setStepValue(2);
myArmSpeedWidget->setToolTip("Limit emulation speed to simulate ARM CPU used for ELF."); myArmSpeedWidget->setToolTip("Limit emulation speed to simulate ARM CPU used for ELF.");
@ -238,7 +238,7 @@ void DeveloperDialog::addEmulationTab(const GUI::Font& font)
ypos = myTab->getHeight() - fontHeight - infofont.getFontHeight() - VGAP - VBORDER; ypos = myTab->getHeight() - fontHeight - infofont.getFontHeight() - VGAP - VBORDER;
lwidth = infofont.getStringWidth("(*) Change requires a reload for ELF ROMs"); lwidth = infofont.getStringWidth("(*) Change requires a reload for ELF ROMs");
new StaticTextWidget(myTab, infofont, HBORDER, ypos, lwidth, infofont.getFontHeight(), new StaticTextWidget(myTab, infofont, HBORDER, ypos, lwidth, infofont.getFontHeight(),
"(*) Change requires a reload for ELF ROMs"); "(*) Change requires a reload for ELF ROMs");
// Add items for tab 0 // Add items for tab 0
@ -286,6 +286,7 @@ void DeveloperDialog::addTiaTab(const GUI::Font& font)
VarList::push_back(items, "Glitched Matchie line", "matchie"); VarList::push_back(items, "Glitched Matchie line", "matchie");
VarList::push_back(items, "Glitched Indy 500 menu", "indy500"); VarList::push_back(items, "Glitched Indy 500 menu", "indy500");
VarList::push_back(items, "Glitched He-Man title", "heman"); VarList::push_back(items, "Glitched He-Man title", "heman");
VarList::push_back(items, "Shifted flashcart menu", "flashmenu");
VarList::push_back(items, "Custom", "custom"); VarList::push_back(items, "Custom", "custom");
myTIATypeWidget = new PopUpWidget(myTab, font, HBORDER + INDENT, ypos - 1, myTIATypeWidget = new PopUpWidget(myTab, font, HBORDER + INDENT, ypos - 1,
pwidth, lineHeight, items, "Chip type ", 0, kTIAType); pwidth, lineHeight, items, "Chip type ", 0, kTIAType);
@ -314,6 +315,24 @@ void DeveloperDialog::addTiaTab(const GUI::Font& font)
wid.push_back(myBlInvPhaseWidget); wid.push_back(myBlInvPhaseWidget);
ypos += lineHeight + VGAP * 1; ypos += lineHeight + VGAP * 1;
myLateHMoveLabel = new StaticTextWidget(myTab, font, HBORDER + INDENT * 2, ypos + 1,
"Short late HMOVE for");
myLateHMoveLabel->setToolTip("Objects react different to late HMOVEs");
wid.push_back(myLateHMoveLabel);
ypos += lineHeight + VGAP * 1;
myPlLateHMoveWidget = new CheckboxWidget(myTab, font, HBORDER + INDENT * 3, ypos + 1, "Players");
wid.push_back(myPlLateHMoveWidget);
myMsLateHMoveWidget = new CheckboxWidget(myTab, font, myPlLateHMoveWidget->getRight() + fontWidth() * 2.5,
ypos + 1, "Missiles");
wid.push_back(myMsLateHMoveWidget);
myBlLateHMoveWidget = new CheckboxWidget(myTab, font, myMsLateHMoveWidget->getRight() + fontWidth() * 2.5,
ypos + 1, "Ball");
wid.push_back(myBlLateHMoveWidget);
ypos += lineHeight + VGAP * 1;
myPlayfieldLabel = new StaticTextWidget(myTab, font, HBORDER + INDENT * 2, ypos + 1, myPlayfieldLabel = new StaticTextWidget(myTab, font, HBORDER + INDENT * 2, ypos + 1,
"Delayed playfield"); "Delayed playfield");
myPlayfieldLabel->setToolTip("Playfield reacts one color clock slower to updates."); myPlayfieldLabel->setToolTip("Playfield reacts one color clock slower to updates.");
@ -758,6 +777,9 @@ void DeveloperDialog::getWidgetStates(SettingsSet set)
myPlInvPhase[set] = myPlInvPhaseWidget->getState(); myPlInvPhase[set] = myPlInvPhaseWidget->getState();
myMsInvPhase[set] = myMsInvPhaseWidget->getState(); myMsInvPhase[set] = myMsInvPhaseWidget->getState();
myBlInvPhase[set] = myBlInvPhaseWidget->getState(); myBlInvPhase[set] = myBlInvPhaseWidget->getState();
myPlLateHMove[set] = myPlLateHMoveWidget->getState();
myMsLateHMove[set] = myMsLateHMoveWidget->getState();
myBlLateHMove[set] = myBlLateHMoveWidget->getState();
myPFBits[set] = myPFBitsWidget->getState(); myPFBits[set] = myPFBitsWidget->getState();
myPFColor[set] = myPFColorWidget->getState(); myPFColor[set] = myPFColorWidget->getState();
myPFScore[set] = myPFScoreWidget->getState(); myPFScore[set] = myPFScoreWidget->getState();
@ -1183,6 +1205,10 @@ void DeveloperDialog::handleTia()
myPlInvPhaseWidget->setEnabled(enable); myPlInvPhaseWidget->setEnabled(enable);
myMsInvPhaseWidget->setEnabled(enable); myMsInvPhaseWidget->setEnabled(enable);
myBlInvPhaseWidget->setEnabled(enable); myBlInvPhaseWidget->setEnabled(enable);
myLateHMoveLabel->setEnabled(enable);
myPlLateHMoveWidget->setEnabled(enable);
myMsLateHMoveWidget->setEnabled(enable);
myBlLateHMoveWidget->setEnabled(enable);
myPlayfieldLabel->setEnabled(enable); myPlayfieldLabel->setEnabled(enable);
myBackgroundLabel->setEnabled(enable); myBackgroundLabel->setEnabled(enable);
myPFBitsWidget->setEnabled(enable); myPFBitsWidget->setEnabled(enable);
@ -1200,6 +1226,9 @@ void DeveloperDialog::handleTia()
myPlInvPhaseWidget->setState(myPlInvPhase[set]); myPlInvPhaseWidget->setState(myPlInvPhase[set]);
myMsInvPhaseWidget->setState(myMsInvPhase[set]); myMsInvPhaseWidget->setState(myMsInvPhase[set]);
myBlInvPhaseWidget->setState(myBlInvPhase[set]); myBlInvPhaseWidget->setState(myBlInvPhase[set]);
myPlLateHMoveWidget->setState(myPlLateHMove[set]);
myMsLateHMoveWidget->setState(myMsLateHMove[set]);
myBlLateHMoveWidget->setState(myBlLateHMove[set]);
myPFBitsWidget->setState(myPFBits[set]); myPFBitsWidget->setState(myPFBits[set]);
myPFColorWidget->setState(myPFColor[set]); myPFColorWidget->setState(myPFColor[set]);
myPFScoreWidget->setState(myPFScore[set]); myPFScoreWidget->setState(myPFScore[set]);
@ -1212,6 +1241,9 @@ void DeveloperDialog::handleTia()
myPlInvPhaseWidget->setState(BSPF::equalsIgnoreCase("koolaidman", myTIATypeWidget->getSelectedTag().toString())); myPlInvPhaseWidget->setState(BSPF::equalsIgnoreCase("koolaidman", myTIATypeWidget->getSelectedTag().toString()));
myMsInvPhaseWidget->setState(BSPF::equalsIgnoreCase("cosmicark", myTIATypeWidget->getSelectedTag().toString())); myMsInvPhaseWidget->setState(BSPF::equalsIgnoreCase("cosmicark", myTIATypeWidget->getSelectedTag().toString()));
myBlInvPhaseWidget->setState(false); myBlInvPhaseWidget->setState(false);
myPlLateHMoveWidget->setState(BSPF::equalsIgnoreCase("flashmenu", myTIATypeWidget->getSelectedTag().toString()));
myMsLateHMoveWidget->setState(false);
myBlLateHMoveWidget->setState(false);
myPFBitsWidget->setState(BSPF::equalsIgnoreCase("pesco", myTIATypeWidget->getSelectedTag().toString())); myPFBitsWidget->setState(BSPF::equalsIgnoreCase("pesco", myTIATypeWidget->getSelectedTag().toString()));
myPFColorWidget->setState(BSPF::equalsIgnoreCase("quickstep", myTIATypeWidget->getSelectedTag().toString())); myPFColorWidget->setState(BSPF::equalsIgnoreCase("quickstep", myTIATypeWidget->getSelectedTag().toString()));
myPFScoreWidget->setState(BSPF::equalsIgnoreCase("matchie", myTIATypeWidget->getSelectedTag().toString())); myPFScoreWidget->setState(BSPF::equalsIgnoreCase("matchie", myTIATypeWidget->getSelectedTag().toString()));

View File

@ -108,14 +108,22 @@ class DeveloperDialog : public Dialog, DevSettingsHandler
// TIA widgets // TIA widgets
RadioButtonGroup* mySettingsGroupTia{nullptr}; RadioButtonGroup* mySettingsGroupTia{nullptr};
PopUpWidget* myTIATypeWidget{nullptr}; PopUpWidget* myTIATypeWidget{nullptr};
StaticTextWidget* myInvPhaseLabel{nullptr}; StaticTextWidget* myInvPhaseLabel{nullptr};
CheckboxWidget* myPlInvPhaseWidget{nullptr}; CheckboxWidget* myPlInvPhaseWidget{nullptr};
CheckboxWidget* myMsInvPhaseWidget{nullptr}; CheckboxWidget* myMsInvPhaseWidget{nullptr};
CheckboxWidget* myBlInvPhaseWidget{nullptr}; CheckboxWidget* myBlInvPhaseWidget{nullptr};
StaticTextWidget* myLateHMoveLabel{nullptr};
CheckboxWidget* myPlLateHMoveWidget{nullptr};
CheckboxWidget* myMsLateHMoveWidget{nullptr};
CheckboxWidget* myBlLateHMoveWidget{nullptr};
StaticTextWidget* myPlayfieldLabel{nullptr}; StaticTextWidget* myPlayfieldLabel{nullptr};
CheckboxWidget* myPFBitsWidget{nullptr}; CheckboxWidget* myPFBitsWidget{nullptr};
CheckboxWidget* myPFColorWidget{nullptr}; CheckboxWidget* myPFColorWidget{nullptr};
CheckboxWidget* myPFScoreWidget{nullptr}; CheckboxWidget* myPFScoreWidget{nullptr};
StaticTextWidget* myBackgroundLabel{nullptr}; StaticTextWidget* myBackgroundLabel{nullptr};
CheckboxWidget* myBKColorWidget{nullptr}; CheckboxWidget* myBKColorWidget{nullptr};
StaticTextWidget* mySwapLabel{nullptr}; StaticTextWidget* mySwapLabel{nullptr};