我使用Graphics对象在表单上绘制矩形或椭圆(取决于所选内容)。在绘制这些图形对象后,有没有办法操纵这些图形对象?我指的是诸如调整大小,删除,拖动等操作。另外,值得一提的是,在同一个表单上绘制的多个形状可以重叠。
绘图本身看起来像这样,由ScrollableControl的OnPaint()事件触发 - 只需将这些方法传递给PaintEventArgs的Graphics对象。
protected override void Fill(System.Drawing.Graphics g, Brush b)
{
g.FillEllipse(b, m_topLeft.X, m_topLeft.Y, m_width, m_height);
}
protected override void Draw(System.Drawing.Graphics g, Pen p)
{
g.DrawEllipse(p, m_topLeft.X, m_topLeft.Y, m_width, m_height);
}
我希望能够点击一个形状,选择如何处理它并采取相应的行动。 我想也许我可以检查光标的位置是否在形状的边界内(m_topLeft,m_width和m_height数据成员)并从那里开始。尽管它确实有效,但它并没有处理潜在的重叠。选择的点可能属于两个(或更多)形状。
这是使用用户定义的参数绘制的两个重叠形状(矩形和椭圆形)的示例:
答案 0 :(得分:0)
不,在绘制完对象后,无法对屏幕上的对象进行微缩处理。您需要做的是拥有需要在屏幕上绘制的所有对象的列表,每当您想要添加,删除或操作该列表中的对象时,您需要重新绘制整个列表。您通常通过调用控件上的Invalidate()
来执行此操作,这将调用Draw
以再次调用,这通常会在foreach
循环中对您想要绘制的对象集合进行迭代。
public YourControl : Control
{
List<IDrawableObject> _itemsToDraw = new List<IDrawableObject>();
protected override void Draw(System.Drawing.Graphics g, Pen p)
{
foreach(var item in _itemsToDraw)
{
item.Draw(g, p);
}
}
protected override void OnMouseClick(MouseEventArgs e)
{
base.OnMouseClick(e);
IDrawableObject clickedItem = _itemsToDraw.FirstOrDefault(x=> x.WasClicked(e.Location));
if(clickedItem != null)
{
//Do something with the clicked item.
}
}
}
interface IDrawableObject
{
void Draw(System.Drawing.Graphics g, Pen p);
bool WasClicked(Point p)
}
private class Ellipse : IDrawableObject
{
Point m_topleft;
int m_width;
int m_height;
//Snip stuff like constructors assigning the values to the private fields.
public void Draw(System.Drawing.Graphics g, Pen p)
{
g.DrawEllipse(p, m_topLeft.X, m_topLeft.Y, m_width, m_height);
}
public bool WasClicked(Point p)
{
return p.X >= m_topLeft.X && p.X < m_topLeft.X + m_width
&& p.Y >= m_topLeft.Y && p.Y < m_topLeft.Y + m_height;
}
}
为了找到单击了哪个控件,您可以创建一个像WasClicked
这样的方法,在单击时接收鼠标的XY并返回true或false。然后,您可以在从WasClicked
函数返回true的集合中操作该对象。