diff options
| author | tslil clingman <> | 2021-09-06 20:22:58 -0400 |
|---|---|---|
| committer | tslil clingman <> | 2021-09-06 20:40:17 -0400 |
| commit | cf1eb8fc551f5f3ee3bc0054fc236ff7d201f44a (patch) | |
| tree | d1407665d0e9b962fb89a5f68e20e9559b7ce59f | |
| parent | 631c1226691505624c08995b6a2ac81e46a9b17e (diff) | |
Only attempt to render cells with h > 0
| -rw-r--r-- | src/raycast.zig | 80 |
1 files changed, 41 insertions, 39 deletions
diff --git a/src/raycast.zig b/src/raycast.zig index e1bfce0..2a9b0a1 100644 --- a/src/raycast.zig +++ b/src/raycast.zig @@ -38,6 +38,13 @@ pub const RenderSliceFunction: type = fn ( ) void; pub fn Player(PlaneWidth: f32, PlaneHeight: f32) type { + const FOV: f32 = std.math.pi / 3.0; + const PlanePixels = PlaneWidth * PlaneHeight; + // given the desired width of the image, how far away must + // the projection plane be from the camera? + const FOV_SCALE = 2 * std.math.tan(FOV / 2); + const PlaneDist = PlaneWidth / FOV_SCALE; + return struct { pos_x: f32, pos_y: f32, @@ -46,17 +53,9 @@ pub fn Player(PlaneWidth: f32, PlaneHeight: f32) type { vel_y: f32 = 0, acc_x: f32 = 0, acc_y: f32 = 0, - fov: f32 = std.math.pi / 3.0, height: f32 = 1.8 / 2.5, // TODO z_buffer: std.BoundedArray(f32, PlanePixels), - const FOV: f32 = std.math.pi / 3.0; - const PlanePixels = PlaneWidth * PlaneHeight; - // given the desired width of the image, how far away must - // the projection plane be from the camera? - const FOV_SCALE = 2 * std.math.tan(FOV / 2); - const PlaneDist = PlaneWidth / FOV_SCALE; - // standing still at the given location, looking in direction ang, pub fn new(pos_x: f32, pos_y: f32, ang: f32) !@This() { const infs = [_]f32{std.math.inf(f32)} ** PlanePixels; @@ -269,46 +268,49 @@ pub fn Player(PlaneWidth: f32, PlaneHeight: f32) type { ipos_y += step_y; } }) { - var cell = map.lookup(ipos_x, ipos_y); + const cell = map.lookup(ipos_x, ipos_y); - // project the top of the wall - var top = PlaneHeight / 2 + PlaneDist * (cell.height - self.height) / distance; + // Is there a wall? + if (cell.height > 0) { + // project the top of the wall + var top = PlaneHeight / 2 + PlaneDist * (cell.height - self.height) / distance; + // We have a wall to draw if it protrudes above what we have so far drawn + if (top > highest_point) { - // We have a wall to draw if it protrudes above what we have so far drawn - if (top > highest_point) { + // did we extend beyond the top of the plane? + if (top > PlaneHeight) { + still_drawing = false; + } - // did we extend beyond the top of the plane? - if (top > PlaneHeight) { - still_drawing = false; - } + // compute the height of this wall + const total_length = PlaneDist * cell.height / distance; - // compute the height of this wall - const total_length = PlaneDist * cell.height / distance; + // as well as the fraction we'll be drawing + const draw_length = top - highest_point; + const draw_frac = std.math.clamp(draw_length / total_length, 0, 1); - // as well as the fraction we'll be drawing - const draw_length = top - highest_point; - const draw_frac = std.math.clamp(draw_length / total_length, 0, 1); + // we need the distance to calculate the fractional + // part of the relevant coordinate for texture + // mapping of the walls + const hit_coordinate = if (horizontal_hit) distance * cosra + self.pos_x else distance * sinra + self.pos_y; + var texfrac = std.math.modf(hit_coordinate).fpart; - // we need the raw Euclidean distance to calculate the - // fractional part of the relevant coordinate for texture - // mapping of the walls - const hit_coordinate = if (horizontal_hit) distance * cosra + self.pos_x else distance * sinra + self.pos_y; - var texfrac = std.math.modf(hit_coordinate).fpart; - // we also want to be sure that we're consistently orienting - // textures, in this case clockwise - if ((horizontal_hit and sinra < 0) or (!horizontal_hit and cosra > 0)) texfrac = 1 - texfrac; + // we also want to be sure that we're consistently orienting + // textures, in this case clockwise + if ((horizontal_hit and sinra < 0) or (!horizontal_hit and cosra > 0)) texfrac = 1 - texfrac; - // draw the wall - renderSlice(window, walls_sprite, col, top, total_length, draw_frac, texfrac, cell.wall_texture); + // draw the wall + renderSlice(window, walls_sprite, col, top, total_length, draw_frac, texfrac, cell.wall_texture); - // record that there's a wall here in the z_buffer - var y = @floatToInt(i32, std.math.min(top, PlaneHeight - 1)); - while (y > @floatToInt(i32, highest_point)) : (y -= 1) { - const index = @intCast(usize, col * @floatToInt(i32, PlaneHeight) + y); - self.z_buffer.set(index, distance); - } + // record that there's a wall here in the z_buffer + var y = @floatToInt(i32, std.math.min(top, PlaneHeight - 1)); + while (y > @floatToInt(i32, highest_point)) : (y -= 1) { + const index = @intCast(usize, col * @floatToInt(i32, PlaneHeight) + y); + self.z_buffer.set(index, distance); + } - highest_point = top; + highest_point = top; + } } } } |
