diff --git a/indexer/index.cpp b/indexer/index.cpp index 68ecf412d6..b07c6375ec 100644 --- a/indexer/index.cpp +++ b/indexer/index.cpp @@ -163,13 +163,14 @@ int Index::UpdateMap(string const & fileName, m2::RectD & rect) if (id != INVALID_MWM_ID && m_info[id].m_lockCount > 0) { m_info[id].SetStatus(MwmInfo::STATUS_PENDING_UPDATE); - return -2; + rv = -2; + } else { + ReplaceFileWithReady(fileName); + rv = RegisterImpl(fileName, rect); } - - ReplaceFileWithReady(fileName); - - rv = RegisterImpl(fileName, rect); } + if (rv != -1) + m_observers.ForEach(&Observer::OnMapUpdateIsReady, fileName); if (rv >= 0) m_observers.ForEach(&Observer::OnMapUpdated, fileName); return rv; diff --git a/indexer/index.hpp b/indexer/index.hpp index 5f89228bc5..1e1f97080d 100644 --- a/indexer/index.hpp +++ b/indexer/index.hpp @@ -40,13 +40,25 @@ protected: virtual void UpdateMwmInfo(MwmId id); public: + /// An Observer interface to MwmSet. Note that these functions can + /// be called from *ANY* thread because most signals are sent when + /// some thread releases its MwmLock, so overrides must be as fast + /// as possible and non-blocking when it's possible. class Observer { public: virtual ~Observer() {} + /// Called when a map is registered for a first time. virtual void OnMapRegistered(string const & file) {} + + /// Called when update for a map is downloaded. + virtual void OnMapUpdateIsReady(string const & file) {} + + /// Called when update for a map is applied. virtual void OnMapUpdated(string const & file) {} + + /// Called when map is deleted. virtual void OnMapDeleted(string const & file) {} }; diff --git a/indexer/indexer_tests/index_test.cpp b/indexer/indexer_tests/index_test.cpp index df3448941d..8d09c4d653 100644 --- a/indexer/indexer_tests/index_test.cpp +++ b/indexer/indexer_tests/index_test.cpp @@ -24,7 +24,11 @@ class Observer : public Index::Observer { public: Observer(string const & file) - : m_file(file), m_map_registered_calls(0), m_map_updated_calls(0), m_map_deleted_calls(0) + : m_file(file), + m_map_registered_calls(0), + m_map_update_is_ready_calls(0), + m_map_updated_calls(0), + m_map_deleted_calls(0) { } @@ -34,11 +38,19 @@ public: CHECK_EQUAL(m_file, file, ()); ++m_map_registered_calls; } + + void OnMapUpdateIsReady(string const & file) override + { + CHECK_EQUAL(m_file, file, ()); + ++m_map_update_is_ready_calls; + } + void OnMapUpdated(string const & file) override { CHECK_EQUAL(m_file, file, ()); ++m_map_updated_calls; } + void OnMapDeleted(string const & file) override { CHECK_EQUAL(m_file, file, ()); @@ -46,12 +58,14 @@ public: } int map_registered_calls() const { return m_map_registered_calls; } + int map_update_is_ready_calls() const { return m_map_update_is_ready_calls; } int map_updated_calls() const { return m_map_updated_calls; } int map_deleted_calls() const { return m_map_deleted_calls; } private: string const m_file; int m_map_registered_calls; + int m_map_update_is_ready_calls; int m_map_updated_calls; int m_map_deleted_calls; }; @@ -100,8 +114,10 @@ UNIT_TEST(Index_MwmStatusNotifications) MY_SCOPE_GUARD(testMapUpdateGuard, bind(&CheckedDeleteFile, testMapUpdatePath)); // Check that observers are notified when map is deleted. + TEST_EQUAL(0, observer.map_update_is_ready_calls(), ()); TEST_EQUAL(0, observer.map_updated_calls(), ()); TEST_LESS_OR_EQUAL(0, index.UpdateMap(testMapName, dummyRect), ()); + TEST_EQUAL(1, observer.map_update_is_ready_calls(), ()); TEST_EQUAL(1, observer.map_updated_calls(), ()); // Check that observers are notified when map is deleted.