GLSL multitexture problem

Hi.

I wanted to draw a several textures on my box, such that one wouldn’t interfere to the other. I’m working with GLSL for the first time. Help me please…

[java]

//j3md file

MaterialDef Plain Texture {



MaterialParameters {

Texture2D m_Grass

Texture2D m_Ground

}



Technique {

VertexShader GLSL100: refs/LocatedTexture.vert

FragmentShader GLSL100: refs/LocatedTexture.frag



WorldParameters {

WorldViewProjectionMatrix

}

}

}

[/java]

[java]

//vert file

uniform mat4 g_WorldViewProjectionMatrix;



attribute vec3 inPosition;

attribute vec2 inTexCoord;



varying vec2 texCoord;



void main(){

gl_Position = g_WorldViewProjectionMatrix * vec4(inPosition, 1.0);

texCoord = inTexCoord;

}

[/java]

[java]

//frag file

varying vec2 texCoord;



uniform sampler2D m_Grass;

uniform sampler2D m_Ground;



void main(){

vec2 coord_grass = vec2(texCoord.x * 2.0, texCoord.y);

vec2 coord_ground = vec2(texCoord.x * 2.0 - 1.0, texCoord.y);



// gl_FragColor = texture2D(m_Grass, coord_grass) + texture2D(m_Ground, coord_ground);

gl_FragColor = texture2D(m_Grass, coord_grass) * texture2D(m_Ground, coord_ground);

}

[/java]

tkey said:
such that one wouldn’t interfere to the other.

What do you mean by that? you want a different texture on each face, or each texture on half the cube, or what?

Each texture on half of each face of the cube.

Just create a UV texture in blender or use shaders.

I wanted to do it dynamically. If I’m able to do this, I’ll be able to do the thing I’ve planned.

I have an array for a map

[java]

1 1 1 1 1 1 1 1 1 1 1

1 0 0 0 0 0 0 0 0 0 1

1 0 0 0 0 0 0 0 0 0 1

1 0 0 0 0 0 0 0 0 0 1

1 0 0 0 1 1 1 0 0 0 1

1 0 0 0 1 1 1 0 0 0 1

1 0 0 0 1 1 1 0 0 0 1

1 0 0 0 0 0 0 0 0 0 1

1 0 0 0 0 0 0 0 0 0 1

1 0 0 0 0 0 0 0 0 0 1

1 1 1 1 1 1 1 1 1 1 1

[/java]

1s are grass and 2s are ground.

My idea is to create a thin box some kind of terrain, and place there grass and ground textures to material.

Map can be changed(bigger or smaller). I can create different boxes for different texture, but for some reasons it is not quite right, i think.

Then you will have to delve into the world of texture coordinates and shaders I’m afraid.

oh ok, you are close in fact.



what you have to do is to introduce some kind of alpha map of what to show and what to hide.

From the pattern you describe it would be white in the center and on the borders, and black everywhere else.

What you can do is create a gray scale map with correct repartition of the grass and ground

and in your shader use :



gl_FragColor =mix( texture2D(m_Grass, texCoord) , texture2D(m_Ground, texCoord),texture2D(m_AlphaMap, texCoord));



the mix function mix 2 values according to the 3rd parameter.

let’s say you have a green pixel for grass and a brown pixel for ground and that your alpha map contains a 0.7 value.

the result will be 70% green and 30% brown.



To go further and to spend a little less memory you can store the alpha value in the alpha channel of one of your map (you’ll need to do that with an image editor like gimp or Photoshop or…anything that can write alpha :p)

then the code will be



vec4 grassColor=texture2D(m_Grass, texCoord);

vec4 groundColor=texture2D(m_Ground, texCoord);

gl_FragColor =mix(grassColor, groundColor,grassColor.a);



That is of course if you stored alpha in the grass texture



Hope that helps.



PS : I don’t know if you read it, but if you are new to GLSL and JME i recommend reading this doc https://wiki.jmonkeyengine.org/legacy/doku.php/jme3:advanced:jme3_shaders. There is no particular solution to your problem in it, but it explains some basics that could help you.

1 Like

Thank you very much.

I did it!!! The main thing is not to forget to type [java]texGrass.setWrap(WrapMode.BorderClamp);[/java].

But I’ve got another problem. GLSL can’t create large arrays, so I can’t create a map 100 x 100. I think better to use terrain and scale it in y axis to make it flat.

Thanks for help.

Why do you need large array?

you must hold the alpha values in a texture

I’m not sure what do you mean. How is it to hold the alpha values???:?

erm maybe that’s not the correct word, i’m French you know :stuck_out_tongue:



I mean alpha values must be stored in a texture, not in an array.

Tkey, a texture is basically an array, lots of values in a 2-dimensional matrix.

I’m sorry, I’ve got no idea how to do it…

PS:

Greetings, I’m Kazakh!:smiley:

hehe so there is no way we don’t understand each other :stuck_out_tongue:



To create the alpha map you need to grab your favorite image editor and do something like that



this is according to the array you wrote 3 posts ago (actually this texture might work you can try)



you’ll need to pass the texture to the shader like you did with the m_grass and m_ground, call it m_AlphaMap

and use this line :



gl_FragColor =mix( texture2D(m_Grass, texCoord) , texture2D(m_Ground, texCoord),texture2D(m_AlphaMap, texCoord));





white areas on the alpha map should display the grass texture, black areas the ground

Oh, thank, but you know, in fact we misunderstood each other (I think).

My idea is to store in some text file all info that i have about my game map(trees, walls and etc.). Grass and ground probably is not only textures that i will use in each map. Then, for each map i’ll have to have one text file for info and one alpha map. Then to have several maps i’ll have to draw several alpha maps and calculate there small peaces. I think it is easyer to have just text files and good dinamical algorithm. So, will be able to create them fast. Futhermore I want to make my gamer to create their map by themselves(if there will be any audience of gamers, this is my course work, so it is essential to have something to show for good grading).

Thank you once more, I’m sure i’ll use it somewhere else. x )

oh ok!

Well if you found a way to do what you want, that’s what matters :wink: