Skip to content

Commit 7fe6c25

Browse files
committed
Example: Geo cubes
1 parent 286cb70 commit 7fe6c25

File tree

8 files changed

+267
-0
lines changed

8 files changed

+267
-0
lines changed

examples/README.md

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,3 +32,16 @@ python manage.py runeffect examples.feedback
3232
```
3333

3434
![screenshot](https://github.com/Contraz/demosys-py/blob/master/examples/images/feedback.png)
35+
36+
Geo Cubes
37+
---------
38+
39+
Geometry shader example. We're drawing points were the geometry shader emits
40+
a cube on each point and slightly modifying the position of each cube.
41+
The texture on these cube is an fbo texture of a spinning cube just for fun.
42+
43+
```bash
44+
python manage.py runeffect examples.geocubes
45+
```
46+
47+
![screenshot](https://raw.githubusercontent.com/Contraz/demosys-py/master/examples/images/geocubes.png)

examples/geocubes/effect.py

Lines changed: 62 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,62 @@
1+
import moderngl as mgl
2+
# import math
3+
from demosys.effects import effect
4+
from demosys import geometry
5+
from demosys.opengl import FBO
6+
7+
8+
class GeoCubesEffect(effect.Effect):
9+
"""Simple effect drawing a textured cube"""
10+
def __init__(self):
11+
self.cube_shader1 = self.get_shader('geocubes/cube_multi_fade.glsl')
12+
self.cube_shader2 = self.get_shader('geocubes/cube_texture_light.glsl')
13+
self.quad_shader = self.get_shader('geocubes/quad_fs_uvscale.glsl')
14+
15+
self.texture1 = self.get_texture('geocubes/texture.png')
16+
self.texture2 = self.get_texture('geocubes/GreenFabric.png')
17+
18+
self.cube = geometry.cube(4.0, 4.0, 4.0)
19+
20+
v = 100.0
21+
r = (-v, v)
22+
23+
self.points = geometry.points_random_3d(50_000, range_x=r, range_y=r, range_z=r, seed=7656456)
24+
self.quad = geometry.quad_fs()
25+
self.fbo = FBO.create((512, 512), depth=True)
26+
27+
@effect.bind_target
28+
def draw(self, time, frametime, target):
29+
self.ctx.enable(mgl.DEPTH_TEST)
30+
self.ctx.enable(mgl.CULL_FACE)
31+
32+
mv_m = self.create_transformation(rotation=(time * 1.2, time * 2.1, time * 0.25),
33+
translation=(0.0, 0.0, -8.0))
34+
normal_m = self.create_normal_matrix(mv_m)
35+
proj_m = self.create_projection(fov=60.0, ratio=1.0)
36+
37+
with self.fbo:
38+
self.cube_shader1.uniform("m_proj", proj_m.astype('f4').tobytes())
39+
self.cube_shader1.uniform("m_mv", mv_m.astype('f4').tobytes())
40+
self.cube_shader1.uniform("m_normal", normal_m.astype('f4').tobytes())
41+
self.texture1.use(location=0)
42+
self.texture2.use(location=1)
43+
self.cube_shader1.uniform("texture0", 0)
44+
self.cube_shader1.uniform("texture1", 1)
45+
self.cube_shader1.uniform("time", time)
46+
self.cube.draw(self.cube_shader1)
47+
48+
self.sys_camera.projection.update(fov=75, near=0.1, far=1000)
49+
50+
view_m = self.sys_camera.view_matrix
51+
normal_m = self.create_normal_matrix(view_m)
52+
53+
self.cube_shader2.uniform("m_proj", self.sys_camera.projection.tobytes())
54+
self.cube_shader2.uniform("m_mv", view_m.astype('f4').tobytes())
55+
self.cube_shader2.uniform("m_normal", normal_m.astype('f4').tobytes())
56+
self.fbo.color_buffers[0].use(location=0)
57+
self.cube_shader2.uniform("texture0", 0)
58+
self.cube_shader2.uniform("time", time)
59+
self.cube_shader2.uniform("lightpos", (0.0, 0.0, 0.0))
60+
self.points.draw(self.cube_shader2)
61+
62+
self.fbo.clear(red=0.5, green=0.5, blue=0.5, alpha=1.0, depth=1.0)
Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
#version 330
2+
3+
#if defined VERTEX_SHADER
4+
5+
in vec3 in_position;
6+
in vec3 in_normal;
7+
in vec2 in_uv;
8+
9+
uniform mat4 m_proj;
10+
uniform mat4 m_mv;
11+
uniform mat3 m_normal;
12+
13+
out vec3 normal;
14+
out vec2 uv;
15+
16+
void main() {
17+
gl_Position = m_proj * m_mv * vec4(in_position, 1.0);
18+
normal = m_normal * in_normal;
19+
uv = in_uv;
20+
}
21+
22+
#elif defined FRAGMENT_SHADER
23+
24+
out vec4 fragColor;
25+
uniform sampler2D texture0;
26+
uniform sampler2D texture1;
27+
uniform float time;
28+
29+
in vec3 normal;
30+
in vec2 uv;
31+
32+
void main()
33+
{
34+
vec4 c1 = texture(texture0, uv);
35+
vec4 c2 = texture(texture1, uv);
36+
float m1 = sin(time * 1.0) / 2.0 + 0.5;
37+
float m2 = 1.0 - m1;
38+
39+
vec3 dir = vec3(0.0, 0.0, 1.0);
40+
float d = dot(dir, normal);
41+
42+
fragColor = (c1 * m1 + c2 * m2) * d;
43+
}
44+
45+
#endif
Lines changed: 119 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,119 @@
1+
#version 330
2+
3+
#if defined VERTEX_SHADER
4+
5+
in vec3 in_position;
6+
7+
uniform mat4 m_proj;
8+
uniform mat4 m_mv;
9+
uniform mat3 m_normal;
10+
11+
void main() {
12+
gl_Position = vec4(in_position, 1.0);
13+
}
14+
15+
#elif defined FRAGMENT_SHADER
16+
17+
out vec4 fragColor;
18+
uniform sampler2D texture0;
19+
uniform float time;
20+
21+
in vec3 normal;
22+
in vec2 uv;
23+
in vec3 lightdir;
24+
in vec3 eyepos;
25+
26+
void main()
27+
{
28+
vec4 diffuse = vec4(0.5, 0.5, 0.5, 1.0);
29+
vec4 ambient = vec4(0.2, 0.2, 0.2, 1.0);
30+
vec4 specular = vec4(1.0, 1.0, 1.0, 1.0);
31+
float shininess = 0.5;
32+
33+
vec4 c = texture(texture0, uv);
34+
vec4 spec = vec4(0.0);
35+
36+
vec3 n = normalize(normal);
37+
vec3 l = normalize(lightdir);
38+
vec3 e = normalize(eyepos);
39+
40+
float intensity = max(dot(n,l), 0.0);
41+
if (intensity > 0.0) {
42+
vec3 h = normalize(l + e);
43+
float intSpec = max(dot(h, n), 0.0);
44+
spec = specular * pow(intSpec, shininess);
45+
}
46+
float att = clamp(1.0 - length(eyepos)/200.0, 0.0, 1.0);
47+
att *= att;
48+
fragColor = c * max(intensity * diffuse + spec, ambient) * att;
49+
}
50+
51+
52+
#elif defined GEOMETRY_SHADER
53+
54+
layout (points) in;
55+
layout (triangle_strip, max_vertices = 24) out; // 4 vertices per side of the cube
56+
57+
uniform mat4 m_proj;
58+
uniform mat4 m_mv;
59+
uniform mat3 m_normal;
60+
uniform vec3 lightpos;
61+
uniform float time;
62+
63+
out vec2 uv;
64+
out vec3 normal;
65+
out vec3 lightdir;
66+
out vec3 eyepos;
67+
68+
// Define the 8 corners of a cube (back plane, front plane (counter clockwise))
69+
vec3 cube_corners[8] = vec3[] (
70+
vec3( 1.0, 1.0, -1.0), // right top far
71+
vec3(-1.0, 1.0, -1.0), // left top far
72+
vec3(-1.0, -1.0, -1.0), // left bottom far
73+
vec3( 1.0, -1.0, -1.0), // right bottom far
74+
vec3( 1.0, 1.0, 1.0), // right top near
75+
vec3(-1.0, 1.0, 1.0), // left top near
76+
vec3(-1.0, -1.0, 1.0), // left bottom near
77+
vec3( 1.0, -1.0, 1.0) // right bottom near
78+
);
79+
80+
#define EMIT_V(POS, UV, NORMAL) \
81+
uv = UV; \
82+
normal = normalize(m_normal * NORMAL); \
83+
lightdir = lightpos - POS.xyz; \
84+
eyepos = -POS.xyz; \
85+
gl_Position = m_proj * vec4(POS, 1.0); \
86+
EmitVertex()
87+
88+
#define EMIT_QUAD(P1, P2, P3, P4, NORMAL) \
89+
EMIT_V(corners[P1], vec2(0.0, 0.0), NORMAL); \
90+
EMIT_V(corners[P2], vec2(1.0, 0.0), NORMAL); \
91+
EMIT_V(corners[P3], vec2(0.0, 1.0), NORMAL); \
92+
EMIT_V(corners[P4], vec2(1.0, 1.0), NORMAL); \
93+
EndPrimitive()
94+
95+
void main()
96+
{
97+
// Calculate the 8 cube corners
98+
vec3 point = gl_in[0].gl_Position.xyz;
99+
vec3 corners[8];
100+
int i;
101+
for(i = 0; i < 8; i++)
102+
{
103+
vec3 pos = point.xyz + cube_corners[i] * 0.5;
104+
pos.y += sin(time + length(gl_in[0].gl_Position.xyz));
105+
pos.x += cos(time + gl_in[0].gl_Position.x);
106+
pos.z += cos(time + gl_in[0].gl_Position.z);
107+
108+
corners[i] = (m_mv * vec4(pos, 1.0)).xyz;
109+
}
110+
EMIT_QUAD(3, 2, 0, 1, vec3( 0.0, 0.0, -1.0)); // back
111+
EMIT_QUAD(6, 7, 5, 4, vec3( 0.0, 0.0, 1.0)); // front
112+
EMIT_QUAD(7, 3, 4, 0, vec3( 1.0, 0.0, 0.0)); // right
113+
EMIT_QUAD(2, 6, 1, 5, vec3(-1.0, 0.0, 0.0)); // left
114+
EMIT_QUAD(5, 4, 1, 0, vec3( 0.0, 1.0, 0.0)); // top
115+
EMIT_QUAD(2, 3, 6, 7, vec3( 0.0, -1.0, 0.0)); // bottom
116+
EndPrimitive();
117+
}
118+
119+
#endif
Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
#version 410
2+
3+
#if defined VERTEX_SHADER
4+
5+
uniform vec2 uv_scale;
6+
in vec3 in_Position;
7+
in vec2 in_UV0;
8+
9+
out vec2 uv0;
10+
11+
void main() {
12+
gl_Position = vec4(in_Position, 1.0);
13+
uv0 = (in_UV0 - vec2(0.5)) * uv_scale;
14+
}
15+
16+
#elif defined FRAGMENT_SHADER
17+
18+
out vec4 fragColor;
19+
uniform sampler2D texture0;
20+
21+
in vec2 uv0;
22+
23+
void main()
24+
{
25+
fragColor = texture(texture0, uv0);
26+
}
27+
28+
#endif
550 KB
Loading
505 KB
Loading

examples/images/geocubes.png

3.72 MB
Loading

0 commit comments

Comments
 (0)