Merge branch 'main' of ssh://git.sijman.nl:221/_/minecrab
All checks were successful
continuous-integration/drone/push Build is passing
All checks were successful
continuous-integration/drone/push Build is passing
This commit is contained in:
commit
b13be0ebc1
8 changed files with 154 additions and 147 deletions
|
@ -1,9 +1,7 @@
|
||||||
mod aabb;
|
mod aabb;
|
||||||
mod camera;
|
mod camera;
|
||||||
mod chunk;
|
|
||||||
mod geometry;
|
mod geometry;
|
||||||
mod npc;
|
mod npc;
|
||||||
mod quad;
|
|
||||||
mod render_context;
|
mod render_context;
|
||||||
mod renderable;
|
mod renderable;
|
||||||
mod state;
|
mod state;
|
||||||
|
|
|
@ -287,8 +287,8 @@ impl HudState {
|
||||||
pub const HUD_VERTICES: [HudVertex; 12] = [
|
pub const HUD_VERTICES: [HudVertex; 12] = [
|
||||||
// Crosshair
|
// Crosshair
|
||||||
HudVertex { position: [UI_SCALE_X * -8.0, UI_SCALE_Y * 8.0], texture_coordinates: [240.0 / 256.0, 0.0 / 256.0] },
|
HudVertex { position: [UI_SCALE_X * -8.0, UI_SCALE_Y * 8.0], texture_coordinates: [240.0 / 256.0, 0.0 / 256.0] },
|
||||||
HudVertex { position: [UI_SCALE_X * 8.0, UI_SCALE_Y * 8.0], texture_coordinates: [256.0 / 256.0, 0.0 / 256.0] },
|
HudVertex { position: [UI_SCALE_X * 8.0, UI_SCALE_Y * 8.0], texture_coordinates: [ 1.0, 0.0 / 256.0] },
|
||||||
HudVertex { position: [UI_SCALE_X * 8.0, UI_SCALE_Y * -8.0], texture_coordinates: [256.0 / 256.0, 16.0 / 256.0] },
|
HudVertex { position: [UI_SCALE_X * 8.0, UI_SCALE_Y * -8.0], texture_coordinates: [ 1.0, 16.0 / 256.0] },
|
||||||
HudVertex { position: [UI_SCALE_X * -8.0, UI_SCALE_Y * -8.0], texture_coordinates: [240.0 / 256.0, 16.0 / 256.0] },
|
HudVertex { position: [UI_SCALE_X * -8.0, UI_SCALE_Y * -8.0], texture_coordinates: [240.0 / 256.0, 16.0 / 256.0] },
|
||||||
|
|
||||||
// Hotbar
|
// Hotbar
|
||||||
|
|
|
@ -20,8 +20,8 @@ pub const PRIMITIVE_STATE: wgpu::PrimitiveState = wgpu::PrimitiveState {
|
||||||
strip_index_format: None,
|
strip_index_format: None,
|
||||||
front_face: wgpu::FrontFace::Ccw,
|
front_face: wgpu::FrontFace::Ccw,
|
||||||
cull_mode: None,
|
cull_mode: None,
|
||||||
polygon_mode: wgpu::PolygonMode::Fill,
|
|
||||||
clamp_depth: false,
|
clamp_depth: false,
|
||||||
|
polygon_mode: wgpu::PolygonMode::Fill,
|
||||||
conservative: false,
|
conservative: false,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -47,6 +47,7 @@ impl State {
|
||||||
})
|
})
|
||||||
.await
|
.await
|
||||||
.unwrap();
|
.unwrap();
|
||||||
|
println!("Using {:?}", adapter.get_info().backend);
|
||||||
|
|
||||||
let (render_device, queue) = adapter
|
let (render_device, queue) = adapter
|
||||||
.request_device(
|
.request_device(
|
||||||
|
|
41
src/world/block.rs
Normal file
41
src/world/block.rs
Normal file
|
@ -0,0 +1,41 @@
|
||||||
|
use serde::{Deserialize, Serialize};
|
||||||
|
use serde_repr::{Deserialize_repr, Serialize_repr};
|
||||||
|
|
||||||
|
#[allow(dead_code)]
|
||||||
|
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash, Serialize_repr, Deserialize_repr)]
|
||||||
|
#[repr(u8)]
|
||||||
|
pub enum BlockType {
|
||||||
|
Cobblestone = 1,
|
||||||
|
Dirt = 2,
|
||||||
|
Stone = 3,
|
||||||
|
Grass = 4,
|
||||||
|
Bedrock = 5,
|
||||||
|
Sand = 6,
|
||||||
|
Gravel = 7,
|
||||||
|
Water = 8,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl BlockType {
|
||||||
|
#[rustfmt::skip]
|
||||||
|
pub const fn texture_indices(self) -> (usize, usize, usize, usize, usize, usize) {
|
||||||
|
match self {
|
||||||
|
BlockType::Cobblestone => ( 0, 0, 0, 0, 0, 0),
|
||||||
|
BlockType::Dirt => ( 1, 1, 1, 1, 1, 1),
|
||||||
|
BlockType::Stone => ( 2, 2, 2, 2, 2, 2),
|
||||||
|
BlockType::Grass => ( 4, 4, 4, 4, 2, 3),
|
||||||
|
BlockType::Bedrock => ( 5, 5, 5, 5, 5, 5),
|
||||||
|
BlockType::Sand => ( 6, 6, 6, 6, 6, 6),
|
||||||
|
BlockType::Gravel => ( 7, 7, 7, 7, 7, 7),
|
||||||
|
BlockType::Water => ( 8, 8, 8, 8, 8, 8), // up to 71
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub const fn is_transparent(self) -> bool {
|
||||||
|
matches!(self, BlockType::Water)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Debug, Clone, Copy, Serialize, Deserialize)]
|
||||||
|
pub struct Block {
|
||||||
|
pub block_type: BlockType,
|
||||||
|
}
|
|
@ -1,81 +1,33 @@
|
||||||
use std::{collections::VecDeque, usize};
|
use std::collections::VecDeque;
|
||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
aabb::Aabb,
|
aabb::Aabb,
|
||||||
geometry::{Geometry, GeometryBuffers},
|
geometry::{Geometry, GeometryBuffers},
|
||||||
quad::Quad,
|
render_context::RenderContext,
|
||||||
vertex::BlockVertex,
|
vertex::BlockVertex,
|
||||||
view::View,
|
view::View,
|
||||||
|
world::{
|
||||||
|
block::{Block, BlockType},
|
||||||
|
face_flags::*,
|
||||||
|
quad::Quad,
|
||||||
|
},
|
||||||
};
|
};
|
||||||
use ahash::{AHashMap, AHashSet};
|
use ahash::{AHashMap, AHashSet};
|
||||||
use cgmath::{Point3, Vector3};
|
use cgmath::{Point3, Vector3};
|
||||||
use noise::utils::{NoiseMapBuilder, PlaneMapBuilder};
|
use noise::utils::{NoiseMapBuilder, PlaneMapBuilder};
|
||||||
use rayon::iter::{IntoParallelIterator, ParallelIterator};
|
use rayon::iter::{IntoParallelIterator, ParallelIterator};
|
||||||
|
|
||||||
use serde::{
|
use serde::{
|
||||||
de::{SeqAccess, Visitor},
|
de::{SeqAccess, Visitor},
|
||||||
ser::{SerializeSeq, Serializer},
|
ser::SerializeSeq,
|
||||||
Deserialize, Serialize,
|
Deserialize, Serialize, Serializer,
|
||||||
};
|
};
|
||||||
use serde_repr::{Deserialize_repr, Serialize_repr};
|
use wgpu::BufferUsage;
|
||||||
|
|
||||||
#[allow(dead_code)]
|
|
||||||
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash, Serialize_repr, Deserialize_repr)]
|
|
||||||
#[repr(u8)]
|
|
||||||
pub enum BlockType {
|
|
||||||
Cobblestone = 1,
|
|
||||||
Dirt = 2,
|
|
||||||
Stone = 3,
|
|
||||||
Grass = 4,
|
|
||||||
Bedrock = 5,
|
|
||||||
Sand = 6,
|
|
||||||
Gravel = 7,
|
|
||||||
Water = 8,
|
|
||||||
}
|
|
||||||
|
|
||||||
impl BlockType {
|
|
||||||
#[rustfmt::skip]
|
|
||||||
pub const fn texture_indices(self) -> (usize, usize, usize, usize, usize, usize) {
|
|
||||||
match self {
|
|
||||||
BlockType::Cobblestone => ( 0, 0, 0, 0, 0, 0),
|
|
||||||
BlockType::Dirt => ( 1, 1, 1, 1, 1, 1),
|
|
||||||
BlockType::Stone => ( 2, 2, 2, 2, 2, 2),
|
|
||||||
BlockType::Grass => ( 4, 4, 4, 4, 2, 3),
|
|
||||||
BlockType::Bedrock => ( 5, 5, 5, 5, 5, 5),
|
|
||||||
BlockType::Sand => ( 6, 6, 6, 6, 6, 6),
|
|
||||||
BlockType::Gravel => ( 7, 7, 7, 7, 7, 7),
|
|
||||||
BlockType::Water => ( 8, 8, 8, 8, 8, 8), // up to 71
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
pub const fn is_transparent(self) -> bool {
|
|
||||||
matches!(self, BlockType::Water)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
pub type FaceFlags = usize;
|
|
||||||
pub const FACE_NONE: FaceFlags = 0;
|
|
||||||
pub const FACE_LEFT: FaceFlags = 1;
|
|
||||||
pub const FACE_RIGHT: FaceFlags = 2;
|
|
||||||
pub const FACE_BOTTOM: FaceFlags = 4;
|
|
||||||
pub const FACE_TOP: FaceFlags = 8;
|
|
||||||
pub const FACE_BACK: FaceFlags = 16;
|
|
||||||
pub const FACE_FRONT: FaceFlags = 32;
|
|
||||||
pub const FACE_ALL: FaceFlags =
|
|
||||||
FACE_LEFT | FACE_RIGHT | FACE_BOTTOM | FACE_TOP | FACE_BACK | FACE_FRONT;
|
|
||||||
|
|
||||||
#[derive(Debug, Clone, Copy, Serialize, Deserialize)]
|
|
||||||
pub struct Block {
|
|
||||||
pub block_type: BlockType,
|
|
||||||
}
|
|
||||||
|
|
||||||
pub const CHUNK_SIZE: usize = 32;
|
pub const CHUNK_SIZE: usize = 32;
|
||||||
pub const CHUNK_ISIZE: isize = CHUNK_SIZE as isize;
|
pub const CHUNK_ISIZE: isize = CHUNK_SIZE as isize;
|
||||||
|
|
||||||
type ChunkBlocks = [[[Option<Block>; CHUNK_SIZE]; CHUNK_SIZE]; CHUNK_SIZE];
|
|
||||||
|
|
||||||
pub struct Chunk {
|
pub struct Chunk {
|
||||||
pub blocks: ChunkBlocks,
|
pub blocks: [[[Option<Block>; CHUNK_SIZE]; CHUNK_SIZE]; CHUNK_SIZE],
|
||||||
pub buffers: Option<GeometryBuffers<u16>>,
|
pub buffers: Option<GeometryBuffers<u16>>,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -88,23 +40,6 @@ impl Default for Chunk {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Serialize for Chunk {
|
|
||||||
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
|
|
||||||
where
|
|
||||||
S: Serializer,
|
|
||||||
{
|
|
||||||
let mut seq = serializer.serialize_seq(Some(CHUNK_SIZE.pow(3)))?;
|
|
||||||
for layer in self.blocks.iter() {
|
|
||||||
for row in layer {
|
|
||||||
for block in row {
|
|
||||||
seq.serialize_element(block)?;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
seq.end()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
struct ChunkVisitor;
|
struct ChunkVisitor;
|
||||||
|
|
||||||
impl<'de> Visitor<'de> for ChunkVisitor {
|
impl<'de> Visitor<'de> for ChunkVisitor {
|
||||||
|
@ -131,6 +66,23 @@ impl<'de> Visitor<'de> for ChunkVisitor {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl Serialize for Chunk {
|
||||||
|
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
|
||||||
|
where
|
||||||
|
S: Serializer,
|
||||||
|
{
|
||||||
|
let mut seq = serializer.serialize_seq(Some(CHUNK_SIZE.pow(3)))?;
|
||||||
|
for layer in self.blocks.iter() {
|
||||||
|
for row in layer {
|
||||||
|
for block in row {
|
||||||
|
seq.serialize_element(block)?;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
seq.end()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
impl<'de> Deserialize<'de> for Chunk {
|
impl<'de> Deserialize<'de> for Chunk {
|
||||||
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
|
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
|
||||||
where
|
where
|
||||||
|
@ -218,6 +170,22 @@ impl Chunk {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn block_coords_to_local(
|
||||||
|
chunk_coords: Point3<isize>,
|
||||||
|
block_coords: Point3<isize>,
|
||||||
|
) -> Option<Vector3<usize>> {
|
||||||
|
let chunk_position = chunk_coords * CHUNK_ISIZE;
|
||||||
|
let position = block_coords - chunk_position;
|
||||||
|
if (0..CHUNK_ISIZE).contains(&position.x)
|
||||||
|
&& (0..CHUNK_ISIZE).contains(&position.y)
|
||||||
|
&& (0..CHUNK_ISIZE).contains(&position.z)
|
||||||
|
{
|
||||||
|
Some(position.cast().unwrap())
|
||||||
|
} else {
|
||||||
|
None
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
#[rustfmt::skip]
|
#[rustfmt::skip]
|
||||||
fn check_visible_faces(&self, x: usize, y: usize, z: usize) -> FaceFlags {
|
fn check_visible_faces(&self, x: usize, y: usize, z: usize) -> FaceFlags {
|
||||||
let mut visible_faces = FACE_NONE;
|
let mut visible_faces = FACE_NONE;
|
||||||
|
@ -294,7 +262,7 @@ impl Chunk {
|
||||||
offset: Point3<isize>,
|
offset: Point3<isize>,
|
||||||
culled: AHashMap<(usize, usize), (BlockType, FaceFlags)>,
|
culled: AHashMap<(usize, usize), (BlockType, FaceFlags)>,
|
||||||
queue: &mut VecDeque<(usize, usize)>,
|
queue: &mut VecDeque<(usize, usize)>,
|
||||||
highlighted: Option<&(Point3<usize>, Vector3<i32>)>,
|
highlighted: Option<(Vector3<usize>, Vector3<i32>)>,
|
||||||
) -> Vec<Quad> {
|
) -> Vec<Quad> {
|
||||||
let mut quads: Vec<Quad> = Vec::new();
|
let mut quads: Vec<Quad> = Vec::new();
|
||||||
let mut visited = AHashSet::new();
|
let mut visited = AHashSet::new();
|
||||||
|
@ -310,7 +278,7 @@ impl Chunk {
|
||||||
if let Some(&(block_type, visible_faces)) = &culled.get(&(x, z)) {
|
if let Some(&(block_type, visible_faces)) = &culled.get(&(x, z)) {
|
||||||
let mut quad_faces = visible_faces;
|
let mut quad_faces = visible_faces;
|
||||||
|
|
||||||
if hl == Some(Point3::new(x, y, z)) {
|
if hl == Some(Vector3::new(x, y, z)) {
|
||||||
let mut quad = Quad::new(position, 1, 1);
|
let mut quad = Quad::new(position, 1, 1);
|
||||||
quad.highlighted_normal = highlighted.unwrap().1;
|
quad.highlighted_normal = highlighted.unwrap().1;
|
||||||
quad.visible_faces = quad_faces;
|
quad.visible_faces = quad_faces;
|
||||||
|
@ -332,7 +300,7 @@ impl Chunk {
|
||||||
for x_ in x..CHUNK_SIZE {
|
for x_ in x..CHUNK_SIZE {
|
||||||
xmax = x_ + 1;
|
xmax = x_ + 1;
|
||||||
|
|
||||||
if visited.contains(&(xmax, z)) || hl == Some(Point3::new(xmax, y, z)) {
|
if visited.contains(&(xmax, z)) || hl == Some(Vector3::new(xmax, y, z)) {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -354,7 +322,7 @@ impl Chunk {
|
||||||
zmax = z_ + 1;
|
zmax = z_ + 1;
|
||||||
|
|
||||||
for x_ in x..xmax {
|
for x_ in x..xmax {
|
||||||
if visited.contains(&(x_, zmax)) || hl == Some(Point3::new(x_, y, zmax)) {
|
if visited.contains(&(x_, zmax)) || hl == Some(Vector3::new(x_, y, zmax)) {
|
||||||
break 'z;
|
break 'z;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -391,20 +359,30 @@ impl Chunk {
|
||||||
geometry
|
geometry
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn to_geometry(
|
pub fn update_geometry(
|
||||||
&self,
|
&mut self,
|
||||||
position: Point3<isize>,
|
render_context: &RenderContext,
|
||||||
highlighted: Option<&(Point3<usize>, Vector3<i32>)>,
|
chunk_coords: Point3<isize>,
|
||||||
) -> Geometry<BlockVertex, u16> {
|
highlighted: Option<(Point3<isize>, Vector3<i32>)>,
|
||||||
|
) {
|
||||||
|
let highlighted = highlighted.and_then(|(position, normal)| {
|
||||||
|
Self::block_coords_to_local(chunk_coords, position).map(|x| (x, normal))
|
||||||
|
});
|
||||||
|
|
||||||
|
let offset = chunk_coords * CHUNK_ISIZE;
|
||||||
let quads: Vec<Quad> = (0..CHUNK_SIZE)
|
let quads: Vec<Quad> = (0..CHUNK_SIZE)
|
||||||
.into_par_iter()
|
.into_par_iter()
|
||||||
.flat_map(|y| {
|
.flat_map(|y| {
|
||||||
let (culled, mut queue) = self.cull_layer(y);
|
let (culled, mut queue) = self.cull_layer(y);
|
||||||
self.layer_to_quads(y, position, culled, &mut queue, highlighted)
|
self.layer_to_quads(y, offset, culled, &mut queue, highlighted)
|
||||||
})
|
})
|
||||||
.collect();
|
.collect();
|
||||||
|
|
||||||
Self::quads_to_geometry(quads)
|
self.buffers = Some(GeometryBuffers::from_geometry(
|
||||||
|
render_context,
|
||||||
|
&Self::quads_to_geometry(quads),
|
||||||
|
BufferUsage::empty(),
|
||||||
|
));
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn save(&self, position: Point3<isize>, store: &sled::Db) -> anyhow::Result<()> {
|
pub fn save(&self, position: Point3<isize>, store: &sled::Db) -> anyhow::Result<()> {
|
10
src/world/face_flags.rs
Normal file
10
src/world/face_flags.rs
Normal file
|
@ -0,0 +1,10 @@
|
||||||
|
pub type FaceFlags = usize;
|
||||||
|
pub const FACE_NONE: FaceFlags = 0;
|
||||||
|
pub const FACE_LEFT: FaceFlags = 1;
|
||||||
|
pub const FACE_RIGHT: FaceFlags = 2;
|
||||||
|
pub const FACE_BOTTOM: FaceFlags = 4;
|
||||||
|
pub const FACE_TOP: FaceFlags = 8;
|
||||||
|
pub const FACE_BACK: FaceFlags = 16;
|
||||||
|
pub const FACE_FRONT: FaceFlags = 32;
|
||||||
|
pub const FACE_ALL: FaceFlags =
|
||||||
|
FACE_LEFT | FACE_RIGHT | FACE_BOTTOM | FACE_TOP | FACE_BACK | FACE_FRONT;
|
|
@ -1,18 +1,28 @@
|
||||||
use std::time::Instant;
|
pub mod block;
|
||||||
use std::{collections::VecDeque, time::Duration};
|
pub mod chunk;
|
||||||
|
pub mod face_flags;
|
||||||
|
pub mod quad;
|
||||||
|
|
||||||
|
use std::{
|
||||||
|
collections::VecDeque,
|
||||||
|
time::{Duration, Instant},
|
||||||
|
};
|
||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
camera::Camera,
|
camera::Camera,
|
||||||
chunk::{self, Block, BlockType, Chunk, CHUNK_ISIZE},
|
|
||||||
geometry::GeometryBuffers,
|
geometry::GeometryBuffers,
|
||||||
npc::Npc,
|
npc::Npc,
|
||||||
render_context::RenderContext,
|
render_context::RenderContext,
|
||||||
renderable::Renderable,
|
renderable::Renderable,
|
||||||
view::View,
|
view::View,
|
||||||
|
world::{
|
||||||
|
block::{Block, BlockType},
|
||||||
|
chunk::{Chunk, CHUNK_ISIZE},
|
||||||
|
},
|
||||||
};
|
};
|
||||||
use ahash::AHashMap;
|
use ahash::AHashMap;
|
||||||
use cgmath::{EuclideanSpace, InnerSpace, Point3, Vector3};
|
use cgmath::{EuclideanSpace, InnerSpace, Point3, Vector3};
|
||||||
use wgpu::{BufferUsage, RenderPass};
|
use wgpu::RenderPass;
|
||||||
|
|
||||||
pub struct World {
|
pub struct World {
|
||||||
pub npc: Npc,
|
pub npc: Npc,
|
||||||
|
@ -203,17 +213,7 @@ impl World {
|
||||||
chunk_position: Point3<isize>,
|
chunk_position: Point3<isize>,
|
||||||
) {
|
) {
|
||||||
let chunk = self.chunks.get_mut(&chunk_position).unwrap();
|
let chunk = self.chunks.get_mut(&chunk_position).unwrap();
|
||||||
let offset = chunk_position * CHUNK_ISIZE;
|
chunk.update_geometry(render_context, chunk_position, self.highlighted);
|
||||||
let geometry = chunk.to_geometry(
|
|
||||||
offset,
|
|
||||||
World::highlighted_for_chunk(self.highlighted, &chunk_position).as_ref(),
|
|
||||||
);
|
|
||||||
|
|
||||||
chunk.buffers = Some(GeometryBuffers::from_geometry(
|
|
||||||
render_context,
|
|
||||||
&geometry,
|
|
||||||
BufferUsage::empty(),
|
|
||||||
));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fn update_highlight(&mut self, render_context: &RenderContext, camera: &Camera) {
|
fn update_highlight(&mut self, render_context: &RenderContext, camera: &Camera) {
|
||||||
|
@ -263,29 +263,6 @@ impl World {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn highlighted_for_chunk(
|
|
||||||
highlighted: Option<(Point3<isize>, Vector3<i32>)>,
|
|
||||||
chunk_position: &Point3<isize>,
|
|
||||||
) -> Option<(Point3<usize>, Vector3<i32>)> {
|
|
||||||
let position = chunk_position * CHUNK_ISIZE;
|
|
||||||
if let Some((pos, face)) = highlighted {
|
|
||||||
if pos.x >= position.x
|
|
||||||
&& pos.x < position.x + CHUNK_ISIZE
|
|
||||||
&& pos.y >= position.y
|
|
||||||
&& pos.y < position.y + CHUNK_ISIZE
|
|
||||||
&& pos.z >= position.z
|
|
||||||
&& pos.z < position.z + CHUNK_ISIZE
|
|
||||||
{
|
|
||||||
let point: Point3<isize> = EuclideanSpace::from_vec(pos - position);
|
|
||||||
Some((point.cast().unwrap(), face))
|
|
||||||
} else {
|
|
||||||
None
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
None
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn get_block(&self, x: isize, y: isize, z: isize) -> Option<&Block> {
|
pub fn get_block(&self, x: isize, y: isize, z: isize) -> Option<&Block> {
|
||||||
let chunk = match self.chunks.get(&Point3::new(
|
let chunk = match self.chunks.get(&Point3::new(
|
||||||
x.div_euclid(CHUNK_ISIZE),
|
x.div_euclid(CHUNK_ISIZE),
|
|
@ -1,12 +1,9 @@
|
||||||
use cgmath::{Point3, Vector3, Zero};
|
use cgmath::{Point3, Vector3, Zero};
|
||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
chunk::{
|
|
||||||
BlockType, FaceFlags, FACE_ALL, FACE_BACK, FACE_BOTTOM, FACE_FRONT, FACE_LEFT, FACE_RIGHT,
|
|
||||||
FACE_TOP,
|
|
||||||
},
|
|
||||||
geometry::Geometry,
|
geometry::Geometry,
|
||||||
vertex::BlockVertex,
|
vertex::BlockVertex,
|
||||||
|
world::{block::BlockType, face_flags::*},
|
||||||
};
|
};
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
|
@ -69,11 +66,11 @@ impl Quad {
|
||||||
let mut current_index = start_index;
|
let mut current_index = start_index;
|
||||||
let mut vertices = Vec::new();
|
let mut vertices = Vec::new();
|
||||||
let mut indices = Vec::new();
|
let mut indices = Vec::new();
|
||||||
let highlighted: [f32; 3] = self.highlighted_normal.cast().unwrap().into();
|
|
||||||
|
|
||||||
if self.visible_faces & FACE_LEFT == FACE_LEFT {
|
if self.visible_faces & FACE_LEFT == FACE_LEFT {
|
||||||
let normal = [-1.0, 0.0, 0.0];
|
let normal = Vector3::new(-1, 0, 0);
|
||||||
let highlighted = (normal == highlighted) as i32;
|
let highlighted = (self.highlighted_normal == normal) as i32;
|
||||||
|
let normal = normal.cast().unwrap().into();
|
||||||
vertices.extend(&[
|
vertices.extend(&[
|
||||||
BlockVertex { position: [x, y, z ], texture_coordinates: [dz, 1.0], texture_id: t.0 as i32, normal, highlighted },
|
BlockVertex { position: [x, y, z ], texture_coordinates: [dz, 1.0], texture_id: t.0 as i32, normal, highlighted },
|
||||||
BlockVertex { position: [x, y, z + dz], texture_coordinates: [0.0, 1.0], texture_id: t.0 as i32, normal, highlighted },
|
BlockVertex { position: [x, y, z + dz], texture_coordinates: [0.0, 1.0], texture_id: t.0 as i32, normal, highlighted },
|
||||||
|
@ -88,8 +85,9 @@ impl Quad {
|
||||||
}
|
}
|
||||||
|
|
||||||
if self.visible_faces & FACE_RIGHT == FACE_RIGHT {
|
if self.visible_faces & FACE_RIGHT == FACE_RIGHT {
|
||||||
let normal = [1.0, 0.0, 0.0];
|
let normal = Vector3::new(1, 0, 0);
|
||||||
let highlighted = (normal == highlighted) as i32;
|
let highlighted = (self.highlighted_normal == normal) as i32;
|
||||||
|
let normal = normal.cast().unwrap().into();
|
||||||
vertices.extend(&[
|
vertices.extend(&[
|
||||||
BlockVertex { position: [x + dx, y, z ], texture_coordinates: [0.0, 1.0], texture_id: t.1 as i32, normal, highlighted },
|
BlockVertex { position: [x + dx, y, z ], texture_coordinates: [0.0, 1.0], texture_id: t.1 as i32, normal, highlighted },
|
||||||
BlockVertex { position: [x + dx, y, z + dz], texture_coordinates: [dz, 1.0], texture_id: t.1 as i32, normal, highlighted },
|
BlockVertex { position: [x + dx, y, z + dz], texture_coordinates: [dz, 1.0], texture_id: t.1 as i32, normal, highlighted },
|
||||||
|
@ -104,8 +102,9 @@ impl Quad {
|
||||||
}
|
}
|
||||||
|
|
||||||
if self.visible_faces & FACE_BACK == FACE_BACK {
|
if self.visible_faces & FACE_BACK == FACE_BACK {
|
||||||
let normal = [0.0, 0.0, -1.0];
|
let normal = Vector3::new(0, 0, -1);
|
||||||
let highlighted = (normal == highlighted) as i32;
|
let highlighted = (self.highlighted_normal == normal) as i32;
|
||||||
|
let normal = normal.cast().unwrap().into();
|
||||||
vertices.extend(&[
|
vertices.extend(&[
|
||||||
BlockVertex { position: [x, y, z], texture_coordinates: [dx, 1.0], texture_id: t.2 as i32, normal, highlighted },
|
BlockVertex { position: [x, y, z], texture_coordinates: [dx, 1.0], texture_id: t.2 as i32, normal, highlighted },
|
||||||
BlockVertex { position: [x, y + dy, z], texture_coordinates: [dx, 0.0], texture_id: t.2 as i32, normal, highlighted },
|
BlockVertex { position: [x, y + dy, z], texture_coordinates: [dx, 0.0], texture_id: t.2 as i32, normal, highlighted },
|
||||||
|
@ -120,8 +119,9 @@ impl Quad {
|
||||||
}
|
}
|
||||||
|
|
||||||
if self.visible_faces & FACE_FRONT == FACE_FRONT {
|
if self.visible_faces & FACE_FRONT == FACE_FRONT {
|
||||||
let normal = [0.0, 0.0, 1.0];
|
let normal = Vector3::new(0, 0, 1);
|
||||||
let highlighted = (normal == highlighted) as i32;
|
let highlighted = (self.highlighted_normal == normal) as i32;
|
||||||
|
let normal = normal.cast().unwrap().into();
|
||||||
vertices.extend(&[
|
vertices.extend(&[
|
||||||
BlockVertex { position: [x, y, z + dz], texture_coordinates: [0.0, 1.0], texture_id: t.3 as i32, normal, highlighted },
|
BlockVertex { position: [x, y, z + dz], texture_coordinates: [0.0, 1.0], texture_id: t.3 as i32, normal, highlighted },
|
||||||
BlockVertex { position: [x, y + dy, z + dz], texture_coordinates: [0.0, 0.0], texture_id: t.3 as i32, normal, highlighted },
|
BlockVertex { position: [x, y + dy, z + dz], texture_coordinates: [0.0, 0.0], texture_id: t.3 as i32, normal, highlighted },
|
||||||
|
@ -136,8 +136,9 @@ impl Quad {
|
||||||
}
|
}
|
||||||
|
|
||||||
if self.visible_faces & FACE_BOTTOM == FACE_BOTTOM {
|
if self.visible_faces & FACE_BOTTOM == FACE_BOTTOM {
|
||||||
let normal = [0.0, -1.0, 0.0];
|
let normal = Vector3::new(0, -1, 0);
|
||||||
let highlighted = (normal == highlighted) as i32;
|
let highlighted = (self.highlighted_normal == normal) as i32;
|
||||||
|
let normal = normal.cast().unwrap().into();
|
||||||
vertices.extend(&[
|
vertices.extend(&[
|
||||||
BlockVertex { position: [x, y, z ], texture_coordinates: [dx, 0.0], texture_id: t.4 as i32, normal, highlighted },
|
BlockVertex { position: [x, y, z ], texture_coordinates: [dx, 0.0], texture_id: t.4 as i32, normal, highlighted },
|
||||||
BlockVertex { position: [x, y, z + dz], texture_coordinates: [dx, dz ], texture_id: t.4 as i32, normal, highlighted },
|
BlockVertex { position: [x, y, z + dz], texture_coordinates: [dx, dz ], texture_id: t.4 as i32, normal, highlighted },
|
||||||
|
@ -152,8 +153,9 @@ impl Quad {
|
||||||
}
|
}
|
||||||
|
|
||||||
if self.visible_faces & FACE_TOP == FACE_TOP {
|
if self.visible_faces & FACE_TOP == FACE_TOP {
|
||||||
let normal = [0.0, 1.0, 0.0];
|
let normal = Vector3::new(0, 1, 0);
|
||||||
let highlighted = (normal == highlighted) as i32;
|
let highlighted = (self.highlighted_normal == normal) as i32;
|
||||||
|
let normal = normal.cast().unwrap().into();
|
||||||
vertices.extend(&[
|
vertices.extend(&[
|
||||||
BlockVertex { position: [x, y + dy, z ], texture_coordinates: [0.0, 0.0], texture_id: t.5 as i32, normal, highlighted },
|
BlockVertex { position: [x, y + dy, z ], texture_coordinates: [0.0, 0.0], texture_id: t.5 as i32, normal, highlighted },
|
||||||
BlockVertex { position: [x, y + dy, z + dz], texture_coordinates: [0.0, dz ], texture_id: t.5 as i32, normal, highlighted },
|
BlockVertex { position: [x, y + dy, z + dz], texture_coordinates: [0.0, dz ], texture_id: t.5 as i32, normal, highlighted },
|
Loading…
Reference in a new issue