1extern crate neocogi;
31
32use neocogi::glfw;
33use neocogi::glfw::{Action, Context, Key};
34
35use neocogi::rs_math3d::*;
36use neocogi::*;
37
38use neocogi::renderer::*;
39
40use std::sync::*;
41
42static VERTEX_SHADER: &'static str = "
43#version 300 es
44in highp vec4 position;
45in highp vec4 color;
46out highp vec4 v_color;
47void main() {
48 gl_Position = position;
49 v_color = color;
50}";
51
52static PIXEL_SHADER: &'static str = "
53#version 300 es
54precision mediump float;
55 in highp vec4 v_color;
56layout(location = 0) out lowp vec4 color_buffer;
57void main() {
58 highp vec4 col = v_color;
59 color_buffer = col;
60}";
61
62render_data! {
63 vertex Vertex {
64 position: Vec4f,
65 color : Vec4f,
66 }
67}
68
69fn init_render_objects(driver: &mut DriverPtr) -> PipelinePtr {
70 let mut model_attribs = Vec::new();
71 model_attribs.push(Vertex::get_attribute_names());
72
73 let model_shader_desc = ShaderDesc {
74 vertex_shader: String::from(VERTEX_SHADER),
75 pixel_shader: String::from(PIXEL_SHADER),
76
77 vertex_attributes: model_attribs,
78 vertex_uniforms: Vec::new(),
79 vertex_surfaces: Vec::new(),
80
81 pixel_uniforms: Vec::new(),
82 pixel_surfaces: Vec::new(),
83 };
84
85 let model_program = driver.create_shader(model_shader_desc).unwrap();
86
87 let vertex_layout = VertexBufferLayout {
88 buffer_id: 0,
89 vertex_attributes: Vertex::get_attribute_descriptors(),
90 stride: Vertex::stride(),
91 divisor: 0,
92 };
93
94 let tri_pipeline_desc = PipelineDesc {
95 primitive_type: PrimitiveType::Triangles,
96 shader: model_program.clone(),
97 buffer_layouts: vec![vertex_layout.clone()],
98 uniform_descs: Vec::new(),
99 index_type: IndexType::None,
100 face_winding: FaceWinding::CCW,
101 cull_mode: CullMode::None,
102 depth_write: true,
103 depth_test: true,
104 blend: BlendOp::None,
105 polygon_offset: PolygonOffset::None,
106 };
107
108 driver.create_pipeline(tri_pipeline_desc).unwrap()
109}
110
111fn main() {
112 let mut glfw = glfw::init(glfw::FAIL_ON_ERRORS).unwrap();
114 glfw.window_hint(glfw::WindowHint::ContextCreationApi(
115 glfw::ContextCreationApi::Egl,
116 ));
117 glfw.window_hint(glfw::WindowHint::ClientApi(glfw::ClientApiHint::OpenGlEs));
118 glfw.window_hint(glfw::WindowHint::ContextVersion(3, 0));
119 glfw.window_hint(glfw::WindowHint::OpenGlProfile(
120 glfw::OpenGlProfileHint::Core,
121 ));
122 glfw.window_hint(glfw::WindowHint::DoubleBuffer(true));
123 glfw.window_hint(glfw::WindowHint::Resizable(true));
124 glfw.window_hint(glfw::WindowHint::Floating(true));
125
126 let (mut window, events) = glfw
127 .create_window(1024, 900, "Triangle", glfw::WindowMode::Windowed)
128 .expect("Failed to create GLFW window.");
129
130 window.set_char_polling(true);
131 window.set_cursor_pos_polling(true);
132 window.set_key_polling(true);
133 window.set_mouse_button_polling(true);
134 window.make_current();
135 glfw.set_swap_interval(glfw::SwapInterval::Sync(1));
136
137 let mut driver = renderer::get_driver();
138
139 let vertices = vec![
140 Vertex {
141 position: Vec4f::new(-0.5, -0.5, 0.0, 1.0),
142 color: Vec4f::new(1.0, 0.0, 0.0, 1.0),
143 },
144 Vertex {
145 position: Vec4f::new(0.5, -0.5, 0.0, 1.0),
146 color: Vec4f::new(0.0, 0.0, 1.0, 1.0),
147 },
148 Vertex {
149 position: Vec4f::new(0.0, 0.5, 0.0, 1.0),
150 color: Vec4f::new(0.0, 1.0, 0.0, 1.0),
151 },
152 ];
153
154 let mut vertex_buffer = driver
155 .create_device_buffer(DeviceBufferDesc::Vertex(Usage::Dynamic(
156 3 * std::mem::size_of::<Vertex>(),
157 )))
158 .unwrap();
159 let pipeline = init_render_objects(&mut driver);
160
161 let mut quit = false;
162 while !window.should_close() {
163 let (width, height) = window.get_framebuffer_size();
164
165 let mut pass = Pass::new(
166 width as usize,
167 height as usize,
168 None,
169 [
170 ColorPassAction::Clear(color4b(0x00, 0x00, 0x00, 0x00)),
171 ColorPassAction::Previous,
172 ColorPassAction::Previous,
173 ColorPassAction::Previous,
174 ],
175 DepthPassAction::Clear(1.0),
176 );
177
178 let bindings = Bindings {
179 vertex_buffers: vec![vertex_buffer.clone()],
180 index_buffer: None,
181
182 vertex_images: Vec::new(),
183 pixel_images: Vec::new(),
184 };
185
186 pass.update_device_buffer(&mut vertex_buffer, 0, Arc::new(vertices.to_vec()));
187 pass.draw(&pipeline, &bindings, Arc::new(Vec::<Vec3f>::new()), 1, 1);
188 driver.render_pass(&mut pass);
189 window.swap_buffers();
190
191 glfw.poll_events();
192 for (_, event) in glfw::flush_messages(&events) {
193 match event {
194 glfw::WindowEvent::Key(glfw::Key::Escape, _, _, _) | glfw::WindowEvent::Close => {
195 quit = true
196 }
197 _ => (),
198 }
199 }
200
201 if quit {
202 window.set_should_close(true)
203 }
204 }
205}