Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/338.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 填充矩形_C#_Graphics_Grid_Draw - Fatal编程技术网

C# 填充矩形

C# 填充矩形,c#,graphics,grid,draw,C#,Graphics,Grid,Draw,我创建了一个winform程序,它使用一个图形对象和两个for循环,根据用户输入生成一个正方形网格 我还创建了一个方法,通过使用与网格相同的坐标,用随机颜色填充网格中的每个正方形 现在,我想通过单击每个正方形,使用光标位置,独立地绘制每个正方形。我该怎么做?洪水填充是最简单的。与其他方法相比,它的速度很慢,并且占用了堆栈空间,但对于使用时间不到15年的计算机来说,这应该不是问题 更新 正如@Ron所提到的,典型的递归洪水填充非常容易将堆栈吹走。因此,我修改了代码以使用堆栈实例(我相信它是从堆中分

我创建了一个winform程序,它使用一个图形对象和两个for循环,根据用户输入生成一个正方形网格

我还创建了一个方法,通过使用与网格相同的坐标,用随机颜色填充网格中的每个正方形


现在,我想通过单击每个正方形,使用光标位置,独立地绘制每个正方形。我该怎么做?

洪水填充是最简单的。与其他方法相比,它的速度很慢,并且占用了堆栈空间,但对于使用时间不到15年的计算机来说,这应该不是问题

更新

正如@Ron所提到的,典型的递归洪水填充非常容易将堆栈吹走。因此,我修改了代码以使用
堆栈
实例(我相信它是从堆中分配的)和所谓的“数据递归”。对于大的(2000x2000+像素)区域,它仍然非常慢,但是对于小的区域,应该可以

bool[] canDraw;
/// <summary>
/// make sure that the given point is within our image boundaries.
/// BufferSize(Point) contains the dimensions of the image buffer.
/// </summary>
/// <param name="p"></param>
/// <returns></returns>
bool InBounds(Point p)
{
    return p.X >= 0 && p.X < BufferSize.X && p.Y >= 0 && p.Y < BufferSize.Y;
}

/// <summary>
/// make sure that we haven't already drawn this pixel and that it has
/// valid coordinates
/// </summary>
/// <param name="p"></param>
/// <returns></returns>
bool CanDraw(Point p)
{
    return InBounds(p) && canDraw[p.Y * BufferSize.X + p.X];
}

/// <summary>
/// Heap "stack" to track which pixels we need to visit
/// </summary>
Stack<Point> fillStack = new Stack<Point>();

/// <summary>
/// initialize recursion.
/// </summary>
/// <param name="startPosition"></param>
/// <param name="fillColor"></param>
void Fill(Point startPosition, Color fillColor)
{
    canDraw = Enumerable.Repeat(true, BufferSize.X * BufferSize.Y).ToArray();
    var backgroundColor = GetPixel(startPosition);

    if (backgroundColor != fillColor)
    {
        fillStack.Push(startPosition);
        RecurseFloodFill(fillColor, backgroundColor);
    }

}

/// <summary>
/// data-recurse through the image.
/// </summary>
/// <param name="fillColor">Color we want to fill with</param>
/// <param name="backgroundColor">Initial background color to overwrite</param>
void RecurseFloodFill(Color fillColor, Color backgroundColor)
{
    while (fillStack.Count > 0 && !IsExiting)
    {
        /*if (fillStack.Count != depth)
            Debug.WriteLine("Depth: {0}", depth = fillStack.Count);
        */
        var position = fillStack.Pop();
        if(!CanDraw(position))
            continue;

        var color = GetPixel(position);
        if (color != backgroundColor)
            continue;

        SetPixel(position, fillColor);

        for(var i=position.X-1;i<=position.X+1;i++)
            for (var j = position.Y - 1; j <= position.Y + 1; j++)
            {
                var p = new Point(i, j);
                fillStack.Push(p);
            }

    }

}
bool[]canDraw;
/// 
///确保给定点位于图像边界内。
///BufferSize(点)包含图像缓冲区的尺寸。
/// 
/// 
/// 
布尔内边界(p点)
{
返回p.X>=0&&p.X=0&&p.Y0&&!IsExit)
{
/*if(fillStack.Count!=深度)
WriteLine(“深度:{0}”,深度=fillStack.Count);
*/
var position=fillStack.Pop();
如果(!CanDraw(位置))
继续;
var color=GetPixel(位置);
如果(颜色!=背景颜色)
继续;
设置像素(位置、填充颜色);

对于(var i=position.X-1;i你为什么不跟踪网格线,从而知道你点击的是哪个正方形?根据这一知识,你可以在一个正方形所属的地方画一个正方形。

你在哪一部分遇到了麻烦?我不确定这是他想要的。同样,递归泛洪填充几乎肯定会耗尽堆栈空间小图像。@Ron将其修改为使用堆。现在效果很好。简单、易于实现的答案会损害工作安全性。+1Plus,如果工作做得太快,你就不能向客户收取太多的账单:)哈哈,怀疑它。StackOverflow对凡人来说毫无意义。哈哈!xP,但我如何跟踪网格线?引用“你自己”:“我创建了一个winform程序,它使用一个图形对象和两个for循环来生成一个正方形网格,具体取决于用户的输入。”如果你在绘制网格,你必须知道在哪里绘制线:p