|
1 /* |
|
2 * Copyright (c) 2008 Nokia Corporation and/or its subsidiary(-ies). |
|
3 * All rights reserved. |
|
4 * This component and the accompanying materials are made available |
|
5 * under the terms of "Eclipse Public License v1.0" |
|
6 * which accompanies this distribution, and is available |
|
7 * at the URL "http://www.eclipse.org/legal/epl-v10.html". |
|
8 * |
|
9 * Initial Contributors: |
|
10 * Nokia Corporation - initial contribution. |
|
11 * |
|
12 * Contributors: |
|
13 * |
|
14 * Description: Video Telephony mediator plugin header |
|
15 * |
|
16 */ |
|
17 |
|
18 |
|
19 // INCLUDE FILES |
|
20 #include <e32def.h> |
|
21 #include <w32std.h> |
|
22 #include <apacmdln.h> |
|
23 #include <apaflrec.h> |
|
24 #include <apgcli.h> |
|
25 #include <mediatordomainuids.h> |
|
26 #include <eikdll.h> |
|
27 #include <apgcli.h> |
|
28 #include <apgwgnam.h> |
|
29 #include <apgtask.h> |
|
30 #include <mediatorcommandstotelephonyapi.h> |
|
31 #include <videotelcontrolmediatorapi.h> |
|
32 #include <videoteltophonecommandsapi.h> |
|
33 #include "cvtmediatorplugin.h" |
|
34 |
|
35 |
|
36 // CONSTANTS |
|
37 #ifdef _DEBUG |
|
38 #define TRACE(x) RDebug::Print( _L(x) ); |
|
39 #define TRACE2(x,y) RDebug::Print( _L(x),y ); |
|
40 #else |
|
41 #define TRACE(x) |
|
42 #define TRACE2(x,y) |
|
43 #endif |
|
44 |
|
45 // This array's values are used in algorithm defining if video telephone |
|
46 // application should be started. Previous state value is substracted from new |
|
47 // state value and if result is greater than zero, app is started. |
|
48 // This tackles transitions where a state is for some reason skipped, |
|
49 // e.g. idle -> connected (dialling/ringing/answering states were not detected). |
|
50 // Negative value indicates call clearing. |
|
51 static const TInt KVtCallStateActionArray[] = { |
|
52 0, //ECallStateUnknown |
|
53 0, //ECallStateIdle |
|
54 1, // ECallStateDialling |
|
55 0, // ECallStateEmergencyDialling (not valid video call state) |
|
56 1, // ECallStateRinging |
|
57 1, // ECallStateConnecting |
|
58 1, // ECallStateConnected |
|
59 0, // ECallStateHangingUp |
|
60 0, // ECallStateHeld (not valid video call state) |
|
61 1, // ECallStateAnswering |
|
62 0, // ECallStateRejecting |
|
63 0 // ECallStateDisconnecting |
|
64 }; |
|
65 |
|
66 static const TInt KVtAppNotReady = 5000; |
|
67 |
|
68 static const TInt KVtEngMdtrCmdTimeout = 500000; |
|
69 |
|
70 static const TInt KVtInitCallId = -1000; |
|
71 |
|
72 // array granularity is 2 (use dataport, release dataport commands) |
|
73 static const TInt KVtMdtrCmdArrayGranularity = 2; |
|
74 |
|
75 const TUid KVtCmVideoTelUiUid = { 0x101F8681 }; |
|
76 |
|
77 static const TInt KRamNeededForVideoCalls = 4000000; |
|
78 |
|
79 // VT application path |
|
80 _LIT( KVtCmVideoTelUiPath, "\\sys\\bin\\videotelui.exe" ); |
|
81 |
|
82 |
|
83 // ----------------------------------------------------------------------------- |
|
84 // CMediatorTestPlugin::CMediatorTestPlugin |
|
85 // First phase construction. |
|
86 // ----------------------------------------------------------------------------- |
|
87 CVtMediatorPlugin::CVtMediatorPlugin() : CMediatorPluginBase(), |
|
88 iCommandList( KVtMdtrCmdArrayGranularity ), |
|
89 iState( EWaitingAppLaunch ), |
|
90 iActiveVideoCallState( ECallStateUnknown ), |
|
91 iWaitingVideoCallState( ECallStateUnknown ) |
|
92 |
|
93 { |
|
94 ClearData(iActiveVideoCallInfo, iActiveVideoCallState); |
|
95 ClearData(iWaitingVideoCallInfo, iWaitingVideoCallState); |
|
96 } |
|
97 |
|
98 CMediatorPluginBase* CVtMediatorPlugin::NewL() |
|
99 { |
|
100 TRACE("CVtMediatorPlugin::NewL<") |
|
101 CVtMediatorPlugin* self = new (ELeave) CVtMediatorPlugin; |
|
102 TRACE("CVtMediatorPlugin::NewL>") |
|
103 return self; |
|
104 } |
|
105 |
|
106 // ----------------------------------------------------------------------------- |
|
107 // Destructor. |
|
108 // ----------------------------------------------------------------------------- |
|
109 CVtMediatorPlugin::~CVtMediatorPlugin() |
|
110 { |
|
111 TRACE("CVtMediatorPlugin::~CVtMediatorPlugin<") |
|
112 |
|
113 if ( iMediatorNotifications ) |
|
114 { |
|
115 iMediatorNotifications->UnregisterNotificationObserver(); |
|
116 delete iMediatorNotifications; |
|
117 } |
|
118 |
|
119 // ignore error |
|
120 if ( iEventConsumer ) |
|
121 { |
|
122 iEventConsumer->UnsubscribeEvent( |
|
123 KMediatorTelephonyDomain, |
|
124 KCatEventsFromTelephony, |
|
125 EPhoneEventCallData ); |
|
126 delete iEventConsumer; |
|
127 } |
|
128 |
|
129 // ignore error |
|
130 if ( iEventProvider ) |
|
131 { |
|
132 iEventProvider->UnregisterEvent( |
|
133 KMediatorVideoTelephonyDomain, |
|
134 KCatVideotelInternalEvents, |
|
135 EVtMediatorEventVideoCallInformation ); |
|
136 delete iEventProvider; |
|
137 } |
|
138 |
|
139 // ignore error |
|
140 if ( iCommandResponder ) |
|
141 { |
|
142 iCommandResponder->UnregisterCommand( |
|
143 KMediatorVideoTelephonyDomain, |
|
144 KCatPhoneToVideotelCommands, |
|
145 iCommandList ); |
|
146 iCommandList.Close(); |
|
147 delete iCommandResponder; |
|
148 } |
|
149 |
|
150 delete iCommandInitiator; |
|
151 |
|
152 |
|
153 if( iAppDeathActive ) |
|
154 { |
|
155 delete iAppDeathActive; |
|
156 iAppThread.Close(); |
|
157 iWsSession.Close(); |
|
158 |
|
159 } |
|
160 |
|
161 TRACE("CVtMediatorPlugin::~CVtMediatorPlugin>") |
|
162 } |
|
163 |
|
164 // ----------------------------------------------------------------------------- |
|
165 // StartL. |
|
166 // ----------------------------------------------------------------------------- |
|
167 void CVtMediatorPlugin::StartL() |
|
168 { |
|
169 TRACE("CVtMediatorPlugin.StartL<") |
|
170 |
|
171 // for monitoring VT app starting |
|
172 iMediatorNotifications = CMediatorNotifications::NewL(); |
|
173 iMediatorNotifications->RegisterNotificationObserver( this ); |
|
174 |
|
175 // consumer for call data events |
|
176 iEventConsumer = CMediatorEventConsumer::NewL( this ); |
|
177 |
|
178 iCommandInitiator = CMediatorCommandInitiator::NewL( this ); |
|
179 |
|
180 |
|
181 RegisterVtInternalEventL(); |
|
182 |
|
183 RegisterDataportCommandL(); |
|
184 |
|
185 TRACE("CVtMediatorPlugin.StartL>") |
|
186 } |
|
187 |
|
188 // ----------------------------------------------------------------------------- |
|
189 // MediatorEventL. |
|
190 // ----------------------------------------------------------------------------- |
|
191 void CVtMediatorPlugin::MediatorEventL( TUid /*aDomain*/, |
|
192 TUid aCategory, |
|
193 TInt aEventId, |
|
194 const TDesC8& aData ) |
|
195 { |
|
196 TRACE("CVtMediatorPlugin.MediatorEventL<") |
|
197 if ( aCategory == KCatEventsFromTelephony && |
|
198 aEventId == EPhoneEventCallData ) |
|
199 { |
|
200 TTelephonyCallDataParamPackage pckg; |
|
201 pckg.Copy( aData ); |
|
202 const TTelephonyCallDataParam telCallData = pckg(); |
|
203 HandleCallStateChangeL( telCallData ); |
|
204 } |
|
205 TRACE("CVtMediatorPlugin.MediatorEventL>") |
|
206 } |
|
207 // ----------------------------------------------------------------------------- |
|
208 // CVtMediatorPlugin::MediatorEventsAddedL |
|
209 // |
|
210 // subscribes to CLI event when it is registered |
|
211 // ----------------------------------------------------------------------------- |
|
212 // |
|
213 void CVtMediatorPlugin::MediatorEventsAddedL( TUid aDomain/*aDomain*/, |
|
214 TUid aCategory, |
|
215 const REventList& aEvents ) |
|
216 { |
|
217 TRACE("CVtMediatorPlugin.MediatorEventsAddedL<") |
|
218 |
|
219 if ( aCategory == KCatEventsFromTelephony ) |
|
220 { |
|
221 ChangeCallDataEventSubscriptionL( aEvents, ETrue ); |
|
222 } |
|
223 TRACE("CVtMediatorPlugin.MediatorEventsAddedL>") |
|
224 } |
|
225 |
|
226 // ----------------------------------------------------------------------------- |
|
227 // ?classname::?member_function |
|
228 // |
|
229 // (other items were commented in a header). |
|
230 // ----------------------------------------------------------------------------- |
|
231 // |
|
232 void CVtMediatorPlugin::MediatorCommandsAddedL( TUid /*aDomain*/, |
|
233 TUid aCategory, |
|
234 const RCommandList& /*aCommands*/ ) |
|
235 { |
|
236 TRACE("CVtMediatorPlugin.MediatorCommandsAddedL<") |
|
237 if ( aCategory == KCatPhoneToVideotelCommands ) |
|
238 { |
|
239 HandleVtCommandRegistrationL(); |
|
240 } |
|
241 TRACE("CVtMediatorPlugin.MediatorCommandsAddedL>") |
|
242 } |
|
243 |
|
244 // ----------------------------------------------------------------------------- |
|
245 // ?classname::?member_function |
|
246 // |
|
247 // (other items were commented in a header). |
|
248 // ----------------------------------------------------------------------------- |
|
249 // |
|
250 void CVtMediatorPlugin::MediatorCategoryRemovedL( TUid /*aDomain*/, |
|
251 TUid /*aCategory*/ ) |
|
252 { |
|
253 } |
|
254 |
|
255 // ----------------------------------------------------------------------------- |
|
256 // ?classname::?member_function |
|
257 // |
|
258 // (other items were commented in a header). |
|
259 // ----------------------------------------------------------------------------- |
|
260 // |
|
261 void CVtMediatorPlugin::MediatorEventsRemovedL( TUid /*aDomain*/, |
|
262 TUid aCategory, |
|
263 const REventList& aEvents ) |
|
264 { |
|
265 TRACE("CVtMediatorPlugin.MediatorEventsRemovedL<") |
|
266 if ( aCategory == KCatEventsFromTelephony ) |
|
267 { |
|
268 ChangeCallDataEventSubscriptionL( aEvents, EFalse ); |
|
269 } |
|
270 TRACE("CVtMediatorPlugin.MediatorEventsRemovedL>") |
|
271 } |
|
272 |
|
273 // ----------------------------------------------------------------------------- |
|
274 // ?classname::?member_function |
|
275 // |
|
276 // (other items were commented in a header). |
|
277 // ----------------------------------------------------------------------------- |
|
278 // |
|
279 void CVtMediatorPlugin::MediatorCommandsRemovedL( TUid /*aDomain*/, |
|
280 TUid aCategory, |
|
281 const RCommandList& /*aCommands*/ ) |
|
282 { |
|
283 TRACE("CVtMediatorPlugin.MediatorCommandsRemovedL<") |
|
284 if ( aCategory == KCatPhoneToVideotelCommands ) |
|
285 { |
|
286 // VT has unregistered commands, meaning it is shutting down |
|
287 HandleVtCommandUnregistrationL(); |
|
288 } |
|
289 TRACE("CVtMediatorPlugin.MediatorCommandsRemovedL>") |
|
290 } |
|
291 |
|
292 // ----------------------------------------------------------------------------- |
|
293 // CVtMediatorPlugin::MediatorCommandL |
|
294 // |
|
295 // |
|
296 // ----------------------------------------------------------------------------- |
|
297 // |
|
298 void CVtMediatorPlugin::MediatorCommandL( TUid aDomain, |
|
299 TUid aCategory, |
|
300 TInt aCommandId, |
|
301 TVersion /*aVersion*/, |
|
302 const TDesC8& aData ) |
|
303 { |
|
304 TRACE("CVtMediatorPlugin.MediatorCommandL<") |
|
305 if ( aCategory == KCatPhoneToVideotelCommands ) |
|
306 { |
|
307 if ( aCommandId == EVtCmdUseDataport ) |
|
308 { |
|
309 #ifdef _DEBUG |
|
310 // error in responding is ignored but printed on debug build |
|
311 const TInt err = |
|
312 #endif |
|
313 iCommandResponder->IssueResponse( |
|
314 aDomain, aCategory, aCommandId, KErrNone, KNullDesC8() ); |
|
315 TRACE2("CVtMediatorPlugin.MediatorCommandL EVtCmdUseDataport err=%d", err ) |
|
316 HandleDataportCommandL( aData ); |
|
317 } |
|
318 else if ( aCommandId == EVtCmdReleaseDataport ) |
|
319 { |
|
320 if ( EReady == iState ) |
|
321 { |
|
322 const TVersion version( |
|
323 KVideotelMdtrCommandsVersionMajor, |
|
324 KVideotelMdtrCommandsVersionMinor, |
|
325 KVideotelMdtrCommandsVersionBuild ); |
|
326 |
|
327 #ifdef _DEBUG |
|
328 // error in responding is ignored but printed on debug build |
|
329 const TInt err = |
|
330 #endif |
|
331 iCommandInitiator->IssueCommand( |
|
332 KMediatorVideoTelephonyDomain, |
|
333 KCatVideotelInternalCommands, |
|
334 EVtMediatorReleaseDataport, |
|
335 version, |
|
336 KNullDesC8() ); |
|
337 TRACE2("CVtMediatorPlugin.MediatorCommandL EVtCmdReleaseDataport, send to VT err=%d", err ) |
|
338 |
|
339 } |
|
340 else |
|
341 { |
|
342 #ifdef _DEBUG |
|
343 // error in responding is ignored but printed on debug build |
|
344 const TInt err = |
|
345 #endif |
|
346 iCommandResponder->IssueResponse( |
|
347 aDomain, |
|
348 aCategory, |
|
349 aCommandId, |
|
350 KErrNone, |
|
351 KNullDesC8() ); |
|
352 TRACE2("CVtMediatorPlugin.MediatorCommandL EVtCmdReleaseDataport, just Resp err=%d", err ) |
|
353 } |
|
354 |
|
355 } |
|
356 } |
|
357 TRACE("CVtMediatorPlugin.MediatorCommandL>") |
|
358 } |
|
359 |
|
360 // ----------------------------------------------------------------------------- |
|
361 // CVtMediatorPlugin::CommandResponseL |
|
362 // |
|
363 // |
|
364 // ----------------------------------------------------------------------------- |
|
365 // |
|
366 void CVtMediatorPlugin::CommandResponseL( TUid aDomain, TUid aCategory, |
|
367 TInt aCommandId, TInt /*aStatus*/, const TDesC8& /*aData*/ ) |
|
368 { |
|
369 TRACE("CVtMediatorPlugin.CommandResponseL<") |
|
370 if( ( aDomain == KMediatorVideoTelephonyDomain ) && |
|
371 ( aCategory == KCatVideotelInternalCommands ) ) |
|
372 { |
|
373 TInt res = |
|
374 iCommandResponder->IssueResponse( |
|
375 KMediatorVideoTelephonyDomain, |
|
376 KCatPhoneToVideotelCommands, |
|
377 EVtCmdReleaseDataport, |
|
378 KErrNone, |
|
379 KNullDesC8() ); |
|
380 TRACE2("CVtMediatorPlugin.CommandResponseL, IssueResponse res: %d", res ) |
|
381 User::LeaveIfError( res ); |
|
382 } |
|
383 TRACE("CVtMediatorPlugin.CommandResponseL>") |
|
384 } |
|
385 |
|
386 // ----------------------------------------------------------------------------- |
|
387 // CVtMediatorPlugin::CancelMediatorCommand |
|
388 // |
|
389 // no-op |
|
390 // ----------------------------------------------------------------------------- |
|
391 // |
|
392 void CVtMediatorPlugin::CancelMediatorCommand( TUid /*aDomain*/, |
|
393 TUid /*aCategory*/, |
|
394 TInt /*aCommandId*/ ) |
|
395 { |
|
396 } |
|
397 // ----------------------------------------------------------------------------- |
|
398 // CVtMediatorPlugin::ChangeCallDataEventSubscriptionL |
|
399 // |
|
400 // Takes care of 'call data' event subscription. |
|
401 // ----------------------------------------------------------------------------- |
|
402 // |
|
403 void CVtMediatorPlugin::ChangeCallDataEventSubscriptionL( |
|
404 const REventList& aEvents, |
|
405 const TBool aEventRegistered ) |
|
406 { |
|
407 TRACE("CVtMediatorPlugin.ChangeCLIEventSubscription<") |
|
408 |
|
409 TInt res( KErrNone ); |
|
410 TInt eventCount = aEvents.Count(); |
|
411 while ( eventCount-- ) |
|
412 { |
|
413 const TEvent& aEvent = aEvents[ eventCount ]; |
|
414 if ( aEvent.iEventId == EPhoneEventCallData ) |
|
415 { |
|
416 if ( aEventRegistered ) |
|
417 { |
|
418 // Phone has registered Call data event => subscribe it |
|
419 const TVersion version( |
|
420 KTelephonyEventsVersionMajor, |
|
421 KTelephonyEventsVersionMinor, |
|
422 KTelephonyEventsVersionBuild ); |
|
423 res = iEventConsumer->SubscribeEvent( |
|
424 KMediatorTelephonyDomain, |
|
425 KCatEventsFromTelephony, |
|
426 EPhoneEventCallData, version ); |
|
427 } |
|
428 else |
|
429 { |
|
430 // Phone has unregistered Call data event => unsubscribe it |
|
431 res = iEventConsumer->UnsubscribeEvent( |
|
432 KMediatorTelephonyDomain, |
|
433 KCatEventsFromTelephony, |
|
434 EPhoneEventCallData ); |
|
435 } |
|
436 TRACE2(" (un)subscribe result=%d", res ) |
|
437 eventCount = 0; // break loop |
|
438 } |
|
439 } |
|
440 |
|
441 TRACE2("CVtMediatorPlugin.ChangeCLIEventSubscription result=%d>", res ) |
|
442 User::LeaveIfError( res ); |
|
443 } |
|
444 |
|
445 // ----------------------------------------------------------------------------- |
|
446 // CVtMediatorPlugin::HandleVtCommandRegistrationL |
|
447 // |
|
448 // |
|
449 // ----------------------------------------------------------------------------- |
|
450 // |
|
451 void CVtMediatorPlugin::HandleVtCommandRegistrationL() |
|
452 { |
|
453 TRACE("CVtMediatorPlugin.HandleVtCommandRegistrationL<" ) |
|
454 if ( iState == EWaitingEventRegistration ) |
|
455 { |
|
456 // VT app registered commands => it can also receive events |
|
457 // NOTE: it is expected that VT application first subscribes |
|
458 // to internal events and only after that registers commands to |
|
459 // avoid timing problems. |
|
460 iState = EReady; |
|
461 delete iCallBack; |
|
462 iCallBack = NULL; |
|
463 TCallBack cb( &EventRaiserCallback, this ); |
|
464 iCallBack = new ( ELeave ) CAsyncCallBack( cb, |
|
465 CActive::EPriorityStandard ); |
|
466 TRACE("CVtMediatorPlugin enque async callback" ) |
|
467 iCallBack->CallBack(); |
|
468 } |
|
469 TRACE("CVtMediatorPlugin.HandleVtCommandRegistrationL>" ) |
|
470 } |
|
471 |
|
472 TInt CVtMediatorPlugin::EventRaiserCallback( TAny* aAny ) |
|
473 { |
|
474 TRACE("CVtMediatorPlugin.EventRaiserCallback<" ) |
|
475 CVtMediatorPlugin* plugin = reinterpret_cast<CVtMediatorPlugin*>( aAny ); |
|
476 delete plugin->iCallBack; |
|
477 plugin->iCallBack = NULL; |
|
478 TRAP_IGNORE( plugin->RaiseVtEventL() ); |
|
479 TRACE("CVtMediatorPlugin.EventRaiserCallback>" ) |
|
480 return KErrNone; |
|
481 } |
|
482 |
|
483 // ----------------------------------------------------------------------------- |
|
484 // CVtMediatorPlugin:: |
|
485 // |
|
486 // |
|
487 // ----------------------------------------------------------------------------- |
|
488 // |
|
489 void CVtMediatorPlugin::HandleVtCommandUnregistrationL() |
|
490 { |
|
491 // unregistration means that VT app is shutting down. |
|
492 TRACE("CVtMediatorPlugin.HandleVtCommandUnregistrationL<" ) |
|
493 ClearData(iActiveVideoCallInfo, iActiveVideoCallState); |
|
494 //ClearData(iWaitingVideoCallInfo); |
|
495 TRACE("CVtMediatorPlugin.HandleVtCommandUnregistrationL>" ) |
|
496 } |
|
497 |
|
498 |
|
499 // ----------------------------------------------------------------------------- |
|
500 // CVtMediatorPlugin:: |
|
501 // |
|
502 // |
|
503 // ----------------------------------------------------------------------------- |
|
504 // |
|
505 void CVtMediatorPlugin::LaunchVtAppL() |
|
506 { |
|
507 |
|
508 TRACE("CVtMediatorPlugin.LaunchVtAppL<" ) |
|
509 |
|
510 if ( !IsEnoughMemory() ) |
|
511 { |
|
512 const TVersion KTelephonyCmdVersion( |
|
513 KTelephonyCommandsVersionMajor, |
|
514 KTelephonyCommandsVersionMinor, |
|
515 KTelephonyCommandsVersionBuild ); |
|
516 const TInt res = |
|
517 iCommandInitiator->IssueCommand( |
|
518 KMediatorTelephonyDomain, |
|
519 KCatVideoTelToPhoneCommands, |
|
520 EVtCmdLowMemory, |
|
521 KTelephonyCmdVersion, |
|
522 KNullDesC8() ); |
|
523 ClearData(iActiveVideoCallInfo, iActiveVideoCallState); |
|
524 ClearData(iWaitingVideoCallInfo, iWaitingVideoCallState); |
|
525 TRACE("CVtMediatorPlugin.LaunchVtAppL, Insufficient Memory" ) |
|
526 return; |
|
527 } |
|
528 |
|
529 iAppDeathActive = new ( ELeave ) CAppDeathActive( *this, iAppThread ); |
|
530 |
|
531 User::LeaveIfError( iWsSession.Connect() ); |
|
532 |
|
533 TInt wgId = 0; |
|
534 TBool found = EFalse; |
|
535 |
|
536 // Check if there is already application running. Then we do not |
|
537 // start new one - rather we just monitor the existing one. |
|
538 while ( ( wgId != KErrNotFound ) && !found ) |
|
539 { |
|
540 CApaWindowGroupName::FindByAppUid( |
|
541 KVtCmVideoTelUiUid, |
|
542 iWsSession, |
|
543 wgId ); |
|
544 |
|
545 TApaTask task( iWsSession ); |
|
546 task.SetWgId( wgId ); |
|
547 if ( task.Exists() ) |
|
548 { |
|
549 if ( iAppThread.Open( task.ThreadId() ) == KErrNone ) |
|
550 { |
|
551 TExitType exitType = iAppThread.ExitType(); |
|
552 found = ( exitType == EExitPending ); |
|
553 |
|
554 if ( found ) |
|
555 { |
|
556 iAppThreadId = task.ThreadId(); |
|
557 } |
|
558 } |
|
559 } |
|
560 |
|
561 if ( !found ) |
|
562 { |
|
563 iAppThread.Close(); |
|
564 } |
|
565 } |
|
566 |
|
567 // If application was not found, then launch new application. |
|
568 if ( !found ) |
|
569 { |
|
570 TThreadId threadId; |
|
571 #ifndef SYMBIAN_SUPPORT_UI_FRAMEWORKS_V1 |
|
572 CApaCommandLine* cmd = CApaCommandLine::NewLC(); |
|
573 cmd->SetExecutableNameL( KVtCmVideoTelUiPath ); |
|
574 #else // !SYMBIAN_SUPPORT_UI_FRAMEWORKS_V1 |
|
575 CApaCommandLine* cmd = CApaCommandLine::NewLC( KVtCmVideoTelUiPath ); |
|
576 #endif // SYMBIAN_SUPPORT_UI_FRAMEWORKS_V1 |
|
577 cmd->SetCommandL( EApaCommandBackground ); |
|
578 |
|
579 RApaLsSession session; |
|
580 User::LeaveIfError( session.Connect() ); |
|
581 CleanupClosePushL( session ); |
|
582 |
|
583 TInt err = session.StartApp( *cmd, threadId ); |
|
584 if ( err > KErrNone ) |
|
585 { |
|
586 err = KErrGeneral; |
|
587 } |
|
588 User::LeaveIfError( err ); |
|
589 CleanupStack::PopAndDestroy( 2, cmd ); // CleanupClosePushL, cmd |
|
590 User::LeaveIfError( iAppThread.Open( threadId ) ); |
|
591 iAppThreadId = threadId; |
|
592 } |
|
593 |
|
594 // Start active objects. |
|
595 iState = EWaitingEventRegistration; |
|
596 iAppDeathActive->Start(); |
|
597 TRACE("CVtMediatorPlugin.LaunchVtAppL>" ) |
|
598 } |
|
599 |
|
600 |
|
601 // ----------------------------------------------------------------------------- |
|
602 // CVtMediatorPlugin:: |
|
603 // |
|
604 // |
|
605 // ----------------------------------------------------------------------------- |
|
606 // |
|
607 void CVtMediatorPlugin::SaveCallData( const TTelephonyCallDataParam& aData, TVtVideoTelephonyCallInformation& iVtCallInfo ) |
|
608 { |
|
609 TRACE("CVtMediatorPlugin.SaveCallData<" ) |
|
610 iVtCallInfo.iDisplayText = aData.iCLIText.Left( |
|
611 TVtVideoTelephonyCallInformation::TDisplayTextMaxLength ); |
|
612 |
|
613 TRACE2("CVtMediatorPlugin.SaveCallData iDisplayText=%S", |
|
614 &iVtCallInfo.iDisplayText ); |
|
615 |
|
616 iVtCallInfo.iCallId = aData.iCallId; |
|
617 |
|
618 if ( KNullDesC() != aData.iRemotePhoneNumber ) |
|
619 { |
|
620 iVtCallInfo.iVoiceCallPossible = ETrue; |
|
621 } |
|
622 iVtCallInfo.iEventDataValidity |= |
|
623 TVtVideoTelephonyCallInformation::EDisplayTextValid; |
|
624 TRACE2("CVtMediatorPlugin.SaveCallData data saved=%d>", |
|
625 aData.iCallType == ECallTypeVideo ) |
|
626 } |
|
627 |
|
628 |
|
629 // ----------------------------------------------------------------------------- |
|
630 // CVtMediatorPlugin:: |
|
631 // |
|
632 // |
|
633 // ----------------------------------------------------------------------------- |
|
634 // |
|
635 void CVtMediatorPlugin::HandleDataportCommandL( const TDesC8& aData ) |
|
636 { |
|
637 TRACE("CVtMediatorPlugin.HandleDataportCommandL<" ) |
|
638 TDataPortPackage pckg; |
|
639 pckg.Copy( aData ); |
|
640 iActiveVideoCallInfo.iDataport = pckg(); |
|
641 iActiveVideoCallInfo.iEventDataValidity |= |
|
642 TVtVideoTelephonyCallInformation::EDataportValid; |
|
643 RaiseVtEventL(); |
|
644 TRACE("CVtMediatorPlugin.HandleDataportCommandL>" ) |
|
645 } |
|
646 |
|
647 |
|
648 // ----------------------------------------------------------------------------- |
|
649 // CVtMediatorPlugin::ClearData |
|
650 // |
|
651 // |
|
652 // ----------------------------------------------------------------------------- |
|
653 // |
|
654 void CVtMediatorPlugin::ClearData(TVtVideoTelephonyCallInformation& aVtCallInfo, TCallState& aCallState) |
|
655 { |
|
656 TRACE("CVtMediatorPlugin.ClearData<" ) |
|
657 if ( aVtCallInfo.iCallId == iActiveVideoCallInfo.iCallId ) |
|
658 { |
|
659 iState = EWaitingAppLaunch; |
|
660 } |
|
661 aVtCallInfo.iEventDataValidity = 0; |
|
662 aVtCallInfo.iDataport.Zero(); |
|
663 aVtCallInfo.iVoiceCallPossible = EFalse; |
|
664 //for video call, it should be 9/10 |
|
665 //for other call, it will be from -1 to 8 |
|
666 aVtCallInfo.iCallId = KVtInitCallId; |
|
667 aVtCallInfo.iDisplayText.Zero(); |
|
668 aCallState = ECallStateIdle; |
|
669 TRACE("CVtMediatorPlugin.ClearData>" ) |
|
670 } |
|
671 |
|
672 // ----------------------------------------------------------------------------- |
|
673 // CVtMediatorPlugin::RegisterVtInternalEventL |
|
674 // |
|
675 // |
|
676 // ----------------------------------------------------------------------------- |
|
677 // |
|
678 void CVtMediatorPlugin::RegisterVtInternalEventL() |
|
679 { |
|
680 TRACE("CVtMediatorPlugin.RegisterVtInternalEventL<" ) |
|
681 iEventProvider = CMediatorEventProvider::NewL(); |
|
682 |
|
683 TVersion version( |
|
684 KVideotelMdtrEventVersionMajor, |
|
685 KVideotelMdtrEventVersionMinor, |
|
686 KVideotelMdtrEventVersionBuild ); |
|
687 |
|
688 TCapabilitySet capSet; |
|
689 capSet.SetEmpty(); |
|
690 capSet.AddCapability( ECapabilityReadDeviceData ); |
|
691 |
|
692 const TInt err = iEventProvider->RegisterEvent( |
|
693 KMediatorVideoTelephonyDomain, |
|
694 KCatVideotelInternalEvents, |
|
695 EVtMediatorEventVideoCallInformation, |
|
696 version, |
|
697 capSet ); |
|
698 |
|
699 |
|
700 TRACE2("CVtMediatorPlugin.RegisterVtInternalEventL err=%d>", err ) |
|
701 User::LeaveIfError( err ); |
|
702 } |
|
703 |
|
704 // ----------------------------------------------------------------------------- |
|
705 // CVtMediatorPlugin::RegisterDataportCommandL |
|
706 // |
|
707 // |
|
708 // ----------------------------------------------------------------------------- |
|
709 // |
|
710 void CVtMediatorPlugin::RegisterDataportCommandL() |
|
711 { |
|
712 TRACE("CVtMediatorPlugin.RegisterDataportCommandL<" ) |
|
713 iCommandResponder = CMediatorCommandResponder::NewL( this ); |
|
714 |
|
715 TCapabilitySet capSet; |
|
716 capSet.SetEmpty(); |
|
717 capSet.AddCapability( ECapabilityWriteDeviceData ); |
|
718 MediatorService::TCommand command; |
|
719 |
|
720 command.iCaps = capSet; |
|
721 command.iVersion = TVersion( |
|
722 KPhoneToVideotelCmdVersionMajor, |
|
723 KPhoneToVideotelCmdVersionMinor, |
|
724 KPhoneToVideotelCmdVersionBuild ); |
|
725 command.iTimeout = KVtEngMdtrCmdTimeout; |
|
726 |
|
727 // enable microphone command |
|
728 command.iCommandId = EVtCmdUseDataport; |
|
729 iCommandList.Append( command ); |
|
730 |
|
731 // Releasedataport command |
|
732 capSet.SetEmpty(); |
|
733 capSet.AddCapability( ECapabilityPowerMgmt ); |
|
734 command.iCommandId = EVtCmdReleaseDataport; |
|
735 iCommandList.Append( command ); |
|
736 |
|
737 const TInt err = iCommandResponder->RegisterCommand( |
|
738 KMediatorVideoTelephonyDomain, |
|
739 KCatPhoneToVideotelCommands, |
|
740 iCommandList ); |
|
741 |
|
742 TRACE2("CVtMediatorPlugin.RegisterDataportCommandL err=%d>", err ) |
|
743 User::LeaveIfError( err ); |
|
744 } |
|
745 |
|
746 // ----------------------------------------------------------------------------- |
|
747 // CVtMediatorPlugin::RaiseVtEventL |
|
748 // |
|
749 // Raises VT call info event if in suitable state, i.e. VT app has subscribed |
|
750 // the event. |
|
751 // ----------------------------------------------------------------------------- |
|
752 // |
|
753 void CVtMediatorPlugin::RaiseVtEventL() |
|
754 { |
|
755 TRACE("CVtMediatorPlugin.RaiseVtEventL<" ) |
|
756 TInt result = KVtAppNotReady; // does not cause leave |
|
757 TRACE2("CVtMediatorPlugin.RaiseVtEventL iState=%d>", |
|
758 iState ) |
|
759 TRACE2("CVtMediatorPlugin.RaiseVtEventL iActiveVideoCallState=%d>", |
|
760 iActiveVideoCallState ) |
|
761 if ( iState == EReady && // application subscribed to the event |
|
762 |
|
763 // don't send event if video call is not starting/ongoing |
|
764 ( iActiveVideoCallState >= ECallStateDialling && |
|
765 iActiveVideoCallState <= ECallStateConnected ) ) |
|
766 { |
|
767 const TVersion version( |
|
768 KVideotelMdtrEventVersionMajor, |
|
769 KVideotelMdtrEventVersionMinor, |
|
770 KVideotelMdtrEventVersionBuild ); |
|
771 |
|
772 const TVtMediatorInfoPackage pckg( iActiveVideoCallInfo ); |
|
773 result = iEventProvider->RaiseEvent( |
|
774 KMediatorVideoTelephonyDomain, |
|
775 KCatVideotelInternalEvents, |
|
776 EVtMediatorEventVideoCallInformation, |
|
777 version, |
|
778 pckg |
|
779 ); |
|
780 } |
|
781 TRACE2("CVtMediatorPlugin.RaiseVtEventL result=%d>", result ) |
|
782 User::LeaveIfError( result ); |
|
783 } |
|
784 |
|
785 // ----------------------------------------------------------------------------- |
|
786 // CVtMediatorPlugin::HandleCallStateChangeL |
|
787 // |
|
788 // Compares previous and new video call states and resolves based on result |
|
789 // if Video telephone applicaton should be launched. |
|
790 // ----------------------------------------------------------------------------- |
|
791 // |
|
792 void CVtMediatorPlugin::HandleCallStateChangeL( |
|
793 const TTelephonyCallDataParam& aData ) |
|
794 { |
|
795 TRACE("CVtMediatorPlugin.HandleCallStateChangeL<" ) |
|
796 |
|
797 TRACE2("CVtMediatorPlugin.HandleCallStateChangeL calltype=%d>", |
|
798 aData.iCallType ) |
|
799 TRACE2("CVtMediatorPlugin.HandleCallStateChangeL saved Activecallid=%d>", |
|
800 iActiveVideoCallInfo.iCallId ) |
|
801 TRACE2("CVtMediatorPlugin.HandleCallStateChangeL saved Waitingcallid=%d>", |
|
802 iWaitingVideoCallInfo.iCallId ) |
|
803 TRACE2("CVtMediatorPlugin.HandleCallStateChangeL callid=%d>", |
|
804 aData.iCallId ) |
|
805 TRACE2("CVtMediatorPlugin.HandleCallStateChangeL ActiveCallOldState=%d>", |
|
806 iActiveVideoCallState ) |
|
807 TRACE2("CVtMediatorPlugin.HandleCallStateChangeL WaitingCallOldState=%d>", |
|
808 iWaitingVideoCallState ) |
|
809 TRACE2("CVtMediatorPlugin.HandleCallStateChangeL NewState=%d>", |
|
810 aData.iCallState ) |
|
811 |
|
812 //if the call is waitingcall, just save/clear |
|
813 if ( aData.iCallType == ECallTypeVideo || |
|
814 // check also call id because in call clearing states call type may |
|
815 // be unspecified but call id is saved in call setup and we can |
|
816 // compare to it. |
|
817 iActiveVideoCallInfo.iCallId == aData.iCallId || |
|
818 iWaitingVideoCallInfo.iCallId == aData.iCallId ) |
|
819 { |
|
820 TBool isWaitingCall = ETrue; |
|
821 |
|
822 /** |
|
823 * firstly we should check the callid to identify if it is a waitingcal/activecall |
|
824 * imagine the usecase that long press endkey to shutdown both calls. |
|
825 * after that checking iState |
|
826 */ |
|
827 if ( iWaitingVideoCallInfo.iCallId == aData.iCallId ) |
|
828 { |
|
829 isWaitingCall = ETrue; |
|
830 } |
|
831 else if ( iActiveVideoCallInfo.iCallId == aData.iCallId ) |
|
832 { |
|
833 isWaitingCall = EFalse; |
|
834 } |
|
835 //no vt app launched, this happens while vt first launching or end key to shutdown both calls |
|
836 else if ( iState == EWaitingAppLaunch ) |
|
837 { |
|
838 isWaitingCall = EFalse; |
|
839 } |
|
840 |
|
841 TRACE2("CVtMediatorPlugin.HandleCallStateChangeL isWaitingCall=%d>", |
|
842 isWaitingCall) |
|
843 |
|
844 TCallState& callState = isWaitingCall?iWaitingVideoCallState:iActiveVideoCallState; |
|
845 TVtVideoTelephonyCallInformation& vtCallInfo = isWaitingCall?iWaitingVideoCallInfo:iActiveVideoCallInfo; |
|
846 |
|
847 TBool launchNeeded = KVtCallStateActionArray[ aData.iCallState ] - |
|
848 KVtCallStateActionArray[callState] > 0; |
|
849 if ( isWaitingCall ) |
|
850 { |
|
851 launchNeeded = EFalse; |
|
852 } |
|
853 callState = aData.iCallState; |
|
854 |
|
855 switch ( callState ) |
|
856 { |
|
857 case ECallStateDialling: |
|
858 case ECallStateRinging: |
|
859 case ECallStateConnecting: |
|
860 case ECallStateConnected: |
|
861 SaveCallData( aData, vtCallInfo); |
|
862 break; |
|
863 default: |
|
864 // data becomes invalid in other states (=call clearing/idle) |
|
865 ClearData(vtCallInfo, callState); |
|
866 break; |
|
867 } |
|
868 if ( launchNeeded ) |
|
869 { |
|
870 LaunchVtAppL(); |
|
871 } |
|
872 if ( !isWaitingCall ) |
|
873 { |
|
874 RaiseVtEventL(); |
|
875 } |
|
876 } |
|
877 |
|
878 TRACE("CVtMediatorPlugin.HandleCallStateChangeL>" ) |
|
879 } |
|
880 |
|
881 // ----------------------------------------------------------------------------- |
|
882 // CVtMediatorPlugin::IsEnoughMemory |
|
883 // |
|
884 // Check if there is enough memory to launch |
|
885 // ----------------------------------------------------------------------------- |
|
886 // |
|
887 TBool CVtMediatorPlugin::IsEnoughMemory() |
|
888 { |
|
889 TRACE("CVtMediatorPlugin::IsEnoughMemory<" ) |
|
890 // Fetch amount of free memory. |
|
891 TMemoryInfoV1Buf memory; |
|
892 UserHal::MemoryInfo( memory ); |
|
893 TInt freeRam = (TInt)( memory().iFreeRamInBytes ); |
|
894 TRACE2("CVtMediatorPlugin::IsEnoughMemory: freeRam = %d", freeRam ) |
|
895 |
|
896 TBool enoughRam = ETrue; |
|
897 |
|
898 if ( freeRam < KRamNeededForVideoCalls ) |
|
899 { |
|
900 FreeRam(); |
|
901 freeRam = (TInt)( memory().iFreeRamInBytes ); |
|
902 TRACE2("CVtMediatorPlugin::IsEnoughMemory: after free, freeRam = %d", freeRam ) |
|
903 if ( freeRam < KRamNeededForVideoCalls ) |
|
904 { |
|
905 enoughRam = EFalse; |
|
906 TRACE ("CVtMediatorPlugin::IsEnoughMemory : Not enough RAM") |
|
907 |
|
908 } |
|
909 } |
|
910 TRACE("CVtMediatorPlugin::IsEnoughMemory>" ) |
|
911 return enoughRam; |
|
912 } |
|
913 // ----------------------------------------------------------------------------- |
|
914 // CVtMediatorPlugin::FreeRam |
|
915 // Try to free memory to match the memory usage of VT |
|
916 // ----------------------------------------------------------------------------- |
|
917 // |
|
918 void CVtMediatorPlugin::FreeRam() |
|
919 { |
|
920 TRACE("CVtMediatorPlugin.FreeRam()<") |
|
921 User::CompressAllHeaps(); |
|
922 TRACE("CVtMediatorPlugin.FreeRam()>") |
|
923 } |
|
924 |
|
925 // ----------------------------------------------------------------------------- |
|
926 // CVtMediatorPlugin::StopDeathActiveL |
|
927 // ----------------------------------------------------------------------------- |
|
928 // |
|
929 void CVtMediatorPlugin::StopDeathActiveL() |
|
930 { |
|
931 TRACE("CVtMediatorPlugin.StopDeathActive<") |
|
932 delete iAppDeathActive; |
|
933 iAppThread.Close(); |
|
934 iWsSession.Close(); |
|
935 //if there is a waiting call, check if we need to launch it |
|
936 TRACE2("CVtMediatorPlugin.StopDeathActive WaitintCallID=%d>", |
|
937 iWaitingVideoCallInfo.iCallId) |
|
938 if ( iWaitingVideoCallInfo.iCallId != KVtInitCallId ) |
|
939 { |
|
940 iActiveVideoCallInfo = iWaitingVideoCallInfo; |
|
941 iActiveVideoCallState = iWaitingVideoCallState; |
|
942 ClearData(iWaitingVideoCallInfo, iWaitingVideoCallState); |
|
943 |
|
944 if ( iActiveVideoCallState == ECallStateDialling || |
|
945 iActiveVideoCallState == ECallStateRinging || |
|
946 iActiveVideoCallState == ECallStateConnecting || |
|
947 iActiveVideoCallState == ECallStateConnected || |
|
948 iActiveVideoCallState == ECallStateAnswering ) |
|
949 { |
|
950 LaunchVtAppL(); |
|
951 RaiseVtEventL(); |
|
952 } |
|
953 } |
|
954 TRACE("CVtMediatorPlugin.StopDeathActive>") |
|
955 } |
|
956 // ----------------------------------------------------------------------------- |
|
957 // CVtMediatorPlugin::CAppDeathActive::CAppDeathActive |
|
958 // ----------------------------------------------------------------------------- |
|
959 // |
|
960 CVtMediatorPlugin::CAppDeathActive::CAppDeathActive( |
|
961 CVtMediatorPlugin& aMediatorPlugin, |
|
962 RThread& aAppThread |
|
963 ) |
|
964 : CActive( CActive::EPriorityStandard ), |
|
965 iMediatorPlugin( aMediatorPlugin ), |
|
966 iAppThread( aAppThread ) |
|
967 |
|
968 { |
|
969 CActiveScheduler::Add( this ); |
|
970 } |
|
971 |
|
972 // ----------------------------------------------------------------------------- |
|
973 // CVtMediatorPlugin::CAppDeathActive::~CAppDeathActive |
|
974 // ----------------------------------------------------------------------------- |
|
975 // |
|
976 CVtMediatorPlugin::CAppDeathActive::~CAppDeathActive() |
|
977 { |
|
978 TRACE("CVtMediatorPlugin.~CAppDeathActive") |
|
979 Cancel(); |
|
980 } |
|
981 |
|
982 // ----------------------------------------------------------------------------- |
|
983 // CVtMediatorPlugin::CAppDeathActive::Start |
|
984 // ----------------------------------------------------------------------------- |
|
985 // |
|
986 void CVtMediatorPlugin::CAppDeathActive::Start() |
|
987 { |
|
988 TRACE("CVtMediatorPlugin.Start<") |
|
989 Cancel(); |
|
990 iAppThread.Logon( iStatus ); |
|
991 SetActive(); |
|
992 TRACE("CVtMediatorPlugin.Start>") |
|
993 } |
|
994 |
|
995 // ----------------------------------------------------------------------------- |
|
996 // CVtMediatorPlugin::CAppDeathActive::RunL |
|
997 // ----------------------------------------------------------------------------- |
|
998 // |
|
999 void CVtMediatorPlugin::CAppDeathActive::RunL() |
|
1000 { |
|
1001 //do something here |
|
1002 TRACE("CVtMediatorPlugin.RunL<") |
|
1003 iMediatorPlugin.StopDeathActiveL(); |
|
1004 TRACE("CVtMediatorPlugin.RunL>") |
|
1005 |
|
1006 } |
|
1007 |
|
1008 // ----------------------------------------------------------------------------- |
|
1009 // CVtMediatorPlugin::CAppDeathActive::DoCancel |
|
1010 // ----------------------------------------------------------------------------- |
|
1011 // |
|
1012 void CVtMediatorPlugin::CAppDeathActive::DoCancel() |
|
1013 { |
|
1014 iAppThread.LogonCancel( iStatus ); |
|
1015 } |
|
1016 |
|
1017 // ----------------------------------------------------------------------------- |
|
1018 // CVtMediatorPlugin::CAppDeathActive::RunError |
|
1019 // ----------------------------------------------------------------------------- |
|
1020 // |
|
1021 TInt CVtMediatorPlugin::CAppDeathActive::RunError( TInt /*aError*/ ) |
|
1022 { |
|
1023 return KErrNone; |
|
1024 } |