--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/phoneplugins/csplugin/src/cspconferencecall.cpp Fri Mar 19 09:28:42 2010 +0200
@@ -0,0 +1,623 @@
+/*
+* Copyright (c) 2007 Nokia Corporation and/or its subsidiary(-ies).
+* All rights reserved.
+* This component and the accompanying materials are made available
+* under the terms of "Eclipse Public License v1.0"
+* which accompanies this distribution, and is available
+* at the URL "http://www.eclipse.org/legal/epl-v10.html".
+*
+* Initial Contributors:
+* Nokia Corporation - initial contribution.
+*
+* Contributors:
+*
+* Description: Implements class CSPConferenceCall which provides call functionality
+*
+*/
+
+
+
+#include <etelmm.h>
+#include <etel.h>
+#include <mccpcall.h>
+
+#include "cspconferencecall.h"
+#include "cspvoicecall.h"
+#include "cspetelconferencecallrequester.h"
+#include "cspetelconferenceeventmonitor.h"
+#include "cspetelconferencestatusmonitor.h"
+#include "cspetelconferencecapsmonitor.h"
+#include "mcspcallinformation.h"
+#include "csplogger.h"
+#include "csppanic.pan"
+#include "cspconsts.h"
+
+
+// ---------------------------------------------------------------------------
+// CSPConferenceCall::NewL
+// ---------------------------------------------------------------------------
+//
+CSPConferenceCall* CSPConferenceCall::NewL(
+ RMobilePhone& aPhone,
+ MCSPCallInformation& aCallInfo,
+ TUint32 aServiceId )
+ {
+ CSPLOGSTRING(CSPOBJECT, "CSPConferenceCall::NewL()");
+
+ CSPConferenceCall* self = new ( ELeave ) CSPConferenceCall( aPhone,
+ aCallInfo, aServiceId );
+ CleanupStack::PushL( self );
+ self->ConstructL( );
+ CleanupStack::Pop( self );
+ CSPLOGSTRING(CSPOBJECT, "CSPConferenceCall::NewL() end");
+ return self;
+ }
+
+// --------------------------------------------------------ß-------------------
+// CSPConferenceCall::~CSPConferenceCall
+// ---------------------------------------------------------------------------
+//
+CSPConferenceCall::~CSPConferenceCall()
+ {
+ CSPLOGSTRING(CSPOBJECT, "CSPConferenceCall::~CSPConferenceCall() start");
+ iObservers.Close();
+
+ delete iCallStatusMonitor;
+ delete iCallEventMonitor;
+ delete iCallCapsMonitor;
+ delete iRequester;
+ iCall.Close();
+
+ CSPLOGSTRING(CSPOBJECT, "CSPConferenceCall::~CSPConferenceCall() end");
+ }
+
+// ---------------------------------------------------------------------------
+// CSPConferenceCall::NotifyEvent
+// Conference event forwarding.
+// This way Added, Removed and Split events are notified.
+// ---------------------------------------------------------------------------
+//
+void CSPConferenceCall::NotifyEvent(
+ MCCPConferenceCallObserver::TCCPConferenceCallEvent aEvent,
+ TName& aCallName )
+ {
+ CSPLOGSTRING2( CSPINT, "CSPConferenceCall::NotifyEvent < %d", aEvent );
+
+ CSPCall* call = iCallInfo.FindCall( aCallName );
+ TInt count = iObservers.Count();
+ for ( TInt i = 0; i < count; i++ )
+ {
+ MCCPConferenceCallObserver *obs = iObservers[i];
+ if ( obs )
+ {
+ obs->ConferenceCallEventOccurred( aEvent, call );
+ }
+ }
+ CSPLOGSTRING2( CSPINT, "CSPConferenceCall::NotifyEvent > %d", aEvent );
+ }
+
+// ---------------------------------------------------------------------------
+// CSPConferenceCall::NotifyEvent
+// Conference event forwarding in case of Terminated, Built or Swapped events.
+// These events are not call specific.
+// ---------------------------------------------------------------------------
+//
+void CSPConferenceCall::NotifyEvent(
+ MCCPConferenceCallObserver::TCCPConferenceCallEvent aEvent )
+ {
+ CSPLOGSTRING2( CSPINT, "CSPConferenceCall::NotifyEvent < %d", aEvent );
+
+ TInt count = iObservers.Count();
+ for ( TInt i = 0; i < count; i++ )
+ {
+ MCCPConferenceCallObserver *obs = iObservers[i];
+ if ( obs )
+ {
+ obs->ConferenceCallEventOccurred( aEvent, NULL );
+ }
+ }
+
+ CSPLOGSTRING2( CSPINT, "CSPConferenceCall::NotifyEvent > %d", aEvent );
+ }
+
+// ---------------------------------------------------------------------------
+// CSPConferenceCall::NotifyStateChanged
+// Conference state change forwarding
+// ---------------------------------------------------------------------------
+//
+void CSPConferenceCall::NotifyStateChange(
+ MCSPConferenceStatusObserver::TCSPConferenceState aStatus )
+ {
+ CSPLOGSTRING3( CSPINT, "CSPConferenceCall::NotifyStateChange %d this: %x", aStatus,
+ this );
+ iCallState = static_cast<MCCPConferenceCallObserver::TCCPConferenceCallState>(aStatus);
+ if ( aStatus == MCSPConferenceStatusObserver::ECSPConferenceIdle )
+ {
+ iCallCountForAddCall = 0;
+ }
+ else
+ {
+ if ( iCallCountForAddCall == 1 )
+ {
+ iCallCountForAddCall++;
+ }
+ }
+
+ TInt count = iObservers.Count();
+ for ( TInt i = 0; i < count; i++ )
+ {
+ MCCPConferenceCallObserver *obs = iObservers[i];
+ if ( obs )
+ {
+ obs->ConferenceCallStateChanged(
+ static_cast<MCCPConferenceCallObserver::TCCPConferenceCallState>(aStatus) );
+ }
+ }
+ }
+
+// ---------------------------------------------------------------------------
+// CSPConferenceCall::ConferenceCapsChanged
+// ---------------------------------------------------------------------------
+//
+void CSPConferenceCall::ConferenceCapsChanged( TUint32 aCaps )
+ {
+ CSPLOGSTRING2( CSPINT, "CSPConferenceCall::ConferenceCapsChanged %b", aCaps );
+
+ TInt count = iObservers.Count();
+ for ( TInt i = 0; i < count; i++ )
+ {
+ MCCPConferenceCallObserver *obs = iObservers[i];
+ if ( obs )
+ {
+ obs->ConferenceCallCapsChanged(
+ (MCCPConferenceCallObserver::TCCPConferenceCallCaps) aCaps );
+ }
+ }
+ }
+
+// ---------------------------------------------------------------------------
+// CSPConferenceCall::NotifyConferenceError
+// ---------------------------------------------------------------------------
+//
+void CSPConferenceCall::NotifyConferenceError( TCCPConferenceCallError aErr )
+ {
+ CSPLOGSTRING2( CSPERROR, "CSPConferenceCall::NotifyConferenceError < %d", aErr );
+
+ TInt count = iObservers.Count();
+ for ( TInt i = 0; i < count; i++ )
+ {
+ MCCPConferenceCallObserver *obs = iObservers[i];
+ if ( obs )
+ {
+ obs->ErrorOccurred( aErr );
+ }
+ }
+
+ CSPLOGSTRING2( CSPERROR, "CSPConferenceCall::NotifyConferenceError > %d", aErr );
+ }
+
+// ---------------------------------------------------------------------------
+// From class MCCPConferenceCall
+// CSPConferenceCall::AddCall
+// ---------------------------------------------------------------------------
+//
+void CSPConferenceCall::AddCallL( MCCPCall* aCall )
+ {
+ CSPLOGSTRING( CSPREQIN, "CSPConferenceCall::AddCallL " );
+
+ TInt err(KErrNone);
+
+ if ( aCall )
+ {
+ iCallCountForAddCall++;
+ CSPLOGSTRING2( CSPINT, "CSPConferenceCall::AddCallL calls added %d",
+ iCallCountForAddCall );
+
+ if ( iCallCountForAddCall < 2 )
+ {
+ CSPLOGSTRING2( CSPINT,
+ "CSPConferenceCall::AddCallL DO NOTHING SINCE CALL COUNT IS %d", iCallCountForAddCall );
+ }
+ else if ( iCallCountForAddCall == 2 )
+ {
+ err = iRequester->MakeRequest(
+ CSPEtelConferenceCallRequester::
+ EConferenceRequestTypeCreateConference );
+ }
+ else if ( iCallCountForAddCall > 2 )
+ {
+ CSPLOGSTRING( CSPINT, "CSPConferenceCall::AddCall cast call");
+ CSPCall* cspCall = static_cast< CSPCall* > ( aCall );
+
+ iAddedCallName.Zero();
+ cspCall->CallName( iAddedCallName );
+ CSPLOGSTRING2( CSPINT, "CSPConferenceCall::AddCall n=%S", &iAddedCallName );
+ err = iRequester->MakeAddCallRequest( iAddedCallName );
+ CSPLOGSTRING2( CSPINT,
+ "CSPConferenceCall::AddCallL result %d", err);
+ }
+ }
+ else
+ {
+ CSPLOGSTRING( CSPERROR,
+ "CSPConferenceCall::AddCallL Invalid argument, call NULL" );
+
+ err = KErrArgument;
+ }
+
+ CSPLOGSTRING2( CSPINT, "CSPConferenceCall::AddCallL returning %d", err);
+
+ User::LeaveIfError( err );
+
+ CSPLOGSTRING( CSPINT, "CSPConferenceCall::AddCallL OK" );
+ }
+
+// ---------------------------------------------------------------------------
+// From class MCCPConferenceCall
+// CSPConferenceCall::RemoveCallL
+// ---------------------------------------------------------------------------
+//
+void CSPConferenceCall::RemoveCallL( MCCPCall* aCall )
+ {
+ CSPLOGSTRING( CSPREQIN, "CSPConferenceCall::RemoveCallL " );
+ if ( aCall )
+ {
+ User::LeaveIfError( aCall->HangUp() );
+ CSPLOGSTRING( CSPINT, "CSPConferenceCall::RemoveCallL Hangup request sent" );
+ }
+ else
+ {
+ CSPLOGSTRING( CSPERROR, "CSPConferenceCall::RemoveCallL Invalid argument" );
+ User::Leave( KErrArgument );
+ }
+
+ CSPLOGSTRING( CSPREQOUT, "CSPConferenceCall::RemoveCallL end" );
+ }
+
+// ---------------------------------------------------------------------------
+// From class MCCPConferenceCall
+// CSPConferenceCall::CallCount
+// ---------------------------------------------------------------------------
+//
+TInt CSPConferenceCall::CallCount( ) const
+ {
+ CSPLOGSTRING( CSPREQIN, "CSPConferenceCall::CallCount" );
+ TInt callCount(0);
+ TInt err = iCall.EnumerateCalls( callCount );
+ CSPLOGSTRING( CSPREQOUT, "CSPConferenceCall::CallCount end" );
+ return callCount;
+ }
+
+// ---------------------------------------------------------------------------
+// From class MCCPConferenceCall
+// CSPConferenceCall::GoOneToOneL
+// ---------------------------------------------------------------------------
+//
+void CSPConferenceCall::GoOneToOneL( MCCPCall& aCall )
+ {
+ CSPLOGSTRING( CSPREQIN, "CSPConferenceCall::GoOneToOneL " );
+
+ if ( aCall.Parameters().CallType() == CCPCall::ECallTypeCSVoice )
+ {
+ CSPVoiceCall& voiceCall = static_cast< CSPVoiceCall& > ( aCall );
+ TInt err = voiceCall.GoOneToOne();
+ CSPLOGSTRING2( CSPREQIN, "CSPConferenceCall::GoOneToOneL Request %d",
+ err );
+ User::LeaveIfError( err );
+ }
+ else
+ {
+ CSPLOGSTRING( CSPREQIN, "CSPConferenceCall::GoOneToOneL ERROR NOT VOICE CALL" );
+ User::Leave( KErrNotSupported );
+ }
+ CSPLOGSTRING( CSPREQOUT, "CSPConferenceCall::GoOneToOneL end" );
+ }
+
+// ---------------------------------------------------------------------------
+// From class MCCPConferenceCall
+// CSPConferenceCall::ServiceId
+// ---------------------------------------------------------------------------
+//
+TUint32 CSPConferenceCall::ServiceId() const
+ {
+ CSPLOGSTRING( CSPREQIN, "CSPConferenceCall::ServiceId " );
+ return iServiceId;
+ }
+
+// ---------------------------------------------------------------------------
+// From class MCCPCall
+// CSPConferenceCall::HangUp
+// ---------------------------------------------------------------------------
+//
+TInt CSPConferenceCall::HangUp()
+ {
+ CSPLOGSTRING( CSPREQIN, "CSPConferenceCall::HangUp " );
+ TInt err(KErrNone);
+
+ err = iRequester->MakeRequest(
+ CSPEtelConferenceCallRequester::EConferenceRequestTypeHangup );
+ if ( err )
+ {
+ CSPLOGSTRING2( CSPERROR, "CSPConferenceCall::HangUp error %d", err );
+ }
+
+ return err;
+ }
+
+// ---------------------------------------------------------------------------
+// From class MCCPCall
+// CSPConferenceCall::Hold
+// ---------------------------------------------------------------------------
+//
+TInt CSPConferenceCall::Hold()
+ {
+ CSPLOGSTRING( CSPREQIN, "CSPConferenceCall::Hold call" );
+
+ TInt err( KErrNone );
+
+ if ( iCallState == MCCPConferenceCallObserver::ECCPConferenceActive )
+ {
+ CSPLOGSTRING( CSPREQOUT, "CSPConferenceCall::Hold > RMobileConferenceCall::Hold" );
+
+ err = iRequester->MakeRequest(
+ CSPEtelConferenceCallRequester::EConferenceRequestTypeHold );
+ if ( err != KErrNone )
+ {
+ CSPLOGSTRING2( CSPERROR, "CSPConferenceCall::Hold error: %d",
+ err );
+ }
+ }
+ else
+ {
+ CSPLOGSTRING2( CSPERROR,
+ "CSPConferenceCall::Hold : invalid state %d",
+ iCallState );
+ err = KErrNotReady;
+ }
+
+
+ return err;
+ }
+
+// ---------------------------------------------------------------------------
+// From class MCCPCall
+// CSPConferenceCall::Resume
+// ---------------------------------------------------------------------------
+//
+TInt CSPConferenceCall::Resume()
+ {
+ CSPLOGSTRING( CSPREQIN, "CSPConferenceCall::Resume " );
+
+ TInt err( KErrNone );
+
+ if ( iCallState == MCCPConferenceCallObserver::ECCPConferenceHold )
+ {
+ CSPLOGSTRING( CSPREQOUT, "CSPConferenceCall::Resume " );
+ err = iRequester->MakeRequest(
+ CSPEtelConferenceCallRequester::EConferenceRequestTypeResume );
+ if ( KErrNone != err )
+ {
+ CSPLOGSTRING2( CSPERROR, "CSPConferenceCall::Resume Error %d",
+ err );
+ }
+
+ }
+ else
+ {
+ CSPLOGSTRING2( CSPERROR,
+ "CSPConferenceCall::Resume : invalid state %d",
+ iCallState );
+ err = KErrNotReady;
+ }
+
+ return err;
+ }
+
+// ---------------------------------------------------------------------------
+// From class MCCPCall
+// CSPConferenceCall::Swap
+// ---------------------------------------------------------------------------
+//
+TInt CSPConferenceCall::Swap()
+ {
+ CSPLOGSTRING( CSPREQIN, "CSPConferenceCall::Swap " );
+ TInt err(KErrNone);
+
+ if ( iCallState == MCCPConferenceCallObserver::ECCPConferenceActive
+ || iCallState == MCCPConferenceCallObserver::ECCPConferenceHold )
+ {
+ err = iRequester->MakeRequest(
+ CSPEtelConferenceCallRequester::EConferenceRequestTypeSwap );
+ if ( err != KErrNone )
+ {
+ CSPLOGSTRING2( CSPERROR, "CSPConferenceCall::Swap Request error: %d", err );
+ }
+ }
+ else
+ {
+ err = KErrNotReady;
+ CSPLOGSTRING2( CSPERROR,
+ "CSPConferenceCall::Swap Invalid state %d",
+ iCallState );
+ }
+
+ return err;
+ }
+
+// ---------------------------------------------------------------------------
+// From class MCCPConferenceCall
+// CSPConferenceCall::CurrentCallsToConferenceL
+// ---------------------------------------------------------------------------
+//
+void CSPConferenceCall::CurrentCallsToConferenceL()
+ {
+ CSPLOGSTRING( CSPREQIN, "CSPConferenceCall::CurrentCallsToConferenceL " );
+ iRequester->MakeRequest(
+ CSPEtelConferenceCallRequester::EConferenceRequestTypeCreateConference );
+ CSPLOGSTRING( CSPREQOUT, "CSPConferenceCall::CurrentCallsToConferenceL end" );
+ }
+
+// ---------------------------------------------------------------------------
+// From class MCCPConferenceCall
+// CSPConferenceCall::GetCallArray
+// ---------------------------------------------------------------------------
+//
+TInt CSPConferenceCall::GetCallArray( RPointerArray<MCCPCall>& aCallArray )
+ {
+ CSPLOGSTRING( CSPREQIN, "CSPConferenceCall::GetCallArray" );
+ // Reset array in case
+ aCallArray.Reset();
+ TInt err( KErrNone );
+
+ RMobileCall::TMobileCallInfoV3 callInfo;
+ RMobileCall::TMobileCallInfoV3Pckg callInfoPck( callInfo );
+
+ TInt callCount = CallCount();
+ CSPCall* call;
+
+ // Resolve call objects that are part of the conference
+ for ( int i = 0; i < callCount; i++ )
+ {
+ err = iCall.GetMobileCallInfo( i, callInfoPck );
+
+ if ( KErrNone == err )
+ {
+ // Find call by call name
+ call = iCallInfo.FindCall( callInfo.iCallName);
+ if ( call )
+ {
+ err = aCallArray.Append( call );
+ }
+ else
+ {
+ err = KErrNotFound;
+ }
+ }
+ CSPLOGSTRING2( CSPERROR, "CSPConferenceCall::GetCallArray err: %d", err );
+ }
+
+ CSPLOGSTRING( CSPREQOUT, "CSPConferenceCall::GetCallArray end");
+ return err;
+ }
+
+// ---------------------------------------------------------------------------
+// Adds observer.
+// ---------------------------------------------------------------------------
+//
+void CSPConferenceCall::AddObserverL( const MCCPConferenceCallObserver& aObserver )
+ {
+ if ( iObservers.Find( &aObserver ) == KErrNotFound )
+ {
+ iObservers.Append( &aObserver );
+ }
+ }
+
+// ---------------------------------------------------------------------------
+// Removes given observer.
+// ---------------------------------------------------------------------------
+//
+TInt CSPConferenceCall::RemoveObserver( const MCCPConferenceCallObserver& aObserver )
+ {
+ CSPLOGSTRING( CSPREQIN, "CSPConferenceCall::RemoveObserver " );
+ TInt found = iObservers.Find( &aObserver );
+ if ( found != KErrNotFound )
+ {
+ iObservers.Remove( found );
+ return KErrNone;
+ }
+
+ return found;
+ }
+
+// ---------------------------------------------------------------------------
+// CSPConferenceCall::GetConferenceCallState
+// ---------------------------------------------------------------------------
+//
+TInt CSPConferenceCall::GetConferenceCallState(
+ MCCPConferenceCallObserver::TCCPConferenceCallState& aState )
+ {
+ CSPLOGSTRING(CSPOBJECT, "CSPConferenceCall::GetConferenceCallState()");
+ RMobileConferenceCall::TMobileConferenceStatus status;
+ TInt err = iCall.GetConferenceStatus( status );
+
+ switch( status )
+ {
+ case RMobileConferenceCall::EConferenceIdle:
+ {
+ aState = MCCPConferenceCallObserver::ECCPConferenceIdle;
+ break;
+ }
+ case RMobileConferenceCall::EConferenceActive:
+ {
+ aState = MCCPConferenceCallObserver::ECCPConferenceActive;
+ break;
+ }
+ case RMobileConferenceCall::EConferenceHold:
+ {
+ aState = MCCPConferenceCallObserver::ECCPConferenceHold;
+ break;
+ }
+ default:
+ break;
+ }
+
+ return err;
+ }
+
+// ---------------------------------------------------------------------------
+// CSPConferenceCall::CSPConferenceCall
+// ---------------------------------------------------------------------------
+//
+CSPConferenceCall::CSPConferenceCall( RMobilePhone& aPhone,
+ MCSPCallInformation& aCallInfo,
+ TUint32 aServiceId ) :
+ iPhone( aPhone ),
+ iRequester( NULL ),
+ iCallInfo( aCallInfo ),
+ iServiceId( aServiceId )
+ {
+ CSPLOGSTRING(CSPOBJECT, "CSPConferenceCall::CSPConferenceCall()");
+ }
+
+// ---------------------------------------------------------------------------
+// CSPConferenceCall::ConstructL
+// Constructing CSPConferenceCall for MT call.
+// ---------------------------------------------------------------------------
+//
+void CSPConferenceCall::ConstructL( )
+ {
+ CSPLOGSTRING(CSPOBJECT, "CSPConferenceCall::ConstructL() start");
+ User::LeaveIfError( iCall.Open(iPhone) );
+
+ iCall.EnumerateCalls( iCallCountForAddCall );
+ CSPLOGSTRING2(CSPERROR, "CSPConferenceCall::Initialize() Call count : %d",
+ iCallCountForAddCall );
+
+ MCCPConferenceCallObserver::TCCPConferenceCallState conferenceState;
+ TInt err = GetConferenceCallState( conferenceState );
+
+ if ( KErrNone == err )
+ {
+ iCallState = conferenceState;
+ CSPLOGSTRING2(CSPINT, "CSPConferenceCall::Initialize() State : %d", iCallState );
+ }
+ else
+ {
+ iCallState = MCCPConferenceCallObserver::ECCPConferenceIdle;
+ CSPLOGSTRING2(CSPERROR,
+ "CSPConferenceCall::Initialize() state fetching error %d", err );
+ }
+
+ // Start Etel monitors
+ iCallEventMonitor = CSPEtelConferenceEventMonitor::NewL( *this, iCall );
+ iCallEventMonitor->StartMonitoring();
+ iCallStatusMonitor = CSPEtelConferenceStatusMonitor::NewL( *this, iCall );
+ iCallStatusMonitor->StartMonitoring();
+ iCallCapsMonitor = CSPEtelConferenceCapsMonitor::NewL( *this, iCall );
+ iCallCapsMonitor->StartMonitoring();
+
+ iRequester = CSPEtelConferenceCallRequester::NewL( *this, iCall );
+ CSPLOGSTRING(CSPOBJECT, "CSPConferenceCall::ConstructL() end");
+ }
+
+// End of file