Background Color for Outlook Property Page

P

paulmcd

Recently I was trying to get this working. I solved it. Here it is:

I used a great sample from here:

http://thecodeproject.com/wtl/ThemedDialog.asp#xx1149261xx

////////////////////////////////////////////////////////////////////////////
// Copyright : Amit Dey 2002
//
// Email :[email protected]
//
// This code may be used in compiled form in any way you desire. This
// file may be redistributed unmodified by any means PROVIDING it is
// not sold for profit without the authors written consent, and
// providing that this notice and the authors name is included.
//
// This file is provided 'as is' with no expressed or implied warranty.
// The author accepts no liability if it causes any damage to your
computer.
//
// Do expect bugs.
// Please let me know of any bugs/mods/improvements.
// and I will try to fix/incorporate them into this file.
// Enjoy!
//
// Description : Outlook2K Addin
////////////////////////////////////////////////////////////////////////////

// PropPage.h : Declaration of the CPropPage

#ifndef __PROPPAGE_H_
#define __PROPPAGE_H_

#include "resource.h" // main symbols
#include <atlctl.h>
#import "c:\src\loop.old\include\msoutl9.olb" raw_interfaces_only
#include <c:\src\loop.old\include\atlcontrols.h>
using namespace ATLControls;
/////////////////////////////////////////////////////////////////////////////
// CPropPage
class ATL_NO_VTABLE CPropPage :
public CComObjectRootEx<CComSingleThreadModel>,
public IDispatchImpl<IPropPage, &IID_IPropPage,
&LIBID_OUTLOOKADDINLib>,
public CComCompositeControl<CPropPage>,
public IPersistStreamInitImpl<CPropPage>,
public IOleControlImpl<CPropPage>,
public IOleObjectImpl<CPropPage>,
public IOleInPlaceActiveObjectImpl<CPropPage>,
public IViewObjectExImpl<CPropPage>,
public IOleInPlaceObjectWindowlessImpl<CPropPage>,
public IPersistStorageImpl<CPropPage>,
public ISpecifyPropertyPagesImpl<CPropPage>,
public IQuickActivateImpl<CPropPage>,
public IDataObjectImpl<CPropPage>,
public IProvideClassInfo2Impl<&CLSID_PropPage, NULL,
&LIBID_OUTLOOKADDINLib>,
public CComCoClass<CPropPage, &CLSID_PropPage>,
public IPersistPropertyBagImpl<CPropPage>,
public
IDispatchImpl<PropertyPage,&__uuidof(PropertyPage),&LIBID_OUTLOOKADDINLib>
{
public:
CPropPage()
{
m_bWindowOnly = TRUE;
CalcExtent(m_sizeExtent);
m_hBrush = NULL;
m_bThemeActive = FALSE;
}

DECLARE_REGISTRY_RESOURCEID(IDR_PROPPAGE)

DECLARE_PROTECT_FINAL_CONSTRUCT()

BEGIN_COM_MAP(CPropPage)
COM_INTERFACE_ENTRY(IPropPage)
COM_INTERFACE_ENTRY2(IDispatch,IPropPage)
COM_INTERFACE_ENTRY(IViewObjectEx)
COM_INTERFACE_ENTRY(IViewObject2)
COM_INTERFACE_ENTRY(IViewObject)
COM_INTERFACE_ENTRY(IOleInPlaceObjectWindowless)
COM_INTERFACE_ENTRY(IOleInPlaceObject)
COM_INTERFACE_ENTRY2(IOleWindow, IOleInPlaceObjectWindowless)
COM_INTERFACE_ENTRY(IOleInPlaceActiveObject)
COM_INTERFACE_ENTRY(IOleControl)
COM_INTERFACE_ENTRY(IOleObject)
COM_INTERFACE_ENTRY(IPersistStreamInit)
COM_INTERFACE_ENTRY2(IPersist, IPersistStreamInit)
COM_INTERFACE_ENTRY(ISpecifyPropertyPages)
COM_INTERFACE_ENTRY(IQuickActivate)
COM_INTERFACE_ENTRY(IPersistStorage)
COM_INTERFACE_ENTRY(IDataObject)
COM_INTERFACE_ENTRY(IProvideClassInfo)
COM_INTERFACE_ENTRY(IProvideClassInfo2)
COM_INTERFACE_ENTRY(IPersistPropertyBag)
COM_INTERFACE_ENTRY(Outlook::propertyPage)
END_COM_MAP()

BEGIN_PROP_MAP(CPropPage)
PROP_DATA_ENTRY("_cx", m_sizeExtent.cx, VT_UI4)
PROP_DATA_ENTRY("_cy", m_sizeExtent.cy, VT_UI4)
// Example entries
// PROP_ENTRY("Property Description", dispid, clsid)
// PROP_PAGE(CLSID_StockColorPage)
END_PROP_MAP()

BEGIN_MSG_MAP(CPropPage)
MESSAGE_HANDLER(WM_CTLCOLORSTATIC, OnCtlColor)
CHAIN_MSG_MAP(CComCompositeControl<CPropPage>)
MESSAGE_HANDLER(WM_INITDIALOG, OnInitDialog)
END_MSG_MAP()
// Handler prototypes:
// LRESULT MessageHandler(UINT uMsg, WPARAM wParam, LPARAM lParam,
BOOL& bHandled);
// LRESULT CommandHandler(WORD wNotifyCode, WORD wID, HWND hWndCtl,
BOOL& bHandled);
// LRESULT NotifyHandler(int idCtrl, LPNMHDR pnmh, BOOL& bHandled);

BEGIN_SINK_MAP(CPropPage)
//Make sure the Event Handlers have __stdcall calling convention
END_SINK_MAP()

STDMETHOD(GetControlInfo)(LPCONTROLINFO pCI);
STDMETHOD(SetClientSite)(IOleClientSite *pSite);

STDMETHOD(OnAmbientPropertyChange)(DISPID dispid)
{
if (dispid == DISPID_AMBIENT_BACKCOLOR)
{
SetBackgroundColorFromAmbient();
FireViewChange();
}
return IOleControlImpl<CPropPage>::OnAmbientPropertyChange(dispid);
}



// IViewObjectEx
DECLARE_VIEW_STATUS(0)

// IPropPage
public:

enum { IDD = IDD_PROPPAGE };
// PropertyPage
STDMETHOD(GetPageInfo)(BSTR * HelpFile, LONG * HelpContext);
STDMETHOD(get_Dirty)(VARIANT_BOOL * Dirty);
STDMETHOD(Apply)();



private:
CComVariant m_fDirty;
CComPtr<Outlook::propertyPageSite> m_pPropPageSite;


HBRUSH m_hBrush;
BOOL m_bThemeActive;
CWindow m_Control;

void UpdateBackgroundBrush()
{

m_bThemeActive = IsAppThemed();

// Destroy old brush
if (m_hBrush)
::DeleteObject(m_hBrush);

m_hBrush = NULL;

// Only do this if the theme is active
if (m_bThemeActive)
{
RECT rc;

// Get tab control dimensions
m_Control.GetWindowRect(&rc);

// Get the tab control DC
HDC hDC = m_Control.GetDC();

// Create a compatible DC
HDC hDCMem = ::CreateCompatibleDC(hDC);
HBITMAP hBmp = ::CreateCompatibleBitmap(hDC, rc.right - rc.left,
rc.bottom - rc.top);
HBITMAP hBmpOld = (HBITMAP):):SelectObject(hDCMem, hBmp));

// Tell the tab control to paint in our DC
m_Control.SendMessage(WM_PRINTCLIENT, (WPARAM)(hDCMem),
(LPARAM)(PRF_ERASEBKGND | PRF_CLIENT | PRF_NONCLIENT));

// Create a pattern brush from the bitmap selected in our DC
m_hBrush = ::CreatePatternBrush(hBmp);

// Restore the bitmap
::SelectObject(hDCMem, hBmpOld);

// Cleanup
::DeleteObject(hBmp);
::DeleteDC(hDCMem);
m_Control.ReleaseDC(hDC);
}
}


void test();


LRESULT OnInitDialog(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL&
bHandled)
{
HRESULT hr = EnableThemeDialogTexture(GetParent(),
ETDT_ENABLETAB);

m_Control = GetParent();
DrawThemeParentBackground(m_hWnd, (HDC)wParam, NULL);
UpdateBackgroundBrush();


return 0;
}


///////////////////////////////////////////////////////////////////////////////////////////////////////////
// Return the created background brush
//
LRESULT OnCtlColor(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& /*
bHandled */)
{
if (m_bThemeActive)
{
RECT rc;

// Set the background mode to transparent
::SetBkMode((HDC)(wParam), TRANSPARENT);

// Get the controls window dimensions
::GetWindowRect((HWND)(lParam), &rc);

// Map the coordinates to coordinates with the upper left corner of
dialog control as base
::MapWindowPoints(NULL, m_Control, (LPPOINT)(&rc), 2);

// Adjust the position of the brush for this control (else we see
the top left of the brush as background)
::SetBrushOrgEx((HDC)(wParam), -rc.left, -rc.top, NULL);

// Return the brush
return (LRESULT)(m_hBrush);
}

return FALSE;
}

};

#endif //__PROPPAGE_H_
 
M

Mark W via OfficeKB.com

Paul,

Just wanted to say thanks (although I have not tested the code yet). This was
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top