diff options
author | Jan-Marek Glogowski <glogow@fbihome.de> | 2017-02-24 18:27:49 +0100 |
---|---|---|
committer | Jan-Marek Glogowski <glogow@fbihome.de> | 2017-07-13 12:10:26 +0200 |
commit | f0aabfe601223cee214b0be1b2ebf51a80b68f2c (patch) | |
tree | 0dfa34248472307a5b9620f201b38e48ad1c8838 /vcl/osx | |
parent | 69977ed917a92d9b07f3429312077357d3aa10fa (diff) |
OSX change to run LO via a single shot timer
As all other backends, this runs the LO main loop just via the
OSX main loop.
Change-Id: Ie7562444951e16ff58edcaf6409f32809314c2fa
Diffstat (limited to 'vcl/osx')
-rw-r--r-- | vcl/osx/salinst.cxx | 27 | ||||
-rw-r--r-- | vcl/osx/salnstimer.mm | 27 | ||||
-rw-r--r-- | vcl/osx/saltimer.cxx | 95 | ||||
-rw-r--r-- | vcl/osx/vclnsapp.mm | 4 |
4 files changed, 82 insertions, 71 deletions
diff --git a/vcl/osx/salinst.cxx b/vcl/osx/salinst.cxx index c1890c8d5eb7..5936c0618805 100644 --- a/vcl/osx/salinst.cxx +++ b/vcl/osx/salinst.cxx @@ -473,8 +473,11 @@ void AquaSalInstance::handleAppDefinedEvent( NSEvent* pEvent ) [pDockMenu release]; pDockMenu = nil; } + break; } - break; + case DispatchTimerEvent: + AquaSalTimer::handleDispatchTimerEvent(); + break; #if !HAVE_FEATURE_MACOSX_SANDBOX case AppleRemoteControlEvent: // Defined in <apple_remote/RemoteMainController.h> { @@ -563,6 +566,7 @@ bool AquaSalInstance::DoYield(bool bWait, bool bHandleAllCurrentEvents, sal_uLon { (void) nReleased; assert(nReleased == 0); // not implemented + bool bHadEvent = false; // ensure that the per thread autorelease pool is top level and // will therefore not be destroyed by cocoa implicitly @@ -587,6 +591,7 @@ bool AquaSalInstance::DoYield(bool bWait, bool bHandleAllCurrentEvents, sal_uLon { aEvent = maUserEvents.front(); maUserEvents.pop_front(); + bHadEvent = true; } else bDispatchUser = false; @@ -598,15 +603,15 @@ bool AquaSalInstance::DoYield(bool bWait, bool bHandleAllCurrentEvents, sal_uLon { aEvent.mpFrame->CallCallback( aEvent.mnType, aEvent.mpData ); maWaitingYieldCond.set(); - // return if only one event is asked for - if( ! bHandleAllCurrentEvents ) - return true; } + + // return if only one event is asked for + if( !bHandleAllCurrentEvents && bDispatchUser ) + return true; } // handle cocoa event queue // cocoa events may be only handled in the thread the NSApp was created - bool bHadEvent = false; if( IsMainThread() && mnActivePrintJobs == 0 ) { // we need to be woken up by a cocoa-event @@ -651,18 +656,6 @@ SAL_WNODEPRECATED_DECLARATIONS_POP [NSApp updateWindows]; AcquireYieldMutex( nCount ); - - // #i86581# - // FIXME: sometimes the NSTimer will never fire. Firing it by hand then - // fixes the problem even seems to set the correct next firing date - // Why oh why? - if( ! pEvent && AquaSalTimer::pRunningTimer ) - { - // this cause crashes on MacOSX 10.4 - // [AquaSalTimer::pRunningTimer fire]; - if (ImplGetSVData()->maSchedCtx.mpSalTimer != nullptr) - ImplGetSVData()->maSchedCtx.mpSalTimer->CallCallback(); - } } mbWaitingYield = bOldWaitingYield; diff --git a/vcl/osx/salnstimer.mm b/vcl/osx/salnstimer.mm index 00f67e52cd26..9c3264295d60 100644 --- a/vcl/osx/salnstimer.mm +++ b/vcl/osx/salnstimer.mm @@ -29,19 +29,20 @@ -(void)timerElapsed:(NSTimer*)pTimer { (void)pTimer; - if( AquaSalTimer::bDispatchTimer ) - { - SolarMutexGuard aGuard; - ImplSVData* pSVData = ImplGetSVData(); - if( pSVData->maSchedCtx.mpSalTimer ) - { - pSVData->maSchedCtx.mpSalTimer->CallCallback(); - - // NSTimer does not end nextEventMatchingMask of NSApplication - // so we need to wakeup a waiting Yield to inform it something happened - GetSalData()->mpFirstInstance->wakeupYield(); - } - } +SAL_WNODEPRECATED_DECLARATIONS_PUSH +// 'NSApplicationDefined' is deprecated: first deprecated in macOS 10.12 + NSEvent* pEvent = [NSEvent otherEventWithType: NSApplicationDefined +SAL_WNODEPRECATED_DECLARATIONS_POP + location: NSZeroPoint + modifierFlags: 0 + timestamp: [NSDate timeIntervalSinceReferenceDate] + windowNumber: 0 + context: nil + subtype: AquaSalInstance::DispatchTimerEvent + data1: 0 + data2: 0 ]; + assert( pEvent ); + [NSApp postEvent: pEvent atStart: YES]; } @end diff --git a/vcl/osx/saltimer.cxx b/vcl/osx/saltimer.cxx index 0221c81a17ae..415ad1284af8 100644 --- a/vcl/osx/saltimer.cxx +++ b/vcl/osx/saltimer.cxx @@ -28,15 +28,42 @@ #include "osx/salinst.h" NSTimer* AquaSalTimer::pRunningTimer = nil; -bool AquaSalTimer::bDispatchTimer = false; -void ImplSalStartTimer( sal_uLong nMS ) +static void ImplSalStopTimer(); + +static inline void ImplPostEvent( short nEventId, bool bAtStart, int nUserData = 0 ) +{ + SalData::ensureThreadAutoreleasePool(); +SAL_WNODEPRECATED_DECLARATIONS_PUSH +// 'NSApplicationDefined' is deprecated: first deprecated in macOS 10.12 + NSEvent* pEvent = [NSEvent otherEventWithType: NSApplicationDefined +SAL_WNODEPRECATED_DECLARATIONS_POP + location: NSZeroPoint + modifierFlags: 0 + timestamp: [NSDate timeIntervalSinceReferenceDate] + windowNumber: 0 + context: nil + subtype: nEventId + data1: nUserData + data2: 0 ]; + assert( pEvent ); + [NSApp postEvent: pEvent atStart: bAtStart]; +} + +static void ImplSalStartTimer( sal_uLong nMS ) { SalData* pSalData = GetSalData(); - if( !pSalData->mpFirstInstance->IsMainThread() ) + + if ( 0 == nMS ) { - AquaSalTimer::bDispatchTimer = true; - NSTimeInterval aTI = double(nMS)/1000.0; + ImplSalStopTimer(); + ImplPostEvent( AquaSalInstance::DispatchTimerEvent, false ); + return; + } + + if( pSalData->mpFirstInstance->IsMainThread() ) + { + NSTimeInterval aTI = double(nMS) / 1000.0; if( AquaSalTimer::pRunningTimer != nil ) { if (rtl::math::approxEqual( @@ -46,18 +73,16 @@ void ImplSalStartTimer( sal_uLong nMS ) [AquaSalTimer::pRunningTimer setFireDate: [NSDate dateWithTimeIntervalSinceNow: aTI]]; } else - { - [AquaSalTimer::pRunningTimer invalidate]; - AquaSalTimer::pRunningTimer = nil; - } + ImplSalStopTimer(); } if( AquaSalTimer::pRunningTimer == nil ) { - AquaSalTimer::pRunningTimer = [NSTimer scheduledTimerWithTimeInterval: aTI - target: [[[TimerCallbackCaller alloc] init] autorelease] - selector: @selector(timerElapsed:) - userInfo: nil - repeats: YES]; + AquaSalTimer::pRunningTimer = [[NSTimer scheduledTimerWithTimeInterval: aTI + target: [[[TimerCallbackCaller alloc] init] autorelease] + selector: @selector(timerElapsed:) + userInfo: nil + repeats: NO + ] retain]; /* #i84055# add timer to tracking run loop mode, so they also elapse while e.g. life resize */ @@ -65,29 +90,25 @@ void ImplSalStartTimer( sal_uLong nMS ) } } else + ImplPostEvent( AquaSalInstance::AppStartTimerEvent, true, nMS ); +} + +static void ImplSalStopTimer() +{ + if( AquaSalTimer::pRunningTimer != nil ) { - SalData::ensureThreadAutoreleasePool(); - // post an event so we can get into the main thread -SAL_WNODEPRECATED_DECLARATIONS_PUSH - // 'NSApplicationDefined' is deprecated: first deprecated in macOS 10.12 - NSEvent* pEvent = [NSEvent otherEventWithType: NSApplicationDefined - location: NSZeroPoint - modifierFlags: 0 - timestamp: [NSDate timeIntervalSinceReferenceDate] - windowNumber: 0 - context: nil - subtype: AquaSalInstance::AppStartTimerEvent - data1: (int)nMS - data2: 0 ]; -SAL_WNODEPRECATED_DECLARATIONS_POP - if( pEvent ) - [NSApp postEvent: pEvent atStart: YES]; + [AquaSalTimer::pRunningTimer invalidate]; + [AquaSalTimer::pRunningTimer release]; + AquaSalTimer::pRunningTimer = nil; } } -void ImplSalStopTimer() +void AquaSalTimer::handleDispatchTimerEvent() { - AquaSalTimer::bDispatchTimer = false; + ImplSVData* pSVData = ImplGetSVData(); + SolarMutexGuard aGuard; + if( pSVData->maSchedCtx.mpSalTimer ) + pSVData->maSchedCtx.mpSalTimer->CallCallback(); } void AquaSalTimer::handleStartTimerEvent( NSEvent* pEvent ) @@ -98,14 +119,10 @@ void AquaSalTimer::handleStartTimerEvent( NSEvent* pEvent ) NSTimeInterval posted = [pEvent timestamp] + NSTimeInterval([pEvent data1])/1000.0; NSTimeInterval current = [NSDate timeIntervalSinceReferenceDate]; if( (posted - current) <= 0.0 ) - { - SolarMutexGuard aGuard; - if( pSVData->maSchedCtx.mpSalTimer ) - pSVData->maSchedCtx.mpSalTimer->CallCallback(); - } - ImplSalStartTimer( sal_uLong( [pEvent data1] ) ); + handleDispatchTimerEvent(); + else + ImplSalStartTimer( sal_uLong( [pEvent data1] ) ); } - } AquaSalTimer::AquaSalTimer( ) diff --git a/vcl/osx/vclnsapp.mm b/vcl/osx/vclnsapp.mm index 4c38466961b0..2add55ffde85 100644 --- a/vcl/osx/vclnsapp.mm +++ b/vcl/osx/vclnsapp.mm @@ -73,8 +73,8 @@ SAL_WNODEPRECATED_DECLARATIONS_PUSH data1: 0 data2: 0 ]; SAL_WNODEPRECATED_DECLARATIONS_POP - if( pEvent ) - [NSApp postEvent: pEvent atStart: NO]; + assert( pEvent ); + [NSApp postEvent: pEvent atStart: NO]; } -(void)sendEvent:(NSEvent*)pEvent |