I'm trying to create procedurally generated terrain, it works but it just uses simple textures. The lower area below sea level I want to add a water material instead of a simple texture. How can I achieve this?
I am using the following code to procedurally generate terrain:
class_name HTerrainGenerator # Import classes const HTerrain: Resource = preload("res://addons/zylann.hterrain/hterrain.gd") const HTerrainData: Resource = preload("res://addons/zylann.hterrain/hterrain_data.gd") const HTerrainTextureSet: Resource = preload("res://addons/zylann.hterrain/hterrain_texture_set.gd") var grass_texture: Resource = load("res://Levels/Textures/T_ground_forest_grass_03_BC_H.PNG") var sand_texture: Resource = load("res://Levels/Textures/T_ground_sand_03_BC_H.PNG") var mud_texture: Resource = load("res://Levels/Textures/t_mud_01_d_1k.PNG") var terrian_seed: int = randi_range(0, 999999999999999999) func generate_terrain() -> HTerrain: # Create terrain resource and give it a size. # It must be either 513, 1025, 2049 or 4097. var terrain_data: HTerrainData = HTerrainData.new() terrain_data.resize(513) var noise: FastNoiseLite = FastNoiseLite.new() noise.seed = terrian_seed var noise_multiplier = 10.0 # affects the height of the terrain # Get access to terrain maps var heightmap: Image = terrain_data.get_image(HTerrainData.CHANNEL_HEIGHT) var normalmap: Image = terrain_data.get_image(HTerrainData.CHANNEL_NORMAL) var splatmap: Image = terrain_data.get_image(HTerrainData.CHANNEL_SPLAT) # Generate terrain maps for z in heightmap.get_height(): for x in heightmap.get_width(): # Generate height var h = noise_multiplier * noise.get_noise_2d(x, z) # Getting normal by generating extra heights directly from noise, # so map borders won't have seams in case you stitch them var h_right = noise_multiplier * noise.get_noise_2d(x + 0.1, z) var h_forward = noise_multiplier * noise.get_noise_2d(x, z + 0.1) var normal: Vector3 = Vector3(h - h_right, 0.1, h_forward - h).normalized() # Generate texture amounts var splat: Color = splatmap.get_pixel(x, z) var slope: float = 4.0 * normal.dot(Vector3.UP) - 2.0 # Sand on the slopes the higher value the more sand shows var sand_amount: float = clamp(2.1 - slope, 0.0, 1.0) # Mud below sea level var mud_amount: float = clamp(0.0 - h, 0.0, 1.0) splat = splat.lerp(Color(0,1,0,0), sand_amount) splat = splat.lerp(Color(0,0,1,0), mud_amount) heightmap.set_pixel(x, z, Color(h, 0, 0)) normalmap.set_pixel(x, z, HTerrainData.encode_normal(normal)) splatmap.set_pixel(x, z, splat) # Commit modifications so they get uploaded to the graphics card var modified_region: Rect2 = Rect2(Vector2(), heightmap.get_size()) terrain_data.notify_region_change(modified_region, HTerrainData.CHANNEL_HEIGHT) terrain_data.notify_region_change(modified_region, HTerrainData.CHANNEL_NORMAL) terrain_data.notify_region_change(modified_region, HTerrainData.CHANNEL_SPLAT) # Create texture set var texture_set: HTerrainTextureSet = HTerrainTextureSet.new() texture_set.set_mode(HTerrainTextureSet.MODE_TEXTURES) texture_set.insert_slot(-1) texture_set.set_texture(0, HTerrainTextureSet.TYPE_ALBEDO_BUMP, grass_texture) texture_set.insert_slot(-1) texture_set.set_texture(1, HTerrainTextureSet.TYPE_ALBEDO_BUMP, sand_texture) texture_set.insert_slot(-1) texture_set.set_texture(2, HTerrainTextureSet.TYPE_ALBEDO_BUMP, mud_texture) # Create terrain node var terrain: HTerrain = HTerrain.new() terrain.set_shader_type(HTerrain.SHADER_CLASSIC4_LITE) terrain.set_data(terrain_data) terrain.set_texture_set(texture_set) terrain.position = Vector3(0, 0, 0) return terrain func reload(terrain: HTerrain): terrain.data.reload() terrain.update_collider()