#include "private.h" #include "globals.h" #include "dispattr.h" #include "proputil.h" #include "catutil.h" #include "ctffunc.h" #include "helpers.h" #include "ciccs.h" extern CCicCriticalSectionStatic g_cs; CDispAttrPropCache *g_pPropCache = NULL; //+--------------------------------------------------------------------------- // // GetDAMLib // //---------------------------------------------------------------------------- ITfDisplayAttributeMgr *GetDAMLib(LIBTHREAD *plt) { return plt->_pDAM; } //+--------------------------------------------------------------------------- // // InitDisplayAttributeLib // //---------------------------------------------------------------------------- HRESULT InitDisplayAttrbuteLib(LIBTHREAD *plt) { IEnumGUID *pEnumProp = NULL; if ( plt == NULL ) return E_FAIL; if (plt->_pDAM) plt->_pDAM->Release(); plt->_pDAM = NULL; if (FAILED(g_pfnCoCreate(CLSID_TF_DisplayAttributeMgr, NULL, CLSCTX_INPROC_SERVER, IID_ITfDisplayAttributeMgr, (void**)&plt->_pDAM))) { return E_FAIL; } LibEnumItemsInCategory(plt, GUID_TFCAT_DISPLAYATTRIBUTEPROPERTY, &pEnumProp); HRESULT hr; EnterCriticalSection(g_cs); // // make a database for Display Attribute Properties. // if (pEnumProp && !g_pPropCache) { GUID guidProp; g_pPropCache = new CDispAttrPropCache; if (!g_pPropCache) { hr = E_OUTOFMEMORY; goto Exit; } // // add System Display Attribute first. // so no other Display Attribute property overwrite it. // g_pPropCache->Add(GUID_PROP_ATTRIBUTE); while(pEnumProp->Next(1, &guidProp, NULL) == S_OK) { if (!IsEqualGUID(guidProp, GUID_PROP_ATTRIBUTE)) g_pPropCache->Add(guidProp); } } hr = S_OK; Exit: LeaveCriticalSection(g_cs); SafeRelease(pEnumProp); return hr; } //+--------------------------------------------------------------------------- // // UninitDisplayAttributeLib // //---------------------------------------------------------------------------- HRESULT UninitDisplayAttrbuteLib(LIBTHREAD *plt) { Assert(plt); if ( plt == NULL ) return E_FAIL; if (plt->_pDAM) plt->_pDAM->Release(); plt->_pDAM = NULL; // if (plt->_fDAMCoInit) // CoUninitialize(); // // plt->_fDAMCoInit = FALSE; return S_OK; } //+--------------------------------------------------------------------------- // // GetDisplayAttributeTrackPropertyRange // //---------------------------------------------------------------------------- HRESULT GetDisplayAttributeTrackPropertyRange(TfEditCookie ec, ITfContext *pic, ITfRange *pRange, ITfReadOnlyProperty **ppProp, IEnumTfRanges **ppEnum, ULONG *pulNumProp) { ITfReadOnlyProperty *pProp = NULL; HRESULT hr = E_FAIL; GUID *pguidProp = NULL; const GUID **ppguidProp; ULONG ulNumProp = 0; ULONG i; EnterCriticalSection(g_cs); if (!g_pPropCache) goto Exit; pguidProp = g_pPropCache->GetPropTable(); if (!pguidProp) goto Exit; ulNumProp = g_pPropCache->Count(); if (!ulNumProp) goto Exit; // TrackProperties wants an array of GUID *'s if ((ppguidProp = (const GUID **)cicMemAlloc(sizeof(GUID *)*ulNumProp)) == NULL) { hr = E_OUTOFMEMORY; goto Exit; } for (i=0; iTrackProperties(ppguidProp, ulNumProp, 0, NULL, &pProp))) { hr = pProp->EnumRanges(ec, ppEnum, pRange); if (SUCCEEDED(hr)) { *ppProp = pProp; pProp->AddRef(); } pProp->Release(); } cicMemFree(ppguidProp); if (SUCCEEDED(hr)) *pulNumProp = ulNumProp; Exit: LeaveCriticalSection(g_cs); return hr; } //+--------------------------------------------------------------------------- // // GetDisplayAttributeData // //---------------------------------------------------------------------------- HRESULT GetDisplayAttributeData(LIBTHREAD *plt, TfEditCookie ec, ITfReadOnlyProperty *pProp, ITfRange *pRange, TF_DISPLAYATTRIBUTE *pda, TfGuidAtom *pguid, ULONG ulNumProp) { VARIANT var; IEnumTfPropertyValue *pEnumPropertyVal; TF_PROPERTYVAL tfPropVal; GUID guid; TfGuidAtom gaVal; ITfDisplayAttributeInfo *pDAI; HRESULT hr = E_FAIL; if (SUCCEEDED(pProp->GetValue(ec, pRange, &var))) { Assert(var.vt == VT_UNKNOWN); if (SUCCEEDED(var.punkVal->QueryInterface(IID_IEnumTfPropertyValue, (void **)&pEnumPropertyVal))) { while (pEnumPropertyVal->Next(1, &tfPropVal, NULL) == S_OK) { if (tfPropVal.varValue.vt == VT_EMPTY) continue; // prop has no value over this span Assert(tfPropVal.varValue.vt == VT_I4); // expecting GUIDATOMs gaVal = (TfGuidAtom)tfPropVal.varValue.lVal; GetGUIDFromGUIDATOM(plt, gaVal, &guid); if ((plt != NULL) && SUCCEEDED(plt->_pDAM->GetDisplayAttributeInfo(guid, &pDAI, NULL))) { // // Issue: for simple apps. // // Small apps can not show multi underline. So // this helper function returns only one // DISPLAYATTRIBUTE structure. // if (pda) { pDAI->GetAttributeInfo(pda); } if (pguid) { *pguid = gaVal; } pDAI->Release(); hr = S_OK; break; } } pEnumPropertyVal->Release(); } VariantClear(&var); } return hr; } //+--------------------------------------------------------------------------- // // GetAttributeColor // //---------------------------------------------------------------------------- HRESULT GetAttributeColor(TF_DA_COLOR *pdac, COLORREF *pcr) { switch (pdac->type) { case TF_CT_NONE: return S_FALSE; case TF_CT_SYSCOLOR: *pcr = GetSysColor(pdac->nIndex); break; case TF_CT_COLORREF: *pcr = pdac->cr; break; } return S_OK; } //+--------------------------------------------------------------------------- // // SetAttributeColor // //---------------------------------------------------------------------------- HRESULT SetAttributeColor(TF_DA_COLOR *pdac, COLORREF cr) { pdac->type = TF_CT_COLORREF; pdac->cr = cr; return S_OK; } //+--------------------------------------------------------------------------- // // SetAttributeSysColor // //---------------------------------------------------------------------------- HRESULT SetAttributeSysColor(TF_DA_COLOR *pdac, int nIndex) { pdac->type = TF_CT_SYSCOLOR; pdac->nIndex = nIndex; return S_OK; } //+--------------------------------------------------------------------------- // // ClearAttributeColor // //---------------------------------------------------------------------------- HRESULT ClearAttributeColor(TF_DA_COLOR *pdac) { pdac->type = TF_CT_NONE; pdac->nIndex = 0; return S_OK; } //+--------------------------------------------------------------------------- // // GetReconversionFromDisplayAttribute // //---------------------------------------------------------------------------- HRESULT GetReconversionFromDisplayAttribute(LIBTHREAD *plt, TfEditCookie ec, ITfThreadMgr *ptim, ITfContext *pic, ITfRange *pRange, ITfFnReconversion **ppReconv, ITfDisplayAttributeMgr *pDAM) { IEnumTfRanges *epr = NULL; ITfReadOnlyProperty *pProp; ITfRange *proprange; ULONG ulNumProp; HRESULT hr = E_FAIL; // // get an enumorator // if (FAILED(GetDisplayAttributeTrackPropertyRange(ec, pic, pRange, &pProp, &epr, &ulNumProp))) goto Exit; // // Get display attribute of the first proprange. // if (epr->Next(1, &proprange, NULL) == S_OK) { ITfRange *rangeTmp = NULL; TfGuidAtom guidatom; if (SUCCEEDED(GetDisplayAttributeData(plt, ec, pProp, proprange, NULL, &guidatom, ulNumProp))) { CLSID clsid; GUID guid; if (GetGUIDFromGUIDATOM(plt, guidatom, &guid) && SUCCEEDED(pDAM->GetDisplayAttributeInfo(guid, NULL, &clsid))) { ITfFunctionProvider *pFuncPrv; if (SUCCEEDED(ptim->GetFunctionProvider(clsid, &pFuncPrv))) { hr = pFuncPrv->GetFunction(GUID_NULL, IID_ITfFnReconversion, (IUnknown **)ppReconv); pFuncPrv->Release(); } } } proprange->Release(); } epr->Release(); pProp->Release(); Exit: return hr; }