2015-07-22 2 views
-1

Я пытаюсь создать базовый шейдер Rim Lighting, но я думаю, что я делаю что-то неправильно.Проблема с GLSL Shader

Он должен выглядеть следующим образом: Rim Light Correct

Но я получаю это: Rim Light Wrong

Вот мой код:

Vertex:

  attribute vec3 AE_POSITION; 
      attribute vec2 AE_TEXCOORD; 
      attribute vec3 AE_NORMAL; 
      attribute vec3 AE_TANGENT; 

      uniform mat4 AE_MVP; 
      uniform mat4 AE_Model; 

      varying vec3 AE_WorldPosition; 
      varying vec3 AE_WorldNormal; 

      void main() { 
       AE_WorldPosition = (AE_Model * vec4(AE_POSITION, 1.0)).xyz; 
       AE_WorldNormal = normalize((AE_Model * vec4(AE_NORMAL, 1.0)).xyz); 

       gl_Position = AE_MVP * AE_Model * vec4(AE_POSITION, 1.0); 
      } 

Фрагмент:

  varying vec3 AE_WorldPosition; 
      varying vec3 AE_WorldNormal; 

      uniform vec3 AE_EyePos; 

      void main() { 
       vec3 v = normalize(AE_EyePos - AE_WorldPosition); 

       float rim = 1.0 - max(dot(v, AE_WorldNormal), 0.0); 
       rim = smoothstep(0.6, 1.0, rim); 
       vec3 finalRim = vec3(1.0, 0.0, 0.0) * vec3(rim); 

       gl_FragColor = vec4(finalRim, 1.0); 
      } 
+1

Можете ли вы объяснить основную идею обода освещения? Похоже, если части на ободе оживлены. Это правда? Потому что вы темнеете части, которые не находятся на ободе. Btw, я бы использовал 'abs (dot (...))' вместо 'max (dot (...), 0.0)' для вычисления 'rim'. И постоянный красный цвет в вашем коде должен быть цвет материала? –

+0

Оправа - яркая область кстати. Красный цвет должен быть цвета обода. – dcubix

+0

Значит, вы не должны добавлять 'finalRim' к результату другой модели освещения? Вы пробовали функцию 'abs'? Он должен дать вам только обод. В настоящее время все нормали, обращенные к камере, зажимаются до 'rim = 1'. –

ответ

0

Если я правильно, вы должны добавить красный, если q=dot(camera_direction,surface_normal) ряд 0.0

  • (не знаю, почему не белые, когда ваш пример имеет белый ободок)
  • вместо вы модулирующих красного цвета по всей поверхности

если это второй проход рендеринга

  • тогда ваш образ уже оказывается
  • так либо выбросить не фрагменты обода
  • или добавить текстуру исходного изображения и объединить в фрагменте
  • или использовать прозрачность и объединить

если это не многопроходная визуализация

  • , то где: цвета, текстуры, texcoords, ... для поверхностей?

Я хотел бы попробовать что-то вроде этого фрагмента:

float q,m=0.3f; 
vec4 col; // let this be surface computed color (does not matter for which of above approaches) 
vec3 v; 

// here compute the col if not multi pass 

v=normalize(AE_EyePos - AE_WorldPosition); 
q=dot(v, AE_WorldNormal); 
q*=q; // enhance rim gradient and also abs can use any even higher power... 
if (q<m) // rim size limit 
{ 
q=1.0-(q/m); 
col.xyz+=vec3(1.0,0.0,0.0)*q; // use = for multi pass 
} 
// else discard; // if multi pass 
gl_FragColor=col;