Click here to Skip to main content
15,891,951 members
Articles / Multimedia / DirectX

Rendering Text with Direct2D & DirectWrite

Rate me:
Please Sign up or sign in to vote.
4.94/5 (39 votes)
3 Jan 2015CPOL8 min read 106.5K   2.8K   76  
Direct2D, DirectWrite, Windows API, C++, std::shared_ptr and more
#pragma once
#ifndef __HWINHANDLE_H__
#define __HWINHANDLE_H__

#include "hwindef.h"
#include "hwinmessage.h"
#include "hwinobject.h"
#include "hwinlog.h"

namespace harlinn
{
    namespace windows
    {
        class Control;
        class ModuleHandle;
        class BitmapHandle;
        class IconHandle;
        class CursorHandle;
        class Menu;
        class Accelerator;
        class DeviceContextHandle;
        class BrushHandle;
        class PenHandle;
        class FontHandle;



        


        class Handle : public Object
        {
            friend class ModuleHandle;
            friend class BitmapHandle;
            friend class IconHandle;
            friend class CursorHandle;
            friend class Menu;
            friend class Accelerator;

            LPVOID value;
            bool ownsHandle;
        protected:
            Handle()
                : value(0), 
                ownsHandle(false)
            {
                HWIN_TRACE();
            }
        private:

            Handle(const Handle& theHandle)
                : value(theHandle.value), 
                ownsHandle(theHandle.ownsHandle)
            {
                HWIN_TRACE();
            }

            Handle(Handle&& theHandle)
                : value(theHandle.value), 
                ownsHandle(theHandle.ownsHandle)
            {
                HWIN_TRACE();
                theHandle.ownsHandle = false;
            }

            Handle& operator = (const Handle& theHandle)
            {
                HWIN_TRACE();
                return *this;
            }

            Handle& operator = (Handle&& theHandle)
            {
                HWIN_TRACE();
                return *this;
            }

        protected:
            
            Handle& SetValue(LPVOID theHandle, bool closeHandle = true) 
            { 
                HWIN_TRACE();
                value = theHandle;ownsHandle = closeHandle; return *this; 
            }
        public:
            typedef Object Base;
        protected:
            explicit Handle(LPVOID theHandle, bool closeHandle = true)
                : value(theHandle), 
                ownsHandle(closeHandle)
            {
                HWIN_TRACE();
            }

        public:
            virtual ~Handle()
            {
                HWIN_TRACE();
            }

            operator LPVOID() const
            {
                return value;
            }

            LPVOID Value() const 
            { 
                return value; 
            }

            bool OwnsHandle() const
            {
                return ownsHandle;
            }
        };


        class SystemHandle : public Handle
        {
        public:
            typedef Handle Base;
        protected:
            explicit SystemHandle(LPVOID theHandle, bool closeHandle = true)
                : Base(theHandle, closeHandle)
            {
                HWIN_TRACE();
            }
        protected:
            SystemHandle()
            {
                HWIN_TRACE();
            }
            
        public:
            bool IsValid()
            {
                return Value() != INVALID_HANDLE_VALUE;
            }
            HWIN_EXPORT virtual ~SystemHandle();


            operator HANDLE() const
            {
                HWIN_TRACE();
                return static_cast<HANDLE>(Value());
            }

            HANDLE GetHANDLE() const
            {
                HWIN_TRACE();
                return static_cast<HANDLE>(Value());
            }

        };


        class ModuleHandle : public Handle
        {
        public:
            typedef Handle Base;

            HWIN_EXPORT explicit ModuleHandle(HMODULE hModule, bool closeHandle = true);

            HWIN_EXPORT ModuleHandle(const wchar_t* theModuleName, DWORD flags = 0);
            HWIN_EXPORT ModuleHandle(const String& theModuleName, DWORD flags = 0);
            HWIN_EXPORT ModuleHandle(std::shared_ptr<String> theModuleName, DWORD flags = 0);

            HWIN_EXPORT virtual ~ModuleHandle();


            HWIN_EXPORT String GetModuleFileName() const;

            operator HMODULE() const
            {
                HWIN_TRACE();
                return static_cast<HMODULE>(Value());
            }

            HMODULE GetHMODULE() const
            {
                HWIN_TRACE();
                return static_cast<HMODULE>(Value());
            }


            HWIN_EXPORT static std::shared_ptr<ModuleHandle> Current();


        };


        class GraphicsDeviceObjectHandle : public Handle
        {
        public:
            typedef Handle Base;

        protected:
            HWIN_EXPORT GraphicsDeviceObjectHandle(HGDIOBJ theHandle, bool closeHandle = true);
            GraphicsDeviceObjectHandle() 
            {
                HWIN_TRACE();
            }

        };

        class BitmapHandle : public GraphicsDeviceObjectHandle
        {
            friend class DeviceContextHandle;
            typedef std::map<HBITMAP,BitmapHandle*> map_t;
            static map_t map;
            HWIN_EXPORT static void AddHandleToMap(HBITMAP hElement,BitmapHandle* theHandle);
            HWIN_EXPORT static BitmapHandle* GetHandleFromMap(HBITMAP hElement);
            HWIN_EXPORT static void RemoveHandleFromMap(HBITMAP hElement);
        public:
            typedef GraphicsDeviceObjectHandle Base;

            HWIN_EXPORT BitmapHandle(HBITMAP theHandle, bool ownsHandle = true);

            HWIN_EXPORT BitmapHandle(int resourceId, int width = 0, int height = 0,DWORD flags = LR_SHARED|LR_DEFAULTSIZE);

            HWIN_EXPORT BitmapHandle(const wchar_t* theBitmapName, int width = 0, int height = 0,DWORD flags = LR_SHARED|LR_DEFAULTSIZE);
            HWIN_EXPORT BitmapHandle(const String& theBitmapName, int width = 0, int height = 0,DWORD flags = LR_SHARED|LR_DEFAULTSIZE);
            HWIN_EXPORT BitmapHandle(std::shared_ptr<String> theBitmapName, int width = 0, int height = 0,DWORD flags = LR_SHARED|LR_DEFAULTSIZE);

            HWIN_EXPORT BitmapHandle(std::shared_ptr<ModuleHandle> theModule, int resourceId, int width = 0, int height = 0,DWORD flags = LR_SHARED|LR_DEFAULTSIZE);
            HWIN_EXPORT BitmapHandle(std::shared_ptr<ModuleHandle> theModule, const wchar_t* theBitmapName, int width = 0, int height = 0,DWORD flags = LR_SHARED|LR_DEFAULTSIZE);
            HWIN_EXPORT BitmapHandle(std::shared_ptr<ModuleHandle> theModule, const String& theBitmapName, int width = 0, int height = 0,DWORD flags = LR_SHARED|LR_DEFAULTSIZE);
            HWIN_EXPORT BitmapHandle(std::shared_ptr<ModuleHandle> theModule, std::shared_ptr<String> theBitmapName, int width = 0, int height = 0,DWORD flags = LR_SHARED|LR_DEFAULTSIZE);

            HWIN_EXPORT ~BitmapHandle();


            HWIN_EXPORT static std::shared_ptr<BitmapHandle> FromHandle(HBITMAP theHandle, bool ownsHandle = true);

            operator HBITMAP() const
            {
                HWIN_TRACE();
                return static_cast<HBITMAP>(Value());
            }

            HBITMAP GetHBITMAP() const
            {
                HWIN_TRACE();
                return static_cast<HBITMAP>(Value());
            }

            HWIN_EXPORT SIZE Size() const;

            HWIN_EXPORT static std::shared_ptr<BitmapHandle> LoadFromFile(const String& theFileMame);



        };

        class ImageListHandle;
        class IconHandle : public Handle
        {
        public:
            typedef Handle Base;

            HWIN_EXPORT static std::shared_ptr<IconHandle> Question;
            HWIN_EXPORT static std::shared_ptr<IconHandle> WinLogo;
            HWIN_EXPORT static std::shared_ptr<IconHandle> Warning;
            HWIN_EXPORT static std::shared_ptr<IconHandle> Error;
            HWIN_EXPORT static std::shared_ptr<IconHandle> Information;
            HWIN_EXPORT static std::shared_ptr<IconHandle> Shield;

            HWIN_EXPORT static std::shared_ptr<IconHandle> Question16x16;
            HWIN_EXPORT static std::shared_ptr<IconHandle> WinLogo16x16;
            HWIN_EXPORT static std::shared_ptr<IconHandle> Warning16x16;
            HWIN_EXPORT static std::shared_ptr<IconHandle> Error16x16;
            HWIN_EXPORT static std::shared_ptr<IconHandle> Information16x16;
            HWIN_EXPORT static std::shared_ptr<IconHandle> Shield16x16;

            HWIN_EXPORT static std::shared_ptr<IconHandle> Question24x24;
            HWIN_EXPORT static std::shared_ptr<IconHandle> WinLogo24x24;
            HWIN_EXPORT static std::shared_ptr<IconHandle> Warning24x24;
            HWIN_EXPORT static std::shared_ptr<IconHandle> Error24x24;
            HWIN_EXPORT static std::shared_ptr<IconHandle> Information24x24;
            HWIN_EXPORT static std::shared_ptr<IconHandle> Shield24x24;

            HWIN_EXPORT static std::shared_ptr<IconHandle> Question32x32;
            HWIN_EXPORT static std::shared_ptr<IconHandle> WinLogo32x32;
            HWIN_EXPORT static std::shared_ptr<IconHandle> Warning32x32;
            HWIN_EXPORT static std::shared_ptr<IconHandle> Error32x32;
            HWIN_EXPORT static std::shared_ptr<IconHandle> Information32x32;
            HWIN_EXPORT static std::shared_ptr<IconHandle> Shield32x32;

            HWIN_EXPORT explicit IconHandle(HICON hIcon, bool closeHandle = true);

            HWIN_EXPORT IconHandle(int resourceId, int width = 0, int height = 0,DWORD flags = LR_SHARED|LR_DEFAULTSIZE);

            HWIN_EXPORT IconHandle(const wchar_t* theIconName, int width = 0, int height = 0,DWORD flags = LR_SHARED|LR_DEFAULTSIZE);
            HWIN_EXPORT IconHandle(const String& theIconName, int width = 0, int height = 0,DWORD flags = LR_SHARED|LR_DEFAULTSIZE);
            HWIN_EXPORT IconHandle(std::shared_ptr<String> theIconName, int width = 0, int height = 0,DWORD flags = LR_SHARED|LR_DEFAULTSIZE);

            HWIN_EXPORT IconHandle(std::shared_ptr<ModuleHandle> theModule, int resourceId, int width = 0, int height = 0,DWORD flags = LR_SHARED|LR_DEFAULTSIZE);
            HWIN_EXPORT IconHandle(std::shared_ptr<ModuleHandle> theModule, const wchar_t* theIconName, int width = 0, int height = 0,DWORD flags = LR_SHARED|LR_DEFAULTSIZE);
            HWIN_EXPORT IconHandle(std::shared_ptr<ModuleHandle> theModule, const String& theIconName, int width = 0, int height = 0,DWORD flags = LR_SHARED|LR_DEFAULTSIZE);
            HWIN_EXPORT IconHandle(std::shared_ptr<ModuleHandle> theModule, std::shared_ptr<String> theIconName, int width = 0, int height = 0,DWORD flags = LR_SHARED|LR_DEFAULTSIZE);

            HWIN_EXPORT ~IconHandle();

            operator HICON() const
            {
                HWIN_TRACE();
                return static_cast<HICON>(Value());
            }

            HICON GetHICON() const
            {
                HWIN_TRACE();
                return static_cast<HICON>(Value());
            }


        };


        class CursorHandle : public Handle
        {
        public:
            typedef Handle Base;

            HWIN_EXPORT static std::shared_ptr<CursorHandle> Normal;
            HWIN_EXPORT static std::shared_ptr<CursorHandle> IBeam;
            HWIN_EXPORT static std::shared_ptr<CursorHandle> Wait;
            HWIN_EXPORT static std::shared_ptr<CursorHandle> Cross;
            HWIN_EXPORT static std::shared_ptr<CursorHandle> Up;
            HWIN_EXPORT static std::shared_ptr<CursorHandle> Size;
            HWIN_EXPORT static std::shared_ptr<CursorHandle> SizeNWSE;
            HWIN_EXPORT static std::shared_ptr<CursorHandle> SizeNESW;
            HWIN_EXPORT static std::shared_ptr<CursorHandle> SizeWE;
            HWIN_EXPORT static std::shared_ptr<CursorHandle> SizeNS;
            HWIN_EXPORT static std::shared_ptr<CursorHandle> No;
            HWIN_EXPORT static std::shared_ptr<CursorHandle> Hand;
            HWIN_EXPORT static std::shared_ptr<CursorHandle> AppStarting;


            HWIN_EXPORT CursorHandle(int resourceId, int width = 0, int height = 0,DWORD flags = LR_SHARED|LR_DEFAULTSIZE);

            HWIN_EXPORT CursorHandle(const wchar_t* theCursorName, int width = 0, int height = 0,DWORD flags = LR_SHARED|LR_DEFAULTSIZE);
            HWIN_EXPORT CursorHandle(const String& theCursorName, int width = 0, int height = 0,DWORD flags = LR_SHARED|LR_DEFAULTSIZE);
            HWIN_EXPORT CursorHandle(std::shared_ptr<String> theCursorName, int width = 0, int height = 0,DWORD flags = LR_SHARED|LR_DEFAULTSIZE);

            HWIN_EXPORT CursorHandle(std::shared_ptr<ModuleHandle> theModule, int resourceId, int width = 0, int height = 0,DWORD flags = LR_SHARED|LR_DEFAULTSIZE);
            HWIN_EXPORT CursorHandle(std::shared_ptr<ModuleHandle> theModule, const wchar_t* theCursorName, int width = 0, int height = 0,DWORD flags = LR_SHARED|LR_DEFAULTSIZE);
            HWIN_EXPORT CursorHandle(std::shared_ptr<ModuleHandle> theModule, const String& theCursorName, int width = 0, int height = 0,DWORD flags = LR_SHARED|LR_DEFAULTSIZE);
            HWIN_EXPORT CursorHandle(std::shared_ptr<ModuleHandle> theModule, std::shared_ptr<String> theCursorName, int width = 0, int height = 0,DWORD flags = LR_SHARED|LR_DEFAULTSIZE);

            HWIN_EXPORT ~CursorHandle();
            

            operator HCURSOR() const
            {
                HWIN_TRACE();
                return static_cast<HCURSOR>(Value());
            }

            HCURSOR GetHCURSOR() const
            {
                HWIN_TRACE();
                return static_cast<HCURSOR>(Value());
            }


        };


        class MenuHandle : public Handle
        {
        public:
            typedef Handle Base;

            HWIN_EXPORT MenuHandle(HMENU hMenu, bool ownsHandle = true);

            HWIN_EXPORT ~MenuHandle( );

            HWIN_EXPORT MenuHandle& AddStyle(DWORD style);

            HWIN_EXPORT MenuHandle& AppendMenu(UINT uFlags,UINT_PTR uIDNewItem,const wchar_t* newItem);
            HWIN_EXPORT MenuHandle& CheckMenuRadioItem(UINT idFirst,UINT idLast,UINT idCheck,UINT uFlags);
            HWIN_EXPORT MenuHandle& DeleteMenu(UINT position,UINT uFlags);
            HWIN_EXPORT MenuHandle& EnableMenuItem(UINT idOfItem, UINT enableFlags);
            HWIN_EXPORT static void EndMenu( );

            HWIN_EXPORT static long GetCheckMarkDimensions();

            HWIN_EXPORT UINT GetMenuDefaultItem(bool byPosition, UINT flags);

            HWIN_EXPORT const MenuHandle& GetMenuInfo(LPMENUINFO lpcmi) const;
            HWIN_EXPORT const MenuHandle& GetMenuInfo(MENUINFO& lpcmi) const;
            HWIN_EXPORT std::shared_ptr<MENUINFO> GetMenuInfo( ) const;

            HWIN_EXPORT int GetMenuItemCount( ) const;
            HWIN_EXPORT UINT GetMenuItemID(int menuItemPosition) const;

            HWIN_EXPORT const MenuHandle& GetMenuItemInfo(UINT itemIdOrPosition, bool byPosition,LPMENUITEMINFO lpmii) const;
            HWIN_EXPORT const MenuHandle& GetMenuItemInfo(UINT itemIdOrPosition, bool byPosition,MENUITEMINFO& lpmii) const;
            HWIN_EXPORT std::shared_ptr<MENUITEMINFO> GetMenuItemInfo(UINT itemIdOrPosition, bool byPosition) const;

            HWIN_EXPORT UINT GetMenuState(UINT itemIdOrPosition,bool byPosition) const;

            HWIN_EXPORT int GetMenuStringLength(UINT itemIdOrPosition,bool byPosition) const;
            HWIN_EXPORT int GetMenuString(UINT itemIdOrPosition,LPTSTR lpString,int nMaxCount,bool byPosition) const;
            HWIN_EXPORT std::shared_ptr<String> GetMenuString(UINT itemIdOrPosition,bool byPosition) const;

            HWIN_EXPORT HMENU GetSubMenu(int position) const;

            HWIN_EXPORT MenuHandle& InsertMenu(UINT uPosition,UINT uFlags, UINT_PTR itemIdOrPosition,LPCTSTR lpNewItem);
            HWIN_EXPORT MenuHandle& InsertMenuItem(UINT itemIdOrPosition,bool byPosition,LPCMENUITEMINFO lpmii);
            HWIN_EXPORT MenuHandle& InsertMenuItem(UINT itemIdOrPosition,bool byPosition,const MENUITEMINFO& lpmii);

            HWIN_EXPORT bool IsMenu() const;


            HWIN_EXPORT static std::shared_ptr<MenuHandle> LoadMenu(LPCTSTR lpMenuName);
            HWIN_EXPORT static std::shared_ptr<MenuHandle> LoadMenu(std::shared_ptr<ModuleHandle> module,LPCTSTR lpMenuName);
            HWIN_EXPORT static std::shared_ptr<MenuHandle> LoadMenu(HINSTANCE module,LPCTSTR lpMenuName);

            HWIN_EXPORT MenuHandle& ModifyMenu(UINT uPosition,UINT uFlags,UINT_PTR uIDNewItem,LPCTSTR lpNewItem);

            HWIN_EXPORT MenuHandle& RemoveMenu(UINT uPosition,UINT uFlags);

            HWIN_EXPORT MenuHandle& SetMenuDefaultItem(UINT itemIdOrPosition,bool byPosition);

            HWIN_EXPORT MenuHandle& SetMenuItemBitmaps(UINT itemIdOrPosition,bool byPosition,HBITMAP hBitmapUnchecked,HBITMAP hBitmapChecked);

            HWIN_EXPORT MenuHandle& SetMenuItemInfo(UINT uItem, BOOL fByPosition, LPMENUITEMINFO lpmii);
            HWIN_EXPORT MenuHandle& SetMenuInfo(LPCMENUINFO lpcmi);
            HWIN_EXPORT MenuHandle& SetMenuInfo(const MENUINFO& lpcmi);

            operator HMENU() const
            {
                HWIN_TRACE();
                return static_cast<HMENU>(Value());
            }

            HMENU GetHMENU() const
            {
                HWIN_TRACE();
                return static_cast<HMENU>(Value());
            }
        };


        enum class SysColor : int
        {
            ScrollBar         = 0,
            Desktop        = 1,
            ActiveCaption     = 2,
            InactiveCaption   = 3,
            Menu              = 4,
            Window            = 5,
            WindowFrame       = 6,
            MenuText          = 7,
            WindowText        = 8,
            ActiveCaptionText = 9,
            ActiveBorder      = 10,
            InactiveBorder    = 11,
            AppWorkspace      = 12,
            Highlight         = 13,
            HighlightText     = 14,
            ButtonFace        = 15,
            Control           = 15,
            ButtonShadow      = 16,
            ControlDark       = 16,
            GrayText          = 17,
            ControlText       = 18,
            InactiveCaptionText = 19,
            ControlLight      = 20,
            ButtonHighlight   = 20,
            ControlDarkDark   = 21,
            ControlLightLight = 22,
            InfoText          = 23,
            Info              = 24,
            HotTrack          = 26,
            GradientActiveCaption = 27,
            GradientInactiveCaption = 28,
            MenuHighlight       = 29,
            MenuBar           = 30
        };


        class ColorRef 
        {
            COLORREF color;
        public:
            inline ColorRef() : color(0) 
            {
                HWIN_TRACE();
            }
            inline ColorRef(BYTE r, BYTE g, BYTE b) : color(RGB(r,g,b)) 
            {
                HWIN_TRACE();
            }
            inline ColorRef(SysColor sysColor) : color( GetSysColor(int(sysColor)) ) 
            {
                HWIN_TRACE();
            }

            inline ColorRef(COLORREF colorref) : color( colorref ) 
            {
                HWIN_TRACE();
            }
            inline ColorRef(const ColorRef& colorref) : color( colorref ) 
            {
                HWIN_TRACE();
            }

            inline ColorRef& operator = (COLORREF colorref) 
            { 
                HWIN_TRACE();
                color =  colorref;
                return *this;
            }

            inline ColorRef& operator = (const ColorRef& colorref) 
            { 
                HWIN_TRACE();
                color =  colorref.color;
                return *this;
            }

            inline bool operator == (COLORREF colorref) const
            { 
                HWIN_TRACE();
                return color == colorref;
            }

            inline bool operator != (COLORREF colorref) const
            { 
                HWIN_TRACE();
                return color != colorref;
            }

            inline bool operator <= (COLORREF colorref) const
            { 
                HWIN_TRACE();
                return color <= colorref;
            }

            inline bool operator < (COLORREF colorref) const
            { 
                HWIN_TRACE();
                return color < colorref;
            }

            inline bool operator >= (COLORREF colorref) const
            { 
                HWIN_TRACE();
                return color >= colorref;
            }

            inline bool operator > (COLORREF colorref) const
            { 
                HWIN_TRACE();
                return color > colorref;
            }

            inline BYTE Red() const 
            { 
                HWIN_TRACE();
                return GetRValue(color); 
            }
            inline BYTE Green() const 
            { 
                HWIN_TRACE();
                return GetGValue(color); 
            }
            inline BYTE Blue() const 
            { 
                HWIN_TRACE();
                return GetBValue(color); 
            }

            inline operator COLORREF() const 
            { 
                HWIN_TRACE();
                return color; 
            }

            inline bool Invalid() const
            {
                HWIN_TRACE();
                return color == CLR_INVALID;
            }

        };

        enum class BrushStyle : UINT
        {
            Solid            = 0,
            Null             = 1,
            Hollow           = Null,
            Hatched          = 2,
            Pattern          = 3,
            Indexed          = 4,
            DibPattern       = 5,
            DibPatternPT     = 6,
            Pattern8X8       = 7,
            DibPattern8X8    = 8,
            MonoPattern      = 9
        };

        enum class HatchStyle : UINT
        {
            Horizontal       = 0,       /* ----- */
            Vertical         = 1,       /* ||||| */
            ForwardDiagonal  = 2,       /* \\\\\ */
            BackwardDiagonal = 3,       /* ///// */
            Cross            = 4,       /* +++++ */
            DiagonalCross    = 5        /* xxxxx */
        };

        enum class PenStyle : UINT
        {
            Solid            = 0,
            Dash             = 1,       /* -------  */
            Dot              = 2,       /* .......  */
            DashDot          = 3,       /* _._._._  */
            DashDotDot       = 4,       /* _.._.._  */
            Null             = 5,
            InsideFrame      = 6,
            UserStyle        = 7,
            Alternate        = 8
        };

        enum class PenEndCaps : UINT
        {
            Round     = 0x00000000,
            Square    = 0x00000100,
            Flat      = 0x00000200
        };

        enum class PenJoin : UINT
        {
            Round       = 0x00000000,
            Bevel       = 0x00001000,
            Miter       = 0x00002000
        };

        enum class PenType : UINT
        {
            Cosmetic         = 0x00000000,
            Geometric        = 0x00010000
        };



        class BrushHandle : public GraphicsDeviceObjectHandle
        {
            friend class DeviceContextHandle;
            typedef std::map<HBRUSH,BrushHandle*> map_t;
            static map_t map;
            HWIN_EXPORT static void AddHandleToMap(HBRUSH hElement,BrushHandle* theHandle);
            HWIN_EXPORT static BrushHandle* GetHandleFromMap(HBRUSH hElement);
            HWIN_EXPORT static void RemoveHandleFromMap(HBRUSH hElement);
        public:
            typedef GraphicsDeviceObjectHandle Base;
            HWIN_EXPORT BrushHandle(HBRUSH theHandle, bool ownsHandle = true);

            HWIN_EXPORT BrushHandle(const LOGBRUSH& theLogBrush);
            HWIN_EXPORT BrushHandle(std::shared_ptr<const LOGBRUSH> theLogBrush);
            HWIN_EXPORT explicit BrushHandle(COLORREF color);
            HWIN_EXPORT explicit BrushHandle(SysColor sysColor);


            HWIN_EXPORT ~BrushHandle( );

            operator HBRUSH() const
            {
                HWIN_TRACE();
                return static_cast<HBRUSH>(Value());
            }

            HBRUSH GetHBRUSH() const
            {
                HWIN_TRACE();
                return static_cast<HBRUSH>(Value());
            }
        };


        class PenHandle : public GraphicsDeviceObjectHandle
        {
            friend class DeviceContextHandle;
            typedef std::map<HPEN,PenHandle*> map_t;
            static map_t map;
            HWIN_EXPORT static void AddHandleToMap(HPEN hElement,PenHandle* theHandle);
            HWIN_EXPORT static PenHandle* GetHandleFromMap(HPEN hElement);
            HWIN_EXPORT static void RemoveHandleFromMap(HPEN hElement);
        public:
            typedef GraphicsDeviceObjectHandle Base;
            HWIN_EXPORT PenHandle(HPEN theHandle, bool ownsHandle = true);

            HWIN_EXPORT ~PenHandle( );

            operator HPEN() const
            {
                HWIN_TRACE();
                return static_cast<HPEN>(Value());
            }

            HPEN GetHPEN() const
            {
                HWIN_TRACE();
                return static_cast<HPEN>(Value());
            }
        };

        class FontHandle : public GraphicsDeviceObjectHandle
        {
            friend class DeviceContextHandle;
            typedef std::map<HFONT,FontHandle*> map_t;
            static map_t map;
            HWIN_EXPORT static void AddHandleToMap(HFONT hElement,FontHandle* theHandle);
            HWIN_EXPORT static FontHandle* GetHandleFromMap(HFONT hElement);
            HWIN_EXPORT static void RemoveHandleFromMap(HFONT hElement);
        public:
            typedef GraphicsDeviceObjectHandle Base;
            HWIN_EXPORT FontHandle(HFONT theHandle, bool ownsHandle = true);

            HWIN_EXPORT ~FontHandle( );

            operator HFONT() const
            {
                HWIN_TRACE();
                return static_cast<HFONT>(Value());
            }

            HFONT GetHFONT() const
            {
                HWIN_TRACE();
                return static_cast<HFONT>(Value());
            }
        };

        enum class RegionType : int
        {
            Error         = 0,
            Null          = 1,
            Simple        = 2,
            Complex       = 3
        };


        class RegionHandle : public GraphicsDeviceObjectHandle
        {
            friend class DeviceContextHandle;
            typedef std::map<HRGN,RegionHandle*> map_t;
            static map_t map;
            HWIN_EXPORT static void AddHandleToMap(HRGN hElement,RegionHandle* theHandle);
            HWIN_EXPORT static RegionHandle* GetHandleFromMap(HRGN hElement);
            HWIN_EXPORT static void RemoveHandleFromMap(HRGN hElement);
        public:
            typedef GraphicsDeviceObjectHandle Base;
            HWIN_EXPORT RegionHandle(HRGN theHandle, bool ownsHandle = true);

            HWIN_EXPORT ~RegionHandle( );

            operator HRGN() const
            {
                HWIN_TRACE();
                return static_cast<HRGN>(Value());
            }

            HRGN GetHRGN() const
            {
                HWIN_TRACE();
                return static_cast<HRGN>(Value());
            }
        };

        class PaletteHandle : public GraphicsDeviceObjectHandle
        {
            friend class DeviceContextHandle;
            typedef std::map<HPALETTE,PaletteHandle*> map_t;
            static map_t map;
            HWIN_EXPORT static void AddHandleToMap(HPALETTE hElement,PaletteHandle* theHandle);
            HWIN_EXPORT static PaletteHandle* GetHandleFromMap(HPALETTE hElement);
            HWIN_EXPORT static void RemoveHandleFromMap(HPALETTE hElement);
        public:
            typedef GraphicsDeviceObjectHandle Base;
            HWIN_EXPORT PaletteHandle(HPALETTE theHandle, bool ownsHandle = true);

            HWIN_EXPORT ~PaletteHandle( );

            operator HPALETTE() const
            {
                HWIN_TRACE();
                return static_cast<HPALETTE>(Value());
            }

            HPALETTE GetHPALETTE() const
            {
                HWIN_TRACE();
                return static_cast<HPALETTE>(Value());
            }
        };

#pragma pack(push,8)
        class Size;
        class Point
        {
            int x;
            int y;
        public:
            Point()
                : x(0),y(0)
            {
                HWIN_TRACE();
            }

            Point(int theXValue,int theYValue)
                : x(theXValue),y(theYValue)
            {
                HWIN_TRACE();
            }

            explicit Point(int theXYValue)
                : x(theXYValue),y(theXYValue)
            {
                HWIN_TRACE();
            }

            Point(const POINT& pt)
                : x(pt.x),y(pt.y)
            {
                HWIN_TRACE();
            }

            Point(const SIZE& size)
                : x(size.cx),y(size.cy)
            {
                HWIN_TRACE();
            }

            Point(const Point& pt)
                : x(pt.x),y(pt.y)
            {
                HWIN_TRACE();
            }


            Point(const Size& size);

            Point& operator = (const POINT& pt)
            {
                HWIN_TRACE();
                x = pt.x;
                y = pt.y;
                return *this;
            }

            Point& operator = (const SIZE& size)
            {
                HWIN_TRACE();
                x = size.cx;
                y = size.cy;
                return *this;
            }

            Point& operator = (const Size& size);


            Point& operator = (const Point& pt)
            {
                HWIN_TRACE();
                x = pt.x;
                y = pt.y;
                return *this;
            }


            int X() const 
            {
                HWIN_TRACE();
                return x;
            }
            Point& SetX(int theValue) 
            {
                HWIN_TRACE();
                x=theValue;
                return *this;
            }
            int Y() const 
            {
                HWIN_TRACE();
                return y;
            }
            Point& SetY(int theValue) 
            {
                HWIN_TRACE();
                y=theValue;
                return *this;
            }
            Point& Set(int theXValue,int theYValue) 
            {
                HWIN_TRACE();
                x=theXValue;
                y=theYValue;
                return *this;
            }

            operator POINT& () 
            { 
                HWIN_TRACE();
                return *((POINT*)&x); 
            }
            operator const POINT& () const 
            { 
                HWIN_TRACE();
                return *((POINT*)&x); 
            }


        };

        class Size
        {
            int width;
            int height;
        public:
            Size()
                : width(0),height(0)
            {
                HWIN_TRACE();
            }


            Size(int theWidth,int theHeight)
                : width(theWidth),height(theHeight)
            {
                HWIN_TRACE();
            }

            explicit Size(int theValue)
                : width(theValue),height(theValue)
            {
                HWIN_TRACE();
            }

            Size(const POINT& pt)
                : width(pt.x),height(pt.y)
            {
                HWIN_TRACE();
            }

            Size(const SIZE& size)
                : width(size.cx),height(size.cy)
            {
                HWIN_TRACE();
            }

            Size(const Point& pt)
                : width(pt.X()),height(pt.Y())
            {
                HWIN_TRACE();
            }


            Size(const Size& size)
                : width(size.width),height(size.height)
            {
                HWIN_TRACE();
            }

            Size& operator = (const SIZE& size)
            {
                HWIN_TRACE();
                width = size.cx;
                height = size.cy;
                return *this;
            }

            Size& operator = (const POINT& pt)
            {
                HWIN_TRACE();
                width = pt.x;
                height = pt.y;
                return *this;
            }

            Size& operator = (const Size& size)
            {
                HWIN_TRACE();
                width = size.width;
                height = size.height;
                return *this;
            }

            Size& operator = (const Point& pt)
            {
                HWIN_TRACE();
                width = pt.X();
                height = pt.Y();
                return *this;
            }

            int Width() const 
            {
                HWIN_TRACE();
                return width;
            }
            Size& SetWidth(int theWidth) 
            {
                HWIN_TRACE();
                width=theWidth;
                return *this;
            }
            int Height() const 
            {
                HWIN_TRACE();
                return height;
            }
            Size& SetHeight(int theValue) 
            {
                HWIN_TRACE();
                height=theValue;
                return *this;
            }
            Size& Set(int theWidth,int theHeight) 
            {
                HWIN_TRACE();
                width=theWidth;
                height=theHeight;
                return *this;
            }

            operator SIZE& () 
            { 
                HWIN_TRACE();
                return *((SIZE*)&width); 
            }
            operator const SIZE& () const 
            { 
                HWIN_TRACE();
                return *((SIZE*)&width); 
            }

        };

        inline Point::Point(const Size& size)
            : x(size.Width()),y(size.Height())
        {
            HWIN_TRACE();
        }

        inline Point& Point::operator = (const Size& size)
        {
            HWIN_TRACE();
            x = size.Width();
            y = size.Height();
            return *this;
        }


        class Rectangle
        {
            int left;
            int top;
            int right;
            int bottom;
        public:
            Rectangle()
                : left(0),top(0),right(0),bottom(0)
            {
                HWIN_TRACE();
            }

            Rectangle(const Rectangle& other)
                : left(other.left),top(other.top),right(other.right),bottom(other.bottom)
            {
                HWIN_TRACE();
            }

            Rectangle(const RECT& other)
                : left(other.left),top(other.top),right(other.right),bottom(other.bottom)
            {
                HWIN_TRACE();
            }

            Rectangle(const Point& position, const Size& size)
                : left(position.X()),top(position.Y()),right(position.X()+size.Width()),bottom(position.Y()+size.Height())
            {
                HWIN_TRACE();
            }

            Rectangle(const Size& size)
                : left(0),top(0),right(size.Width()),bottom(size.Height())
            {
                HWIN_TRACE();
            }


            explicit Rectangle(int size)
                : left(0),top(0),right(size),bottom(size)
            {
                HWIN_TRACE();
            }

            Rectangle& operator = (const Rectangle& other)
            {
                left = other.left;
                top = other.top;
                right = other.right;
                bottom = other.bottom;
                return *this;
            }

            Rectangle& operator = (const RECT& other)
            {
                left = other.left;
                top = other.top;
                right = other.right;
                bottom = other.bottom;
                return *this;
            }


            int X() const 
            {
                HWIN_TRACE();
                return left;
            }
            Rectangle& SetX(int theValue) 
            {
                HWIN_TRACE();
                left=theValue;
                return *this;
            }
            int Y() const 
            {
                HWIN_TRACE();
                return top;
            }
            Rectangle& SetY(int theValue) 
            {
                HWIN_TRACE();
                top=theValue;
                return *this;
            }

            int Width() const 
            {
                HWIN_TRACE();
                return labs(right-left);
            }
            Rectangle& SetWidth(int theWidth) 
            {
                HWIN_TRACE();
                right=left + theWidth;
                return *this;
            }
            int Height() const 
            {
                HWIN_TRACE();
                return labs(bottom - top);
            }
            Rectangle& SetHeight(int theValue) 
            {
                HWIN_TRACE();
                bottom=top+theValue;
                return *this;
            }


            int Left() const 
            {
                HWIN_TRACE();
                return left;
            }
            Rectangle& SetLeft(int theValue) 
            {
                HWIN_TRACE();
                left=theValue;
                return *this;
            }
            int Top() const 
            {
                HWIN_TRACE();
                return top;
            }
            Rectangle& SetTop(int theValue) 
            {
                HWIN_TRACE();
                top=theValue;
                return *this;
            }

            int Right() const 
            {
                HWIN_TRACE();
                return right;
            }
            Rectangle& SetRight(int theValue) 
            {
                HWIN_TRACE();
                right=theValue;
                return *this;
            }
            int Bottom() const 
            {
                HWIN_TRACE();
                return bottom;
            }
            Rectangle& SetBottom(int theValue) 
            {
                HWIN_TRACE();
                bottom=theValue;
                return *this;
            }

            Point Position() const
            {
                HWIN_TRACE();
                return Point(left,top);
            }

            Rectangle& SetPosition(const Point& pt)
            {
                HWIN_TRACE();
                int width = right-left;
                int height = bottom - top;
                left = pt.X();
                top = pt.Y();
                right = left + width;
                bottom = top + height;
                return *this;
            }

            Point LeftTop() const
            {
                HWIN_TRACE();
                return Point(left,top);
            }

            Rectangle& SetLeftTop(const Point& pt)
            {
                HWIN_TRACE();
                left = pt.X();
                top = pt.Y();
                return *this;
            }

            Rectangle& SetLeftTop(int theLeft, int theTop)
            {
                HWIN_TRACE();
                left = theLeft;
                top = theTop;
                return *this;
            }

            Point RightTop() const
            {
                HWIN_TRACE();
                return Point(right,top);
            }


            Rectangle& SetRightTop(const Point& pt)
            {
                HWIN_TRACE();
                right = pt.X();
                top = pt.Y();
                return *this;
            }

            Rectangle& SetRightTop(int theRight, int theTop)
            {
                HWIN_TRACE();
                right = theRight;
                top = theTop;
                return *this;
            }

            Point LeftBottom() const
            {
                HWIN_TRACE();
                return Point(left,bottom);
            }

            Rectangle& SetLeftBottom(const Point& pt)
            {
                HWIN_TRACE();
                left = pt.X();
                bottom = pt.Y();
                return *this;
            }

            Rectangle& SetLeftBottom(int theLeft, int theBottom)
            {
                HWIN_TRACE();
                left = theLeft;
                bottom = theBottom;
                return *this;
            }


            Point RightBottom() const
            {
                HWIN_TRACE();
                return Point(right,bottom);
            }

            Rectangle& SetRightBottom(const Point& pt)
            {
                HWIN_TRACE();
                right = pt.X();
                bottom = pt.Y();
                return *this;
            }

            Rectangle& SetRightBottom(int theRight, int theBottom)
            {
                HWIN_TRACE();
                right = theRight;
                bottom = theBottom;
                return *this;
            }

            Point Center() const
            {
                HWIN_TRACE();
                return Point((left+right)/2,(top+bottom)/2);
            }

            Rectangle& SetCenter(const Point& pt)
            {
                HWIN_TRACE();
                int width = (right-left);
                int height = (bottom - top);
                left = pt.X() - (width/2);
                top = pt.Y() - (height/2);
                right = left + width;
                bottom = top + height;
                return *this;
            }

            Point LeftCenter() const
            {
                HWIN_TRACE();
                return Point(left,(top+bottom)/2);
            }

            Point RightCenter() const
            {
                HWIN_TRACE();
                return Point(right,(top+bottom)/2);
            }

            Point TopCenter() const
            {
                HWIN_TRACE();
                return Point((left+right)/2,top);
            }

            Point BottomCenter() const
            {
                HWIN_TRACE();
                return Point((left+right)/2,bottom);
            }



            Size Size() const
            {
                HWIN_TRACE();
                return harlinn::windows::Size(labs(right - left),labs(bottom - top));
            }


            operator RECT& () 
            { 
                HWIN_TRACE();
                return *((RECT*)&left); 
            }
            operator const RECT& () const 
            { 
                HWIN_TRACE();
                return *((RECT*)&left); 
            }
        };
#pragma pack(pop)


        enum class DrawCaptionOptions : int
        {
            Active           = 0x0001,
            SmallCaption     = 0x0002,
            Icon             = 0x0004,
            Text             = 0x0008,
            InButton         = 0x0010,
            Gradient         = 0x0020,
            Buttons          = 0x1000
        };
        DEFINE_ENUM_FLAG_OPERATORS(DrawCaptionOptions)

        enum class ForegroundMixMode : int
        {
            Black            = 1,   /*  0       */
            NotMergePen      = 2,   /* DPon     */
            MaskNotPen       = 3,   /* DPna     */
            NotCopyPen       = 4,   /* PN       */
            MaskPenNot       = 5,   /* PDna     */
            Not              = 6,   /* Dn       */
            XorPen           = 7,   /* DPx      */
            NotMaskPen       = 8,   /* DPan     */
            MaskPen          = 9,   /* DPa      */
            NotXorPen        = 10,  /* DPxn     */
            Nop              = 11,  /* D        */
            MergeNotPen      = 12,  /* DPno     */
            CopyPen          = 13,  /* P        */
            MergePenNot      = 14,  /* PDno     */
            MergePen         = 15,  /* DPo      */
            White            = 16  /*  1       */
        };


        enum class BackgroundMixMode : int
        {
            Transparent         = 1,
            Opaque              = 2
        };

        enum class BorderStyle : UINT
        {
            RaisedOuter = 0x0001,
            SunkenOuter = 0x0002,
            RaisedInner = 0x0004,
            SunkenInner = 0x0008,
            Raised      = (BDR_RAISEDOUTER | BDR_RAISEDINNER),
            Sunken      = (BDR_SUNKENOUTER | BDR_SUNKENINNER),
            Etched      = (BDR_SUNKENOUTER | BDR_RAISEDINNER),
            Bump        = (BDR_RAISEDOUTER | BDR_SUNKENINNER)
        };
        DEFINE_ENUM_FLAG_OPERATORS(BorderStyle)

        enum class BorderFlags : UINT
        {
            Left         = 0x0001,
            Top          = 0x0002,
            Right        = 0x0004,
            Bottom       = 0x0008,

            TopLeft      = (BF_TOP | BF_LEFT),
            TopRight     = (BF_TOP | BF_RIGHT),
            BottomLeft   = (BF_BOTTOM | BF_LEFT),
            BottomRight  = (BF_BOTTOM | BF_RIGHT),
            Rectangle    = (BF_LEFT | BF_TOP | BF_RIGHT | BF_BOTTOM),

            Diagonal     = 0x0010,

            // For diagonal lines, the BF_RECT flags specify the end point of the
            // vector bounded by the rectangle parameter.
            DiagonalEndTopRight     = (BF_DIAGONAL | BF_TOP | BF_RIGHT),
            DiagonalEndTopLeft      = (BF_DIAGONAL | BF_TOP | BF_LEFT),
            DiagonalEndBottomLeft   = (BF_DIAGONAL | BF_BOTTOM | BF_LEFT),
            DiagonalEndBottomRight  = (BF_DIAGONAL | BF_BOTTOM | BF_RIGHT),


            Middle       = 0x0800,  /* Fill in the middle */
            Soft         = 0x1000,  /* For softer buttons */
            Adjust       = 0x2000,  /* Calculate the space left over */
            Flat         = 0x4000,  /* For flat rather than 3D borders */
            Mono         = 0x8000  /* For monochrome borders */
        };
        DEFINE_ENUM_FLAG_OPERATORS(BorderFlags)


        enum class DrawFrameControlType : UINT
        {
            Caption             = 1,
            MenuBar             = 2,
            ScrollBar           = 3,
            Button              = 4,
            PopupMenu           = 5
        };

        enum class DrawFrameControlCaptionPart
        {
            CloseButton       = 0x0000,
            MinimizeButton    = 0x0001,
            MaximizeButton    = 0x0002,
            RestoreButton     = 0x0003,
            HelpButton        = 0x0004
        };

        enum class DrawFrameControlMenuBarPart
        {
            Arrow          = 0x0000,
            Check          = 0x0001,
            Bullet         = 0x0002,
            ArrowRight     = 0x0004
        };


        enum class DrawFrameControlScrollBarPart
        {
            Up           = 0x0000,
            Down         = 0x0001,
            Left         = 0x0002,
            Right        = 0x0003,
            ComboBox     = 0x0005,
            SizeGrip     = 0x0008,
            SizeGripRight = 0x0010
        };

        enum class DrawFrameControlButtonOptions
        {
            CheckBox        = 0x0000,
            RadioImage      = 0x0001,
            RadioMask       = 0x0002,
            RadioButton     = 0x0004,
            ThreeState      = 0x0008,
            PushButton      = 0x0010
        };
        DEFINE_ENUM_FLAG_OPERATORS(DrawFrameControlButtonOptions)

        enum class DrawFrameControlPopupMenuPart
        {
            Arrow          = 0x0000,
            Check          = 0x0001,
            Bullet         = 0x0002,
            ArrowRight     = 0x0004
        };

        enum class DrawFrameControlOptions : UINT
        {
            None               = 0x0000,
            Inactive           = 0x0100,
            Pushed             = 0x0200,
            Checked            = 0x0400,
            Transparent        = 0x0800,
            HotTracked         = 0x1000,
            AdjustRectangle    = 0x2000,
            Flat               = 0x4000,
            Mono               = 0x8000
        };
        DEFINE_ENUM_FLAG_OPERATORS(DrawFrameControlOptions)

        enum class DrawStateFlags
        {
            Normal      = 0x0000,
            Prefix      = 0x0002,
            Dithered    = 0x0010,  /* Gray string appearance */
            Disabled    = 0x0020,
            Mono        = 0x0080,
            HidePrefix  = 0x0200,
            PrefixOnly  = 0x0400,
            Right       = 0x8000
        };
        DEFINE_ENUM_FLAG_OPERATORS(DrawStateFlags)


        enum class BoundsAccumulationFlags
        {
            Reset       = 0x0001,
            Accumulate  = 0x0002,
            Dirty       = DCB_ACCUMULATE,
            Set         = (DCB_RESET | DCB_ACCUMULATE),
            Enable      = 0x0004,
            Disable     = 0x0008
        };
        DEFINE_ENUM_FLAG_OPERATORS(BoundsAccumulationFlags)

        enum class ArcDirection
        {
            CounterClockwise = AD_COUNTERCLOCKWISE,
            Clockwise = AD_CLOCKWISE
        };

        enum class PolyDrawCommand : BYTE
        {
            CloseFigure = PT_CLOSEFIGURE,
            LineTo = PT_LINETO,
            LineToAndClose = PT_LINETO | PT_CLOSEFIGURE,
            BezierTo = PT_BEZIERTO,
            BezierToAndClose = PT_BEZIERTO | PT_CLOSEFIGURE,
            MoveTo = PT_MOVETO
        };
        DEFINE_ENUM_FLAG_OPERATORS(PolyDrawCommand)


        enum class DrawTextFlags : UINT
        {
            Top                      = 0x00000000,
            Left                     = 0x00000000,
            Center                   = 0x00000001,
            Right                    = 0x00000002,
            VCenter                  = 0x00000004,
            Bottom                   = 0x00000008,
            WordBreak                = 0x00000010,
            SingleLine               = 0x00000020,
            ExpandTabs               = 0x00000040,
            TabStop                  = 0x00000080,
            NoClip                   = 0x00000100,
            ExternalLeading          = 0x00000200,
            CalcRect                 = 0x00000400,
            NoPrefix                 = 0x00000800,
            Internal                 = 0x00001000,
            EditControl              = 0x00002000,
            PathEllipsis            = 0x00004000,
            EndEllipsis             = 0x00008000,
            ModifyString             = 0x00010000,
            RtlReading               = 0x00020000,
            WordEllipsis            = 0x00040000,
            NoFullWidthCharBreak     = 0x00080000,
            HidePrefix               = 0x00100000,
            PrefixOnly               = 0x00200000
        };
        DEFINE_ENUM_FLAG_OPERATORS(DrawTextFlags)

        enum class TextAlignment : UINT
        {
            NoUpdateCP                = 0,
            Left                      = 0,
            Top                       = 0,
            UpdateCP                  = 1,
            Right                     = 2,
            Center                    = 6,
            Bottom                    = 8,
            Baseline                  = 24,
            RtlReading                = 256
        };
        DEFINE_ENUM_FLAG_OPERATORS(TextAlignment)

        enum class GraphicsMode
        {
            Compatible = GM_COMPATIBLE,
            Advanced = GM_ADVANCED
        };


        enum class MapMode
        {
            Text             = 1,
            LoMetric         = 2,
            HiMetric         = 3,
            LoEnglish        = 4,
            HiEnglish        = 5,
            Twips            = 6,
            Isotropic        = 7,
            Anisotropic      = 8
        };


        enum class RasterOperation : DWORD
        {
            SourceCopy              = 0x00CC0020, /* dest = source                   */
            SourcePaint             = 0x00EE0086, /* dest = source OR dest           */
            SourceOrDestination     = 0x00EE0086, /* dest = source OR dest           */
            SourceAndDestination    = 0x008800C6, /* dest = source AND dest          */
            SourceInvert            = 0x00660046, /* dest = source XOR dest          */
            SourceXorDestination    = 0x00660046, /* dest = source XOR dest          */
            SourceErase             = 0x00440328, /* dest = source AND (NOT dest )   */
            SourceAndNotDestination   = 0x00440328, /* dest = source AND (NOT dest )   */
            NotSourceCopy           = 0x00330008, /* dest = (NOT source)             */
            NotSourceErase          = 0x001100A6, /* dest = (NOT src) AND (NOT dest) */
            NotSourceAndNotDestination = 0x001100A6, /* dest = (NOT src) AND (NOT dest) */
            MergeCopy               = 0x00C000CA, /* dest = (source AND pattern)     */
            MergePaint              = 0x00BB0226, /* dest = (NOT source) OR dest     */
            PatternCopy             = 0x00F00021, /* dest = pattern                  */
            PatternPaint            = 0x00FB0A09, /* dest = DPSnoo                   */
            PatternInvert           = 0x005A0049, /* dest = pattern XOR dest         */
            DestinationInvert       = 0x00550009, /* dest = (NOT dest)               */
            Blackness               = 0x00000042, /* dest = BLACK                    */
            Whiteness               = 0x00FF0062, /* dest = WHITE                    */
            NoMirrorBitmap          = 0x80000000, /* Do not Mirror the bitmap in this call */
            CaptureBlt              = 0x40000000 /* Include layered windows */
        };


        class DeviceContextHandle : public Handle
        {
            HPEN originalPen;
            HBRUSH originalBrush;
            HBITMAP originalBitmap;
            HFONT originalFont;
        protected: 
            HWIN_EXPORT DeviceContextHandle( );

            HWIN_EXPORT void SaveDefaultObjects();
            HWIN_EXPORT void RestoreDefaultObjects();

        public:
            typedef Handle Base;

            HWIN_EXPORT DeviceContextHandle(HDC theHandle, bool ownsHandle = true);

            HWIN_EXPORT ~DeviceContextHandle( );

            operator HDC() const
            {
                HWIN_TRACE();
                return static_cast<HDC>(Value());
            }

            HDC GetHDC() const
            {
                HWIN_TRACE();
                return static_cast<HDC>(Value());
            }

            HWIN_EXPORT std::shared_ptr<PenHandle> Pen() const;
            HWIN_EXPORT std::shared_ptr<PenHandle> SetPen(const std::shared_ptr<PenHandle>& newPen);

            HWIN_EXPORT std::shared_ptr<BrushHandle> Brush() const;
            HWIN_EXPORT std::shared_ptr<BrushHandle> SetBrush(const std::shared_ptr<BrushHandle>& newBrush);

            HWIN_EXPORT std::shared_ptr<BitmapHandle> Bitmap() const;
            HWIN_EXPORT std::shared_ptr<BitmapHandle> SetBitmap(const std::shared_ptr<BitmapHandle>& newBitmap);

            HWIN_EXPORT std::shared_ptr<FontHandle> Font() const;
            HWIN_EXPORT std::shared_ptr<FontHandle> SetFont(const std::shared_ptr<FontHandle>& newFont);


            HWIN_EXPORT DeviceContextHandle& DrawCaption(std::shared_ptr<Control> control, const RECT& boundingRectangle, DrawCaptionOptions options);

            HWIN_EXPORT DeviceContextHandle& DrawEdge(RECT& boundingRectangle, BorderStyle borderStyle, BorderFlags borderFlags );
            HWIN_EXPORT DeviceContextHandle& DrawFocusRect(RECT& boundingRectangle );

            HWIN_EXPORT DeviceContextHandle& DrawCaptionFrameControl(DrawFrameControlCaptionPart part, RECT& boundingRectangle, DrawFrameControlOptions options);
            HWIN_EXPORT DeviceContextHandle& DrawMenuBarFrameControl(DrawFrameControlMenuBarPart part, RECT& boundingRectangle, DrawFrameControlOptions options);
            HWIN_EXPORT DeviceContextHandle& DrawScrollBarFrameControl(DrawFrameControlScrollBarPart part, RECT& boundingRectangle, DrawFrameControlOptions options);
            HWIN_EXPORT DeviceContextHandle& DrawButtonFrameControl(DrawFrameControlButtonOptions buttonOptions, RECT& boundingRectangle, DrawFrameControlOptions options);
            HWIN_EXPORT DeviceContextHandle& DrawPopupMenuFrameControl(DrawFrameControlPopupMenuPart part, RECT& boundingRectangle, DrawFrameControlOptions options);


            HWIN_EXPORT DeviceContextHandle& DrawState(const String& theText, int x,int y,int cx,int cy,DrawStateFlags flags);
            HWIN_EXPORT DeviceContextHandle& DrawState(const String& theText, int x,int y,DrawStateFlags flags);

            HWIN_EXPORT DeviceContextHandle& DrawState(std::shared_ptr<BrushHandle> brush, const String& theText, int x,int y,int cx,int cy,DrawStateFlags flags);
            HWIN_EXPORT DeviceContextHandle& DrawState(std::shared_ptr<BrushHandle> brush, const String& theText, int x,int y,DrawStateFlags flags);

            HWIN_EXPORT DeviceContextHandle& DrawState(std::shared_ptr<BitmapHandle> bitmap, int x,int y,int cx,int cy,DrawStateFlags flags);
            HWIN_EXPORT DeviceContextHandle& DrawState(std::shared_ptr<BitmapHandle> bitmap, int x,int y,DrawStateFlags flags);
            HWIN_EXPORT DeviceContextHandle& DrawState(std::shared_ptr<IconHandle> icon, int x,int y,int cx,int cy,DrawStateFlags flags);
            HWIN_EXPORT DeviceContextHandle& DrawState(std::shared_ptr<IconHandle> icon, int x,int y,DrawStateFlags flags);


            HWIN_EXPORT RegionType ExcludeUpdateRgn(std::shared_ptr<Control> control);
            HWIN_EXPORT static void Flush();
            HWIN_EXPORT static DWORD BatchLimit();
            HWIN_EXPORT static DWORD SetBatchLimit(DWORD newBatchLimit);

            HWIN_EXPORT ColorRef BackgroundColor() const;
            HWIN_EXPORT ColorRef SetBackgroundColor(COLORREF color);

            HWIN_EXPORT harlinn::windows::BackgroundMixMode BackgroundMixMode() const;
            HWIN_EXPORT harlinn::windows::BackgroundMixMode SetBackgroundMixMode(harlinn::windows::BackgroundMixMode mixMode);

            HWIN_EXPORT BoundsAccumulationFlags BoundsRect(RECT& boundingRectangle) const;
            HWIN_EXPORT BoundsAccumulationFlags BoundsRect(RECT& boundingRectangle, bool clear);
            HWIN_EXPORT BoundsAccumulationFlags SetBoundsRect(const RECT& boundingRectangle, BoundsAccumulationFlags flags);

            HWIN_EXPORT harlinn::windows::ForegroundMixMode ForegroundMixMode() const;
            HWIN_EXPORT harlinn::windows::ForegroundMixMode SetForegroundMixMode(harlinn::windows::ForegroundMixMode mixMode);

            HWIN_EXPORT DeviceContextHandle& DrawGrayString(const String& theText,int X,int Y,int nWidth = 0,int nHeight = 0);
            HWIN_EXPORT DeviceContextHandle& DrawGrayString(std::shared_ptr<BrushHandle> brush,const String& theText,int X,int Y,int nWidth = 0,int nHeight = 0);

            HWIN_EXPORT DeviceContextHandle& DrawDesktopWallPaper();

            HWIN_EXPORT DeviceContextHandle& DrawChord(int nLeftRect,int nTopRect,int nRightRect,int nBottomRect,int nXRadial1,int nYRadial1,int nXRadial2,int nYRadial2);
            HWIN_EXPORT DeviceContextHandle& DrawChord(const RECT& rectangle,const POINT& start,const POINT& end);

            HWIN_EXPORT DeviceContextHandle& DrawEllipse(int nLeftRect,int nTopRect,int nRightRect,int nBottomRect);
            HWIN_EXPORT DeviceContextHandle& DrawEllipse(const RECT& rectangle);

            HWIN_EXPORT DeviceContextHandle& DrawFilledRectangle(int nLeftRect,int nTopRect,int nRightRect,int nBottomRect, std::shared_ptr<BrushHandle> brush);
            HWIN_EXPORT DeviceContextHandle& DrawFilledRectangle(const RECT& rectangle, std::shared_ptr<BrushHandle> brush);

            HWIN_EXPORT DeviceContextHandle& DrawFrameRectangle(int nLeftRect,int nTopRect,int nRightRect,int nBottomRect, std::shared_ptr<BrushHandle> brush);
            HWIN_EXPORT DeviceContextHandle& DrawFrameRectangle(const RECT& rectangle, std::shared_ptr<BrushHandle> brush);

            HWIN_EXPORT DeviceContextHandle& DrawInvertedRectangle(int nLeftRect,int nTopRect,int nRightRect,int nBottomRect);
            HWIN_EXPORT DeviceContextHandle& DrawInvertedRectangle(const RECT& rectangle);

            HWIN_EXPORT DeviceContextHandle& DrawPie(int nLeftRect,int nTopRect,int nRightRect,int nBottomRect,int nXRadial1,int nYRadial1,int nXRadial2,int nYRadial2);
            HWIN_EXPORT DeviceContextHandle& DrawPie(const RECT& rectangle,const POINT& start,const POINT& end);

            HWIN_EXPORT DeviceContextHandle& DrawPolygon(const POINT *lpPoints, int nCount);
            HWIN_EXPORT DeviceContextHandle& DrawPolygon(const std::vector<POINT>& points);
            HWIN_EXPORT DeviceContextHandle& DrawPolygon(std::shared_ptr<const std::vector<POINT> > polygon);

            HWIN_EXPORT DeviceContextHandle& DrawPolyPolygons(const std::vector< std::vector<POINT> >& polyPolygons);
            HWIN_EXPORT DeviceContextHandle& DrawPolyPolygon(const POINT *lpPoints,const INT *lpPolyCounts,int nCount);

            HWIN_EXPORT DeviceContextHandle& DrawRectangle(int nLeftRect,int nTopRect,int nRightRect,int nBottomRect);
            HWIN_EXPORT DeviceContextHandle& DrawRectangle(const RECT& rectangle);

            HWIN_EXPORT DeviceContextHandle& DrawRoundedRectangle(int nLeftRect,int nTopRect,int nRightRect,int nBottomRect,int nWidth,int nHeight);
            HWIN_EXPORT DeviceContextHandle& DrawRoundedRectangle(const RECT& rectangle,int nWidth,int nHeight);
            HWIN_EXPORT DeviceContextHandle& DrawRoundedRectangle(const RECT& rectangle,const SIZE& ellipseSize);

            HWIN_EXPORT DeviceContextHandle& DrawAngleArc(int X,int Y,DWORD dwRadius,FLOAT eStartAngle,FLOAT eSweepAngle);
            HWIN_EXPORT DeviceContextHandle& DrawAngleArc(const POINT& center,DWORD dwRadius,FLOAT eStartAngle,FLOAT eSweepAngle);

            HWIN_EXPORT DeviceContextHandle& DrawArc(int nLeftRect,int nTopRect,int nRightRect,int nBottomRect,int nXStartArc,int nYStartArc,int nXEndArc,int nYEndArc);
            HWIN_EXPORT DeviceContextHandle& DrawArc(const RECT& rectangle,const POINT& start,const POINT& end);

            HWIN_EXPORT harlinn::windows::ArcDirection ArcDirection() const;
            HWIN_EXPORT harlinn::windows::ArcDirection SetArcDirection(harlinn::windows::ArcDirection newArcDirection);

            HWIN_EXPORT DeviceContextHandle& DrawLineTo(int nXEnd,int nYEnd);
            HWIN_EXPORT DeviceContextHandle& DrawLineTo(const POINT& endPoint);

            HWIN_EXPORT DeviceContextHandle& MoveTo(int newX,int newY);
            HWIN_EXPORT DeviceContextHandle& MoveTo(int newX,int newY, int& previousX, int& previousY );
            HWIN_EXPORT DeviceContextHandle& MoveTo(const POINT& newPosition);
            HWIN_EXPORT DeviceContextHandle& MoveTo(const POINT& newPosition, POINT& previousPosition);

            HWIN_EXPORT DeviceContextHandle& DrawPolyBezier(const POINT *lppt,DWORD cPoints);
            HWIN_EXPORT DeviceContextHandle& DrawPolyBezier(const std::vector<POINT>& points);
            HWIN_EXPORT DeviceContextHandle& DrawPolyBezier(std::shared_ptr<const std::vector<POINT> > points);

            HWIN_EXPORT DeviceContextHandle& DrawPolyBezierTo(const POINT *lppt,DWORD cPoints);
            HWIN_EXPORT DeviceContextHandle& DrawPolyBezierTo(const std::vector<POINT>& points);
            HWIN_EXPORT DeviceContextHandle& DrawPolyBezierTo(std::shared_ptr<const std::vector<POINT> > points);

            HWIN_EXPORT DeviceContextHandle& Draw(const POINT *lppt,const PolyDrawCommand *lpbTypes,int cCount);

            HWIN_EXPORT DeviceContextHandle& DrawPolyLine(const POINT *lppt,DWORD cPoints);
            HWIN_EXPORT DeviceContextHandle& DrawPolyLine(const std::vector<POINT>& points);
            HWIN_EXPORT DeviceContextHandle& DrawPolyLine(std::shared_ptr<const std::vector<POINT> > points);

            HWIN_EXPORT DeviceContextHandle& DrawPolyLineTo(const POINT *lppt,DWORD cPoints);
            HWIN_EXPORT DeviceContextHandle& DrawPolyLineTo(const std::vector<POINT>& points);
            HWIN_EXPORT DeviceContextHandle& DrawPolyLineTo(std::shared_ptr<const std::vector<POINT> > points);

            HWIN_EXPORT ColorRef TextColor() const;
            HWIN_EXPORT ColorRef SetTextColor(COLORREF colorRef);


            HWIN_EXPORT harlinn::windows::TextAlignment TextAlignment() const;
            HWIN_EXPORT harlinn::windows::TextAlignment SetTextAlignment(harlinn::windows::TextAlignment textAlignment);


            HWIN_EXPORT int DrawText(const String& theText,RECT& rect, DrawTextFlags uFormat);
            HWIN_EXPORT int DrawText(LPCTSTR lpchText,int nCount,RECT& rect, DrawTextFlags uFormat);
            HWIN_EXPORT int DrawText(LPWSTR lpchText,int nCount,RECT& rect, DrawTextFlags uFormat, DRAWTEXTPARAMS& drawTextParams);
            HWIN_EXPORT DeviceContextHandle& DrawText(int nXStart,int nYStart,LPCTSTR lpString,int cchString);
            HWIN_EXPORT DeviceContextHandle& DrawText(int nXStart,int nYStart,const String& theText);
            HWIN_EXPORT DeviceContextHandle& DrawText(const POINT& startPosition,const String& theText);
            HWIN_EXPORT SIZE DrawText(int X, int Y,LPCTSTR lpString, int nCount, int nTabPositions, const LPINT lpnTabStopPositions, int nTabOrigin);
            HWIN_EXPORT DeviceContextHandle& DrawText(int X,int Y, UINT fuOptions, const RECT *lprc, LPCTSTR lpString, UINT cbCount, const INT *lpDx);

            HWIN_EXPORT POINT CurrentPosition() const;
            HWIN_EXPORT const DeviceContextHandle& CurrentPosition(POINT& currentPosition) const;

            HWIN_EXPORT harlinn::windows::GraphicsMode GraphicsMode() const;
            HWIN_EXPORT harlinn::windows::GraphicsMode SetGraphicsMode(harlinn::windows::GraphicsMode newGraphicsMode);

            HWIN_EXPORT harlinn::windows::MapMode MapMode() const;
            HWIN_EXPORT harlinn::windows::MapMode SetMapMode(harlinn::windows::MapMode newMapMode);

            HWIN_EXPORT SIZE ViewportExtent() const;
            HWIN_EXPORT SIZE SetViewportExtent(const SIZE& newViewportExtent );
            HWIN_EXPORT SIZE ScaleViewportExtent(int Xnum,int Xdenom,int Ynum,int Ydenom);

            HWIN_EXPORT POINT ViewportOrigin() const;
            HWIN_EXPORT POINT SetViewportOrigin(const POINT& newViewportOrigin);
            HWIN_EXPORT POINT OffsetViewportOrigin(int xOffset, int yOffset);

            HWIN_EXPORT SIZE WindowExtent() const;
            HWIN_EXPORT SIZE SetWindowExtent(const SIZE& newWindowExtent );
            HWIN_EXPORT SIZE ScaleWindowExtent(int Xnum,int Xdenom,int Ynum,int Ydenom);

            HWIN_EXPORT POINT WindowOrigin() const;
            HWIN_EXPORT POINT SetWindowOrigin(const POINT& newWindowOrigin);
            HWIN_EXPORT POINT OffsetWindowOrigin(int xOffset, int yOffset);

            HWIN_EXPORT const DeviceContextHandle& WorldTransform(XFORM& xform) const;
            HWIN_EXPORT XFORM WorldTransform( ) const;

            HWIN_EXPORT DeviceContextHandle& SetWorldTransform(XFORM& xform);

            HWIN_EXPORT DeviceContextHandle& ModifyWorldTransform(const XFORM& xform, bool rightMultiply = false);
            HWIN_EXPORT DeviceContextHandle& ResetWorldTransform( );


            HWIN_EXPORT DeviceContextHandle& DrawBitmap(std::shared_ptr<BitmapHandle> bitmap);
            HWIN_EXPORT DeviceContextHandle& DrawBitmap(std::shared_ptr<BitmapHandle> bitmap, const POINT& position);
            HWIN_EXPORT DeviceContextHandle& DrawBitmap(std::shared_ptr<BitmapHandle> bitmap, const POINT& position, const SIZE size);

            HWIN_EXPORT DeviceContextHandle& DrawBitmap(std::shared_ptr<DeviceContextHandle> source);
            HWIN_EXPORT DeviceContextHandle& DrawBitmap(std::shared_ptr<DeviceContextHandle> source, const POINT& position);
            HWIN_EXPORT DeviceContextHandle& DrawBitmap(std::shared_ptr<DeviceContextHandle> source, const POINT& position, const SIZE size);



        };


        enum class WindowDeviceContextFlags : int
        {
            // Returns a DeviceContext that corresponds to the window 
            // rectangle rather than the client rectangle.
            Window           = 0x00000001L,
            // Returns a DeviceContext  from the cache, rather than the OWNDC or 
            // CLASSDC window. Essentially overrides CS_OWNDC and CS_CLASSDC
            Cache            = 0x00000002L,
            // Does not reset the attributes of this DeviceContext  to the 
            // default attributes when this DC is released.
            NoResetAttributes = 0x00000004L,
            // Excludes the visible regions of all child windows 
            // below the window identified by hWnd.
            ClipChildren     = 0x00000008L,
            // Excludes the visible regions of all sibling windows above 
            // the window identified by hWnd
            ClipSiblings     = 0x00000010L,
            // Uses the visible region of the parent window. The parent's 
            // WS_CLIPCHILDREN and CS_PARENTDC style bits are ignored. The origin is 
            // set to the upper-left corner of the window identified by hWnd.
            ParentClip       = 0x00000020L,
            // The clipping region identified by hrgnClip is excluded from 
            // the visible region of the returned DeviceContext.
            ExcludeRegion    = 0x00000040L,
            // The clipping region identified by hrgnClip is intersected with the 
            // visible region of the returned DeviceContext
            IntersectRegion  = 0x00000080L,

            ExcludeUpdate    = 0x00000100L,
            //IntersectUpdate  = 0x00000200L,

            // Allows drawing even if there is a LockWindowUpdate call in effect that would 
            // otherwise exclude this window. Used for drawing during tracking.
            LockWindowUpdate = 0x00000400L,
            //Validate         = 0x00200000L
        };

        class WindowDeviceContextHandle : public DeviceContextHandle
        {
            
        public:
            typedef DeviceContextHandle Base;
        };


        class PaintDeviceContextHandle : public DeviceContextHandle
        {
            PAINTSTRUCT paintStruct;
            HWND windowHandle;
        public:
            typedef DeviceContextHandle Base;

            HWIN_EXPORT PaintDeviceContextHandle(const std::shared_ptr<Control> theControl);
            HWIN_EXPORT PaintDeviceContextHandle(HWND hWnd);

            HWIN_EXPORT virtual ~PaintDeviceContextHandle();
        };


        class MemoryDeviceContextHandle : public DeviceContextHandle
        {
        public:
            typedef DeviceContextHandle Base;

            HWIN_EXPORT MemoryDeviceContextHandle(std::shared_ptr<DeviceContextHandle> deviceContext);
            HWIN_EXPORT MemoryDeviceContextHandle(std::shared_ptr<DeviceContextHandle> deviceContext, std::shared_ptr<BitmapHandle> theBitmap);
            HWIN_EXPORT virtual ~MemoryDeviceContextHandle();

        };




        /*
        class Accelerator : public Handle
        {
        public:
            typedef Handle Base;

        };*/


        class BitmapSelection
        {
            std::shared_ptr<DeviceContextHandle> deviceContext;
            std::shared_ptr<BitmapHandle> previouslySelectedBitmap;
        public:
            BitmapSelection(std::shared_ptr<DeviceContextHandle> theDeviceContext, std::shared_ptr<BitmapHandle> theBitmap)
                : deviceContext(theDeviceContext)
            {
                HWIN_TRACE();
                previouslySelectedBitmap = deviceContext->SetBitmap(theBitmap);
            }
            ~BitmapSelection()
            {
                HWIN_TRACE();
                deviceContext->SetBitmap(previouslySelectedBitmap);
            }
        };


        class BrushSelection
        {
            std::shared_ptr<DeviceContextHandle> deviceContext;
            std::shared_ptr<BrushHandle> previouslySelectedBrush;
        public:
            BrushSelection(std::shared_ptr<DeviceContextHandle> theDeviceContext, std::shared_ptr<BrushHandle> theBrush)
                : deviceContext(theDeviceContext)
            {
                HWIN_TRACE();
                previouslySelectedBrush = deviceContext->SetBrush(theBrush);
            }
            ~BrushSelection()
            {
                HWIN_TRACE();
                deviceContext->SetBrush(previouslySelectedBrush);
            }
        };


        class PenSelection
        {
            std::shared_ptr<DeviceContextHandle> deviceContext;
            std::shared_ptr<PenHandle> previouslySelectedPen;
        public:
            PenSelection(std::shared_ptr<DeviceContextHandle> theDeviceContext, std::shared_ptr<PenHandle> thePen)
                : deviceContext(theDeviceContext)
            {
                HWIN_TRACE();
                previouslySelectedPen = deviceContext->SetPen(thePen);
            }
            ~PenSelection()
            {
                HWIN_TRACE();
                deviceContext->SetPen(previouslySelectedPen);
            }
        };

        class FontSelection
        {
            std::shared_ptr<DeviceContextHandle> deviceContext;
            std::shared_ptr<FontHandle> previouslySelectedFont;
        public:
            FontSelection(std::shared_ptr<DeviceContextHandle> theDeviceContext, std::shared_ptr<FontHandle> theFont)
                : deviceContext(theDeviceContext)
            {
                HWIN_TRACE();
                previouslySelectedFont = deviceContext->SetFont(theFont);
            }
            ~FontSelection()
            {
                HWIN_TRACE();
                deviceContext->SetFont(previouslySelectedFont);
            }
        };


    };
};

#endif 

By viewing downloads associated with this article you agree to the Terms of Service and the article's licence.

If a file you wish to view isn't highlighted, and is a text file (not binary), please let us know and we'll add colourisation support for it.

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)


Written By
Architect Sea Surveillance AS
Norway Norway
Chief Architect - Sea Surveillance AS.

Specializing in integrated operations and high performance computing solutions.

I’ve been fooling around with computers since the early eighties, I’ve even done work on CP/M and MP/M.

Wrote my first “real” program on a BBC micro model B based on a series in a magazine at that time. It was fun and I got hooked on this thing called programming ...

A few Highlights:

  • High performance application server development
  • Model Driven Architecture and Code generators
  • Real-Time Distributed Solutions
  • C, C++, C#, Java, TSQL, PL/SQL, Delphi, ActionScript, Perl, Rexx
  • Microsoft SQL Server, Oracle RDBMS, IBM DB2, PostGreSQL
  • AMQP, Apache qpid, RabbitMQ, Microsoft Message Queuing, IBM WebSphereMQ, Oracle TuxidoMQ
  • Oracle WebLogic, IBM WebSphere
  • Corba, COM, DCE, WCF
  • AspenTech InfoPlus.21(IP21), OsiSoft PI


More information about what I do for a living can be found at: harlinn.com or LinkedIn

You can contact me at espen@harlinn.no

Comments and Discussions