Captain Spazer Posted June 7, 2021 Share Posted June 7, 2021 I'm having a hard time thinking this setup out. My idea is this: There is a world where each screen is a place on a grid, and there is a variable that randomly picks a playfield for each of those screens in order to build the world. At the moment, the best I can think up in terms of a setup is having a variable for each possible room on the grid, and a variable that picks out a playfield for that room, so when the player goes to that room on that grid the roompicker variable picks a playfield, then I would need another variable I am guessing that keeps track of whether the room has been visited before so the screen remains what was picked the first time the player enters the room, but it is very variable heavy, and I have yet to figure out how the game will remember if the rooms have been visited or not. dim has_room_been_visited.s dim roompicker.c dim grid_room1.d dim grid_room2.e dim grid_room3.f dim grid_room4.g dim grid_room5.h dim grid_room6.i dim grid_room7.j dim grid_room8.k dim grid_room9.l dim grid_room10.m dim grid_room11.n dim grid_room12.o dim grid_room13.p dim grid_room14.q dim grid_room15.r I have another idea too that is a little less heavy on variables: Each time the player leaves the current room, the roompicker picks a playfield, and adds 1 to the add_new_room variable and subtracts 1 to the rooms_left_to_place variable. When the rooms_left_to_place variable reaches 0, no new rooms are placed. Still, need a way to remember if room has been visited or not so it remains static and does not randomize again. dim roompicker.a dim add_new_room.b dim rooms_left_to_place.c Any thoughts, insights or ideas? 1 Quote Link to comment Share on other sites More sharing options...
Captain Spazer Posted June 7, 2021 Author Share Posted June 7, 2021 (edited) Here is a functional tech demo code, when moving to the right, the game chooses between 4 different rooms, and the rooms remain static throughout the whole game. And it has a pretty good collision detection too. There are 3 rooms total you can move in by going to the right, head back to a previous room by going left. I am sure it can be optimized to save memory, as it's currently setup, it will require a lot of memory for a sizable map. Is there a way to have the screens share the playfield data so the game can pick from a pool of rooms without duplicating the playfields for each screen? rem Generated 06/06/2021 18:41:05 by Visual bB Version 1.0.0.554 rem ********************************** rem *<filename> * rem *<description> * rem *<author> * rem *<contact info> * rem *<license> * rem ********************************** set kernel_option no_blank_lines dim rand16 = z dim current_room_number = c dim p0_x = d dim p0_y = e dim room11_generator = f dim room12_generator = g dim room13_generator = h game_setup ballx = 80 : bally = 50 current_room_number = 10 room11_generator = (rand&3) + 1 room12_generator = (rand&3) + 1 room13_generator = (rand&3) + 1 setup_map main if current_room_number = 10 then playfield: XXXXXXXXXXXXX......XXXXXXXXXXXXX X............................... X............................... X............................... X............................... X............................... X............................... X............................... X............................... X............................... XXXXXXXXXXXXX......XXXXXXXXXXXXX end rem ROOM11 OPTIONS if current_room_number = 11 && room11_generator = 1 then playfield: XXXXXXXXXXXXX......XXXXXXXXXXXXX ................................ ................................ ................................ ........XXX...........XXX....... .........X.............X........ .........X.............X........ ........XXX...........XXX....... ................................ ................................ XXXXXXXXXXXXX......XXXXXXXXXXXXX end if current_room_number = 11 && room11_generator = 2 then playfield: XXXXXXXXXXXXX......XXXXXXXXXXXXX ................................ ................................ ................................ ................................ ................................ ................................ ................................ ................................ ................................ XXXXXXXXXXXXX......XXXXXXXXXXXXX end if current_room_number = 11 && room11_generator = 3 then playfield: XXXXXXXXXXXXX......XXXXXXXXXXXXX ................................ ................................ .........XX..........XX......... .......XXXXXX......XXXXXX....... ......XXXXXXXX....XXXXXXXX...... .......XXXXXX......XXXXXX....... .........XX..........XX......... ................................ ................................ XXXXXXXXXXXXX......XXXXXXXXXXXXX end if current_room_number = 11 && room11_generator = 4 then playfield: XXXXXXXXXXXXX......XXXXXXXXXXXXX ....XXXXXXXXX................... ....XXXXXXXXX................... ....XXXXXXXXX................... ...................XXXXXXXXX.... ...................XXXXXXXXX.... ...................XXXXXXXXX.... ....XXXXXXXXX................... ....XXXXXXXXX................... ....XXXXXXXXX................... XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX end rem ROOM12 OPTIONS if current_room_number = 12 && room12_generator = 1 then playfield: XXXXXXXXXXXXX......XXXXXXXXXXXXX ................................ ................................ ................................ ........XXX...........XXX....... .........X.............X........ .........X.............X........ ........XXX...........XXX....... ................................ ................................ XXXXXXXXXXXXX......XXXXXXXXXXXXX end if current_room_number = 12 && room12_generator = 2 then playfield: XXXXXXXXXXXXX......XXXXXXXXXXXXX ................................ ................................ ................................ ................................ ................................ ................................ ................................ ................................ ................................ XXXXXXXXXXXXX......XXXXXXXXXXXXX end if current_room_number = 12 && room12_generator = 3 then playfield: XXXXXXXXXXXXX......XXXXXXXXXXXXX ................................ ................................ .........XX..........XX......... .......XXXXXX......XXXXXX....... ......XXXXXXXX....XXXXXXXX...... .......XXXXXX......XXXXXX....... .........XX..........XX......... ................................ ................................ XXXXXXXXXXXXX......XXXXXXXXXXXXX end if current_room_number = 12 && room12_generator = 4 then playfield: XXXXXXXXXXXXX......XXXXXXXXXXXXX ....XXXXXXXXX................... ....XXXXXXXXX................... ....XXXXXXXXX................... ...................XXXXXXXXX.... ...................XXXXXXXXX.... ...................XXXXXXXXX.... ....XXXXXXXXX................... ....XXXXXXXXX................... ....XXXXXXXXX................... XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX end rem ROOM13 OPTIONS if current_room_number = 13 && room13_generator = 1 then playfield: XXXXXXXXXXXXX......XXXXXXXXXXXXX ................................ ................................ ................................ ........XXX...........XXX....... .........X.............X........ .........X.............X........ ........XXX...........XXX....... ................................ ................................ XXXXXXXXXXXXX......XXXXXXXXXXXXX end if current_room_number = 13 && room13_generator = 2 then playfield: XXXXXXXXXXXXX......XXXXXXXXXXXXX ................................ ................................ ................................ ................................ ................................ ................................ ................................ ................................ ................................ XXXXXXXXXXXXX......XXXXXXXXXXXXX end if current_room_number = 13 && room13_generator = 3 then playfield: XXXXXXXXXXXXX......XXXXXXXXXXXXX ................................ ................................ .........XX..........XX......... .......XXXXXX......XXXXXX....... ......XXXXXXXX....XXXXXXXX...... .......XXXXXX......XXXXXX....... .........XX..........XX......... ................................ ................................ XXXXXXXXXXXXX......XXXXXXXXXXXXX end if current_room_number = 13 && room13_generator = 4 then playfield: XXXXXXXXXXXXX......XXXXXXXXXXXXX ....XXXXXXXXX................... ....XXXXXXXXX................... ....XXXXXXXXX................... ...................XXXXXXXXX.... ...................XXXXXXXXX.... ...................XXXXXXXXX.... ....XXXXXXXXX................... ....XXXXXXXXX................... ....XXXXXXXXX................... XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX end CTRLPF = $31 ballheight = 8 COLUPF=$0E COLUBK=$00 scorecolor = $0E rem PLAYER CONTROLS p0_x = 0 if joy0left then p0_x = 255 if joy0right then p0_x = 1 ballx = ballx + p0_x p0_y = 0 if joy0up then p0_y = 255 if joy0down then p0_y = 1 bally = bally + p0_y if ballx > 130 then ballx = 10 : current_room_number = current_room_number + 1 : score = score + 1 if ballx < 10 then ballx = 130 : current_room_number = current_room_number - 1 : score = score - 1 if bally > 80 then bally = 10 : current_room_number = current_room_number + 10 if bally < 10 then bally = 80 : current_room_number = current_room_number - 10 drawscreen if collision(ball,playfield) then gosub knock_player_back goto main knock_player_back ballx = ballx - p0_x bally = bally - p0_y return goto main Edited June 7, 2021 by Captain Spazer Quote Link to comment Share on other sites More sharing options...
+Random Terrain Posted June 7, 2021 Share Posted June 7, 2021 Instead of a bunch of if-thens, you'd probably use on…goto. Quote Link to comment Share on other sites More sharing options...
+Karl G Posted June 7, 2021 Share Posted June 7, 2021 This is similar to a problem I've tried to figure out for myself. To get a simple repeating pattern, one can use the rand function, and you can even use an "unrand" function to get the previous number. The sequence of numbers would be the same within the same game, so you would get the same numbers going forward and backwards every time for a consistent world. This could be used e.g. to generate screens for a game like Pitfall where you can move right or left to get to new screens, but not up or down. Using rand and the reverse rand function depending on which direction you are going would get you consistent screens as you traverse the linear world without having to store the screen types in variables. Now, in the case of a grid, it becomes slightly more complicated. Going to new screens on the left and right are covered as described above, but for going up or down, you would run the rand or reverse rand function multiple times, depending on the number of columns. For example, if the world were an 8x8 grid, and the player moved down one screen, the rand function would be run 8 times, or the reverse rand in the case of the player going up one screen. This would be a lot of cycles used, but it might be okay since it would only need to happen for screen changes. If I get a chance, I may try to whip up a proof-of-concept demo to demonstrate this. Quote Link to comment Share on other sites More sharing options...
Captain Spazer Posted June 8, 2021 Author Share Posted June 8, 2021 Interesting idea! Quote Link to comment Share on other sites More sharing options...
+Karl G Posted June 8, 2021 Share Posted June 8, 2021 Here's an example that uses rand and unrand as described previously to generate an 8x8 world of 64 screens without having to use variables to track what type of screen is in what position. I also track whether each screen has been visited, and an eye icon shows at the bottom of the screen if the current screen has been previously visited (using the 6lives minikernel to display the icon). Bad graphics aside, I think this is more or less what you were going for? A couple of issues with this version: The screen type at each coordinate will vary from game to game, although it will remain the same throughout the same game. This may or may not be what you want. To make it consistent for every game, you can seed the random number generator with a specific number. If you use the rand function for anything else, it throws off the pattern with the rooms. This can be avoided by using a separate rand function, and a different rand variable that does not conflict with the built-in bB one. I'll update this demo to show how this can be done, as I imagine most games will want to make use of the rand function for more than just generating screens. Note: Not a WIP game for tracking purposes; just a code demo. openworld.bas openworld.bas.bin 9 Quote Link to comment Share on other sites More sharing options...
+Karl G Posted June 8, 2021 Share Posted June 8, 2021 Here's the version with a separate rand function and variable for cases where you would want to use rand for more than just generating screens. If you want the generated screens to be the same between game sessions, then you will want to change this line: bbrand = rand Set bbrand to any nonzero number at the beginning of the game to act as a number seed, and have the screen types be consistent from game to game. (No compiled version, since it is functionally the same as the previous demo) openworld-separate-rand.bas 4 Quote Link to comment Share on other sites More sharing options...
+Random Terrain Posted June 23, 2021 Share Posted June 23, 2021 On 6/8/2021 at 3:29 PM, Karl G said: Here's the version with a separate rand function and variable for cases where you would want to use rand for more than just generating screens. If you want the generated screens to be the same between game sessions, then you will want to change this line: bbrand = rand Set bbrand to any nonzero number at the beginning of the game to act as a number seed, and have the screen types be consistent from game to game. (No compiled version, since it is functionally the same as the previous demo) openworld-separate-rand.bas 7.5 kB · 7 downloads Just double checking. The variable bbrand is just for the rooms and rand works normally for everything else as always, right? If so I can use "dim rand16 = <var>" with normal bB, right? I could also adapt the program to work with the DPC+ kernel. Quote Link to comment Share on other sites More sharing options...
+Karl G Posted June 23, 2021 Share Posted June 23, 2021 3 hours ago, Random Terrain said: Just double checking. The variable bbrand is just for the rooms and rand works normally for everything else as always, right? If so I can use "dim rand16 = <var>" with normal bB, right? I could also adapt the program to work with the DPC+ kernel. Yes, all of that is correct. For DPC+ you would probably want to find another way of showing the screens that have been visited instead of the 6lives minikernel as well. 1 Quote Link to comment Share on other sites More sharing options...
+Random Terrain Posted July 7, 2021 Share Posted July 7, 2021 The bB page now has two example programs based on what Karl G posted in this thread: https://www.randomterrain.com/atari-2600-memories-batari-basic-commands.html#ex_8x8_world https://www.randomterrain.com/atari-2600-memories-batari-basic-commands.html#ex_16x16_world 2 1 Quote Link to comment Share on other sites More sharing options...
+Philsan Posted September 3, 2022 Share Posted September 3, 2022 @Karl G first of all, thanks for your code (and thanks to @Random Terrain for example program). I would like to design a world that always remains the same. Is there a way to make the rooms appear in a defined order? I don't need to track visited rooms. For example, room# 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 Thanks! Quote Link to comment Share on other sites More sharing options...
+Karl G Posted September 3, 2022 Share Posted September 3, 2022 2 hours ago, Philsan said: @Karl G first of all, thanks for your code (and thanks to @Random Terrain for example program). I would like to design a world that always remains the same. Is there a way to make the rooms appear in a defined order? I don't need to track visited rooms. For example, room# 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 Thanks! Sure. In that case you can just calculate the room number based on your coordinates in the grid. If you stared out at room 3, 4 the room number would just be 3 + (4 * 6). Since your width isn't a power of two, you would probably want to use a lookup table to get the value instead of actually doing the multiplication. Something like: CurrentRoom = RoomX + y_values[RoomY] data y_values 0, 6, 12, 18, 24, 30 end When you have your room number, you can use it in an index to look up e.g. that room's COLUBK and COLUPF values, or to use in a routine that uses on ... goto with the room number to set the appropriate playfield value for the room in question. Quote Link to comment Share on other sites More sharing options...
+Philsan Posted September 3, 2022 Share Posted September 3, 2022 Thank you very much, unfortunately it's too complicated for my bB skills. Isn't there a seed that makes the rooms appear in order? I would need a modification of Random Terrain's example. Quote Link to comment Share on other sites More sharing options...
+Karl G Posted September 3, 2022 Share Posted September 3, 2022 12 minutes ago, Philsan said: Thank you very much, unfortunately it's too complicated for my bB skills. Isn't there a seed that makes the rooms appear in order? I would need a modification of Random Terrain's example. No, I don't think there's a seed that can make the random number routine generate numbers in order like that. Perhaps I'm not understanding what you are trying to do. If you aren't wanting to use a random number generator, then the approach would be to decide for yourself what is in each of those rooms by having data or new playfields set based on the number you assign to the room yourself. No real trick to it other than that, unless I misunderstood what you are trying to do here. Quote Link to comment Share on other sites More sharing options...
+Philsan Posted September 3, 2022 Share Posted September 3, 2022 In Random Terrain's 8x8 example there are 64 rooms ; World limit constants. Change these based on world size. ; The default here is 8 x 8 (64 rooms). ; [The c stands for constant.] ; const _c_World_Limit_Top = 0 const _c_World_Limit_Bottom = 7 const _c_World_Limit_Left = 0 const _c_World_Limit_Right = 7 and the rooms have 32 different shapes ;``````````````````````````````````````````````````````````````` ; Jumps to the current scene to be displayed. ; on _CurrentScene goto __s0 __s1 __s2 __s3 __s4 __s5 __s6 __s7 __s8 __s9 __sA __sB __sC __sD __sE __sF __sG __sH __sI __sJ __sK __sL __sM __sN __sO __sP __sQ __sR __sS __sT __sU __sV If you select the same seed, rooms location remains the same. Therefore, to have an 6x6 world with 32 different rooms I think I could change this const _c_World_Limit_Top = 0 const _c_World_Limit_Bottom =5 const _c_World_Limit_Left = 0 const _c_World_Limit_Right = 5 select a seed and then find out where the following rooms are located in the grid with that seed on _CurrentScene goto __s0 __s1 __s2 __s3 __s4 __s5 __s6 __s7 __s8 __s9 __sA __sB __sC __sD __sE __sF __sG __sH __sI __sJ __sK __sL __sM __sN __sO __sP __sQ __sR __sS __sT __sU __sV Quote Link to comment Share on other sites More sharing options...
+Philsan Posted September 3, 2022 Share Posted September 3, 2022 Otherwise I should merge Random Terrain's example with @Atarius Maximus Space Dungeon. I only need a 5x5/6x6 map with 25/36 different rooms connected with each other. Quote Link to comment Share on other sites More sharing options...
Fort Apocalypse Posted September 4, 2022 Share Posted September 4, 2022 (edited) I'm a little late to the discussion, but when I've used unrand in the past for playfield generation, a problem I ran into, practically, was that I needed to use rand outside of the playfield generation. You could rand and unrand right away just to get a rand for something else without messing up the consistency of the rand for playfield generation, but then it's not really random, as it may give the same answer each time. Also, with unrand, you can neither use 16bit rand nor the DPC+ kernel. Edited September 4, 2022 by Fort Apocalypse Quote Link to comment Share on other sites More sharing options...
+Random Terrain Posted September 4, 2022 Share Posted September 4, 2022 27 minutes ago, Fort Apocalypse said: I'm a little late to the discussion, but when I've used unrand in the past for playfield generation, a problem I ran into, practically, was that I needed to use rand outside of the playfield generation. You could rand and unrand right away just to get a rand for something else without messing up the consistency of the rand for playfield generation, but then it's not really random, as it may give the same answer each time. Also, with unrand, you can neither use 16bit rand nor the DPC+ kernel. Before I moved, I was working on a DPC+ version of this example program and it was working fine. It just wasn't very fun yet. I need to work on it some more. Quote Link to comment Share on other sites More sharing options...
Fort Apocalypse Posted September 4, 2022 Share Posted September 4, 2022 (edited) 6 hours ago, Random Terrain said: Before I moved, I was working on a DPC+ version of this example program and it was working fine. It just wasn't very fun yet. I need to work on it some more. Oh ok. I was assuming it was the same as the one by RevEng here: which was: asm .unrand LDA rand ASL BCC unrandnoeor EOR #$69 unrandnoeor: STA rand STA temp6 RETURN end but the new one by Karl G looks to be a little different in a few ways. First, it's not storing in rand, but rather _RoomRand: ;``````````````````````````````````````````````````````````````` ; Special UnRand for rooms. ; __UnRand asm LDA _RoomRand ASL BCC __UnRand_no_eor EOR #$69 __UnRand_no_eor: STA _RoomRand STA _CurrentScene end And there's also: ;``````````````````````````````````````````````````````````````` ; Special Rand for rooms. ; __bBRand asm lda _RoomRand lsr bcc __bB_Rand_no_eor eor #$B4 __bB_Rand_no_eor sta _RoomRand end And, it seems to be using: set optimization inlinerand then it uses: ;``````````````````````````````````````````````````````````````` ; Makes better random numbers. ; dim rand16 = z And in the rand section of your page: https://www.randomterrain.com/atari-2600-memories-batari-basic-commands.html#rand it says: Quote The DPC+ kernel has an ARM-based 32-bit LFSR for random numbers, so “dim rand16 = <var>” should not be used when making games with the DPC+ kernel. Then, I see rand used once in the program, here: ;``````````````````````````````````````````````````````````````` ; Makes _RoomRand a random number. ; _RoomRand = rand : if !_RoomRand then _RoomRand = 1 So, in summary: It's not RevEng's unrand, which I was talking about, so I'm sorry for the confusion. inlinerand is being used. rand16 is being dimmed, even though it's DPC+. rand is only used once in the code. Could you or @Karl G maybe provide a short summary of what the asm is doing and whether and why inlinerand and rand16 are needed? Thanks! That would help in my understanding of this. Edited September 4, 2022 by Fort Apocalypse Quote Link to comment Share on other sites More sharing options...
+Random Terrain Posted September 4, 2022 Share Posted September 4, 2022 As usual, we remove "dim rand16 = <var>" when using DPC+. 1 Quote Link to comment Share on other sites More sharing options...
+Random Terrain Posted September 4, 2022 Share Posted September 4, 2022 I made a video of my DPC+ work in progress: youtu.be/0xWuy0AQTCA 5 Quote Link to comment Share on other sites More sharing options...
+Karl G Posted September 4, 2022 Share Posted September 4, 2022 6 hours ago, Fort Apocalypse said: It's not RevEng's unrand, which I was talking about, so I'm sorry for the confusion. inlinerand is being used. rand16 is being dimmed, even though it's DPC+. rand is only used once in the code. I think the inlinerand and dimming of rand16 were inherited from my first example, which was not DPC+, so you are right that they don't need to be used for the DPC+ example. Both examples are indeed using RevEng's unrand code, but as separate rand and unrand routines that don't actually use the rand variable to allow for rand-ing outside of the map generation without messing that up. The one use of actual rand in the example is just to populate the seed for those custom functions (making sure the seed isn't zero, which doesn't work). That line can be replaced with something that sets the variable to a static seed number instead in the range of 1 - 255 so that the map layout will be the same everytime. 1 1 Quote Link to comment Share on other sites More sharing options...
Fort Apocalypse Posted September 4, 2022 Share Posted September 4, 2022 (edited) 34 minutes ago, Karl G said: I think the inlinerand and dimming of rand16 were inherited from my first example, which was not DPC+, so you are right that they don't need to be used for the DPC+ example. Both examples are indeed using RevEng's unrand code, but as separate rand and unrand routines that don't actually use the rand variable to allow for rand-ing outside of the map generation without messing that up. The one use of actual rand in the example is just to populate the seed for those custom functions (making sure the seed isn't zero, which doesn't work). That line can be replaced with something that sets the variable to a static seed number instead in the range of 1 - 255 so that the map layout will be the same everytime. Thanks! And I thought that 8x8 example code was DPC+, but it wasn't; I got confused somehow. Edited September 4, 2022 by Fort Apocalypse Quote Link to comment Share on other sites More sharing options...
Lewis2907 Posted December 23, 2022 Share Posted December 23, 2022 Curios if RT made the DPC Demo version? I'm still tinkering with some stuff. Life has slowed down some now I can start to build some small games. Quote Link to comment Share on other sites More sharing options...
Recommended Posts
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.