2015-12-17 7 views
5

पर बदलते हुए मैं एमवीवीएम पैटर्न में एक सच्चा शुरुआत कर रहा हूं। मैं बटन के क्लिक पर ग्रिड के बैकगॉउंड को बदलने की कोशिश कर रहा हूं। मेरे पास एक बटन युक्त एक ग्रिड वाला एक एक्सएमएल है, और एक व्यूमोडेल .cs जहां से मैं बटन के क्लिक पर ग्रिड की पृष्ठभूमि बदलना चाहता हूं। वहाँ तक मैं सिर्फ एक संदेशबॉक्स दिखाने के लिए सफल होने जब मैं क्लिक किया ...एमवीवीएम ग्रिड के पृष्ठभूमि रंग को

.xaml कोड:

<Window x:Class="WpfSimple.MainWindow" 
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
    xmlns:local="clr-namespace:WpfSimple" 
    Title="MainWindow" Height="150" Width="370"> 
<Window.DataContext> 
    <local:MainWindowViewModel/> 
</Window.DataContext> 
    <Grid> 
    <Button Content="Click" 
      Height="23" 
      HorizontalAlignment="Left" 
      Background="Gray" 
      Margin="75.944,47.465,0,0" 
      Name="btnClick" 
      VerticalAlignment="Top" 
      Width="203" 
      Command="{Binding ButtonCommand}"/> 
     <!--What is necessary to add for changing grid color ? Commandparameter ?--> 
</Grid> 

MainWindowViewModel.cs कोड:

namespace WpfSimple 
{ 
    class MainWindowViewModel 
    { 
     private ICommand m_ButtonCommand; 
     public ICommand ButtonCommand 
     { 
      get 
      { 
       return m_ButtonCommand; 
      } 
      set 
      { 
       m_ButtonCommand = value; 
      } 
     } 

     public MainWindowViewModel() 
     { 
      ButtonCommand=new RelayCommand(new Action<object>(ChangeBgColor)); 
     } 

     public void ChangeBgColor(object obj) 
     { 
      /*HERE I WANT TO CHANGE GRID COLOR*/ 
     } 
    } 
} 

मेरे लिए खेद है बुरा अंग्रेजी।

सर्वश्रेष्ठ संबंध।

उत्तर

1

सभी की Fitst आप अपने ViewModel में INotifyPropertyChanged को लागू करना चाहिए:

public class MainWindowViewModel : INotifyPropertyChanged 
{ 
    public event PropertyChangedEventHandler PropertyChanged; 

    // This method is called by the Set accessor of each property. 
    // The CallerMemberName attribute that is applied to the optional propertyName 
    // parameter causes the property name of the caller to be substituted as an argument. 
    private void NotifyPropertyChanged([CallerMemberName] String propertyName = "") 
    { 
     if (PropertyChanged != null) 
     { 
      PropertyChanged(this, new PropertyChangedEventArgs(propertyName)); 
     } 
    } 
} 

फिर, अपने गुण सेटर को NotifyPropertyChanged() जोड़ें।

ठीक है। इसके बाद, अपने ViewModel करने के लिए अपने ग्रिड पृष्ठभूमि रंग के साथ नए संपत्ति जोड़ें:

private Brush _gridBackground; 
public Brush GridBackground 
{ 
    get { return _gridBackground; } 
    set 
    { 
     _gridBackground = value; 
     NotifyPropertyChanged(); 
    } 
} 

और अपनी संपत्ति के लिए अपने ग्रिड की पृष्ठभूमि बाँध:

<Grid Background="{Binding GridBackground}"> 

अंत में आप सिर्फ आदेश हैंडलर में GridBackground बदल सकते हैं:

public void ChangeBgColor(object obj) 
{ 
    GridBackground = Brushes.Blue; 
} 

आपको याद रखना चाहिए कि ब्रश जैसे कोड को अपने कोड में जोड़ने के लिए यह एक बुरा अभ्यास है। बेहतर तरीका है IValueConverter एक्सएएमएल कोड और बीसीएल कक्षाओं में अपने व्यूमोडेल में उपयोग करना। उदाहरण के लिए, आप ViewModel में गणना का उपयोग कर सकते हैं और इसे ValueConverter में ब्रश में परिवर्तित कर सकते हैं।

  1. अपने ViewModel की संपत्ति के लिए नए enum जोड़ें:

    public enum GridState { Valid, Invalid } 
    
  2. बदलें संपत्ति के प्रकार:

    private GridState _gridBackground; 
    public GridState GridBackground 
    { 
        get { return _gridBackground; } 
        set 
        { 
         _gridBackground = value; 
         NotifyPropertyChanged(); 
        } 
    } 
    
  3. मूल्य कनवर्टर के साथ नया वर्ग जोड़ें

    public class GridStateToBackgroundColorConverter : IValueConverter 
    { 
        #region IValueConverter Members 
    
        public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture) 
        { 
         GridState val = (GridState) value; 
         if(val == GridState.Valid) 
          return Brushes.Green; 
         return Brushes.Red; 
        } 
    
        public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture) 
        { 
         throw new NotSupportedException(); 
        } 
    
        #endregion 
    } 
    
  4. अपने नियंत्रण

    <UserControl.Resources> 
        <converters:GridStateToBackgroundColorConverter x:Key="gridStateToBackgroundColorConverter" /> 
    </UserControl.Resources> 
    
  5. अद्यतन करने के लिए नए स्थिर संसाधन जोड़े अपनी संपत्ति

    <Grid Background="{Binding GridBackground, Converter={StaticResource gridStateToBackgroundColorConverter}"> 
    
+0

हाँ! वडिम मार्टिनोव बहुत बहुत धन्यवाद! मुझे यकीन नहीं है कि मैं "INotifyPropertyChanged इंटरफेस" के उद्देश्य को समझ गया क्योंकि यह मुझे कुछ भी अधिसूचित नहीं है ... लेकिन आपका जवाब वास्तव में सहायक था। सर्वश्रेष्ठ संबंध। डेटा बाइंडिंग के लिए – Chefty

+0

@ सुरक्षा आईएनपीसी की आवश्यकता है। इसके बिना जब आप ViewModel में संपत्ति बदल देंगे तो आपका रंग नहीं बदलेगा। इसके अलावा, आईएनपीसी डेटा बाध्यकारी की एक आम विशेषता है। आप एमएसडीएन पर और अधिक पढ़ सकते हैं: https://msdn.microsoft.com/en-US/library/ms752347(v=vs.100).aspx –

+0

मैं अपने नियंत्रण में नया स्थिर संसाधन नहीं जोड़ सकता, यह एक त्रुटि बना देता है: " GridStateToBackgroundColorConverter एक WPF प्रोजेक्ट में समर्थित नहीं है "क्या यह सामान्य है? – Chefty

-1

के लिए बाध्य आप तो आप आदेश पैरामीटर का उपयोग कर सकते हैं ग्रिड पृष्ठभूमि रंग बदलना चाहते हैं। आप कमांड पैरामीटर के रूप में किसी भी यूआई नियंत्रण को पारित कर सकते हैं। आपके मामले में ग्रिड को अपने दृश्य मॉडल में ग्रिड तक पहुंचने के लिए पास करें। अपना ग्रिड नाम दें और कमांड पैरामीटर के रूप में उपयोग करने के लिए उस नाम का उपयोग करें। .xaml फ़ाइल को यह परिवर्तन करने के बाद

<Window x:Class="WpfSimple.MainWindow" 
     xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
     xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
     xmlns:local="clr-namespace:WpfSimple" 
     Title="MainWindow" Height="150" Width="370"> 
<Window.DataContext> 
    <local:MainWindowViewModel/> 
</Window.DataContext> 
<Grid Name="grid"> 
<Button Content="Click" 
     Height="23" 
     HorizontalAlignment="Left" 
     Background="Gray" 
     Margin="75.944,47.465,0,0" 
     Name="btnClick" 
     VerticalAlignment="Top" 
     Width="203" 
     Command="{Binding ButtonCommand}" 
     CommandParameter="{Binding Elementname="grid"}"/> 
</Grid> 

: इसके लिए आपको इस तरह कोड को लागू करने की जरूरत है। अपने व्यूमोडेल फ़ाइल में उपयोग करने के लिए इस उत्तीर्ण ग्रिड का उपयोग करने के लिए पैरामीटरेटेड रिले कमांड को कार्यान्वित करें। लागू करने Parameterized रिले कमान कोड निम्नलिखित को लागू करने का प्रयास करें:

private ICommand m_ButtonCommand; 
    public ICommand ButtonCommand 
    { 
     get 
     { 
      return m_ButtonCommand; 
     } 
     set 
     { 
      m_ButtonCommand = value; 
     } 
    } 

    public MainWindowViewModel() 
    { 
     ButtonCommand=new RelayCommand<Grid>(ChangeBgColor); 
    } 

    public void ChangeBgColor(Grid grid) 
    { 
     if(grid!=null) 
      grid.Background = Brushes.Red; //Any color you want to change. 
    } 

मुझे आशा है कि यह काम करेगा। धन्यवाद।

+0

हाय! ध्रुव पंचल धन्यवाद, लेकिन यह काम नहीं है। "RelayCommand " एक त्रुटि करें, और मैं इसे हल नहीं कर सकता। – Chefty

+0

@Chefty आपको कौन सी त्रुटि मिल रही है? क्या तुम मुझे बता सकते हो? क्या आपने अपने आवेदन में RelayCommand लागू किया है? –

+0

यह मुझे बताया गया है कि रिलेकॉमैंड का उपयोग तर्क तर्कों के साथ नहीं किया जा सकता है। – Chefty

संबंधित मुद्दे