1 /* |
1 /* |
2 * Copyright (c) 2009 Nokia Corporation and/or its subsidiary(-ies). |
2 * Copyright (c) 2009-2010 Nokia Corporation and/or its subsidiary(-ies). |
3 * All rights reserved. |
3 * All rights reserved. |
4 * This component and the accompanying materials are made available |
4 * This component and the accompanying materials are made available |
5 * under the terms of "Eclipse Public License v1.0" |
5 * under the terms of "Eclipse Public License v1.0" |
6 * which accompanies this distribution, and is available |
6 * which accompanies this distribution, and is available |
7 * at the URL "http://www.eclipse.org/legal/epl-v10.html". |
7 * at the URL "http://www.eclipse.org/legal/epl-v10.html". |
26 #include <avkondomainpskeys.h> // keyguard state |
26 #include <avkondomainpskeys.h> // keyguard state |
27 #include <hwrmpowerstatesdkpskeys.h> // battery status |
27 #include <hwrmpowerstatesdkpskeys.h> // battery status |
28 #include <UsbWatcherInternalPSKeys.h> // usb status |
28 #include <UsbWatcherInternalPSKeys.h> // usb status |
29 #include <usbman.h> |
29 #include <usbman.h> |
30 #include <usbpersonalityids.h> |
30 #include <usbpersonalityids.h> |
|
31 #include <tspropertydefs.h> |
31 |
32 |
32 #include <QMetaEnum> |
33 #include <QMetaEnum> |
33 #include <QString> |
34 #include <QString> |
34 #include <QVariant> |
35 #include <QVariant> |
35 #include <QTimer> |
36 #include <QTimer> |
41 #include "cxuieventlog.h" |
42 #include "cxuieventlog.h" |
42 #include "cxuiapplication.h" |
43 #include "cxuiapplication.h" |
43 #include "cxesettings.h" |
44 #include "cxesettings.h" |
44 #include "cxuiapplicationframeworkmonitorprivate.h" |
45 #include "cxuiapplicationframeworkmonitorprivate.h" |
45 |
46 |
46 namespace{ |
47 namespace |
|
48 { |
47 const int CXUI_USB_MODE_CHECK_TIMER_DELAY = 1000; // 1 second |
49 const int CXUI_USB_MODE_CHECK_TIMER_DELAY = 1000; // 1 second |
48 } |
50 |
49 |
51 #ifdef Q_OS_SYMBIAN |
50 #ifdef Q_OS_SYMBIAN |
|
51 namespace |
|
52 { |
|
53 inline QString convertTDesC2QString(const TDesC& aDescriptor) |
52 inline QString convertTDesC2QString(const TDesC& aDescriptor) |
54 { |
53 { |
55 #ifdef QT_NO_UNICODE |
54 #ifdef QT_NO_UNICODE |
56 return QString::fromLocal8Bit(aDescriptor.Ptr(), aDescriptor.Length()); |
55 return QString::fromLocal8Bit(aDescriptor.Ptr(), aDescriptor.Length()); |
57 #else |
56 #else |
71 } |
70 } |
72 } |
71 } |
73 return convertTDesC2QString(name); |
72 return convertTDesC2QString(name); |
74 } |
73 } |
75 |
74 |
76 inline QString bitString(int number, char fill = '0', int width = 32) |
|
77 { |
|
78 return QString::number(number, 2).rightJustified(width, fill); |
|
79 } |
|
80 |
|
81 //!@todo: Avkon UIDs not needed once device dialogs fully implemented in Orbit. |
|
82 |
|
83 // AknCapServer |
|
84 static const unsigned int UID_AKNCAPSERVER = 0x10207218; |
|
85 |
|
86 // Phone ui |
75 // Phone ui |
87 static const unsigned int UID_PHONEUI = 0x100058B3; |
76 static const unsigned int UID_PHONEUI = 0x100058B3; |
88 // Task switcher |
77 // Task switcher |
89 static const unsigned int UID_TASKSWITCHER = 0x2002677D; |
78 static const unsigned int UID_TASKSWITCHER = 0x2002677D; |
90 // Dialog server |
79 // Dialog server |
91 static const unsigned int UID_DIALOGAPPSERVER = 0x20022FC5; |
80 static const unsigned int UID_DIALOGAPPSERVER = 0x20022FC5; |
92 |
81 |
93 // Log event types |
82 // Log event types |
94 static const char *EVENT_USB = "usb"; |
83 static const char *EVENT_USB = "usb"; |
95 static const char *EVENT_FOREGROUND = "foreground"; |
84 static const char *EVENT_FOREGROUND = "foreground"; |
96 } |
85 |
97 #endif // Q_OS_SYMBIAN |
86 #endif // Q_OS_SYMBIAN |
|
87 } // namespace |
98 |
88 |
99 |
89 |
100 /*! |
90 /*! |
101 * Constructor |
91 * Constructor |
102 */ |
92 */ |
112 mWindowGroupId(mWindowGroup.Identifier()), |
102 mWindowGroupId(mWindowGroup.Identifier()), |
113 mWindowGroupName(), |
103 mWindowGroupName(), |
114 mKeyLockState(EKeyguardNotActive), |
104 mKeyLockState(EKeyguardNotActive), |
115 mBatteryStatus(EBatteryStatusUnknown), |
105 mBatteryStatus(EBatteryStatusUnknown), |
116 mUsbPersonality(0), |
106 mUsbPersonality(0), |
|
107 mTaskManagerVisibility(false), |
117 mUsbModeCheckTimer(this), |
108 mUsbModeCheckTimer(this), |
118 mEventLog(NULL), |
109 mEventLog(NULL), |
119 #endif // Q_OS_SYMBIAN |
110 #endif // Q_OS_SYMBIAN |
120 mState(CxuiApplicationFrameworkMonitor::ForegroundOwned) |
111 mState(CxuiApplicationFrameworkMonitor::ForegroundOwned) |
121 { |
112 { |
122 CX_DEBUG_ENTER_FUNCTION(); |
113 CX_DEBUG_ENTER_FUNCTION(); |
123 #ifdef Q_OS_SYMBIAN |
114 #ifdef Q_OS_SYMBIAN |
124 mWindowGroup.EnableFocusChangeEvents(); |
115 mWindowGroup.EnableFocusChangeEvents(); |
125 mWindowGroupName = windowGroupName(mWsSession, mWindowGroupId); |
116 mWindowGroupName = windowGroupName(mWsSession, mWindowGroupId); |
126 mEventLog = new CxuiEventLog("CxuiApplicationFrameworkMonitorPrivate"); |
117 mEventLog = new CxuiEventLog("CxuiApplicationFrameworkMonitorPrivate"); |
|
118 |
127 init(); |
119 init(); |
|
120 |
128 mUsbModeCheckTimer.setSingleShot(true); |
121 mUsbModeCheckTimer.setSingleShot(true); |
129 mUsbModeCheckTimer.setInterval(CXUI_USB_MODE_CHECK_TIMER_DELAY); |
122 mUsbModeCheckTimer.setInterval(CXUI_USB_MODE_CHECK_TIMER_DELAY); |
130 connect(&mUsbModeCheckTimer, SIGNAL(timeout()), |
123 connect(&mUsbModeCheckTimer, SIGNAL(timeout()), |
131 this, SLOT(usbModeCheckTimerCallback())); |
124 this, SLOT(usbModeCheckTimerCallback())); |
132 #endif // Q_OS_SYMBIAN |
125 #endif // Q_OS_SYMBIAN |
257 mUsbModeCheckTimer.start(); |
250 mUsbModeCheckTimer.start(); |
258 } |
251 } |
259 |
252 |
260 } |
253 } |
261 } |
254 } |
|
255 } else if (uid == TsProperty::KCategory.iUid && key == TsProperty::KVisibilityKey) { |
|
256 CX_DEBUG(("CxuiApplicationFrameworkMonitor - Task Manager visibility: %d -> %d", mTaskManagerVisibility, value.toBool())); |
|
257 const bool newTsVisibility(value.toBool()); |
|
258 |
|
259 // If the task switcher state is changed, then emit signal to inform client(s). |
|
260 if (mTaskManagerVisibility != newTsVisibility) { |
|
261 mTaskManagerVisibility = newTsVisibility; |
|
262 emit q->taskSwitcherStateChanged(mTaskManagerVisibility); |
|
263 } |
262 } |
264 } |
263 |
265 |
264 CX_DEBUG_EXIT_FUNCTION(); |
266 CX_DEBUG_EXIT_FUNCTION(); |
265 } |
267 } |
266 |
268 |
286 */ |
288 */ |
287 void CxuiApplicationFrameworkMonitorPrivate::init() |
289 void CxuiApplicationFrameworkMonitorPrivate::init() |
288 { |
290 { |
289 CX_DEBUG_ENTER_FUNCTION(); |
291 CX_DEBUG_ENTER_FUNCTION(); |
290 |
292 |
|
293 // To be able to release resources fast enough, we need foreground |
|
294 // priority also when moving to background. Once we have moved to |
|
295 // background fully, we re-adjust Window Server "compute mode" |
|
296 // to the normal value. |
|
297 mWsSession.ComputeMode(RWsSession::EPriorityControlDisabled); |
|
298 |
291 // Connect to application (window server) events. |
299 // Connect to application (window server) events. |
292 connect(&mApplication, SIGNAL(symbianEvent(const QSymbianEvent *)), this, SLOT(handleEvent(const QSymbianEvent *))); |
300 connect(&mApplication, SIGNAL(symbianEvent(const QSymbianEvent *)), this, SLOT(handleEvent(const QSymbianEvent *))); |
293 |
301 |
294 QVariant value; |
302 QVariant value; |
295 |
303 |
302 mKeyLockState = value.toInt(); |
310 mKeyLockState = value.toInt(); |
303 |
311 |
304 // Get current USB personality |
312 // Get current USB personality |
305 mSettings.get(KPSUidUsbWatcher.iUid, KUsbWatcherSelectedPersonality, Cxe::PublishAndSubscribe, value); |
313 mSettings.get(KPSUidUsbWatcher.iUid, KUsbWatcherSelectedPersonality, Cxe::PublishAndSubscribe, value); |
306 mUsbPersonality = value.toInt(); |
314 mUsbPersonality = value.toInt(); |
|
315 |
|
316 // Get current Task Switcher foreground status |
|
317 mSettings.get(TsProperty::KCategory.iUid, TsProperty::KVisibilityKey, Cxe::PublishAndSubscribe, value); |
|
318 mTaskManagerVisibility = value.toBool(); |
307 |
319 |
308 bool ok = connect(&mSettings, SIGNAL(settingValueChanged(long int, unsigned long int, QVariant)), |
320 bool ok = connect(&mSettings, SIGNAL(settingValueChanged(long int, unsigned long int, QVariant)), |
309 this, SLOT(handlePropertyEvent(long int, unsigned long int, QVariant))); |
321 this, SLOT(handlePropertyEvent(long int, unsigned long int, QVariant))); |
310 CX_DEBUG_ASSERT(ok); |
322 CX_DEBUG_ASSERT(ok); |
311 |
323 |
340 case EEventFocusLost: { |
352 case EEventFocusLost: { |
341 CX_DEBUG(("CxuiApplicationFrameworkMonitor - EEventFocusLost event")); |
353 CX_DEBUG(("CxuiApplicationFrameworkMonitor - EEventFocusLost event")); |
342 setState(getCurrentState()); |
354 setState(getCurrentState()); |
343 break; |
355 break; |
344 } |
356 } |
345 case EEventWindowVisibilityChanged: { |
|
346 const TWsVisibilityChangedEvent *visibilityEvent = wsEvent->VisibilityChanged(); |
|
347 if (visibilityEvent) { |
|
348 CX_DEBUG(("CxuiApplicationFrameworkMonitor - EFullyVisible: bits[%s]", |
|
349 bitString(TWsVisibilityChangedEvent::EFullyVisible).toAscii().constData() )); |
|
350 CX_DEBUG(("CxuiApplicationFrameworkMonitor - EPartiallyVisible: bits[%s]", |
|
351 bitString(TWsVisibilityChangedEvent::EPartiallyVisible).toAscii().constData() )); |
|
352 CX_DEBUG(("CxuiApplicationFrameworkMonitor - ENotVisible: bits[%s]", |
|
353 bitString(TWsVisibilityChangedEvent::ENotVisible).toAscii().constData() )); |
|
354 CX_DEBUG(("CxuiApplicationFrameworkMonitor - event: bits[%s]", |
|
355 bitString(visibilityEvent->iFlags).toAscii().constData() )); |
|
356 } |
|
357 break; |
|
358 } |
|
359 default: |
357 default: |
360 break; |
358 break; |
361 } |
359 } |
362 } |
360 } |
363 } |
361 } |
368 */ |
366 */ |
369 void CxuiApplicationFrameworkMonitorPrivate::setState(CxuiApplicationFrameworkMonitor::ForegroundState state) |
367 void CxuiApplicationFrameworkMonitorPrivate::setState(CxuiApplicationFrameworkMonitor::ForegroundState state) |
370 { |
368 { |
371 if (mState != state) { |
369 if (mState != state) { |
372 const CxuiApplicationFrameworkMonitor::ForegroundState original(mState); |
370 const CxuiApplicationFrameworkMonitor::ForegroundState original(mState); |
373 |
|
374 // Check if state transition is acceptable in current state. |
371 // Check if state transition is acceptable in current state. |
375 switch (mState) { |
372 switch (mState) { |
376 case CxuiApplicationFrameworkMonitor::ForegroundOwned: |
373 case CxuiApplicationFrameworkMonitor::ForegroundOwned: |
377 case CxuiApplicationFrameworkMonitor::ForegroundPartiallyLost: |
374 case CxuiApplicationFrameworkMonitor::ForegroundPartiallyLost: |
378 // All changes accepted. |
375 // All changes accepted. |
387 CX_DEBUG(("CxuiApplicationFrameworkMonitor - state change full bg -> partial bg ignored")); |
384 CX_DEBUG(("CxuiApplicationFrameworkMonitor - state change full bg -> partial bg ignored")); |
388 } |
385 } |
389 } |
386 } |
390 |
387 |
391 if (mState != original) { |
388 if (mState != original) { |
|
389 if (mState == CxuiApplicationFrameworkMonitor::ForegroundOwned) { |
|
390 // Keep foreground priority until fully in background. |
|
391 // See init() for more comments. |
|
392 mWsSession.ComputeMode(RWsSession::EPriorityControlDisabled); |
|
393 } |
|
394 |
|
395 // If state was changed, signal it to listeners. |
|
396 emit q->foregroundStateChanged(mState); |
|
397 |
|
398 if (mState == CxuiApplicationFrameworkMonitor::ForegroundFullyLost) { |
|
399 // Background has been entered. |
|
400 // Return Window Server "compute mode" to the normal value. |
|
401 mWsSession.ComputeMode(RWsSession::EPriorityControlComputeOff); |
|
402 } |
|
403 |
|
404 #ifdef CX_DEBUG |
392 // Print the event log with this foreground event included. |
405 // Print the event log with this foreground event included. |
393 if (mEventLog) { |
406 if (mEventLog) { |
394 mEventLog->append( |
407 mEventLog->append( |
395 EVENT_FOREGROUND, |
408 EVENT_FOREGROUND, |
396 CxuiApplicationFrameworkMonitor::staticMetaObject.enumerator( |
409 CxuiApplicationFrameworkMonitor::staticMetaObject.enumerator( |
397 CxuiApplicationFrameworkMonitor::staticMetaObject.indexOfEnumerator("ForegroundState")).valueToKey(mState)); |
410 CxuiApplicationFrameworkMonitor::staticMetaObject.indexOfEnumerator("ForegroundState")).valueToKey(mState)); |
398 mEventLog->print(); |
411 mEventLog->print(); |
399 } |
412 } |
400 |
413 #endif // CX_DEBUG |
401 // If state was changed, signal it to listeners. |
|
402 emit q->foregroundStateChanged(mState); |
|
403 } |
414 } |
404 } |
415 } |
405 } |
416 } |
406 |
417 |
407 /*! |
418 /*! |
428 // Need to check if foreground is owned by known apps. |
439 // Need to check if foreground is owned by known apps. |
429 unsigned int uid(focusedApplicationUid()); |
440 unsigned int uid(focusedApplicationUid()); |
430 |
441 |
431 // Check the app uid. |
442 // Check the app uid. |
432 switch (uid) { |
443 switch (uid) { |
433 case UID_AKNCAPSERVER: |
|
434 case UID_TASKSWITCHER: |
444 case UID_TASKSWITCHER: |
435 case UID_DIALOGAPPSERVER: |
445 case UID_DIALOGAPPSERVER: |
436 // Note or task switcher in foreground. |
446 // Note or task switcher in foreground. |
437 state = CxuiApplicationFrameworkMonitor::ForegroundPartiallyLost; |
447 state = CxuiApplicationFrameworkMonitor::ForegroundPartiallyLost; |
438 break; |
448 break; |