I can display, save, and check the tile map.
But I can't seem to get my player to move around it, while checking for values of a square that he CAN move on.

Code:

.Drawing the map
For(A,0,11)
For(B,0,7)
If {B*12+A+L₁}=1
Pt-On(A*8,B*8,Pic1)
End
End
End

.Game Loop
Repeat GetKey(15)
getKey→K
DispGraph
Pt-On(X,Y,Pic2)
...
I was going to use this
to help with checking for
a to the adjacent spot
from where the player
will be moving.
...
X/8→A
Y/8→B

.Movement code
.This is what I was hoping to work, but it didn't.
If K=1 and {B+1*12+A+L₁}
Pt-Change(X,Y,Pic2)
Y+8→Y
End

...
The rest of the movement code
went here, but it doesn't work.
...


I'm using simple 8x8 sprites for the player and other tiles.
How would I check for the adjacent tile, and if a certain value, then move there, otherwise, do nothing?

Edit by Merth: Moved to General Programming forum, since this isn't z80 asm.
Here's how I would do it, withholding as much crazy and unreadable optimization as posible:


Code:
.TESTHELL

[FFFFFFFFFFFFFFFF]→Pic1
[FF818181818181FF]→Pic2

DiagnosticOff
3→X→Y

.Drawing the map
ClrDraw
For(A,0,11)
For(B,0,7)
If {rand^4=0→{B*12+A+L₁}}
Pt-Change(A*8,B*8,Pic1)
End
End
End

.Game Loop
While 1
DrawP()
DispGraph
DrawP()
getKey→K:TryMv()
End!If K xor 15

.Xor player sprite
Lbl DrawP
Pt-Change(X*8,Y*8,Pic2)
Return

.Try to move player according to given key value
Lbl TryMv
MvP()
Return!If {Y*12+X+L₁}
K-1 xor 3+1
Goto MvP

.Move player according to given key value
Lbl MvP
Z-Test(-1,Mv1,Mv2,Mv3,Mv4)
Return
Lbl Mv1
Yʳ++
Return
Lbl Mv2
Xʳ--
Return
Lbl Mv3
Xʳ++
Return
Lbl Mv4
Yʳ--
Return


Notes about it:
    ▪ I made the assumption that your player is restricted to tile-based movement. Hopefully this was a correct assumption, or pretty much my solution is entirely wrong.
    ▪ I changed X and Y to be stored as tile values rather than pixel values, so they're scaled down by a factor of 8. This makes the movement code a lot easier, while making the drawing code negligibly larger. Of course, this relies on the assumption above.
    ▪ Don't worry about my changes to map drawing, that was just so it worked in this test program.
    ▪ I changed the main loop to quit based on the OS getKey function instead of direct key input.
    ▪ I wasn't sure how you drew the player, but I used the trick of drawing the sprite with xor logic right before the DispGraph so it shows up, and then erasing it with the same xor logic right after. This could be done differently.
    ▪ Finally, the meat of the changes. The movement function TryMv() takes the key value passed in and calls the unconditional movement function MvP(). The MvP() function works using the nice fact that the arrow keys are contiguous from 1-4, so it is easy to subtract one from the key value to align the arrow keys to 0-3 for a movement jump table. Any other key values will fall through and not result in a jump anywhere, merely a return. Once the MvP() function has finished, it is checked if the player is now inside of a solid tile. If so, it is assumed that the player was just moved into the solid tile, so the key value is "inverted" on the range 1-4 and the unconditional movement function MvP() is called to cancel out the movement made.
hellninjas wrote:
If K=1 and {B+1*12+A+L₁}

I don't know if the problem comes from here but it may be since Axe's "and" is bitwise. This means that if {B+1*12+A+L₁} equals 2, then K=1 and {B+1*12+A+L₁} equals 0.

(got ninja'd by Runer112 but Hellninjas said that I could post anyway).
Runner: Thanks but the code itself it barely understandable from my view o_o, I get it, though. Thanks for making a description x3

Hayleia, so how would I change it..?
Here is a code that is easier to understand (but of course less optimized). Needs 1.2.1a to compile due to custom constants with names larger than 5 characters (or just change their names).


Code:
.ATEST
[]->°Map
[010101010101010101010101]
[010000000000000000000001]
[010000000000000000000001]
[010000000000000000000001]
[010000000000000000000001]
[010000000000000000000001]
[010000000000000000000001]
[010101010101010101010101]

[]->°Sprites
[0000000000000000]
[FFFFFFFFFFFFFFFF]

.draw the map
For(X,0,11)
 For(Y,0,7)
  Pt-On(X*8,Y*8,{Y*12+X+°Map}*8+°Sprites)
 End
End

5->X->Y
While 1
 Draw()
 DispGraph
 Erase()
 getKey(1)?{Y+1*12+X+°Map}??Y++
 getKey(4)?{Y-1*12+X+°Map}??Y--
 getKey(2)?{Y*12+X-1+°Map}??X--
 getKey(3)?{Y*12+X+1+°Map}??X++
EndIf getKey(15)

Return

Lbl Draw
Lbl Erase
Pt-Change(X*8,Y*8,°Sprites+8)
Return


Another code if you really want to use the slow getKey routine instead of getKey(#):

Code:

.ATEST
[]->°Map
[010101010101010101010101]
[010000000000000000000001]
[010000000000000000000001]
[010000000000000000000001]
[010000000000000000000001]
[010000000000000000000001]
[010000000000000000000001]
[010101010101010101010101]

[]->°Player
[FF818181818181FF]

[]->°Sprites
[0000000000000000]
[FFFFFFFFFFFFFFFF]

.draw the map
0->X
For(12)
 ~1->Y
 For(8)
  Pt-On(X*8,Y++*8,{Y*12+X+°Map}*8+°Sprites)
 End
 X++
End

5->X->Y
While 1
 Draw()
 DispGraph
 Erase()
 getKey
 !If -1
  InMap(X,Y+1)??Y++
 Else!If -1
  InMap(X-1,Y)??X--
 Else!If -1
  InMap(X+1,Y)??X++
 Else!If -1
  InMap(X,Y-1)??Y--
 End
EndIf getKey(15)

Return

Lbl Draw
Lbl Erase
Pt-Change(X*8,Y*8,°Player)
Return

Lbl InMap
{r2*12+r1+°Map}
Return
hellninjas wrote:
Runner: Thanks but the code itself it barely understandable from my view o_o, I get it, though. Thanks for making a description x3

Hayleia, so how would I change it..?

You'd use the "short-circut" operators - ones that stop evaluating if the current point is true or false.

Code:
...
EXPR1 will evaluate first,
and if it is false ("?"), it will jump
to the end of the line.
Otherwise EXPR2 will evaluate,
and if it is true ("??"), it will again
jump to the end.
Otherwise, EXPR3 will evaluate.
...
EXPR1?EXPR2??EXPR3

.This transitions to and/or quite well:
.If A and B:
If A?B
.If A or B
If A??B
.If not A nor B
!If A??B
.If either !A or !B
!If A?B


I won't give you the short answer, because programming requires you to understand what's going on and solve problems dynamically.
Typically speaking, one would 'center' the player on the screen, and offset the tile coordinate to adjust the map. This allows you to have maps bigger than the screen.


Code:

.draw the map around player X,Y (suggesting a 11x7 map)
For(B,Y-3,Y+3)
 For(A,X-5,X+5)
  If(A>0 && A<W && B>0 && B<H)
   .Draw tile at (A,B)
  Else
   .Draw blank tile
 End
End
.Draw player at (6, 4)

.Check movement input
.Match new X+6,Y+4 destination coordinate against tile types
.On failure, set destination to player location.
.Set player location to destination


Moving X and Y (player coordinates) would move the map
  
Register to Join the Conversation
Have your own thoughts to add to this or any other topic? Want to ask a question, offer a suggestion, share your own programs and projects, upload a file to the file archives, get help with calculator and computer programming, or simply chat with like-minded coders and tech and calculator enthusiasts via the site-wide AJAX SAX widget? Registration for a free Cemetech account only takes a minute.

» Go to Registration page
Page 1 of 1
» All times are UTC - 5 Hours
 
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum

 

Advertisement