我正在尝试编写类似绘画的程序。您可以通过选择所需的形状来绘制填充的形状,单击图片框并拖动鼠标以获取所需的大小。但是这时候我能拖发生。当我使用时refresh();,先前绘制的shapes会自行删除。如何绘制填充形状?
refresh();
private void CizimPicture_MouseDown(object sender, MouseEventArgs e) { Cursor = Cursors.Cross; if (e.Button == MouseButtons.Left) { cizim = true; } X1 = e.X; Y1 = e.Y; } private void CizimPicture_MouseUp(object sender, MouseEventArgs e) { Cursor = Cursors.Default; cizim = false; } private void CizimPicture_MouseMove(object sender, MouseEventArgs e) { if (!cizim) return; if (cizim == true) { X = e.X; Y = e.Y; X2 = (e.X - X1); Y2 = (Y1 - e.Y); if (dikdörtgen == true) { resmim.FillRectangle(renk.Brush, X1, Y1, X2, -Y2); } if (elips == true) { resmim.FillEllipse(renk.Brush, X1, Y1, X2, -Y2); } } }
我寻找的示例代码既简单又有效,却什么也没找到。您不需要屏幕外的位图CreateGraphics,也不需要这样做,但是您将需要跟踪鼠标的位置,在屏幕上绘图以及按照Eric的建议将绘制的形状添加到形状列表中。要处理交互式图形,您需要在窗体处理程序中存储鼠标状态,初始单击位置和当前矩形:
CreateGraphics
bool mouseDown; Point clickPos; Rectangle rect;
然后,当用户单击时,请记住初始位置:
private void MouseDown(object sender, MouseEventArgs e) { mouseDown = true; clickPos = e.Location; rect = new Rectangle(clickPos, new Size(0, 0)); }
当用户用鼠标向下拖动时,创建一个包含开始位置和当前位置的矩形:
private void MouseMove(object sender, MouseEventArgs e) { if (mouseDown) { this.Invalidate(rect); if (e.Location.X > clickPos.X && e.Location.Y > clickPos.Y) { rect = new Rectangle(clickPos.X, clickPos.Y, e.Location.X - clickPos.X, e.Location.Y - clickPos.Y); } else if (e.Location.X > clickPos.X && e.Location.Y < clickPos.Y) { rect = new Rectangle(clickPos.X, e.Location.Y, e.Location.X - clickPos.X, clickPos.Y - e.Location.Y); } else if (e.Location.X < clickPos.X && e.Location.Y < clickPos.Y) { rect = new Rectangle(e.Location.X, e.Location.Y, clickPos.X - e.Location.X, clickPos.Y - e.Location.Y); } else if (e.Location.X < clickPos.X && e.Location.Y > clickPos.Y) { rect = new Rectangle(e.Location.X, clickPos.Y, clickPos.X - e.Location.X, e.Location.Y - clickPos.Y); } this.Invalidate(rect); } }
当用户释放鼠标时,停止绘制:
private void MouseUp(object sender, MouseEventArgs e) { mouseDown = false; }
Windows窗体中最重要的#1规则是: 仅在Paint事件中绘制到屏幕上 。永远不要画图MouseMoved:
MouseMoved
private void Paint(object sender, PaintEventArgs e) { e.Graphics.FillRectangle(Brushes.DarkGray, rect); }
完成此工作后,创建一个表单List<Rectangle>并在MouseUp事件中添加当前矩形,并在事件中绘制所有矩形Paint。您可能还希望将图形裁剪到要在其中进行绘图的面板或窗口。您还可以进行一些优化,MouseMoved以仅使更改后的屏幕区域无效,而不会使旧矩形和新矩形无效。
List<Rectangle>
MouseUp
Paint