FloatingLabelComboBox can't seem to set binding data to codebehind

50 Views Asked by At

I have a project in order to create a custom control that binds properties to display the properties of the selected item.

For example, I have two instances of my CustomControl, one for "StudentName" and the other for "Student's BloodGroup." For StudentName, I want to bind it to StudentName, and for the BloodGroup, I want to use .

Q1: Why FloatingLabelComboBox can't to set binding data to codebehind.

Q2: how can i set second ComboBox SelectedItem match with SelectedItem of first ComboBox .

FloatingLabelComboBox :


  public class FloatingLabelComboBox : ComboBox
  {
        static FloatingLabelComboBox()
        {
            DefaultStyleKeyProperty.OverrideMetadata(typeof(FloatingLabelComboBox), new FrameworkPropertyMetadata(typeof(FloatingLabelComboBox)));
        }
        public static readonly DependencyProperty LabelTextProperty =
           DependencyProperty.Register("LabelText", typeof(string), typeof(FloatingLabelComboBox), new PropertyMetadata("LabelText"));

        public string LabelText
        {
            get { return (string)GetValue(LabelTextProperty); }
            set { SetValue(LabelTextProperty, value); }
        }

        public static readonly DependencyProperty LabelForegroundProperty =
            DependencyProperty.Register("LabelForeground", typeof(Brush), typeof(FloatingLabelComboBox), new PropertyMetadata(Brushes.AliceBlue));

        public Brush LabelForeground
        {
            get { return (Brush)GetValue(LabelForegroundProperty); }
            set { SetValue(LabelForegroundProperty, value); }
        }


        public static readonly DependencyProperty LabelFontSizeProperty =
            DependencyProperty.Register("LabelFontSize", typeof(double), typeof(FloatingLabelComboBox), new PropertyMetadata(10.0));

        public double LabelFontSize
        {
            get { return (double)GetValue(LabelFontSizeProperty); }
            set { SetValue(LabelFontSizeProperty, value); }
        }

  }


<ResourceDictionary
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
     xmlns:materialdesign="http://materialdesigninxaml.net/winfx/xaml/themes"
    xmlns:local="clr-namespace:FloatingLabelComboBox"
    xmlns:custom="clr-namespace:FloatingLabelComboBox.CustomControls">
    
    <Style TargetType="{x:Type custom:FloatingLabelComboBox }">
        <Setter Property="Template">
            <Setter.Value>
                <ControlTemplate TargetType="{x:Type  custom:FloatingLabelComboBox }">
                    <StackPanel FlowDirection="LeftToRight">
                        <TextBlock Text="{TemplateBinding LabelText}"
                               Foreground="{TemplateBinding LabelForeground}"
                               FontSize="{TemplateBinding LabelFontSize}"
                               VerticalAlignment="Stretch"
                               Margin="-5 0 0 0" />

                        <ComboBox x:Name="textBox" 
                                     ItemsSource="{TemplateBinding ItemsSource}"
                                  SelectedItem="{TemplateBinding SelectedItem}"
                                
                               DisplayMemberPath="{TemplateBinding DisplayMemberPath}"
                                
                                  HorizontalAlignment="Stretch"
                                  VerticalAlignment="Center"
                                  materialdesign:HintAssist.IsFloating="False"
                                  materialdesign:ColorZoneAssist.Mode="Dark"
                                  materialdesign:HintAssist.HintOpacity="0.10"
                                  materialdesign:HintAssist.FontFamily="Century Gothic"
                                  Foreground="{TemplateBinding Foreground}" />
                    </StackPanel>
                </ControlTemplate>
            </Setter.Value>
        </Setter>
    </Style>
</ResourceDictionary>

StudentModel :

 public class StudentModel : INotifyPropertyChanged
    {
        private int _studentId;
        public int StudentId
        {
            get => _studentId;
            set
            {
                if (value == _studentId) return;
                _studentId = value;
                OnPropertyChanged(nameof(_studentId));
            }
        }

   
    private string _studentName;
    public string StudentName
    {
      get => _studentName;
      set
      {
        _studentName = value;
        OnPropertyChanged();
      }
    }

    private ObservableCollection<string> _bloodgroup;
    public ObservableCollection<string> BloodGroup
    {
      get => _bloodgroup;
      set
      {
        _bloodgroup = value;
        OnPropertyChanged();
      }
    }


    public event PropertyChangedEventHandler PropertyChanged;

        private void OnPropertyChanged([CallerMemberName] string propertyName = null)
        {
            PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
        }

      }



 <Window.DataContext>
        <local:ViewModel/>
    </Window.DataContext>
    <Grid>
       <StackPanel Margin="30" Orientation="Horizontal" Height="80">
            <custom:FloatingLabelComboBox Width="160" 
                                         LabelText="Student" 
                                         Foreground="AliceBlue" 
                                         LabelForeground="LimeGreen"
                                         materialdesign:HintAssist.Hint="Student"
                                         FontSize="20"   
                                         LabelFontSize="13"
                                           ItemsSource="{Binding Students}"  
                                          DisplayMemberPath="StudentName"    SelectedItem="{Binding SelectedStudent,Mode=TwoWay,UpdateSourceTrigger=PropertyChanged}"
                                       
            />
            <custom:FloatingLabelComboBox Width="160" 
                                         Margin="40 0 0 0"
                                         LabelText="Blood Group" 
                                         Foreground="AliceBlue" 
                                         LabelForeground="LimeGreen"
                                         materialdesign:HintAssist.Hint="Blood Group"
                                         FontSize="20"
                                         LabelFontSize="13"   ItemsSource="{Binding SelectedStudent.BloodGroup}"
                                     SelectedItem="{Binding SelectedBloodGroup,Mode=TwoWay,UpdateSourceTrigger=PropertyChanged}"     />
            <StackPanel>
                <TextBlock Text="Categories" Width="100"/>
                <ComboBox ItemsSource="{Binding Students}" Foreground="White"  Width="100"  Height="50" DisplayMemberPath="StudentName"  SelectedItem="{Binding SelectedStudent}" />
            </StackPanel>
            <StackPanel>
                <TextBlock Text="Proucts" Width="100"/>
                <ComboBox ItemsSource="{Binding SelectedStudent.BloodGroup}" Width="100"  Height="50"  Foreground="White"   SelectedItem="{Binding SelectedBloodGroup}"   />
            </StackPanel>
        </StackPanel>
    </Grid>

ViewModel:

 public class ViewModel : INotifyPropertyChanged
  {
    
    public ViewModel()
    {
      this.Students = new ObservableCollection<StudentModel>()
            { new StudentModel(){ StudentName = "Jane", BloodGroup = new ObservableCollection<string>() { "A", "B", "AB", "0"  }},
              new StudentModel(){ StudentName = "Jone",  BloodGroup = new ObservableCollection<string>()  { "A", "B", "AB", "0" }},
              new StudentModel(){ StudentName = "Tina", BloodGroup = new ObservableCollection<string>() {"A", "B", "AB", "0"}}
            };
    

      this.SelectedStudent = Students.FirstOrDefault();
    }
    public ObservableCollection<StudentModel> Students { get; private set; }
    public ObservableCollection<string> BloodGroups { get; private set; }


    public StudentModel _selectedStudent;
    public StudentModel SelectedStudent
    {
      get { return _selectedStudent; }
      set
      {
        _selectedStudent = value;
        if (_selectedStudent != null)
        {
          BloodGroups = _selectedStudent.BloodGroup;
          OnPropertyChanged(nameof(BloodGroups));
        }

        OnPropertyChanged();
      }
    }

    public string _selectedBloodGroup ;
    public string SelectedBloodGroup
    {
      get { return _selectedBloodGroup; }
      set
      {
        _selectedBloodGroup = value;
        OnPropertyChanged();
      }
    }

    public event PropertyChangedEventHandler PropertyChanged;

    private void OnPropertyChanged([CallerMemberName] String propertyName = "")
    {
      PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
    }
  }

The result: enter image description here

0

There are 0 best solutions below