bc7006fc70342db5ae71ab48f6abc7ff40fb9c7e
[apps/osp/Call.git] / src / CallSoundManager.cpp
1 //
2 // Copyright (c) 2012 Samsung Electronics Co., Ltd.
3 //
4 // Licensed under the Flora License, Version 1.1 (the License);
5 // you may not use this file except in compliance with the License.
6 // You may obtain a copy of the License at
7 //
8 //     http://floralicense.org/license/
9 //
10 // Unless required by applicable law or agreed to in writing, software
11 // distributed under the License is distributed on an AS IS BASIS,
12 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 // See the License for the specific language governing permissions and
14 // limitations under the License.
15 //
16
17 /**
18  * @file    CallSettingsMoreOptionsForm.cpp
19  * @brief   Sound manager class
20  */
21 #include "CallSoundManager.h"
22
23 using namespace Tizen::Base;
24 using namespace Tizen::Graphics;
25 using namespace Tizen::Io;
26 using namespace Tizen::Media;
27 using namespace Tizen::Social;
28 using namespace Tizen::System;
29 using namespace Tizen::Base::Collection;
30 using namespace Tizen::Base::Runtime;
31
32 static const wchar_t* RINGTONE_PATH = L"/opt/usr/apps/zktdpemtmw/shared/data/ringtone_sdk.mp3";
33 static const wchar_t* CALLCONNECTTONE_PATH = L"/opt/usr/apps/zktdpemtmw/shared/data/Call_Connect.ogg";
34 static const wchar_t* CALLDISCONNECTTONE_PATH = L"/opt/usr/apps/zktdpemtmw/shared/data/Call_Disconnect.ogg";
35 static const wchar_t* MINUTEREMINDERTONE_PATH = L"/opt/usr/apps/zktdpemtmw/shared/data/Call_RecordStart.wav";
36 static const wchar_t* CALLWAITINGTONE_PATH = L"/opt/usr/apps/zktdpemtmw/shared/data/Call_WaitingTone.wav";
37
38
39 SoundManager::SoundManager(void)
40         : __pSoundCallSession(null)
41         , __pVibrator(null)
42         , __pPlayer(null)
43         , __lastEndedConferenceCall(false)
44         , __pConnectPlayer(null)
45         , __pDisconnectPlayer(null)
46         , __pReminderPlayer(null)
47         , __pWaitingTonePlayer(null)
48 {
49         __timer.Construct(*this);
50         __isSoundStatusOn = false;
51         __isVibrateStatusOn = false;
52 }
53
54 SoundManager::~SoundManager(void)
55 {
56         if(__pSoundCallSession != null)
57         {
58                 sound_manager_call_session_destroy(__pSoundCallSession);
59         }
60         if (__pVibrator != null)
61         {
62                 delete __pVibrator;
63                 __pVibrator = null;
64         }
65         if (__pPlayer != null)
66         {
67                 delete __pPlayer;
68                 __pPlayer = null;
69         }
70         if(__pConnectPlayer != null)
71         {
72                 delete __pConnectPlayer;
73                 __pConnectPlayer = null;
74         }
75         if(__pDisconnectPlayer != null)
76         {
77                 delete __pDisconnectPlayer;
78                 __pDisconnectPlayer = null;
79         }
80         if(__pReminderPlayer != null)
81         {
82                 delete __pReminderPlayer;
83                 __pReminderPlayer = null;
84         }
85         if(__pWaitingTonePlayer != null)
86         {
87                 delete __pWaitingTonePlayer;
88                 __pWaitingTonePlayer = null;
89         }
90
91 }
92
93 void
94 SoundManager::SetlastEndedConferenceCall()
95 {
96         __lastEndedConferenceCall = true;
97 }
98
99 bool
100 SoundManager::GetLastConferenceCall()
101 {
102         return __lastEndedConferenceCall;
103 }
104
105 Timer*
106 SoundManager::GetTimer()
107 {
108         return &__timer;
109 }
110
111 result
112 SoundManager::StopSession(void)
113 {
114         AppLogDebug("Enter");
115         if(__pSoundCallSession != null)
116         {
117                 AppLogDebug("sound_manager_call_session_destroy");
118                 sound_manager_call_session_destroy(__pSoundCallSession);
119                 __pSoundCallSession = null;
120         }
121
122         return E_SUCCESS;
123 }
124
125 result
126 SoundManager::StartSession(void)
127 {
128         AppLogDebug("Enter");
129         if (__pSoundCallSession != null)
130         {
131                 sound_manager_call_session_set_mode(__pSoundCallSession,(sound_call_session_mode_e)SOUND_CALL_SESSION_MODE_VOICE);
132                 sound_manager_set_active_route((sound_route_e)SOUND_ROUTE_IN_MIC_OUT_RECEIVER);
133                 sound_manager_set_volume((sound_type_e)SOUND_TYPE_CALL,5);
134                 return E_SUCCESS;
135         }
136         int res = sound_manager_call_session_create((sound_call_session_type_e)SOUND_SESSION_TYPE_CALL, &__pSoundCallSession);
137         if (res != SOUND_MANAGER_ERROR_NONE)
138         {
139                 AppLogDebug("Sound manager creation failed");
140                 return E_FAILURE;
141         }
142         res = sound_manager_call_session_set_mode(__pSoundCallSession,(sound_call_session_mode_e)SOUND_CALL_SESSION_MODE_VOICE);
143         sound_manager_set_active_route((sound_route_e)SOUND_ROUTE_IN_MIC_OUT_RECEIVER);
144         //todo start listening for volume key and set the volume
145         sound_manager_set_volume((sound_type_e)SOUND_TYPE_CALL,5);
146         return E_SUCCESS;
147 }
148
149 result
150 SoundManager::SetSpeakerStatus(bool setSpeaker)
151 {
152         result r = E_FAILURE;
153         int res = -1;
154         bool isEarJackPresent = IsEarJackConnected();
155         sound_route_e soundRoute;
156         if (setSpeaker == true)
157         {
158                 soundRoute = SOUND_ROUTE_IN_MIC_OUT_SPEAKER;
159         }
160         else
161         {
162                 if (isEarJackPresent == true)
163                 {
164                         soundRoute = SOUND_ROUTE_IN_MIC_OUT_HEADPHONE;
165                 }
166                 else
167                 {
168                         soundRoute = SOUND_ROUTE_IN_MIC_OUT_RECEIVER;
169                 }
170         }
171         res = sound_manager_set_active_route(soundRoute);
172         if (res == SOUND_MANAGER_ERROR_NONE)
173         {
174                 r = E_SUCCESS;
175         }
176         else
177         {
178                 r = E_FAILURE;
179         }
180         return r;
181 }
182
183 result
184 SoundManager::SetSoundMode(SoundMode soundMode)
185 {
186         if (__pSoundCallSession == null)
187         {
188                 return E_FAILURE;
189         }
190         sound_call_session_mode_e sessionMode;
191         switch (soundMode)
192         {
193         case SOUND_MODE_RINGTONE:
194         {
195                 sessionMode = SOUND_CALL_SESSION_MODE_RINGTONE;
196                 break;
197         }
198         case SOUND_MODE_MEDIA:
199         {
200                 sessionMode = SOUND_CALL_SESSION_MODE_MEDIA;
201                 break;
202         }
203         case SOUND_MODE_VOICE:
204         {
205                 sessionMode = SOUND_CALL_SESSION_MODE_VOICE;
206         }
207         break;
208         default:
209         {
210                 sessionMode = SOUND_CALL_SESSION_MODE_RINGTONE;
211                 break;
212         }
213         }
214         int res = sound_manager_call_session_set_mode(__pSoundCallSession,sessionMode);
215         if (res != SOUND_MANAGER_ERROR_NONE)
216         {
217                 return E_FAILURE;
218         }
219         return E_SUCCESS;
220 }
221
222 void
223 SoundManager::OnTimerExpired(Timer& timer)
224 {
225         AppLogDebug("Enter");
226         String reminderTonePath;
227         int unknownRejectStatus = -1;
228         vconf_get_bool(VCONFKEY_CISSAPPL_MINUTE_MINDER_BOOL, &unknownRejectStatus);
229         bool ReminderToneSetStatus = unknownRejectStatus;
230         result res = E_FAILURE;
231         reminderTonePath.Append(MINUTEREMINDERTONE_PATH);
232
233         if(ReminderToneSetStatus == true)
234         {
235
236                 if(__pReminderPlayer == null)
237                 {
238
239                         if(reminderTonePath.IsEmpty() == false)
240                         {
241                                 __pReminderPlayer =  new (std::nothrow) Player();
242                                 res = __pReminderPlayer->Construct(*this);
243                                 if(res != E_SUCCESS)
244                                 {
245                                         AppLogDebug("__pReminderPlayer Construct failed with %d",res);
246                                         delete __pReminderPlayer;
247                                         __pReminderPlayer = null;
248                                         return;
249                                 }
250                                 res = __pReminderPlayer->OpenFile(reminderTonePath,false);
251                                 if(res != E_SUCCESS)
252                                 {
253                                         AppLogDebug("__pReminderPlayer OpenFile failed with %d",res);
254                                         delete __pReminderPlayer;
255                                         __pReminderPlayer = null;
256                                         return;
257                                 }
258                                 res = __pReminderPlayer->SetLooping(false);
259                                 if(res != E_SUCCESS)
260                                 {
261                                         AppLogDebug("__pReminderPlayer SetLooping failed with %d",res);
262                                         delete __pReminderPlayer;
263                                         __pReminderPlayer = null;
264                                         return;
265                                 }
266                                 res = __pReminderPlayer->SetVolume(80);
267                                 if(res != E_SUCCESS)
268                                 {
269                                         AppLogDebug("__pReminderPlayer SetVolume failed with %d",res);
270                                         delete __pReminderPlayer;
271                                         __pReminderPlayer = null;
272                                         return;
273                                 }
274                         }
275                 }
276
277                 if(__pReminderPlayer != null)
278                 {
279                         SetSoundMode(SOUND_MODE_MEDIA);
280                         res = __pReminderPlayer->Play();
281                         if(res != E_SUCCESS)
282                         {
283                                 AppLogDebug("__pReminderPlayer Play failed with %d",res);
284                                 return;
285                         }
286                         SetSoundMode(SOUND_MODE_VOICE);
287                 }
288         }
289         /*else if(ReminderToneSetStatus == false)
290         {
291                 timer.Cancel();
292         }*/
293
294 }
295
296
297
298 void
299 SoundManager::SetDisconnectTone(void)
300 {
301
302         AppLogDebug("Enter");
303         int unknownRejectStatus = -1;
304         String disconnectTonePath=L"";
305         vconf_get_bool(VCONFKEY_CISSAPPL_CALL_END_TONE_BOOL, &unknownRejectStatus);
306         bool disconnectToneSetStatus = unknownRejectStatus;
307         result res = E_FAILURE;
308
309         if(disconnectToneSetStatus == true)
310         {
311                 AppLogDebug("disconnectToneSetStatus == true");
312                 disconnectTonePath.Append(CALLDISCONNECTTONE_PATH);
313                 if(disconnectTonePath.IsEmpty() == false)
314                 {
315                         if(__pDisconnectPlayer == null)
316                         {
317                                 AppLogDebug("__pConnectPlayer == null");
318                                 __pDisconnectPlayer =  new (std::nothrow) Player();
319                                 res = __pDisconnectPlayer->Construct(*this);
320                                 if(res != E_SUCCESS)
321                                 {
322                                         AppLogDebug("__pDisconnectPlayer Construct failed with %d",res);
323                                         delete __pDisconnectPlayer;
324                                         __pDisconnectPlayer = null;
325                                         return;
326                                 }
327                                 res = __pDisconnectPlayer->OpenFile(disconnectTonePath,false);
328                                 if(res != E_SUCCESS)
329                                 {
330                                         AppLogDebug("__pDisconnectPlayer OpenFile failed with %d",res);
331                                         delete __pDisconnectPlayer;
332                                         __pDisconnectPlayer = null;
333                                         return;
334                                 }
335                                 res = __pDisconnectPlayer->SetLooping(false);
336                                 if(res != E_SUCCESS)
337                                 {
338                                         AppLogDebug("__pDisconnectPlayer SetLooping failed with %d",res);
339                                         delete __pDisconnectPlayer;
340                                         __pDisconnectPlayer = null;
341                                         return;
342                                 }
343                                 res = __pDisconnectPlayer->SetVolume(80);
344                                 if(res != E_SUCCESS)
345                                 {
346                                         AppLogDebug("__pDisconnectPlayer SetLooping SetVolume with %d",res);
347                                         delete __pDisconnectPlayer;
348                                         __pDisconnectPlayer = null;
349                                         return;
350                                 }
351
352                         }
353                 }
354
355                 if(__pDisconnectPlayer != null)
356                 {
357                         AppLogDebug("__pDisconnectPlayer OpenFile %ls",disconnectTonePath.GetPointer());
358                         SetSoundMode(SOUND_MODE_MEDIA);
359                         AppLogDebug("__pDisconnectPlayer SetVolume");
360                         if(__pDisconnectPlayer->GetState() == PLAYER_STATE_PLAYING)
361                         {
362                                 __pDisconnectPlayer->Stop();
363                         }
364                         res = __pDisconnectPlayer->Play();
365                         if(res != E_SUCCESS)
366                         {
367                                 AppLogDebug("__pDisconnectPlayer Play with %d",res);
368                                 return;
369                         }
370                 }
371
372         }
373
374
375
376
377         AppLogDebug("Exit");
378
379 }
380
381 void
382 SoundManager::SetMinuteReminderTone(void)
383 {
384         __timer.StartAsRepeatable(60000);
385 }
386
387
388 void
389 SoundManager::SetConnectTone(void)
390 {
391
392         String connectTonePath;
393         int unknownRejectStatus = -1;
394         vconf_get_bool(VCONFKEY_CISSAPPL_CALL_CONNECT_TONE_BOOL, &unknownRejectStatus);
395         bool connectToneSetStatus = unknownRejectStatus;
396         result res = E_FAILURE;
397
398         connectTonePath.Append(CALLCONNECTTONE_PATH);
399
400         if(connectToneSetStatus == true)
401         {
402
403                 if(__pConnectPlayer == null)
404                 {
405                         if (connectTonePath.IsEmpty() == false)
406                         {
407                                 __pConnectPlayer =  new (std::nothrow) Player();
408                                 res = __pConnectPlayer->Construct(*this);
409                                 if(res != E_SUCCESS)
410                                 {
411                                         AppLogDebug("__pConnectPlayer Construct failed with %d",res);
412                                         delete __pConnectPlayer;
413                                         __pConnectPlayer = null;
414                                         return;
415                                 }
416                                 res = __pConnectPlayer->OpenFile(connectTonePath,false);
417                                 if(res != E_SUCCESS)
418                                 {
419                                         AppLogDebug("__pConnectPlayer OpenFile failed with %d",res);
420                                         delete __pConnectPlayer;
421                                         __pConnectPlayer = null;
422                                         return;
423                                 }
424                                 res = __pConnectPlayer->SetLooping(false);
425                                 if(res != E_SUCCESS)
426                                 {
427                                         AppLogDebug("__pConnectPlayer SetLooping failed with %d",res);
428                                         delete __pConnectPlayer;
429                                         __pConnectPlayer = null;
430                                         return;
431                                 }
432                                 res = __pConnectPlayer->SetVolume(80);
433                                 if(res != E_SUCCESS)
434                                 {
435                                         AppLogDebug("__pConnectPlayer SetVolume failed with %d",res);
436                                         delete __pConnectPlayer;
437                                         __pConnectPlayer = null;
438                                         return;
439                                 }
440                         }
441                 }
442
443                 if(__pConnectPlayer != null)
444                 {
445                         res = SetSoundMode(SOUND_MODE_MEDIA);
446                         AppLogDebug("__pConnectPlayer Playing connect tone");
447                         res = __pConnectPlayer->Play();
448                         if(res != E_SUCCESS)
449                         {
450                                 AppLogDebug("__pConnectPlayer Play failed with %d",res);
451                                 return;
452                         }
453                 }
454
455         }
456
457
458 }
459
460 void
461 SoundManager::SetWaitTone(void)
462 {
463         CallAlertStatus status= CALL_ALERT_SOUND;
464         int alertStatus = -1;
465         result res = E_FAILURE;
466         int retVal = vconf_get_int(VCONFKEY_CISSAPPL_ALERT_ON_CALL_INT, &alertStatus);
467         if (retVal == 0)
468         {
469                 status = (CallAlertStatus) alertStatus;
470         }
471         AppLogDebug("No Alert already in call");
472         if(status == CALL_ALERT_SOUND)
473         {
474                 AppLogDebug("Playing alert tone");
475                 String waitingTonePath;
476                 waitingTonePath.Append(CALLWAITINGTONE_PATH);
477                 if(__pWaitingTonePlayer == null)
478                 {
479                         if (waitingTonePath.IsEmpty() == false)
480                         {
481                                 __pWaitingTonePlayer =  new (std::nothrow) Player();
482                                 res = __pWaitingTonePlayer->Construct(*this);
483                                 if(res != E_SUCCESS)
484                                 {
485                                         AppLogDebug("__pWaitingTonePlayer Construct failed with %d",res);
486                                         delete __pWaitingTonePlayer;
487                                         __pWaitingTonePlayer = null;
488                                         return;
489                                 }
490                                 res = __pWaitingTonePlayer->OpenFile(waitingTonePath,false);
491                                 if(res != E_SUCCESS)
492                                 {
493                                         AppLogDebug("__pWaitingTonePlayer OpenFile failed with %d",res);
494                                         delete __pWaitingTonePlayer;
495                                         __pWaitingTonePlayer = null;
496
497                                         return;
498                                 }
499                                 res = __pWaitingTonePlayer->SetLooping(true);
500                                 if(res != E_SUCCESS)
501                                 {
502                                         AppLogDebug("__pWaitingTonePlayer SetLooping failed with %d",res);
503                                         delete __pWaitingTonePlayer;
504                                         __pWaitingTonePlayer = null;
505
506                                         return;
507                                 }
508                                 res = __pWaitingTonePlayer->SetVolume(80);
509                                 if(res != E_SUCCESS)
510                                 {
511                                         AppLogDebug("__pWaitingTonePlayer SetVolume failed with %d",res);
512                                         delete __pWaitingTonePlayer;
513                                         __pWaitingTonePlayer = null;
514
515                                         return;
516                                 }
517                         }
518                 }
519
520                 if( __pWaitingTonePlayer != null )
521                 {
522                         SetSoundMode(SOUND_MODE_MEDIA);
523                         res = __pWaitingTonePlayer->Play();
524                         if(res != E_SUCCESS)
525                         {
526                                 AppLogDebug("__pWaitingTonePlayer Play failed with %d",res);
527                                 return;
528                         }
529                 }
530
531         }
532 }
533
534 void
535 SoundManager::StartAlert(String& contactRingTone)
536 {
537         result res = E_FAILURE;
538         IntensityDurationVibrationPattern vibration;
539         vibration.duration = 3000;
540         vibration.intensity = -1;
541         AppLogDebug("Enter");
542         if(__pSoundCallSession != null)
543         {
544                 SetWaitTone();
545                 return;
546         }
547         else
548         {
549                 StartSession();
550         }
551         if(__pVibrator == null)
552         {
553                 __pVibrator = new (std::nothrow) Vibrator();
554                 res = __pVibrator->Construct();
555                 if(res != E_SUCCESS)
556                 {
557                         AppLogDebug("__pVibrator Construct failed with %d",res);
558                         return;
559                 }
560         }
561         if(__pPlayer == null)
562         {
563                 __pPlayer =  new (std::nothrow) Player();
564                 res = __pPlayer->Construct(*this);
565                 if(res != E_SUCCESS)
566                 {
567                         AppLogDebug("__pPlayer Construct failed with %d",res);
568                         delete __pPlayer;
569                         __pPlayer = null;
570                         return;
571                 }
572         }
573         int retVal = -1;
574         vconf_get_bool(VCONFKEY_SETAPPL_SOUND_STATUS_BOOL, &retVal);
575         __isSoundStatusOn = retVal;
576         vconf_get_bool(VCONFKEY_SETAPPL_VIBRATION_STATUS_BOOL, &retVal);
577         __isVibrateStatusOn = retVal;
578         //todo: do only if call alert mode is set
579         if (__isSoundStatusOn == true)
580         {
581                 String ringTonePath;
582                 //Check if contact has any custom ringtone, else play defautl ringtone.
583                 if(contactRingTone.IsEmpty() == true)
584                 {
585                         char* pRingTonePtr = vconf_get_str(VCONFKEY_SETAPPL_CALL_RINGTONE_PATH_STR);
586                         AppLog("Ringtone Path : %s",pRingTonePtr);
587                         ringTonePath.Append(pRingTonePtr);
588                 }
589                 else
590                 {
591                         AppLog("Ringtone Path : %ls",contactRingTone.GetPointer());
592                         ringTonePath.Append(contactRingTone);
593                 }
594
595                 //Check if file is present
596                 File file;
597                 res = file.Construct(ringTonePath, "r");
598                 if(res != E_SUCCESS )
599                 {
600                         ringTonePath.Clear();
601                         ringTonePath.Append(RINGTONE_PATH);
602                 }
603
604                 res = __pPlayer->OpenFile(ringTonePath,false);
605                 if(res != E_SUCCESS)
606                 {
607                         AppLogDebug("__pPlayer Construct failed with %d",res);
608                         return;
609                 }
610                 res = __pPlayer->SetLooping(true);
611                 if(res != E_SUCCESS)
612                 {
613                         AppLogDebug("__pPlayer Construct failed with %d",res);
614                         return;
615                 }
616                 res = __pPlayer->SetVolume(80);
617                 if(res != E_SUCCESS)
618                 {
619                         AppLogDebug("__pPlayer Construct failed with %d",res);
620                         return;
621                 }
622                 res = SetSoundMode(SOUND_MODE_RINGTONE);
623                 res = __pPlayer->Play();
624                 if(res != E_SUCCESS)
625                 {
626                         AppLogDebug("__pPlayer Construct failed with %d",res);
627                         return;
628                 }
629         }
630         if (__isVibrateStatusOn == true)
631         {
632                 //todo: Get the level from settings
633                 __pVibrator->Start(&vibration, 1, 1000);
634         }
635         AppLogDebug("Exit");
636         return;
637 }
638
639 void
640 SoundManager::StopAlert(void)
641 {
642         result res = E_FAILURE;
643         AppLogDebug("Enter");
644         if (__isSoundStatusOn == true)
645         {
646                 //todo: stop player
647                 if(__pPlayer != null)
648                 {
649                         AppLogDebug("Stopping ring tone");
650                         if(__pPlayer->GetState() == PLAYER_STATE_PLAYING)
651                         {
652                                 res = __pPlayer->Stop();
653                         }
654                         if(res != E_SUCCESS)
655                         {
656                                 AppLogDebug("__pPlayer Stop failed with %d",res);
657                                 return;
658                         }
659                         res = __pPlayer->Close();
660                         if(res != E_SUCCESS)
661                         {
662                                 AppLogDebug("__pPlayer Close failed with %d",res);
663                                 return;
664                         }
665                         SetSoundMode(SOUND_MODE_VOICE);
666                         __isSoundStatusOn = false;
667                         StopSession();
668                 }
669         }
670         if (__isVibrateStatusOn == true)
671         {
672                 __pVibrator->Stop();
673                 __isVibrateStatusOn = false;
674         }
675         if(__pWaitingTonePlayer != null)
676         {
677                 if(__pWaitingTonePlayer->GetState() == PLAYER_STATE_PLAYING)
678                 {
679                         __pWaitingTonePlayer->Stop();
680                 }
681         }
682
683         AppLogDebug("Exit");
684 }
685
686 void
687 SoundManager::OnPlayerOpened(result r)
688 {
689 }
690
691 void
692 SoundManager::OnPlayerEndOfClip(void)
693 {
694 }
695
696 void
697 SoundManager::OnPlayerSeekCompleted(result r)
698 {
699 }
700
701 void
702 SoundManager::OnPlayerBuffering(int percent)
703 {
704 }
705
706 void
707 SoundManager::OnPlayerErrorOccurred(Tizen::Media::PlayerErrorReason r)
708 {
709 }
710
711 void
712 SoundManager::OnPlayerInterrupted(void)
713 {
714 }
715
716 void
717 SoundManager::OnPlayerReleased(void)
718 {
719 }
720
721 bool
722 SoundManager::IsEarJackConnected(void)
723 {
724         int earJackStatus = -1;
725         if (vconf_get_int(VCONFKEY_SYSMAN_EARJACK, &earJackStatus) == 0)
726         {
727                 if (earJackStatus == VCONFKEY_SYSMAN_EARJACK_REMOVED)
728                 {
729                         return false;
730                 }
731                 else
732                 {
733                         return true;
734                 }
735         }
736         else
737         {
738                 return false;
739         }
740 }