2017-11-19 16 views
0

모두! MVVM과 mySql 데이터베이스를 사용하여 WPF App을 구축하고 있습니다. 속성에 저장된 ComboBox에서 SelectedItem을 가져 오는 데 어려움을 겪고 있습니다. 기본적으로이 시점에서 SelectedItem을 텍스트 상자에 표시하고 싶습니다. 그것은 제가 Binding 과정을 더 잘 이해할 수 있도록 도와 줄 것입니다.WPF MVVM Combobox SelectionChanged/SelectedItem

궁극적으로 DB에서 다른 값을 가져 오기위한 참조로 저장된 값/속성을 사용하고 싶습니다. 다음은 몇 가지 샘플 코드입니다. 어떤 도움이라도 대단히 감사하겠습니다. 고맙습니다!

VIEW

 <Grid Background="AliceBlue"> 

     <Label Content="Street Address" HorizontalAlignment="Left" Margin="10,54,0,0" VerticalAlignment="Top" Width="87" Height="28"/> 
     <Label Content="State" HorizontalAlignment="Left" Margin="10,125,0,0" VerticalAlignment="Top" Width="87" Height="22"/> 


     <TextBox Name="txtStreetAddress" HorizontalAlignment="Left" Height="23" Margin="119,55,0,0" TextWrapping="Wrap" VerticalAlignment="Top" Width="120" 
       Text="{Binding StreetAddress, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" 
       /> 
     <ComboBox Name="cboState" 
       HorizontalAlignment="Left" Margin="119,125,0,0" VerticalAlignment="Top" Width="52" 
       DisplayMemberPath="StateAbb" 
       ItemsSource="{Binding StateAbbList}" 
       SelectedItem="{Binding SelectedStateAbb, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" 
       /> 

     <TextBox HorizontalAlignment="Left" Height="23" Margin="180,124,0,0" TextWrapping="Wrap" VerticalAlignment="Top" Width="59" 
       Text="{Binding SelectedStateAbb, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" 
       /> 


    </Grid> 

VIEW의 모델

public class AddStreetAddressVM : ObservableObject, IPageViewModel 
{ 

    public string Name 
    { 
     get 
     { 
      return "Add Street Address"; 
     } 
    } 

    const string dbConnectionString = @"datasource=localhost;port=3306;Initial Catalog='optest1a1';username=root;password="; 

    private ICommand _cboStateAbb; 

    private string _streetAddress; 
    private ObservableCollection<tblStateAbb> _stateAbbList; 
    private string _selectedStateAbb; 
    private int _selectedStateNum; 

    public ICommand CboStateAbb 
    { 
     get 
     { 
      if (_cboStateAbb == null) 
      { 
       _cboStateAbb = new RelayCommand(param => this.fillStateAbb(), null); 
      } 

      return _cboStateAbb; 
     } 
    } 

    public string StreetAddress 
    { 
     get { return _streetAddress; } 
     set { SetProperty(ref _streetAddress, value,() => StreetAddress); } 
    } 

    public ObservableCollection<tblStateAbb> StateAbbList 
    { 
     get { return _stateAbbList; } 
     set 
     { 
      SetProperty(ref _stateAbbList, value,() => StateAbbList); 
     } 
    } 

    public string SelectedStateAbb 
    { 
     get { return _selectedStateAbb; } 
     set 
     { 
      SetProperty(ref _selectedStateAbb, value,() => SelectedStateAbb); 
      //if (_selectedStateAbb != null) 
      //{ 
      // GetStateNum(); 
      //} 

      //_selectedStateAbb = value; 
     } 
    } 

    public int SelectedStateNum 
    { 
     get { return _selectedStateNum; } 
     set { SetProperty(ref _selectedStateNum, value,() => SelectedStateNum); } 
    } 

    public AddStreetAddressVM() : base() 
    { 
     StateAbbList = new ObservableCollection<tblStateAbb>(); 
     fillStateAbb(); 
    } 

    private void fillStateAbb() 
    { 
     using (MySqlConnection con = new MySqlConnection(dbConnectionString)) 
     { 
      StateAbbList = new ObservableCollection<tblStateAbb>(); 
      con.Open(); 
      string Query = "SELECT * FROM tbl_states"; 
      MySqlCommand createCommand = new MySqlCommand(Query, con); 
      MySqlDataReader dr = createCommand.ExecuteReader(); 
      int count = 1; 
      while (dr.Read()) 
      { 
       string StateAbb = dr.GetString(2); 
       tblStateAbb stateabb = new tblStateAbb(count, StateAbb); 
       StateAbbList.Add(stateabb); 
       count++; 
      } 
      con.Close(); 
     } 
    } 

    private void GetStateNum() 
    { 
     using (MySqlConnection con = new MySqlConnection(dbConnectionString)) 
     { 
      con.Open(); 
      string Query = "SELECT State_Num FROM tbl_states WHERE State_Abb='" + SelectedStateAbb + "' "; 
      MySqlCommand createCommand = new MySqlCommand(Query, con); 
      MySqlDataReader dr = createCommand.ExecuteReader(); 
      int count = 1; 
      while (dr.Read()) 
      { 
       int StateNum = dr.GetInt32(1); 
       StateNum = SelectedStateNum; 
      } 
      con.Close(); 
     } 

    } 

} 

모델 - 국가 약어

public class tblStateAbb : ObservableObject 
{ 
    private Int32 _count; 
    private String _stateAbb; 
    private Int32 _stateNum; 
    private ObservableCollection<tblStateAbb> _tblStateAbb; 

    public Int32 Count 
    { 
     get { return _count; } 
     set { SetProperty(ref _count, value,() => Count); } 
    } 

    public String StateAbb 
    { 
     get { return _stateAbb; } 
     set { SetProperty(ref _stateAbb, value,() => StateAbb); } 
    } 

    public Int32 StateNum 
    { 
     get { return _stateNum; } 
     set { SetProperty(ref _stateNum, value,() => StateNum); } 
    } 

    public ObservableCollection<tblStateAbb> StateAbbList 
    { 
     get { return _tblStateAbb; } 
     set { SetProperty(ref _tblStateAbb, value,() => StateAbbList); } 
    } 

    public tblStateAbb() : base() 
    { 
     Count = 0; 
     StateAbb = ""; 
     StateAbbList = new ObservableCollection<tblStateAbb>(); 
    } 

    public tblStateAbb(int count, string stateabb) : base() 
    { 
     Count = count; 
     StateAbb = stateabb; 
     StateAbbList = new ObservableCollection<tblStateAbb>(); 
    } 

    public tblStateAbb(int count, string stateabb, int statenum) : base() 
    { 
     Count = count; 
     StateAbb = stateabb; 
     StateNum = statenum; 
     StateAbbList = new ObservableCollection<tblStateAbb>(); 
    } 

} 

감시 오브젝트 (INotifyPropertyChange) SelectedStateAbb 이후

public class RelayCommand : ICommand 
{ 
    private Action<object> execute; 
    private Func<object, bool> canExecute; 

    public event EventHandler CanExecuteChanged 
    { 
     add { CommandManager.RequerySuggested += value; } 
     remove { CommandManager.RequerySuggested -= value; } 
    } 

    public RelayCommand(Action<object> execute, Func<object, bool> canExecute = null) 
    { 
     this.execute = execute; 
     this.canExecute = canExecute; 
    } 

    public bool CanExecute(object parameter) 
    { 
     return this.canExecute == null || this.canExecute(parameter); 
    } 

    public void Execute(object parameter) 
    { 
     this.execute(parameter); 
    } 
} 
+1

도움이 필요하다는 것을 공정하다고 생각하고 게시 한 코드를 모두 읽으라고 요청하십니까? 문제의 범위를 좁히고 코드의 해당 부분 만 게시하십시오. – CodingYoshi

+0

왜 관심이있는 부분을 읽지 않는가? 보기 만 게시하면된다고 생각되면보기 만 읽고 다른 모든 것은 무시하십시오. 아니? – Progolfer79

+1

글쎄, 나는 그 중 하나를 읽는 것에 관심이 없다. 솔직히 말해서 대부분의 사람들은 관심이 없습니다. 내가 만들고있는 요점은 당신이 당신의 질문에 약간의 노력을 기울여 사람들이 당신을 도울 수 있도록 쉽게 만들어야한다는 것입니다. 바로 지금 쉽지 않습니다. 말이 돼? – CodingYoshi

답변

0

string입니다

public abstract class ObservableObject : INotifyPropertyChanged 
{ 
    public event PropertyChangedEventHandler PropertyChanged; 

    protected virtual void OnPropertyChanged(string propName) 
    { 
     Debug.Assert(GetType().GetProperty(propName) != null); 

     var pc = PropertyChanged; 
     if (pc != null) 
     { 
      pc(this, new PropertyChangedEventArgs(propName)); 
     } 
    } 

    protected bool SetProperty<T>(ref T field, T value, string propName) 
    { 
     if (!EqualityComparer<T>.Default.Equals(field, value)) 
     { 
      field = value; 
      OnPropertyChanged(propName); 
      return true; 
     } 

     return false; 
    } 

    protected bool SetProperty<T>(ref T field, T value, Expression<Func<T>> expr) 
    { 
     if (!EqualityComparer<T>.Default.Equals(field, value)) 
     { 
      field = value; 
      var lambda = (LambdaExpression)expr; 
      MemberExpression memberExpr; 

      if (lambda.Body is UnaryExpression) 
      { 
       var unaryExpr = (UnaryExpression)lambda.Body; 
       memberExpr = (MemberExpression)unaryExpr.Operand; 
      } 
      else 
      { 
       memberExpr = (MemberExpression)lambda.Body; 
      } 

      OnPropertyChanged(memberExpr.Member.Name); 
      return true; 
     } 

     return false; 
    } 
} 

릴레이 COMMAND, 당신은 ComboBox에 "StateAbb"의 SelectedValuePath 속성을 설정하기 위해 SelectedValue 속성을 결합한다 SelectedStateAbb :

<ComboBox Name="cboState" 
     HorizontalAlignment="Left" Margin="119,125,0,0" VerticalAlignment="Top" Width="52" 
     DisplayMemberPath="StateAbb" 
     SelectedValuePath="StateAbb" 
     ItemsSource="{Binding StateAbbList}" 
     SelectedValue="{Binding SelectedStateAbb, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"/> 

<TextBox HorizontalAlignment="Left" Height="23" Margin="180,124,0,0" TextWrapping="Wrap" VerticalAlignment="Top" Width="59" 
     Text="{Binding SelectedStateAbb, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" /> 
+0

이것은 잘 작동합니다. CodingYoshi와 Roger Leblanc의 답변 (원래의 의견에 따르면)도 효과가있었습니다. 모든 도움과 의견을 보내 주셔서 대단히 감사합니다! 나는 앞으로 내 질문에 더 간결하게하려고 노력할 것이다. 건배! – Progolfer79