/// <summary> /// Initializes the VBO but does not modify graphics state /// </summary> public void Prerender(Structure structure, BlockAtlas blockAtlas) { _vbi.Reset(); for (var pass = 0; pass <= 1; pass++) { for (var x = X * 16; x < X * 16 + 16; x++) { for (var y = 0; y < 256; y++) { for (var z = Z * 16; z < Z * 16 + 16; z++) { if (!structure.Contains(x, y, z)) { continue; } var block = structure[x, y, z]; if (block == null) { continue; } var blockData = blockAtlas[block.Id]; if (blockData == null || blockData.Properties.Render == "none" || blockData.Textures.Count == 0) { continue; } ChunkRenderer.Render(structure, x, y, z, blockAtlas, _vbi, pass); } } } } }
public RenderEngine(GameWindow window, MappingEngine mappingEngine) { _window = window; _mappingEngine = mappingEngine; _fgJobs = new ConcurrentQueue <IJob>(); _bgJobs = new ConcurrentQueue <IJob>(); _framebuffer = new Framebuffer(8); _framebuffer.Init(window.Width, window.Height); _framebufferUi = new Framebuffer(1); _framebufferUi.Init(window.Width, window.Height); _texRandom = LoadGlTexture(EmbeddedFiles.random); _shaderModel = new ShaderProgram(EmbeddedFiles.fs_terrain, EmbeddedFiles.vs_terrain); _shaderModel.Init(); _shaderScreen = new ShaderProgram(EmbeddedFiles.fs_screen, EmbeddedFiles.vs_screen); _shaderScreen.Init(); _workerHandle = new EventWaitHandle(false, EventResetMode.ManualReset); LightPosition = new Vector3(0.25f, 1, 0.25f); Chunks = new Chunk[0]; CreateScreenVao(); _texAtlas = new BlockAtlas(mappingEngine, 32); }
public void Render(Structure structure, int x, int y, int z, BlockAtlas blockAtlas, ChunkBuffer vbi) { var block = structure[x, y, z]; var blockData = blockAtlas[block.Id]; var tex = blockData.Textures[0]; var tc00 = new Uv(0, 0); var tc10 = new Uv(1, 0); var tc01 = new Uv(0, 1); var tc11 = new Uv(1, 1); if (tex != null) { var d = 0.0002f; // bleed compensation tc00 = new Uv(tex.MinU + d, tex.MinV + d); tc10 = new Uv(tex.MaxU - d, tex.MinV + d); tc01 = new Uv(tex.MinU + d, tex.MaxV - d); tc11 = new Uv(tex.MaxU - d, tex.MaxV - d); } var norm = (Vector3.UnitX + Vector3.UnitZ).Normalized(); vbi.Append(new Vertex(x, y, z + 1), new Vertex(norm.X, norm.Y, norm.Z), tc01); vbi.Append(new Vertex(x + 1, y, z), new Vertex(norm.X, norm.Y, norm.Z), tc11); vbi.Append(new Vertex(x + 1, y + 1, z), new Vertex(norm.X, norm.Y, norm.Z), tc10); vbi.Append(new Vertex(x, y + 1, z + 1), new Vertex(norm.X, norm.Y, norm.Z), tc00); norm = (Vector3.UnitX - Vector3.UnitZ).Normalized(); vbi.Append(new Vertex(x, y, z), new Vertex(norm.X, norm.Y, norm.Z), tc01); vbi.Append(new Vertex(x + 1, y, z + 1), new Vertex(norm.X, norm.Y, norm.Z), tc11); vbi.Append(new Vertex(x + 1, y + 1, z + 1), new Vertex(norm.X, norm.Y, norm.Z), tc10); vbi.Append(new Vertex(x, y + 1, z), new Vertex(norm.X, norm.Y, norm.Z), tc00); }
public static void Render(Structure structure, int x, int y, int z, BlockAtlas blockAtlas, ChunkBuffer vbi, int pass) { var block = structure[x, y, z]; var renderType = blockAtlas[block.Id].Properties.Render; if (!VertexProducers.TryGetValue(renderType, out var producer)) { return; } if (producer.ShouldRenderInPass(pass)) { producer.Render(structure, x, y, z, blockAtlas, vbi); } }
public JobPregenerateChunks(Structure structure, BlockAtlas texAtlas) { _structure = structure; _texAtlas = texAtlas; }
public void Render(Structure structure, int x, int y, int z, BlockAtlas blockAtlas, ChunkBuffer vbi) { var block = structure[x, y, z]; var blockData = blockAtlas[block.Id]; var tex = blockData.Textures[0]; Uv tc00, tc10, tc01, tc11; TexCoord front, back, left, right; front = back = left = right = blockData.Textures[1]; var top = blockData.Textures[0]; var bottom = blockData.Textures[2]; const float d = 0.0002f; // bleed compensation if (structure.IsBorderingTransparent(x, y, z, FaceDir.PosX, blockAtlas)) { CreateUv(right, d, out tc00, out tc10, out tc01, out tc11); vbi.Append(new Vertex(x + 1, y + 1, z), new Vertex(FaceDir.PosX), tc00); vbi.Append(new Vertex(x + 1, y + 1, z + 1), new Vertex(FaceDir.PosX), tc10); vbi.Append(new Vertex(x + 1, y, z + 1), new Vertex(FaceDir.PosX), tc11); vbi.Append(new Vertex(x + 1, y, z), new Vertex(FaceDir.PosX), tc01); } if (structure.IsBorderingTransparent(x, y, z, FaceDir.NegX, blockAtlas)) { CreateUv(left, d, out tc00, out tc10, out tc01, out tc11); vbi.Append(new Vertex(x, y, z), new Vertex(FaceDir.NegX), tc01); vbi.Append(new Vertex(x, y, z + 1), new Vertex(FaceDir.NegX), tc11); vbi.Append(new Vertex(x, y + 1, z + 1), new Vertex(FaceDir.NegX), tc10); vbi.Append(new Vertex(x, y + 1, z), new Vertex(FaceDir.NegX), tc00); } if (structure.IsBorderingTransparent(x, y, z, FaceDir.PosY, blockAtlas)) { CreateUv(top, d, out tc00, out tc10, out tc01, out tc11); vbi.Append(new Vertex(x, y + 1, z + 1), new Vertex(FaceDir.PosY), tc00); vbi.Append(new Vertex(x + 1, y + 1, z + 1), new Vertex(FaceDir.PosY), tc10); vbi.Append(new Vertex(x + 1, y + 1, z), new Vertex(FaceDir.PosY), tc11); vbi.Append(new Vertex(x, y + 1, z), new Vertex(FaceDir.PosY), tc01); } if (structure.IsBorderingTransparent(x, y, z, FaceDir.NegY, blockAtlas)) { CreateUv(bottom, d, out tc00, out tc10, out tc01, out tc11); vbi.Append(new Vertex(x, y, z), new Vertex(FaceDir.NegY), tc01); vbi.Append(new Vertex(x + 1, y, z), new Vertex(FaceDir.NegY), tc11); vbi.Append(new Vertex(x + 1, y, z + 1), new Vertex(FaceDir.NegY), tc10); vbi.Append(new Vertex(x, y, z + 1), new Vertex(FaceDir.NegY), tc00); } if (structure.IsBorderingTransparent(x, y, z, FaceDir.PosZ, blockAtlas)) { CreateUv(back, d, out tc00, out tc10, out tc01, out tc11); vbi.Append(new Vertex(x, y, z + 1), new Vertex(FaceDir.PosZ), tc01); vbi.Append(new Vertex(x + 1, y, z + 1), new Vertex(FaceDir.PosZ), tc11); vbi.Append(new Vertex(x + 1, y + 1, z + 1), new Vertex(FaceDir.PosZ), tc10); vbi.Append(new Vertex(x, y + 1, z + 1), new Vertex(FaceDir.PosZ), tc00); } if (structure.IsBorderingTransparent(x, y, z, FaceDir.NegZ, blockAtlas)) { CreateUv(front, d, out tc00, out tc10, out tc01, out tc11); vbi.Append(new Vertex(x, y + 1, z), new Vertex(FaceDir.NegZ), tc00); vbi.Append(new Vertex(x + 1, y + 1, z), new Vertex(FaceDir.NegZ), tc10); vbi.Append(new Vertex(x + 1, y, z), new Vertex(FaceDir.NegZ), tc11); vbi.Append(new Vertex(x, y, z), new Vertex(FaceDir.NegZ), tc01); } }
public void Render(Structure structure, int x, int y, int z, BlockAtlas blockAtlas, ChunkBuffer vbi) { var block = structure[x, y, z]; var blockData = blockAtlas[block.Id]; var tex = blockData.Textures[0]; var tc00 = new Uv(0, 0); var tc10 = new Uv(1, 0); var tc01 = new Uv(0, 1); var tc11 = new Uv(1, 1); if (tex != null) { var d = 0.0002f; // bleed compensation tc00 = new Uv(tex.MinU + d, tex.MinV + d); tc10 = new Uv(tex.MaxU - d, tex.MinV + d); tc01 = new Uv(tex.MinU + d, tex.MaxV - d); tc11 = new Uv(tex.MaxU - d, tex.MaxV - d); } if (structure.IsBorderingTransparent(x, y, z, FaceDir.PosX, blockAtlas)) { vbi.Append(new Vertex(x + 1, y + 1, z), new Vertex(FaceDir.PosX), tc00); vbi.Append(new Vertex(x + 1, y + 1, z + 1), new Vertex(FaceDir.PosX), tc10); vbi.Append(new Vertex(x + 1, y, z + 1), new Vertex(FaceDir.PosX), tc11); vbi.Append(new Vertex(x + 1, y, z), new Vertex(FaceDir.PosX), tc01); } if (structure.IsBorderingTransparent(x, y, z, FaceDir.NegX, blockAtlas)) { vbi.Append(new Vertex(x, y, z), new Vertex(FaceDir.NegX), tc01); vbi.Append(new Vertex(x, y, z + 1), new Vertex(FaceDir.NegX), tc11); vbi.Append(new Vertex(x, y + 1, z + 1), new Vertex(FaceDir.NegX), tc10); vbi.Append(new Vertex(x, y + 1, z), new Vertex(FaceDir.NegX), tc00); } if (structure.IsBorderingTransparent(x, y, z, FaceDir.PosY, blockAtlas)) { vbi.Append(new Vertex(x, y + 1, z + 1), new Vertex(FaceDir.PosY), tc00); vbi.Append(new Vertex(x + 1, y + 1, z + 1), new Vertex(FaceDir.PosY), tc10); vbi.Append(new Vertex(x + 1, y + 1, z), new Vertex(FaceDir.PosY), tc11); vbi.Append(new Vertex(x, y + 1, z), new Vertex(FaceDir.PosY), tc01); } if (structure.IsBorderingTransparent(x, y, z, FaceDir.NegY, blockAtlas)) { vbi.Append(new Vertex(x, y, z), new Vertex(FaceDir.NegY), tc01); vbi.Append(new Vertex(x + 1, y, z), new Vertex(FaceDir.NegY), tc11); vbi.Append(new Vertex(x + 1, y, z + 1), new Vertex(FaceDir.NegY), tc10); vbi.Append(new Vertex(x, y, z + 1), new Vertex(FaceDir.NegY), tc00); } if (structure.IsBorderingTransparent(x, y, z, FaceDir.PosZ, blockAtlas)) { vbi.Append(new Vertex(x, y, z + 1), new Vertex(FaceDir.PosZ), tc01); vbi.Append(new Vertex(x + 1, y, z + 1), new Vertex(FaceDir.PosZ), tc11); vbi.Append(new Vertex(x + 1, y + 1, z + 1), new Vertex(FaceDir.PosZ), tc10); vbi.Append(new Vertex(x, y + 1, z + 1), new Vertex(FaceDir.PosZ), tc00); } if (structure.IsBorderingTransparent(x, y, z, FaceDir.NegZ, blockAtlas)) { vbi.Append(new Vertex(x, y + 1, z), new Vertex(FaceDir.NegZ), tc00); vbi.Append(new Vertex(x + 1, y + 1, z), new Vertex(FaceDir.NegZ), tc10); vbi.Append(new Vertex(x + 1, y, z), new Vertex(FaceDir.NegZ), tc11); vbi.Append(new Vertex(x, y, z), new Vertex(FaceDir.NegZ), tc01); } }
public static bool IsTransparent(this Structure structure, int x, int y, int z, BlockAtlas blockAtlas) { var block = structure[x, y, z]; if (block == null || block.Id == "minecraft:air") { return(true); } var data = blockAtlas[block.Id]; if (data == null) { return(true); } switch (data.Properties.Render) { case "none": case "transparent": case "liquid": case "cross": case "fence": case "skinny": case "cactus": case "layer": case "button": case "torch": case "pressureplate": case "door": case "wallsign": case "sign": case "stairs": case "slab": case "rail": case "ladder": case "wheat": return(true); } return(false); }
public static bool IsBorderingTransparent(this Structure structure, int x, int y, int z, FaceDir face, BlockAtlas blockAtlas) { switch (face.Facing) { case FaceDir.Dir.PosX: if (x == structure.Width - 1) { return(true); } break; case FaceDir.Dir.NegX: if (x == 0) { return(true); } break; case FaceDir.Dir.PosY: if (y == structure.Height - 1) { return(true); } break; case FaceDir.Dir.NegY: if (y == 0) { return(true); } break; case FaceDir.Dir.PosZ: if (z == structure.Length - 1) { return(true); } break; case FaceDir.Dir.NegZ: if (z == 0) { return(true); } break; default: throw new ArgumentOutOfRangeException(); } return(structure.IsTransparent(x + face.X, y + face.Y, z + face.Z, blockAtlas)); }
public static bool IsBorderingTransparent(this Structure structure, int x, int y, int z, BlockAtlas blockAtlas) { return(structure.IsBorderingTransparent(x, y, z, FaceDir.PosX, blockAtlas) || structure.IsBorderingTransparent(x, y, z, FaceDir.NegX, blockAtlas) || structure.IsBorderingTransparent(x, y, z, FaceDir.PosY, blockAtlas) || structure.IsBorderingTransparent(x, y, z, FaceDir.NegY, blockAtlas) || structure.IsBorderingTransparent(x, y, z, FaceDir.PosZ, blockAtlas) || structure.IsBorderingTransparent(x, y, z, FaceDir.NegZ, blockAtlas)); }