2011-08-02 89 views
1

我正在研究將(作爲其功能的次要子集)提供倒計時器的應用程序。但是,可能並且會有同時發生多次倒計時的情況。每個Count Down在透視圖中都有自己的數據透視表項。由於這些倒計數是動態創建的,因此我將每個倒計時添加到列表中的文本塊(用作剩餘時間的輸出),並且設置了一個計時器來調用循環遍歷每個文本塊的方法在列表中並相應地更新它們。但是,我收到「System.UnauthorizedAccessException」異常,但我不完全確定原因。我被告知這是「無效的跨線程訪問」錯誤。使用計時器更新WP7中的文本塊的問題

這裏是有問題的行線:

c.Label.Dispatcher.BeginInvoke(delegate() { c.Label.Text = timeRemaining; }); 

以下是完整的方法:

private static void TimeRemainingCallback(object state) 
    { 
     if (countDowns.Count == 0) 
     { 
      return; 
     } 

     foreach (CountDown c in countDowns) 
     { 
      DateTime rightNow = DateTime.Today; 

      if (c.ExpirationDate >= rightNow) 
      { 
       DateTime offsetExpiration = c.ExpirationDate.Add(c.LocalNow); 
       TimeSpan timeDifference = offsetExpiration.Subtract(rightNow); 


       String timeRemaining = ""; 
       String timeDays = ""; 
       String timeHours = ""; 
       String timeMinutes = ""; 
       String timeSeconds = ""; 

       if (timeDifference.Days == 1) 
       { 
        timeDays = "1 Day"; 
       } 
       else 
       { 
        timeDays = timeDifference.Days + " Days"; 
       } 

       if (timeDifference.Hours == 1) 
       { 
        timeHours = "1 Hour"; 
       } 
       else 
       { 
        timeHours = timeDifference.Hours + " Hours"; 
       } 

       if (timeDifference.Minutes == 1) 
       { 
        timeMinutes = "1 Minute"; 
       } 
       else 
       { 
        timeMinutes = timeDifference.Minutes + " Minutes"; 
       } 

       if (timeDifference.Seconds == 1) 
       { 
        timeSeconds = "1 Second"; 
       } 
       else 
       { 
        timeSeconds = timeDifference.Seconds + " Seconds"; 
       } 

       if (timeDifference.Days == 0 && timeDifference.Hours >= 1) 
       { 
        timeRemaining = timeHours + " " + timeMinutes; 
       } 
       else if (timeDifference.Days == 0 && timeDifference.Hours == 0 && timeDifference.Minutes >= 1) 
       { 
        timeRemaining = timeMinutes + " " + timeSeconds; 
       } 
       else if (timeDifference.Days == 0 && timeDifference.Hours == 0 && timeDifference.Minutes == 0) 
       { 
        timeRemaining = timeSeconds; 
       } 
       else 
       { 
        timeRemaining = timeDays + " " + timeHours + " " + timeMinutes; 
       } 

       c.Label.Dispatcher.BeginInvoke(delegate() { c.Label.Text = timeRemaining; }); 
      } 
     } 
    } 

這裏是我創建的計時器,唯一一次回調中提到:

Timer updateRemainingTime = new Timer(TimeRemainingCallback, null, 0, 1000); 

該列表實際上充滿了包含日期時間和文本塊的對象(這裏稱爲標籤),因此c.Label交易。

timeRemaining是在timercallback中形成的剩餘時間的字符串。

有什麼想法發生了什麼?有關如何做到這一點的更好的想法?

+0

你介意發表一段代碼,說明你如何修改'timeRemaining'以及它在哪裏聲明? –

+0

@ Dennis我已經添加了完整的方法調用... – Hosemeyer

+0

另外,TimeRemainingCallback調用/有線(郵政編碼)在哪裏? –

回答

1

爲整個循環迭代調用Dispatcher,並刪除當前的Dispatcher調用。

Dispatcher.BeginInvoke(() => 
{ 
    foreach (CountDown c in countDowns) 
    { 
     // Actions here. 
     c.Label.Text = timeRemaining; 
    } 
}); 

我假設你有countDowns必將給您正在使用的列表UI控件。

+0

如何在沒有任何對象的情況下使用分派器? – Hosemeyer

+0

無論如何你在哪裏使用'Timer'?如果它位於'Page'內部,那麼您可以使用與其關聯的'Dispatcher'而不引用源對象。 –

+0

它在頁面內......但是在異步服務調用的回調方法中(因爲那時我知道數據被填充以便被定時器操縱)。 – Hosemeyer