2013-07-30 27 views
2

我以C#中的默認Windows窗體應用程序開始,我改變的只是Progam.cs。從main函數,我改變如何在C#系統托盤應用程序中重複運行代碼(如在計時器上)?

Application.Run(new Form1()); 

Application.Run(new MyCustomApplicationContext()); 

其指的是自定義類(MyCustomApplicationContext:ApplicationContext中)運行我的程序作爲一個系統托盤圖標,而不是Windows窗體。構造函數包含以下代碼:

private NotifyIcon trayIcon = new NotifyIcon(); 
trayIcon.ContextMenu = new ContextMenu(
    new MenuItem[] 
    { 
     new MenuItem("Exit", Exit) 
    }); 

這允許用戶右鍵點擊該圖標,讓他們與將運行關閉了該程序的功能的「退出」選項的上下文菜單。

在MyCustomApplicationContext構造函數的末尾,我調用類Update()中的遞歸函數,該函數執行ping功能並根據ping延遲更改系統托盤圖標。

不幸的是,我相信因爲它是遞歸的,所以不允許運行任何其他代碼,所以右鍵單擊上下文菜單不會出現。我寧願通過事件來調用Update()函數,如System.Timers.Timer Elapsed事件。我只是不知道事件是如何工作的或者代碼的放置位置。

+0

因爲您的構造函數正在調用遞歸函數,所以它永遠不會完成,並且該對象不可用。 – Jay

回答

3

您是對的,遞歸調用會阻止您的應用程序主線程停止GUI中的任何交互。如果你有Windows應用程序將它標記爲「(無響應)」。

您可以使用Timer類

http://msdn.microsoft.com/en-us/library/system.timers.timer.aspx

 var timer = new Timer(tick_milliseconds); 
     timer.Elapsed += DoOnTimerClick; 
     timer.Enabled = true; 
+0

好吧,你去!我不知道它是如此簡單。謝謝! – user2536496

5

由於dmay曾表示,你可以使用一個Timer類調用您的更新功能;然而,從閱讀你的描述,這聽起來像你也需要考慮線程在這裏。

... 
aTimer = new System.Timers.Timer(10000); 

// Hook up the Elapsed event for the timer. 
aTimer.Elapsed += UpdateTimer; 
aTimer.Interval = 2000; 
aTimer.Enabled = true; 
... 

public delegate void delUpdate(); // This is your delegate. Put it in your MyCustomApplicationContext class. 

// This method will invoke your delegate method. 
public void UpdateTimer(object sender, ElapsedEventArgs e) 
{ 
    this.Invoke((delUpdate)Update); 
} 

之所以使用Invoke方法是計時器將被從另一個線程運行,如果你想打電話,更新您的用戶界面的方法,你需要Invoke您的控制。否則,您將通過嘗試訪問不屬於定時器觸發的線程的對象來生成異常。

相關問題