mirror of
https://github.com/juce-framework/JUCE.git
synced 2026-01-10 23:44:24 +00:00
HWNDComponentPeer: Fix icon leaks
Co-authored-by: ValentynPavliuchenkoA <valentyn.pavliuchenko@avid.com>
This commit is contained in:
parent
d8301ddc1c
commit
59a47a4638
2 changed files with 39 additions and 37 deletions
|
|
@ -42,7 +42,7 @@ WinRTWrapper::WinRTWrapper()
|
|||
return;
|
||||
|
||||
HRESULT status = roInitialize (1);
|
||||
initialised = ! (status != S_OK && status != S_FALSE && status != 0x80010106L);
|
||||
initialised = ! (status != S_OK && status != S_FALSE && status != (HRESULT) 0x80010106L);
|
||||
}
|
||||
|
||||
WinRTWrapper::~WinRTWrapper()
|
||||
|
|
|
|||
|
|
@ -1113,6 +1113,13 @@ Image createSnapshotOfNativeWindow (void* nativeWindowHandle)
|
|||
//==============================================================================
|
||||
namespace IconConverters
|
||||
{
|
||||
struct IconDestructor
|
||||
{
|
||||
void operator() (HICON ptr) const { if (ptr != nullptr) DestroyIcon (ptr); }
|
||||
};
|
||||
|
||||
using IconPtr = std::unique_ptr<std::remove_pointer_t<HICON>, IconDestructor>;
|
||||
|
||||
static Image createImageFromHICON (HICON icon)
|
||||
{
|
||||
if (icon == nullptr)
|
||||
|
|
@ -1675,9 +1682,6 @@ public:
|
|||
|
||||
callFunctionIfNotLocked (&destroyWindowCallback, (void*) hwnd);
|
||||
|
||||
if (currentWindowIcon != nullptr)
|
||||
DestroyIcon (currentWindowIcon);
|
||||
|
||||
if (dropTarget != nullptr)
|
||||
{
|
||||
dropTarget->peerIsDeleted = true;
|
||||
|
|
@ -2315,7 +2319,7 @@ private:
|
|||
bool fullScreen = false, isDragging = false, isMouseOver = false,
|
||||
hasCreatedCaret = false, constrainerIsResizing = false;
|
||||
BorderSize<int> windowBorder;
|
||||
HICON currentWindowIcon = nullptr;
|
||||
IconConverters::IconPtr currentWindowIcon;
|
||||
FileDropTarget* dropTarget = nullptr;
|
||||
uint8 updateLayeredWindowAlpha = 255;
|
||||
UWPUIViewSettings uwpViewSettings;
|
||||
|
|
@ -2377,7 +2381,6 @@ private:
|
|||
|
||||
TCHAR moduleFile[1024] = {};
|
||||
GetModuleFileName (moduleHandle, moduleFile, 1024);
|
||||
WORD iconNum = 0;
|
||||
|
||||
WNDCLASSEX wcex = {};
|
||||
wcex.cbSize = sizeof (wcex);
|
||||
|
|
@ -2386,9 +2389,13 @@ private:
|
|||
wcex.lpszClassName = windowClassName.toWideCharPointer();
|
||||
wcex.cbWndExtra = 32;
|
||||
wcex.hInstance = moduleHandle;
|
||||
wcex.hIcon = ExtractAssociatedIcon (moduleHandle, moduleFile, &iconNum);
|
||||
iconNum = 1;
|
||||
wcex.hIconSm = ExtractAssociatedIcon (moduleHandle, moduleFile, &iconNum);
|
||||
|
||||
for (const auto& [index, field, ptr] : { std::tuple { 0, &wcex.hIcon, &iconBig },
|
||||
std::tuple { 1, &wcex.hIconSm, &iconSmall } })
|
||||
{
|
||||
auto iconNum = static_cast<WORD> (index);
|
||||
ptr->reset (*field = ExtractAssociatedIcon (moduleHandle, moduleFile, &iconNum));
|
||||
}
|
||||
|
||||
atom = RegisterClassEx (&wcex);
|
||||
jassert (atom != 0);
|
||||
|
|
@ -2483,6 +2490,8 @@ private:
|
|||
return false;
|
||||
}
|
||||
|
||||
IconConverters::IconPtr iconBig, iconSmall;
|
||||
|
||||
JUCE_DECLARE_NON_COPYABLE (WindowClassHolder)
|
||||
};
|
||||
|
||||
|
|
@ -2668,15 +2677,11 @@ private:
|
|||
|
||||
void setIcon (const Image& newIcon) override
|
||||
{
|
||||
if (auto hicon = IconConverters::createHICONFromImage (newIcon, TRUE, 0, 0))
|
||||
if (IconConverters::IconPtr hicon { IconConverters::createHICONFromImage (newIcon, TRUE, 0, 0) })
|
||||
{
|
||||
SendMessage (hwnd, WM_SETICON, ICON_BIG, (LPARAM) hicon);
|
||||
SendMessage (hwnd, WM_SETICON, ICON_SMALL, (LPARAM) hicon);
|
||||
|
||||
if (currentWindowIcon != nullptr)
|
||||
DestroyIcon (currentWindowIcon);
|
||||
|
||||
currentWindowIcon = hicon;
|
||||
SendMessage (hwnd, WM_SETICON, ICON_BIG, reinterpret_cast<LPARAM> (hicon.get()));
|
||||
SendMessage (hwnd, WM_SETICON, ICON_SMALL, reinterpret_cast<LPARAM> (hicon.get()));
|
||||
currentWindowIcon = std::move (hicon);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -5367,27 +5372,23 @@ void Displays::findDisplays (float masterScale)
|
|||
}
|
||||
|
||||
//==============================================================================
|
||||
static HICON extractFileHICON (const File& file)
|
||||
static auto extractFileHICON (const File& file)
|
||||
{
|
||||
WORD iconNum = 0;
|
||||
WCHAR name[MAX_PATH * 2];
|
||||
file.getFullPathName().copyToUTF16 (name, sizeof (name));
|
||||
|
||||
return ExtractAssociatedIcon ((HINSTANCE) Process::getCurrentModuleInstanceHandle(),
|
||||
name, &iconNum);
|
||||
return IconConverters::IconPtr { ExtractAssociatedIcon ((HINSTANCE) Process::getCurrentModuleInstanceHandle(),
|
||||
name,
|
||||
&iconNum) };
|
||||
}
|
||||
|
||||
Image juce_createIconForFile (const File& file)
|
||||
{
|
||||
Image image;
|
||||
if (const auto icon = extractFileHICON (file))
|
||||
return IconConverters::createImageFromHICON (icon.get());
|
||||
|
||||
if (auto icon = extractFileHICON (file))
|
||||
{
|
||||
image = IconConverters::createImageFromHICON (icon);
|
||||
DestroyIcon (icon);
|
||||
}
|
||||
|
||||
return image;
|
||||
return {};
|
||||
}
|
||||
|
||||
//==============================================================================
|
||||
|
|
@ -5435,12 +5436,6 @@ private:
|
|||
public:
|
||||
explicit ImageImpl (const CustomMouseCursorInfo& infoIn) : info (infoIn) {}
|
||||
|
||||
~ImageImpl() override
|
||||
{
|
||||
for (auto& pair : cursorsBySize)
|
||||
DestroyCursor (pair.second);
|
||||
}
|
||||
|
||||
HCURSOR getCursor (ComponentPeer& peer) override
|
||||
{
|
||||
JUCE_ASSERT_MESSAGE_THREAD;
|
||||
|
|
@ -5451,7 +5446,7 @@ private:
|
|||
const auto iter = cursorsBySize.find (size);
|
||||
|
||||
if (iter != cursorsBySize.end())
|
||||
return iter->second;
|
||||
return iter->second.get();
|
||||
|
||||
const auto logicalSize = info.image.getScaledBounds();
|
||||
const auto scale = (float) size / (float) unityCursorSize;
|
||||
|
|
@ -5466,12 +5461,19 @@ private:
|
|||
const auto hx = jlimit (0, rescaled.getWidth(), roundToInt ((float) info.hotspot.x * effectiveScale));
|
||||
const auto hy = jlimit (0, rescaled.getHeight(), roundToInt ((float) info.hotspot.y * effectiveScale));
|
||||
|
||||
return cursorsBySize.emplace (size, IconConverters::createHICONFromImage (rescaled, false, hx, hy)).first->second;
|
||||
return cursorsBySize.emplace (size, CursorPtr { IconConverters::createHICONFromImage (rescaled, false, hx, hy) }).first->second.get();
|
||||
}
|
||||
|
||||
private:
|
||||
struct CursorDestructor
|
||||
{
|
||||
void operator() (HCURSOR ptr) const { if (ptr != nullptr) DestroyCursor (ptr); }
|
||||
};
|
||||
|
||||
using CursorPtr = std::unique_ptr<std::remove_pointer_t<HCURSOR>, CursorDestructor>;
|
||||
|
||||
const CustomMouseCursorInfo info;
|
||||
std::map<int, HCURSOR> cursorsBySize;
|
||||
std::map<int, CursorPtr> cursorsBySize;
|
||||
};
|
||||
|
||||
static auto getCursorSizeForPeerFunction() -> int (*) (ComponentPeer&)
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue