+
+ Ray aim = cam.Aim();
+ Chunk *chunk;
+ int blkid;
+ float dist;
+ glm::vec3 normal;
+ if (world.Intersection(aim, glm::mat4(1.0f), &chunk, &blkid, &dist, &normal)) {
+ glm::vec3 pos = Chunk::ToCoords(blkid);
+ outline_visible = true;
+ outline.Clear();
+ chunk->BlockAt(blkid).type->FillOutlineModel(outline);
+ outline_transform = glm::translate(chunk->Transform(), pos);
+ } else {
+ outline_visible = false;
+ }
+
+ if (pick) {
+ if (chunk) {
+ place_id = chunk->BlockAt(blkid).type->id;
+ hud.Display(*world.BlockTypes()[place_id]);
+ }
+ pick = false;
+ }
+ if (remove) {
+ if (chunk) {
+ chunk->BlockAt(blkid).type = world.BlockTypes()[remove_id];
+ chunk->Invalidate();
+ }
+ remove = false;
+ }
+ if (place) {
+ if (chunk) {
+ Chunk *mod_chunk = chunk;
+ glm::vec3 next_pos = Chunk::ToCoords(blkid) + normal;
+ if (!Chunk::InBounds(next_pos)) {
+ mod_chunk = &world.Next(*chunk, normal);
+ next_pos -= normal * Chunk::Extent();
+ }
+ mod_chunk->BlockAt(next_pos).type = world.BlockTypes()[place_id];
+ mod_chunk->Invalidate();
+ }
+ place = false;
+ }