diff --git a/drape_frontend/backend_renderer.cpp b/drape_frontend/backend_renderer.cpp index 12bb2f977f..cfe6319585 100644 --- a/drape_frontend/backend_renderer.cpp +++ b/drape_frontend/backend_renderer.cpp @@ -56,21 +56,26 @@ void BackendRenderer::AcceptMessage(RefPointer message) { case Message::UpdateReadManager: { - UpdateReadManagerMessage * msg = static_cast(message.GetRaw()); + UpdateReadManagerMessage * msg = df::CastMessage(message); ScreenBase const & screen = msg->GetScreen(); set const & tiles = msg->GetTiles(); m_readManager->UpdateCoverage(screen, tiles); } + case Message::InvalidateReadManagerRect: + { + InvalidateReadManagerRectMessage * msg = df::CastMessage(message); + m_readManager->Invalidate(msg->GetTilesForInvalidate()); + } break; case Message::TileReadStarted: - m_batchersPool->ReserveBatcher(static_cast(message.GetRaw())->GetKey()); + m_batchersPool->ReserveBatcher(df::CastMessage(message)->GetKey()); break; case Message::TileReadEnded: - m_batchersPool->ReleaseBatcher(static_cast(message.GetRaw())->GetKey()); + m_batchersPool->ReleaseBatcher(df::CastMessage(message)->GetKey()); break; case Message::MapShapeReaded: { - MapShapeReadedMessage * msg = static_cast(message.GetRaw()); + MapShapeReadedMessage * msg = df::CastMessage(message); RefPointer batcher = m_batchersPool->GetTileBatcher(msg->GetKey()); MasterPointer shape(msg->GetShape()); shape->Draw(batcher, m_textures); diff --git a/drape_frontend/frontend_renderer.cpp b/drape_frontend/frontend_renderer.cpp index f67746d413..b198ceb6b4 100644 --- a/drape_frontend/frontend_renderer.cpp +++ b/drape_frontend/frontend_renderer.cpp @@ -99,7 +99,7 @@ void FrontendRenderer::AcceptMessage(RefPointer message) { case Message::FlushTile: { - FlushRenderBucketMessage * msg = static_cast(message.GetRaw()); + FlushRenderBucketMessage * msg = df::CastMessage(message); const GLState & state = msg->GetState(); const TileKey & key = msg->GetKey(); MasterPointer bucket(msg->AcceptBuffer()); @@ -114,7 +114,7 @@ void FrontendRenderer::AcceptMessage(RefPointer message) case Message::Resize: { - ResizeMessage * rszMsg = static_cast(message.GetRaw()); + ResizeMessage * rszMsg = df::CastMessage(message); m_viewport = rszMsg->GetViewport(); m_view.OnSize(0, 0, m_viewport.GetWidth(), m_viewport.GetHeight()); RefreshProjection(); @@ -128,7 +128,7 @@ void FrontendRenderer::AcceptMessage(RefPointer message) case Message::UpdateModelView: { - UpdateModelViewMessage * coverMessage = static_cast(message.GetRaw()); + UpdateModelViewMessage * coverMessage = df::CastMessage(message); m_view = coverMessage->GetScreen(); RefreshModelView(); ResolveTileKeys(); @@ -138,6 +138,18 @@ void FrontendRenderer::AcceptMessage(RefPointer message) break; } + case Message::InvalidateRect: + { + InvalidateRectMessage * m = df::CastMessage(message); + + set * keyStorage = new set(); + ResolveTileKeys(*keyStorage, m->GetRect()); + InvalidateRenderGroups(*keyStorage); + + Message * msgToBackend = new InvalidateReadManagerRectMessage(MovePointer(keyStorage)); + m_commutator->PostMessage(ThreadsCommutator::ResourceUploadThread, MovePointer(msgToBackend)); + } + default: ASSERT(false, ()); } @@ -224,10 +236,16 @@ void FrontendRenderer::RefreshModelView() void FrontendRenderer::ResolveTileKeys() { - set & tiles = GetTileKeyStorage(); - tiles.clear(); + ResolveTileKeys(GetTileKeyStorage(), df::GetTileScaleBase(m_view)); +} - int const tileScale = df::GetTileScaleBase(m_view); +void FrontendRenderer::ResolveTileKeys(set & keyStorage, m2::RectD const & rect) +{ + ResolveTileKeys(keyStorage, df::GetTileScaleBase(rect)); +} + +void FrontendRenderer::ResolveTileKeys(set & keyStorage, int tileScale) +{ // equal for x and y double const range = MercatorBounds::maxX - MercatorBounds::minX; double const rectSize = range / (1 << tileScale); @@ -239,10 +257,21 @@ void FrontendRenderer::ResolveTileKeys() int const minTileY = static_cast(floor(clipRect.minY() / rectSize)); int const maxTileY = static_cast(ceil(clipRect.maxY() / rectSize)); + keyStorage.clear(); for (int tileY = minTileY; tileY < maxTileY; ++tileY) { for (int tileX = minTileX; tileX < maxTileX; ++tileX) - tiles.insert(TileKey(tileX, tileY, tileScale)); + keyStorage.insert(TileKey(tileX, tileY, tileScale)); + } +} + +void FrontendRenderer::InvalidateRenderGroups(set & keyStorage) +{ + for (size_t i = 0; i < m_renderGroups.size(); ++i) + { + RenderGroup * group = m_renderGroups[i]; + if (keyStorage.find(group->GetTileKey()) != keyStorage.end()) + group->DeleteLater(); } } diff --git a/drape_frontend/frontend_renderer.hpp b/drape_frontend/frontend_renderer.hpp index 49b08cb54c..d122687939 100644 --- a/drape_frontend/frontend_renderer.hpp +++ b/drape_frontend/frontend_renderer.hpp @@ -66,8 +66,12 @@ private: void RefreshModelView(); void ResolveTileKeys(); + void ResolveTileKeys(set & keyStorage, m2::RectD const & rect); + void ResolveTileKeys(set & keyStorage, int tileScale); set & GetTileKeyStorage(); + void InvalidateRenderGroups(set & keyStorage); + private: void StartThread(); void StopThread(); diff --git a/drape_frontend/read_manager.cpp b/drape_frontend/read_manager.cpp index 669ac839d6..0215b7ccae 100644 --- a/drape_frontend/read_manager.cpp +++ b/drape_frontend/read_manager.cpp @@ -29,11 +29,6 @@ struct LessCoverageCell } }; -TileKey TileInfoPtrToTileKey(shared_ptr const & p) -{ - return p->GetTileKey(); -} - } // namespace ReadManager::ReadManager(EngineContext & context, model::FeaturesFetcher & model) @@ -75,17 +70,25 @@ void ReadManager::UpdateCoverage(ScreenBase const & screen, set const & back_inserter(inputRects), LessCoverageCell()); for_each(outdatedTiles.begin(), outdatedTiles.end(), bind(&ReadManager::ClearTileInfo, this, _1)); - - buffer_vector outdatedTileKeys; - transform(outdatedTiles.begin(), outdatedTiles.end(), - back_inserter(outdatedTileKeys), &TileInfoPtrToTileKey); - for_each(m_tileInfos.begin(), m_tileInfos.end(), bind(&ReadManager::PushTaskFront, this, _1)); for_each(inputRects.begin(), inputRects.end(), bind(&ReadManager::PushTaskBackForTileKey, this, _1)); } m_currentViewport = screen; } +void ReadManager::Invalidate(set const & keyStorage) +{ + tile_set_t::iterator it = m_tileInfos.begin(); + for (; it != m_tileInfos.end(); ++it) + { + if (keyStorage.find((*it)->GetTileKey()) != keyStorage.end()) + { + CancelTileInfo(*it); + PushTaskFront(*it); + } + } +} + void ReadManager::Stop() { for_each(m_tileInfos.begin(), m_tileInfos.end(), bind(&ReadManager::CancelTileInfo, this, _1)); @@ -119,12 +122,12 @@ void ReadManager::PushTaskFront(tileinfo_ptr const & tileToReread) m_pool->PushFront(new ReadMWMTask(tileToReread, m_memIndex, m_model, m_context)); } -void ReadManager::CancelTileInfo(tileinfo_ptr tileToCancel) +void ReadManager::CancelTileInfo(tileinfo_ptr const & tileToCancel) { tileToCancel->Cancel(m_memIndex); } -void ReadManager::ClearTileInfo(tileinfo_ptr & tileToClear) +void ReadManager::ClearTileInfo(tileinfo_ptr const & tileToClear) { CancelTileInfo(tileToClear); m_tileInfos.erase(tileToClear); diff --git a/drape_frontend/read_manager.hpp b/drape_frontend/read_manager.hpp index ec3ad60416..5b169e9b56 100644 --- a/drape_frontend/read_manager.hpp +++ b/drape_frontend/read_manager.hpp @@ -28,6 +28,7 @@ public: ReadManager(EngineContext & context, model::FeaturesFetcher & model); void UpdateCoverage(ScreenBase const & screen, set const & tiles); + void Invalidate(set const & keyStorage); void Stop(); static size_t ReadCount(); @@ -57,10 +58,11 @@ private: } }; - set m_tileInfos; + typedef set tile_set_t; + tile_set_t m_tileInfos; - void CancelTileInfo(tileinfo_ptr tileToCancel); - void ClearTileInfo(tileinfo_ptr & tileToClear); + void CancelTileInfo(tileinfo_ptr const & tileToCancel); + void ClearTileInfo(tileinfo_ptr const & tileToClear); }; } // namespace df