Silverlight:在MVVM模式中打开子窗体(Child Window)

Silverlight:在MVVM模式中打开子窗体(Child Window),第1张

概述转载于 http://www.cnblogs.com/888h/archive/2010/12/08/1900149.html 这篇文章主要展示在Silverlight4的应用程序中,用MVVM模式【编者注:如果你对MVVM模式不太理解,请先去熟悉一下关于这方面的资料】怎么打开一个子窗体(Child Window),怎么向子窗体传值,以及怎么从子窗体返回值到主窗体等等   我使用的方法不是严格意义

转载于 http://www.cnblogs.com/888h/archive/2010/12/08/1900149.html

这篇文章主要展示在Silverlight4的应用程序中,用MVVM模式【编者注:如果你对MVVM模式不太理解,请先去熟悉一下关于这方面的资料】怎么打开一个子窗体(Child Window),怎么向子窗体传值,以及怎么从子窗体返回值到主窗体等等

  我使用的方法不是严格意义上的MVVM模式,因为我实际上在viewmodel中实例化了子窗体,这通常很不方便的。但是在Google上找了好长时间,仅仅找到了打开子窗体的工具包的向导,我认为最好的方法就是亲自去实现它。我期望最方便且有严格意义上的MVVM的解决方案在Silverlight5中能够实现。

  本篇文章只仅仅是一个概念的验证,并且是基于一个最简单的例子。MainPage.xaml文件包含两个TextBox控件,即name和Address,另外,子窗体和主窗体一样,也有两个的控件。当用户在主窗体输入他们的名字,然后点击按钮,那么子窗体就d出来。并且显示刚才输入的名字(请看下面的图片)。用户可以在子窗体中输入地址然后点击按钮,返回到主窗体【编者注:子窗体同时关闭】,那么主窗体上的地址框中就会显示刚才在子窗体中输入的地址。【编者注:这样就可以达到主窗体和子窗体之间互相传值】

  实现上面的功能是很简单的,仅仅在VIEw Model工程中创建一个子窗体。然后就可以实现子窗体和主窗体之间传递数据。然后创建每一个TextBox建一个属性,为button创建Command,这是为了打开和关闭子窗体并且传递属性值。需要注意的是子窗体没有viewmodel,所有的需要实现的业务都在主窗体的viewmodel中实现

  第一步:在viewmodel工程中创建一个子窗体,把它命名为MyChilDWindow.xmal.

  第二步:为MainPage创建一个viewmodel层。命名为:MainPage_viewmodel.cs

  第三步:通过MainPage_viewmodel.cs来实现 MainPage.xaml.cs和MyChilDWindow.xaml.cs 相互传值。【编者注:下面为各个文件的代码】

MainPage.xaml.cs:

namespace VIEw
{
    
public partial class MainPage : UserControl
    {

        
public MainPage()
        {
            InitializeComponent();
            
this.DataContext = new MainPage_viewmodel();
         }
     }
}
MyChilDWindow.xaml.cs: namespace viewmodel
{
    
public partial class MyChilDWindow : ChilDWindow
    {
        
public MyChilDWindow(MainPage_viewmodel ma)
        {
            InitializeComponent();
            
this.DataContext = ma;
        }

    }
}
第四步:在 MainPage_viewmodel.cs为主窗体每个TextBox建属性和viewmodel using System.ComponentModel;
using System.Collections.ObjectModel;
using viewmodel; 

namespace viewmodel
{
    
public class MainPage_viewmodel : INotifyPropertyChanged
    {
//PropertIEs of Mainpage
private string mynameVM = "";
        
public string MynameVM
        {

            
get { return mynameVM; }
            
set {
                mynameVM 
= value;
                RaisePropertyChanged(
"mynameVM");
            }
        }

        
private string myAddressVM = "";
        
public string MyAddressVM
        {

            
get { return myAddressVM; }
            
set
            {
                myAddressVM 
= value;
                RaisePropertyChanged(
"MyAddressVM");
            }
        }

//PropertIEs of ChilDWindow
        private string mynameCW = "";
        
public string MynameCW
        {

            
get { return mynameCW; }
            
set
            {
                mynameCW 
= value;
                RaisePropertyChanged(
"MynameCW");
            }
        }

        
private string myAddressCW = "";
        
public string MyAddressCW
        {

            
get { return myAddressCW; }
            
set
            {
                myAddressCW 
= value;
                RaisePropertyChanged(
"MyAddressCW");
            }
        }

          
//EventHandler
        public event PropertyChangedEventHandler PropertyChanged;
        
private voID RaisePropertyChanged(string propertyname)
        {
            
if (PropertyChanged != null)
            {
                PropertyChanged(
thisnew PropertyChangedEventArgs(propertyname));
            }
        }
    }

 }
第五步:如果以前没有创建这个,你就必须得在viewmodel中创建一个类DelegateCommand,主要是处理button的命令。因此,你必须创建这个类。代码如下:
using System;
using System.windows.input;

namespace viewmodel
{
    
public class DelegateCommand : ICommand //
    {
        
private Predicate<object> _canExecute;
        
private Action<object> _method;
        
public event EventHandler CanExecuteChanged;

        
public DelegateCommand(Action<object> method)
            : 
this(method, null)
        {
        }

        
public DelegateCommand(Action<object> method, Predicate<object> canExecute)
        {
            _method 
= method;
            _canExecute 
= canExecute;
        }

        
public bool CanExecute(object parameter)
        {
            
if (_canExecute == null)
            {
                
return true;
            }

            
return _canExecute(parameter);
        }

        
public voID Execute(object parameter)
        {
            _method.Invoke(parameter);
        }

        
protected virtual voID OnCanExecuteChanged(EventArgs e)
        {
            var canExecuteChanged 
= CanExecuteChanged;

            
if (canExecuteChanged != null)
                canExecuteChanged(
this, e);
        }

        
public voID RaiseCanExecuteChanged()
        {
            OnCanExecuteChanged(EventArgs.Empty);
        }
    }
}
第六步:在MainPage_viewmodel.cs创建一个Commands,它可以绑定到主窗体和子窗体中的按钮上。 using System.ComponentModel;
using System.Collections.ObjectModel;
using viewmodel; 

namespace viewmodel
{
    
public class MainPage_viewmodel : INotifyPropertyChanged
    {
//PropertIEs of Mainpage
private string mynameVM = "";
        
public string MynameVM
        {
            
get { return mynameVM; }
            
set {mynameVM = value;
                RaisePropertyChanged(
"mynameVM");
                 }
            }

        
private string myAddressVM = "";
        
public string MyAddressVM
        {

            
get { return myAddressVM; }
            
set
            { myAddressVM 
= value;
                RaisePropertyChanged(
"MyAddressVM");
            }
        }

//PropertIEs of ChilDWindow
        private string mynameCW = "";
        
public string MynameCW
        {

            
get { return mynameCW; }
            
set
            {  mynameCW 
= value;
                RaisePropertyChanged(
"MynameCW");
            }
        }

        
private string myAddressCW = "";
        
public string MyAddressCW
        {

            
get { return myAddressCW; }
            
set
            {  myAddressCW 
= value;
                RaisePropertyChanged(
"MyAddressCW");
            }
        }

         
//When the button is pressed in MainPage, executes method ExecuteOpenChilDWindow
        private DelegateCommand _openChilDWindow;
        
public DelegateCommand OpenChilDWindow
        {
            
get
            {
                
if (_openChilDWindow == null)
                    _openChilDWindow 
= new DelegateCommand(executeOpenChilDWindow);

                
return _openChilDWindow;
            }
        }

        
// New instance of ChilDWindow. Sets the nameProperty of the ChilDWindow equal to the name entered in the MainPage.
        MyChilDWindow cw;
        
private voID executeOpenChilDWindow(object parameter)
        {
            cw 
= new MyChilDWindow(this);
            MynameCW 
= MynameVM;
            cw.Show();
        }

      
//When OK-button is pressed in ChilDWindow
        private DelegateCommand _okChilDWindow;
        
public DelegateCommand OkChilDWindow
        {
            
get {
                
if (_okChilDWindow == null)
                    _okChilDWindow 
= new DelegateCommand(OkSaveChilDWindow);

                
return _okChilDWindow;
            }
        }
        
//MainPage Address property is set to the value entered in the address textBox in Child Window. Child Window is closed.
        private voID OkSaveChilDWindow(object parameter)
        {
            MyAddressVM 
= MyAddressCW;
            cw.Close();
        }

          
//EventHandler
        public event PropertyChangedEventHandler PropertyChanged;
        
private voID RaisePropertyChanged(string propertyname)
        {
            
if (PropertyChanged != null)
            {
                PropertyChanged(
thisnew PropertyChangedEventArgs(propertyname));
            }
        }
  }
}
第七步:在MainPage.xaml 和 MyChilDWindow.xaml中分别新增两个TextBox,然后把他们分别绑定到MainPage_viewmodel中的属性上。然后再分别建一个按钮,绑定到Command上。

MainPage.xaml

<StackPanel>

        <
GrID margin="0 10 0 5" WIDth="350">

    
<GrID.RowDeFinitions>
        
<RowDeFinition Height="*"/>
        
<RowDeFinition Height="*"/>
        
<RowDeFinition Height="*"/>

    
</GrID.RowDeFinitions>
    
<GrID.ColumnDeFinitions>
        
<ColumnDeFinition WIDth="150"/>
        
<ColumnDeFinition WIDth="*"/>

    
</GrID.ColumnDeFinitions>

    
<!--TextBlocks-->
    
<TextBlock Text="name:" textwrapPing="Wrap" margin="5,5,5" GrID.Row="0"  />
    
<TextBlock Text="Address:" GrID.Row="1" GrID.Column="0"  />

   
<!--TextBox, where the users enters data. Binds to the propertIEs of MainPage_viewmodel-->
  
<TextBox Text="{Binding MynameVM, Mode=TwoWay}" GrID.Row="0" GrID.Column="1"/>
  
<TextBox Text="{Binding MyAddressVM, Mode=TwoWay}"  GrID.Row="1" GrID.Column="1"/>

    
<button Content="Open Child Window"
            VerticalAlignment
="Center"
            HorizontalAlignment
="left"
            WIDth
="auto"
            margin
="5"
            GrID.Row
="2"
            Command
="{Binding OpenChilDWindow}" <!--Binds to CommandDelegate from the viewmodel -->
        
/>
        
</GrID>
    
</StackPanel>

MyChilDWindow.xaml
<GrID margin="0 30 0 5" WIDth="350">

    <
GrID.RowDeFinitions >
        
<RowDeFinition Height="auto"/>
        
<RowDeFinition Height="auto"/>
        
<RowDeFinition Height="205*"/>

    
</GrID.RowDeFinitions>
    
<GrID.ColumnDeFinitions>
        
<ColumnDeFinition WIDth="150"/>
        
<ColumnDeFinition WIDth="*"/>

    
</GrID.ColumnDeFinitions>

    
<TextBlock Text="name: " GrID.Row="0" />
    
<TextBlock Text="Address:" GrID.Row="1" GrID.Column="0"  />

    
<!-- TextBoxes are bind to the propertIEs from the viewmodel.  -->
    
<TextBox x:name="inputname" Text="{Binding MynameCW, Mode=TwoWay}" GrID.Row="0" GrID.Column="1" Height="20"/>
    
<TextBox x:name="OutputAddress" Text="{Binding MyAddressCW, Mode=TwoWay}" GrID.Row="1" GrID.Column="1" Height="20"/>

   
<!-- button comand bind to CommandDelegate from viewmodel -->
  
<button x:name="OKbutton" Command="{Binding OkChilDWindow}" Content="OK" WIDth="75" Height="23" margin="0,12,79,0" GrID.Row="2" GrID.Column="1"/>
</GrID> 翻译的不足之处,请多多指教。原文地址http://mariaevert.dk/thesis/?p=710 总结

以上是内存溢出为你收集整理的Silverlight:在MVVM模式中打开子窗体(Child Window)全部内容,希望文章能够帮你解决Silverlight:在MVVM模式中打开子窗体(Child Window)所遇到的程序开发问题。

如果觉得内存溢出网站内容还不错,欢迎将内存溢出网站推荐给程序员好友。

欢迎分享,转载请注明来源:内存溢出

原文地址: http://outofmemory.cn/web/1020392.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2022-05-23
下一篇 2022-05-23

发表评论

登录后才能评论

评论列表(0条)

保存