wxWindow无法实现透明背景的问题及解决方案
wxWindow无法实现透明背景的问题及解决方案
我最近在做一个wxWidgets趣味小项目,目标是实现一个轻量组件,只显示带透明背景的游戏角色,同时支持和角色交互。我选了wxWindow作为容器,觉得它是满足绘图需求的最轻量选项,结果却踩了个坑——PNG素材本身带透明通道,但wxWindow的背景始终不透明,直接把游戏的底层背景给挡住了,折腾好久才解决,跟大家分享下过程:
先贴出我最初写的代码:
#include <wx/wx.h> #include <wx/image.h> class PouCharacter : public wxWindow { public: PouCharacter(wxWindow* parent) : wxWindow(parent, wxID_ANY, wxDefaultPosition, wxSize(338, 302)) , m_Image("assets/png/Pousy.png", wxBITMAP_TYPE_PNG) , m_Bitmap(m_Image) { Bind(wxEVT_PAINT, &PouCharacter::OnPaint, this); } void OnPaint(wxPaintEvent& evt) { wxPaintDC dc(this); // 试过设置透明画笔清背景,没用 // dc.SetBrush(*wxTRANSPARENT_BRUSH); // dc.Clear(); dc.DrawBitmap(m_Bitmap, 0, 0, true); } private: wxImage m_Image; wxBitmap m_Bitmap; };
遇到的问题
- 素材Bitmap的透明效果正常,但wxWindow本身的背景总是黑色/不透明
- 尝试过设置
wxPaintDC的透明画笔并清除背景,也试过用wxGraphicsContext绘图,结果都一样,背景还是不透明 - 初期查文档没找到wxWindow和设备上下文相关的透明解决方案
最终解决方案
后来在wxWidgets的文档里找到了关键:wxWindow默认会自动绘制不透明背景,我们需要通过SetBackgroundStyle函数修改它的背景样式。
只需要在PouCharacter的构造函数里添加一行代码,禁用wxWindow的自动背景绘制:
SetBackgroundStyle(wxBG_STYLE_PAINT);
修改后的完整构造函数如下:
PouCharacter(wxWindow* parent) : wxWindow(parent, wxID_ANY, wxDefaultPosition, wxSize(338, 302)) , m_Image("assets/png/Pousy.png", wxBITMAP_TYPE_PNG) , m_Bitmap(m_Image) { // 关键设置:让wxWindow不自动绘制背景,交给OnPaint逻辑处理 SetBackgroundStyle(wxBG_STYLE_PAINT); Bind(wxEVT_PAINT, &PouCharacter::OnPaint, this); }
设置wxBG_STYLE_PAINT后,wxWindow就不会再自动填充不透明背景了,我们在OnPaint里绘制的带透明通道的Bitmap就能正确显示,组件背景也会变成透明,完美解决了挡住游戏底层背景的问题~
内容来源于stack exchange




