User File #24585969853799990

Upload All User Files

#24585969853799990 - Veup run-syncing script

Tetris_DS_Marathon_by_veup_9.11_sync_script.lua
1082 downloads
Uploaded 8/4/2015 5:14 AM by morningpee (see all 6)
To be paired with this movie. The piece sequence is hard-coded in the script, eliminating the need to brute-force the RNG.
pieceMap = "ZSLJTOI" -- Represents values 0-6
pieces = 
{
    "ZITLJOS",
    "OZSITLJ",
    "SITZJOL",
    "TJOLIZS",
    "JIOTZSL",
    "SZOILJT",
    "OJTLZSI",
    "STILOZJ",
    "JZLOTSI",
    "ZILJOTS",
    "LSJOZIT",
    "OISZJLT",
    "TZSIOLJ",
    "IOJTZSL",
    "TLISZJO",
    "ZOJLSIT",
    "SLJITOZ",
    "JTILZSO",
    "LZOSJIT",
    "LSOITJZ",
    "IZLTOSJ",
    "JITSOLZ",
    "LZJOSIT",
    "ZLIJSTO",
    "LJIOTSZ",
    "TSZIOLJ",
    "JSZTOIL",
    "JLSIOTZ",
    "SLOJZIT",
    "OTJZSLI",
    "JOZSITL",
    "ZSOLTJI",
    "ZOTILSJ",
    "ZSTOJLI",
    "ISTZOJL",
    "ZJSILOT",
    "LZISJTO",
    "ILJSZOT",
    "JOZLTSI",
    "SIZOJLT",
    "ZOTJSLI",
    "JTOZSLI",
    "ISLZTJO",
    "LTIOJSZ",
    "LTIOSZJ",
    "OZISTLJ",
    "IOJZSTL",
    "ZTILJSO",
    "ITZOSLJ",
    "SLIOJZT",
    "JSLZTOI",
    "LTJISZO",
    "IZTJSOL",
    "JSTZIOL",
    "LSTJOZI",
    "JZISOLT",
    "LSTJIOZ",
    "LJIOZST",
    "IOSJLZT",
    "ZISTJLO",
    "JOZILTS",
    "ITJLSOZ",
    "TLJZSIO",
    "JSLZTIO",
    "TLOJISZ",
    "ILOTZSJ",
    "IJLZTSO",
    "SOZLIJT",
    "JOTLISZ",
    "IOJLSZT",
    "IOTZJLS",
    "OITZSJL",
    "OZISTJL"
}

totalBags = 73 -- 1 bag = 7 unique pieces
pieceLandedLastFrame = false
currentBag = 1
currentBagIndex = 7
holdPiece = 255 -- Unsigned masterrace
nextHoldPiece = 255
currentPieces = pieces[1] -- All currently visible pieces, besides hold

INDICATOR_ADDRESS = 0x021C453C -- This address is 0 right before the game starts
PIECE_IDLE_FRAMES_ADDRESS = 0x0217DD30 -- Increments every frame a piece is in play
CURRENT_PIECE_ADDRESS = 0x0217DD1C
NEXT_PIECE_ADDRESS = 0x0217DD24
NEXT_PIECES_QUEUE = 0x0217DDA9 -- Includes the 5 pieces after the next piece
HOLD_PIECE_ADDRESS = 0x0217DD2C
PIECE_STATUS_ADDRESS = 0x0217DD32 -- Hard drop = 4, clearing lines = 3, lowering lines above cleared lines = 6

function getPieceNumberFromString(pieceString)
    return (string.find(pieceMap, pieceString) - 1)
end

function fillCurrentBagWithPieceArray(pieceArray, holdPieceValue)
    if( holdPiece == 255 ) then -- Stupid way to tell if it is really early in the game
        memory.writebyte( CURRENT_PIECE_ADDRESS, getPieceNumberFromString( pieceArray[1] ) )
        memory.writebyte( NEXT_PIECE_ADDRESS, getPieceNumberFromString( pieceArray[2] ) )
        memory.writebyte( HOLD_PIECE_ADDRESS, holdPieceValue )
    end
    for a = 3, 7 do
        memory.writebyte( NEXT_PIECES_QUEUE + a - 3, getPieceNumberFromString( pieceArray[a] ) )
    end
end

function getPieceArrayFromBag(bagString)
    pieceArray = {}
    for a = 1, 7 do
        pieceArray[a] = string.sub(bagString, a, a)
    end
    return pieceArray
end

function cycleCurrentPieces()
    _G.currentBagIndex = currentBagIndex + 1
    if currentBagIndex == 8 then
        _G.currentBag = currentBag + 1
        if currentBag > totalBags then -- Overflow protection
            _G.currentBag = 1
        end
        _G.currentBagIndex = 1
    end
    _G.currentPieces = string.sub(currentPieces, 2, -1) .. string.sub(pieces[ currentBag ], currentBagIndex, currentBagIndex)
end

function holdCurrentPiece()
    if(pieceLandedLastFrame == 1) then
        indexToTakeHoldFrom = 2;
    else
        indexToTakeHoldFrom = 1
    end
    _G.nextHoldPiece = getPieceNumberFromString( string.sub(_G.currentPieces, indexToTakeHoldFrom, indexToTakeHoldFrom) )
    if holdPiece == 255 then
        cycleCurrentPieces()
    else
        if(pieceLandedLastFrame == 1) then
            _G.currentPieces = string.sub(currentPieces, 1, 1) .. string.sub(pieceMap, holdPiece + 1, holdPiece + 1) .. string.sub(currentPieces, 3, -1)
        else
            _G.currentPieces = string.sub(pieceMap, holdPiece + 1, holdPiece + 1) .. string.sub(currentPieces, 2, -1)
        end
    end
    _G.holdPiece = nextHoldPiece
end

function thereWasAHardDrop()
    return memory.readbyte( PIECE_STATUS_ADDRESS ) == 4
end

function thereWasAHold()
    return joypad.get()["L"] or joypad.get()["R"]
end

function tetrisCoreLogic()
    if thereWasAHold() then
        holdCurrentPiece()
    end
    if thereWasAHardDrop() and not pieceLandedLastFrame then -- Wait 1 frame before cycling pieces
        _G.pieceLandedLastFrame = true
    elseif pieceLandedLastFrame then
        _G.pieceLandedLastFrame = thereWasAHardDrop() -- In the case of a hold + hard drop right after a tetris, PIECE_STATUS_ADDRESS can equal 4 for two consecutive frames
        cycleCurrentPieces()
    end
end

function resetEngine()
    _G.pieceLandedLastFrame = false
    _G.currentBag = 1
    _G.currentBagIndex = 7
    _G.holdPiece = 255
    _G.nextHoldPiece = 255
    _G.currentPieces = pieces[currentBag]
end

function inMarathonMode()
    return memory.readbyte( PIECE_IDLE_FRAMES_ADDRESS ) ~= 0x80 and emu.framecount() > 232 -- PIECE_IDLE_FRAMES_ADDRESS starts to equal 0x80 at frame 232
end

function updateBag()
    fillCurrentBagWithPieceArray( getPieceArrayFromBag( currentPieces ), holdPiece)
end

emu.registerbefore(
    function ()
        if inMarathonMode() then
            if memory.readword( INDICATOR_ADDRESS ) == 0 then
                resetEngine()
            else
                tetrisCoreLogic()
            end
            updateBag()
        end
    end
)