From e95b3cb3e1a054a9d6bd766d4904e569ac2b2a68 Mon Sep 17 00:00:00 2001 From: Jon Bergli Heier Date: Sun, 3 Jul 2011 15:26:40 +0200 Subject: Added terrain objects. --- terrain_cache.cpp | 10 +++++++++- terrain_cache.h | 6 +++++- terrain_loader.cpp | 56 +++++++++++++++++++++++++++++++++++++++++++++++++++++- terrain_loader.h | 10 +++++++++- 4 files changed, 78 insertions(+), 4 deletions(-) diff --git a/terrain_cache.cpp b/terrain_cache.cpp index 01cc161..f0f757b 100644 --- a/terrain_cache.cpp +++ b/terrain_cache.cpp @@ -2,20 +2,28 @@ /* TerrainCacheObject */ -TerrainCacheObject::TerrainCacheObject(TerrainCache *cache, int64_t x, int64_t y, unsigned int width, unsigned int height, float *heights) { +TerrainCacheObject::TerrainCacheObject(TerrainCache *cache, int64_t x, int64_t y, unsigned int width, unsigned int height, + float *heights, std::list *objects) { this->cache = cache; this->x = x; this->y = y; this->width = width; this->height = height; + if(heights) this->heights = heights; else this->heights = cache->tl->get_chunk(x, y, width, height); + + if(objects) + this->objects.insert(this->objects.end(), objects->begin(), objects->end()); + else + this->objects = cache->tl->get_objects(x, y); } TerrainCacheObject::~TerrainCacheObject() { cache->tl->save_chunk(heights, x, y, width, height); + cache->tl->save_objects(objects, x, y); delete[] heights; } diff --git a/terrain_cache.h b/terrain_cache.h index dcc4f34..e8101fa 100644 --- a/terrain_cache.h +++ b/terrain_cache.h @@ -2,6 +2,7 @@ #define TERRAIN_CACHE_H #include "terrain_loader.h" +#include "vector.h" #include @@ -15,10 +16,13 @@ struct TerrainCacheObject { TerrainCache *cache; float *heights; + // FIXME: Support other object types. + std::list objects; int64_t x, y; unsigned int width, height; - TerrainCacheObject(TerrainCache *cache, int64_t x, int64_t y, unsigned int width, unsigned int height, float *heights = NULL); + TerrainCacheObject(TerrainCache *cache, int64_t x, int64_t y, unsigned int width, unsigned int height, + float *heights = NULL, std::list *objects = NULL); virtual ~TerrainCacheObject(); }; diff --git a/terrain_loader.cpp b/terrain_loader.cpp index ef61e1e..5a4aec7 100644 --- a/terrain_loader.cpp +++ b/terrain_loader.cpp @@ -11,6 +11,7 @@ TerrainLoader::TerrainLoader(fs::path root) { TerrainLoader::~TerrainLoader() { } + float *TerrainLoader::get_chunk(int64_t x, int64_t y, unsigned int width, unsigned int height) { if(has_chunk(x, y)) return load_chunk(x, y, width, height); @@ -47,8 +48,9 @@ float *TerrainLoader::load_chunk(int64_t x, int64_t y, unsigned int width, unsig is.read((char*)&h, sizeof(h)); // TODO: should return w and h, fix calling code - if(w != width || h != height) + if(w != width || h != height) { throw std::runtime_error("width or height doesn't match"); + } float *chunk = new float[width*height]; is.read((char*)chunk, width*height*sizeof(float)); @@ -56,3 +58,55 @@ float *TerrainLoader::load_chunk(int64_t x, int64_t y, unsigned int width, unsig return chunk; } + +std::list TerrainLoader::get_objects(int64_t x, int64_t y) { + std::list objects; + + if(has_objects(x, y)) + objects = load_objects(x, y); + + return objects; +} + +bool TerrainLoader::has_objects(int64_t x, int64_t y) { + return fs::exists(root / (boost::format("%d.%d.objs") % x % y).str()); +} + +void TerrainLoader::save_objects(std::list& objects, int64_t x, int64_t y) { + fs::path p = root / (boost::format("%d.%d.objs") % x % y).str(); + fs::ofstream os(p, std::ios::out | std::ios::binary); + + uint32_t count = objects.size(); + os.write((const char*)&count, sizeof(count)); + + for(std::list::iterator it = objects.begin(); it != objects.end(); it++) { + Vector3& obj = *it; + os.write((const char*)&obj.x, sizeof(obj.x)); + os.write((const char*)&obj.y, sizeof(obj.y)); + os.write((const char*)&obj.z, sizeof(obj.z)); + } + os.close(); +} + +std::list TerrainLoader::load_objects(int64_t x, int64_t y) { + fs::path p = root / (boost::format("%d.%d.objs") % x % y).str(); + fs::ifstream is(p, std::ios::in | std::ios::binary); + + std::list objects; + + uint32_t count; + is.read((char*)&count, sizeof(count)); + + for(uint32_t i = 0; i < count; i++) { + Vector3 obj; + + is.read((char*)&obj.x, sizeof(obj.x)); + is.read((char*)&obj.y, sizeof(obj.y)); + is.read((char*)&obj.z, sizeof(obj.z)); + + objects.push_back(obj); + } + is.close(); + + return objects; +} diff --git a/terrain_loader.h b/terrain_loader.h index f99fb09..a30ddec 100644 --- a/terrain_loader.h +++ b/terrain_loader.h @@ -1,9 +1,13 @@ #ifndef TERRAIN_LOADER_H #define TERRAIN_LOADER_H +#include "vector.h" + #include #include +#include + namespace fs = boost::filesystem; class TerrainLoader { @@ -16,12 +20,16 @@ class TerrainLoader { TerrainLoader(fs::path root); virtual ~TerrainLoader(); - float *generate_heights(int64_t x, int64_t y, unsigned int width, unsigned int height); virtual float *get_chunk(int64_t x, int64_t y, unsigned int width, unsigned int height); bool has_chunk(int64_t x, int64_t y); void save_chunk(float *chunk, int64_t x, int64_t y, unsigned int width, unsigned int height); float *load_chunk(int64_t x, int64_t y, unsigned int width, unsigned int height); + // FIXME: Support other object types. + virtual std::list get_objects(int64_t x, int64_t y); + bool has_objects(int64_t x, int64_t y); + void save_objects(std::list& objects, int64_t x, int64_t y); + std::list load_objects(int64_t x, int64_t y); }; #endif -- cgit v1.2.3