306 lines
6.8 KiB
C++
306 lines
6.8 KiB
C++
//=============================================================================
|
|
// (c) Copyright Wang Laboratories, Inc. 1995 All rights reserved.
|
|
//-----------------------------------------------------------------------------
|
|
// File Name: occopy.cpp
|
|
// Component: CFontHolder - helper class for dealing with font objects
|
|
// Comment/Description:
|
|
//
|
|
//-----------------------------------------------------------------------------
|
|
// Maintenance Log:
|
|
/*
|
|
$Header: S:\norway\iedit95\occopy.cpv 1.2 18 Oct 1995 10:46:24 LMACLENNAN $
|
|
$Log: S:\norway\iedit95\occopy.cpv $
|
|
|
|
Rev 1.2 18 Oct 1995 10:46:24 LMACLENNAN
|
|
added version/comment header
|
|
|
|
Rev 1.1 10 Oct 1995 14:32:42 JPRATT
|
|
VC++ 4.0 updates
|
|
|
|
Rev 1.0 31 May 1995 09:28:26 MMB
|
|
Initial entry
|
|
*/
|
|
//=============================================================================
|
|
|
|
#include "stdafx.h"
|
|
#include "occopy.h"
|
|
|
|
#ifdef _DEBUG
|
|
#undef THIS_FILE
|
|
static char BASED_CODE THIS_FILE[] = __FILE__;
|
|
#endif
|
|
|
|
#define new DEBUG_NEW
|
|
|
|
BOOL AFXAPI IEditAfxConnectionAdvise(LPUNKNOWN pUnkSrc, REFIID iid,
|
|
LPUNKNOWN pUnkSink, BOOL bRefCount, DWORD FAR* pdwCookie)
|
|
{
|
|
IEDITASSERT_POINTER(pUnkSrc, IUnknown);
|
|
IEDITASSERT_POINTER(pUnkSink, IUnknown);
|
|
IEDITASSERT_POINTER(pdwCookie, DWORD);
|
|
|
|
BOOL bSuccess = FALSE;
|
|
|
|
LPCONNECTIONPOINTCONTAINER pCPC;
|
|
|
|
if (SUCCEEDED(pUnkSrc->QueryInterface(
|
|
IID_IConnectionPointContainer,
|
|
(LPVOID FAR*)&pCPC)))
|
|
{
|
|
IEDITASSERT_POINTER(pCPC, IConnectionPointContainer);
|
|
|
|
LPCONNECTIONPOINT pCP;
|
|
|
|
if (SUCCEEDED(pCPC->FindConnectionPoint(iid, &pCP)))
|
|
{
|
|
IEDITASSERT_POINTER(pCP, IConnectionPoint);
|
|
|
|
if (SUCCEEDED(pCP->Advise(pUnkSink, pdwCookie)))
|
|
bSuccess = TRUE;
|
|
|
|
pCP->Release();
|
|
|
|
// The connection point just AddRef'ed us. If we don't want to
|
|
// keep this reference count (because it would prevent us from
|
|
// being deleted; our reference count wouldn't go to zero), then
|
|
// we need to cancel the effects of the AddRef by calling
|
|
// Release.
|
|
|
|
if (bSuccess && !bRefCount)
|
|
pUnkSink->Release();
|
|
}
|
|
|
|
pCPC->Release();
|
|
}
|
|
|
|
return bSuccess;
|
|
}
|
|
|
|
|
|
/////////////////////////////////////////////////////////////////////////////
|
|
// AfxConnectionAdvise
|
|
|
|
BOOL AFXAPI IEditAfxConnectionUnadvise(LPUNKNOWN pUnkSrc, REFIID iid,
|
|
LPUNKNOWN pUnkSink, BOOL bRefCount, DWORD dwCookie)
|
|
{
|
|
IEDITASSERT_POINTER(pUnkSrc, IUnknown);
|
|
IEDITASSERT_POINTER(pUnkSink, IUnknown);
|
|
|
|
// When we call Unadvise, the connection point will Release us. If we
|
|
// didn't keep the reference count when we called Advise, we need to
|
|
// AddRef now, to keep our reference count consistent. Note that if
|
|
// the Unadvise fails, then we need to undo this extra AddRef by
|
|
// calling Release before we return.
|
|
|
|
if (!bRefCount)
|
|
pUnkSink->AddRef();
|
|
|
|
BOOL bSuccess = FALSE;
|
|
|
|
LPCONNECTIONPOINTCONTAINER pCPC;
|
|
|
|
if (SUCCEEDED(pUnkSrc->QueryInterface(
|
|
IID_IConnectionPointContainer,
|
|
(LPVOID FAR*)&pCPC)))
|
|
{
|
|
IEDITASSERT_POINTER(pCPC, IConnectionPointContainer);
|
|
|
|
LPCONNECTIONPOINT pCP;
|
|
|
|
if (SUCCEEDED(pCPC->FindConnectionPoint(iid, &pCP)))
|
|
{
|
|
IEDITASSERT_POINTER(pCP, IConnectionPoint);
|
|
|
|
if (SUCCEEDED(pCP->Unadvise(dwCookie)))
|
|
bSuccess = TRUE;
|
|
|
|
pCP->Release();
|
|
}
|
|
|
|
pCPC->Release();
|
|
}
|
|
|
|
// If we failed, undo the earlier AddRef.
|
|
|
|
if (!bRefCount && !bSuccess)
|
|
pUnkSink->Release();
|
|
|
|
return bSuccess;
|
|
}
|
|
|
|
/////////////////////////////////////////////////////////////////////////////
|
|
// CFontHolder
|
|
|
|
CFontHolder::CFontHolder(LPPROPERTYNOTIFYSINK pNotify) :
|
|
m_pFont(NULL),
|
|
m_dwConnectCookie(0),
|
|
m_pNotify(pNotify)
|
|
{
|
|
IEDITASSERT_NULL_OR_POINTER(pNotify, IPropertyNotifySink);
|
|
}
|
|
|
|
CFontHolder::~CFontHolder()
|
|
{
|
|
ReleaseFont();
|
|
}
|
|
|
|
void CFontHolder::ReleaseFont()
|
|
{
|
|
if ((m_pFont != NULL) && (m_pNotify != NULL))
|
|
{
|
|
// AfxConnectionUnadvise(m_pFont, IID_IPropertyNotifySink, m_pNotify,
|
|
// FALSE, m_dwConnectCookie);
|
|
}
|
|
|
|
IEDITRELEASE(m_pFont);
|
|
}
|
|
|
|
|
|
static const FONTDESC NEAR _fdDefault =
|
|
{ sizeof(FONTDESC), (LPOLESTR) _T("MS Sans Serif"), FONTSIZE(12), FW_NORMAL,
|
|
DEFAULT_CHARSET, FALSE, FALSE, FALSE };
|
|
|
|
|
|
void CFontHolder::InitializeFont(const FONTDESC FAR* pFontDesc,
|
|
LPDISPATCH pFontDispAmbient)
|
|
{
|
|
IEDITASSERT_NULL_OR_POINTER(pFontDesc, FONTDESC);
|
|
IEDITASSERT_NULL_OR_POINTER(pFontDispAmbient, IDispatch);
|
|
#ifdef _DEBUG
|
|
if (pFontDesc != NULL)
|
|
ASSERT(pFontDesc->cbSizeofstruct == sizeof(FONTDESC));
|
|
#endif
|
|
|
|
// Release any previous font, in preparation for creating a new one.
|
|
ReleaseFont();
|
|
|
|
LPFONT pFontAmbient;
|
|
LPFONT pFontNew = NULL;
|
|
|
|
if ((pFontDispAmbient != NULL) &&
|
|
SUCCEEDED(pFontDispAmbient->QueryInterface(IID_IFont,
|
|
(LPVOID FAR*)&pFontAmbient)))
|
|
{
|
|
IEDITASSERT_POINTER(pFontAmbient, IFont);
|
|
|
|
// Make a clone of the ambient font.
|
|
pFontAmbient->Clone(&pFontNew);
|
|
pFontAmbient->Release();
|
|
}
|
|
else
|
|
{
|
|
// Create the font.
|
|
if (pFontDesc == NULL)
|
|
pFontDesc = &_fdDefault;
|
|
|
|
if (FAILED(OleCreateFontIndirect((LPFONTDESC)pFontDesc, IID_IFont,
|
|
(LPVOID FAR *)&pFontNew)))
|
|
pFontNew = NULL;
|
|
}
|
|
|
|
// Setup advisory connection and find dispatch interface.
|
|
if (pFontNew != NULL)
|
|
SetFont(pFontNew);
|
|
}
|
|
|
|
HFONT CFontHolder::GetFontHandle()
|
|
{
|
|
// Assume a screen DC for logical/himetric ratio.
|
|
CDC dc;
|
|
dc.CreateCompatibleDC(NULL);
|
|
return ((HFONT)NULL); //miki
|
|
// return GetFontHandle((long)dc.GetDeviceCaps(LOGPIXELSY), HIMETRIC_PER_INCH);
|
|
}
|
|
|
|
HFONT CFontHolder::GetFontHandle(long cyLogical, long cyHimetric)
|
|
{
|
|
HFONT hFont = NULL;
|
|
|
|
if ((m_pFont != NULL) &&
|
|
SUCCEEDED(m_pFont->SetRatio(cyLogical, cyHimetric)) &&
|
|
SUCCEEDED(m_pFont->get_hFont(&hFont)))
|
|
{
|
|
ASSERT(hFont != NULL);
|
|
}
|
|
|
|
return hFont;
|
|
}
|
|
|
|
CFont* CFontHolder::Select(CDC* pDC, long cyLogical, long cyHimetric)
|
|
{
|
|
IEDITASSERT_POINTER(pDC, CDC);
|
|
|
|
HFONT hFont = NULL;
|
|
|
|
if (m_pFont != NULL)
|
|
hFont = GetFontHandle(cyLogical, cyHimetric);
|
|
|
|
if (hFont != NULL)
|
|
{
|
|
if ((pDC->m_hAttribDC != pDC->m_hDC) &&
|
|
(pDC->m_hAttribDC != NULL))
|
|
{
|
|
::SelectObject(pDC->m_hAttribDC, hFont);
|
|
}
|
|
|
|
return CFont::FromHandle((HFONT)::SelectObject(pDC->m_hDC, hFont));
|
|
}
|
|
|
|
return NULL;
|
|
}
|
|
|
|
|
|
void CFontHolder::QueryTextMetrics(LPTEXTMETRICOLE lptm)
|
|
{
|
|
ASSERT(lptm != NULL);
|
|
|
|
if (m_pFont != NULL)
|
|
{
|
|
m_pFont->QueryTextMetrics(lptm);
|
|
}
|
|
else
|
|
{
|
|
memset(lptm, 0, sizeof(TEXTMETRIC));
|
|
}
|
|
}
|
|
|
|
|
|
LPFONTDISP EXPORT CFontHolder::GetFontDispatch()
|
|
{
|
|
LPFONTDISP pFontDisp = NULL;
|
|
|
|
if ((m_pFont != NULL) &&
|
|
SUCCEEDED(m_pFont->QueryInterface(IID_IFontDisp, (LPVOID*)&pFontDisp)))
|
|
{
|
|
IEDITASSERT_POINTER(pFontDisp, IFontDisp);
|
|
}
|
|
|
|
return pFontDisp;
|
|
}
|
|
|
|
|
|
void EXPORT CFontHolder::SetFont(LPFONT pFontNew)
|
|
{
|
|
IEDITASSERT_NULL_OR_POINTER(pFontNew, IFont);
|
|
|
|
if (m_pFont != NULL)
|
|
ReleaseFont();
|
|
|
|
m_pFont = pFontNew;
|
|
|
|
if (m_pNotify != NULL)
|
|
{
|
|
// AfxConnectionAdvise(m_pFont, IID_IPropertyNotifySink, m_pNotify,
|
|
// FALSE, &m_dwConnectCookie);
|
|
}
|
|
}
|
|
|
|
|
|
BOOL EXPORT CFontHolder::GetDisplayString(CString& strValue)
|
|
{
|
|
return TRUE; //miki
|
|
// return strValue.LoadString(AFX_IDS_DISPLAYSTRING_FONT);
|
|
}
|
|
|
|
|