2013-02-09 2 views
0

Я хочу, чтобы металлическая поверхность с сильным отражением от солнца практически стала белой на свету. Он работал очень хорошо с двухпроходным рендерингом и добавлением, смешивающим второй проход (с почти белой текстурой и самым большим зеркальным светом) над первым (металлическим).Смешивание присадок для мультитектуры в opengl

Однако, для работы, я хочу, чтобы перейти к Мультитекстурированию, но нет такой вещи, как аддитивного смешивание там, только

glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); 
glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_DECAL); 
glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_BLEND); 
glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE); 

ни одна из этих работ в качестве добавки смеси. :-(

Мой второй вопрос:. Есть возможность иметь второй текстуры более блестящими, чем первая текстура на том же треугольнике кажется, что использование glMaterial перекрывает материал другой текстуры

мог решение, вероятно, было бы хорошим glTexEnvi - взломом, который бы имитировал эффект текстуры с сильной блеском?

+0

Непонятно, чего вы пытаетесь достичь здесь. Какую математику вы пытаетесь сделать? –

+0

математика цвет = tex1 + tex2 или даже цвет = tex1 + tex2 * 2 – Kenobi

+1

Рассматривали ли вы использование программируемого конвейера (шейдеров)? Проблемы, подобные вашим, были причиной, по которой он был создан в первую очередь @Kenobi. Если вы хотите просто добавить цвета, то «GL_ADD» должен быть доступной операцией. –

ответ

1

ребята, я, наконец, сделал это, написав шейдер для этой цели! Как ни странно, я, наконец, не использовал аддитивное смешение (просто измените одну строку в шейдере, чтобы добиться этого серьезно), но расширила идею, чтобы вторая текстура была зеркальной картой - так, чтобы ее текстура была видна только тогда, когда зеркальный свет попадает в него!

Большая часть эффекта может быть достигнуто за счет того, что мой собственный шейдер может просто обработать значение для зеркальности намного выше 1 - зло OpenGL будет обрезать его до 1, не спрашивая :-(

GLfloat mat_specular[] ={ 2, 2, 2, 1 }; glMaterialfv(GL_FRONT, GL_SPECULAR,mat_specular); //works here :-) 

вершинного шейдера:

vs = const_cast<char *>(
    "varying vec4 diffuse, ambient;" 
    "varying vec3 normal, lightDir, halfVector;" 
    "uniform float time;" 
    "void main(void){" 
     "normal = normalize(gl_NormalMatrix * gl_Normal);" //Transform Normal into Eye Space 
     "lightDir = normalize(vec3(gl_LightSource[0].position));" 
     "halfVector = normalize(gl_LightSource[0].halfVector.xyz);" 
     "diffuse = gl_FrontMaterial.diffuse * gl_LightSource[0].diffuse;" 
     "ambient = gl_FrontMaterial.ambient * gl_LightSource[0].ambient + gl_FrontMaterial.ambient * gl_LightModel.ambient;" 
     "gl_TexCoord[0] = gl_MultiTexCoord0;" 
     "gl_Position = ftransform();"  //Apply Changes 
    "}") ; 

И Fragment Shader:

fs =const_cast<char *>( 
    "uniform sampler2D tex1;" 
    "uniform sampler2D tex2;"  
    "varying vec4 diffuse,ambient;" 
    "varying vec3 normal, lightDir, halfVector;" 
    "void main() {" 
    "vec3 n,halfV,colortexel,colorfragment;" 
    "vec4 texel,specularmap;" 
    "float NdotL,NdotHV,alphatexel,alphafragment;\n" 
    "colorfragment = ambient.rgb;" //initialize color with ambient part 
    "alphafragment = gl_FrontMaterial.diffuse.a;" 
    "n = normalize(normal);" //copy to write 
    "NdotL = max(dot(normal, lightDir), -0.1);" 
    "specularmap = texture2D(tex2,gl_TexCoord[0].st);" //MUST Be started first! 
    "texel = texture2D(tex1,gl_TexCoord[0].st*2.0);" 

    "if (NdotL>=-0.1) {" 
     "colorfragment += diffuse.rgb * NdotL;" 
     "halfV = normalize(halfVector);" 
     "NdotHV = max (dot(n,halfV),0.0);" 
     "colorfragment += gl_FrontMaterial.specular.rgb * specularmap.rgb * gl_LightSource[0].specular.rgb * pow(NdotHV, gl_FrontMaterial.shininess);"    
    "}"   

    "colortexel = texel.rgb; alphatexel = texel.a;"   
    "gl_FragColor = vec4(colortexel * colorfragment, alphatexel * alphafragment);" 
    "}"); 

Это совсем не оптимизировано и на данный момент просто доказательство концепции без художественного мастерства, но вот результат:

Render без каких-либо шейдеров, но мультитектура на модуляции. Вы можете увидеть немного грязи на судне, но бедный зеркальная свет:

http://i.stack.imgur.com/8whUC.jpg

Вынесено с шейдерами - грязь есть, хотя и не ясно видно на этом снимке. Тяжелая зеркальная свет, который может быть даже укрепился рост зеркальности-значения в glMaterialfv:

http://i.stack.imgur.com/IpnTa.jpg

Вынесена с преувеличенной 4x блеском. Вы можете увидеть грязь текстуру теперь свечение:

http://i.stack.imgur.com/MPAm3.jpg

Остается один вопрос - почему на земле я не могу использовать gl_TexCoord (1) - результат не текстуры, но пиксель рендеринг артефактов, хотя мультитекстурирование отлично работает без шейдер. Любая помощь оценивается.

Смежные вопросы