11 #include "CallAppFrame.h"
12 #include "CallPresentationModel.h"
13 #include "CallTypes.h"
14 #include "CallAppUtility.h"
15 #include "CallIAppStateChangeListner.h"
17 using namespace Tizen::App;
18 using namespace Tizen::Base;
19 using namespace Tizen::System;
20 using namespace Tizen::Ui;
21 using namespace Tizen::Ui::Controls;
22 using namespace Tizen::Ui::Scenes;
23 using namespace Tizen::Base::Utility;
24 using namespace Tizen::Base::Collection;
25 using namespace Tizen::Base::Utility;
26 using namespace Tizen::Shell;
29 CallApp::CallApp(void):__initialSceneId(L""), __pLaunchArgs(null)
31 __listenerList.Construct();
34 CallApp::~CallApp(void)
39 CallApp::CreateInstance(void)
41 // Create the instance through the constructor.
46 CallApp::OnAppInitializing(AppRegistry& appRegistry)
48 AppControlProviderManager* pProviderMgr = AppControlProviderManager::GetInstance();
49 pProviderMgr->SetAppControlProviderEventListener(this);
50 PowerManager::AddScreenEventListener(*this);
55 CallApp::OnAppInitialized(void)
61 CallAppFrame* pCallAppFrame = new CallAppFrame();
62 pCallAppFrame->Construct();
63 pCallAppFrame->SetName(L"CallApp");
64 AddFrame(*pCallAppFrame);
66 //Check if there is no initial scene, then exit application.
67 //This case will normally come when invalid AppControl request has come,
68 //or incoming call is coming from unknown number and "reject unknown number" settings is enabled.
69 if (GetInitialScene().IsEmpty() == true)
78 CallApp::OnAppWillTerminate(void)
86 CallApp::OnAppTerminating(AppRegistry& appRegistry, bool forcedTermination)
89 // Deallocate resources allocated by this App for termination.
90 // The App's permanent data and context can be saved via appRegistry.
91 PowerManager::RemoveScreenEventListener(*this);
96 CallApp::OnForeground(void)
98 IEnumerator* pEnum = __listenerList.GetEnumeratorN();
99 while (pEnum->MoveNext() == E_SUCCESS)
101 IAppStateChangeListener* pInterface = static_cast<IAppStateChangeListener*>(pEnum->GetCurrent());
102 if (pInterface == null)
108 pInterface->OnForeground();
114 CallApp::OnBackground(void)
117 // Stop drawing when the application is moved to the background.
121 CallApp::OnLowMemory(void)
124 // Free unused resources or close the application.
128 CallApp::OnBatteryLevelChanged(BatteryLevel batteryLevel)
131 // Handle any changes in battery level here.
132 // Stop using multimedia features(camera, mp3 etc.) if the battery level is CRITICAL.
136 CallApp::OnScreenOn(void)
139 // Get the released resources or resume the operations that were paused or stopped in OnScreenOff().
143 CallApp::OnScreenOff(void)
145 AppLogDebug("Enter");
146 IEnumerator* pEnum = __listenerList.GetEnumeratorN();
147 while (pEnum->MoveNext() == E_SUCCESS)
149 IAppStateChangeListener* pInterface = static_cast<IAppStateChangeListener*>(pEnum->GetCurrent());
150 if (pInterface == null)
156 pInterface->OnScreenOff();
163 CallApp::GetInitialScene(void)
165 return __initialSceneId;
169 CallApp::GetAppLaunchArguments(void)
171 return __pLaunchArgs;
175 CallApp::AddAppStateChangeListener(const IAppStateChangeListener& listener)
177 __listenerList.Add(listener);
181 CallApp::RemoveAppStateChangeListener(const IAppStateChangeListener& listener)
183 __listenerList.Remove(listener);
187 CallApp::OnAppControlRequestReceived(RequestId reqId, const String& operationId, const String* pUriData,
188 const String* pMimeType, const IMap* pExtraData)
190 AppLogDebug("Enter ");
193 AppLogDebug("%ls ",pUriData->GetPointer());
196 if(pExtraData == null && pUriData != null)
198 //The request is from web app
199 AppLogDebug("%ls",pUriData->GetPointer());
200 ProcessWebAppControlRequest(reqId, operationId, pUriData);
204 //process AppControl parameters
205 ProcessAppControlRequest(reqId, operationId, pExtraData,pUriData);
211 CallApp::ProcessWebAppControlRequest(RequestId reqId, const String& operationId,const String* pUriData)
213 //Construct map from string
214 String delim(DELIMITER);
215 StringTokenizer st(*pUriData,delim);
218 extraData.Construct();
219 while(st.HasMoreTokens())
223 st.GetNextToken(token);
226 if(st.HasMoreTokens())
229 st.GetNextToken(token);
233 extraData.Add(new (std::nothrow) String(key), new (std::nothrow) String(value));
236 //Adding this explicitly as there no other way to invoke call from webapp
237 extraData.Add(new (std::nothrow) String(PARAM_CALL_TYPE), new (std::nothrow) String(PARAM_CALL_VALUE_VOICE));
239 ProcessAppControlRequest(reqId,operationId,&extraData);
241 extraData.RemoveAll(true);
245 CallApp::ProcessAppControlRequest(RequestId reqId, const String& operationId,const IMap* pArgsMap,const String* pUriData)
247 AppLogDebug("Enter %ls",operationId.GetPointer());
248 __pLaunchArgs = null;
249 if(operationId.Equals(OPERATION_ID_CALL,true) == true)
251 AppLogDebug("OPERATION_ID_CALL");
254 bool isIncomingCallRequest = false;
255 String* pKey = new (std::nothrow) String(LAUNCHTYPE);
256 if (pArgsMap->ContainsKey(*pKey) == true)
258 const String* pValue = static_cast<const String*>(pArgsMap->GetValue(*pKey));
259 if ((pValue != null) && (pValue->Equals(PARAM_ORIGIN_MT, true) == true))
261 isIncomingCallRequest = true;
264 //Check if incoming call request or outgoing call request
265 if(isIncomingCallRequest == true)
267 HandleIncomingCallAppControlRequest(reqId, pArgsMap);
271 HandleDialCallAppControlRequest(reqId, pArgsMap,pUriData);
276 AppLogDebug("pArgsMap == null");
282 CallApp::HandleIncomingCallAppControlRequest(RequestId reqId,const IMap* pArgsMap)
284 AppLogDebug("Enter");
285 SceneManager* pSceneManager = SceneManager::GetInstance();
287 AppCtrlResult appControlResult = APP_CTRL_RESULT_FAILED;
290 String callHandle(L"");
291 String* pKey = new (std::nothrow) String(CALL_HANDLE);
292 if (pArgsMap->ContainsKey(*pKey) == true)
294 const String* pValue = static_cast<const String*>(pArgsMap->GetValue(*pKey));
297 callHandle.Append(*pValue);
302 String contactNumber(L"");
303 pKey = new (std::nothrow) String(CONTACT_NUMBER);
304 if (pArgsMap->ContainsKey(*pKey) == true)
306 const String* pContactValue = static_cast<const String*>(pArgsMap->GetValue(*pKey));
307 if (pContactValue != null)
309 contactNumber.Append(*pContactValue);
310 AppLogDebug("%ls",contactNumber.GetPointer());
316 //Fetch incoming call details
317 CallPresentationModel* pCallPresentor = CallPresentationModel::GetInstance();
318 AppCallInfo* pIncomingCall = pCallPresentor->FetchIncomingCallDetailsN(callHandle, contactNumber);
319 if(pIncomingCall != null)
321 bool isCallRejected = pCallPresentor->CheckIncomingCallToBeRejected(pIncomingCall);
322 if(isCallRejected == false)
324 //Abort any AppControl Request running already to show incoming call screen
325 if (pCallPresentor->IsAppControlRunning() == true)
327 pCallPresentor->AbortAppControlRequest();
329 //save app launch argument list
330 __pLaunchArgs = new (std::nothrow) ArrayList(SingleObjectDeleter);
331 __pLaunchArgs->Construct(1);
332 __pLaunchArgs->Add(pIncomingCall);
333 if(__initialSceneId.IsEmpty() == true)
335 __initialSceneId = IDSCN_SCENE_INCOMINGCALL;
339 //App already initialized, goto incoming call form
340 pSceneManager->GoForward(ForwardSceneTransition(IDSCN_SCENE_INCOMINGCALL), __pLaunchArgs);
341 __pLaunchArgs = null;
346 //Show messageBox showing automatic call rejection
347 /*MessageBox callRejectedInoMsgBox;
348 String msg(L"Call From ");
349 msg.Append(contactNumber);
350 msg.Append(L" Rejected.");
351 callRejectedInoMsgBox.Construct(L"Call Rejected", msg, MSGBOX_STYLE_NONE,1000);
353 // Calls ShowAndWait() : Draws and Shows itself and processes events
354 callRejectedInoMsgBox.ShowAndWait(modalResult);*/
356 //go back to previous scene if App was already running, else exit application.
357 if(__initialSceneId.IsEmpty() == true)
359 //KEEP "__initialSceneId" as empty and return false from "OnAppInitialized()"
360 AppLog("Terminate Phone Application");
364 //set success message
365 appControlResult = APP_CTRL_RESULT_SUCCEEDED;
369 appControlResult = APP_CTRL_RESULT_FAILED;
371 AppLogDebug("Exiting %d",appControlResult);
372 AppControlProviderManager::GetInstance()->SendAppControlResult(reqId, appControlResult, null);
376 CallApp::HandleDialCallAppControlRequest(RequestId reqId,const IMap* pArgsMap,const String* pUriData)
379 AppCtrlResult appControlResult = APP_CTRL_RESULT_FAILED;
381 if (pArgsMap != null)
383 String callType(L"");
384 String phoneNumber(L"");
386 String* pKey = new (std::nothrow) String(PARAM_PHONE_NUMBER);
387 if(pArgsMap->ContainsKey(*pKey) == true)
389 const String* pPhoneValue = static_cast<const String*>(pArgsMap->GetValue(*pKey));
390 if(pPhoneValue != null)
392 AppLogDebug("%ls",pPhoneValue->GetPointer());
393 phoneNumber.Append(*pPhoneValue);
398 AppLogDebug("PARAM_PHONE_NUMBER not present");
399 //Now check if tel uri is present
402 AppLogDebug("pUriData is present %ls",pUriData->GetPointer());
403 phoneNumber.Append(*pUriData);
404 if(phoneNumber.Contains(PARAM_PHONE_NUMBER))
406 phoneNumber.Replace(PARAM_PHONE_NUMBER,L"");
407 if(phoneNumber.Contains(DELIMITER))
409 phoneNumber.Replace(DELIMITER,L"");
410 AppLogDebug("%ls",phoneNumber.GetPointer());
413 AppLogDebug("%ls",phoneNumber.GetPointer());
417 //Check if its a valid number
418 if(CheckNumberIsValid(phoneNumber) == false)
420 //go back to previous scene if App was already running, else exit application.
421 if(__initialSceneId.IsEmpty() == true)
423 //KEEP "__initialSceneId" as empty and return false from "OnAppInitialized()"
424 AppLog("Terminate Phone Application");
425 AppControlProviderManager::GetInstance()->SendAppControlResult(reqId, appControlResult, null);
431 //invalid phone number.always return, but App will come to foreground
432 //and show current screen, if any calls is present.
437 pKey = new (std::nothrow) String(PARAM_CALL_TYPE);
438 if(pArgsMap->ContainsKey(*pKey) == true)
440 const String* pCallTypeValue = static_cast<const String*>(pArgsMap->GetValue(*pKey));
441 if(pCallTypeValue != null)
443 callType.Append(*pCallTypeValue);
449 //Fetch currently active call count
450 if (callType.IsEmpty() == false
451 && callType.Equals(PARAM_CALL_VALUE_VOICE, false) == true
452 && phoneNumber.IsEmpty() == false)
454 SceneManager* pSceneManager = SceneManager::GetInstance();
455 //check if there is already a call in dialing mode, then dont accept any other dialing request.
456 if (pSceneManager->GetCurrentSceneId() == IDSCN_SCENE_OUTCALL
457 || pSceneManager->GetCurrentSceneId()
458 == IDSCN_SCENE_OUT_EMERGENCYCALL)
461 appControlResult = APP_CTRL_RESULT_CANCELED;
462 AppControlProviderManager::GetInstance()->SendAppControlResult(reqId, appControlResult, null);
465 CallPresentationModel* pCallPresentor = CallPresentationModel::GetInstance();
466 int currentActiveCallCount = pCallPresentor->GetCurrentCallCount();
467 if(currentActiveCallCount <= 1)
469 //Abort any AppControl Request running already to show incoming call screen
470 if (pCallPresentor->IsAppControlRunning() == true)
472 pCallPresentor->AbortAppControlRequest();
474 //make an outgoing call with given number
475 String* contactTxt = new (std::nothrow) String(phoneNumber);
476 __pLaunchArgs = new (std::nothrow) ArrayList(SingleObjectDeleter);
477 __pLaunchArgs->Construct();
478 __pLaunchArgs->Add(contactTxt);
479 bool isEmergencyCall = pCallPresentor->IsEmergencyNumber(*contactTxt, true);
481 SceneId nextScene = IDSCN_SCENE_OUTCALL;
484 nextScene = IDSCN_SCENE_OUT_EMERGENCYCALL;
486 //Check if app was already running
487 if(__initialSceneId.IsEmpty() == true)
489 //phone App is not already launched
490 __initialSceneId = nextScene;
494 AppLog("Outgoing call");
495 pSceneManager->GoForward( ForwardSceneTransition( nextScene), __pLaunchArgs);
497 appControlResult = APP_CTRL_RESULT_SUCCEEDED;
501 //already 2 active calls, 3rd call not allowed
502 appControlResult = APP_CTRL_RESULT_CANCELED;
507 appControlResult = APP_CTRL_RESULT_FAILED;
510 //send response message
511 AppControlProviderManager::GetInstance()->SendAppControlResult(reqId, appControlResult, null);
515 CallApp::CheckNumberIsValid(String phoneNumber)
517 //Pattern to compare all characters except 0-9 * # P ; , +
518 String phoneNumberPattern(L"[^0-9*#P,p+;]");
519 RegularExpression checkPhoneNumber;
520 checkPhoneNumber.Construct(phoneNumberPattern);
521 //If there is any character other than these listed above then display invalid number
522 bool resultMatch = checkPhoneNumber.Match(phoneNumber,false);
523 //return false for patterns other than 0-9 * # P ; , +
524 if(resultMatch == true)
526 //return phone number is invalid
535 CallApp::SetTopMostWindow(bool bTopMost)
537 AppLogDebug("bTopMost = %d",bTopMost);
538 result res = E_FAILURE;
539 //ToDO: Need to see if there is better way to handle
544 GetAppFrame()->GetFrame()->SetZOrderGroup(WINDOW_Z_ORDER_GROUP_HIGHEST);
545 AppManager::GetInstance()->AddActiveAppEventListener(*this);
546 if(PowerManager::IsScreenOn() == false)
548 AppLogDebug("TurnScreenOn");
549 res = PowerManager::TurnScreenOn();
550 AppLogDebug("TurnScreenOn %d",res);
556 GetAppFrame()->GetFrame()->SetZOrderGroup(WINDOW_Z_ORDER_GROUP_NORMAL);
557 PowerManager::KeepScreenOnState(false);
558 AppManager::GetInstance()->RemoveActiveAppEventListener(*this);
561 if(LockManager::GetInstance()->IsLocked())
563 AppLogDebug("Phone Locked");
564 LockManager::GetInstance()->Unlock();
569 CallApp::OnActiveAppChanged(const String& appId)
571 AppLogDebug("Enter %ls",appId.GetPointer());
572 if(GetAppId().Equals(appId) == true)
574 result res = PowerManager::KeepScreenOnState(true,false);
575 AppLogDebug("KeepScreenOnState %d",res);