VideoTexture module.
[blender-staging.git] / source / gameengine / VideoTexture / FilterNormal.h
1 /* $Id$
2 -----------------------------------------------------------------------------
3 This source file is part of blendTex library
4
5 Copyright (c) 2007 The Zdeno Ash Miklas
6
7 This program is free software; you can redistribute it and/or modify it under
8 the terms of the GNU Lesser General Public License as published by the Free Software
9 Foundation; either version 2 of the License, or (at your option) any later
10 version.
11
12 This program is distributed in the hope that it will be useful, but WITHOUT
13 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
14 FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details.
15
16 You should have received a copy of the GNU Lesser General Public License along with
17 this program; if not, write to the Free Software Foundation, Inc., 59 Temple
18 Place - Suite 330, Boston, MA 02111-1307, USA, or go to
19 http://www.gnu.org/copyleft/lesser.txt.
20 -----------------------------------------------------------------------------
21 */
22
23 #if !defined FILTERNORMAL_H
24 #define FILTERNORMAL_H
25
26 #include "Common.h"
27
28 #include "FilterBase.h"
29
30
31 // scale constants for normals
32 const float depthScaleKoef = 255.0;
33 const float normScaleKoef = float(depthScaleKoef / 2.0);
34
35
36 /// pixel filter for normal mapping
37 class FilterNormal : public FilterBase
38 {
39 public:
40         /// constructor
41         FilterNormal (void);
42         /// destructor
43         virtual ~FilterNormal (void) {}
44
45         /// get index of color used to calculate normals
46         unsigned short getColor (void) { return m_colShift >> 3; }
47         /// set index of color used to calculate normals
48         void setColor (unsigned short colIdx);
49
50         /// get depth
51         float getDepth (void) { return m_depth; }
52         /// set depth
53         void setDepth (float depth);
54
55 protected:
56         /// depth of normal relief
57         float m_depth;
58         /// scale to calculate normals
59         float m_depthScale;
60
61         /// shift to used color component
62         unsigned short m_colShift;
63
64         /// filter pixel, source int buffer
65         template <class SRC> unsigned int tFilter (SRC * src, short x, short y,
66                 short * size, unsigned int pixSize, unsigned int val = 0)
67         {
68                 // get value of required color
69                 int actPix = int((val >> m_colShift) & 0xFF);
70                 // get upper and left pixel from actual pixel
71                 int upPix = y > 0 ? int((convertPrevious(src - pixSize * size[0], x, y - 1,
72                         size, pixSize) >> m_colShift) & 0xFF) : actPix;
73                 int leftPix = x > 0 ? int((convertPrevious(src - pixSize, x - 1, y, size, pixSize)
74                         >> m_colShift) & 0xFF) : actPix;
75                 // height differences (from blue color)
76                 float dx = (actPix - leftPix) * m_depthScale;
77                 float dy = (actPix - upPix) * m_depthScale;
78                 // normalize vector
79                 float dz = float(normScaleKoef / sqrt(dx * dx + dy * dy + 1.0));
80                 dx = dx * dz + normScaleKoef;
81                 dy = dy * dz + normScaleKoef;
82                 dz += normScaleKoef;
83                 // return normal vector converted to color
84                 return 0xFF000000 | int(dz) << 16 | int(dy) << 8 | int(dx);
85         }
86
87         /// filter pixel, source byte buffer
88         virtual unsigned int filter (unsigned char * src, short x, short y,
89                 short * size, unsigned int pixSize, unsigned int val = 0)
90         { return tFilter(src, x, y, size, pixSize, val); }
91         /// filter pixel, source int buffer
92         virtual unsigned int filter (unsigned int * src, short x, short y,
93                 short * size, unsigned int pixSize, unsigned int val = 0)
94         { return tFilter(src, x, y, size, pixSize, val); }
95 };
96
97
98 #endif