diff options
author | Ton Roosendaal <ton@blender.org> | 2005-12-09 18:14:32 +0300 |
---|---|---|
committer | Ton Roosendaal <ton@blender.org> | 2005-12-09 18:14:32 +0300 |
commit | 485dd1d37673d229db9062d8cad98e624d79c8ec (patch) | |
tree | 4594dc9f61d65286c430a304ba11742f1acea818 /source/blender/render | |
parent | c492729b3a0d52ae01ee67e5ad92bdb02f6585df (diff) |
Orange; WIP commit for inclusion of "Tangent" vector in rendering.
This first implementation only supports it for Meshes with UV maps, and
only tangents in V direction.
Tangent diffuse:
http://www.blender.org/bf/0001_0080.avi
Tangent spec, diffuse, and bump:
http://www.blender.org/bf/20001_0080.avi
NOTE: since UV coordinates are still very badly subsurfed, this won't work
well for subsurf meshes... on the todo.
On the todo;
- generate tangents for meshes without UV (with some options)
- use tangents from Curve/Surface
- add the Ashkimin shader from tracker
-----
Important bugfix; curves didn't render anymore since yesterday. :)
Diffstat (limited to 'source/blender/render')
-rw-r--r-- | source/blender/render/intern/source/rendercore.c | 59 | ||||
-rw-r--r-- | source/blender/render/intern/source/renderdatabase.c | 3 | ||||
-rw-r--r-- | source/blender/render/intern/source/texture.c | 29 |
3 files changed, 63 insertions, 28 deletions
diff --git a/source/blender/render/intern/source/rendercore.c b/source/blender/render/intern/source/rendercore.c index 3ca504e2ce4..0d6e141df5f 100644 --- a/source/blender/render/intern/source/rendercore.c +++ b/source/blender/render/intern/source/rendercore.c @@ -1636,7 +1636,14 @@ void shade_lamp_loop(ShadeInput *shi, ShadeResult *shr) if(vlr->flag & R_TANGENT) { float cross[3]; Crossf(cross, lv, vn); - Crossf(vnor, cross, shi->vn); + Crossf(vnor, cross, vn); + vnor[0]= -vnor[0];vnor[1]= -vnor[1];vnor[2]= -vnor[2]; + vn= vnor; + } + else if(ma->mode & MA_TANGENT_V) { + float cross[3]; + Crossf(cross, lv, shi->tang); + Crossf(vnor, cross, shi->tang); vnor[0]= -vnor[0];vnor[1]= -vnor[1];vnor[2]= -vnor[2]; vn= vnor; } @@ -1685,7 +1692,9 @@ void shade_lamp_loop(ShadeInput *shi, ShadeResult *shr) } vn= shi->vn; // bring back original vector, we use special specular shaders for tangent - + if(ma->mode & MA_TANGENT_V) + vn= shi->tang; + /* shadow and spec, (lampdist==0 outside spot) */ if(lampdist> 0.0) { @@ -1762,15 +1771,15 @@ void shade_lamp_loop(ShadeInput *shi, ShadeResult *shr) float specfac; if(ma->spec_shader==MA_SPEC_PHONG) - specfac= Phong_Spec(vn, lv, view, shi->har, vlr->flag & R_TANGENT); + specfac= Phong_Spec(vn, lv, view, shi->har, (vlr->flag & R_TANGENT) || (ma->mode & MA_TANGENT_V)); else if(ma->spec_shader==MA_SPEC_COOKTORR) - specfac= CookTorr_Spec(vn, lv, view, shi->har, vlr->flag & R_TANGENT); + specfac= CookTorr_Spec(vn, lv, view, shi->har, (vlr->flag & R_TANGENT) || (ma->mode & MA_TANGENT_V)); else if(ma->spec_shader==MA_SPEC_BLINN) - specfac= Blinn_Spec(vn, lv, view, ma->refrac, (float)shi->har, vlr->flag & R_TANGENT); + specfac= Blinn_Spec(vn, lv, view, ma->refrac, (float)shi->har, (vlr->flag & R_TANGENT) || (ma->mode & MA_TANGENT_V)); else if(ma->spec_shader==MA_SPEC_WARDISO) - specfac= WardIso_Spec( vn, lv, view, ma->rms, vlr->flag & R_TANGENT); + specfac= WardIso_Spec( vn, lv, view, ma->rms, (vlr->flag & R_TANGENT) || (ma->mode & MA_TANGENT_V)); else - specfac= Toon_Spec(vn, lv, view, ma->param[2], ma->param[3], vlr->flag & R_TANGENT); + specfac= Toon_Spec(vn, lv, view, ma->param[2], ma->param[3], (vlr->flag & R_TANGENT) || (ma->mode & MA_TANGENT_V)); /* area lamp correction */ if(lar->type==LA_AREA) specfac*= inp; @@ -1979,9 +1988,25 @@ void shade_input_set_coords(ShadeInput *shi, float u, float v, int i1, int i2, i shi->dyno[2]= dl*n3[2]-shi->dyuv[0]*n1[2]-shi->dyuv[1]*n2[2]; } + + if(mode & MA_TANGENT_V) { + float *s1, *s2, *s3; + + s1= RE_vertren_get_tangent(v1, 0); + s2= RE_vertren_get_tangent(v2, 0); + s3= RE_vertren_get_tangent(v3, 0); + if(s1 && s2 && s3) { + shi->tang[0]= (l*s3[0] - u*s1[0] - v*s2[0]); + shi->tang[1]= (l*s3[1] - u*s1[1] - v*s2[1]); + shi->tang[2]= (l*s3[2] - u*s1[2] - v*s2[2]); + } + else shi->tang[0]= shi->tang[1]= shi->tang[2]= 0.0f; + } } else { VECCOPY(shi->vn, shi->facenor); + if(mode & MA_TANGENT_V) + shi->tang[0]= shi->tang[1]= shi->tang[2]= 0.0f; } /* texture coordinates. shi->dxuv shi->dyuv have been set */ @@ -2100,20 +2125,6 @@ void shade_input_set_coords(ShadeInput *shi, float u, float v, int i1, int i2, i shi->dyuv[0]= 2.0*(dl*uv3[0]-duv[0]*uv1[0]-duv[1]*uv2[0]); shi->dyuv[1]= 2.0*(dl*uv3[1]-duv[0]*uv1[1]-duv[1]*uv2[1]); } -#if 0 - { /* tangent derived from UV, comes back later! (ton) */ - //float s1= uv2[0] - uv1[0]; - //float s2= uv3[0] - uv1[0]; - float t1= uv2[1] - uv1[1]; - float t2= uv3[1] - uv1[1]; - - shi->vn[0]= (t2 * (v2->co[0]-v1->co[0]) - t1 * (v3->co[0]-v1->co[0])); - shi->vn[1]= (t2 * (v2->co[1]-v1->co[1]) - t1 * (v3->co[1]-v1->co[1])); - shi->vn[2]= (t2 * (v2->co[2]-v1->co[2]) - t1 * (v3->co[2]-v1->co[2])); - Normalise(shi->vn); - vlr->flag |= R_TANGENT; - } -#endif if(mode & MA_FACETEXTURE) { if((mode & (MA_VERTEXCOL|MA_VERTEXCOLP))==0) { shi->vcol[0]= 1.0; @@ -2176,6 +2187,12 @@ void shade_input_set_coords(ShadeInput *shi, float u, float v, int i1, int i2, i } else shi->stress= 0.0f; } + if(texco & TEXCO_TANGENT) { + if((mode & MA_TANGENT_V)==0) { + /* just prevent surprises */ + shi->tang[0]= shi->tang[1]= shi->tang[2]= 0.0f; + } + } } else { shi->rad[0]= shi->rad[1]= shi->rad[2]= 0.0; diff --git a/source/blender/render/intern/source/renderdatabase.c b/source/blender/render/intern/source/renderdatabase.c index 4c7453bf1b1..d37c73dc932 100644 --- a/source/blender/render/intern/source/renderdatabase.c +++ b/source/blender/render/intern/source/renderdatabase.c @@ -160,6 +160,7 @@ float *RE_vertren_get_strand(VertRen *ver, int verify) return strand + (ver->index & 255)*RE_STRAND_ELEMS; } +/* needs calloc */ float *RE_vertren_get_tangent(VertRen *ver, int verify) { float *tangent; @@ -168,7 +169,7 @@ float *RE_vertren_get_tangent(VertRen *ver, int verify) tangent= R.vertnodes[nr].tangent; if(tangent==NULL) { if(verify) - tangent= R.vertnodes[nr].tangent= MEM_mallocN(256*RE_TANGENT_ELEMS*sizeof(float), "tangent table"); + tangent= R.vertnodes[nr].tangent= MEM_callocN(256*RE_TANGENT_ELEMS*sizeof(float), "tangent table"); else return NULL; } diff --git a/source/blender/render/intern/source/texture.c b/source/blender/render/intern/source/texture.c index 38936ec89fa..dff275e0a71 100644 --- a/source/blender/render/intern/source/texture.c +++ b/source/blender/render/intern/source/texture.c @@ -1444,6 +1444,9 @@ void do_material_tex(ShadeInput *shi) else if(mtex->texco==TEXCO_NORM) { co= shi->orn; dx= shi->dxno; dy= shi->dyno; } + else if(mtex->texco==TEXCO_TANGENT) { + co= shi->tang; dx= shi->dxno; dy= shi->dyno; + } else if(mtex->texco==TEXCO_GLOB) { co= shi->gl; dx= shi->dxco; dy= shi->dyco; } @@ -1690,14 +1693,28 @@ void do_material_tex(ShadeInput *shi) fact= Tnor*tex->norfac; if(fact>1.0) fact= 1.0; else if(fact<-1.0) fact= -1.0; facm= 1.0- fact; - shi->vn[0]= facm*shi->vn[0] + fact*texres.nor[0]; - shi->vn[1]= facm*shi->vn[1] + fact*texres.nor[1]; - shi->vn[2]= facm*shi->vn[2] + fact*texres.nor[2]; + if(shi->mat->mode & MA_TANGENT_V) { + shi->tang[0]= facm*shi->tang[0] + fact*texres.nor[0]; + shi->tang[1]= facm*shi->tang[1] + fact*texres.nor[1]; + shi->tang[2]= facm*shi->tang[2] + fact*texres.nor[2]; + } + else { + shi->vn[0]= facm*shi->vn[0] + fact*texres.nor[0]; + shi->vn[1]= facm*shi->vn[1] + fact*texres.nor[1]; + shi->vn[2]= facm*shi->vn[2] + fact*texres.nor[2]; + } } else { - shi->vn[0]+= Tnor*tex->norfac*texres.nor[0]; - shi->vn[1]+= Tnor*tex->norfac*texres.nor[1]; - shi->vn[2]+= Tnor*tex->norfac*texres.nor[2]; + if(shi->mat->mode & MA_TANGENT_V) { + shi->tang[0]+= Tnor*tex->norfac*texres.nor[0]; + shi->tang[1]+= Tnor*tex->norfac*texres.nor[1]; + shi->tang[2]+= Tnor*tex->norfac*texres.nor[2]; + } + else { + shi->vn[0]+= Tnor*tex->norfac*texres.nor[0]; + shi->vn[1]+= Tnor*tex->norfac*texres.nor[1]; + shi->vn[2]+= Tnor*tex->norfac*texres.nor[2]; + } } Normalise(shi->vn); |