So now that I've messed around with ASM a bit, I spent most of last weekend making my first psuedo-real code with it. It works nearly as I want, but I think that it could be optimized quite a bit, since I just started and don't know many commands or shortcuts, and because I've only had the EnHacklopedia examples to look at lately (lost internet T_T). So I was hoping some of you guys could take a look at it and give some pointers or any way for it to run smoother and whatnot.
First, it'd probably help to describe what it is I'm trying to do. It's for Castlevania: Dawn of Sorrow, and there's a soul that surrounds you with normally 2-6 balls of fire that slowly circle you and hurt anything they contact. What I do is make it spawn 22 balls of fire around you and with the ASM I make it so that when you touch the screen, they shoot out in the direction you point. I ran into some difficulties with achieving conservation of velocity when working with different directions, as I don't know how to do sine/cosine equations in ASM or how to divide properly, and I'm doubting that sine/cosine is doable in ASM >_>
Anyway, the gist of what's happening is it checks to see if you're touching the screen, if not, then it refills some your MP and skips the rest of the code. If you are, it takes the coordinates of the touch screen, converts it into the coordinates used for the character, and compares where it is on the screen in relation to your character. Then it says to add X and Y to the X and Y coordinates of one fireball out of the 22. Each time it cycles through the code, it moves the next fireball, up to the 22, at which point the counter resets itself and deducts you MP.
Secondly, it'd probably be helpful to know the addresses I'll be using and what they are:
X coordinate of what the fireballs circle - 020CB13C
Y coordinate of same - 020CB140
Fireball 1 X coordinate - 020CB3DC
Fireball 1 Y coordinate - 020CB3E0
Left Side of screen - 020F7070 (used with the first address to figure out the position of the character on the screen, as in long rooms/tall ones the touch screen doesn't stack values like the character info)
Top side of screen - 020F7074
X coord of Touch Screen - 0219C890
Y coord of Touch Screen - 0219C892
Touch Screen On/Off - 0219C894 (00 when not touching, 01 when touching)
And then some preliminary stuff to understand. The touch screen coordinates go from 0x0140-0x0EE0 (total of 0x0DA0) in the X direction and from 0x00E0-0x0F40 (total of 0x0E60) in the Y. The character coordinates in one screen can be from 0x00000000-0x00100000 in the X direction and 0x00000000-0x000C0000 in the Y. I have no idea why the touch screen would be more sensitive in the Y direction, seeing as how there are fewer pixels, but it is for whatever upsetting reason. Anyway, to convert between the two I subtract 0x0140 or 0x00E0 from the X or Y touch screen coordinates, respectively, then multiply them by 0x012C and 0x00D5 to get them in the range of the character X and Y.
I'm not sure how lsr and lsl stuff is supposed to work, but it seems like it just divides or multiplies by the square of whatever number is after it. Since I don't know how to divide otherwise, you'll see me do this a couple of times. Any other way to divide would be greatly appreciated ^_^
Also, if someone could explain how the AND and OR logical commands are supposed to work I'd appreciate that as well. I spent some time trying to figure out what they did, but I can't find a real use for them (even though they were used in the MP:H example on EnHacklopedia)
So, with that out of the way, here's the wall of code >_>
I'll put in some linebreaks for the different sections of code and give an overview below, if you don't want to have to proofread while trying to figure out what something even does.
Code:
ldr r8,=0x0219C894
ldrb r8,[r8]
cmp r8,#0
bne code
ldr r0,=0x020F7414
ldrh r2,[r0]
ldr r1,=0x020F7416
ldrh r1,[r1]
sub r1,r1,r2
mov r1,r1,lsr#5
cmp r1,#0
moveq r1,#0001
add r1,r2
strh r1,[r0]
b quit
code:
ldr r0,=0x0219C890
ldrh r0,[r0]
sub r0,#0x0140
mov r1,#0x0120
add r1,#0xC
mul r1,r0,r1
ldr r0,=0x020CB13C
ldr r0,[r0]
ldr r2,=0x020F7070
ldr r2,[2]
sub r0,r0,r2
mov r12,#2
cmp r1,r0
movlt r12,#0
sublt r0,r1
cmp r12,#2
subeq r0,r1,r0
move r0,r0,lsr#4
ldr r1,=0x020CB3DC
ldr r2,[r1]
mov r8,#21
mul r3,r8,r0
cmp r12,#0
subeq r2,r3
cmp r12,#2
addeq r2,r3
ldr r12,counter
mov r3,#0x02A0
mla r0,r12,r3,r1
str r2,[r0]
str r0,addr1
ldr r1,=0x0219C892
ldrh r1,[r1]
sub r1,#0xE0
mov r0,#0xD5
mul r1,r0,r1
ldr r0,=0x020CB140
ldr r0,[r0]
ldr r2,=0x020F7074
ldr r2,[r2]
sub r0,r0,r2
mov r12,#2
cmp r1,r0
movlt r12,#0
sublt r0,r1
cmp r12,#2
subeq r0,r1,r0
move r0,r0,lsr#4
ldr r1,=0x020CB3E0
ldr r2,[r1]
mov r8,#21
mul r3,r8,r0
cmp r12,#0
subeq r2,r3
cmp r12,#2
addeq r2,r3
ldr r0,addr1
str r2,[r0,#4]
ldr r0,=0x020F7414
ldrh r1,[r0]
sub r1,#4
ldr r12,counter
add r12,#1
cmp r12,#22
streqh r1,[r0]
moveq r12,#0x00000000
str r12,counter
quit:
bx r14
Hopefully there aren't any typos in that (had to enter all that manually on a library comp).
The first section just checks if the screen is being touched, skipping the rest of the code and adding to MP if it isn't.
The second part loads the X coord of the touch screen, then converts it to the same number range as the ones used for characters/screen frames. One thing in particular that I couldn't figure out is why I can't just move 0x012C to the register, so I had to do the 2 line thing as you can see.
The third part takes the characters position and calibrates it to the side of the screen, which means that it'll always be in the range of what I specified the X coordinate to be at the top.
Using that, I compare it to the touch screen X, and see if it's to the left or right. Then I use the lsr#4 to divide the difference by 16.
Then I multiply this by 22 (number of fireballs) and add that value to the X coordinate of the current fireball (specified by the counter).
Then I repeat most everything for the Y coordinate.
The end adds to the counter, and deducts from MP.
But yeah, one weird thing is that when comparing left/right, if I use r6 instead of r12, when going to the left things are normal, but when going to the right, everything runs crazy fast or something, and it basically looks like a crazy firestorm, which is the effect that I want to achieve. When using r6 on the up/down comparison, the game freezes, and setting r6 to anything other than 0 and not editing it after makes it go haywire as well, everything warps way too quickly and disappears offscreen in a split second.
Also, is it a really dire thing if the code is really long? With the additional non-ASM specifications, it stands at about 70-80 lines currently.
Lastly, the only activator I know for AR is 9400130 XXXX0000, but I've seen other ones used, is there a list of these comewhere that I haven't seen? Or are they just specified in the Trainer Toolkit manual?
And yeah, if anyone actually takes the time to help me with any of this, you're my hero ^_^