Jump to content
IGNORED

Playfield line with random pieces missing..


yuppicide

Recommended Posts

Is there a way to draw a playfield line like

 

PFHLINE 2 0 31 ON

 

But.. randomly remove a few blocks?

 

I want a playfield line, but want a random exit for players to get through.

Yes, generate a random number x between 1 and 30, inclusive, then do "pfpixel 2 x off" (assuming this is on row 2 as was your pfhline statement). Note that rand won't return a 0, so the random value would be between 1 and 255, but playfield pixels go up to only 31 in bB's canned kernels, so 1 to 30 would ensure that the open (or turned-off) pfpixel would be at least 1 pixel from the edge of the playfield:

 

from

- ------------------------------

to

------------------------------ -

 

Michael

Link to comment
Share on other sites

This is probably a stupid way to do it, but I made a solid line on the hidden row using playfield variables, then I plop down a hole of any size I want and slide it into position. The player only sees the result, not the slide. Here's a simplistic, visible example of the slide:

 

http://www.atariage.com/forums/index.php?s...t&p=1528985

Link to comment
Share on other sites

Here's a quick example, probably not the best way to do it but it works:

 

 COLUPF=66 : COLUBK=130

start
pfhline 0 0 31 on
drawscreen
if !joy0fire then goto start

test
x=rand
if x< 1 || x>30 then goto test 
pfpixel x 0 off

display
drawscreen
if !joy0up then goto display
goto start

pl.bas.bin

Edited by Impaler_26
Link to comment
Share on other sites

A 1 pfpixel-wide gap is probably too narrow so here's an example for a 2 pfpixel-wide gap:

 

 COLUPF=28 : COLUBK=84

start
pfhline 0 0 31 on
drawscreen
if !joy0fire then goto start

test
x=rand
if x< 1  || x>29 then goto test
a=x+1 
pfpixel x 0 off
pfpixel a 0 off


display
drawscreen
if !joy0up then goto display
goto start

pl2.bas.bin

Edited by Impaler_26
Link to comment
Share on other sites

Edited: I can do what I was asking. Already tried it.

 

Now, how can I simplify the following code (and make it work):

 

 REM ** f is my timer to make the line scroll down by one every time **

f=f+1

REM ** g is implementing by one so the line moves down by one space **
g=g+1

REM ** if f=10 then it'll draw the first line **
if f=10 then pfhline 4 g 28 on

REM ** if f=20 then it'll clear the first line and draw the second **

if f=20 then pfhline 4 h 28 off: pfhline 4 g 28 on

REM ** if f=30 then.. well you get the idea.. so I won't comment each and every one of these **
if f=30 then pfhline 4 h 28 off: pfhline 4 g 28 on
if f=40 then pfhline 4 h 28 off: pfhline 4 g 28 on
if f=50 then pfhline 4 h 28 off: pfhline 4 g 28 on
if f=60 then pfhline 4 h 28 off: pfhline 4 g 28 on
if f=70 then pfhline 4 h 28 off: pfhline 4 g 28 on
if f=80 then pfhline 4 h 28 off: pfhline 4 g 28 on
if f=90 then pfhline 4 h 28 off: pfhline 4 g 28 on
if f=100 then pfhline 4 h 28 off: pfhline 4 g 28 on
if f=110 then pfhline 4 h 28 off: pfhline 4 g 28 on
if f=120 then pfhline 4 h 28 off: pfhline 4 g 28 on
if f=130 then pfhline 4 h 28 off: pfhline 4 g 28 on
if f=140 then pfhline 4 h 28 off: pfhline 4 g 28 on
if f=150 then pfhline 4 h 28 off: pfhline 4 g 28 on
if f=160 then pfhline 4 h 28 off: pfhline 4 g 28 on
if f=170 then pfhline 4 h 28 off: pfhline 4 g 28 on
if f=180 then pfhline 4 h 28 off: pfhline 4 g 28 on

REM ** the line is at the bottom so it needs to disappear.. reset f, g, and h to 0 so we can start this all over again and have another line come down at you. **
if f=181 then pfhline 4 h 28 off: f=0: g=0: h=0

REM ** set h=g. Remember g was what line coming down you were on. I need to set this to h because I want to use it above to clear the last line. g=current line, h=last line **
h=g

drawscreen

 

I am using f to control the speed of the line coming down. If I am to understand correct, f cannot be greater than 255? What do I do if I wanted a slower speed?

 

Also, my code doesn't work. What it's supposed to do is scroll a line down the screen which you must avoid. Eventually I want it to have two blocks missing at random next to each other that the player must go through, but for now I'll settle on getting this line to work.

 

Attached is my source.

panicattack_v101.bas

Edited by yuppicide
Link to comment
Share on other sites

I am using f to control the speed of the line coming down. If I am to understand correct, f cannot be greater than 255? What do I do if I wanted a slower speed?

That's correct-- f is a one-byte variable, so it can be 0 to 255, but that's it. However, you can use two variables (two bytes) to effectively get values of 0 to 65535 (e.g., 256 * a + b, where a and b are each 0 to 255). For instance, if you're adding 1 to f each time you draw the screen, such that f is a frame counter, then you could use f and h as the two variables, and do away with g. You could also add a line counter and a speed setting, and automatically speed up the lines as more of them fall, such as in the following example. It will start out nice and leisurely, but will gradually speed up to a maximum speed:

 

   COLUBK = $00 : rem ** black background

  COLUPF = $1A : rem ** yellow playfield

  scorecolor = $0E : rem ** white score

  rem ** f is the frame counter
  f = 0 : rem ** initialize the frame counter

  rem ** h is the horizontal line number
  h = 0 : rem ** initialize the horizontal line number

  rem ** s is the speed setting, in frames
  s = 20 : rem ** set the initial speed to 20 frames
  rem ** changing s to a smaller number will be faster
  rem ** changing s to a larger number will be slower

  rem ** l is the line counter (the number of lines that have fallen)
  l = 0 : rem ** initialize the line counter

  score = 0 : rem ** initialize the score (total lines fallen)

loop_1

  pfhline 4 h 28 on : rem ** draw a horizontal line

loop_2

  drawscreen : rem ** display the screen as currently defined

  f = f + 1 : if f <> s then loop_2 : rem ** display the current screen again

  f = 0 : rem ** reset f after every s frames

  pfhline 4 h 28 off : rem ** erase the old horizontal line

  h = h + 1 : rem ** increment the horizontal line number

  rem ** reset h if the line just scrolled off the screen
  rem ** and then increment the line counter and the score
  if h = 11 then h = 0 : l = l + 1 : score = score + 1

  rem ** speed up a little bit after every 10 lines
  if l = 10 then l = 0 : s = s - 1

  rem ** check the speed against some desired maximum setting
  if s < 3 then s = 3

  goto loop_1 : rem ** go draw the new horizontal line

Michael

Link to comment
Share on other sites

Thanks! Got your code to randomize working.

 

Is it me or does the random generator generate the same number every time in the same sequence? So far I'm trying out my game and it's the same thing everytime. I kind of know what is coming next. I've switched to 16-bit random now and that works great, but as far as regular random number generator it always generates the same exact thing for me in the same order.

Edited by yuppicide
Link to comment
Share on other sites

Thanks! Got your code to randomize working.

 

Is it me or does the random generator generate the same number every time in the same sequence? So far I'm trying out my game and it's the same thing everytime. I kind of know what is coming next. I've switched to 16-bit random now and that works great, but as far as regular random number generator it always generates the same exact thing for me in the same order.

You need to use some randomish event to help seed it some. Keep polling for random numbers while you are waiting for a person to start the game, then keep pulling for numbers while reset/fire is pressed until they release it. This will give you a more random starting point.

Link to comment
Share on other sites

Thanks! Got your code to randomize working.

 

Is it me or does the random generator generate the same number every time in the same sequence? So far I'm trying out my game and it's the same thing everytime. I kind of know what is coming next. I've switched to 16-bit random now and that works great, but as far as regular random number generator it always generates the same exact thing for me in the same order.

You need to use some randomish event to help seed it some. Keep polling for random numbers while you are waiting for a person to start the game, then keep pulling for numbers while reset/fire is pressed until they release it. This will give you a more random starting point.

yuppicide, the problem lies with the emulators. On an actual Atari, "rand" should give you a random starting number the first time you call it. But it's still a good idea to use some random event as kenfused suggested.

 

Once you get a random starting number, the actual sequence of numbers that will be returned by "rand" will always follow a specific cycle-- only the point at which you enter the cycle will be different. If you use the bB option for a 16-bit random number generator, you'll get a much longer cycle before the number sequence starts to repeat itself.

 

Michael

Link to comment
Share on other sites

Well, here is what I get.. I did the normal rand. What I would get is the same thing everytime.. no matter if I reset Stella or just exited and went back in. The openings in my PFHLINE were always in the same place and same exact order. It was so predictable I knew where to move.

 

With the 16bit, it seemed that it's always different.

 

yuppicide, the problem lies with the emulators. On an actual Atari, "rand" should give you a random starting number the first time you call it. But it's still a good idea to use some random event as kenfused suggested.

 

Once you get a random starting number, the actual sequence of numbers that will be returned by "rand" will always follow a specific cycle-- only the point at which you enter the cycle will be different. If you use the bB option for a 16-bit random number generator, you'll get a much longer cycle before the number sequence starts to repeat itself.

 

Michael

Link to comment
Share on other sites

yuppicide, the problem lies with the emulators. On an actual Atari, "rand" should give you a random starting number the first time you call it. But it's still a good idea to use some random event as kenfused suggested.

What bit of hardware is the random number coming from? Because it should be possible to correctly emulate this 'randomness' in Stella (ie, if it's from RAM, have the RAM randomized, etc).

Link to comment
Share on other sites

yuppicide, the problem lies with the emulators. On an actual Atari, "rand" should give you a random starting number the first time you call it. But it's still a good idea to use some random event as kenfused suggested.

What bit of hardware is the random number coming from? Because it should be possible to correctly emulate this 'randomness' in Stella (ie, if it's from RAM, have the RAM randomized, etc).

I *think* this is the bB startup code that "seeds" the rand variable with its initial value:

 

   lda #1
  sta CTRLPF
  ora INTIM
  sta rand

So if that's right, bB uses whatever value happens to be in INTIM when that section of startup code is being performed, but does "ora #1"* with it to make sure rand doesn't get seeded with 0 (since that would "break" rand).

 

* Note that if we leave out the "sta CTRLPF" instruction, the above code is equivalent to

 

   lda INTIM
  ora #1
  sta rand

So to more accurately emulate the randomness of the Atari, not only would you want to initialize the TIA registers and RAM addresses to random values, but you would also want to set the timer to a random value. Which raises the question, if the timer is random on powerup, does that mean the timer *interval* is also random? That is, if the timer would be counting down from whatever initial value it contained on powerup, could it potentially be counting down at any of the intervals (i.e., 1 cycle, 8 cycles, 64 cycles, or 1024 cycles)? Of course, once the timer counted down past 0, it would continue counting down at the 1-cycle rate.

 

Michael

Link to comment
Share on other sites

So to more accurately emulate the randomness of the Atari, not only would you want to initialize the TIA registers and RAM addresses to random values, but you would also want to set the timer to a random value. Which raises the question, if the timer is random on powerup, does that mean the timer *interval* is also random? That is, if the timer would be counting down from whatever initial value it contained on powerup, could it potentially be counting down at any of the intervals (i.e., 1 cycle, 8 cycles, 64 cycles, or 1024 cycles)? Of course, once the timer counted down past 0, it would continue counting down at the 1-cycle rate.

The random generation facilities in the latest versions of Stella are supposed to be more 'random' than before, but I think I've just found a bug. It seems while the 6532 RAM is getting a random sequence of values, it's always getting the same sequence. This should definitely not be happening. The timer value is correctly randomized, while the timer interval is always 1024 on startup. I'll have to look into the TIA registers, but for now I'm more concerned about the RAM issue.

 

EDIT: OK, I just looked into this, and it seems that all RAM in Stella (M6532 and carts) is being randomized with the same 'random' data. It wasn't an issue of correctly generating random numbers, but actually calling the method at the right time (each time the virtual system is 'hardware-reset'). So the current CVS code correctly randomized M6532 RAM, cart RAM, and timer value. Timer interval is always initialized to 1024, and the TIA registers are always initialized to 0. I'd like some feedback on those last two; should they be random as well??

Edited by stephena
Link to comment
Share on other sites

So the current CVS code correctly randomized M6532 RAM, cart RAM, and timer value. Timer interval is always initialized to 1024, and the TIA registers are always initialized to 0. I'd like some feedback on those last two; should they be random as well??

I'm no 2600 hardware guru, but it's my understanding that it powers up in a *completely* random state, meaning any and every byte or bit of the TIA registers, RIOT registers, RIOT RAM, 6507 lines, etc., are utterly unpredictable-- including any extra goodies on the cart, such as expansion RAM or bank-switching hotspots. Keep in mind, though, that when I say "my understanding," I really mean "my unverified assumptions based on what precious little official documentation or unofficial hearsay I happen to be aware of at the present moment," so take my utterances with a grain of salt the size of a salt lick, because I've just put an "ass" before "u" and "me." :) But if my ass is correct, I'd say the timer interval probably ought to be unpredictable, and the TIA registers surely ought to be unpredictable as well. With respect to the timer, I'm thinking along the lines of random values being shoved into the addresses that set the timer to a particular value and interval-- i.e., sort of as if the following code were being performed on powerup:

 

   LDX #unknown_value_1
  LDA #unknown_value_2
  STA TIM1T,X

I presume this also means the RIOT's timer *flag* might be on or off on powerup, just as each of the 6507's processor flags might be on or off, and just as the program counter could be pointing anywhere, etc.

 

For that matter, not only should the TIA registers be randomized, but any "hidden" TIA registers should be randomized as well (e.g., the extra copies of the player0 and player1 graphics registers, and anything else like that).

 

Any byte, bit, flag, counter, or connecting line could be set any which way, including not knowing if a particular R/W pin, interrupt pin, or chip select pin is set low or high, etc.

 

Michael

Edited by SeaGtGruff
Link to comment
Share on other sites

the program counter could be pointing anywhere

I should qualify some of my statements by clarifying that I'm referring to the situation upon initially powering up the 2600. Obviously, the 6507 processor does have a "reset" sequence that it goes through on powerup, and of course one thing it does during its "reset" sequence is load the lo-byte/hi-byte of the program counter from the "RESET" vector at addresses $FFFC/$FFFD, so the program counter won't be pointing "anywhere" after that's been done. And this is assuming the user hasn't "fried" the Atari by flicking the power switch on/off/on, which I take it can interfere with the 6507's "reset" sequence.

 

Michael

Link to comment
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Loading...
  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...