如何实现点击Windows窗体绘制矩形并保留历史图形?
嘿,这个需求其实很好实现,核心就是要把每一批绘制的矩形都存起来,而不是每次只画新的就丢掉旧的。我给你梳理一下具体的实现步骤和代码示例(以C# WinForms为例):
核心思路
原来的程序每次点击后旧矩形消失,大概率是因为你没有保存之前绘制的矩形数据,每次重绘时只渲染了新的那一批。解决的关键就是用一个集合持久化保存所有历史矩形的位置和尺寸,每次重绘时遍历这个集合,把所有矩形都画出来。
具体实现步骤
1. 定义全局集合存储所有矩形
在窗体类里声明一个全局的List<Rectangle>,用来保存每一次点击生成的70个矩形:
// 全局集合,保存所有需要绘制的矩形 private List<Rectangle> _allDrawnRectangles = new List<Rectangle>();
2. 修改鼠标点击事件的逻辑
点击鼠标时,不再清除旧矩形,而是计算出新的70个矩形,把它们添加到全局集合里,然后触发窗体重绘:
private void Form1_MouseClick(object sender, MouseEventArgs e) { List<Rectangle> newRectangles = new List<Rectangle>(); Random random = new Random(); // 生成70个围绕点击点的矩形(这里假设每个矩形20x20,随机偏移) for (int i = 0; i < 70; i++) { // 随机生成偏移量,让矩形在点击点周围散开 int offsetX = random.Next(-100, 101); int offsetY = random.Next(-100, 101); int rectX = e.X + offsetX; int rectY = e.Y + offsetY; newRectangles.Add(new Rectangle(rectX, rectY, 20, 20)); } // 将新生成的矩形添加到全局集合(而不是替换) _allDrawnRectangles.AddRange(newRectangles); // 触发窗体重绘,让Paint事件绘制所有矩形 this.Invalidate(); }
3. 重写Paint事件绘制所有矩形
在窗体的Paint事件里,遍历全局集合中的每一个矩形,逐个绘制出来:
private void Form1_Paint(object sender, PaintEventArgs e) { // 创建红色画刷,用using自动释放资源 using (SolidBrush redBrush = new SolidBrush(Color.Red)) { // 遍历所有保存的矩形,依次绘制 foreach (Rectangle rect in _allDrawnRectangles) { e.Graphics.FillRectangle(redBrush, rect); } } }
额外小技巧(可选)
如果需要清空所有已绘制的矩形,可以加一个按钮,点击时执行以下代码:
private void btnClear_Click(object sender, EventArgs e) { _allDrawnRectangles.Clear(); this.Invalidate(); }
这样每次点击鼠标,新的70个矩形会叠加在旧的上面,所有历史绘制的矩形都会保留下来啦!
内容的提问来源于stack exchange,提问作者Rune Heidtmann
相关产品推荐
相关产品推荐

