1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
use gl;
use gl::types::*;
use na::Vector2;
use resource::{BufferType, AllocationType, Shader, ShaderUniform, ShaderAttribute, RenderTarget, GPUVec};
use post_processing::post_processing_effect::PostProcessingEffect;
#[path = "../error.rs"]
mod error;
pub struct Waves {
shader: Shader,
time: f32,
offset: ShaderUniform<GLfloat>,
fbo_texture: ShaderUniform<GLint>,
v_coord: ShaderAttribute<Vector2<f32>>,
fbo_vertices: GPUVec<Vector2<GLfloat>>
}
impl Waves {
pub fn new() -> Waves {
let fbo_vertices: Vec<Vector2<GLfloat>> = vec!(
Vector2::new(-1.0, -1.0),
Vector2::new(1.0, -1.0),
Vector2::new(-1.0, 1.0),
Vector2::new(1.0, 1.0));
let mut fbo_vertices = GPUVec::new(fbo_vertices, BufferType::Array, AllocationType::StaticDraw);
fbo_vertices.load_to_gpu();
fbo_vertices.unload_from_ram();
let mut shader = Shader::new_from_str(VERTEX_SHADER, FRAGMENT_SHADER);
shader.use_program();
Waves {
time: 0.0,
offset: shader.get_uniform("offset").unwrap(),
fbo_texture: shader.get_uniform("fbo_texture").unwrap(),
v_coord: shader.get_attrib("v_coord").unwrap(),
fbo_vertices: fbo_vertices,
shader: shader
}
}
}
impl PostProcessingEffect for Waves {
fn update(&mut self, dt: f32, _: f32, _: f32, _: f32, _: f32) {
self.time = self.time + dt;
}
fn draw(&mut self, target: &RenderTarget) {
self.shader.use_program();
let move_amount = self.time * 2.0 * 3.14159 * 0.75;
self.offset.upload(&move_amount);
verify!(gl::ClearColor(0.0, 0.0, 0.0, 1.0));
verify!(gl::Clear(gl::COLOR_BUFFER_BIT | gl::DEPTH_BUFFER_BIT));
verify!(gl::BindTexture(gl::TEXTURE_2D, target.texture_id()));
self.fbo_texture.upload(&0);
self.v_coord.enable();
self.v_coord.bind(&mut self.fbo_vertices);
verify!(gl::DrawArrays(gl::TRIANGLE_STRIP, 0, 4));
self.v_coord.disable();
}
}
static VERTEX_SHADER: &'static str =
"#version 120
attribute vec2 v_coord;
uniform sampler2D fbo_texture;
varying vec2 f_texcoord;
void main(void) {
gl_Position = vec4(v_coord, 0.0, 1.0);
f_texcoord = (v_coord + 1.0) / 2.0;
}";
static FRAGMENT_SHADER: &'static str =
"#version 120
uniform sampler2D fbo_texture;
uniform float offset;
varying vec2 f_texcoord;
void main(void) {
vec2 texcoord = f_texcoord;
texcoord.x += sin(texcoord.y * 4 * 2 * 3.14159 + offset) / 100;
gl_FragColor = texture2D(fbo_texture, texcoord);
}";