📄 olefont.c
字号:
}
/************************************************************************
* OLEFontImpl_IDispatch_AddRef (IUnknown)
*
* See Windows documentation for more details on IUnknown methods.
*/
static ULONG WINAPI OLEFontImpl_IDispatch_AddRef(
IDispatch* iface)
{
OLEFontImpl *this = impl_from_IDispatch(iface);
return IFont_AddRef((IFont *)this);
}
/************************************************************************
* OLEFontImpl_GetTypeInfoCount (IDispatch)
*
* See Windows documentation for more details on IDispatch methods.
*/
static HRESULT WINAPI OLEFontImpl_GetTypeInfoCount(
IDispatch* iface,
unsigned int* pctinfo)
{
OLEFontImpl *this = impl_from_IDispatch(iface);
FIXME("(%p)->(%p): Stub\n", this, pctinfo);
return E_NOTIMPL;
}
/************************************************************************
* OLEFontImpl_GetTypeInfo (IDispatch)
*
* See Windows documentation for more details on IDispatch methods.
*/
static HRESULT WINAPI OLEFontImpl_GetTypeInfo(
IDispatch* iface,
UINT iTInfo,
LCID lcid,
ITypeInfo** ppTInfo)
{
static const WCHAR stdole2tlb[] = {'s','t','d','o','l','e','2','.','t','l','b',0};
ITypeLib *tl;
HRESULT hres;
OLEFontImpl *this = impl_from_IDispatch(iface);
TRACE("(%p, iTInfo=%d, lcid=%04x, %p)\n", this, iTInfo, (int)lcid, ppTInfo);
if (iTInfo != 0)
return E_FAIL;
hres = LoadTypeLib(stdole2tlb, &tl);
if (FAILED(hres)) {
ERR("Could not load the stdole2.tlb?\n");
return hres;
}
hres = ITypeLib_GetTypeInfoOfGuid(tl, &IID_IFontDisp, ppTInfo);
if (FAILED(hres)) {
FIXME("Did not IDispatch typeinfo from typelib, hres %lx\n",hres);
}
return hres;
}
/************************************************************************
* OLEFontImpl_GetIDsOfNames (IDispatch)
*
* See Windows documentation for more details on IDispatch methods.
*/
static HRESULT WINAPI OLEFontImpl_GetIDsOfNames(
IDispatch* iface,
REFIID riid,
LPOLESTR* rgszNames,
UINT cNames,
LCID lcid,
DISPID* rgDispId)
{
OLEFontImpl *this = impl_from_IDispatch(iface);
FIXME("(%p,%s,%p,%d,%04x,%p), stub!\n", this, debugstr_guid(riid), rgszNames,
cNames, (int)lcid, rgDispId
);
return E_NOTIMPL;
}
/************************************************************************
* OLEFontImpl_Invoke (IDispatch)
*
* See Windows documentation for more details on IDispatch methods.
*
* Note: Do not call _put_Xxx methods, since setting things here
* should not call notify functions as I found out debugging the generic
* MS VB5 installer.
*/
static HRESULT WINAPI OLEFontImpl_Invoke(
IDispatch* iface,
DISPID dispIdMember,
REFIID riid,
LCID lcid,
WORD wFlags,
DISPPARAMS* pDispParams,
VARIANT* pVarResult,
EXCEPINFO* pExepInfo,
UINT* puArgErr)
{
OLEFontImpl *this = impl_from_IDispatch(iface);
OLEFontImpl *xthis = (OLEFontImpl*)this;
switch (dispIdMember) {
case DISPID_FONT_NAME:
switch (wFlags) {
case DISPATCH_PROPERTYGET:
case DISPATCH_PROPERTYGET|DISPATCH_METHOD:
V_VT(pVarResult) = VT_BSTR;
return OLEFontImpl_get_Name((IFont *)this, &V_BSTR(pVarResult));
case DISPATCH_PROPERTYPUT: {
BSTR name;
BOOL freename;
if (V_VT(&pDispParams->rgvarg[0]) == VT_DISPATCH) {
IFont *font;
HRESULT hr = S_OK;
hr = IUnknown_QueryInterface(V_DISPATCH(&pDispParams->rgvarg[0]), &IID_IFont, (void **) &font);
if (FAILED(hr))
{
FIXME("dispatch value for name property is not an OleFont, returning hr=0x%lx\n", hr);
return hr;
}
hr = IFont_get_Name(font, &name); /* this allocates a new BSTR so free it later */
if (FAILED(hr)) return hr;
IUnknown_Release(font);
freename = TRUE;
} else if (V_VT(&pDispParams->rgvarg[0]) == VT_BSTR) {
name = V_BSTR(&pDispParams->rgvarg[0]);
freename = FALSE;
} else {
FIXME("app is trying to set name property with a non BSTR, non dispatch value. returning E_FAIL\n");
return E_FAIL;
}
TRACE("name is %s\n", debugstr_w(name));
if (!xthis->description.lpstrName)
xthis->description.lpstrName = HeapAlloc(GetProcessHeap(), 0, (lstrlenW(name)+1) * sizeof(WCHAR));
else
xthis->description.lpstrName = HeapReAlloc(GetProcessHeap(), 0, xthis->description.lpstrName, (lstrlenW(name)+1) * sizeof(WCHAR));
if (xthis->description.lpstrName==0)
return E_OUTOFMEMORY;
strcpyW(xthis->description.lpstrName, name);
if (freename) SysFreeString(name);
return S_OK;
}
}
break;
case DISPID_FONT_BOLD:
switch (wFlags) {
case DISPATCH_PROPERTYGET:
case DISPATCH_PROPERTYGET|DISPATCH_METHOD:
V_VT(pVarResult) = VT_BOOL;
return OLEFontImpl_get_Bold((IFont *)this, (BOOL*)&V_BOOL(pVarResult));
case DISPATCH_PROPERTYPUT:
if (V_VT(&pDispParams->rgvarg[0]) != VT_BOOL) {
FIXME("DISPID_FONT_BOLD/put, vt is %d, not VT_BOOL.\n",V_VT(&pDispParams->rgvarg[0]));
return E_FAIL;
} else {
xthis->description.sWeight = V_BOOL(&pDispParams->rgvarg[0]) ? FW_BOLD : FW_NORMAL;
return S_OK;
}
}
break;
case DISPID_FONT_ITALIC:
switch (wFlags) {
case DISPATCH_PROPERTYGET:
case DISPATCH_PROPERTYGET|DISPATCH_METHOD:
V_VT(pVarResult) = VT_BOOL;
return OLEFontImpl_get_Italic((IFont *)this, (BOOL*)&V_BOOL(pVarResult));
case DISPATCH_PROPERTYPUT:
if (V_VT(&pDispParams->rgvarg[0]) != VT_BOOL) {
FIXME("DISPID_FONT_ITALIC/put, vt is %d, not VT_BOOL.\n",V_VT(&pDispParams->rgvarg[0]));
return E_FAIL;
} else {
xthis->description.fItalic = V_BOOL(&pDispParams->rgvarg[0]);
return S_OK;
}
}
break;
case DISPID_FONT_UNDER:
switch (wFlags) {
case DISPATCH_PROPERTYGET:
case DISPATCH_PROPERTYGET|DISPATCH_METHOD:
V_VT(pVarResult) = VT_BOOL;
return OLEFontImpl_get_Underline((IFont *)this, (BOOL*)&V_BOOL(pVarResult));
case DISPATCH_PROPERTYPUT:
if (V_VT(&pDispParams->rgvarg[0]) != VT_BOOL) {
FIXME("DISPID_FONT_UNDER/put, vt is %d, not VT_BOOL.\n",V_VT(&pDispParams->rgvarg[0]));
return E_FAIL;
} else {
xthis->description.fUnderline = V_BOOL(&pDispParams->rgvarg[0]);
return S_OK;
}
}
break;
case DISPID_FONT_STRIKE:
switch (wFlags) {
case DISPATCH_PROPERTYGET:
case DISPATCH_PROPERTYGET|DISPATCH_METHOD:
V_VT(pVarResult) = VT_BOOL;
return OLEFontImpl_get_Strikethrough((IFont *)this, (BOOL*)&V_BOOL(pVarResult));
case DISPATCH_PROPERTYPUT:
if (V_VT(&pDispParams->rgvarg[0]) != VT_BOOL) {
FIXME("DISPID_FONT_STRIKE/put, vt is %d, not VT_BOOL.\n",V_VT(&pDispParams->rgvarg[0]));
return E_FAIL;
} else {
xthis->description.fStrikethrough = V_BOOL(&pDispParams->rgvarg[0]);
return S_OK;
}
}
break;
case DISPID_FONT_SIZE:
switch (wFlags) {
case DISPATCH_PROPERTYPUT: {
assert (pDispParams->cArgs == 1);
xthis->description.cySize.s.Hi = 0;
if (V_VT(&pDispParams->rgvarg[0]) != VT_CY) {
if (V_VT(&pDispParams->rgvarg[0]) == VT_I2) {
xthis->description.cySize.s.Lo = V_I2(&pDispParams->rgvarg[0]) * 10000;
} else {
FIXME("property put for Size with vt %d unsupported!\n",V_VT(&pDispParams->rgvarg[0]));
}
} else {
xthis->description.cySize.s.Lo = V_CY(&pDispParams->rgvarg[0]).s.Lo;
}
return S_OK;
}
case DISPATCH_PROPERTYGET:
case DISPATCH_PROPERTYGET|DISPATCH_METHOD:
V_VT(pVarResult) = VT_CY;
return OLEFontImpl_get_Size((IFont *)this, &V_CY(pVarResult));
}
break;
case DISPID_FONT_CHARSET:
switch (wFlags) {
case DISPATCH_PROPERTYPUT:
assert (pDispParams->cArgs == 1);
if (V_VT(&pDispParams->rgvarg[0]) != VT_I2)
FIXME("varg of first disparg is not VT_I2, but %d\n",V_VT(&pDispParams->rgvarg[0]));
xthis->description.sCharset = V_I2(&pDispParams->rgvarg[0]);
return S_OK;
case DISPATCH_PROPERTYGET:
case DISPATCH_PROPERTYGET|DISPATCH_METHOD:
V_VT(pVarResult) = VT_I2;
return OLEFontImpl_get_Charset((IFont *)this, &V_I2(pVarResult));
}
break;
}
FIXME("%p->(%ld,%s,%lx,%x,%p,%p,%p,%p), unhandled dispid/flag!\n",
this,dispIdMember,debugstr_guid(riid),lcid,
wFlags,pDispParams,pVarResult,pExepInfo,puArgErr
);
return S_OK;
}
/************************************************************************
* OLEFontImpl_IPersistStream_QueryInterface (IUnknown)
*
* See Windows documentation for more details on IUnknown methods.
*/
static HRESULT WINAPI OLEFontImpl_IPersistStream_QueryInterface(
IPersistStream* iface,
REFIID riid,
VOID** ppvoid)
{
OLEFontImpl *this = impl_from_IPersistStream(iface);
return IFont_QueryInterface((IFont *)this, riid, ppvoid);
}
/************************************************************************
* OLEFontImpl_IPersistStream_Release (IUnknown)
*
* See Windows documentation for more details on IUnknown methods.
*/
static ULONG WINAPI OLEFontImpl_IPersistStream_Release(
IPersistStream* iface)
{
OLEFontImpl *this = impl_from_IPersistStream(iface);
return IFont_Release((IFont *)this);
}
/************************************************************************
* OLEFontImpl_IPersistStream_AddRef (IUnknown)
*
* See Windows documentation for more details on IUnknown methods.
*/
static ULONG WINAPI OLEFontImpl_IPersistStream_AddRef(
IPersistStream* iface)
{
OLEFontImpl *this = impl_from_IPersistStream(iface);
return IFont_AddRef((IFont *)this);
}
/************************************************************************
* OLEFontImpl_GetClassID (IPersistStream)
*
* See Windows documentation for more details on IPersistStream methods.
*/
static HRESULT WINAPI OLEFontImpl_GetClassID(
IPersistStream* iface,
CLSID* pClassID)
{
TRACE("(%p,%p)\n",iface,pClassID);
if (pClassID==0)
return E_POINTER;
memcpy(pClassID, &CLSID_StdFont, sizeof(CLSID_StdFont));
return S_OK;
}
/************************************************************************
* OLEFontImpl_IsDirty (IPersistStream)
*
* See Windows documentation for more details on IPersistStream methods.
*/
static HRESULT WINAPI OLEFontImpl_IsDirty(
IPersistStream* iface)
{
TRACE("(%p)\n",iface);
return S_OK;
}
/************************************************************************
* OLEFontImpl_Load (IPersistStream)
*
* See Windows documentation for more details on IPersistStream methods.
*
* This is the format of the standard font serialization as far as I
* know
*
* Offset Type Value Comment
* 0x0000 Byte Unknown Probably a version number, contains 0x01
* 0x0001 Short Charset Charset value from the FONTDESC structure
* 0x0003 Byte Attributes Flags defined as follows:
* 00000010 - Italic
* 00000100 - Underline
* 00001000 - Strikethrough
* 0x0004 Short Weight Weight value from FONTDESC structure
* 0x0006 DWORD size "Low" portion of the cySize member of the FONTDESC
* structure/
* 0x000A Byte name length Length of the font name string (no null character)
* 0x000B String name Name of the font (ASCII, no nul character)
*/
static HRESULT WINAPI OLEFontImpl_Load(
IPersistStream* iface,
IStream* pLoadStream)
{
char readBuffer[0x100];
ULONG cbRead;
BYTE bVersion;
BYTE bAttributes;
BYTE bStringSize;
INT len;
OLEFontImpl *this = impl_from_IPersistStream(iface);
/*
* Read the version byte
*/
IStream_Read(pLoadStream, &bVersion, 1, &cbRead);
if ( (cbRead!=1) ||
(bVersion!=0x01) )
return E_FAIL;
/*
* Charset
*/
IStream_Read(pLoadStream, &this->description.sCharset, 2, &cbRead);
if (cbRead!=2)
return E_FAIL;
/*
* Attributes
*/
IStream_Read(pLoadStream, &bAttributes, 1, &cbRead);
if (cbRead!=1)
return E_FAIL;
this->description.fItalic = (bAttributes & FONTPERSIST_ITALIC) != 0;
this->description.fStrikethrough = (bAttributes & FONTPERSIST_STRIKETHROUGH) != 0;
this->description.fUnderline = (bAttributes & FONTPERSIST_UNDERLINE) != 0;
/*
* Weight
*/
IStream_Read(pLoadStream, &this->description.sWeight, 2, &cbRead);
if (cbRead!=2)
return E_FAIL;
/*
* Size
*/
IStream_Read(pLoadStream, &this->description.cySize.s.Lo, 4, &cbRead);
if (cbRead!=4)
return E_FAIL;
this->description.cySize.s.Hi = 0;
/*
* FontName
*/
IStream_Read(pLoadStream, &bStringSize, 1, &cbRead);
if (cbRead!=1)
return E_FAIL;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -