diff --git a/drape_frontend/backend_renderer.cpp b/drape_frontend/backend_renderer.cpp index 31a0860e10..f18a69f51f 100644 --- a/drape_frontend/backend_renderer.cpp +++ b/drape_frontend/backend_renderer.cpp @@ -189,6 +189,8 @@ void BackendRenderer::AcceptMessage(ref_ptr message) auto const & tileKey = msg->GetKey(); if (m_requestedTiles->CheckTileKey(tileKey) && m_readManager->CheckTileKey(tileKey)) { + CleanupOverlays(tileKey); + OverlayBatcher batcher(tileKey); for (drape_ptr const & shape : msg->GetShapes()) batcher.Batch(shape, m_texMng); @@ -345,4 +347,13 @@ void BackendRenderer::FlushGeometry(drape_ptr && message) m_commutator->PostMessage(ThreadsCommutator::RenderThread, move(message), MessagePriority::Normal); } +void BackendRenderer::CleanupOverlays(TileKey const & tileKey) +{ + auto const functor = [&tileKey](OverlayRenderData const & data) + { + return data.m_tileKey == tileKey && data.m_tileKey.m_generation < tileKey.m_generation; + }; + m_overlays.erase(remove_if(m_overlays.begin(), m_overlays.end(), functor), m_overlays.end()); +} + } // namespace df diff --git a/drape_frontend/backend_renderer.hpp b/drape_frontend/backend_renderer.hpp index 116dfd0231..55997a49cb 100644 --- a/drape_frontend/backend_renderer.hpp +++ b/drape_frontend/backend_renderer.hpp @@ -81,6 +81,8 @@ private: void InitGLDependentResource(); void FlushGeometry(drape_ptr && message); + void CleanupOverlays(TileKey const & tileKey); + MapDataProvider m_model; drape_ptr m_batchersPool; drape_ptr m_readManager; diff --git a/drape_frontend/frontend_renderer.cpp b/drape_frontend/frontend_renderer.cpp index 5849018998..f4d8aa1b3e 100755 --- a/drape_frontend/frontend_renderer.cpp +++ b/drape_frontend/frontend_renderer.cpp @@ -205,14 +205,18 @@ void FrontendRenderer::AcceptMessage(ref_ptr message) dp::GLState const & state = msg->GetState(); TileKey const & key = msg->GetKey(); drape_ptr bucket = msg->AcceptBuffer(); - PrepareBucket(state, bucket); if (!IsUserMarkLayer(key)) { if (key.m_zoomLevel == m_currentZoomLevel && CheckTileGenerations(key)) + { + PrepareBucket(state, bucket); AddToRenderGroup(state, move(bucket), key); + } } else { + PrepareBucket(state, bucket); + ref_ptr program = m_gpuProgramManager->GetProgram(state.GetProgramIndex()); ref_ptr program3d = m_gpuProgramManager->GetProgram(state.GetProgram3dIndex()); @@ -777,7 +781,8 @@ bool FrontendRenderer::CheckTileGenerations(TileKey const & tileKey) { return group->GetTileKey() == tileKey && group->GetTileKey().m_generation < tileKey.m_generation; }; - RemoveRenderGroups(removePredicate); + for (RenderLayer & layer : m_layers) + layer.m_isDirty |= RemoveGroups(removePredicate, layer.m_renderGroups, make_ref(m_overlayTree)); return result; } @@ -972,9 +977,7 @@ void FrontendRenderer::RenderScene(ScreenBase const & modelView) MergeBuckets(); - size_t const kMinDeletedPerFrame = 10; - size_t const kAvgDeletionFrameCount = 30; - size_t countToDelete = max(kMinDeletedPerFrame, m_bucketsToDelete.size() / kAvgDeletionFrameCount); + int countToDelete = max(1, static_cast(m_bucketsToDelete.size()) / 2); while (!m_bucketsToDelete.empty() && countToDelete > 0) { m_bucketsToDelete.pop_front(); @@ -1057,13 +1060,17 @@ void FrontendRenderer::MergeBuckets() forMerge[MergedGroupKey(state, group->GetTileKey())].push_back(move(layer.m_renderGroups[i])); } else + { newGroups.push_back(move(layer.m_renderGroups[i])); + } } for (TGroupMap::value_type & node : forMerge) { if (node.second.size() < 2) + { newGroups.emplace_back(move(node.second.front())); + } else { BatchMergeHelper::MergeBatches(node.second, newGroups, isPerspective, true); @@ -1528,7 +1535,10 @@ void FrontendRenderer::UpdateScene(ScreenBase const & modelView) auto removePredicate = [this](drape_ptr const & group) { - return group->IsOverlay() && group->GetTileKey().m_zoomLevel > m_currentZoomLevel; + uint32_t const kMaxGenerationRange = 5; + TileKey const & key = group->GetTileKey(); + return (group->IsOverlay() && key.m_zoomLevel > m_currentZoomLevel) || + (m_maxGeneration - key.m_generation > kMaxGenerationRange); }; for (RenderLayer & layer : m_layers) layer.m_isDirty |= RemoveGroups(removePredicate, layer.m_renderGroups, make_ref(m_overlayTree));