dungeon_crawler

changeset 23:fa8f89d06f6f

progress with light rendering
author John Tsiombikas <nuclear@member.fsf.org>
date Thu, 23 Aug 2012 00:10:10 +0300
parents 7b65bba15553
children e122ba214ee1
files prototype/Makefile prototype/data/test.level prototype/src/level.cc prototype/src/level.h prototype/src/light.cc prototype/src/light.h prototype/src/main.cc prototype/src/renderer.cc prototype/src/renderer.h prototype/src/sdr.c prototype/src/sdr.h prototype/src/tile.cc prototype/src/tile.h
diffstat 13 files changed, 245 insertions(+), 59 deletions(-) [+]
line diff
     1.1 --- a/prototype/Makefile	Tue Aug 21 06:34:14 2012 +0300
     1.2 +++ b/prototype/Makefile	Thu Aug 23 00:10:10 2012 +0300
     1.3 @@ -10,7 +10,7 @@
     1.4  
     1.5  CFLAGS = -pedantic $(warn) $(dbg) $(opt) -Ivmath
     1.6  CXXFLAGS = $(CFLAGS) -std=c++11
     1.7 -LDFLAGS = $(libgl) -lm -lassimpD -limago
     1.8 +LDFLAGS = $(libgl) -lm -lassimp -limago
     1.9  
    1.10  ifeq ($(shell uname -s), Darwin)
    1.11  	libgl = -framework OpenGL -framework GLUT -lglew
     2.1 --- a/prototype/data/test.level	Tue Aug 21 06:34:14 2012 +0300
     2.2 +++ b/prototype/data/test.level	Thu Aug 23 00:10:10 2012 +0300
     2.3 @@ -30,7 +30,6 @@
     2.4  ################################################################
     2.5  ################################################################
     2.6  ################################################################
     2.7 -###############################  ###############################
     2.8  ################################ ###############################
     2.9  ################################################################
    2.10  ################################################################
    2.11 @@ -63,3 +62,4 @@
    2.12  ################################################################
    2.13  ################################################################
    2.14  ################################################################
    2.15 +################################################################
     3.1 --- a/prototype/src/level.cc	Tue Aug 21 06:34:14 2012 +0300
     3.2 +++ b/prototype/src/level.cc	Thu Aug 23 00:10:10 2012 +0300
     3.3 @@ -99,6 +99,24 @@
     3.4  	return Vector3(posx, 0, posy);
     3.5  }
     3.6  
     3.7 +unsigned int Level::get_cell_dirmask(int x, int y) const
     3.8 +{
     3.9 +	unsigned int dmask = TILE_ALL;
    3.10 +	if(y > 0 && get_cell(x, y - 1)) {
    3.11 +		dmask &= ~TILE_NORTH;
    3.12 +	}
    3.13 +	if(y < ysz - 1 && get_cell(x, y + 1)) {
    3.14 +		dmask &= ~TILE_SOUTH;
    3.15 +	}
    3.16 +	if(x > 0 && get_cell(x - 1, y)) {
    3.17 +		dmask &= ~TILE_WEST;
    3.18 +	}
    3.19 +	if(x < xsz - 1 && get_cell(x + 1, y)) {
    3.20 +		dmask &= ~TILE_EAST;
    3.21 +	}
    3.22 +	return dmask;
    3.23 +}
    3.24 +
    3.25  void Level::draw() const
    3.26  {
    3.27  	glMatrixMode(GL_MODELVIEW);
    3.28 @@ -114,19 +132,7 @@
    3.29  				glTranslatef(pos.x, pos.y, pos.z);
    3.30  				glScalef(cell_size, cell_size, cell_size);
    3.31  
    3.32 -				unsigned int dmask = TILE_ALL;
    3.33 -				if(i > 0 && get_cell(j, i - 1)) {
    3.34 -					dmask &= ~TILE_NORTH;
    3.35 -				}
    3.36 -				if(i < ysz - 1 && get_cell(j, i + 1)) {
    3.37 -					dmask &= ~TILE_SOUTH;
    3.38 -				}
    3.39 -				if(j > 0 && get_cell(j - 1, i)) {
    3.40 -					dmask &= ~TILE_WEST;
    3.41 -				}
    3.42 -				if(j < xsz - 1 && get_cell(j + 1, i)) {
    3.43 -					dmask &= ~TILE_EAST;
    3.44 -				}
    3.45 +				unsigned int dmask = get_cell_dirmask(j, i);
    3.46  
    3.47  				cell->draw(dmask);
    3.48  				glPopMatrix();
    3.49 @@ -135,6 +141,29 @@
    3.50  	}
    3.51  }
    3.52  
    3.53 +void Level::draw_lights() const
    3.54 +{
    3.55 +	glMatrixMode(GL_MODELVIEW);
    3.56 +
    3.57 +	for(int i=0; i<ysz; i++) {
    3.58 +		for(int j=0; j<xsz; j++) {
    3.59 +			const GridCell *cell = get_cell(j, i);
    3.60 +			if(cell) {
    3.61 +				Vector3 pos = get_cell_pos(j, i);
    3.62 +
    3.63 +				glPushMatrix();
    3.64 +				glTranslatef(pos.x, pos.y, pos.z);
    3.65 +				glScalef(cell_size, cell_size, cell_size);
    3.66 +
    3.67 +				unsigned int dmask = get_cell_dirmask(j, i);
    3.68 +				cell->draw_lights(dmask);
    3.69 +
    3.70 +				glPopMatrix();
    3.71 +			}
    3.72 +		}
    3.73 +	}
    3.74 +}
    3.75 +
    3.76  void Level::draw_grid() const
    3.77  {
    3.78  	float xlen = xsz * cell_size;
    3.79 @@ -179,7 +208,14 @@
    3.80  
    3.81  void GridCell::draw(unsigned int draw_mask) const
    3.82  {
    3.83 -	for(size_t i=0; i<tiles.size(); i++) {
    3.84 -		tiles[i]->draw(draw_mask);
    3.85 +	for(auto tile : tiles) {
    3.86 +		tile->draw(draw_mask);
    3.87  	}
    3.88  }
    3.89 +
    3.90 +void GridCell::draw_lights(unsigned int draw_mask) const
    3.91 +{
    3.92 +	for(auto tile : tiles) {
    3.93 +		tile->draw_lights(draw_mask);
    3.94 +	}
    3.95 +}
     4.1 --- a/prototype/src/level.h	Tue Aug 21 06:34:14 2012 +0300
     4.2 +++ b/prototype/src/level.h	Thu Aug 23 00:10:10 2012 +0300
     4.3 @@ -26,8 +26,10 @@
     4.4  
     4.5  	const GridCell *get_cell(int x, int y) const;
     4.6  	Vector3 get_cell_pos(int x, int y) const;
     4.7 +	unsigned int get_cell_dirmask(int x, int y) const;
     4.8  
     4.9  	void draw() const;
    4.10 +	void draw_lights() const;
    4.11  };
    4.12  
    4.13  class GridCell {
    4.14 @@ -41,6 +43,7 @@
    4.15  	void add_tile(const Tile *tile);
    4.16  
    4.17  	void draw(unsigned int draw_mask) const;
    4.18 +	void draw_lights(unsigned int draw_mask) const;
    4.19  };
    4.20  
    4.21  #endif	// LEVEL_H_
     5.1 --- a/prototype/src/light.cc	Tue Aug 21 06:34:14 2012 +0300
     5.2 +++ b/prototype/src/light.cc	Thu Aug 23 00:10:10 2012 +0300
     5.3 @@ -5,6 +5,8 @@
     5.4  	: color(col)
     5.5  {
     5.6  	intensity = 1.0;
     5.7 +	vbo = 0;
     5.8 +	num_faces = 0;
     5.9  }
    5.10  
    5.11  Light::~Light() {}
    5.12 @@ -30,6 +32,29 @@
    5.13  	glLightfv(GL_LIGHT0 + id, GL_SPECULAR, &color.x);
    5.14  }
    5.15  
    5.16 +void Light::draw() const
    5.17 +{
    5.18 +	if(!vbo) {
    5.19 +		if(!((Light*)this)->create_mesh()) {
    5.20 +			return;
    5.21 +		}
    5.22 +	}
    5.23 +
    5.24 +	glEnableClientState(GL_VERTEX_ARRAY);
    5.25 +	glBindBuffer(GL_ARRAY_BUFFER, vbo);
    5.26 +	glVertexPointer(3, GL_FLOAT, 0, 0);
    5.27 +
    5.28 +	glDrawArrays(GL_TRIANGLES, 0, num_faces * 3);
    5.29 +
    5.30 +	glDisableClientState(GL_VERTEX_ARRAY);
    5.31 +}
    5.32 +
    5.33 +bool Light::create_mesh()
    5.34 +{
    5.35 +	fprintf(stderr, "%s: undefined\n", __FUNCTION__);
    5.36 +	return false;
    5.37 +}
    5.38 +
    5.39  
    5.40  PointLight::PointLight()
    5.41  {
    5.42 @@ -80,6 +105,67 @@
    5.43  	glLightf(GL_LIGHT0 + id, GL_QUADRATIC_ATTENUATION, atten[2]);
    5.44  }
    5.45  
    5.46 +void PointLight::draw() const
    5.47 +{
    5.48 +	//glMatrixMode(GL_MODELVIEW);
    5.49 +	//glPushMatrix();
    5.50 +	//glScalef(radius, radius, radius);
    5.51 +
    5.52 +	Light::draw();
    5.53 +
    5.54 +	//glPopMatrix();
    5.55 +}
    5.56 +
    5.57 +
    5.58 +
    5.59 +Vector3 sphvertex(float u, float v)
    5.60 +{
    5.61 +	float theta = u * M_PI * 2.0;
    5.62 +	float phi = v * M_PI;
    5.63 +
    5.64 +	Vector3 res;
    5.65 +	res.x = sin(theta) * cos(phi);
    5.66 +	res.y = sin(theta);
    5.67 +	res.z = cos(theta) * cos(phi);
    5.68 +	return res;
    5.69 +}
    5.70 +
    5.71 +
    5.72 +bool PointLight::create_mesh()
    5.73 +{
    5.74 +	const static int udiv = 8;
    5.75 +	const static int vdiv = 4;
    5.76 +
    5.77 +	int nquads = udiv * vdiv;
    5.78 +	num_faces = nquads * 2;
    5.79 +	int nverts = num_faces * 3;
    5.80 +
    5.81 +	float du = 1.0 / (float)udiv;
    5.82 +	float dv = 1.0 / (float)vdiv;
    5.83 +
    5.84 +	glGenBuffers(1, &vbo);
    5.85 +	glBindBuffer(GL_ARRAY_BUFFER, vbo);
    5.86 +	glBufferData(GL_ARRAY_BUFFER, nverts * sizeof(Vector3), 0, GL_STATIC_DRAW);
    5.87 +
    5.88 +	Vector3 *vptr = (Vector3*)glMapBuffer(GL_ARRAY_BUFFER, GL_WRITE_ONLY);
    5.89 +
    5.90 +	for(int i=0; i<vdiv; i++) {
    5.91 +		float v = (float)i / (float)vdiv;
    5.92 +		for(int j=0; j<udiv; j++) {
    5.93 +			float u = (float)j / (float)udiv;
    5.94 +
    5.95 +			*vptr++ = sphvertex(u, v);
    5.96 +			*vptr++ = sphvertex(u + du, v);
    5.97 +			*vptr++ = sphvertex(u, v + dv);
    5.98 +
    5.99 +			*vptr++ = sphvertex(u + du, v);
   5.100 +			*vptr++ = sphvertex(u + du, v + dv);
   5.101 +			*vptr++ = sphvertex(u, v + dv);
   5.102 +		}
   5.103 +	}
   5.104 +	glUnmapBuffer(GL_ARRAY_BUFFER);
   5.105 +	return true;
   5.106 +}
   5.107  
   5.108  void set_light(int id, const Light *lt)
   5.109  {
     6.1 --- a/prototype/src/light.h	Tue Aug 21 06:34:14 2012 +0300
     6.2 +++ b/prototype/src/light.h	Thu Aug 23 00:10:10 2012 +0300
     6.3 @@ -8,6 +8,12 @@
     6.4  	float intensity;
     6.5  	Color color;
     6.6  
     6.7 +	// VBO for rendering the light source
     6.8 +	unsigned int vbo;
     6.9 +	unsigned int num_faces;
    6.10 +
    6.11 +	virtual bool create_mesh();
    6.12 +
    6.13  public:
    6.14  	Light(const Color &col = 1.0);
    6.15  	virtual ~Light();
    6.16 @@ -18,6 +24,8 @@
    6.17  	virtual Color get_color(bool with_intensity = true) const;
    6.18  
    6.19  	virtual void use(int id = 0) const;
    6.20 +
    6.21 +	virtual void draw() const;
    6.22  };
    6.23  
    6.24  class PointLight : public Light {
    6.25 @@ -26,6 +34,8 @@
    6.26  	float atten[3];
    6.27  	float radius;
    6.28  
    6.29 +	bool create_mesh();
    6.30 +
    6.31  public:
    6.32  	PointLight();
    6.33  	PointLight(const Vector3 &pos, const Color &col = 1.0);
    6.34 @@ -37,12 +47,16 @@
    6.35  	float get_radius() const;
    6.36  
    6.37  	virtual void use(int id = 0) const;
    6.38 +
    6.39 +	virtual void draw() const;
    6.40  };
    6.41  
    6.42  class DirLight : public Light {
    6.43  protected:
    6.44  	Vector3 dir;
    6.45  
    6.46 +	bool create_mesh();
    6.47 +
    6.48  public:
    6.49  	DirLight();
    6.50  	DirLight(const Vector3 &dir, const Color &col = 1.0);
     7.1 --- a/prototype/src/main.cc	Tue Aug 21 06:34:14 2012 +0300
     7.2 +++ b/prototype/src/main.cc	Thu Aug 23 00:10:10 2012 +0300
     7.3 @@ -128,7 +128,7 @@
     7.4  		glLoadIdentity();
     7.5  		view_matrix(-1);
     7.6  
     7.7 -		render_deferred(draw);
     7.8 +		render_deferred(level);
     7.9  
    7.10  		glDrawBuffer(GL_BACK_RIGHT);
    7.11  
    7.12 @@ -139,7 +139,7 @@
    7.13  		glLoadIdentity();
    7.14  		view_matrix(1);
    7.15  
    7.16 -		render_deferred(draw);
    7.17 +		render_deferred(level);
    7.18  
    7.19  	} else {
    7.20  		glMatrixMode(GL_PROJECTION);
    7.21 @@ -149,7 +149,7 @@
    7.22  		glLoadIdentity();
    7.23  		view_matrix(0);
    7.24  
    7.25 -		render_deferred(draw);
    7.26 +		render_deferred(level);
    7.27  	}
    7.28  
    7.29  	glutSwapBuffers();
    7.30 @@ -158,12 +158,6 @@
    7.31  	usleep(10000);
    7.32  }
    7.33  
    7.34 -void draw()
    7.35 -{
    7.36 -	glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
    7.37 -	level->draw();
    7.38 -}
    7.39 -
    7.40  void view_matrix(int eye)
    7.41  {
    7.42  	float offs = stereo_eye_sep * eye * 0.5;
     8.1 --- a/prototype/src/renderer.cc	Tue Aug 21 06:34:14 2012 +0300
     8.2 +++ b/prototype/src/renderer.cc	Thu Aug 23 00:10:10 2012 +0300
     8.3 @@ -5,6 +5,7 @@
     8.4  #include <assert.h>
     8.5  #include "opengl.h"
     8.6  #include "renderer.h"
     8.7 +#include "level.h"
     8.8  #include "sdr.h"
     8.9  #include "datapath.h"
    8.10  
    8.11 @@ -60,9 +61,26 @@
    8.12  	if(!(mrt_prog = load_sdr("mrt.v.glsl", "mrt.p.glsl"))) {
    8.13  		return false;
    8.14  	}
    8.15 +	set_uniform_int(mrt_prog, "tex_dif", 0);
    8.16 +	set_uniform_int(mrt_prog, "tex_norm", 1);
    8.17 +
    8.18  	if(!(deferred_debug = load_sdr("deferred.v.glsl", "deferred.p.glsl"))) {
    8.19  		return false;
    8.20  	}
    8.21 +	for(int i=0; i<MRT_COUNT; i++) {
    8.22 +		char uname[32];
    8.23 +		sprintf(uname, "mrt%d", i);
    8.24 +		set_uniform_int(deferred_debug, uname, i);
    8.25 +	}
    8.26 +
    8.27 +	if(!(deferred_omni = load_sdr("deferred.v.glsl", "deferred_omni.p.glsl"))) {
    8.28 +		return false;
    8.29 +	}
    8.30 +	for(int i=0; i<MRT_COUNT; i++) {
    8.31 +		char uname[32];
    8.32 +		sprintf(uname, "mrt%d", i);
    8.33 +		set_uniform_int(deferred_omni, uname, i);
    8.34 +	}
    8.35  	return true;
    8.36  }
    8.37  
    8.38 @@ -75,23 +93,51 @@
    8.39  	glDeleteFramebuffersEXT(1, &fbo);
    8.40  }
    8.41  
    8.42 -void render_deferred(void (*draw_func)())
    8.43 +void resize_renderer(int xsz, int ysz)
    8.44  {
    8.45 -	int loc;
    8.46 +	fb_xsz = xsz;
    8.47 +	fb_ysz = ysz;
    8.48  
    8.49 +	// if we need a bigger rendertarget resize all colorbuffer textures and the depth buffer
    8.50 +	if(xsz > tex_xsz || ysz > tex_ysz) {
    8.51 +		tex_xsz = round_pow2(xsz);
    8.52 +		tex_ysz = round_pow2(ysz);
    8.53 +
    8.54 +		for(int i=0; i<MRT_COUNT; i++) {
    8.55 +			glBindTexture(GL_TEXTURE_2D, mrt_tex[i]);
    8.56 +			glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, tex_xsz, tex_ysz, 0, GL_RGBA,
    8.57 +					GL_UNSIGNED_BYTE, 0);
    8.58 +		}
    8.59 +
    8.60 +		glBindRenderbufferEXT(GL_RENDERBUFFER, rbuf_depth);
    8.61 +		glRenderbufferStorageEXT(GL_RENDERBUFFER, GL_DEPTH_COMPONENT, tex_xsz, tex_ysz);
    8.62 +	}
    8.63 +
    8.64 +
    8.65 +	// update the texture coordinate scaling factors
    8.66 +	float tex_scale_x = (float)fb_xsz / tex_xsz;
    8.67 +	float tex_scale_y = (float)fb_ysz / tex_ysz;
    8.68 +
    8.69 +	set_uniform_float2(deferred_omni, "tex_scale", tex_scale_x, tex_scale_y);
    8.70 +	set_uniform_float2(deferred_debug, "tex_scale", tex_scale_x, tex_scale_y);
    8.71 +}
    8.72 +
    8.73 +void render_deferred(const Level *level)
    8.74 +{
    8.75 +	glClearColor(0.4, 0.2, 0.1, 0.0);
    8.76 +	glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
    8.77 +	glPushAttrib(GL_ENABLE_BIT);
    8.78 +	glDisable(GL_LIGHTING);
    8.79 +	level->draw_lights();
    8.80 +	glPopAttrib();
    8.81 +#if 0
    8.82  	// render into the MRT buffers
    8.83 +	glUseProgram(mrt_prog);
    8.84  	glBindFramebufferEXT(GL_FRAMEBUFFER, fbo);
    8.85  
    8.86 -	glUseProgram(mrt_prog);
    8.87 -	if((loc = glGetUniformLocation(mrt_prog, "tex_dif")) != -1) {
    8.88 -		glUniform1i(loc, 0);
    8.89 -	}
    8.90 -	if((loc = glGetUniformLocation(mrt_prog, "tex_norm")) != -1) {
    8.91 -		glUniform1i(loc, 1);
    8.92 -	}
    8.93 -	draw_func();
    8.94 +	glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
    8.95 +	level->draw();
    8.96  
    8.97 -	glUseProgram(0);
    8.98  	glBindFramebufferEXT(GL_FRAMEBUFFER, 0);
    8.99  
   8.100  
   8.101 @@ -101,33 +147,16 @@
   8.102  	glDisable(GL_LIGHTING);
   8.103  	glDisable(GL_DEPTH_TEST);
   8.104  
   8.105 -	glUseProgram(deferred_debug);
   8.106 +	glUseProgram(deferred_omni);
   8.107  	for(int i=0; i<MRT_COUNT; i++) {
   8.108 -		char uname[32];
   8.109 -
   8.110 -		sprintf(uname, "mrt%d", i);
   8.111 -		if((loc = glGetUniformLocation(deferred_debug, uname)) != -1) {
   8.112 -			glUniform1i(loc, i);
   8.113 -		}
   8.114 -
   8.115  		glActiveTexture(GL_TEXTURE0 + i);
   8.116  		glBindTexture(GL_TEXTURE_2D, mrt_tex[i]);
   8.117  		glEnable(GL_TEXTURE_2D);
   8.118  	}
   8.119 -	if((loc = glGetUniformLocation(deferred_debug, "tex_scale")) != -1) {
   8.120 -		glUniform2f(loc, (float)fb_xsz / tex_xsz, (float)fb_ysz / tex_ysz);
   8.121 -	}
   8.122  
   8.123 -	glBegin(GL_QUADS);
   8.124 -	glTexCoord2f(0, 0);
   8.125 -	glVertex2f(-1, -1);
   8.126 -	glTexCoord2f(1, 0);
   8.127 -	glVertex2f(1, -1);
   8.128 -	glTexCoord2f(1, 1);
   8.129 -	glVertex2f(1, 1);
   8.130 -	glTexCoord2f(0, 1);
   8.131 -	glVertex2f(-1, 1);
   8.132 -	glEnd();
   8.133 +	glDepthMask(0);
   8.134 +	level->draw_lights();
   8.135 +	glDepthMask(1);
   8.136  
   8.137  	for(int i=0; i<MRT_COUNT; i++) {
   8.138  		glActiveTexture(GL_TEXTURE0 + MRT_COUNT - i - 1);
   8.139 @@ -136,6 +165,7 @@
   8.140  
   8.141  	glUseProgram(0);
   8.142  	glPopAttrib();
   8.143 +#endif
   8.144  }
   8.145  
   8.146  static bool create_fbo(int xsz, int ysz)
     9.1 --- a/prototype/src/renderer.h	Tue Aug 21 06:34:14 2012 +0300
     9.2 +++ b/prototype/src/renderer.h	Thu Aug 23 00:10:10 2012 +0300
     9.3 @@ -1,9 +1,13 @@
     9.4  #ifndef RENDERER_H_
     9.5  #define RENDERER_H_
     9.6  
     9.7 +class Level;
     9.8 +
     9.9  bool init_renderer(int xsz, int ysz);
    9.10  void destroy_renderer();
    9.11  
    9.12 -void render_deferred(void (*draw_func)());
    9.13 +void resize_renderer(int xsz, int ysz);
    9.14 +
    9.15 +void render_deferred(const Level *level);
    9.16  
    9.17  #endif	// RENDERER_H_
    10.1 --- a/prototype/src/sdr.c	Tue Aug 21 06:34:14 2012 +0300
    10.2 +++ b/prototype/src/sdr.c	Thu Aug 23 00:10:10 2012 +0300
    10.3 @@ -273,6 +273,14 @@
    10.4  	END_UNIFORM_CODE;
    10.5  }
    10.6  
    10.7 +int set_uniform_float2(unsigned int prog, const char *name, float x, float y)
    10.8 +{
    10.9 +	BEGIN_UNIFORM_CODE {
   10.10 +		glUniform2f(loc, x, y);
   10.11 +	}
   10.12 +	END_UNIFORM_CODE;
   10.13 +}
   10.14 +
   10.15  int set_uniform_float3(unsigned int prog, const char *name, float x, float y, float z)
   10.16  {
   10.17  	BEGIN_UNIFORM_CODE {
    11.1 --- a/prototype/src/sdr.h	Tue Aug 21 06:34:14 2012 +0300
    11.2 +++ b/prototype/src/sdr.h	Thu Aug 23 00:10:10 2012 +0300
    11.3 @@ -34,6 +34,7 @@
    11.4  
    11.5  int set_uniform_int(unsigned int prog, const char *name, int val);
    11.6  int set_uniform_float(unsigned int prog, const char *name, float val);
    11.7 +int set_uniform_float2(unsigned int prog, const char *name, float x, float y);
    11.8  int set_uniform_float3(unsigned int prog, const char *name, float x, float y, float z);
    11.9  int set_uniform_float4(unsigned int prog, const char *name, float x, float y, float z, float w);
   11.10  int set_uniform_matrix4(unsigned int prog, const char *name, float *mat);
    12.1 --- a/prototype/src/tile.cc	Tue Aug 21 06:34:14 2012 +0300
    12.2 +++ b/prototype/src/tile.cc	Thu Aug 23 00:10:10 2012 +0300
    12.3 @@ -56,6 +56,15 @@
    12.4  	}
    12.5  }
    12.6  
    12.7 +void Tile::draw_lights(unsigned int draw_mask) const
    12.8 +{
    12.9 +	for(size_t i=0; i<lights.size(); i++) {
   12.10 +		if(light_side[i] & draw_mask) {
   12.11 +			lights[i]->draw();
   12.12 +		}
   12.13 +	}
   12.14 +}
   12.15 +
   12.16  /*
   12.17  int Tile::load_lights(const aiScene *scn)
   12.18  {
    13.1 --- a/prototype/src/tile.h	Tue Aug 21 06:34:14 2012 +0300
    13.2 +++ b/prototype/src/tile.h	Thu Aug 23 00:10:10 2012 +0300
    13.3 @@ -34,6 +34,7 @@
    13.4  	bool load(const char *fname);
    13.5  
    13.6  	void draw(unsigned int drawmask) const;
    13.7 +	void draw_lights(unsigned int drawmask) const;
    13.8  };
    13.9  
   13.10