shaderPhong.cpp 8.25 KB
Newer Older
Sylvain Thery's avatar
Sylvain Thery committed
1
2
3
/*******************************************************************************
* CGoGN: Combinatorial and Geometric modeling with Generic N-dimensional Maps  *
* version 0.1                                                                  *
4
* Copyright (C) 2009-2012, IGG Team, LSIIT, University of Strasbourg           *
Sylvain Thery's avatar
Sylvain Thery committed
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
*                                                                              *
* This library is free software; you can redistribute it and/or modify it      *
* under the terms of the GNU Lesser General Public License as published by the *
* Free Software Foundation; either version 2.1 of the License, or (at your     *
* option) any later version.                                                   *
*                                                                              *
* This library is distributed in the hope that it will be useful, but WITHOUT  *
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or        *
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License  *
* for more details.                                                            *
*                                                                              *
* You should have received a copy of the GNU Lesser General Public License     *
* along with this library; if not, write to the Free Software Foundation,      *
* Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301 USA.           *
*                                                                              *
20
* Web site: http://cgogn.unistra.fr/                                           *
Sylvain Thery's avatar
Sylvain Thery committed
21
22
23
* Contact information: cgogn@unistra.fr                                        *
*                                                                              *
*******************************************************************************/
Sylvain Thery's avatar
Sylvain Thery committed
24
#define CGoGN_UTILS_DLL_EXPORT 1
Sylvain Thery's avatar
Sylvain Thery committed
25
#include <GL/glew.h>
26
#include "Utils/Shaders/shaderPhong.h"
Sylvain Thery's avatar
Sylvain Thery committed
27
28
29

namespace CGoGN
{
Pierre Kraemer's avatar
merge..    
Pierre Kraemer committed
30

Sylvain Thery's avatar
Sylvain Thery committed
31
32
namespace Utils
{
33

34
35
#include "shaderPhong.vert"
#include "shaderPhong.frag"
Sylvain Thery's avatar
Sylvain Thery committed
36
37
#include "shaderPhongClip.vert"
#include "shaderPhongClip.frag"
Sylvain Thery's avatar
Sylvain Thery committed
38
39


40
	ShaderPhong::ShaderPhong(bool withClipping, bool withEyePosition) :
Pierre Kraemer's avatar
merge..    
Pierre Kraemer committed
41
	m_with_color(false),
42
	m_with_eyepos(withEyePosition),
43
	m_doubleSided(1),
Pierre Kraemer's avatar
merge..    
Pierre Kraemer committed
44
45
46
47
	m_ambiant(Geom::Vec4f(0.05f,0.05f,0.1f,0.0f)),
	m_diffuse(Geom::Vec4f(0.1f,1.0f,0.1f,0.0f)),
	m_specular(Geom::Vec4f(1.0f,1.0f,1.0f,0.0f)),
	m_shininess(100.0f),
48
	m_lightPos(Geom::Vec3f(10.0f,10.0f,1000.0f)),
Sylvain Thery's avatar
Sylvain Thery committed
49
	m_backColor(0.0f,0.0f,0.0f,0.0f),
50
51
	m_vboPos(NULL),
	m_vboNormal(NULL),
Sylvain Thery's avatar
Sylvain Thery committed
52
53
	m_vboColor(NULL),
	m_planeClip(Geom::Vec4f(0.0f,0.0f,0.0f,0.0f))
Sylvain Thery's avatar
Sylvain Thery committed
54
{
55
56
	std::string glxvert(GLSLShader::defines_gl());
	std::string glxfrag(GLSLShader::defines_gl());
Sylvain Thery's avatar
Sylvain Thery committed
57
58
59
60
61
62
63
64
65

	if (withClipping)
	{
		m_nameVS = "ShaderPhongClip_vs";
		m_nameFS = "ShaderPhongClip_fs";
		if (m_with_eyepos)
			glxvert.append("#define WITH_EYEPOSITION");
		glxvert.append(vertexShaderClipText);
		// Use double sided lighting if set
66
67
		//if (doubleSided)
		//	glxfrag.append("#define DOUBLE_SIDED\n");
Sylvain Thery's avatar
Sylvain Thery committed
68
69
70
71
72
73
74
75
76
77
		glxfrag.append(fragmentShaderClipText);
	}
	else
	{
		m_nameVS = "ShaderPhong_vs";
		m_nameFS = "ShaderPhong_fs";
		if (m_with_eyepos)
			glxvert.append("#define WITH_EYEPOSITION");
		glxvert.append(vertexShaderText);
		// Use double sided lighting if set
78
79
		//if (doubleSided)
		//	glxfrag.append("#define DOUBLE_SIDED\n");
Sylvain Thery's avatar
Sylvain Thery committed
80
81
		glxfrag.append(fragmentShaderText);
	}
Sylvain Thery's avatar
Sylvain Thery committed
82
83
84
85
86
87
88
89

	loadShadersFromMemory(glxvert.c_str(), glxfrag.c_str());

	// and get and fill uniforms
	getLocations();
	sendParams();
}

90

Sylvain Thery's avatar
Sylvain Thery committed
91
void ShaderPhong::getLocations()
Sylvain Thery's avatar
Sylvain Thery committed
92
{
93
	bind();
94
95
96
97
98
	*m_unif_ambiant   = glGetUniformLocation(this->program_handler(), "materialAmbient");
	*m_unif_diffuse   = glGetUniformLocation(this->program_handler(), "materialDiffuse");
	*m_unif_specular  = glGetUniformLocation(this->program_handler(), "materialSpecular");
	*m_unif_shininess = glGetUniformLocation(this->program_handler(), "shininess");
	*m_unif_lightPos  = glGetUniformLocation(this->program_handler(), "lightPosition");
Sylvain's avatar
Sylvain committed
99
100
	if (m_with_eyepos)
		*m_unif_eyePos  = glGetUniformLocation(this->program_handler(), "eyePosition");
Sylvain Thery's avatar
Sylvain Thery committed
101
102
	*m_unif_backColor  = glGetUniformLocation(this->program_handler(), "backColor");
	*m_unif_planeClip = glGetUniformLocation(this->program_handler(), "planeClip");
103
	*m_unif_doubleSided = glGetUniformLocation(this->program_handler(), "doubleSided");
Sylvain Thery's avatar
Sylvain Thery committed
104

105
	unbind();
Sylvain Thery's avatar
Sylvain Thery committed
106
107
}

Sylvain Thery's avatar
Sylvain Thery committed
108
void ShaderPhong::sendParams()
Sylvain Thery's avatar
Sylvain Thery committed
109
{
110
	bind();
111
112
113
114
115
	glUniform4fv(*m_unif_ambiant,  1, m_ambiant.data());
	glUniform4fv(*m_unif_diffuse,  1, m_diffuse.data());
	glUniform4fv(*m_unif_specular, 1, m_specular.data());
	glUniform1f(*m_unif_shininess,    m_shininess);
	glUniform3fv(*m_unif_lightPos, 1, m_lightPos.data());
116
	glUniform1i(*m_unif_doubleSided, m_doubleSided);
Sylvain's avatar
Sylvain committed
117
118
	if (m_with_eyepos)
		glUniform3fv(*m_unif_eyePos, 1, m_eyePos.data());
Sylvain Thery's avatar
Sylvain Thery committed
119
120
121
	glUniform4fv(*m_unif_backColor,  1, m_backColor.data());
	if (*m_unif_planeClip > 0)
		glUniform4fv(*m_unif_planeClip, 1, m_planeClip.data());
122
	unbind();
Sylvain Thery's avatar
Sylvain Thery committed
123
124
}

125
126
127
128
129
130
131
132
133
134
void ShaderPhong::setDoubleSided(bool doubleSided)
{
	m_doubleSided = doubleSided;

	bind();
	glUniform1i(*m_unif_doubleSided, m_doubleSided);
	unbind();
}


Sylvain Thery's avatar
Sylvain Thery committed
135
void ShaderPhong::setAmbiant(const Geom::Vec4f& ambiant)
Sylvain Thery's avatar
Sylvain Thery committed
136
{
137
	bind();
138
	glUniform4fv(*m_unif_ambiant,1, ambiant.data());
Sylvain Thery's avatar
Sylvain Thery committed
139
	m_ambiant = ambiant;
140
	unbind();
Sylvain Thery's avatar
Sylvain Thery committed
141
142
}

Sylvain Thery's avatar
Sylvain Thery committed
143
void ShaderPhong::setDiffuse(const Geom::Vec4f& diffuse)
Sylvain Thery's avatar
Sylvain Thery committed
144
{
145
	bind();
146
	glUniform4fv(*m_unif_diffuse,1, diffuse.data());
Sylvain Thery's avatar
Sylvain Thery committed
147
	m_diffuse = diffuse;
148
	unbind();
Sylvain Thery's avatar
Sylvain Thery committed
149
150
}

Sylvain Thery's avatar
Sylvain Thery committed
151
void ShaderPhong::setSpecular(const Geom::Vec4f& specular)
Sylvain Thery's avatar
Sylvain Thery committed
152
{
153
	bind();
154
	glUniform4fv(*m_unif_specular,1,specular.data());
Sylvain Thery's avatar
Sylvain Thery committed
155
	m_specular = specular;
156
	unbind();
Sylvain Thery's avatar
Sylvain Thery committed
157
158
}

Sylvain Thery's avatar
Sylvain Thery committed
159
void ShaderPhong::setShininess(float shininess)
Sylvain Thery's avatar
Sylvain Thery committed
160
{
161
	bind();
162
	glUniform1f (*m_unif_shininess, shininess);
Sylvain Thery's avatar
Sylvain Thery committed
163
	m_shininess = shininess;
164
	unbind();
Sylvain Thery's avatar
Sylvain Thery committed
165
166
}

Sylvain Thery's avatar
Sylvain Thery committed
167
168
169
170
171
172
173
174
175
void ShaderPhong::setBackColor(const Geom::Vec4f& back)
{
	bind();
	glUniform4fv(*m_unif_backColor,1, back.data());
	m_backColor = back;
	unbind();
}


176
void ShaderPhong::setLightPosition(const Geom::Vec3f& lightPos)
Sylvain Thery's avatar
Sylvain Thery committed
177
{
178
	bind();
179
	glUniform3fv(*m_unif_lightPos,1,lightPos.data());
Sylvain Thery's avatar
Sylvain Thery committed
180
	m_lightPos = lightPos;
181
	unbind();
Sylvain Thery's avatar
Sylvain Thery committed
182
183
}

184
void ShaderPhong::setEyePosition(const Geom::Vec3f& eyePos)
Sylvain's avatar
Sylvain committed
185
186
187
{
	if (m_with_eyepos)
	{
188
		bind();
Sylvain Thery's avatar
Sylvain Thery committed
189
		glUniform3fv(*m_unif_eyePos,1,eyePos.data());
Sylvain's avatar
Sylvain committed
190
		m_eyePos = eyePos;
191
		unbind();
Sylvain's avatar
Sylvain committed
192
193
194
	}
}

Sylvain Thery's avatar
Sylvain Thery committed
195
void ShaderPhong::setParams(const Geom::Vec4f& ambiant, const Geom::Vec4f& diffuse, const Geom::Vec4f& specular, float shininess, const Geom::Vec3f& lightPos)
Sylvain Thery's avatar
Sylvain Thery committed
196
197
198
199
200
201
202
203
204
{
	m_ambiant = ambiant;
	m_diffuse = diffuse;
	m_specular = specular;
	m_shininess = shininess;
	m_lightPos = lightPos;
	sendParams();
}

205
unsigned int ShaderPhong::setAttributeColor(VBO* vbo)
Sylvain Thery's avatar
Sylvain Thery committed
206
{
207
	m_vboColor = vbo;
Sylvain Thery's avatar
Sylvain Thery committed
208
209
210
211
	if (!m_with_color)
	{
		m_with_color=true;
		// set the define and recompile shader
212
		std::string gl3vert(GLSLShader::defines_gl());
Sylvain Thery's avatar
Sylvain Thery committed
213
214
		gl3vert.append("#define WITH_COLOR 1\n");
		gl3vert.append(vertexShaderText);
215
		std::string gl3frag(GLSLShader::defines_gl());
Sylvain Thery's avatar
Sylvain Thery committed
216
217
218
219
220
221
222
223
224
		gl3frag.append("#define WITH_COLOR 1\n");
		gl3frag.append(fragmentShaderText);
		loadShadersFromMemory(gl3vert.c_str(), gl3frag.c_str());

		// and treat uniforms
		getLocations();
		sendParams();
	}
	// bind th VA with WBO
225
226
227
228
	bind();
	unsigned int id = bindVA_VBO("VertexColor", vbo);
	unbind();
	return id;
Sylvain Thery's avatar
Sylvain Thery committed
229
230
}

Sylvain Thery's avatar
Sylvain Thery committed
231
void ShaderPhong::unsetAttributeColor()
Sylvain Thery's avatar
Sylvain Thery committed
232
{
233
	m_vboColor = NULL;
Sylvain Thery's avatar
Sylvain Thery committed
234
235
	if (m_with_color)
	{
236
		m_with_color = false;
Sylvain Thery's avatar
Sylvain Thery committed
237
		// unbind the VA
238
		bind();
Sylvain Thery's avatar
Sylvain Thery committed
239
		unbindVA("VertexColor");
240
		unbind();
Sylvain Thery's avatar
Sylvain Thery committed
241
		// recompile shader
242
		std::string gl3vert(GLSLShader::defines_gl());
Sylvain Thery's avatar
Sylvain Thery committed
243
		gl3vert.append(vertexShaderText);
244
		std::string gl3frag(GLSLShader::defines_gl());
Sylvain Thery's avatar
Sylvain Thery committed
245
246
247
248
249
250
		gl3frag.append(fragmentShaderText);
		loadShadersFromMemory(gl3vert.c_str(), gl3frag.c_str());
		// and treat uniforms
		getLocations();
		sendParams();
	}
251
252
}

Sylvain Thery's avatar
Sylvain Thery committed
253
254
255
256
257
258
259
260
261
262
263
void ShaderPhong::setClippingPlane(const Geom::Vec4f& plane)
{
	if (*m_unif_planeClip > 0)
	{
		m_planeClip = plane;
		bind();
		glUniform4fv(*m_unif_planeClip, 1, plane.data());
		unbind();
	}
}

264
265
266
267
void ShaderPhong::restoreUniformsAttribs()
{
	getLocations();
	sendParams();
Sylvain Thery's avatar
Sylvain Thery committed
268

269
	bind();
270
271
272
273
	bindVA_VBO("VertexPosition", m_vboPos);
	bindVA_VBO("VertexNormal", m_vboNormal);
	if (m_vboColor)
		bindVA_VBO("VertexColor", m_vboColor);
274

275
	unbind();
Sylvain Thery's avatar
Sylvain Thery committed
276
277
}

278
279
unsigned int ShaderPhong::setAttributePosition(VBO* vbo)
{
Pierre Kraemer's avatar
merge..    
Pierre Kraemer committed
280
	m_vboPos = vbo;
281
282
283
284
	bind();
	unsigned int id = bindVA_VBO("VertexPosition", vbo);
	unbind();
	return id;
285
286
287
288
289
}

unsigned int ShaderPhong::setAttributeNormal(VBO* vbo)
{
	m_vboNormal = vbo;
290
291
292
293
	bind();
	unsigned int id = bindVA_VBO("VertexNormal", vbo);
	unbind();
	return id;
294
295
}

Pierre Kraemer's avatar
merge..    
Pierre Kraemer committed
296
} // namespace Utils
297

Pierre Kraemer's avatar
merge..    
Pierre Kraemer committed
298
} // namespace CGoGN