0

您好,这可能是一个愚蠢的问题,但我无法在这里找出问题..这是我用单个块填写表格的代码:

    private void drawBackground()
{
    Graphics g = genPan.CreateGraphics();
    Image Block = Image.FromFile(@"C:\Users\Administrator\Desktop\movment V1\movment V1\images\BrownBlock.png");
    float recWidth = Block.Width; 
    // rectangle width didnt change the name from previous code, it's picture width.

    float recHeight = Block.Height;
    // rectangle Heightdidnt change the name from previous code, it's picture Height.

    float WinWidth = genPan.Width; // genPan is a panel that docked to the form

    float WinHeight = genPan.Height;

    float curWidth = 0; //indicates where the next block will be placed int the X axis
    float curHeight = 0;//indicates where the next block will be placed int the Y axis

    while ((curHeight + recHeight) <= WinHeight)
    {
        if (curWidth >= WinWidth / 3 || curWidth <= WinWidth / 1.5 ||
            curHeight >= WinHeight / 3 || curHeight <= WinHeight / 1.5)
        {
            g.DrawImage(Block, curWidth, curHeight, recWidth , recHeight );
        }
        curWidth += recWidth;
        if ((WinWidth - curWidth) < recWidth)
        {
            curWidth = 0;
            curHeight += 50;
        }
    }
}

如果我通过一个按钮启动这个函数,它会工作得很好。但是如果我在 InitializeComponent(); 之后启动函数 构造函数或 FORM 显示事件中的方法,当按钮仍在表单上时,它将执行 func 但是块背景将不可见,但灰色将是。但如果我删除按钮,背景将可见。=\

我不明白为什么会发生这种情况,如何解决它以及我做错了什么..谁能解释一下..?

4

2 回答 2

1

如果您只需要根据某些条件/动作/用户交互来绘制背景......

将此函数的调用放入表单 OnPaint 方法中,并在某些布尔变量等于时 启用它true。只有在单击按钮时,该布尔值才会变为真。

一些假设的例子:

protected override OnPaint(...) //FORMS ONPAINT OVERRIDE
{
    if(needBackGround) //INITIAL VALUE AT STARTUP IS FALSE
       drawBackground(); 
} 

public void ButtonClickHandler(...)
{
    needBackGround= !needBackGround;  //INVERSE THE VALUE OF BOOLEAN
}

这显然只是一个给你提示的片段,而不是真正的代码。您可能还需要面对其他问题,例如:闪烁、处理大小调整、性能……但这只是一个开始。

于 2013-01-17T11:12:58.070 回答
1

使用当前的逻辑,您无法真正做到这一点。问题是控件(genPan在您的情况下为面板)具有自己的 Paint 事件,当调用该事件时,会覆盖您在其上使用的任何图形。

即使您在按钮中单击它,它也仅在重新绘制表单之前起作用,例如尝试聚焦其他窗口并再次聚焦您的表单:您将丢失您绘制的内容。

做这些事情的正确方法是编写自己的类,该类继承自一些基本控件(在您的情况下为 Panel),然后覆盖其 OnPaint 事件并在那里绘制任何您想要的东西。

所以首先,有这样的课程:

public class BlockBackgroundPanel : Panel
{
    protected override void OnPaint(PaintEventArgs e)
    {
        Graphics g = e.Graphics;
        Image Block = Image.FromFile(@"C:\Users\Administrator\Desktop\movment V1\movment V1\images\BrownBlock.png");
        float recWidth = Block.Width; 
        //rest of your code, replace "genPan" with "this" as you are inside the Panel
    }
}

然后在您的.Designer.cs文件中(您可以在 Studio 中打开它)更改代码,使其genPan成为您的新类实例:

private BlockBackgroundPanel genPan;
//...
this.genPan = new BlockBackgroundPanel ();
于 2013-01-17T11:30:57.427 回答