CCONF.CPP
//**************************************************************************** 
//  Module:     NMUI.EXE 
//  File:       CCONF.CPP  
//  Content:    INmConference Routines 
//               
// 
//  Copyright (c) Microsoft Corporation 1995-1997 
// 
// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF  
// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO  
// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A  
// PARTICULAR PURPOSE. 
//**************************************************************************** 
 
 
#include "precomp.h" 
 
COBLIST * g_pListConference = (COBLIST *) NULL; 
COBLIST * g_pListConferenceNotify = (COBLIST *) NULL; 
 
 
//**************************************************************************** 
// 
// INmConference * GetCurrentConference(void) 
// 
//**************************************************************************** 
 
INmConference * GetCurrentConference(void) 
{ 
if (NULL == g_pListConference) 
return NULL; 
 
return (INmConference *) g_pListConference->GetTail(); 
} 
 
 
//**************************************************************************** 
// 
// HRESULT HookConference(INmConference * pConference) 
// 
//**************************************************************************** 
 
HRESULT HookConference(INmConference * pConference) 
{ 
HRESULT hr; 
CConfNotify * pNotify; 
 
ASSERT(NULL != pConference); 
pConference->AddRef(); 
AddNode(pConference, &g_pListConference); 
 
    // Connect to the conference object 
    pNotify = new CConfNotify(); 
    if (NULL == pNotify) 
    { 
        hr = E_OUTOFMEMORY; 
        ERROR_MSG("Unable to allocate CConfNotify"); 
    } 
    else 
    { 
hr = pNotify->Connect(pConference); 
if (FAILED(hr)) 
{ 
TRACE_MSG("CConfNotify Failed (%s)", GetHrSz(hr)); 
pNotify->Release(); 
pNotify = NULL; 
} 
else 
{ 
TRACE_MSG("Conference Connection point established successfully"); 
AddNode(pNotify, &g_pListConferenceNotify); 
} 
} 
 
if (SUCCEEDED(hr)) 
{ 
UpdateStatusIcon(ICO_PHONE); 
} 
 
return hr; 
} 
 
 
//**************************************************************************** 
// 
// VOID FreeConferences(void) 
// 
//**************************************************************************** 
 
VOID FreeConferences(void) 
{ 
// Release all notify 
if (NULL != g_pListConferenceNotify) 
{ 
while (!g_pListConferenceNotify->IsEmpty()) 
{ 
CConfNotify * pNotify = (CConfNotify *) g_pListConferenceNotify->RemoveHead(); 
ASSERT(NULL != pNotify); 
OBJECT_MSG("[%08X] conference notify released", pNotify); 
pNotify->Disconnect(); 
pNotify->Release(); 
} 
} 
 
if (NULL != g_pListConference) 
{ 
while (!g_pListConference->IsEmpty()) 
{ 
INmConference * pConference = (INmConference *) g_pListConference->RemoveHead(); 
ASSERT(NULL != pConference); 
OBJECT_MSG("[%08X] conference released", pConference); 
pConference->Release(); 
} 
} 
 
UpdateStatusIcon(NULL); 
} 
 
 
//**************************************************************************** 
// 
// VOID DoConferenceCreate(void) 
// 
// Create a local conference object 
// 
//**************************************************************************** 
 
VOID DoConferenceCreate(void) 
{ 
HRESULT hr; 
INmConference * pConference; 
 
// Validate system 
if (NULL == g_pMgr) 
{ 
ERROR_MSG("No conference manager object"); 
return; 
} 
if (NULL != GetCurrentConference()) 
{ 
WARN_MSG("Attempting to create second conference"); 
} 
 
// Create Local Conference 
BSTRING bstrName(gPref.pszConferenceName); 
 
hr = g_pMgr->CreateConference(&pConference, bstrName, NULL, NMCH_ALL); 
if (SUCCEEDED(hr)) 
{ 
if (NULL != pConference) 
{ 
hr = pConference->Host(); 
if (FAILED(hr)) 
{ 
WARN_MSG("Failed to host conference"); 
} 
// Release here, because we always AddRef in INmManager.ConferenceCreated 
ASSERT(pConference == GetCurrentConference()); 
pConference->Release(); 
} 
TRACE_MSG("CreateConference succeeded"); 
} 
else 
{ 
ERROR_MSG("CreateConference failed HResult=%s", GetHrSz(hr)); 
} 
} 
 
 
//**************************************************************************** 
// 
// VOID DoConferenceLeave(void) 
// 
//**************************************************************************** 
 
VOID DoConferenceLeave(void) 
{ 
HRESULT hr; 
INmConference * pConference; 
 
pConference = GetCurrentConference(); 
if (NULL == pConference) 
{ 
ERROR_MSG("No conference object"); 
return; 
} 
 
hr = pConference->Leave(); 
if (FAILED(hr)) 
{ 
ERROR_MSG("Conference Leave hresult=%s", GetHrSz(hr)); 
} 
else 
{ 
TRACE_MSG("Conference Leave successful..."); 
} 
} 
 
 
//**************************************************************************** 
// 
// CLASS CConfNotify 
// 
//**************************************************************************** 
 
CConfNotify::CConfNotify() : RefCount(), CNotify() 
{ 
OBJECT_MSG("CConfNotify created"); 
} 
 
CConfNotify::~CConfNotify() 
{ 
OBJECT_MSG("CConfNotify destroyed"); 
} 
 
 
//**************************************************************************** 
// 
// Methods from IUknown 
// 
//**************************************************************************** 
 
ULONG STDMETHODCALLTYPE CConfNotify::AddRef(void) 
{ 
return RefCount::AddRef(); 
} 
 
 
ULONG STDMETHODCALLTYPE CConfNotify::Release(void) 
{ 
return RefCount::Release(); 
} 
 
HRESULT STDMETHODCALLTYPE CConfNotify::QueryInterface(REFIID riid, PVOID *ppvObject) 
{ 
HRESULT hr = S_OK; 
 
if (riid == IID_IUnknown) 
{ 
*ppvObject = (IUnknown *)this; 
OBJECT_MSG("CConfNotify::QueryInterface(): Returning IUnknown."); 
} 
else if (riid == IID_INmConferenceNotify) 
{ 
*ppvObject = (INmConferenceNotify *)this; 
OBJECT_MSG("CConfNotify::QueryInterface(): Returning INmConferenceNotify."); 
} 
else 
{ 
hr = E_NOINTERFACE; 
*ppvObject = NULL; 
OBJECT_MSG("CConfNotify::QueryInterface(): Called on unknown interface."); 
} 
 
if (S_OK == hr) 
{ 
AddRef(); 
} 
 
return hr; 
} 
 
 
//**************************************************************************** 
// 
// Methods from ICNotify 
// 
//**************************************************************************** 
 
HRESULT STDMETHODCALLTYPE CConfNotify::Connect(IUnknown *pUnk) 
{ 
return CNotify::Connect(pUnk, IID_INmConferenceNotify, (IUnknown *)this); 
} 
 
HRESULT STDMETHODCALLTYPE CConfNotify::Disconnect(void) 
{ 
return CNotify::Disconnect(); 
} 
 
 
//**************************************************************************** 
// 
// Methods from IConfNotify 
// 
//**************************************************************************** 
 
 
//**************************************************************************** 
// 
// HRESULT STDMETHODCALLTYPE CConfNotify::NmUI(CONFN uNotify) 
// 
//**************************************************************************** 
 
HRESULT STDMETHODCALLTYPE CConfNotify::NmUI(CONFN uNotify) 
{ 
LOG_MSG(RGB(255, 0, 255), "INmConference.NmUI CONFN=%s", GetConfnSz(uNotify)); 
return S_OK; 
} 
 
 
//**************************************************************************** 
// 
// HRESULT STDMETHODCALLTYPE CConfNotify::StateChanged(NM_CONFERENCE_STATE uState) 
// 
//**************************************************************************** 
 
HRESULT STDMETHODCALLTYPE CConfNotify::StateChanged(NM_CONFERENCE_STATE uState) 
{ 
NOTIFY_MSG("INmConference.StateChanged uState=%s", GetConferenceStateSz(uState)); 
 
switch (uState) 
{ 
case NM_CONFERENCE_ACTIVE: 
{ 
if (gPref.fAutoChat) 
{ 
DoCreateDataChannel(GetCurrentConference()); 
} 
break; 
} 
case NM_CONFERENCE_IDLE: 
{ 
FreeDataChannel(); 
FreeAllUsers(); 
FreeChannels(); 
break; 
} 
default: 
break; 
} /* switch (uState) */ 
 
return S_OK; 
} 
 
 
//**************************************************************************** 
// 
// HRESULT STDMETHODCALLTYPE CConfNotify::MemberChanged(NM_MEMBER_NOTIFY uNotify, INmMember *pMember) 
// 
//**************************************************************************** 
 
HRESULT STDMETHODCALLTYPE CConfNotify::MemberChanged(NM_MEMBER_NOTIFY uNotify, INmMember *pMember) 
{ 
NOTIFY_MSG("INmConference.MemberChanged uNotify=%d", uNotify); 
DumpMemberInfo(pMember); 
 
switch (uNotify) 
{ 
case NM_MEMBER_ADDED: 
AddMember(pMember); 
break; 
case NM_MEMBER_REMOVED: 
RemoveMember(pMember); 
break; 
default: 
break; 
} 
 
return S_OK; 
} 
 
 
//**************************************************************************** 
// 
// HRESULT STDMETHODCALLTYPE CConfNotify::ChannelChanged(NM_CHANNEL_NOTIFY uNotify, INmChannel *pChannel) 
// 
//**************************************************************************** 
 
HRESULT STDMETHODCALLTYPE CConfNotify::ChannelChanged(NM_CHANNEL_NOTIFY uNotify, INmChannel *pChannel) 
{ 
NOTIFY_MSG("INmConference.ChannelChanged uNotify=%d", uNotify); 
DumpChannelInfo(pChannel); 
 
switch (uNotify) 
{ 
case NM_CHANNEL_ADDED: 
HookChannel(pChannel); 
break; 
case NM_CHANNEL_REMOVED: 
UnHookChannel(pChannel); 
break; 
case NM_CHANNEL_UPDATED: 
UpdateChannelState(pChannel); 
break; 
default: 
break; 
} 
 
return S_OK; 
}