2025-11-28 00:35:46 +09:00

290 lines
6.9 KiB
C++

/**************************************************************************
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.
Copyright 2001 Microsoft Corporation. All Rights Reserved.
**************************************************************************/
/**************************************************************************
File: Monitor.cpp
Description:
**************************************************************************/
/**************************************************************************
#include statements
**************************************************************************/
#include "Monitor.h"
/**************************************************************************
global variables and definitions
**************************************************************************/
/**************************************************************************
CCompartmentMonitor::CCompartmentMonitor()
**************************************************************************/
CCompartmentMonitor::CCompartmentMonitor(void)
{
m_dwRef = 1;
m_dwCookie = 0;
m_pCompartment = NULL;
m_guidCompartment = GUID_NULL;
m_pCallback = NULL;
}
/**************************************************************************
CCompartmentMonitor::~CCompartmentMonitor()
**************************************************************************/
CCompartmentMonitor::~CCompartmentMonitor()
{
Uninitialize();
}
/**************************************************************************
CCompartmentMonitor::Initialize()
**************************************************************************/
HRESULT CCompartmentMonitor::Initialize( const GUID *pguidCompartment,
PCOMPARTMENTMONITORPROC pCallback,
LPARAM lParam)
{
if(!IsEqualGUID(m_guidCompartment, GUID_NULL))
{
//Initialize() has already been called
return E_UNEXPECTED;
}
m_guidCompartment = *pguidCompartment;
m_pCallback = pCallback;
m_lParam = lParam;
HRESULT hr;
ITfThreadMgr *pThreadMgr;
//create a thread manager object
hr = CoCreateInstance(CLSID_TF_ThreadMgr,
NULL,
CLSCTX_INPROC_SERVER,
IID_ITfThreadMgr,
(void**)&pThreadMgr);
if(SUCCEEDED(hr))
{
ITfCompartmentMgr *pCompMgr;
//get the global compartment manager
hr = pThreadMgr->GetGlobalCompartment(&pCompMgr);
if(SUCCEEDED(hr))
{
//get the Speech UI compartment
hr = pCompMgr->GetCompartment(m_guidCompartment,
&m_pCompartment);
if(SUCCEEDED(hr))
{
ITfSource *pSource;
//install the advise sink
hr = m_pCompartment->QueryInterface(IID_ITfSource,
(LPVOID*)&pSource);
if(SUCCEEDED(hr))
{
hr = pSource->AdviseSink(IID_ITfCompartmentEventSink,
(ITfCompartmentEventSink*)this,
&m_dwCookie);
}
//if something went wrong, release the member interface
if(FAILED(hr))
{
m_pCompartment->Release();
m_pCompartment = NULL;
}
}
//release the compartment manager
pCompMgr->Release();
}
//release the thread manager
pThreadMgr->Release();
}
return hr;
}
/**************************************************************************
CCompartmentMonitor::Uninitialize()
**************************************************************************/
HRESULT CCompartmentMonitor::Uninitialize(void)
{
HRESULT hr = S_OK;
if(m_pCompartment)
{
ITfSource *pSource;
hr = m_pCompartment->QueryInterface(IID_ITfSource, (void **)&pSource);
if(SUCCEEDED(hr))
{
hr = pSource->UnadviseSink(m_dwCookie);
pSource->Release();
}
m_pCompartment->Release();
m_pCompartment = NULL;
}
m_guidCompartment = GUID_NULL;
return hr;
}
//
// IUnknown
//
/**************************************************************************
CCompartmentMonitor::QueryInterface()
**************************************************************************/
STDAPI CCompartmentMonitor::QueryInterface(REFIID riid, void **ppvObj)
{
*ppvObj = NULL;
if (IsEqualIID(riid, IID_IUnknown) ||
IsEqualIID(riid, IID_ITfCompartmentEventSink))
{
*ppvObj = (ITfCompartmentEventSink*)this;
}
if (*ppvObj)
{
AddRef();
return S_OK;
}
return E_NOINTERFACE;
}
/**************************************************************************
CCompartmentMonitor::AddRef()
**************************************************************************/
STDAPI_(ULONG) CCompartmentMonitor::AddRef()
{
return ++m_dwRef;
}
/**************************************************************************
CCompartmentMonitor::Release()
**************************************************************************/
STDAPI_(ULONG) CCompartmentMonitor::Release()
{
m_dwRef--;
if(0 == m_dwRef)
{
delete this;
return 0;
}
return m_dwRef;
}
//
// ITfCompartmentEventSink
//
/**************************************************************************
CCompartmentMonitor::OnChange()
**************************************************************************/
STDAPI CCompartmentMonitor::OnChange(REFGUID rguid)
{
HRESULT hr = S_OK;
if(IsEqualGUID(rguid, m_guidCompartment))
{
GUID guid = m_guidCompartment;
BOOL fStatus;
GetStatus(&fStatus);
//notify the status of this compartment has changed
hr = (*m_pCallback)(&guid, fStatus, m_lParam);
}
return hr;
}
/**************************************************************************
CCompartmentMonitor::GetStatus()
**************************************************************************/
HRESULT CCompartmentMonitor::GetStatus(BOOL *pfEnabled)
{
if(NULL == pfEnabled)
{
return E_INVALIDARG;
}
if(!m_pCompartment)
{
return E_UNEXPECTED;
}
HRESULT hr;
VARIANT var;
VariantInit(&var);
hr = m_pCompartment->GetValue(&var);
if(S_OK == hr)
{
switch(var.vt)
{
case VT_I4:
*pfEnabled = var.lVal;
break;
}
VariantClear(&var);
}
else
{
//this usually means the text service is not installed
return E_UNEXPECTED;
}
return S_OK;
}