在C#中绘制父母和父母子女的自定义背景
作者:互联网
我正在尝试使用this tutorial,以便可以使用透明按钮.在主要背景下效果很好,但不会覆盖其他子项.如果我使用BringToFront(),则它应该在其他子项的绘图处.
我已经开始通过将其添加到代码中来解决它:
foreach (Control child in Parent.Controls) {
if(child != this) {
InvokePaintBackground(child, pea);
InvokePaint(child, pea);
}
}
尽管我得到了一些想要的东西,但它位于错误的位置(在左侧而不是应该在中间的位置),并且在儿童绘画事件中绘制的形状也没有显示.
我该如何进行修改,以便让其他所有孩子也都完全了解透明性?
注意:除了我的孩子,我不担心会给其他人带来痛苦,因为我知道这没有任何问题,并且还有很多其他地方可以找到如何递归让所有孩子痛苦的方法.
感谢C.Evenhuis的回答,它现在可以工作了.我的实现很简单(只有另一个孩子),所以这是我的代码.对于将来的读者,请务必阅读该文章,以获取fll范围.
using (PaintEventArgs pea = new PaintEventArgs(e.Graphics, rect)) {
pea.Graphics.SetClip(rect);
InvokePaintBackground(Parent, pea);
InvokePaint(Parent, pea);
foreach (Control child in Parent.Controls) {
if (child != this) {
pea.Graphics.ResetTransform();
pea.Graphics.TranslateTransform(child.Left - Left, child.Top - Top);
InvokePaintBackground(child, pea);
InvokePaint(child, pea);
}
}
}
解决方法:
绘画时,所有控件均假定其左上角位于(0,0)坐标处.这是通过在调用OnPaint之前将Graphics对象的视口设置为控件的坐标来实现的.
要绘制其他控件,您必须手动执行以下操作:
if (child != this)
{
int offsetX = control.Left - Left;
int offsetY = control.Top - Top;
// Set the viewport to that of the control
pevent.Graphics.TranslateTransform(offsetX, offsetY);
// Translate the clip rectangle to the new coordinate base
Rectangle clip = pevent.ClipRectangle;
clip.Offset(-offsetX, -offsetY); // Ugly self-modifying struct
PaintEventArgs clippedArgs = new PaintEventArgs(pevent.Graphics, clip);
InvokePaintBackground(control, clippedArgs);
InvokePaint(control, clippedArgs);
pevent.Graphics.TranslateTransform(-offsetX, -offsetY)
}
如果基础控件是包含自己的子控件的Panel,则事情会变得更加复杂-这些控件不会自动与其父控件一起绘制.如果您也需要支持,我建议将WM_PRINT消息发送到父控件和当前控件下方的缓冲控件-对于兄弟控件,您可以设置PRF_CHILDREN标志以使其也绘制其后代.
同样,当前您正在绘制所有同级控件-包括当前控件上方的那些.您可能希望让循环倒退并在到达当前控件时中断.在您开始堆叠多个透明控件之前,这将不是一个真正的问题.
标签:transparency,paint,custom-painting,c 来源: https://codeday.me/bug/20191120/2045296.html