如何用QPainter绘制带动态镂空区域的半透明遮罩?
实现带圆角镂空半透明遮罩的方法
不用先绘制到QImage再反转,直接用QPainter的组合模式就能实现和paint.net一致的效果,核心思路是先铺半透明遮罩,再用清除模式“挖”出镂空区域,同时开启抗锯齿保证边缘平滑。
具体实现步骤
- 先绘制原始图片作为底层
- 开启抗锯齿渲染提示,保证圆角边缘平滑
- 绘制覆盖整个部件的半透明遮罩
- 切换到
QPainter::CompositionMode_Clear模式,绘制需要镂空的圆角矩形(此模式下绘制的内容会清除掉当前图层的像素,透出下面的图片)
示例代码
void CustomWidget::paintEvent(QPaintEvent *event) { QPainter painter(this); // 开启抗锯齿,确保圆角和遮罩边缘平滑 painter.setRenderHint(QPainter::Antialiasing, true); // 1. 绘制原始图片,铺满整个部件 QPixmap img("your_image_path.png"); painter.drawPixmap(this->rect(), img); // 2. 绘制半透明遮罩并制作镂空 painter.save(); // 保存当前画笔状态,避免影响后续操作 // 绘制全屏半透明黑色遮罩(alpha值127对应50%透明度,可自行调整) painter.fillRect(this->rect(), QColor(0, 0, 0, 127)); // 切换组合模式为Clear:绘制内容会清除当前图层的像素,露出底层图片 painter.setCompositionMode(QPainter::CompositionMode_Clear); // 绘制第一个镂空圆角矩形 QRect hollowRect1(60, 60, 220, 160); painter.drawRoundedRect(hollowRect1, 18, 18); // 绘制第二个镂空圆角矩形 QRect hollowRect2(320, 110, 190, 130); painter.drawRoundedRect(hollowRect2, 12, 12); painter.restore(); // 恢复画笔状态 }
关键细节说明
- 抗锯齿:通过
setRenderHint(QPainter::Antialiasing)开启,QPainter会自动处理圆角和遮罩边缘的锯齿问题 - 组合模式:
CompositionMode_Clear等价于paint.net里的“删除选中区域”操作,直接清除遮罩层对应位置的像素 - 多镂空区域:可以重复调用
drawRoundedRect或者用QPainterPath组合多个形状,一次性绘制完成
内容的提问来源于stack exchange,提问作者Andreas Haferburg
相关产品推荐
相关产品推荐

