2011-12-31 59 views
1

在我的wp7.5應用程序中,我有一個塊需要顯示停止位(例如30,29,28 ... 1,0)。我嘗試過使用DispatchTimer和Timer類來實現這個功能,但沒有一個解決了我的問題。停止時鐘在wp7中的實現

方法1: 這裏是我用於DispatchTimer片斷,

DispatcherTimer dt = new DispatcherTimer(); 
dt.Interval = new TimeSpan(0, 0, 1); // 1 second 
dt.Tick += new EventHandler(dt_Tick); 

for(int count=0;count<30;count++) 
    dt.Start(); 

void dt_Tick(object sender, EventArgs e) 
{ 
    // my UI control update here 
} 
在我的Tick事件執行

我更新與時間計數器UI控件。我在這裏閱讀了一些關於同一主題的問題,因爲UI線程在某些場景中調度器刻度從不會觸發。它發生在我身上,tick事件從未解僱。

方法2: 我嘗試使用System.Threading.Timer類,

Timer timer = new Timer(TimerProc); 

for(int count=0;count<30;count++) 
    timer.Change(1000, 0); 

void TimerProc(object sender) 
{ 
    // my UI control update here 
} 

無我的方法奏效。我可能會問一個重複的問題,任何人都可以指出我在代碼中的錯誤行爲嗎?

回答

2

DispatcherTimerStart()之後的方法稱爲保留時間爲Tick event,直到你調用Stop()就可以了。所以,你不需要調用Start() 30次,但你必須保持一個計數器,並在Tick event處理後30只蜱停止計時:

private int counter; 

private void Start_Click(object sender, RoutedEventArgs e) 
{ 
    counter = 30; 
    DispatcherTimer dt = new DispatcherTimer(); 
    dt.Interval = new TimeSpan(0, 0, 1); // 1 second 
    dt.Tick += new EventHandler(dt_Tick); 
    dt.Start(); 
} 

void dt_Tick(object sender, EventArgs e) 
{ 
    if (counter >= 0) 
    { 
     timeText.Text = counter.ToString(); 
     counter--; 
    } 
    else 
     ((DispatcherTimer)sender).Stop(); 
} 

編輯:
如果DispatcherTimer的精度是不夠的你可以使用System.Threading.Timer代替,但在這種情況下,你必須調用Tick事件處理程序Dispatcher.BeginInvoke啓用UI線程對象的訪問:

private int counter; 

private void Start_Click(object sender, RoutedEventArgs e) 
{ 
    counter = 30; 
    timeText.Text = counter.ToString(); 
    Timer dt = new Timer(dt_Tick); 
    dt.Change(1000 /* delay to start the timer */, 1000 /* period time */); 
} 

private void dt_Tick(object sender) 
{ 
    if (counter > 0) 
    { 
     Dispatcher.BeginInvoke(() => timeText.Text = counter.ToString()); 
     counter--; 
    } 
    else 
     ((Timer) sender).Dispose(); 
} 
+0

感謝您的回答,但我注意到這種方法的問題。如果我使用20秒的間隔,實際上會循環到24秒。有什麼辦法可以使它準確嗎? – Mahender 2011-12-31 13:11:26

+0

在這種情況下,您可以使用Timmer,查看我的更新答案。 – nemesv 2011-12-31 13:52:36

0

的計時器滴答方法musn't可以在一個保持跟蹤時間。爲什麼?有兩個原因。

1/DispatcherTimer的每個Tick之間的間隔不精確,並且取決於您對UI執行的操作。它可以是1秒,就像它可以多一點。

2 /在前一個滴答結束後一秒鐘觸發下一個滴答。由於tick內的更新代碼需要一些時間,它會自動落後。例如,如果更新代碼需要0.1秒,則在1秒後觸發滴答聲,更新完成,並且在更新結束後1秒,下一個滴答聲將在定時器啓動後2.1秒!

因此,你應該保存的時間,當您啓動定時器,並計算所經過的時間,在每個刻度:

protected DispatcherTimer Timer { get; set; } 

    protected DateTime TimerStartTime { get; set; } 

    private void ButtonStart_Click(object sender, RoutedEventArgs e) 
    { 
     this.Timer = new DispatcherTimer(); 
     this.Timer.Interval = TimeSpan.FromSeconds(1); 
     this.Timer.Tick += this.Timer_Tick; 
     this.TimerStartTime = DateTime.Now; 
     this.Timer.Start(); 
    } 

    private void Timer_Tick(object sender, EventArgs e) 
    { 
     int elapsedSeconds = (int)DateTime.Now.Subtract(this.TimerStartTime).TotalSeconds; 

     this.TextTimer.Text = (30 - elapsedSeconds).ToString(); 
    } 

這樣一來,即使每一跳之間的時間是不準確的,該計時器不會表明錯誤的時間。您甚至可以將計時器時間間隔縮短到500 ms或更短,以便擁有更精確的計時器,而無需更改Tick方法。