Skip to content

Commit

Permalink
修复BUG并改善用户体验
Browse files Browse the repository at this point in the history
  • Loading branch information
ALTaleX531 committed Jul 28, 2022
1 parent d26d738 commit 04f6baa
Show file tree
Hide file tree
Showing 6 changed files with 179 additions and 53 deletions.
7 changes: 4 additions & 3 deletions TranslucentFlyouts/ThemeHelper.h
Original file line number Diff line number Diff line change
Expand Up @@ -230,12 +230,13 @@ namespace TranslucentFlyoutsLib
T&& t,
BYTE dwOpacity = 255,
DWORD dwFlag = BPPF_ERASE,
BOOL bUpdateTarget = TRUE
BOOL bUpdateTarget = TRUE,
BOOL bUseBlendFunction = TRUE
)
{
HDC hMemDC = nullptr;
BLENDFUNCTION BlendFunction = {AC_SRC_OVER, 0, dwOpacity, AC_SRC_ALPHA};
BP_PAINTPARAMS PaintParams = {sizeof(BP_PAINTPARAMS), dwFlag, nullptr, &BlendFunction};
BP_PAINTPARAMS PaintParams = {sizeof(BP_PAINTPARAMS), dwFlag, nullptr, bUseBlendFunction ? &BlendFunction : nullptr};
HPAINTBUFFER hPaintBuffer = BeginBufferedPaint(hdc, Rect, BPBF_TOPDOWNDIB, &PaintParams, &hMemDC);
if (hPaintBuffer and hMemDC)
{
Expand All @@ -246,7 +247,7 @@ namespace TranslucentFlyoutsLib
SetTextAlign(hMemDC, GetTextAlign(hdc));

t(hMemDC, hPaintBuffer);
EndBufferedPaint(hPaintBuffer, TRUE);
EndBufferedPaint(hPaintBuffer, bUpdateTarget);
}
else
{
Expand Down
192 changes: 161 additions & 31 deletions TranslucentFlyouts/Win32HookHelper.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -90,19 +90,18 @@ HRESULT WINAPI TranslucentFlyoutsLib::MyDrawThemeBackground(
{
RECT Rect = {0, 0, 1, 1};
bool bResult = false;

auto verify = [&](int y, int x, RGBQUAD * pRGBAInfo)
auto f = [&](HDC hMemDC, HPAINTBUFFER hPaintBuffer)
{
if (pRGBAInfo->rgbReserved != 0xFF)
auto verify = [&](int y, int x, RGBQUAD * pRGBAInfo)
{
bResult = true;
return false;
}
return true;
};
if (pRGBAInfo->rgbReserved != 0xFF)
{
bResult = true;
return false;
}
return true;
};

auto f = [&](HDC hMemDC, HPAINTBUFFER hPaintBuffer)
{
HRESULT hr = DrawThemeBackgroundHook.OldFunction<decltype(MyDrawThemeBackground)>(
hTheme,
hMemDC,
Expand All @@ -118,7 +117,13 @@ HRESULT WINAPI TranslucentFlyoutsLib::MyDrawThemeBackground(
}
};

DoBufferedPaint(hdc, &Rect, f, 0xFF, BPPF_ERASE | BPPF_NOCLIP, FALSE);
MARGINS mr = {};
if (SUCCEEDED(GetThemeMargins(hTheme, hdc, iPartId, iStateId, TMT_SIZINGMARGINS, nullptr, &mr)))
{
Rect.right = max(mr.cxLeftWidth + mr.cxRightWidth, 1);
Rect.bottom = max(mr.cyTopHeight + mr.cyBottomHeight, 1);
}
DoBufferedPaint(hdc, &Rect, f, 0xFF, BPPF_ERASE | BPPF_NOCLIP, FALSE, FALSE);

return bResult;
};
Expand All @@ -131,6 +136,7 @@ HRESULT WINAPI TranslucentFlyoutsLib::MyDrawThemeBackground(
::IntersectRect(&Rect, pRect, pClipRect);
}

// 通用绘制函数
auto f = [&](HDC hMemDC, HPAINTBUFFER hPaintBuffer)
{
Clear(hdc, &Rect);
Expand All @@ -144,7 +150,123 @@ HRESULT WINAPI TranslucentFlyoutsLib::MyDrawThemeBackground(
pClipRect
);

BufferedPaintSetAlpha(hPaintBuffer, &Rect, 0xFF);
// 为Windows 11准备的特化实现
COLORREF Color = 0;
if (
SUCCEEDED(hr) and
SUCCEEDED(GetThemeColor(hTheme, iPartId, iStateId, TMT_FILLCOLOR, &Color))
)
{
// 修复Windows 11以来的FILLCOLOR的丑陋边框
bool bHasOpaqueBorder = false;
if (iPartId == MENU_POPUPITEM or iPartId == MENU_INTERNAL_POPUPITEM)
{
BYTE r = 0;
BYTE g = 0;
BYTE b = 0;
BYTE a = 0;
auto remove_opaque_border = [&](int y, int x, RGBQUAD * pRGBAInfo)
{
// 初始化要过滤的颜色
if (x == 0 and y == 0)
{
RECT rect = {0, 0, 1, 1};
auto f = [&](HDC hMemDC, HPAINTBUFFER hPaintBuffer)
{
HRESULT hr = S_OK;
auto initialize = [&](int y, int x, RGBQUAD * pRGBAInfo)
{
r = pRGBAInfo->rgbRed;
g = pRGBAInfo->rgbGreen;
b = pRGBAInfo->rgbBlue;
a = pRGBAInfo->rgbReserved;
return false;
};

if (iPartId == MENU_POPUPITEM)
{
hr = DrawThemeBackgroundHook.OldFunction<decltype(MyDrawThemeBackground)>(
hTheme,
hMemDC,
MENU_POPUPBACKGROUND,
0,
&rect,
nullptr
);
hr = DrawThemeBackgroundHook.OldFunction<decltype(MyDrawThemeBackground)>(
hTheme,
hMemDC,
MENU_POPUPITEM,
MPI_NORMAL,
&rect,
nullptr
);
}
if (iPartId == MENU_INTERNAL_POPUPITEM)
{
hr = DrawThemeBackgroundHook.OldFunction<decltype(MyDrawThemeBackground)>(
hTheme,
hMemDC,
MENU_INTERNAL_POPUPBACKGROUND,
0,
&rect,
nullptr
);
hr = DrawThemeBackgroundHook.OldFunction<decltype(MyDrawThemeBackground)>(
hTheme,
hMemDC,
MENU_INTERNAL_POPUPITEM,
MPI_NORMAL,
&rect,
nullptr
);
}
if (SUCCEEDED(hr))
{
BufferedPaintWalkBits(hPaintBuffer, initialize);
}
};
DoBufferedPaint(hdc, &rect, f, 0xFF, BPPF_ERASE | BPPF_NOCLIP, FALSE);

// 没有边框,是完全透明的
if (r == 0 and g == 0 and b == 0 and a == 0)
{
return false;
}
else
{
bHasOpaqueBorder = true;
}
}

if (
pRGBAInfo->rgbRed == r and
pRGBAInfo->rgbGreen == g and
pRGBAInfo->rgbBlue == b and
pRGBAInfo->rgbReserved == a
)
{
pRGBAInfo->rgbRed = 0;
pRGBAInfo->rgbGreen = 0;
pRGBAInfo->rgbBlue = 0;
pRGBAInfo->rgbReserved = 0;
}
return true;
};
// Windows 11聚焦的菜单项会有纯色Alpha为255的边框,之前我们抠掉了这层边框,这里我们与不透明度做一次运算再画到HDC
if (BufferedPaintWalkBits(hPaintBuffer, remove_opaque_border) and bHasOpaqueBorder)
{
auto partimage_background = [&](HDC hMemDC, HPAINTBUFFER hPaintBuffer)
{
HBRUSH hBrush = CreateSolidBrush(RGB(r, g, b));
FillRect(hMemDC, &Rect, hBrush);
DeleteObject(hBrush);
BufferedPaintSetAlpha(hPaintBuffer, &Rect, a);
};
DoBufferedPaint(hdc, &Rect, partimage_background, (BYTE)GetCurrentFlyoutOpacity(), BPPF_ERASE, TRUE);
}
}
}
};

// 工具提示
Expand Down Expand Up @@ -244,6 +366,7 @@ HRESULT WINAPI TranslucentFlyoutsLib::MyDrawThemeBackground(
iPartId == MENU_POPUPBORDERS
)
{
// 完全不透明的位图
if (
(
iPartId == MENU_POPUPBACKGROUND or
Expand Down Expand Up @@ -280,6 +403,7 @@ HRESULT WINAPI TranslucentFlyoutsLib::MyDrawThemeBackground(
}
}
else
// 主题位图有透明部分
{
// 对Windows 11 22H2的支持
// 先检查是否定义了MENU_INTERNAL_POPUPITEM和MENU_INTERNAL_POPUPBACKGROUND
Expand All @@ -288,15 +412,18 @@ HRESULT WINAPI TranslucentFlyoutsLib::MyDrawThemeBackground(
IsThemePartDefined(hTheme, MENU_INTERNAL_POPUPITEM, 0)
)
{
MyDrawThemeBackground(
hTheme,
hdc,
MENU_INTERNAL_POPUPBACKGROUND,
0,
pRect,
pClipRect
);
if (iPartId != MENU_INTERNAL_POPUPITEM or (iPartId == MENU_INTERNAL_POPUPITEM and iStateId != MPI_NORMAL))
if (iPartId != MENU_INTERNAL_POPUPBACKGROUND)
{
MyDrawThemeBackground(
hTheme,
hdc,
MENU_INTERNAL_POPUPBACKGROUND,
0,
pRect,
pClipRect
);
}
if (!(iPartId == MENU_INTERNAL_POPUPITEM and iStateId == MPI_NORMAL))
{
MyDrawThemeBackground(
hTheme,
Expand All @@ -308,17 +435,21 @@ HRESULT WINAPI TranslucentFlyoutsLib::MyDrawThemeBackground(
);
}
}

else
{
MyDrawThemeBackground(
hTheme,
hdc,
MENU_POPUPBACKGROUND,
0,
pRect,
pClipRect
);
if (iPartId != MENU_POPUPITEM or (iPartId == MENU_POPUPITEM and iStateId != MPI_NORMAL))
if (iPartId != MENU_POPUPBACKGROUND)
{
MyDrawThemeBackground(
hTheme,
hdc,
MENU_POPUPBACKGROUND,
0,
pRect,
pClipRect
);
}
if (!(iPartId == MENU_POPUPITEM and iStateId == MPI_NORMAL))
{
MyDrawThemeBackground(
hTheme,
Expand All @@ -330,7 +461,6 @@ HRESULT WINAPI TranslucentFlyoutsLib::MyDrawThemeBackground(
);
}
}
// 对Windows 11 22H2的支持
goto Default;
}
}
Expand Down
18 changes: 1 addition & 17 deletions TranslucentFlyouts/tflapi.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -232,26 +232,10 @@ extern "C"

VOID WINAPI GetVersionString(LPWSTR pszClassName, const int cchClassName)
{
wcscpy_s(pszClassName, cchClassName, L"1.0.2");
wcscpy_s(pszClassName, cchClassName, L"1.0.3");
}

VOID WINAPI FlushSettingsCache()
{
/*TCHAR pszMutexName[] = TEXT("Local\\FlushSettingsCache");
HANDLE hMutex = OpenMutex(SYNCHRONIZE, FALSE, pszMutexName);
if (!hMutex)
{
hMutex = CreateMutex(nullptr, TRUE, pszMutexName);
}
else
{
WaitForSingleObject(hMutex, INFINITE);
}
if (hMutex)
{
g_settings.Update();
ReleaseMutex(hMutex);
CloseHandle(hMutex);
}*/
}
}
12 changes: 10 additions & 2 deletions TranslucentFlyoutsGUI/TranslucentFlyoutsGUI.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -428,7 +428,7 @@ INT_PTR CALLBACK DialogProc2(HWND hWnd, UINT Message, WPARAM wParam, LPARAM lPar
SendMessage(hWnd, WM_SETICON, FALSE, (LPARAM)hIcon);
DestroyIcon(hIcon);
GetVersionString(pszLibVersion, MAX_PATH);
_stprintf_s(pszVersionInfo, TEXT("TranslucentFlyoutsLib v%s\nTranslucentFlyoutsGUI v1.0.2"), pszLibVersion);
_stprintf_s(pszVersionInfo, TEXT("TranslucentFlyoutsLib v%s\nTranslucentFlyoutsGUI v1.0.3"), pszLibVersion);
SetWindowText(GetDlgItem(hWnd, IDC_STATIC4), pszVersionInfo);
break;
}
Expand Down Expand Up @@ -521,7 +521,7 @@ INT_PTR CALLBACK DialogProc(HWND hWnd, UINT Message, WPARAM wParam, LPARAM lPara
TCHAR pszOpacityTip[512] = TEXT("当前不透明度:");
TCHAR pszOpacity2Tip[512] = TEXT("此参数决定弹出窗口的不透明度\n此值越高,越不透明(Opaque),窗口背后的内容可见度越低,反之亦然\n只有渲染完全不透明的主题位图会受此影响,正常情况下不应也不需要设置为255或0");
TCHAR pszBorderTip[512] = TEXT("此参数决定弹出窗口是否具有一个额外的边框或是阴影\n当窗口被设置特效时,边框也会被同步添加到窗口\n当使用高透明度设置时,这对于增强视觉对比度十分有用\n");
TCHAR pszColorizeOptionTip[512] = TEXT("此参数决定弹出菜单鼠标悬停项的主题位图AlphaBlend混合方式,即不透明度选择方案\n通常情况下选择<不透明>增加对比度,但Windows 11默认主题黑暗模式下具有缺陷\n其在较高透明度下菜单项会又一层黑边,所以推荐使用<跟随透明度>设置\n但是如果你什么都不知道,就选择<自动计算(Auto)>");
TCHAR pszColorizeOptionTip[512] = TEXT("此参数决定弹出菜单鼠标悬停项的主题位图AlphaBlend混合方式,即不透明度选择方案\n通常情况下选择<不透明>增加对比度,但Windows 11 22H2之前默认主题黑暗模式下具有缺陷\n其在较高透明度下菜单项会又一层黑边,所以推荐使用<跟随透明度>设置\n但是如果你什么都不知道,就选择<自动计算>");
TCHAR pszResetTip[512] = TEXT("注意此选项会删除默认的配置信息,清除你对此应用的授权\n但是不影响用户界面选项的设置,即不会影响自启动\n如果你想停用此应用且不残留信息,点击它我会自动帮你清理掉");
TCHAR pszAutoRunTip[512] = TEXT("该选项会让你开机时运行此程序\n但如果你需要以管理员权限自启动,请在计划任务处添加自启动任务\n而不是在此处设置自启动,该处设置与计划任务保持独立");
if (GetUserDefaultUILanguage() != MAKELANGID(LANG_CHINESE, SUBLANG_CHINESE_SIMPLIFIED))
Expand Down Expand Up @@ -654,6 +654,14 @@ INT_PTR CALLBACK DialogProc(HWND hWnd, UINT Message, WPARAM wParam, LPARAM lPara
}
if (!_tcsicmp(szBuffer, pszFollow))
{
TCHAR pszText[MAX_PATH + 1] = _T("注意,自1.0.3开始<跟随透明度>已被弃用。其依旧可以正常工作,但用户没有理由也不需要继续使用该值");
TCHAR pszCaption[MAX_PATH + 1] = _T("被弃用的值");
if (GetUserDefaultUILanguage() != MAKELANGID(LANG_CHINESE, SUBLANG_CHINESE_SIMPLIFIED))
{
LoadString(g_hInst, IDS_DEPRECATED, pszCaption, MAX_PATH);
LoadString(g_hInst, IDS_DEPRECATEDTEXT, pszText, MAX_PATH);
}
ShowBalloonTip(g_mainWindow, pszText, pszCaption, 3000, NIIF_INFO);
dwColorizeOption = 1;
}
if (!_tcsicmp(szBuffer, pszAuto))
Expand Down
Binary file modified TranslucentFlyoutsGUI/TranslucentFlyoutsGUI.rc
Binary file not shown.
3 changes: 3 additions & 0 deletions TranslucentFlyoutsGUI/resource.h
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,9 @@
#define IDS_FO 160
#define IDS_AC 161
#define IDS_OPAC 162
#define IDS_DEPRECATED 163
#define IDS_DC_V_T 164
#define IDS_DEPRECATEDTEXT 164
#define IDC_COMBO1 1001
#define IDC_COMBO2 1002
#define IDC_SLIDER1 1003
Expand Down

0 comments on commit 04f6baa

Please sign in to comment.