forked from organicmaps/organicmaps
added CoverageGenerator pausing and Coverage caching command cancellation for smoother GUI performance.
This commit is contained in:
parent
d03e167bc0
commit
89adf0faef
12 changed files with 125 additions and 16 deletions
|
@ -89,12 +89,16 @@ void BasicTilingRenderPolicy::DrawFrame(shared_ptr<PaintEvent> const & e, Screen
|
|||
bool doForceUpdate = DoForceUpdate();
|
||||
bool doIntersectInvalidRect = GetInvalidRect().IsIntersect(s.GlobalRect());
|
||||
|
||||
bool doForceUpdateFromGenerator = m_CoverageGenerator->DoForceUpdate();
|
||||
|
||||
if (doForceUpdate)
|
||||
m_CoverageGenerator->InvalidateTiles(GetInvalidRect(), scales::GetUpperWorldScale() + 1);
|
||||
|
||||
if (!m_IsNavigating && (!IsAnimating()))
|
||||
m_CoverageGenerator->AddCoverScreenTask(s,
|
||||
m_DoRecreateCoverage || (doForceUpdate && doIntersectInvalidRect));
|
||||
doForceUpdateFromGenerator
|
||||
|| m_DoRecreateCoverage
|
||||
|| (doForceUpdate && doIntersectInvalidRect));
|
||||
|
||||
SetForceUpdate(false);
|
||||
m_DoRecreateCoverage = false;
|
||||
|
@ -144,6 +148,8 @@ void BasicTilingRenderPolicy::PauseBackgroundRendering()
|
|||
{
|
||||
m_TileRenderer->SetIsPaused(true);
|
||||
m_TileRenderer->CancelCommands();
|
||||
m_CoverageGenerator->SetIsPaused(true);
|
||||
m_CoverageGenerator->CancelCommands();
|
||||
if (m_QueuedRenderer)
|
||||
m_QueuedRenderer->SetPartialExecution(GetPlatform().CpuCores(), true);
|
||||
}
|
||||
|
@ -151,6 +157,7 @@ void BasicTilingRenderPolicy::PauseBackgroundRendering()
|
|||
void BasicTilingRenderPolicy::ResumeBackgroundRendering()
|
||||
{
|
||||
m_TileRenderer->SetIsPaused(false);
|
||||
m_CoverageGenerator->SetIsPaused(false);
|
||||
m_DoRecreateCoverage = true;
|
||||
if (m_QueuedRenderer)
|
||||
m_QueuedRenderer->SetPartialExecution(GetPlatform().CpuCores(), false);
|
||||
|
|
|
@ -30,7 +30,9 @@ CoverageGenerator::CoverageGenerator(
|
|||
m_glQueue(glQueue),
|
||||
m_skinName(skinName),
|
||||
m_fenceManager(2),
|
||||
m_currentFenceID(-1)
|
||||
m_currentFenceID(-1),
|
||||
m_doForceUpdate(false),
|
||||
m_isPaused(false)
|
||||
{
|
||||
g_coverageGeneratorDestroyed = false;
|
||||
|
||||
|
@ -151,7 +153,7 @@ void CoverageGenerator::AddCoverScreenTask(ScreenBase const & screen, bool doFor
|
|||
|
||||
++m_sequenceID;
|
||||
|
||||
m_queue.AddCommand(bind(&CoverageGenerator::CoverScreen, this, screen, m_sequenceID));
|
||||
m_queue.AddCommand(bind(&CoverageGenerator::CoverScreen, this, _1, screen, m_sequenceID));
|
||||
}
|
||||
|
||||
int CoverageGenerator::InsertBenchmarkFence()
|
||||
|
@ -172,7 +174,9 @@ void CoverageGenerator::SignalBenchmarkFence()
|
|||
m_fenceManager.signalFence(m_currentFenceID);
|
||||
}
|
||||
|
||||
void CoverageGenerator::CoverScreen(ScreenBase const & screen, int sequenceID)
|
||||
void CoverageGenerator::CoverScreen(core::CommandsQueue::Environment const & env,
|
||||
ScreenBase const & screen,
|
||||
int sequenceID)
|
||||
{
|
||||
if (sequenceID < m_sequenceID)
|
||||
return;
|
||||
|
@ -188,13 +192,16 @@ void CoverageGenerator::CoverScreen(ScreenBase const & screen, int sequenceID)
|
|||
AddCheckEmptyModelTask(sequenceID);
|
||||
}
|
||||
|
||||
m_workCoverage->Cache();
|
||||
bool shouldSwap = !m_isPaused && m_workCoverage->Cache(env);
|
||||
|
||||
if (shouldSwap)
|
||||
{
|
||||
threads::MutexGuard g(m_mutex);
|
||||
swap(m_currentCoverage, m_workCoverage);
|
||||
}
|
||||
|
||||
m_doForceUpdate = !shouldSwap;
|
||||
|
||||
m_workCoverage->Clear();
|
||||
|
||||
m_windowHandle->invalidate();
|
||||
|
@ -206,10 +213,12 @@ void CoverageGenerator::AddMergeTileTask(Tiler::RectInfo const & rectInfo,
|
|||
if (g_coverageGeneratorDestroyed)
|
||||
return;
|
||||
|
||||
m_queue.AddCommand(bind(&CoverageGenerator::MergeTile, this, rectInfo, sequenceID));
|
||||
m_queue.AddCommand(bind(&CoverageGenerator::MergeTile, this, _1, rectInfo, sequenceID));
|
||||
}
|
||||
|
||||
void CoverageGenerator::MergeTile(Tiler::RectInfo const & rectInfo, int sequenceID)
|
||||
void CoverageGenerator::MergeTile(core::CommandsQueue::Environment const & env,
|
||||
Tiler::RectInfo const & rectInfo,
|
||||
int sequenceID)
|
||||
{
|
||||
if (sequenceID < m_sequenceID)
|
||||
{
|
||||
|
@ -227,13 +236,16 @@ void CoverageGenerator::MergeTile(Tiler::RectInfo const & rectInfo, int sequence
|
|||
AddCheckEmptyModelTask(sequenceID);
|
||||
}
|
||||
|
||||
m_workCoverage->Cache();
|
||||
bool shouldSwap = !m_isPaused && m_workCoverage->Cache(env);
|
||||
|
||||
if (shouldSwap)
|
||||
{
|
||||
threads::MutexGuard g(m_mutex);
|
||||
swap(m_currentCoverage, m_workCoverage);
|
||||
}
|
||||
|
||||
m_doForceUpdate = !shouldSwap;
|
||||
|
||||
m_workCoverage->Clear();
|
||||
|
||||
m_windowHandle->invalidate();
|
||||
|
@ -302,3 +314,18 @@ string CoverageGenerator::GetCountryName(m2::PointD const & pt) const
|
|||
{
|
||||
return m_countryNameFn(pt);
|
||||
}
|
||||
|
||||
void CoverageGenerator::CancelCommands()
|
||||
{
|
||||
m_queue.CancelCommands();
|
||||
}
|
||||
|
||||
void CoverageGenerator::SetIsPaused(bool flag)
|
||||
{
|
||||
m_isPaused = flag;
|
||||
}
|
||||
|
||||
bool CoverageGenerator::DoForceUpdate() const
|
||||
{
|
||||
return m_doForceUpdate;
|
||||
}
|
||||
|
|
|
@ -66,6 +66,9 @@ private:
|
|||
FenceManager m_fenceManager;
|
||||
int m_currentFenceID;
|
||||
|
||||
bool m_doForceUpdate;
|
||||
bool m_isPaused;
|
||||
|
||||
ScreenCoverage * CreateCoverage();
|
||||
|
||||
public:
|
||||
|
@ -93,9 +96,16 @@ public:
|
|||
void AddCheckEmptyModelTask(int sequenceID);
|
||||
void AddFinishSequenceTask(int sequenceID);
|
||||
|
||||
void CoverScreen(ScreenBase const & screen, int sequenceID);
|
||||
void MergeTile(Tiler::RectInfo const & rectInfo, int sequenceID);
|
||||
void CoverScreen(core::CommandsQueue::Environment const & env,
|
||||
ScreenBase const & screen,
|
||||
int sequenceID);
|
||||
|
||||
void MergeTile(core::CommandsQueue::Environment const & env,
|
||||
Tiler::RectInfo const & rectInfo,
|
||||
int sequenceID);
|
||||
|
||||
void CheckEmptyModel(int sequenceID);
|
||||
|
||||
void FinishSequence(int sequenceID);
|
||||
|
||||
void Cancel();
|
||||
|
@ -110,9 +120,14 @@ public:
|
|||
void JoinBenchmarkFence(int fenceID);
|
||||
void SignalBenchmarkFence();
|
||||
|
||||
bool DoForceUpdate() const;
|
||||
|
||||
void SetSequenceID(int sequenceID);
|
||||
|
||||
threads::Mutex & Mutex();
|
||||
|
||||
shared_ptr<yg::ResourceManager> const & resourceManager() const;
|
||||
|
||||
void SetIsPaused(bool flag);
|
||||
void CancelCommands();
|
||||
};
|
||||
|
|
|
@ -10,6 +10,7 @@
|
|||
|
||||
#include "../yg/screen.hpp"
|
||||
#include "../yg/display_list.hpp"
|
||||
#include "../yg/skin.hpp"
|
||||
#include "../yg/base_texture.hpp"
|
||||
|
||||
#include "screen_coverage.hpp"
|
||||
|
@ -154,13 +155,15 @@ void ScreenCoverage::Merge(Tiler::RectInfo const & ri)
|
|||
}
|
||||
}
|
||||
|
||||
void ScreenCoverage::Cache()
|
||||
bool ScreenCoverage::Cache(core::CommandsQueue::Environment const & env)
|
||||
{
|
||||
/// caching tiles blitting commands.
|
||||
|
||||
m_displayList.reset();
|
||||
m_displayList.reset(m_cacheScreen->createDisplayList());
|
||||
|
||||
m_cacheScreen->setEnvironment(&env);
|
||||
|
||||
m_cacheScreen->beginFrame();
|
||||
m_cacheScreen->setDisplayList(m_displayList.get());
|
||||
|
||||
|
@ -195,6 +198,12 @@ void ScreenCoverage::Cache()
|
|||
/// while recording of displayList(for example UnlockStorage)
|
||||
|
||||
m_cacheScreen->completeCommands();
|
||||
|
||||
bool isCancelled = m_cacheScreen->isCancelled();
|
||||
|
||||
m_cacheScreen->setEnvironment(0);
|
||||
|
||||
return !isCancelled;
|
||||
}
|
||||
|
||||
void ScreenCoverage::SetScreen(ScreenBase const & screen)
|
||||
|
|
|
@ -113,7 +113,9 @@ public:
|
|||
/// Getter for Overlay
|
||||
shared_ptr<yg::Overlay> const & GetOverlay() const;
|
||||
/// Cache coverage in display list
|
||||
void Cache();
|
||||
/// @return true - if the coverage was cached successfully,
|
||||
/// false - otherwise(p.e. the caching was cancelled)
|
||||
bool Cache(core::CommandsQueue::Environment const & env);
|
||||
/// add rendered tile to coverage. Tile is locked, so make sure to unlock it in case it's not needed.
|
||||
void Merge(Tiler::RectInfo const & ri);
|
||||
/// recalculate screen coverage, using as much info from prev coverage as possible
|
||||
|
|
|
@ -274,6 +274,14 @@ namespace yg
|
|||
}
|
||||
}
|
||||
|
||||
/// is the rendering was cancelled, there possibly could
|
||||
/// be "ghost" render styles which are present in internal
|
||||
/// skin structures, but aren't rendered onto skin texture.
|
||||
/// so we are clearing the whole skin, to ensure that they
|
||||
/// are gone(slightly heavy, but very simple solution).
|
||||
if (isCancelled())
|
||||
m_skin->clearHandles();
|
||||
|
||||
base_t::endFrame();
|
||||
}
|
||||
|
||||
|
|
|
@ -89,6 +89,9 @@ namespace yg
|
|||
shared_ptr<BaseTexture> const & texture,
|
||||
bool shouldAddCheckPoint)
|
||||
{
|
||||
if (isCancelled())
|
||||
return;
|
||||
|
||||
vector<shared_ptr<ResourceStyle> > v;
|
||||
v.reserve(end - start);
|
||||
copy(&uploadQueue[0] + start, &uploadQueue[0] + end, back_inserter(v));
|
||||
|
@ -185,6 +188,9 @@ namespace yg
|
|||
size_t indicesOffs,
|
||||
unsigned primType)
|
||||
{
|
||||
if (isCancelled())
|
||||
return;
|
||||
|
||||
shared_ptr<DrawGeometry> command(new DrawGeometry());
|
||||
|
||||
command->m_texture = texture;
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
#include "../base/SRC_FIRST.hpp"
|
||||
|
||||
#include "overlay.hpp"
|
||||
#include "overlay_renderer.hpp"
|
||||
#include "text_element.hpp"
|
||||
|
||||
#include "../base/logging.hpp"
|
||||
|
@ -28,9 +29,17 @@ namespace yg
|
|||
return elem->roughBoundRect();
|
||||
}
|
||||
|
||||
void DrawIfNotCancelled(gl::OverlayRenderer * r,
|
||||
shared_ptr<OverlayElement> const & e,
|
||||
math::Matrix<double, 3, 3> const & m)
|
||||
{
|
||||
if (!r->isCancelled())
|
||||
e->draw(r, m);
|
||||
}
|
||||
|
||||
void Overlay::draw(gl::OverlayRenderer * r, math::Matrix<double, 3, 3> const & m)
|
||||
{
|
||||
m_tree.ForEach(bind(&OverlayElement::draw, _1, r, cref(m)));
|
||||
m_tree.ForEach(bind(&DrawIfNotCancelled, r, _1, cref(m)));
|
||||
}
|
||||
|
||||
Overlay::Overlay()
|
||||
|
|
|
@ -27,7 +27,8 @@ namespace yg
|
|||
m_isSynchronized(params.m_isSynchronized),
|
||||
m_isRendering(false),
|
||||
m_width(0),
|
||||
m_height(0)
|
||||
m_height(0),
|
||||
m_env(0)
|
||||
{
|
||||
m_frameBuffer = params.m_frameBuffer;
|
||||
m_resourceManager = params.m_resourceManager;
|
||||
|
@ -287,5 +288,18 @@ namespace yg
|
|||
if (m_renderQueue)
|
||||
m_renderQueue->completeCommands();
|
||||
}
|
||||
|
||||
void Renderer::setEnvironment(core::CommandsQueue::Environment const * env)
|
||||
{
|
||||
m_env = env;
|
||||
}
|
||||
|
||||
bool Renderer::isCancelled() const
|
||||
{
|
||||
if (m_env)
|
||||
return m_env->isCancelled();
|
||||
else
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -5,6 +5,7 @@
|
|||
#include "resource_manager.hpp"
|
||||
|
||||
#include "../base/threaded_list.hpp"
|
||||
#include "../base/commands_queue.hpp"
|
||||
#include "../std/function.hpp"
|
||||
#include "../std/shared_ptr.hpp"
|
||||
#include "../geometry/rect2d.hpp"
|
||||
|
@ -102,6 +103,8 @@ namespace yg
|
|||
unsigned int m_width;
|
||||
unsigned int m_height;
|
||||
|
||||
core::CommandsQueue::Environment const * m_env;
|
||||
|
||||
public:
|
||||
|
||||
static const yg::Color s_bgColor;
|
||||
|
@ -151,6 +154,9 @@ namespace yg
|
|||
void addFramePoint();
|
||||
|
||||
void completeCommands();
|
||||
|
||||
void setEnvironment(core::CommandsQueue::Environment const * env);
|
||||
bool isCancelled() const;
|
||||
};
|
||||
}
|
||||
}
|
||||
|
|
|
@ -354,6 +354,12 @@ namespace yg
|
|||
m_additionalPages[0]->setPipelineID(0 + m_pages.size());
|
||||
}
|
||||
|
||||
void Skin::clearHandles()
|
||||
{
|
||||
for (unsigned i = 0; i < m_pages.size(); ++i)
|
||||
m_pages[i]->clear();
|
||||
}
|
||||
|
||||
void Skin::clearAdditionalPage()
|
||||
{
|
||||
m_additionalPages.clear();
|
||||
|
|
|
@ -57,8 +57,6 @@ namespace yg
|
|||
|
||||
bool m_fillAlpha;
|
||||
|
||||
void clearHandles();
|
||||
|
||||
Skin(shared_ptr<ResourceManager> const & resourceManager,
|
||||
TSkinPages const & pages);
|
||||
|
||||
|
@ -141,6 +139,8 @@ namespace yg
|
|||
void setAdditionalPage(shared_ptr<SkinPage> const & pages);
|
||||
void clearAdditionalPage();
|
||||
|
||||
void clearHandles();
|
||||
|
||||
void memoryWarning();
|
||||
void enterBackground();
|
||||
void enterForeground();
|
||||
|
|
Loading…
Add table
Reference in a new issue