Added 'jitter recovery' emulation from SpiceWare, in which large

scanline count differences can take multiple frames to recover.
Currently the code uses a hard-coded delay; next I'll make it a
variable, changable within the UI (and on the commandline).


git-svn-id: svn://svn.code.sf.net/p/stella/code/trunk@3272 8b62c5a3-ac7e-4cc8-8f21-d9a121418aba
This commit is contained in:
stephena 2016-02-01 23:43:00 +00:00
parent 65bb073968
commit 3b2f534bf7
3 changed files with 54 additions and 14 deletions

View File

@ -14,6 +14,11 @@
4.7 to 4.7.1: (xxx xx, 2016)
* Improved TV 'jitter' emulation; the recovery time can now be spread
over multiple frame, to simulate a real TV taking multiple frames to
recover. Special thanks to SpiceWare of AtariAge for the initial idea
and implementation.
* Fixed bug with 'Medieval Mayhem' ROMs; the paddle range was set too
low, and as a result the number of players couldn't be selected.

View File

@ -39,6 +39,7 @@
#include "TIA.hxx"
#define HBLANK 68
#define JITTER_RECOVERY 10
#define CLAMP_POS(reg) if(reg < 0) { reg += 160; } reg %= 160;
@ -128,7 +129,7 @@ void TIA::initialize()
myBitsEnabled = myCollisionsEnabled = true;
myJitterEnabled = mySettings.getBool("tv.jitter");
myNextFrameJitter = myCurrentFrameJitter = 0;
myNextFrameJitter = myCurrentFrameJitter = myJitterRecovery = 0;
// Make sure all TIA bits are enabled
enableBits(true);
@ -646,7 +647,10 @@ inline void TIA::endFrame()
if(myJitterEnabled && myFrameCounter > 3)
{
// Set the jitter amount for the current frame
myCurrentFrameJitter = myNextFrameJitter * 160;
myCurrentFrameJitter = (myNextFrameJitter + myJitterRecovery*JITTER_RECOVERY)* 160;
if(myJitterRecovery < 0) myJitterRecovery++;
else if (myJitterRecovery > 0) myJitterRecovery--;
// Calculate the jitter amount for the next frame.
// Jitter amount of a frame depends upon the difference
@ -655,23 +659,51 @@ inline void TIA::endFrame()
if(myNextFrameJitter < -1)
{
myNextFrameJitter = (myNextFrameJitter-1) / 2;
if(myNextFrameJitter/JITTER_RECOVERY < myJitterRecovery)
{
myJitterRecovery = myNextFrameJitter/JITTER_RECOVERY;
myNextFrameJitter = 0;
// Make sure currentFrameBuffer() doesn't return a pointer that
// results in memory being accessed outside of the 160*320 bytes
// allocated for the frame buffer
if(myNextFrameJitter < -Int32(myFrameYStart))
myNextFrameJitter = myFrameYStart;
// Make sure currentFrameBuffer() doesn't return a pointer that
// results in memory being accessed outside of the 160*320 bytes
// allocated for the frame buffer
if(myJitterRecovery*JITTER_RECOVERY < -Int32(myFrameYStart))
myJitterRecovery = myFrameYStart / JITTER_RECOVERY;
}
else
{
myNextFrameJitter = (myNextFrameJitter-1) / 2;
// Make sure currentFrameBuffer() doesn't return a pointer that
// results in memory being accessed outside of the 160*320 bytes
// allocated for the frame buffer
if(myNextFrameJitter + myJitterRecovery*JITTER_RECOVERY < -Int32(myFrameYStart))
myNextFrameJitter = myFrameYStart;
}
}
else if(myNextFrameJitter > 1)
{
myNextFrameJitter = (myNextFrameJitter+1) / 2;
if (myNextFrameJitter/JITTER_RECOVERY > myJitterRecovery)
{
myJitterRecovery = myNextFrameJitter / JITTER_RECOVERY;
myNextFrameJitter = 0;
// Make sure currentFrameBuffer() doesn't return a pointer that
// results in memory being accessed outside of the 160*320 bytes
// allocated for the frame buffer
if(myNextFrameJitter > 320 - Int32(myFrameYStart) - Int32(myFrameHeight))
myNextFrameJitter = 320 - myFrameYStart - myFrameHeight;
// Make sure currentFrameBuffer() doesn't return a pointer that
// results in memory being accessed outside of the 160*320 bytes
// allocated for the frame buffer
if(myJitterRecovery*JITTER_RECOVERY > 320 - Int32(myFrameYStart) - Int32(myFrameHeight))
myJitterRecovery = (320 - myFrameYStart - myFrameHeight)/JITTER_RECOVERY;
}
else
{
myNextFrameJitter = (myNextFrameJitter+1) / 2;
// Make sure currentFrameBuffer() doesn't return a pointer that
// results in memory being accessed outside of the 160*320 bytes
// allocated for the frame buffer
if(myNextFrameJitter + myJitterRecovery*JITTER_RECOVERY > 320 - Int32(myFrameYStart) - Int32(myFrameHeight))
myNextFrameJitter = 320 - myFrameYStart - myFrameHeight;
}
}
else
myNextFrameJitter = 0;

View File

@ -634,6 +634,9 @@ class TIA : public Device
// Jitter amount for the current frame
Int32 myCurrentFrameJitter;
// Large jitter values will take multiple frames to recover from
Int32 myJitterRecovery;
private:
// Following constructors and assignment operators not supported