forked from organicmaps/organicmaps
added Animator class as a central manager of all map-related animations.
This commit is contained in:
parent
c928d967c8
commit
43e6ed5c89
7 changed files with 102 additions and 44 deletions
52
map/animator.cpp
Normal file
52
map/animator.cpp
Normal file
|
@ -0,0 +1,52 @@
|
|||
#include "animator.hpp"
|
||||
#include "rotate_screen_task.hpp"
|
||||
#include "framework.hpp"
|
||||
|
||||
#include "../anim/controller.hpp"
|
||||
|
||||
#include "../geometry/angles.hpp"
|
||||
|
||||
Animator::Animator(Framework * framework)
|
||||
: m_framework(framework)
|
||||
{
|
||||
m_rotationThreshold = ang::DegreeToRad(10);
|
||||
}
|
||||
|
||||
void Animator::RotateScreen(double startAngle, double endAngle, double duration)
|
||||
{
|
||||
bool shouldRotate = false;
|
||||
|
||||
if (m_rotateScreenTask && m_rotateScreenTask->IsRunning())
|
||||
{
|
||||
// if the end angle seriously changed we should re-create rotation task.
|
||||
if (fabs(ang::GetShortestDistance(m_rotateScreenTask->EndAngle(), endAngle)) > m_rotationThreshold)
|
||||
shouldRotate = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
// if there are no current rotate screen task or the task is finished already
|
||||
// we check for the distance between current screen angle and headingAngle
|
||||
if (fabs(ang::GetShortestDistance(startAngle, endAngle)) > m_rotationThreshold)
|
||||
shouldRotate = true;
|
||||
}
|
||||
|
||||
if (shouldRotate)
|
||||
{
|
||||
StopRotation();
|
||||
m_rotateScreenTask.reset(new RotateScreenTask(m_framework,
|
||||
startAngle,
|
||||
endAngle,
|
||||
duration));
|
||||
|
||||
m_framework->GetAnimController()->AddTask(m_rotateScreenTask);
|
||||
}
|
||||
}
|
||||
|
||||
void Animator::StopRotation()
|
||||
{
|
||||
if (m_rotateScreenTask
|
||||
&& m_rotateScreenTask->IsRunning())
|
||||
m_rotateScreenTask->Cancel();
|
||||
|
||||
m_rotateScreenTask.reset();
|
||||
}
|
31
map/animator.hpp
Normal file
31
map/animator.hpp
Normal file
|
@ -0,0 +1,31 @@
|
|||
#pragma once
|
||||
|
||||
#include "../std/shared_ptr.hpp"
|
||||
|
||||
class Framework;
|
||||
class RotateScreenTask;
|
||||
|
||||
/// Class, which is responsible for
|
||||
/// tracking all map animations.
|
||||
class Animator
|
||||
{
|
||||
private:
|
||||
|
||||
Framework * m_framework;
|
||||
|
||||
shared_ptr<RotateScreenTask> m_rotateScreenTask;
|
||||
|
||||
bool m_rotationThreshold;
|
||||
|
||||
public:
|
||||
|
||||
/// constructor by Framework
|
||||
Animator(Framework * framework);
|
||||
/// rotate screen by shortest path.
|
||||
void RotateScreen(double startAngle,
|
||||
double endAngle,
|
||||
double duration);
|
||||
/// stopping screen rotation
|
||||
void StopRotation();
|
||||
|
||||
};
|
|
@ -117,6 +117,7 @@ static void GetResourcesMaps(vector<string> & outMaps)
|
|||
Framework::Framework()
|
||||
: //m_hasPendingInvalidate(false),
|
||||
//m_doForceUpdate(false),
|
||||
m_animator(this),
|
||||
m_etalonSize(GetPlatform().ScaleEtalonSize()),
|
||||
m_queryMaxScaleMode(false),
|
||||
m_drawPlacemark(false),
|
||||
|
@ -1317,6 +1318,11 @@ bool Framework::GetVisiblePOI(m2::PointD const & pxPoint, m2::PointD & pxPivot,
|
|||
return false;
|
||||
}
|
||||
|
||||
Animator & Framework::GetAnimator()
|
||||
{
|
||||
return m_animator;
|
||||
}
|
||||
|
||||
Navigator & Framework::GetNavigator()
|
||||
{
|
||||
return m_navigator;
|
||||
|
|
|
@ -6,6 +6,7 @@
|
|||
#include "window_handle.hpp"
|
||||
#include "location_state.hpp"
|
||||
#include "navigator.hpp"
|
||||
#include "animator.hpp"
|
||||
#include "feature_vec_model.hpp"
|
||||
#include "bookmark.hpp"
|
||||
|
||||
|
@ -71,6 +72,7 @@ protected:
|
|||
mutable scoped_ptr<search::Engine> m_pSearchEngine;
|
||||
model::FeaturesFetcher m_model;
|
||||
Navigator m_navigator;
|
||||
Animator m_animator;
|
||||
|
||||
vector<BookmarkCategory *> m_bookmarks;
|
||||
|
||||
|
@ -356,6 +358,8 @@ public:
|
|||
|
||||
gui::Controller * GetGuiController() const;
|
||||
anim::Controller * GetAnimController() const;
|
||||
|
||||
Animator & GetAnimator();
|
||||
Navigator & GetNavigator();
|
||||
|
||||
/// Set the localized strings bundle
|
||||
|
|
|
@ -376,7 +376,9 @@ namespace location
|
|||
|
||||
void State::CheckFollowCompass()
|
||||
{
|
||||
if (m_hasCompass && (CompassProcessMode() == ECompassFollow) && IsCentered())
|
||||
if (m_hasCompass
|
||||
&& (CompassProcessMode() == ECompassFollow)
|
||||
&& IsCentered())
|
||||
FollowCompass();
|
||||
}
|
||||
|
||||
|
@ -392,51 +394,15 @@ namespace location
|
|||
double startAngle = m_framework->GetNavigator().Screen().GetAngle();
|
||||
double endAngle = -m_compassFilter.GetHeadingRad();
|
||||
|
||||
bool shouldRotate = false;
|
||||
|
||||
if (m_rotateScreenTask && m_rotateScreenTask->IsRunning())
|
||||
{
|
||||
// if the end angle seriously changed we should re-create rotation task.
|
||||
if (fabs(ang::GetShortestDistance(m_rotateScreenTask->EndAngle(), endAngle)) > ang::DegreeToRad(10))
|
||||
shouldRotate = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
// if there are no current rotate screen task or the task is finished already
|
||||
// we check for the distance between current screen angle and headingAngle
|
||||
if (fabs(ang::GetShortestDistance(startAngle, endAngle)) > ang::DegreeToRad(10))
|
||||
shouldRotate = true;
|
||||
}
|
||||
|
||||
if (shouldRotate)
|
||||
{
|
||||
m_framework->GetInformationDisplay().locationState()->StopAnimation();
|
||||
StopAnimation();
|
||||
|
||||
m_rotateScreenTask.reset(new RotateScreenTask(m_framework,
|
||||
startAngle,
|
||||
endAngle,
|
||||
2));
|
||||
|
||||
controller->AddTask(m_rotateScreenTask);
|
||||
}
|
||||
m_framework->GetAnimator().RotateScreen(startAngle, endAngle, 2);
|
||||
|
||||
controller->Unlock();
|
||||
}
|
||||
|
||||
void State::StopAnimation()
|
||||
{
|
||||
if (m_rotateScreenTask
|
||||
&& !m_rotateScreenTask->IsEnded()
|
||||
&& !m_rotateScreenTask->IsCancelled())
|
||||
m_rotateScreenTask->Cancel();
|
||||
m_rotateScreenTask.reset();
|
||||
}
|
||||
|
||||
void State::StopCompassFollowing()
|
||||
{
|
||||
SetCompassProcessMode(ECompassDoNothing);
|
||||
StopAnimation();
|
||||
m_framework->GetAnimator().StopRotation();
|
||||
}
|
||||
|
||||
bool State::IsCentered() const
|
||||
|
|
|
@ -60,8 +60,6 @@ namespace location
|
|||
ELocationProcessMode m_locationProcessMode;
|
||||
ECompassProcessMode m_compassProcessMode;
|
||||
|
||||
shared_ptr<RotateScreenTask> m_rotateScreenTask;
|
||||
|
||||
void FollowCompass();
|
||||
|
||||
/// GUI element related fields.
|
||||
|
@ -119,7 +117,6 @@ namespace location
|
|||
|
||||
void TurnOff();
|
||||
|
||||
void StopAnimation();
|
||||
void StopCompassFollowing();
|
||||
void SetIsCentered(bool flag);
|
||||
bool IsCentered() const;
|
||||
|
|
|
@ -50,7 +50,8 @@ HEADERS += \
|
|||
country_status_display.hpp \
|
||||
rotate_screen_task.hpp \
|
||||
compass_arrow.hpp \
|
||||
compass_filter.hpp
|
||||
compass_filter.hpp \
|
||||
animator.hpp
|
||||
|
||||
SOURCES += \
|
||||
feature_vec_model.cpp \
|
||||
|
@ -92,7 +93,8 @@ SOURCES += \
|
|||
country_status_display.cpp \
|
||||
rotate_screen_task.cpp \
|
||||
compass_arrow.cpp \
|
||||
compass_filter.cpp
|
||||
compass_filter.cpp \
|
||||
animator.cpp
|
||||
|
||||
!iphone*:!bada*:!android* {
|
||||
HEADERS += qgl_render_context.hpp
|
||||
|
|
Loading…
Add table
Reference in a new issue