I have a custom control that I’m using as a rubber band which paints a blue border and a semi-transparent middle. I’m handling the mouse down / move events to resize the panel. Everything seems to work fine when the mouse move event is called, it all draws as I’d expect, but when the mouse stops moving, certain custom controls below the semi-transparency are redrawing themselves on top. Playing around with the z-order doesn’t do anything.
Here is the transparent panel:
protected override CreateParams CreateParams
{
get
{
CreateParams cp = base.CreateParams;
cp.ExStyle |= 0x00000020; //WS_EX_TRANSPARENT
return cp;
}
}
protected override void OnPaint(PaintEventArgs pe)
{
pe.Graphics.FillRectangle(new SolidBrush(Color.FromArgb(128, 101, 135, 196)), this.ClientRectangle);
pe.Graphics.DrawRectangle(Pens.DarkBlue,
pe.ClipRectangle.Left,
pe.ClipRectangle.Top,
this.Width - 1,
this.Height - 1);
}
protected override void OnPaintBackground(PaintEventArgs pevent)
{
//do not allow the background to be painted
}
protected override void OnSizeChanged(EventArgs e)
{
base.OnSizeChanged(e);
}
So, it turns out this is a pretty difficult problem with the semi-transparency (even if Microsoft have done it in Explorer etc). In the end I hacked up a solution where the middle is now totally transparent, and the rubber band is just a border.
The border still draws underneath certain controls, so for each control, we add a statement in their Paint event that calls
ruberBand.Invalidate()if the rubberBand is visible. Hey presto, a hacked together rubber band that draws itself above controls.IMO this is still better than using
DrawReversibleRectangle, because you can use it inside panels for autoscrolling at the edge, and on top of that it doesn’t flicker.