From: Tim Moore Date: Sat, 2 Oct 2010 21:00:59 +0000 (+0200) Subject: Thorsten Renk's fix for tile manager problems X-Git-Url: https://git.mxchange.org/?a=commitdiff_plain;h=b5f3978b8aa7c2b016f9ebbc4bcfe8df6e249ac7;p=simgear.git Thorsten Renk's fix for tile manager problems Locking tiles in cache keeps tiles from mysteriously disappearing. --- diff --git a/simgear/scene/tgdb/TileCache.cxx b/simgear/scene/tgdb/TileCache.cxx index 1d34fd8d..390e52d5 100644 --- a/simgear/scene/tgdb/TileCache.cxx +++ b/simgear/scene/tgdb/TileCache.cxx @@ -98,6 +98,11 @@ long TileCache::get_oldest_tile() { for ( ; current != end; ++current ) { long index = current->first; TileEntry *e = current->second; + if (e->get_cache_lock()) + { + // tile locked to cache => must not be dropped + } + else if ( e->is_loaded() ) { timestamp = e->get_timestamp(); if ( timestamp < min_time ) { @@ -125,8 +130,27 @@ void TileCache::clear_inner_ring_flags() { for ( ; current != end; ++current ) { TileEntry *e = current->second; - if ( e->is_loaded() ) { + //if ( e->is_loaded() ) { e->set_inner_ring( false ); + //} + } +} + +// Clear all locked flags for all tiles in the cache. +// (Tiles belonging to the current position are locked to +// the cache to prevent them from being dropped). +void TileCache::clear_cache_lock_flags() +{ + tile_map_iterator current = tile_cache.begin(); + tile_map_iterator end = tile_cache.end(); + + for ( ; current != end; ++current ) { + TileEntry *e = current->second; + if (e->get_cache_lock()) + { + // update timestamps for tiles belonging to most recent position + e->set_timestamp( current_time ); + e->set_cache_lock( false ); } } } diff --git a/simgear/scene/tgdb/TileCache.hxx b/simgear/scene/tgdb/TileCache.hxx index adcaacf7..f427c2bf 100644 --- a/simgear/scene/tgdb/TileCache.hxx +++ b/simgear/scene/tgdb/TileCache.hxx @@ -80,6 +80,11 @@ public: // the external tile scheduler can flag the inner ring correctly. void clear_inner_ring_flags(); + // Clear all locked flags for all tiles in the cache. + // (Tiles belonging to the current position are locked to + // the cache to prevent them from being dropped). + void clear_cache_lock_flags(); + // Clear a cache entry, note that the cache only holds pointers // and this does not free the object which is pointed to. void clear_entry( long cache_entry ); diff --git a/simgear/scene/tgdb/TileEntry.cxx b/simgear/scene/tgdb/TileEntry.cxx index dae9ed26..ffe59352 100644 --- a/simgear/scene/tgdb/TileEntry.cxx +++ b/simgear/scene/tgdb/TileEntry.cxx @@ -64,6 +64,7 @@ osgDB::RegisterReaderWriterProxy g_readerWriterSTGProxy; ModelRegistryCallbackProxy g_stgCallbackProxy("stg"); } +#ifdef USE_CULLCALLBACK_TS namespace { // Update the timestamp on a tile whenever it is in view. @@ -91,24 +92,33 @@ void TileCullCallback::operator()(osg::Node* node, osg::NodeVisitor* nv) _timeStamp = nv->getFrameStamp()->getReferenceTime(); traverse(node, nv); } +#endif double TileEntry::get_timestamp() const { +#ifdef USE_CULLCALLBACK_TS if (_node.valid()) { return (dynamic_cast(_node->getCullCallback())) ->getTimeStamp(); } else return DBL_MAX; +#else + return timestamp; +#endif } void TileEntry::set_timestamp(double time_ms) { +#ifdef USE_CULLCALLBACK_TS if (_node.valid()) { TileCullCallback* cb = dynamic_cast(_node->getCullCallback()); if (cb) cb->setTimeStamp(time_ms); } +#else + timestamp = time_ms; +#endif } // Constructor @@ -117,8 +127,14 @@ TileEntry::TileEntry ( const SGBucket& b ) tileFileName(b.gen_index_str()), _node( new osg::LOD ), is_inner_ring(false) + ,is_cache_locked(false) +#ifndef USE_CULLCALLBACK_TS + ,timestamp(0.0) +#endif { +#ifdef USE_CULLCALLBACK_TS _node->setCullCallback(new TileCullCallback); +#endif tileFileName += ".stg"; _node->setName(tileFileName); // Give a default LOD range so that traversals that traverse diff --git a/simgear/scene/tgdb/TileEntry.hxx b/simgear/scene/tgdb/TileEntry.hxx index e22ae643..924b5666 100644 --- a/simgear/scene/tgdb/TileEntry.hxx +++ b/simgear/scene/tgdb/TileEntry.hxx @@ -81,6 +81,8 @@ private: * inner ring. (For instance vasi color updating) */ bool is_inner_ring; + bool is_cache_locked; + double timestamp; static ModelLoadHelper *_modelLoader; @@ -139,6 +141,8 @@ public: inline bool get_inner_ring() const { return is_inner_ring; } inline void set_inner_ring( bool val ) { is_inner_ring = val; } + inline void set_cache_lock( bool val ) { is_cache_locked = val; } + inline bool get_cache_lock() const { return is_cache_locked; } // Get the ref_ptr to the DatabaseRequest object, in order to pass // this to the pager.