diff --git a/build/WinStd-15.0.vcxproj.filters b/build/WinStd-15.0.vcxproj.filters index 898934f5..00ac3ad3 100644 --- a/build/WinStd-15.0.vcxproj.filters +++ b/build/WinStd-15.0.vcxproj.filters @@ -47,6 +47,9 @@ Source Files + + Source Files + @@ -100,5 +103,8 @@ Header Files + + Header Files + \ No newline at end of file diff --git a/build/WinStd-16.0.vcxproj.filters b/build/WinStd-16.0.vcxproj.filters index 898934f5..00ac3ad3 100644 --- a/build/WinStd-16.0.vcxproj.filters +++ b/build/WinStd-16.0.vcxproj.filters @@ -47,6 +47,9 @@ Source Files + + Source Files + @@ -100,5 +103,8 @@ Header Files + + Header Files + \ No newline at end of file diff --git a/build/WinStd.props b/build/WinStd.props index f41e3911..d123a7a3 100644 --- a/build/WinStd.props +++ b/build/WinStd.props @@ -26,6 +26,7 @@ + @@ -39,11 +40,12 @@ + - + diff --git a/include/WinStd/GDI.h b/include/WinStd/GDI.h new file mode 100644 index 00000000..4d3c8e33 --- /dev/null +++ b/include/WinStd/GDI.h @@ -0,0 +1,199 @@ +/* + Copyright © 1991-2021 Amebis + + This file is part of WinStd. + + Setup is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + Setup is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with Setup. If not, see . +*/ + +/// +/// \defgroup WinStdGdiAPI GDI API +/// Integrates WinStd classes with Microsoft Windows GDI +/// + +#include "Common.h" + +#include + +namespace winstd +{ + template class gdi_handle; + class dc; + class window_dc; + class dc_selector; +} + + +#pragma once + + +namespace winstd +{ + /// \addtogroup WinStdGdiAPI + /// @{ + + /// + /// Windows HGDIOBJ wrapper class + /// + template + class gdi_handle : public handle + { + HANDLE_IMPL(gdi_handle, NULL) + + public: + /// + /// Closes an open object handle. + /// + /// \sa [DeleteObject function](https://docs.microsoft.com/en-us/windows/win32/api/wingdi/nf-wingdi-deleteobject) + /// + virtual ~gdi_handle() + { + if (m_h != invalid) + DeleteObject(m_h); + } + + protected: + /// + /// Closes an open object handle. + /// + /// \sa [DeleteObject function](https://docs.microsoft.com/en-us/windows/win32/api/wingdi/nf-wingdi-deleteobject) + /// + void free_internal() noexcept override + { + DeleteObject(m_h); + } + }; + + + /// + /// Device context wrapper class + /// + class dc : public handle + { + HANDLE_IMPL(dc, NULL) + + public: + /// + /// Deletes the specified device context (DC). + /// + /// \sa [DeleteDC function](https://docs.microsoft.com/en-us/windows/win32/api/wingdi/nf-wingdi-deletedc) + /// + virtual ~dc(); + + protected: + /// + /// Deletes the specified device context (DC). + /// + /// \sa [DeleteDC function](https://docs.microsoft.com/en-us/windows/win32/api/wingdi/nf-wingdi-deletedc) + /// + void free_internal() noexcept override; + }; + + + /// + /// Device context wrapper class + /// + class window_dc : public handle + { + public: + inline window_dc() noexcept : + m_hwnd(NULL) + {} + + inline window_dc(_In_opt_ handle_type h, _In_opt_ HWND hwnd) noexcept : + handle(h), + m_hwnd(hwnd) + {} + + inline window_dc(_Inout_ window_dc &&h) noexcept : + handle(std::move(h)), + m_hwnd(h.m_hwnd) + {} + + inline window_dc& operator=(_Inout_ window_dc &&h) noexcept + { + handle::operator=(std::move(h)); + m_hwnd = h.m_hwnd; + return *this; + } + + WINSTD_NONCOPYABLE(window_dc) + + public: + /// + /// Releases a device context (DC), freeing it for use by other applications. + /// + /// \sa [ReleaseDC function](https://docs.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-releasedc) + /// + virtual ~window_dc(); + + protected: + /// + /// Releases a device context (DC), freeing it for use by other applications. + /// + /// \sa [ReleaseDC function](https://docs.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-releasedc) + /// + void free_internal() noexcept override; + + protected: + HWND m_hwnd; ///< Window handle + }; + + + /// + /// Context scope DC object restorer + /// + class dc_selector + { + WINSTD_NONCOPYABLE(dc_selector) + WINSTD_NONMOVABLE(dc_selector) + + public: + /// + /// Selects an object into the specified device context (DC). The new object replaces the previous object of the same type. + /// + /// \sa [SelectObject function](https://docs.microsoft.com/en-us/windows/win32/api/wingdi/nf-wingdi-selectobject) + /// + inline dc_selector(_In_ HDC hdc, _In_ HGDIOBJ h) noexcept : + m_hdc(hdc), + m_orig(SelectObject(hdc, h)) + { + } + + + /// + /// Restores original object. + /// + /// \sa [SelectObject function](https://docs.microsoft.com/en-us/windows/win32/api/wingdi/nf-wingdi-selectobject) + /// + virtual ~dc_selector(); + + + /// + /// Return result of `SelectObject()` call. + /// + /// \sa [SelectObject function](https://docs.microsoft.com/en-us/windows/win32/api/wingdi/nf-wingdi-selectobject) + /// + inline HGDIOBJ status() const noexcept + { + return m_orig; + } + + protected: + HDC m_hdc; ///< A handle to the device context + HGDIOBJ m_orig; ///< Original object handle + }; + + /// @} +} diff --git a/src/GDI.cpp b/src/GDI.cpp new file mode 100644 index 00000000..b67cd6bb --- /dev/null +++ b/src/GDI.cpp @@ -0,0 +1,66 @@ +/* + Copyright © 1991-2021 Amebis + Copyright © 2016 GÉANT + + This file is part of WinStd. + + Setup is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + Setup is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with Setup. If not, see . +*/ + +#include "PCH.h" + + +////////////////////////////////////////////////////////////////////// +// winstd::dc +////////////////////////////////////////////////////////////////////// + +winstd::dc::~dc() +{ + if (m_h != invalid) + DeleteDC(m_h); +} + + +void winstd::dc::free_internal() noexcept +{ + DeleteDC(m_h); +} + + +////////////////////////////////////////////////////////////////////// +// winstd::window_dc +////////////////////////////////////////////////////////////////////// + +winstd::window_dc::~window_dc() +{ + if (m_h != invalid) + ReleaseDC(m_hwnd, m_h); +} + + +void winstd::window_dc::free_internal() noexcept +{ + ReleaseDC(m_hwnd, m_h); +} + + +////////////////////////////////////////////////////////////////////// +// winstd::dc_selector +////////////////////////////////////////////////////////////////////// + +winstd::dc_selector::~dc_selector() +{ + if (m_orig) + SelectObject(m_hdc, m_orig); +} diff --git a/src/PCH.h b/src/PCH.h index 06f3d782..d74cea1a 100644 --- a/src/PCH.h +++ b/src/PCH.h @@ -30,6 +30,7 @@ #if _WIN32_WINNT >= _WIN32_WINNT_VISTA #include "../include/WinStd/ETW.h" #endif +#include "../include/WinStd/GDI.h" #include "../include/WinStd/Hex.h" #include "../include/WinStd/MSI.h" #if defined(SECURITY_WIN32) || defined(SECURITY_KERNEL) || defined(SECURITY_MAC)