@@ -4,7 +4,7 @@ use re::prelude::*;
44
55use re:: core:: math:: color:: gray;
66use re:: core:: render:: {
7- cam:: { FirstPerson , Fov , PitchYawRoll } ,
7+ cam:: { Fov , PitchYawRoll } ,
88 clip:: Status :: * ,
99 scene:: Obj ,
1010 tex:: SamplerClamp ,
@@ -14,6 +14,7 @@ use re::core::util::{pixfmt::Rgba8888, pnm::read_pnm};
1414
1515use re:: front:: sdl2:: Window ;
1616use re:: geom:: solids:: { Build , Cube } ;
17+ use re:: prelude:: rand:: { DefaultRng , Distrib , Uniform } ;
1718
1819fn main ( ) {
1920 let mut win = Window :: builder ( )
@@ -25,16 +26,19 @@ fn main() {
2526 let tex_data = * include_bytes ! ( "../../assets/crate.ppm" ) ;
2627 let tex = Texture :: from ( read_pnm ( & tex_data[ ..] ) . expect ( "data exists" ) ) ;
2728
28- let light_dir = vec3 ( -2.0 , 1 .0, -4.0 ) . normalize ( ) ;
29+ let light_dir = vec3 ( -2.0 , 5 .0, -4.0 ) . normalize ( ) ;
2930
30- let floor_shader = shader:: new (
31- |v : Vertex3 < _ > , mvp : & ProjMat3 < _ > | vertex ( mvp. apply ( & v. pos ) , v. attrib ) ,
32- |frag : Frag < Vec2 > | {
33- let even_odd = ( frag. var . x ( ) > 0.5 ) ^ ( frag. var . y ( ) > 0.5 ) ;
34- gray ( if even_odd { 0.8 } else { 0.1 } ) . to_color4 ( )
31+ let terrain_shader = shader:: new (
32+ |v : Vertex3 < Normal3 > , mvp : & ProjMat3 < _ > | {
33+ vertex ( mvp. apply ( & v. pos ) , ( v. pos , v. attrib ) )
34+ } ,
35+ |frag : Frag < ( Point3 < Model > , Normal3 ) > | {
36+ let l = frag. var . 1 . dot ( & light_dir) . max ( 0.2 ) ;
37+ let h = ( frag. var . 0 . y ( ) / 4.0 ) . rem_euclid ( 1.0 ) ;
38+ gray ( if h > 0.95 { 0.1 } else { l } ) . to_color4 ( )
3539 } ,
3640 ) ;
37- let crate_shader = shader:: new (
41+ let _crate_shader = shader:: new (
3842 |v : Vertex3 < ( Normal3 , TexCoord ) > , mvp : & ProjMat3 < _ > | {
3943 vertex ( mvp. apply ( & v. pos ) , v. attrib )
4044 } ,
@@ -54,7 +58,6 @@ fn main() {
5458 . perspective ( Fov :: Diagonal ( degs ( 90.0 ) ) , 0.1 ..1000.0 ) ;
5559
5660 let floor = floor ( ) ;
57- let crates = crates ( ) ;
5861
5962 let mut target_vel_z = 0.0 ;
6063 let mut cam_vel = Vec3 :: zero ( ) ;
@@ -75,8 +78,8 @@ fn main() {
7578 for key in ep. keyboard_state ( ) . pressed_scancodes ( ) {
7679 use sdl2:: keyboard:: Scancode as Sc ;
7780 match key {
78- Sc :: W => target_vel_z += 0.1 ,
79- Sc :: S => target_vel_z -= 0.05 ,
81+ Sc :: W => target_vel_z += 10.0 ,
82+ Sc :: S => target_vel_z -= 10.0 ,
8083 Sc :: A => tr = rv,
8184 Sc :: D => tr = -rv,
8285
@@ -99,8 +102,8 @@ fn main() {
99102 . view_to_world ( )
100103 . apply ( & ( target_vel_z * Vec3 :: Z ) ) ;
101104
102- let acc = 8 .0;
103- cam_vel = cam_vel. lerp ( & target_vel, acc * dt) ;
105+ let acc = 20 .0;
106+ cam_vel = cam_vel. lerp ( & target_vel, ( acc * dt) . min ( 1.0 ) ) ;
104107
105108 cam. transform . rotate ( p, y, r) ;
106109
@@ -126,15 +129,15 @@ fn main() {
126129 let mut b = batch
127130 . clone ( )
128131 . mesh ( geom)
129- . shader ( floor_shader )
132+ . shader ( terrain_shader )
130133 . uniform ( & model_to_project) ;
131134 b. render ( ) ;
132135 }
133136 }
134137
135138 // Crates
136139
137- for Obj { geom, bbox, tf } in & crates {
140+ /* for Obj { geom, bbox, tf } in &crates {
138141 frame.ctx.stats.borrow_mut().objs.i += 1;
139142
140143 let model_to_project = tf.then(&world_to_project);
@@ -153,41 +156,170 @@ fn main() {
153156 .render();
154157
155158 frame.ctx.stats.borrow_mut().objs.o += 1;
156- }
159+ }*/
157160
158161 Continue ( ( ) )
159162 } )
160163 . expect ( "should run" ) ;
161164}
162165
163- fn crates ( ) -> Vec < Obj < ( Normal3 , TexCoord ) > > {
164- let obj = Obj :: new ( Cube { side_len : 2.0 } . build ( ) ) ;
165-
166- let mut res = vec ! [ ] ;
167- let n = 30 ;
168- for i in ( -n..=n) . step_by ( 5 ) {
169- for j in ( -n..=n) . step_by ( 5 ) {
170- res. push ( Obj {
171- tf : translate3 ( i as f32 , 0.0 , j as f32 ) . to ( ) ,
172- // TODO Same geometry cloned many times
173- ..obj. clone ( )
174- } ) ;
166+ #[ inline( never) ]
167+ fn diamond_square ( n : u32 ) -> Buf2 < f32 > {
168+ let mut buf = Buf2 :: new_with ( ( n + 1 , n + 1 ) , |_, _| f32:: NAN ) ;
169+ let rng = & mut DefaultRng :: from_time ( ) ;
170+ let heights = Uniform ( -1.0 ..1.0 ) ;
171+
172+ buf[ [ 0 , 0 ] ] = 0.0 ; //dbg!(heights.sample(rng));
173+ buf[ [ 0 , n] ] = 0.0 ; //dbg!(heights.sample(rng));
174+ buf[ [ n, 0 ] ] = 0.0 ; //dbg!(heights.sample(rng));
175+ buf[ [ n, n] ] = 0.0 ; //dbg!(heights.sample(rng));
176+ let mut s = n;
177+
178+ let mut scale = 1.0 ;
179+
180+ while s > 0 {
181+ // Diamond phase
182+ eprintln ! ( "Starting diamond phase {s}..." ) ;
183+
184+ for j in ( 0 ..n) . step_by ( s as usize ) {
185+ for i in ( 0 ..n) . step_by ( s as usize ) {
186+ let p0 = pt2 ( i, j) ;
187+ let p1 = pt2 ( i + s, j + s) ;
188+ let c = pt2 ( p0. x ( ) . midpoint ( p1. x ( ) ) , p0. y ( ) . midpoint ( p1. y ( ) ) ) ;
189+
190+ let mean = ( buf[ p0]
191+ + buf[ pt2 ( p1. x ( ) , p0. y ( ) ) ]
192+ + buf[ pt2 ( p0. x ( ) , p1. y ( ) ) ]
193+ + buf[ p1] )
194+ / 4.0 ;
195+
196+ buf[ c] = mean + heights. sample ( rng) * scale;
197+ }
175198 }
199+
200+ // eprintln!("After diamond phase {s}:");
201+ // for row in buf.rows() {
202+ // for &c in row {
203+ // if c.is_nan() {
204+ // eprint!(" ____");
205+ // } else {
206+ // eprint!(" {c:-4.1}");
207+ // }
208+ // }
209+ // eprintln!();
210+ // }
211+
212+ eprintln ! ( "Starting square phase {s}..." ) ;
213+ // Square phase
214+ for j in ( 0 ..n) . step_by ( s as usize ) {
215+ for i in ( 0 ..n) . step_by ( s as usize ) {
216+ //
217+ // / \
218+ // / \
219+ // (i,j)---(i+s,j)
220+ // / | \ /
221+ // / | \ /
222+ // \ | /
223+ // \ | /
224+ // (i,j+s)
225+ //
226+
227+ let mean_u = if s / 2 <= j {
228+ ( buf[ [ i, j] ]
229+ + buf[ [ i + s, j] ]
230+ + buf[ [ i + s / 2 , j - s / 2 ] ]
231+ + buf[ [ i + s / 2 , j + s / 2 ] ] )
232+ / 4.0
233+ } else {
234+ ( buf[ [ i, j] ]
235+ + buf[ [ i + s, j] ]
236+ + buf[ [ i + s / 2 , j + s / 2 ] ] )
237+ / 3.0
238+ } ;
239+ let mean_d = if j + s + s / 2 <= n {
240+ ( buf[ [ i, j + s] ]
241+ + buf[ [ i + s, j + s] ]
242+ + buf[ [ i + s / 2 , j + s / 2 ] ]
243+ + buf[ [ i + s / 2 , j + s + s / 2 ] ] )
244+ / 4.0
245+ } else {
246+ ( buf[ [ i, j + s] ]
247+ + buf[ [ i + s, j + s] ]
248+ + buf[ [ i + s / 2 , j + s / 2 ] ] )
249+ / 3.0
250+ } ;
251+ let mean_l = if s / 2 <= i {
252+ ( buf[ [ i, j] ]
253+ + buf[ [ i, j + s] ]
254+ + buf[ [ i - s / 2 , j + s / 2 ] ]
255+ + buf[ [ i + s / 2 , j + s / 2 ] ] )
256+ / 4.0
257+ } else {
258+ ( buf[ [ i, j] ]
259+ + buf[ [ i, j + s] ]
260+ + buf[ [ i + s / 2 , j + s / 2 ] ] )
261+ / 3.0
262+ } ;
263+ let mean_r = if i + s + s / 2 <= n {
264+ ( buf[ [ i + s, j] ]
265+ + buf[ [ i + s, j + s] ]
266+ + buf[ [ i + s / 2 , j + s / 2 ] ]
267+ + buf[ [ i + s + s / 2 , j + s / 2 ] ] )
268+ / 4.0
269+ } else {
270+ ( buf[ [ i + s, j] ]
271+ + buf[ [ i + s, j + s] ]
272+ + buf[ [ i + s / 2 , j + s / 2 ] ] )
273+ / 3.0
274+ } ;
275+
276+ buf[ [ i, j + s / 2 ] ] = mean_l + heights. sample ( rng) * scale;
277+ buf[ [ i + s / 2 , j] ] = mean_u + heights. sample ( rng) * scale;
278+ buf[ [ i + s, j + s / 2 ] ] = mean_r + heights. sample ( rng) * scale;
279+ buf[ [ i + s / 2 , j + s] ] = mean_d + heights. sample ( rng) * scale;
280+ }
281+ }
282+
283+ // eprintln!("After square phase {s}:");
284+ // for row in buf.rows() {
285+ // for &c in row {
286+ // if c.is_nan() {
287+ // eprint!(" ____");
288+ // } else {
289+ // eprint!(" {c:-4.1}");
290+ // }
291+ // }
292+ // eprintln!();
293+ // }
294+
295+ scale /= 2.0 ;
296+ s /= 2 ;
176297 }
177- res
298+
299+ buf
178300}
179- fn floor ( ) -> Obj < Vec2 > {
301+
302+ #[ inline( never) ]
303+ fn floor ( ) -> Obj < Normal3 > {
180304 let mut bld = Mesh :: builder ( ) ;
181305
182- let size = 50 ;
306+ let hf = diamond_square ( 512 ) ;
307+
308+ let size = 256 ;
183309 for j in -size..=size {
184310 for i in -size..=size {
185311 let i_odd = i & 1 ;
186312 let j_odd = j & 1 ;
187313
188- let pos = pt3 ( i as f32 , -1.0 , j as f32 ) ;
189- let attrib = vec2 ( i_odd as f32 , j_odd as f32 ) ;
190- bld. push_vert ( pos, attrib) ;
314+ let h = -32.0
315+ + 64.0
316+ * smoothstep ( smootherstep (
317+ hf[ [ ( i + size) as u32 , ( j + size) as u32 ] ] * 0.5 + 0.5 ,
318+ ) ) ;
319+
320+ let pos = pt3 ( i as f32 , -1.0 + h, j as f32 ) ;
321+ //let attrib = vec2(i_odd as f32, j_odd as f32);
322+ bld. push_vert ( pos, ( ) ) ;
191323
192324 if j > -size && i > -size {
193325 let w = size * 2 + 1 ;
@@ -211,5 +343,5 @@ fn floor() -> Obj<Vec2> {
211343 }
212344 }
213345 }
214- Obj :: new ( bld. build ( ) )
346+ Obj :: new ( bld. with_vertex_normals ( ) . build ( ) )
215347}
0 commit comments