Large terrain texturing. How to change pixel RGB value to texture?

BadSadCoderBadSadCoder Posts: 6Member

I have a question about large terrain texturing. I've heard about splat maps but I don't like 3/4 texture limit.
Lets say I have texture like the one I've attached. Kind of splat map. I would like shader to read RGB pixel value from my texturemap file and replace it with specific texture image. Those color=texture.png pairs would be defined:

swamp = (0,12,0)
sand = (213,12,0)
dirtpath = (123,123,123)
rock = (12,12,12)
riverbed = (123,0,19)

and so on.
I would also like that those textures to blend with each other... Simple blending nothing fancy. How one can achieve that?

I think that in Arma game series textures on terrains are made like that.

Comments

  • ZylannZylann Posts: 31Member
    edited May 19

    I work on a terrain plugin and I've been thinking about this for a while.
    The approach I may try soon is to use a texture array, and sample a slice of that array in a shader based on the index of the texture in the splatmap (so it would not be colors like you said, but more like a specialized splatmap painted with a specific tool, although you could feed in such color textures and generate a proper splatmap from it).
    That kind of splatmap would be different from the classic RGBA=1234, instead it would be R=textureIndex1, G=textureIndex2, B=blendingFactor. Then in the shader, color could simply be calculated like this:

    // Not true code, only as example
    
    vec3 index_and_weight = texture(u_terrain_splatmap, cell_position);
    
    float index1 = index_and_weight.r * 255;
    float index2 = index_and_weight.g * 255;
    float weight = index_and_weight.b;
    
    vec4 color1 = texture(u_texture_array, vec3(ground_uv, index1));
    vec4 color2 = texture(u_texture_array, vec3(ground_uv, index2));
    
    ALBEDO = mix(color1, color2, weight);
    

    The first downside I find so far is that you have to find out how to actually paint such a splatmap, because a constraint is that you cannot have a pixel of the ground that blends more than 2 textures. However, that can be largely enough if taken care of, and the texture array allows for up to 256 different textures, as long as your graphics card can handle it.

    I don't know if that helps, it's only theory, I have yet to actually try this out ;)

  • BadSadCoderBadSadCoder Posts: 6Member

    Maybe this will be more descriptive. Here's link to info about how it is done in Arma. I guess this whole different thing but... maybe this will be some help.
    https://community.bistudio.com/wiki/Layered_Terrain_Surface_Representation

    @Zylann said:
    I work on a terrain plugin and I've been thinking about this for a while.
    The approach I may try soon is to use a texture array, and sample a slice of that array in a shader based on the index of the texture in the splatmap (so it would not be colors like you said, but more like a specialized splatmap painted with a specific tool, although you could feed in such color textures and generate a proper splatmap from it).
    That kind of splatmap would be different from the classic RGBA=1234, instead it would be R=textureIndex1, G=textureIndex2, B=blendingFactor. Then in the shader, color could simply be calculated like this:

    // Not true code, only as example
    
    vec3 index_and_weight = texture(u_terrain_splatmap, cell_position);
    
    float index1 = index_and_weight.r * 255;
    float index2 = index_and_weight.g * 255;
    float weight = index_and_weight.b;
    
    vec4 color1 = texture(u_texture_array, vec3(ground_uv, index1));
    vec4 color2 = texture(u_texture_array, vec3(ground_uv, index2));
    
    ALBEDO = mix(color1, color2, weight);
    

    The first downside I find so far is that you have to find out how to actually paint such a splatmap, because a constraint is that you cannot have a pixel of the ground that blends more than 2 textures. However, that can be largely enough if taken care of, and the texture array allows for up to 256 different textures, as long as your graphics card can handle it.

    I don't know if that helps, it's only theory, I have yet to actually try this out ;)

  • ZylannZylann Posts: 31Member

    It doesnt seem like the Arma link describe how they actually render this internally. It mostly explains how to make a map from a user/modder point of view.

    In other news, I just made my idea work :D https://github.com/Zylann/godot_heightmap_plugin/issues/10#issuecomment-631078641

    Now I think what Arma does more likely is a variation of this technique, just with more indexes and more blend weights (see footnotes in the wiki page).

Leave a Comment

BoldItalicStrikethroughOrdered listUnordered list
Emoji
Image
Align leftAlign centerAlign rightToggle HTML viewToggle full pageToggle lights
Drop image/file