2016-08-11 115 views
1

我在c#中制作了一个基本的窗口化游戏,我无法为屏幕创建基本的位图。我在屏幕面板,并且我希望能够吸引到它,所以我用下面的代码:C#位图 - 参数无效

public partial class GameWIndow : Form 
{ 
    public GameWIndow() 
    { 
     InitializeComponent(); 
    } 





    private void panel1_Paint(object sender, PaintEventArgs e) 
    { 
     Bitmap buffer; 
     buffer = new Bitmap(Width, Height); 
     Task.Factory.StartNew(() => 
     { 
      using (Graphics g = Graphics.FromImage(buffer)) 
      { 
       g.FillRectangle(new SolidBrush(Color.PaleGoldenrod), 10, 10, 100, 100); 
      } 
      this.Invoke(new Action(() => 
      { 
       this.BackgroundImage = buffer; 
      })); 
     }); 
    } 

当这个运行时,它给我的错误“参数无效”为线

buffer = new Bitmap(Width, Height); 

宽度和高度分别是900和700,都是整数。

如果问题是我这样做完全错了,那么更好的方法来实现这一点。

-------- -------编辑

我看过您的意见,似乎是我在上面所做的是非常可怕的,所以我尝试了不同的方法,和我不确定这是否更好。

private Game game; 
    private Thread renderThread; 
    private Stopwatch stopwatch = new Stopwatch(); 

    public GameWindow() 
    { 
     InitializeComponent(); 

     //Starts game 
     game = new Game(); 

     //Starts rendering 
     this.DoubleBuffered = true; 
     renderThread = new Thread(new ThreadStart(draw)); 
     renderThread.Start(); 
    } 

    //Runs when screen is asked to refresh 
    private void panel1_Paint(object sender, PaintEventArgs e) 
    { 
     //Sends graphics to game class where it draws game 
     game.draw(e.Graphics); 

    } 

    private void draw() 
    { 
     stopwatch.Start(); 

     while (true) 
     { 

      //If 1/60th of a sec has passed 
      if (stopwatch.ElapsedMilliseconds > 1000D/60D) 
      { 

       stopwatch.Restart(); 
       Invalidate(); 

      } 
     } 

    } 

上面的代码不能正常运行,我不太清楚为什么,如果有人可以提供帮助的,我对此表示赞赏。然而,我的主要问题不是如何解决这个问题,但如果这是一个有效的或“正确的”绘制方式。

+0

这个问题很可能是你完全错误的。我不知道为什么你会得到这个错误,但是禁止从其它线程修改GUI。 (仔细阅读,这绝对不是你得到这个错误的原因,但该规则仍然适用。) – adv12

+1

你想做什么?这看起来有点可疑。 'PaintEventArgs'已经包含了你应该绘制的'Graphics'的一个实例。 – vcsjones

+0

如果您为该控件启用了双缓冲样式,则只需以最直接的方式编写“Paint”事件处理代码即可。 –

回答

0

正如@TaW所示,存在很多问题。我认为这是WinForms应用程序的Paint事件处理程序?这是你应该告诉我们的重要信息。

每当您的表单内容中的任何内容需要重绘时,操作系统都会调用Paint事件处理函数。 PaintEventArgs为您提供ClipRectangle您必须绘制和Graphics上下文,您必须绘制。你只能在你的处理程序中画出来;您不得执行任何其他处理,启动线程或执行任何I/O。如果您需要加载图像或执行I/O,则必须在处理程序外执行此操作,将结果保存为表单属性,使要绘制的矩形无效,然后使用保存的属性在绘制处理程序中绘制。它应该是这个样子:

private void Panel1_Paint(object sender, PaintEventArgs e) 
{ 
    e.Graphics.DrawImage(_buffer, _position); 
} 

什么是_bufferImage你在处理程序外面填充。 _position?您在处理程序外部更新的位置。

不要在您的Paint处理程序中分配缓冲区,Brush es或图像;在处理程序外创建它们并重新使用它们。如果您需要通过长时间过程或网络连接更新控件,请在您的处理程序外部创建一个TaskBackgroundWorker并使完成例程保存结果并使控件失效。在处理程序中使用保存的结果。如果您需要执行某种动画,请先创建所有动画帧,使用计时器使显示无效,然后在处理程序中绘制正确的帧。

WinForm图形是一个巨大的话题,您需要获得一本书或遵循教程。