To use the Privacy Query and Notification API to create a notifier a licensee must first implement a single notifier class that derives from the Privacy Query and Notification API base class CPosPrivacyNotifier.
The CPosPrivacyNotifier subclass must implement the virtual functions of the base class:
New privacy verification query and notification requests are received by the notifier through CPosPrivacyNotifier::HandleNewRequestL(). The example code below shows how the notifier handles requests sequentially by simply calling a helper function HandleNextRequestL() to get the next request.
void CMyPrivacyNotifier::HandleNewRequestL(TPosQNRequestId /*aRequestId*/) { if (iIsBusy) // TBool flag which specifies if the notifier is already { // handling a request. If it is, do nothing for now. return; } // Handle the request HandleNextRequestL(); }
The example code below shows how the notifier gets the next request to be processed. The code shows how the notifier:
Gets an array of all waiting requests by calling CPosPrivacyNotifier::GetRequestsL().
Gets the first request in the array and sets it as the current request by calling CPosPrivacyNotifier::SetCurrentRequestL().
Checks if the request is a notification, and if so, checks if the request type is supported by calling CPosPrivacyNotifier::NotificationReason(). If the request type is not supported the request is completed by calling CPosPrivacyNotifier::CompleteRequest().
Checks if the type of request is a privacy verification (EQuery) or a notification (ENotification) and launches the appropriate dialog for each case.
void CMyPrivacyNotifier::HandleNextRequestL() { // Read the next request RArray<TPosQNRequestId> requests; CleanupClosePushL(requests); GetRequestsL(requests); // Choose next request to handle TBool requestFound = EFalse; while (!requestFound) { if (requests.Count() == 0) { // There are no requests to handle. Do nothing. CleanupStack::PopAndDestroy(); // requests return; } // Read information about the active request iActiveRequest = requests[0]; SetCurrentRequestL(iActiveRequest); // In case of notification request, check that notification reason is // supported, otherwise complete the request with KErrNotSupported. if (RequestTypeL(iActiveRequest) == ENotification && !(NotificationReason() == EPosDecisionByRequestSource || NotificationReason() == EPosVerificationTimeout)) { // The notification reason is not supported by the UI. CompleteRequest(iActiveRequest, KErrNotSupported); requests.Remove(0); } else { requestFound = ETrue; } } CleanupStack::PopAndDestroy(); // requests iIsBusy = ETrue; CDesCArrayFlat* requestors = new (ELeave) CDesCArrayFlat (KRequestorGranularity); CleanupStack::PushL(requestors); TInt nofRequestors = RequestorCountL(); for (TInt I = 0; I < nofRequestors; I++) { CPosRequestor* requestor = RequestorLC(I); requestors->AppendL(requestor->RequestorIdString()); CleanupStack::PopAndDestroy(requestor); } // Check whether the request is a query or a notification if (RequestTypeL(iActiveRequest) == EQuery) { LaunchQueryDialogL(requestors); // takes array ownership } else // RequestTypeL(iActiveRequest) == ENotification { LaunchNotificationDialogL(requestors); // takes array ownership } CleanupStack::Pop(requestors); }
When the mobile device user has responded to the dialog, the notifier must send a response back to the LBS subsystem. In the example code below, the method DialogDismissed() is called when the dialog is closed. The type of request (EQuery or ENotification) and the reason why the dialog was closed is passed as an input parameter to the method.
Note also how requests are handled sequentially in the code: CPosPrivacyNotifier::HandleNextRequest() is called to process the next request only when the current request is completed.
void CMyPrivacyNotifier::DialogDismissed(TRequestType aRequestType, TInt aDismissReason) { iIsBusy = EFalse; // Complete the request with correct completion code. TInt completionCode = KErrNone; if (aRequestType == EQuery) { switch (aDismissReason) { case EUserChooseAccept : completionCode = KErrNone; break; case EUserChooseReject : completionCode = KErrAccessDenied; break; case EDialogTimedOut : completionCode = KErrTimedOut; break; default : completionCode = KErrGeneral; } } else // aRequestType == ENotification { switch (aDismissReason) { case EUserPressedOk : completionCode = KErrNone; break; case EDialogTimedOut : completionCode = KErrTimedOut; break; default : completionCode = KErrGeneral; } } CompleteRequest(iActiveRequest, completionCode); // Handle the next request HandleNextRequest(); } // Non leaving method for handling the next request void CMyPrivacyNotifier::HandleNextRequest() { TRAPD(err, HandleNextRequestL()); if (err) { CompleteAllRequests(err); } }
A privacy request can be cancelled by the network. The LBS subsystem calls CPosPrivacyNotifier::HandleRequestCancelled() on the notifier to cancel the request. The code example below shows an implementation.
void CMyPrivacyNotifier::HandleRequestCancelled(TPosQNRequestId aRequestId) { switch (CancelReason()) { case EPosCancelReasonTimeout: // Notify the user that the query timed out. break; default: // Do nothing break; } // We only need to do anything if the request is the one which is currently // handled. if (iActiveRequest == aRequestId) { // Close the active dialog DismissDialog(); HandleNextRequest(); } }
Copyright ©2010 Nokia Corporation and/or its subsidiary(-ies).
All rights
reserved. Unless otherwise stated, these materials are provided under the terms of the Eclipse Public License
v1.0.