don't click here

[HELP] - Super Peel-Out in Sonic 1

Discussion in 'Engineering & Reverse Engineering' started by CS, Mar 23, 2025.

  1. CS

    CS

    Member
    29
    4
    3
    I'm currently using HiveBrain 2005 to create a custom version of Sonic 1.

    What do I intend to do with this custom version?

    - Replace all of Sonic's default sprites with Weber13's TOEI Sonic version (98% done, just need to fix 2 sprites for me to consider the work perfect);

    - I'll add several customizations (after the mechanics are resolved) that make the game much more difficult.

    - Add Sonic CD's Spindash to Sonic 1 (95% done, just need to adjust some small details related to the animation); Sonic CD's spindash in Sonic 1 will be a nerfed version of Sonic CD itself, considering that Sonic 1 is him at the "beginning of his career", Sonic 1's spindash will be much more limited, (in Sonic CD it improves and in Sonic 2 it is perfect);

    - Add Peel Out which, in the same way, is a nerfed version of Sonic CD's Super Peel Out (that's why it's not Super Peel Out, it's just Peel Out);

    Well, I'm having a lot of trouble adding Peel Out to the game. There is a tutorial on the internet for adding Sonic 2's spindash to Sonic 1, so with the help of ChatGPT, DeepSeek, and other conversational AIs, I was able to adapt the code for Sonic 2's spindash to look like Sonic CD's.

    The little I know about programming is Python, and it doesn't help me understand Assembly at all. Even using DeepSeek, ChatGPT, Mistral, etc., I couldn't make a functional Peel Out using the code for my spindash adapted for Sonic 1, Sonic CD style, as a base. I've tried everything and I can't make it work, even with the help of AI, which is why I'm here, it's the "last shot".

    All the code I put in sonic1.asm doesn't work, up arrow + jump, in theory it should work, it's in the code.

    I'll explain how Peel Out will work in my customized version of Sonic 1.

    - Its maximum loading time is 1.5 seconds;
    - Before 1.5 seconds, it will remain static using Sonic's walk cycle animation;
    - When it reaches 1.5 seconds, the animation changes to Sonic's run cycle;
    - When released, Sonic will instantly run from the speed predefined in code;
    - The animation to be used in the race will be the one that is already in the game for Sonic's run cycle (saving work editing and adding new sprites and animation);
    - If you release the up button before 1.5 seconds, the command is canceled;
    - Does not work in water;

    If anyone can give me a clue as to what is missing to make it work, I would be extremely grateful, I will put the code developed so far in a quote for evaluation and suggestions.

    Thx.

     
  2. MarkeyJester

    MarkeyJester

    You smash your heart against the rocks Resident Jester
    2,306
    558
    93
    Japan
    inb4 Devon ninja's me again (any second now... :flunked:)

    Firstly, I think you're doing great! This is EXACTLY how I made mine about nearly 20 years ago, a modified spindash, and it'll do you proud if you tinker with it. I donno about the use of ChatGPT though, that might sway you in the wrong direction and you might not really grasp what's going on by the end of it. ...but each to their own, I've not used it, so who am I to judge.

    You've not really specified what's not working, so I tried to assemble your peelout in a blank 2005 disassembly, and straight away, there are assembly errors:

    upload_2025-3-23_12-18-54.png

    It'll tell you what line the error is on (your line numbers will be different to mine), if you go to those lines you'll find:

    Code (Text):
    1.  
    2. ; Check if Sonic is in the "looking up" animation (#7)
    3.     cmpi.b #7,$1C(a0) ; Compare the current animation with animation #7 (looking up)
    4.     bne.s .exit ; If not animation #7, exit the routine
    5.  
    6. ; Check if the jump button was pressed
    7.     move.b ($FFFFF603).w,d0 ; Read the player's input (buttons pressed)
    8.     andi.b #$70,d0 ; Check if the jump button (bit 4, 5, or 6) was pressed
    9.     beq.s .exit ; If the jump button was not pressed, exit the routine
    The "bne.s" and "beq.s" you can see will be the cause, it's the .s (for short), these branches are smaller in size to save space, but they cannot reach a far distance. You can use .w (for word) instead (so "bne.w" and "beq.w"), these will branch a much further distance, but will cost you more space (not much, and nothing worth crying over, but I would say don't change all of your branches to .w unless the assembler complains it's "out of range").

    Once it builds it kinda works...

    There are some things the Spindash had that your peelout doesn't have, but that your peelout should have kept. For example, at ".no_water:" just before the "rts", there should be an "addq.w #4,sp", this is what the spindash does to prevent the jump routine from running later on if a spindash was successful. This will stop it from jumping before releasing. You might also need one at ".post_charge:" before the "rts" there too.

    The biggest problem is probably around ".charging:", the floor check I don't think it actually works:

    Code (Text):
    1.     move.b $3F(a0),d0 ; Read the ground state (0 = in air, 1 = on ground)
    2.     beq.s .release ; If not on the ground, release the Super Peel Out
    This causes immediate release of the peelout with no charge.

    Also this:

    Code (Text):
    1.     cmpi.b #7,$1C(a0) ; Compare the current animation with animation #7 (looking up)
    2.     bne.s .release ; If not animation #7, release the Super Peel Out
    This is the one in ".charging:", not the first one, the second one. If Sonic is charging, then he's not using the looking up animation, he's using the running animation which is 0, so this will cause release instantly too with no charge.

    I'll leave it here for now, that should give you enough info to make some corrections and at least play test it as it builds now.

    Good luck, I think you're heading in the right direction :thumbsup:
     
  3. CS

    CS

    Member
    29
    4
    3
    Thx MarkeyJester,


    I made the changes you suggested and it didn't work (for me), so I "talked to DeepSeek" and passed on his information and he suggested I adapt some things based on what he said, my code ended up like this:

    What happens now? It even responds to the up arrow + jump, it starts the first frame after the command with the roll frame and stops, at least it's responding now, although this roll frame doesn't make any sense, lol.

    Code:
     
  4. Kilo

    Kilo

    The Scatterbrained Hacker Tech Member
    1,328
    1,265
    93
    Canada
    Sonic 1 Source Code Recration
    If you already have the spindash it's probably also using $39(a0) as a flag, which would mean there's a conflict of both the spindash and peelout using the same byte of RAM for a flag, same with $3A(a0) for the charge count. You should probably switch it out with $29(a0) and $2A(a0), assuming those aren't being used by your hack. I can't promise that'll immediately fix it but it's one of the bigger things standing out to me right now with this code.
     
  5. CS

    CS

    Member
    29
    4
    3
    Hey, thanks Kilo. With your help and a chat with DeepSeek, I changed it to use unused memory addresses in the Sonic1.asm source code and Super Peel Out started working. Boy, working with low-level language is not easy. LOL

    But it has a small problem, it doesn't load Super Peel Out, when I press up arrow + jump, Sonic instantly starts running at maximum speed. It's a great skill for those who don't want to keep walking with Sonic until he starts to pick up speed. But this way, the skill becomes unbalanced. I'll try to make some more changes here with the help of artificial intelligence. If I get a perfect result, I'll post the code here for people to use in their Sonic games. :)
     
  6. Sin

    Sin

    Heroine Member
    13
    4
    3
    I'd recommend not using AI. You're not learning how your code works by running it through LLMs. It's better to step back and read it yourself so you know what code you're writing and understand more complex problems that LLM chatbots will most likely not know how to solve. It's clear that you understand how certain things work in engine so if you just take a bit of time you'll be able to fully grasp the object format in no time!

    LLMs regurgitate words they've already observed through scraping the internet, so they don't know what their code actually does, and whatever code it does give you may contain code written by others.

    I suggest using the Basic Questions & Answers thread when you encounter any roadblocks instead!
     
    Last edited: Mar 23, 2025
  7. CS

    CS

    Member
    29
    4
    3
    There are a few reasons why I'm choosing to interact with AI for these codes.
    1 - Learning: I'm learning a lot, even if it spits out "ready-made stuff" at me. Due to the token limitation, I can't simply copy the entire Sonic 1 source code (sonic1.asm) for it to see, including possible memory management conflicts, so I'm learning.
    2 - "Intellectual property": I joined this forum in 2008 where, in order to be a member, you had to answer some questions related to ROM hacks. If you got them right, you were admitted. And I noticed something: both in this forum and in others that deal with ROM hacks, many people who participate in these spaces to ask questions often don't get answers. The impression I get is that many users don't really like sharing their knowledge. So nowadays, unlike in 2008, I can interact with an artificial intelligence and it can teach me and explain things that I wouldn't be able to do by accessing forums.
    3 - Speed of feedback: complements the previous point, while with AIs I can get instant feedback, in forums I have to wait for a response. So I can combine business with pleasure: chat with AI and interact with other users in spaces designed for this.
    4 - Accelerated learning and time saving: any AI today is a 24/7 teacher. Even though it has its problems, it makes it much easier to learn a lot of things and the fact that they have a database trained on practically all the content available on the internet and much of the content outside it, this speeds things up, I don't have to waste a lot of time searching forums or search engines.
     
  8. BenoitRen

    BenoitRen

    Tech Member
    945
    573
    93
    Learning from a bot that can give you wrong information is not a good idea.
     
  9. CS

    CS

    Member
    29
    4
    3
    I respect the opinion of those who think otherwise, but for me, artificial intelligence is just another tool. And for me, it has served me well.

    But this is not the subject of the thread, now if you want to discuss whether intelligence can or cannot be good for those who are learning to edit ROM hacks, I can debate and give my opinions there. btw

    As a way of giving back (the artificial intelligence was trained with data from the internet), I will make the code for my Sonic CD-style spindash available for anyone who wants to use it in Sonic 1 and Peel Out when I finish solving its loading problem. So no one will have to spend so much time looking for solutions to put in their game and it won't be "hidden knowledge" that the few who know it won't reveal the recipe for.

    My spindash is only missing one thing: adjusting the rotation speed while it loads.

    My spindash fully loads in 1.5 seconds, so I asked the AIs how to implement a system where from 0.1 to 0.75 seconds it has a spin equivalent to 1/3 of the maximum, from 0.76 to 1.49 2/3 of the maximum and from 1.5 onwards the maximum spin, while loading. The AIs gave me solutions that didn't work, so from this point on I'm trying to solve it.

    My intention with this "spin flow" was to give the player a feeling of acceleration and the right moment to release the spindash at maximum speed.

    So I'm going to go for a simpler implementation, just a medium spin speed while charging, then maybe in the future I'll implement the improvements in a possible new version of the ROM.

    The Super Peel Out is instantaneous, I haven't solved this yet. But then I reduced the exit speed when releasing the up button and I was playing with the numbers, I put a value that Sonic goes very fast instantly, but without reaching his run cycle, as if it were an impulse. It looks interesting, if you do the command and keep the directional pad pointing in the direction Sonic is going quickly, he enters a run cycle, which could be a good solution if it doesn't solve the Peel Out problem.

    I'm going to try to solve these problems in both codes this week, if I can't I want to move forward, I don't want to get stuck in the code part and implement it the way it is. I want to edit aspects of the game to make it more difficult, here's a list of things I intend to change (these are the ones I remember at the moment, there are probably more things):

    - There's only 1 life;
    - Losing rings, regardless of the amount, only shows 1 ring coming out of Sonic (Master System Sonic style);
    - This ring that is lost when taking damage will last half the time it currently does;
    - Recovering the lost ring only restores 1 ring to the counter;
    - I'm planning for acts 1 and 2 to have only 10 rings (yes - I'll have to manually edit stage by stage) and in act 3 only 1 ring;
    - Adapt the acts only when absolutely necessary (I want to avoid changing the layout of the stages as much as possible, I want to increase the difficulty by changing it as little as possible);
    - Change the code so that the Special Stage appears if it has at least 5 rings.
    - The only monitor that will appear will be the shield one;
    - Single life, no extra lives or continues;
    - Since I don't want to have to go through the hassle of editing the Special Stage rings, I want to change the code so that the rings don't generate extra lives or continues;
    - Increase the number of enemies per stage;
    - Increase the speed of the enemies and those that shoot projectiles, so that they shoot more often and faster;
    - Natural obstacles in the stage are more dangerous, increasing their speed or adding 1 more obstacle where there already is one, or both;
    - Eggman is defeated with 12 hits;
    - Increase the difficulty of bosses by implementing something in an easy way, which can be speed or duplicate attack types (for example, Eggman from Green Hill having 2 balls) or both;
    - I'm thinking about using custom sprites to make Eggman look like Starved Eggman.

    Practical use of artificial intelligence. I asked him where the code to control the rings would be and he said some files that didn't exist (AI can hallucinate if it doesn't know), but he gave me important tips: look for some expression involving 'sonic hurts' or 'rings'. I opened the Sonic 1 source code to search and found the routine "Object 37 - rings flying out of Sonic when he's hit". For those who know the Sonic source code, it's very much with Assembly and everything else, this is nonsense, for people like me, AI is being a helping hand.

    So I copied all the code of this routine and asked him to show me where to change it so that it would always drop only 1 ring and reduce the duration of the dropped ring.

    To change the issue of the dropped rings, he told me to change the line specified below:

    Obj37_CountRings:
    movea.l a0,a1
    move.w ($FFFFFE20).w,d5 ; check number of rings
    beq.s Obj37_ResetCounter ; if zero, skip spawning rings
    moveq #0,d5 ; d5 = 0 (so only 1 ring spawns after DBF)
    move.w #$288,d4 ; initial angle for the single ring
    bra.s Obj37_MakeRings

    Then I asked him to tell me where to change the duration of the rings to 2 seconds, and he specified it, I changed it, tested it, and found it fast. I changed it to 2.5 seconds and I think it's OK. The AI also explained to me that depending on the system, NTSC or PAL, the duration of the ring can change because the duration of the rings is measured in frames. In other words, I learned a lot in a short conversation with the AI. So I didn't want to create complications in the code and assuming a time of 60 frames per second, I put the code below:

    move.b #150,($FFFFFEC6).w ; 150 frames = 2,5 seconds

    In 15 minutes I managed to solve 4 things that I want my custom version of Sonic 1 to have:
    - Losing rings, regardless of the amount, only shows 1 ring coming out of Sonic (Master System Sonic style);
    - This ring that is lost when taking damage will last half the time it currently does;
    - Recovering the lost ring only restores 1 ring to the counter;
    - Maximum 10 rings.

    I also made changes to the code so that 100 and 200 rings never give extra lives.

    As I said, AI for me is just another tool like Flex 2, image editors, etc. If I can use it to speed up the creation process, I will, but without discarding the contribution of people, which is certainly very valuable and more assertive than AI in many aspects.
     
    Last edited by a moderator: Mar 24, 2025
  10. Overlord

    Overlord

    Now playable in Smash Bros Ultimate Moderator
    19,613
    1,142
    93
    Long-term happiness
    Please don't double post, and please don't use this thread to debate the merits of AI - there's a topic elsewhere on the forum for that.