2017-02-23 8 views
0

私はテスト用に使用しているコントローラの入力状態を設定できるC#/ WPF/MVVMを使用して小さなユーティリティを開発しています。私が開発しているアプリケーションとハードウェアとの通信はハードウェアとの唯一の方法であり、アプリケーションがに設定できるのはです。の状態はです。バインディングラジオボタンオブジェクトの現在の配列の要素にチェックされています

もう1つ言及しなければならない点は、このソリューションのいくつかの他の部分(これはすべてF#にあります)で既に定義されている種類があることです。私のアプリケーションを行うために、私は現在C#を使用しています。だから、F#で定義されたLocalControllerTypes.LocalController型をラップするために、多くの必要な情報を含んだUnitクラスを実行しました。 、私はenum可能InputStateを列挙していることを行うために

(現在ActiveまたはNormalがあるが、そのリストは、潜在的に、時間とともに成長できます)。また、各ユニットタイプに存在する入力数は異なります(一部は2、一部は4、一部はそれ以上)ので、選択されたユニットの配列InputsにバインドされたItemControlがあります。残念ながら入力の名前のみが含まれています私はそれを表示しなければならない。ユニットには、そのハードウェアと通信するハードウェア/ Webサービスにコマンドを送信するために使用するタイプの配列であるInputWritersの入力に関連する2つのプロパティがあり、InputStatesInputStateの配列です。 (ハードウェアから状態を取得することができないため)最後にアプリケーションに設定されているように、それぞれの入力があります。

今私は(私のViewModelに)現在SelectedUnitInputStateに(私はItemsControlItemTemplateとして定義するものである)ラジオボタンのIsCheckedプロパティをバインドしたいと思います。 の問題は、SelectedUnitInputStatesプロパティの同じインデックスで項目を取得するために、何らかの理由でラジオボタンがSelectedUnitのインデックスのInputs配列のインデックスであることを知る必要があるということです。

これを達成する方法はありますか?

MainWindow.xaml:

  ... 
      <ItemsControl Grid.Row="1" ItemsSource="{Binding SelectedUnit.LocalControllerInfo.Inputs}"> 
       <ItemsControl.ItemTemplate> 
        <DataTemplate> 
         <StackPanel Orientation="Horizontal"> 
          <TextBlock Margin="10" FontSize="15" Style="{StaticResource TextBlockNormalBase}" Text="{Binding InputName}"/> 
          <StackPanel Orientation="Horizontal"> 
           <RadioButton Margin="10" Foreground="White" Content="Normal" 
              IsChecked="{Binding Path=?, 
                   Converter={StaticResource inputToBoolConverter}, 
                   ConverterParameter=?}"/> 
           <RadioButton Margin="10" Foreground="White" Content="Active" 
              IsChecked="{Binding Path=?, 
                   Converter={StaticResource inputToBoolConverter}, 
                   ConverterParameter=?}"/> 
          </StackPanel> 
         </StackPanel> 
        </DataTemplate> 
       </ItemsControl.ItemTemplate> 
      </ItemsControl> 
      ... 

Unit.cs:

public class Unit : BindableObject 
{ 
    public enum InputState 
    { 
     Normal, 
     Active 
    } 

    private LocalControllerTypes.LocalController _localControllerInfo; 
    private LocalControllerTypes.ArduinoInjector[] _arduinoInjector; 
    private WebWriter.WebWriter[] _inputWriters; 
    private SNMPNetworkSwitchConnection.SNMPNetworkSwitchConnection _networkSwitchConnection; 
    private InputState[] _inputStates; 
    private bool _isUnitConnected; 

    public Unit(LocalControllerTypes.LocalController localControllerInfo, 
     LocalControllerTypes.ArduinoInjector[] arduinoInjector, 
     WebWriter.WebWriter[] inputWriters, 
     SNMPNetworkSwitchConnection.SNMPNetworkSwitchConnection networkSwitchConnection) 
    { 
     _localControllerInfo = localControllerInfo; 
     _arduinoInjector = arduinoInjector; 
     _inputWriters = inputWriters; 
     _networkSwitchConnection = networkSwitchConnection; 
     // This assumption might not always be true, but there is no way for now to get the input state 
     _inputStates = Enumerable.Repeat(InputState.Normal, _inputWriters.Length).ToArray(); 
     // This assumption might not always be true, but there is no way for now to get the connection state 
     _isUnitConnected = true; 
    } 

    public LocalControllerTypes.LocalController LocalControllerInfo 
    { 
     get 
     { 
      return _localControllerInfo; 
     } 
     set 
     { 
      if (_localControllerInfo != value) 
      { 
       _localControllerInfo = value; 
       RaisePropertyChanged(); 
      } 
     } 
    } 

    public LocalControllerTypes.ArduinoInjector[] ArduinoInjectors 
    { 
     get 
     { 
      return _arduinoInjector; 
     } 
     set 
     { 
      if (_arduinoInjector != value) 
      { 
       _arduinoInjector = value; 
       RaisePropertyChanged(); 
      } 
     } 
    } 

    public WebWriter.WebWriter[] InputWriters 
    { 
     get 
     { 
      return _inputWriters; 
     } 
     set 
     { 
      if (_inputWriters != value) 
      { 
       _inputWriters = value; 
       RaisePropertyChanged(); 
      } 
     } 
    } 

    public SNMPNetworkSwitchConnection.SNMPNetworkSwitchConnection NetworkSwitchConnection 
    { 
     get 
     { 
      return _networkSwitchConnection; 
     } 
     set 
     { 
      if (_networkSwitchConnection != value) 
      { 
       _networkSwitchConnection = value; 
       RaisePropertyChanged(); 
      } 
     } 
    } 

    public InputState[] InputStates 
    { 
     get 
     { 
      return _inputStates; 
     } 
     set 
     { 
      if (_inputStates != value) 
      { 
       _inputStates = value; 
       RaisePropertyChanged(); 
      } 
     } 
    } 

    public bool IsUnitConnected 
    { 
     get 
     { 
      return _isUnitConnected; 
     } 
     set 
     { 
      if (_isUnitConnected != value) 
      { 
       _isUnitConnected = value; 
       RaisePropertyChanged(); 
      } 
     } 
    } 
} 

MainViewModel.cs:

public class MainViewModel : INotifyPropertyChanged 
{ 
    private Unit _selectedUnit; 
    private ObservableCollection<Unit> _units; 
    private string _reader1RawCardData; 
    private string _reader2RawCardData; 
    private int _reader1BitsCount; 
    private int _reader2BitsCount; 

    public event PropertyChangedEventHandler PropertyChanged; 

    public MainViewModel(IUnitStore unitStore) 
    { 
     UnitStore = unitStore; 

     // We could use directly the unitstore instead of creating another container and binding on that, but 
     // not doing so will allow us to add unit filtering further down the road 
     _units = new ObservableCollection<Unit>(unitStore.Units); 
     _selectedUnit = _units.First(); 

     _reader1RawCardData = ""; 
     _reader2RawCardData = ""; 
     _reader1BitsCount = 0; 
     _reader2BitsCount = 0; 
    } 

    protected void RaisePropertyChanged([CallerMemberName]string propertName = "") 
    { 
     var temp = PropertyChanged; 
     if (temp != null) 
     { 
      temp(this, new PropertyChangedEventArgs(propertName)); 
     } 
    } 

    protected void RefreshUnitStore(object obj) 
    { 
     UnitStore.UpdateStore(); 
     Units = new ObservableCollection<Unit>(UnitStore.Units); 
     SelectedUnit = Units.First(); 
    } 

    protected void SendReaderCardSwipe(object obj) 
    { 
     int unitReaderNumber = (int)obj; 
     IPAddress arduinoIp = SelectedUnit.LocalControllerInfo.Readers[unitReaderNumber - 1].InjectorIp; 
     int injectorNumber = SelectedUnit.LocalControllerInfo.Readers[unitReaderNumber - 1].InjectorNumber; 
     string serviceUrl = SelectedUnit.ArduinoInjectors.Where(injector => injector.Ip.Equals(arduinoIp)).First().Url; 

     InjectorInterface.CardSwipe<IPAddress>(serviceUrl, arduinoIp, injectorNumber, Reader1BitsCount, Reader1RawCardData); 
    } 

    protected void UpdateSelectedUnitConnectionState(object obj) 
    { 
     ((INetworkConnection.INetworkConnection)SelectedUnit.NetworkSwitchConnection).SetConnection(SelectedUnit.IsUnitConnected); 
    } 

    public IUnitStore UnitStore 
    { 
     get; 
     private set; 
    } 

    public Unit SelectedUnit 
    { 
     get 
     { 
      return _selectedUnit; 
     } 
     set 
     { 
      if (_selectedUnit != value) 
      { 
       _selectedUnit = value; 
       RaisePropertyChanged(); 
      } 
     } 
    } 

    public ObservableCollection<Unit> Units 
    { 
     get 
     { 
      return _units; 
     } 
     set 
     { 
      if (_units != value) 
      { 
       _units = value; 
       RaisePropertyChanged(); 
      } 
     } 
    } 

    public string Reader1RawCardData 
    { 
     get 
     { 
      return _reader1RawCardData; 
     } 
     set 
     { 
      if (_reader1RawCardData != value) 
      { 
       _reader1RawCardData = value; 
       RaisePropertyChanged(); 
      } 
     } 
    } 

    public string Reader2RawCardData 
    { 
     get 
     { 
      return _reader2RawCardData; 
     } 
     set 
     { 
      if (_reader2RawCardData != value) 
      { 
       _reader2RawCardData = value; 
       RaisePropertyChanged(); 
      } 
     } 
    } 

    public int Reader1BitsCount 
    { 
     get 
     { 
      return _reader1BitsCount; 
     } 
     set 
     { 
      if (_reader1BitsCount != value) 
      { 
       _reader1BitsCount = value; 
       RaisePropertyChanged(); 
      } 
     } 
    } 

    public int Reader2BitsCount 
    { 
     get 
     { 
      return _reader2BitsCount; 
     } 
     set 
     { 
      if (_reader2BitsCount != value) 
      { 
       _reader2BitsCount = value; 
       RaisePropertyChanged(); 
      } 
     } 
    } 

    public ICommand RefreshSourceCommand 
    { 
     get 
     { 
      return new RelayCommand(RefreshUnitStore); 
     } 
    } 

    public ICommand SendReaderCardSwipeCommand 
    { 
     get 
     { 
      return new RelayCommand(SendReaderCardSwipe); 
     } 
    } 

    public ICommand UpdateSelectedUnitConnectionStateCommand 
    { 
     get 
     { 
      return new RelayCommand(UpdateSelectedUnitConnectionState); 
     } 
    } 
} 

答えて

0

はあなたのItemsControlSelectedUnit.LocalControllerInfo.Inputsにバインドされています。 .Inputsの種類は何ですか?

あなたのバインディングはInputStateまたはInputNameにアクセスできません。それは、あなたのオリジナルの問題に対処するために

、一つの可能​​性は巣にいくつかのタプルこととそれに結合するであろう「何列挙型で何が起こっ配列項目を特定する方法」の範囲には本当にラ

ではありません
List<Tuple<int,State>> States = new List<Tuple<int,State>>(); 

States.Add(new Tuple<int, State>(1,State.Bar)); 
States.Add(new Tuple<int, State>(2, State.Foo)); 
States.Add(new Tuple<int, State>(3, State.Bar)); 
関連する問題