diff options
author | Tobias Madl <tobias.madl.dev@gmail.com> | 2014-10-30 20:07:59 +0100 |
---|---|---|
committer | Michael Meeks <michael.meeks@collabora.com> | 2014-11-05 20:59:44 +0000 |
commit | d6e89e7516271d246b255ec5ebc752713da3dfd5 (patch) | |
tree | bcbcf58593f6191eb88057f2da2ea8ff2fa15410 | |
parent | 9632045906baf165076d11a97f45b153d8e2acb7 (diff) |
Basic Idle handler implementation
An idle handler will ultimately be a zero time timeout with
prioritisation layered on top of that.
Change-Id: I3f0802d5001172fc7b8409274bc5a3632e5dad34
-rw-r--r-- | include/vcl/timer.hxx | 36 | ||||
-rw-r--r-- | vcl/inc/window.h | 4 | ||||
-rw-r--r-- | vcl/source/app/timer.cxx | 57 | ||||
-rw-r--r-- | vcl/source/window/paint.cxx | 16 | ||||
-rw-r--r-- | vcl/source/window/window.cxx | 14 | ||||
-rw-r--r-- | vcl/source/window/winproc.cxx | 2 |
6 files changed, 111 insertions, 18 deletions
diff --git a/include/vcl/timer.hxx b/include/vcl/timer.hxx index d3ebe1a256e5..10dd3fca730f 100644 --- a/include/vcl/timer.hxx +++ b/include/vcl/timer.hxx @@ -73,6 +73,42 @@ public: AutoTimer& operator=( const AutoTimer& rTimer ); }; +enum IdlePriority { + VCL_IDLE_PRIORITY_HIGHEST, // -> 0ms + VCL_IDLE_PRIORITY_HIGH, // -> 1ms + VCL_IDLE_PRIORITY_REPAINT, // -> 30ms + VCL_IDLE_PRIORITY_RESIZE, // -> 50ms + VCL_IDLE_PRIORITY_MEDIUM, // -> 50ms + VCL_IDLE_PRIORITY_LOW, // -> 100ms + VCL_IDLE_PRIORITY_LOWER, // -> 200ms + VCL_IDLE_PRIORITY_LOWEST // -> 400ms +}; + + +// To port from Timer -> Idle switch class name, +// s/Timeout/DoIdle/ etc. and select priority +class VCL_DLLPUBLIC Idle : public Timer +{ + public: + Idle(); + Idle( IdlePriority ePriority ); + virtual ~Idle(); + + void SetPriority( IdlePriority ePriority ); + + /// Make it possible to associate a callback with this idle handler + /// of course, you can also sub-class and override 'DoIdle' + void SetIdleHdl( const Link& rLink ) { SetTimeoutHdl( rLink ); } + const Link& GetIdleHdl() const { return GetTimeoutHdl(); } + + void Start() { Timer::Start(); } + void Stop() { Timer::Stop(); } + + virtual void DoIdle(); + + virtual void Timeout() SAL_OVERRIDE { DoIdle(); } +}; + #endif // INCLUDED_VCL_TIMER_HXX /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/vcl/inc/window.h b/vcl/inc/window.h index 53d077f200e8..2b2082e75d59 100644 --- a/vcl/inc/window.h +++ b/vcl/inc/window.h @@ -127,8 +127,8 @@ struct ImplOverlapData struct ImplFrameData { - Timer maPaintTimer; //< paint timer - Timer maResizeTimer; //< resize timer + Idle maPaintIdle; //< paint idle handler + Idle maResizeIdle; //< resize timer InputContext maOldInputContext; //< last set Input Context vcl::Window* mpNextFrame; //< next frame window vcl::Window* mpFirstOverlap; //< first overlap vcl::Window diff --git a/vcl/source/app/timer.cxx b/vcl/source/app/timer.cxx index ecbfa7467cdc..5f706abcb88a 100644 --- a/vcl/source/app/timer.cxx +++ b/vcl/source/app/timer.cxx @@ -336,4 +336,61 @@ AutoTimer& AutoTimer::operator=( const AutoTimer& rTimer ) return *this; } +Idle::Idle() + : Timer() +{ + SetPriority(VCL_IDLE_PRIORITY_LOWEST); +} + +Idle::Idle( IdlePriority ePriority ) + : Timer() +{ + SetPriority( ePriority ); +} + +void Idle::SetPriority( IdlePriority ePriority ) +{ + sal_uLong nTimeoutMS = 0; + + // Ultimately this will just be a sort key in a work queue. + switch (ePriority) { + case VCL_IDLE_PRIORITY_HIGHEST: + nTimeoutMS = 0; + break; + case VCL_IDLE_PRIORITY_HIGH: + nTimeoutMS = 1; + break; + case VCL_IDLE_PRIORITY_REPAINT: + nTimeoutMS = 30; + break; + case VCL_IDLE_PRIORITY_RESIZE: + nTimeoutMS = 50; + break; + case VCL_IDLE_PRIORITY_MEDIUM: + nTimeoutMS = 50; + break; + case VCL_IDLE_PRIORITY_LOW: + nTimeoutMS = 100; + break; + case VCL_IDLE_PRIORITY_LOWER: + nTimeoutMS = 200; + break; + case VCL_IDLE_PRIORITY_LOWEST: + default: + nTimeoutMS = 400; + break; + } + SetTimeout( nTimeoutMS ); +} + +void Idle::DoIdle() +{ + maTimeoutHdl.Call( this ); +} + + +Idle::~Idle() +{ +} + /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/vcl/source/window/paint.cxx b/vcl/source/window/paint.cxx index ce10abae4ae3..7ec329cc1388 100644 --- a/vcl/source/window/paint.cxx +++ b/vcl/source/window/paint.cxx @@ -283,8 +283,8 @@ void Window::ImplCallOverlapPaint() void Window::ImplPostPaint() { - if ( !ImplDoTiledRendering() && !mpWindowImpl->mpFrameData->maPaintTimer.IsActive() ) - mpWindowImpl->mpFrameData->maPaintTimer.Start(); + if ( !ImplDoTiledRendering() && !mpWindowImpl->mpFrameData->maPaintIdle.IsActive() ) + mpWindowImpl->mpFrameData->maPaintIdle.Start(); } IMPL_LINK_NOARG(Window, ImplHandlePaintHdl) @@ -292,14 +292,14 @@ IMPL_LINK_NOARG(Window, ImplHandlePaintHdl) // save paint events until layout is done if (!ImplDoTiledRendering() && IsSystemWindow() && static_cast<const SystemWindow*>(this)->hasPendingLayout()) { - mpWindowImpl->mpFrameData->maPaintTimer.Start(); + mpWindowImpl->mpFrameData->maPaintIdle.Start(); return 0; } // save paint events until resizing is done if( !ImplDoTiledRendering() && - mpWindowImpl->mbFrame && mpWindowImpl->mpFrameData->maResizeTimer.IsActive() ) - mpWindowImpl->mpFrameData->maPaintTimer.Start(); + mpWindowImpl->mbFrame && mpWindowImpl->mpFrameData->maResizeIdle.IsActive() ) + mpWindowImpl->mpFrameData->maPaintIdle.Start(); else if ( mpWindowImpl->mbReallyVisible ) ImplCallOverlapPaint(); return 0; @@ -314,10 +314,10 @@ IMPL_LINK_NOARG(Window, ImplHandleResizeTimerHdl) { ImplHandlePaintHdl(NULL); } - else if( mpWindowImpl->mpFrameData->maPaintTimer.IsActive() ) + else if( mpWindowImpl->mpFrameData->maPaintIdle.IsActive() ) { - mpWindowImpl->mpFrameData->maPaintTimer.Stop(); - mpWindowImpl->mpFrameData->maPaintTimer.GetTimeoutHdl().Call( NULL ); + mpWindowImpl->mpFrameData->maPaintIdle.Stop(); + mpWindowImpl->mpFrameData->maPaintIdle.GetIdleHdl().Call( NULL ); } } diff --git a/vcl/source/window/window.cxx b/vcl/source/window/window.cxx index 606a4f551ead..b4468848ef20 100644 --- a/vcl/source/window/window.cxx +++ b/vcl/source/window/window.cxx @@ -1029,11 +1029,11 @@ void Window::ImplInit( vcl::Window* pParent, WinBits nStyle, SystemParentData* p mpWindowImpl->mpFrameData->mbSysObjFocus = false; if (!ImplDoTiledRendering()) { - mpWindowImpl->mpFrameData->maPaintTimer.SetTimeout( 30 ); - mpWindowImpl->mpFrameData->maPaintTimer.SetTimeoutHdl( LINK( this, Window, ImplHandlePaintHdl ) ); + mpWindowImpl->mpFrameData->maPaintIdle.SetPriority( VCL_IDLE_PRIORITY_REPAINT ); + mpWindowImpl->mpFrameData->maPaintIdle.SetIdleHdl( LINK( this, Window, ImplHandlePaintHdl ) ); } - mpWindowImpl->mpFrameData->maResizeTimer.SetTimeout( 50 ); - mpWindowImpl->mpFrameData->maResizeTimer.SetTimeoutHdl( LINK( this, Window, ImplHandleResizeTimerHdl ) ); + mpWindowImpl->mpFrameData->maResizeIdle.SetPriority( VCL_IDLE_PRIORITY_RESIZE ); + mpWindowImpl->mpFrameData->maResizeIdle.SetIdleHdl( LINK( this, Window, ImplHandleResizeTimerHdl ) ); mpWindowImpl->mpFrameData->mbInternalDragGestureRecognizer = false; if ( pRealParent && IsTopWindow() ) @@ -2476,11 +2476,11 @@ Size Window::GetSizePixel() const } // #i43257# trigger pending resize handler to assure correct window sizes - if( mpWindowImpl->mpFrameData->maResizeTimer.IsActive() ) + if( mpWindowImpl->mpFrameData->maResizeIdle.IsActive() ) { ImplDelData aDogtag( this ); - mpWindowImpl->mpFrameData->maResizeTimer.Stop(); - mpWindowImpl->mpFrameData->maResizeTimer.GetTimeoutHdl().Call( NULL ); + mpWindowImpl->mpFrameData->maResizeIdle.Stop(); + mpWindowImpl->mpFrameData->maResizeIdle.GetIdleHdl().Call( NULL ); if( aDogtag.IsDead() ) return Size(0,0); } diff --git a/vcl/source/window/winproc.cxx b/vcl/source/window/winproc.cxx index 62974ca3621e..ee864f4de982 100644 --- a/vcl/source/window/winproc.cxx +++ b/vcl/source/window/winproc.cxx @@ -1596,7 +1596,7 @@ void ImplHandleResize( vcl::Window* pWindow, long nNewWidth, long nNewHeight ) bStartTimer = false; if( bStartTimer ) - pWindow->ImplGetWindowImpl()->mpFrameData->maResizeTimer.Start(); + pWindow->ImplGetWindowImpl()->mpFrameData->maResizeIdle.Start(); else pWindow->ImplCallResize(); // otherwise menus cannot be positioned } |