Editor, Skilled player (1172)
Joined: 9/27/2008
Posts: 1085
Magician. A game where you, amazingly enough, get a bunch of spells to help you through each situation. It's got elements of a puzzles sort of game, where you need to figure out the right spells. There's also some fighting, which of course you use spells to do the fighting. Meet Paul: A guy who can starve to death five minutes after a grand meal. Quite the metabolism, there. He also feels more experienced doing trivial tasks, such as entering a store or delivering a letter. Out of curiosity, I felt like TASing this game. This is the result. Not a whole lot to see early on. Mostly just walking. Later on, there's still a lot of walking, but at least you see more interesting scenes. Possible improvements involves using FLEET FOOT, not learning FEATHERLITE (never used), not learning POW SHIELD (apparently optional), and trying out VEGETABLES to see if +1 health/second instead of -2 health/second (hunger issues) lets me avoid using an unknown spell at one point. Here's what my memory watch looks like:
0053 Food
0054 Water
!0049 Gold
!004B Current|MANA
!004D Max|MANA
005A Main|Timer
X04BE Health|pp33
X04C2 Venom|pp33
X04D2 PHY-SH|pp33
X04D6 VEN-SH|pp33
X04DA FIR-SH|pp33
X04DE POW-SH|pp33
x04AF X-pos
x04B3 X-pos(2)
x04B7 Y-pos
x04BB Y-pos(2)
00C2 Item|selected
06CB Fly|timer
X04BC Health|2211
X04C0 Venom|2211
X04D0 PHY-SH|2211
X04D4 VEN-SH|2211
X04D8 FIR-SH|2211
X04DC POW-SH|2211
Player (98)
Joined: 7/16/2005
Posts: 34
I did a Magician run a few years ago, which was rejected because nobody knew the game. It's somewhat faster than yours. Here's the submission link. I suspect that this could still be improved on by 15 or more seconds, but without much audience for the TAS I've never bothered.
Editor, Skilled player (1172)
Joined: 9/27/2008
Posts: 1085
Hmm, so this has already been attempted. That's all I need to know. Thanks for pointing me to your attempts, and now I see what you did. I will make an effort to search harder next time, so I don't blindly make a thread without seeing what's already done. Our goals and routes are different, by the way. You aim to win, while I go for the "best" ending, hence, I'm slower in that respect as I get everything that involves raising mana. You hunt down various chests for mana potions while I skip everything but the required items, ignoring yummy food from within the same chests. The way we played is certainly different, but since our goals were different to begin with, it's hard to compare who is faster. Lastly, my final battle was played at 50% speed, not frame advance. So my final battle is obviously less than optimal. I didn't want to bother, since the run already had some potential improvements to make. I suggest watching what I did and see what I did different, but then again, your single post has a point. I don't exactly see much of a future for this thread now, as all that needs to be said is done now. The lack of audience approval is certainly a factor.
Active player (277)
Joined: 5/29/2004
Posts: 5712
Ignore the audience and keep submitting! That's the only way to win!
put yourself in my rocketpack if that poochie is one outrageous dude
Editor, Skilled player (1172)
Joined: 9/27/2008
Posts: 1085
Bag of Magic Food wrote:
Ignore the audience and keep submitting! That's the only way to win!
So basically, the audience (by not being an author of the run, you are part of it, correct?) is telling me to ignore itself. But if I do that, then I would have followed exactly what they say and hence, failed to ignore them. And since I didn't ignore them, I will have taken their advice to ignore them, but... ... Okay, now I know I'm in trouble, when I can neither listen or ignore the audience!
Player (98)
Joined: 7/16/2005
Posts: 34
I didn't realize this was a 100% run. After watching it, I'm pretty impressed by your time considering that you didn't use Jump for boosting at any point. There are a couple of things in your run that are clearly better than mine. Double-dipping the mana potion shop is clever. Also, I didn't really think about grabbing the easy puzzle points for free mana, that could be helpful in the any%, allowing for skipping the well and some of the chests. Hmm...
Banned User, Former player
Joined: 12/23/2004
Posts: 1850
BOMF was basically saying to ignore the rejection and make the run anyway, and I agree :P Meh.
Perma-banned
Editor, Skilled player (1172)
Joined: 9/27/2008
Posts: 1085
Xkeeper wrote:
BOMF was basically saying to ignore the rejection and make the run anyway, and I agree :P Meh.
I basically got that idea already. I just had to make fun of what was said! It seemed perfect at the time. With you also chipping in, I should continue then. In any case, I should try to speed up my run a bit, and see how it fares. Very needed entertainment at all the points where I'm not constrained to walking right is desired, correct? Hopefully, dancing my cursor around in the chests and other spots helped in that respect.
Editor, Skilled player (1172)
Joined: 9/27/2008
Posts: 1085
I think it went faster this time. Still using the good ending route, by the way. A few notes: I save twice in this run. The only reason for these saves is so the item selection is on the POUCH OF COINS, saving a few frames from actually scrolling all the way to the needed item. My first save is not in a place of common sense. There are several points where I intentionally delay in order to trick the 60-frame timer into extending time such as my FLEET FOOT. Stuff like "I can go now and have 10 frames of FLEET FOOT or delay 10 frames and get 60 frames of FLEET FOOT". I rather generously spent mana on plenty of FLEET FOOT and a few extra JUMPs. Then the fire demon showed his face, and I found that I slightly overspent my mana. Just slightly. Rather than FLEET FOOT my way across the flame bridge, I had to trick the 60-frame timer into giving me a little more time so I don't melt in a puddle of flesh, plus another two JUMPs on top of that. I wanted to show I had nothing left by attempting to cast one more LIGHTNING and displaying the related message of no mana. Paul's health hit critical a few times. Very critical. The final battle ended at 4 health left, on brink of starvation and death by poison, but as the final boss vanishes, everything is all nice and dandy, as though Paul is in no imminent danger. There are other points, but they should be obvious when I start "risking my life" with the unknown spell. The run is fairly optimal, but I'm pretty sure one can still find improvements. I may want to run through it once more for any% instead of "best ending". Or not, and just submit this one only. I don't think there's enough variety to publish both, if there's a good reason to publish at all.
Editor, Skilled player (1172)
Joined: 9/27/2008
Posts: 1085
Mostly the same run, with input required to show the whole ending and added subtitles. So, uh... Thought I'd play around with subtitles and see how it looks. Seems I talked less about the run and more about other things, but I do have some stuff related to the run itself. Thought I should ask about it before I submit. I've decided not to run the game once more for any%.
Joined: 1/28/2009
Posts: 6
Location: USA
This is an ideal use of FCEUX's new subtitle feature. The commentary adds a lot of interest to what could otherwise be seen as a "walk right" video. That said, I'd be happy to see even an unsubtitled run, just because this game frustrated me to no end.
Editor, Skilled player (1172)
Joined: 9/27/2008
Posts: 1085
I'm just breaking the game a few times. None of them any good for speed, but the point is entertainment. Those save slots do prove useful to show up to five different scenes in one movie file. Scene 1 - Paul makes it to town even when dead! What the hey?! Scene 2 - Did I create a portal with "death" and "new area" triggers? Scene 3 - Boat guy wasn't intended to be used more than once... Scene 4 - Anti-grav spikes plus UNKNOWN... spell = a mess Scene 5 - Here's what happens if I don't get through the door in time... I'm thinking about trying to improve my run. Maybe not actively trying, but the thought is there.
Editor, Skilled player (1172)
Joined: 9/27/2008
Posts: 1085
Well, here's an improvement of around 35 seconds. Syncs with Old PPU and New PPU. Not submitting due to lack of dancing at the end. Besides, I wasn't aggressive enough with my mana usage. But I basically changed every segment throughout the game, as follows: TOWN - Slotermeyer's strategy of JUMPs first was the better choice. Unfortunately, the act of getting the LETTER erases the JUMP spell from my list of spells for some reason... Also snatched up 500 gold! WILDERNESS - Used EXORCISE on the plant monster instead of LIGHTNING. LAKE - Bought an extra mana potion with the extra gold, using excess mana beyond the 1250 mark on FLEET FOOT (4). Also jumped off a shell and almost into water... Almost! More efficient gargoyle battle. FOREST - Aggressive use of FLEET FOOT. EXORCISE against mushroom spirit. CAVERNS - Aggressive use of FLEET FOOT. Sidetracked to grab a REFRESH POTION. DUNGEONS - I JUMP throughout this whole place, using the massive load of mana I got from the side-path. Yes, JUMP is faster than FLEET FOOT, at a slightly higher mana cost. CASTLE - A few other JUMPs and an extra FLEET FOOT. EXORCISE the flame demon. TOWER - Skip the mana fountain. The mana from the REFRESH POTION used in the DUNGEONS is still lasting. TOWER TOP - EXORCISE versus Abadon. EXORCISE wins! About 280 mana to spare One thing to check is how much more aggressively can I cast my speedy spells. There doesn't appear to be much room to squeeze in much more. Also, I can't make fun of how Paul manages to return home with critical injuries, malnutrition, and deadly venom anymore! The REFRESH POTION is too powerful! Then again, it's hard for viewers to see such stats.
Editor, Skilled player (1172)
Joined: 9/27/2008
Posts: 1085
I've already completed the run, which can be seen here. Regardless, I am holding on to a lua script, one that shows some information. I think I should post it now. A lua script for FCEUX 2.1.3-interim. the gui.box works differently between 2.1.2 and 2.1.3-interim for whatever reason. This pretty much displays the HP, shields, and venom of everything. It also shows an approximation of food and water, mana, and the 60-frame timer. It even points out certain active timers and when you can cast your next spell. In spite of this information on screen, I've rarely used this script in my run...
--*****************************************************************************
Draw= {}     --Draw[digit](left,top,color)
--*****************************************************************************
-- A set of functions to draw specific digits.

function Draw.D0(left, top, color)
    gui.box(left  ,top  ,left+2,top+4,0,color)
end

function Draw.D1(left, top, color)
    gui.line(left  ,top+4,left+2,top+4,color)
    gui.line(left+1,top  ,left+1,top+3,color)
    gui.pixel(left  ,top+1,color)
end

function Draw.D2(left, top, color)
    gui.line(left  ,top  ,left+2,top  ,color)
    gui.line(left  ,top+3,left+2,top+1,color)
    gui.line(left  ,top+4,left+2,top+4,color)
    gui.pixel(left  ,top+2,color)
    gui.pixel(left+2,top+2,color)
end

function Draw.D3(left, top, color)
    gui.line(left  ,top  ,left+1,top  ,color)
    gui.line(left  ,top+2,left+1,top+2,color)
    gui.line(left  ,top+4,left+1,top+4,color)
    gui.line(left+2,top  ,left+2,top+4,color)
end

function Draw.D4(left, top, color)
    gui.line(left  ,top  ,left  ,top+2,color)
    gui.line(left+2,top  ,left+2,top+4,color)
    gui.pixel(left+1,top+2,color)
end

function Draw.D5(left, top, color)
    gui.line(left  ,top  ,left+2,top  ,color)
    gui.line(left  ,top+1,left+2,top+3,color)
    gui.line(left  ,top+4,left+2,top+4,color)
    gui.pixel(left  ,top+2,color)
    gui.pixel(left+2,top+2,color)
end

function Draw.D6(left, top, color)
    gui.box(left  ,top+2,left+2,top+4,0,color)
    gui.line(left  ,top  ,left+2,top  ,color)
    gui.pixel(left  ,top+1,color)
end

function Draw.D7(left, top, color)
    gui.line(left  ,top  ,left+1,top  ,color)
    gui.line(left+2,top  ,left+1,top+4,color)
end

function Draw.D8(left, top, color)
    gui.box(left,top,left+2,top+4,0,color)
    gui.pixel(left+1,top+2,color)
end

function Draw.D9(left, top, color)
    gui.box(left  ,top  ,left+2,top+2,0,color)
    gui.line(left  ,top+4,left+2,top+4,color)
    gui.pixel(left+2,top+3,color)
end


Draw[0],Draw[1],Draw[2],Draw[3],Draw[4]=Draw.D0,Draw.D1,Draw.D2,Draw.D3,Draw.D4
Draw[5],Draw[6],Draw[7],Draw[8],Draw[9]=Draw.D5,Draw.D6,Draw.D7,Draw.D8,Draw.D9
--*****************************************************************************
function DrawNum(right, top, Number, color, bkgnd)
--*****************************************************************************
-- Paints the input number as right-aligned.
-- Returns the x position where it would paint another digit.
-- It only works with integers. Rounds fractions toward zero.

    local Negative= false
    if Number < 0 then
        Number= -Number
        Negative= true
    end

    Number= math.floor(Number)
    if not color then color= "white" end
    if not bkgnd then bkgnd= "clear" end

    if Number < 1 then
        gui.box(right+1,top-1,right-2,top+5,bkgnd,bkgnd)
        Draw[0](right-2,top,color)
        right= right-4
    end

    while (Number >= 1) do
        local digit= Number % 10
        Number= math.floor(Number/10)

        gui.box(right+1,top-1,right-2,top+5,bkgnd,bkgnd)
        Draw[digit](right-2,top,color)
        right= right-4
    end

    if Negative then
        gui.box(right+1,top-1,right-2,top+5,bkgnd,bkgnd)
        gui.line(right, top+2,right-2,top+2,color)
        right= right-4
    end
    gui.line(right+1,top-1,right+1,top+5,bkgnd)
    return right
end


local MemRead= memory.readbyte

--*****************************************************************************
function within(input, low, high)
--*****************************************************************************
    return (input >= low) and (input <= high)
end

--*****************************************************************************
function ShowHP()
--*****************************************************************************
if memory.readbyte(0x0005) ~= 0x48 then return end
local ShClr= {"#FFFFFFFF","#00FF00FF","#FF8000FF","#00FFFFFF"}
local background= "#000000FF"
local ShX= { 0,13, 0,13}
local ShY= { 0, 0, 7, 7}

    local SCR_x= MemRead(0x0094) + MemRead(0x0095)*256
    local SCR_y= MemRead(0x0096) + MemRead(0x0097)*256

    for i= 0, 3 do
        local xpos= MemRead(0x04AC+i) + MemRead(0x04B0+i)*256
        local ypos= MemRead(0x04B4+i) + MemRead(0x04B8+i)*256
        xpos , ypos= xpos - SCR_x -2  ,  ypos - SCR_y -28

        local HV= MemRead(0x04BC+i)

        if (HV > 0) and within(xpos,-15,270) and within(ypos,0,170) then
            xpos= math.min(math.max(xpos,9),239)
            DrawNum(xpos,ypos,HV,"white",background)

            HV= MemRead(0x04C0+i)
            if HV > 0 then
                DrawNum(xpos+13,ypos,HV,"green",background)
            end

            for Sh= 1, 4 do
                Shield= MemRead(0x04CC +4*Sh +i)

                if Shield > 0 then
                    local DX , DY= xpos+ShX[Sh]  ,  ypos+10+ShY[Sh]
                    DrawNum(DX,DY, Shield, background, ShClr[Sh])
                end
            end
        end
    end
end


--*****************************************************************************
function TimerDance()
--*****************************************************************************
local tmr= MemRead(0x005A)
local clr= "white"
if tmr == 0 then clr= "red" end

    gui.box( 250,222,251,163+tmr,0,clr)
    gui.line(249,222,252,222,clr)
    gui.line(249,162,252,162,clr)
end

--*****************************************************************************
function FoodBar()
--*****************************************************************************
local Fd= math.floor((MemRead(0x0053)+3)/4)
local Wt= math.floor((MemRead(0x0054)+3)/4)
    gui.box(  1,158,  6,223,0,"white")

    if Fd > 0 then  gui.box(  2,222,  3,223-Fd,"green"    )  end
    if Wt > 0 then  gui.box(  4,222,  5,223-Wt,"#0040FFFF")  end
end



--*****************************************************************************
function NextSpell()
--*****************************************************************************
local MUD= MemRead(0x04F3)
local count= 0

    for i= 0, 2 do
        if MemRead(0x054D+i) < 128 then
            count= count+1
        end
    end

    if     MUD == 0 then
        MUD= 1
    elseif MUD == 1 then
        MUD= 0
    else
        MUD= 2
    end

    for i= 1, 3 do
        local H, Hc= 133, ((MUD-i)%3)*8
        local color= "blue"
        if i == 3 then color= "white" end

        if count >= i then
            gui.box(3,H+Hc+2,4,H+Hc+3,0,color)
        else
            gui.box(1,H+Hc  ,6,H+Hc+5,0,color)
        end
    end
end


--             Attack      Meditate    Fly         Speed
--               Weight      Light       Slomo       Fire Doom!
local timers= {0x06C9     ,0x06D5     ,0x06CB     ,0x04E7,
                 0x04EB,     0x06CC,     0x04E4,     0x06E3}
local colors= {"#FF4000FF","#00FF00FF","#00FFFFFF","#FFFF00FF",
                 "#C0C0C0FF","#FFFFFFFF","#FF00FFFF","#FFFF00FF"}
--*****************************************************************************
function SpellTimers()
--*****************************************************************************

    for i= 1, 8 do
        temp= MemRead(timers[i])
        if temp > 0 then
            if temp >= 100 then  --Draw HI
                local y= 7*i
                gui.line(1,y  ,1,y+4,colors[i])
                gui.line(3,y  ,3,y+4,colors[i])
                gui.line(5,y  ,7,y  ,colors[i])
                gui.line(5,y+4,7,y+4,colors[i])
                gui.line(6,y+1,6,y+3,colors[i])
                gui.pixel(2,y+2,colors[i])
            else
                DrawNum(7,7*i,temp,colors[i])
            end
        end
    end
end

--*****************************************************************************
function zammie()
--*****************************************************************************
    ShowHP()
    TimerDance()
    FoodBar()
    DrawNum(254, 1,MemRead(0x004B)+MemRead(0x004C)*256,"#0080FFFF","black")
    DrawNum(254, 8,MemRead(0x004D)+MemRead(0x004E)*256,"#00C0FFFF","black")
    SpellTimers()
    NextSpell()

end
emu.registerafter(zammie)