Permalink
Browse files

Cleanup shader handling and fix normal shaders on older gl versions

Do not test texture available in shader, instead set it as a material
property, this should work on mac's and older OpenGL implementations.
  • Loading branch information...
1 parent 89ce99f commit bb7426ce2eee19d1537c71b4a0743a100571f1a9 @dgud dgud committed Jan 2, 2013
Showing with 90 additions and 42 deletions.
  1. +8 −6 shaders/envmap.fs
  2. +1 −1 shaders/envmap.vs
  3. +10 −9 shaders/hemilight.fs
  4. +1 −1 shaders/hemilight.vs
  5. +3 −3 src/wings.erl
  6. +15 −1 src/wings_draw.erl
  7. +20 −1 src/wings_material.erl
  8. +4 −2 src/wings_render.erl
  9. +7 −3 src/wings_shaders.erl
  10. +21 −15 src/wings_view.erl
View
@@ -16,6 +16,9 @@ const vec3 Yunitvec = vec3(0.0, 1.0, 0.0);
vec3 BaseColor = vec3(1.0, 1.0, 1.0);
float MixRatio = 0.3;
+uniform int UseDiffuseMap;
+uniform int UseNormalMap;
+
uniform sampler2D EnvMap;
uniform sampler2D NormalMap;
@@ -26,17 +29,16 @@ varying vec4 tangent;
vec3 LightPos = vec3(0.0, 10.0, 0.0);
vec3 get_normal() {
- ivec2 dim = textureSize(NormalMap, 0);
vec3 T = tangent.xyz;
- if((dim.x <= 1 && dim.y <= 1) || dot(T,T) < 0.1)
+ if(UseNormalMap == 0 || dot(T,T) < 0.1)
return normalize(Normal); // No normal-map or Tangents
//return normalize(tangent.xyz);
// Calc Bumped normal
vec3 N = normalize(Normal);
T = normalize(T);
T = normalize(T - dot(T, N) * N);
vec3 B = cross(T, N) * tangent.w;
- vec3 BumpMapNormal = texture(NormalMap, gl_TexCoord[0].xy).xyz;
+ vec3 BumpMapNormal = texture2D(NormalMap, gl_TexCoord[0].xy).xyz;
BumpMapNormal = 2.0 * BumpMapNormal - vec3(1.0, 1.0, 1.0);
vec3 NewNormal;
mat3 TBN = mat3(T, B, N);
@@ -48,8 +50,8 @@ vec3 get_normal() {
void main()
{
// Compute reflection vector
-
- vec3 reflectDir = reflect(EyeDir, get_normal());
+ vec3 normal = get_normal();
+ vec3 reflectDir = reflect(EyeDir, normal);
// Compute altitude and azimuth angles
@@ -78,7 +80,7 @@ void main()
vec3 envColor = vec3(texture2D(EnvMap, index));
// Add lighting to base color and mix
- float LightIntensity = max(dot(normalize(LightPos - EyeDir), Normal), 0.0);
+ float LightIntensity = max(dot(normalize(LightPos - EyeDir), normal), 0.0);
vec3 base = LightIntensity * BaseColor;
envColor = mix(envColor, BaseColor, MixRatio);
View
@@ -10,7 +10,7 @@
// See 3Dlabs-License.txt for license information
//
-in vec4 wings_tangent;
+attribute vec4 wings_tangent;
varying vec3 Normal;
varying vec3 EyeDir;
View
@@ -9,6 +9,9 @@ uniform vec3 LightPosition;
uniform vec3 SkyColor;
uniform vec3 GroundColor;
+uniform int UseDiffuseMap;
+uniform int UseNormalMap;
+
uniform sampler2D DiffuseMap;
uniform sampler2D NormalMap;
@@ -17,24 +20,17 @@ varying vec3 ecPosition;
varying vec4 color;
varying vec4 tangent;
-vec4 get_diffuse() {
- ivec2 dim = textureSize(DiffuseMap, 0);
- if(dim.x > 1 && dim.y > 1) return texture2D(DiffuseMap, gl_TexCoord[0].xy);
- else return vec4(1.0, 1.0, 1.0, 1.0);
-}
-
vec3 get_normal() {
- ivec2 dim = textureSize(NormalMap, 0);
vec3 T = tangent.xyz;
- if((dim.x <= 1 && dim.y <= 1) || dot(T,T) < 0.1)
+ if(UseNormalMap == 0 || dot(T,T) < 0.1)
return normalize(normal); // No normal-map or Tangents
//return normalize(tangent.xyz);
// Calc Bumped normal
vec3 N = normalize(normal);
T = normalize(T);
T = normalize(T - dot(T, N) * N);
vec3 B = cross(T, N) * tangent.w;
- vec3 BumpMapNormal = texture(NormalMap, gl_TexCoord[0].xy).xyz;
+ vec3 BumpMapNormal = texture2D(NormalMap, gl_TexCoord[0].xy).xyz;
BumpMapNormal = 2.0 * BumpMapNormal - vec3(1.0, 1.0, 1.0);
vec3 NewNormal;
mat3 TBN = mat3(T, B, N);
@@ -43,6 +39,11 @@ vec3 get_normal() {
return NewNormal;
}
+vec4 get_diffuse() {
+ if(UseDiffuseMap > 0) return texture2D(DiffuseMap, gl_TexCoord[0].xy);
+ else return vec4(1.0, 1.0, 1.0, 1.0);
+}
+
void main(void)
{
vec3 lightVec = normalize(LightPosition - ecPosition);
View
@@ -9,7 +9,7 @@
// See 3Dlabs-License.txt for license information
//
-in vec4 wings_tangent;
+attribute vec4 wings_tangent;
varying vec3 normal;
varying vec3 ecPosition;
View
@@ -1037,12 +1037,12 @@ info(#st{sel=[]}) ->
[],
Progs = get(light_shaders),
NumLights = wings_pref:get_value(number_of_lights),
- NumShaders = wings_pref:get_value(number_of_shaders),
+ ActiveSh = wings_pref:get_value(active_shader),
UseProg = (Progs /= undefined) and (NumLights == 2),
case UseProg of
true ->
- {_Prog,Name} = element(NumShaders, Progs),
- io_lib:format("Shader ~p of ~p: ~s ",[NumShaders,tuple_size(Progs),Name]);
+ {_Prog,Name} = element(ActiveSh, Progs),
+ io_lib:format("Shader ~p of ~p: ~s ",[ActiveSh,tuple_size(Progs),Name]);
false ->
[]
end;
View
@@ -996,6 +996,17 @@ draw_mat_faces(MatGroups, Mtab, ActiveColor) ->
DeApply(),
gl:popAttrib();
true ->
+ %% Setup shader for materials
+ Progs = get(light_shaders),
+ case get(light_shaders) of
+ undefined -> ignore;
+ _ ->
+ NumShaders = wings_pref:get_value(active_shader),
+ {Prog,_Name} = element(NumShaders, Progs),
+ put(active_shader, Prog),
+ %%gl:useProgram(Prog),
+ ok
+ end,
%% Show materials.
foreach(
fun({Mat,Type,Start,NumElements}) ->
@@ -1005,7 +1016,10 @@ draw_mat_faces(MatGroups, Mtab, ActiveColor) ->
gl:drawArrays(Type, Start, NumElements),
DeApply(),
gl:popAttrib()
- end, MatGroups)
+ end, MatGroups),
+ put(active_shader, 0),
+ %% gl:useProgram(0),
+ ok
end.
%%
View
@@ -464,6 +464,20 @@ apply_material(Name, Mtab, ActiveVertexColors) when is_atom(Name) ->
apply_normal_map(get_normal_map(Maps0)), %% Combine with vertex colors
DeApply.
+enable(true) -> 1;
+enable(false) -> 0.
+
+texture_var(diffuse) -> "UseDiffuseMap";
+texture_var(normal) -> "UseNormalMap".
+
+shader_texture(What, Enable) ->
+ case get(active_shader) of
+ Prog when is_integer(Prog), Prog > 0 ->
+ wings_gl:set_uloc(Prog, texture_var(What), enable(Enable));
+ _ ->
+ ok
+ end.
+
apply_texture(none) -> no_texture();
apply_texture(Image) ->
case wings_pref:get_value(show_textures) of
@@ -484,14 +498,18 @@ get_normal_map(Maps) ->
Map -> Map
end.
-apply_normal_map(none) -> ok;
+apply_normal_map(none) ->
+ shader_texture(normal, false),
+ ok;
apply_normal_map(TexId) ->
+ shader_texture(normal, true),
Bump = wings_image:bumpid(TexId),
gl:activeTexture(?GL_TEXTURE0 + ?NORMAL_MAP_UNIT),
gl:bindTexture(?GL_TEXTURE_2D, Bump),
gl:activeTexture(?GL_TEXTURE0).
apply_texture_1(Image, TxId) ->
+ shader_texture(diffuse, true),
gl:enable(?GL_TEXTURE_2D),
gl:texEnvi(?GL_TEXTURE_ENV, ?GL_TEXTURE_ENV_MODE, ?GL_MODULATE),
gl:bindTexture(?GL_TEXTURE_2D, TxId),
@@ -531,6 +549,7 @@ no_texture() ->
false ->
ok
end,
+ shader_texture(diffuse, false),
gl:disable(?GL_TEXTURE_2D),
gl:disable(?GL_ALPHA_TEST),
false.
View
@@ -673,11 +673,12 @@ enable_lighting(SceneLights) ->
wings_pref:get_value(number_of_lights) =:= 2,
case UseProg of
false ->
+ put(active_shader, 0),
gl:enable(?GL_LIGHTING);
true ->
- NumShaders = wings_pref:get_value(number_of_shaders),
+ NumShaders = wings_pref:get_value(active_shader),
{Prog,_Name} = element(NumShaders, Progs),
-
+ put(active_shader, Prog),
%% Reset color. Needed by some drivers.
%% We put it here and not in apply_material, because we
%% can't use some optimizations (e.g. reuse display lists)
@@ -688,6 +689,7 @@ enable_lighting(SceneLights) ->
disable_lighting() ->
gl:disable(?GL_LIGHTING),
+ put(active_shader, 0),
case get(light_shaders) /= undefined of
true -> gl:useProgram(0);
false -> ok
View
@@ -12,7 +12,7 @@
%%
-module(wings_shaders).
--export([init/0, read_texture/1]).
+-export([init/0, read_texture/1, set_active/1]).
-define(NEED_OPENGL, 1).
-include("wings.hrl").
@@ -40,12 +40,16 @@ init() ->
?CHECK_ERROR(),
gl:useProgram(0),
put(light_shaders, Programs),
- case wings_pref:get_value(number_of_shaders) > tuple_size(Programs) of
- true -> wings_pref:set_value(number_of_shaders, 1);
+ case wings_pref:get_value(active_shader) > tuple_size(Programs) of
+ true -> set_active(1);
false -> ok
end,
io:format("Using GPU shaders.\n").
+set_active(Id) ->
+ wings_pref:set_value(active_shader, Id),
+ ok.
+
read_texture(FileName) ->
Path = filename:join(wings_util:lib_dir(wings), "textures"),
NewFileName = filename:join(Path, FileName),
View
@@ -845,7 +845,7 @@ init() ->
wings_pref:set_default(show_edges, true),
wings_pref:set_default(show_backfaces, true),
wings_pref:set_default(number_of_lights, 1),
- wings_pref:set_default(number_of_shaders, 1),
+ wings_pref:set_default(active_shader, 1),
wings_pref:set_default(show_normals, false),
wings_pref:set_default(show_bb, true),
wings_pref:set_default(show_bb_center, true),
@@ -1195,21 +1195,27 @@ toggle_lights() ->
shader_set(N) ->
case wings_gl:support_shaders() of
true ->
- NumShaders = wings_pref:get_value(number_of_shaders),
+ NumShaders = wings_pref:get_value(active_shader),
NumProgs = tuple_size(get(light_shaders)),
- case N of
- next -> Shaders = case NumShaders of
- NumProgs -> 1;
- _ -> NumShaders+1
- end;
- prev -> Shaders = case NumShaders of
- 1 -> NumProgs;
- _ -> NumShaders-1
- end;
- _ -> Shaders = N
- end,
+ Shader = case N of
+ next -> case NumShaders of
+ NumProgs -> 1;
+ _ -> NumShaders+1
+ end;
+ prev -> case NumShaders of
+ 1 -> NumProgs;
+ _ -> NumShaders-1
+ end;
+ _ -> N
+ end,
+ %% Invalidate displaylists so that shader data get set correctly
+ %% for materials
+ wings_dl:map(fun(#dlo{proxy_data=PD}=D, _) ->
+ D#dlo{work=none,smooth=none,
+ proxy_data=wings_proxy:invalidate(PD, dl)}
+ end, []),
wings_pref:set_value(number_of_lights, 2),
- wings_pref:set_value(number_of_shaders, Shaders);
+ wings_shaders:set_active(Shader);
false ->
toggle_lights()
end.
@@ -1234,7 +1240,7 @@ shader_index() ->
case wings_pref:get_value(number_of_lights) of
2 ->
Progs = get(light_shaders),
- NumShaders = wings_pref:get_value(number_of_shaders),
+ NumShaders = wings_pref:get_value(active_shader),
{_Prog,Name} = element(NumShaders, Progs),
Name;
_ ->

0 comments on commit bb7426c

Please sign in to comment.