Topic was automatically imported from the old Question2Answer platform.
Asked By
slightly_seasoned
I’m following NAD LABS’ tutorial on procedural tile generation, & came across a problem. Sometimes, when I play the scene, all of the tiles are grass tiles, & none of them are water tiles. I thought of scanning the screen & seeing if the amount of water tiles are < insert random integer here, then restart the scene until there’s a reasonable amount of water tiles on the screen. Can anyone tell me how to scan the screen & how to get a tile’s ID?
BTW here’s the code I’m using:
extends Node2D
var width = 60
var height = 34
onready var tile_map = get_node("ProceduralWorldTileMap")
var open_simplex_noise = OpenSimplexNoise.new()
func _ready():
randomize()
open_simplex_noise.seed = randi()
open_simplex_noise.octaves = 5
_generate_map()
func _generate_map():
for x in width:
for y in height:
var map = floor(abs(open_simplex_noise.get_noise_2d(x, y) * 3))
tile_map.set_cell(x, y, map)
So what you’re trying to accomplish and the method you’re using to generate a random tile map are conflicting. If you have 1 water tile and 1 grass tile in your TileSet it’s equally likely that you’ll get a grass or a water tile. I would suggest making your map generation function more general first. Then you can add more water tiles to your TileSet to make them have a higher probability of occurring. So if you have 3 water tiles and 1 grass in your TileSet, your code is 3x more likely to select a water tile than a grass tile.
func _generate_map():
var tile_set = tile_map.tile_set
var tile_types = tile_set.get_tiles_ids()
var max_index = tile_types.size() - 1
for x in width:
for y in height:
var map = floor(abs(open_simplex_noise.get_noise_2d(x, y) * max_index))
tile_map.set_cell(x, y, map)
If you insist on the more brute force method of having a minimum number of water tiles on the map then this will do that but you’ll lose the niceness of the open_simplex_noise generation and the water tiles will look more randomly thrown in there:
func _generate_map():
var water_tile_index = 2 # whatever the index of your water tile index is
var water_tiles_generated = []
var minimum_number_of_water_tiles = 30
var tile_set = tile_map.tile_set
var tile_types = tile_set.get_tiles_ids()
var max_index = tile_types.size() - 1
for x in width:
for y in height:
var map = floor(abs(open_simplex_noise.get_noise_2d(x, y) * max_index))
tile_map.set_cell(x, y, map)
if map == water_tile_index:
water_tiles_generated.append(Vector2(x,y))
while water_tiles_generated.size() < minimum_number_of_water_tiles:
randomize()
var random_vector = Vector2(randi() % width + 1, randi() % height +1)
if random_vector in water_tiles_generated:
continue
else:
tile_map.set_cell(random_vector.x, random_vector.y, water_tile_index)
water_tiles_generated.append(random_vector)