2016-04-19 70 views
0

我是WPF的新手,所以可能會非常簡單,我錯過了。Databound列表框不更新到可觀察集合的正確值WPF

我有一個列表框,它是從static observableCollection<myClass>持有databound類屬性。該集合每秒從網絡流源更新幾次,從調試中我可以看出,集合正在更新。聲明如下:static ObservableCollection<PumpItem> pumpCollection = new ObservableCollection<PumpItem>();其中PumpItem是我班的名字。

這並不是說列表框沒有顯示任何東西,但它正在更新以顯示添加到集合中的任何新值,但這些值只反映了它們進入集合的第一刻的屬性。

列表框的值被綁定爲這樣:

<ListBox x:Name="pumpListBox" ItemsSource="{Binding PumpCollection}" Grid.IsSharedSizeScope="True" Margin="0,0,153,0"> 
     <ListBox.ItemTemplate> 
      <DataTemplate> 
       <Grid> 
        <Grid.ColumnDefinitions> 
         <ColumnDefinition SharedSizeGroup="ID" /> 
         <ColumnDefinition SharedSizeGroup="State" /> 
         <ColumnDefinition SharedSizeGroup="Selection" /> 
         <ColumnDefinition SharedSizeGroup="Fuel Pumped" /> 
         <ColumnDefinition SharedSizeGroup="Cost" /> 
        </Grid.ColumnDefinitions> 
        <TextBlock Margin="2" Text="{Binding PumpID}" Grid.Column="0"/> 
        <TextBlock Margin="2" Text="{Binding State}" Grid.Column="1"/> 
        <TextBlock Margin="2" Text="{Binding Selection}" Grid.Column="2"/> 
        <TextBlock Margin="2" Text="{Binding FuelPumped}" Grid.Column="3"/> 
        <TextBlock Margin="2" Text="{Binding FuelCost}" Grid.Column="4"/> 
       </Grid> 
      </DataTemplate> 
     </ListBox.ItemTemplate> 
    </ListBox> 

我有這樣的聲明後面的代碼中,以資源設置爲集合:

public static ObservableCollection<PumpItem> PumpCollection 
     { 
      get { return pumpCollection; } 

     } 

在我`主窗口( )構造函數我已經設置:

this.DataContext = this; 

之前InitialiseComponent(); and my background worker thread to receive network inputs to update the list: worker.RunWorker異步();`

這個後臺線程然後循環不斷地從流將更新集合,並調用資源更新:

private void worker_DoWork(object sender, DoWorkEventArgs e) 
    { 
     //background tasks 
     Thread.Sleep(500); //allows the ui time to update and initialise 
     string s_decryptedMessage = string.Empty; 

     App.Current.Dispatcher.Invoke((Action)(() => 
     { 
      Resources["PumpCollection"] = pumpCollection; 

     })); 


     while (true) 
     { 

      byteMessage = Recieve(stream);//get the number of pumps about to be recieved 
      Interact(byteMessage); //signal server to update pumplist 

     } 
} 

如果有幫助,我的類代碼是這樣的:

namespace PoSClientWPF 

{ 公共枚舉pumpState { 可用, 等待, 抽, 支付 };

public enum fuelSelection 
{ 
    Petrol, 
    Diesel, 
    LPG, 
    Hydrogen, 
    None 

}; 
public class PumpItem 
{ 
    private string pumpID; 
    public string PumpID 
    { 
     get 
     { 
      return pumpID; 
     } 
     set 
     { 
      pumpID = value; 
     } 
    } 

    private double fuelPumped; 
    public double FuelPumped 
    { 
     get 
     { 
      return fuelPumped; 
     } 
     set 
     { 
      fuelPumped = value; 
     } 
    } 

    private double fuelCost; 
    public double FuelCost 
    { 
     get 
     { 

      return fuelCost; 
     } 
     set 
     { 

      fuelCost = Math.Round(value, 2); //cost to two DP 
     } 
    } 

    private fuelSelection selection; 
    public fuelSelection Selection 
    { 
     get 
     { 
      return selection; 
     } 
     set 
     { 
      selection = value; 
     } 
    } 

    private pumpState state; 
    public pumpState State 
    { 
     get 
     { 
      return state; 
     } 
     set 
     { 
      state = value; 
     } 
    } 

    public PumpItem(string _ID, pumpState _state, fuelSelection _selection) 
    { 
     this.pumpID = _ID; 
     this.FuelPumped = 0; 
     this.FuelCost = 0; 
     this.Selection = _selection; 
     this.State = _state; 
    } 
} 

}

正如我所說的,我很新的WPF所以將不勝感激任何指導或解決方案。謝謝。

+1

'這些只反映了他們進入集合的第一刻的屬性。通知ui關於viewModel(在PumpItem中)變化的最簡單方法是在PumpItem中實現'INotifyPropertyChanged'並在setter中引發OnPropertyChanged事件 – ASh

+0

爲什麼你的PumpCollection是靜態的?這是設計決定,還是試圖讓綁定工作? –

+0

@MattWilkinson你得到了我,認爲這是一種絕望的行爲。想不到爲什麼我需要靜態的任何理由。所以回到公共場合吧。 (如果您引用了get方法PumpCollection,而不是我想要靜態的實際pumpCollection集合。 – James

回答

1

灰是完全正確的,但這裏是一個簡單的例子,您可以瀏覽。這是典型的所有ViewModel繼承的ViewModelBase的示例。從我的回購之一。這你將如何調用你的OnChangedEvent。

private sample _Item; 
    public sample Item 
    { 
     get 
     { 
      return _Item; 
     } 
     set 
     { 
      if (_Item != value) 
      { 
       _Item = value; 
       OnPropertyChanged("Item"); 
      } 
     } 
    } 

這會得到它更新所有屬性更改時的位置。

+0

我確實最終走下了這條路,並設法獲得了所需的功能。還要感謝這個非常有用的文章http://www.blackwasp.co.uk/INotifyPropertyChanged.aspx – James

相關問題