2015-01-04 74 views
1

我創建了一個模擬時鐘,可以根據實時正常工作。使用面板繪畫事件時圖形閃爍

我不想讓你爲我解決它 - 我的代碼已經在工作,但它閃爍很多,而且我的知識有限,我無法確定究竟是什麼,我需要改變停止閃爍。

using System; 
using System.Collections.Generic; 
using System.ComponentModel; 
using System.Data; 
using System.Drawing; 
using System.Linq; 
using System.Text; 
using System.Threading.Tasks; 
using System.Windows.Forms; 

namespace ClockAndStuff 
{ 

    public partial class TheName : Form 
    { 

     public TheName() 
     { 
      InitializeComponent(); 
      timer1.Start(); 
     } 

     private void panel1_Paint(object sender, PaintEventArgs e) 
     { 
      Graphics surfaceBckg; 
      Graphics surfaceMin; 
      Graphics surfaceH; 
      Graphics surfaceSec; 

      Pen penMin = new Pen(Color.Pink,2); 
      Pen penH = new Pen(Color.Red,3); 
      Pen penSec = new Pen(Color.DeepPink,1); 
      Pen black = new Pen(Color.Black, 4F); 

      surfaceBckg = panel1.CreateGraphics(); 
      surfaceBckg.TranslateTransform(250, 250); 
      surfaceBckg.DrawEllipse(black,-220,-220,440,440); 

      surfaceMin = panel1.CreateGraphics(); 
      surfaceMin.TranslateTransform(250, 250); 
      surfaceMin.RotateTransform(6 * DateTime.Now.Minute); 

      surfaceH = panel1.CreateGraphics(); 
      surfaceH.TranslateTransform(250, 250); 
      surfaceH.RotateTransform(30 * DateTime.Now.Hour); 

      surfaceSec = panel1.CreateGraphics(); 
      surfaceSec.TranslateTransform(250, 250); 
      surfaceSec.RotateTransform(6 * DateTime.Now.Second); 

      surfaceMin.DrawLine(penMin, 0, 0, 0, -200); 
      surfaceH.DrawLine(penH, 0, 0, 0, -120); 
      surfaceSec.DrawLine(penSec, 0, 0, 1, -180); 
     } 

     private void timer1_Tick(object sender, EventArgs e) 
     { 
      panel1.Refresh(); 
     } 
    } 
} 

根據我的任務,這是正確的,但我不禁要想,必須有更好的方式來做到這一點。

我不是C#還大,所以如果你能給我的代碼示例作爲一個答案有更大的可能性,我就可以去了解它...

This is what it looks like

+0

timer_tick被多久調用一次? – rene 2015-01-04 11:15:34

+2

你可以找到很多解決方案,像[this](http://stackoverflow.com/questions/16882921/how-to-fix-panel-flickering-when-redrawing),[this](http://stackoverflow.com/問題/ 8046560/how-to-stop-flickering -c-sharp-winforms)或[this](http://stackoverflow.com/questions/4777135/how-can-i-draw-on-panel-so-it -does-not-blink) – Grundy 2015-01-04 11:18:52

+0

@Grundy我已經看到了所有這些鏈接,但我根本無法確定如何使用它們來解決我的問題,這就是爲什麼我再次問** **的具體細節我的問題 – Keashi 2015-01-04 11:31:47

回答

1

我建議建立一個自定義的控制,使適當的雙緩衝:

public class Canvas : Control 
{ 
    public Canvas() 
    { 
     this.SetStyle(ControlStyles.AllPaintingInWmPaint, true); 
     this.SetStyle(ControlStyles.OptimizedDoubleBuffer, true); 
     this.SetStyle(ControlStyles.UserPaint, true); 
     this.SetStyle(ControlStyles.ResizeRedraw, true); 
    } 
} 

鉤住您的繪製代碼的Paint事件並使用Invalidate觸發重繪。切勿使用CreateGraphics,爲提供給事件的圖形對象繪製顏色。這將讓你完全無閃爍繪圖!

private void canvas1_Paint(object sender, PaintEventArgs e) 
{ 
    // do your painting here, using the Graphics object passed to 
    // you in the PaintEventArgs 

    Pen penMin = new Pen(Color.Pink, 2); 
    Pen penH = new Pen(Color.Red, 3); 
    Pen penSec = new Pen(Color.DeepPink, 1); 
    Pen black = new Pen(Color.Black, 4f); 

    e.Graphics.TranslateTransform(250, 250); 
    e.Graphics.DrawEllipse(black, -220, -220, 440, 440); 

    e.Graphics.ResetTransform(); 
    e.Graphics.TranslateTransform(250, 250); 
    e.Graphics.RotateTransform(6 * DateTime.Now.Minute); 
    e.Graphics.DrawLine(penMin, 0, 0, 0, -200); 

    e.Graphics.ResetTransform(); 
    e.Graphics.TranslateTransform(250, 250); 
    e.Graphics.RotateTransform(30 * DateTime.Now.Hour); 
    e.Graphics.DrawLine(penH, 0, 0, 0, -120); 

    e.Graphics.ResetTransform(); 
    e.Graphics.TranslateTransform(250, 250); 
    e.Graphics.RotateTransform(6 * DateTime.Now.Second);   
    e.Graphics.DrawLine(penSec, 0, 0, 1, -180); 
} 
+0

剛纔你是什麼意思的「從不使用CreateGraphics」?我的意思是,它顯然告訴我不要使用它,但我不知道還有什麼可以做的。但我認爲有限的知識是我的問題在這裏.. – Keashi 2015-01-04 11:36:32

+0

查看更新的答案。 – Chris 2015-01-04 11:39:40

+0

當我改變它時,它根本沒有手臂。例如: 'e.Graphics.TranslateTransform(250,250);' 'e.Graphics.RotateTransform(6 * DateTime.Now.Second);' 'e.Graphics.DrawLine(penSec,0,0,1, -180);' 等 – Keashi 2015-01-04 11:51:31

0

的閃爍來自計時器滴答,速度非常快,您可以在timer1_tick方法中創建一個檢查,以確保第二個實際已經過了一秒鐘,然後更新繪圖。

您也可以使用計時器,在計時器中告訴它何時開始以及您希望更新的頻率。由你可以按照你自己的電腦秒鐘實時

+0

嗚!所以我試了一下,幾乎完全停止了 - 只有每隔一段時間它會閃爍幾次,然後恢復正常。永遠不會認爲它是這樣簡單的:) – Keashi 2015-01-04 11:22:51

+0

因爲它的一個學校項目我不會告訴你如何做到這一點,但我可以給你一個地方看看,但是你已經在計時器上有一個間隔屬性使用:) – 2015-01-04 11:27:21

+0

閃爍只有*少*與更大的計時器間隔。請查看解決方案,瞭解如何使其停止*。這只是一個繃帶,而不是一種治療方法。 – nvoigt 2015-01-04 11:32:37