笑嘻嘻的老爸 发表于 2023-4-11 16:40:01

CommunityToolkit.Mvvm8.1 viewmodel源生成器写法(3)

 
本系列文章导航
[*]https://www.cnblogs.com/aierong/p/17300066.html
[*]https://github.com/aierong/WpfDemo (自我Demo地址)


希望提到的知识对您有所提示,同时欢迎交流和指正
作者:aierong
出处:https://www.cnblogs.com/aierong 
说明

CommunityToolkit.Mvvm8.1最令人惊喜的是它提供的源生成器功能,它极大简化我们的mvvm代码
我们通过标记一个属性就可以实现某个功能,这个很方便快捷,推荐
常用标记总结
1.继承ObservableObject 并且类标记是分部类partial
2.私有变量标记属性
3.NotifyCanExecuteChangedFor  通知依赖命令
  NotifyPropertyChangedFor    通知依赖属性
4.RelayCommand  定义命令
5.OnPropertyChanged 手动通知属性更新
6.ButtonClickCommand.NotifyCanExecuteChanged() 手动通知命令更新
7.OnLastNameChanging OnLastNameChanged  某个属性改变
8.OnPropertyChanged  所有属性改变
 
定义viewmodel

定义vm时,请使用分部类,并且继承ObservableObject
public partial class DataViewModel2 : ObservableObject
{


ObservableProperty标记属性

定义属性如此简单:一个标记搞定
/*
标记后,会自动生成属性(大写命名),例如:下面会自动生成Title

注意:这个私有变量命名:必须是小写开头,或者下划线,或者m_
*/


private string title = "hello";

//public string Title
//{
//    get
//    {
//      return title;
//    }
//    set
//    {
//      //title = value;
//      //PropertyChanged?.Invoke( this , new PropertyChangedEventArgs( "Name" ) );

//      //SetProperty 相当与设置值,并且PropertyChanged通知调用
//      SetProperty( ref title , value );
//    }
//} 
NotifyPropertyChangedFor通知依赖属性

标识:在LastName改变后,去通知Caption
public string Caption
{
    get
    {
      return string.Format( "Title:{0}-{1}" , Title , LastName );
    }
}




private string lastName = "abc"; 
NotifyCanExecuteChangedFor通知依赖命令

在属性IsEnabled改变后,通知命令:ButtonClickCommand
/*
      
NotifyCanExecuteChangedFor是通知依赖命令(触发命令),相当于set中ButtonClickCommand.NotifyCanExecuteChanged();
*/



private bool isEnabled = false;

//public bool IsEnabled
//{
//    get => isEnabled;
//    set
//    {
//      SetProperty( ref isEnabled , value );

//      //通知命令 已经改变
//      ButtonClickCommand.NotifyCanExecuteChanged();
//    }
//}

//partial void OnIsEnabledChanged ( bool value )
//{
//   //如果上面的不写,可以这里手动通知更新
//    //ButtonClickCommand.NotifyCanExecuteChanged();
//} 
 
命令

RelayCommand标识定义一个命令,如此简单
/*
RelayCommand是定义命令,自动生成的命令名是方法名+Command,并且初始化
例如:下面的会自动生成ButtonClickCommand

CanExecute是指定一个判断方法,判断是否可用
*/


void ButtonClick ()
{
    //点击按钮,修改标题
    Title = "hello(改)";
}

bool CanButton ()
{
    return IsEnabled;
}

//public RelayCommand ButtonClickCommand
//{
//    get;
//}




void ButtonClickPar ( double val )
{
    Title = $"hello(改):{val}";
}

//public RelayCommand<double> ButtonClickParCommand
//{
//    get;
//} 
 
异步命令

把方法标识为async,即可定义为异步命令,它带有一个IsRunning属性,可以在view中做进度条判断

async Task AsyncButtonClick ()
{
    await Task.Delay( 4800 );
    Title = "hello(Task改)";
}




async Task AsyncButtonParClick ( double val )
{
    await Task.Delay( 4800 );
    Title = $"hello(Task改):{val}";

某个属性改变

On+属性Changing  On+属性Changed,可以记录某个属性值变化事件
/*
还可以实现2个方法:OnLastNameChanging OnLastNameChanged (注意2个方法只可以实现其中一个,或者都不实现(不能同时2个))
*/

//partial void OnLastNameChanging ( string value )
//{
//    Debug.WriteLine( value );
//}

partial void OnLastNameChanged ( string value )
{
    // 可以做一些其它事情 例如:属性改变后,消息通知某某某
    Debug.WriteLine( value );



    //说明:如果上面不写,可以这里手动通知属性更新
    //OnPropertyChanged( nameof( Caption ) );

所有属性改变

所有属性改变后都会调用这个事件,参数PropertyName可以区分具体哪个属性
/// <summary>
/// 所有属性改变
/// </summary>
/// <param name="e"></param>
protected override void OnPropertyChanged ( PropertyChangedEventArgs e )
{

    base.OnPropertyChanged( e );

    // 可以获取到是哪个属性改变了
    var _proname = e.PropertyName;

完整代码
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Diagnostics;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using CommunityToolkit.Mvvm.ComponentModel;
using CommunityToolkit.Mvvm.Input;

/*
这里演示自动生成属性和命令

1.继承ObservableObject 并且类标记是分部类partial
2.私有变量标记属性
3.NotifyCanExecuteChangedFor通知依赖命令
NotifyPropertyChangedFor    通知依赖属性
4.RelayCommand定义命令
5.OnPropertyChanged 手动通知属性更新
6.ButtonClickCommand.NotifyCanExecuteChanged() 手动通知命令更新
7.OnLastNameChanging OnLastNameChanged某个属性改变
8.OnPropertyChanged所有属性改变
*/

namespace WpfDemoNet6.Demo
{
    public partial class DataViewModel2 : ObservableObject
    {
      /*
      标记后,会自动生成属性(大写命名),例如:下面会自动生成Title

      注意:这个私有变量命名:必须是小写开头,或者下划线,或者m_
      */

      /*
      NotifyPropertyChangedFor 通知依赖属性Caption
      */

      
      
      private string title = "hello";

      //public string Title
      //{
      //    get
      //    {
      //      return title;
      //    }
      //    set
      //    {
      //      //title = value;
      //      //PropertyChanged?.Invoke( this , new PropertyChangedEventArgs( "Name" ) );

      //      //SetProperty 相当与设置值,并且PropertyChanged通知调用
      //      SetProperty( ref title , value );
      //    }
      //}


      /*
               
      NotifyCanExecuteChangedFor是通知依赖命令(触发命令),相当于set中ButtonClickCommand.NotifyCanExecuteChanged();
      */

      
      
      private bool isEnabled = false;

      //public bool IsEnabled
      //{
      //    get => isEnabled;
      //    set
      //    {
      //      SetProperty( ref isEnabled , value );

      //      //通知命令 已经改变
      //      ButtonClickCommand.NotifyCanExecuteChanged();
      //    }
      //}

      //partial void OnIsEnabledChanged ( bool value )
      //{
      //   //如果上面的不写,可以这里手动通知更新
      //    //ButtonClickCommand.NotifyCanExecuteChanged();
      //}




      /*
      RelayCommand是定义命令,自动生成的命令名是方法名+Command,并且初始化
      例如:下面的会自动生成ButtonClickCommand

      CanExecute是指定一个判断方法,判断是否可用
      */

      
      void ButtonClick ()
      {
            //点击按钮,修改标题
            Title = "hello(改)";
      }

      bool CanButton ()
      {
            return IsEnabled;
      }

      //public RelayCommand ButtonClickCommand
      //{
      //    get;
      //}



      public DataViewModel2 ()
      {
            //RelayCommand的第一个参数是命令调用语句
            //            第2个参数(可选)是否允许使用
            //ButtonClickCommand = new RelayCommand( () =>
            //{
            //    //点击按钮,修改标题
            //    Title = "hello(改)";
            //} , () =>
            //{
            //    return IsEnabled;
            //} );

            //ButtonClickParCommand = new RelayCommand<double>( ( double val ) =>
            //{
            //    Title = $"hello(改):{val}";
            //} );
      }



      
      void ButtonClickPar ( double val )
      {
            Title = $"hello(改):{val}";
      }

      //public RelayCommand<double> ButtonClickParCommand
      //{
      //    get;
      //}



      public string Caption
      {
            get
            {
                return string.Format( "Title:{0}-{1}" , Title , LastName );
            }
      }


      
      
      private string lastName = "abc";

      /*
      还可以实现2个方法:OnLastNameChanging OnLastNameChanged (注意2个方法只可以实现其中一个,或者都不实现(不能同时2个))
      */

      //partial void OnLastNameChanging ( string value )
      //{
      //    Debug.WriteLine( value );
      //}

      partial void OnLastNameChanged ( string value )
      {
            // 可以做一些其它事情 例如:属性改变后,消息通知某某某
            Debug.WriteLine( value );



            //说明:如果上面不写,可以这里手动通知属性更新
            //OnPropertyChanged( nameof( Caption ) );
      }



      /// <summary>
      /// 所有属性改变
      /// </summary>
      /// <param name="e"></param>
      protected override void OnPropertyChanged ( PropertyChangedEventArgs e )
      {

            base.OnPropertyChanged( e );

            // 可以获取到是哪个属性改变了
            var _proname = e.PropertyName;
      }

    }

导航https://github.com/aierong/WpfDemo/tree/main/WpfDemoNet6 (项目地址)
https://github.com/aierong/WpfDemo/blob/main/WpfDemoNet6/Demo/DataViewModel2.cs (代码地址)
 
A.Sql Server2005 Transact-SQL 新兵器学习
B.MCAD学习
C.代码阅读总结
D.ASP.NET状态管理
E.DB(数据库)
F.WAP
G.WinForm
H.Flex

希望上面提到的知识对您有所提示,同时欢迎交流和指正
作者:aierong
出处:http://www.cnblogs.com/aierong
贴子以"现状"提供且没有任何担保,同时也没有授予任何权利!
本文版权归作者所有,欢迎转载!
原创技术文章和心得,转载注明出处!这也是对原创者的尊重!


来源:https://www.cnblogs.com/aierong/archive/2023/04/11/17305990.html
免责声明:由于采集信息均来自互联网,如果侵犯了您的权益,请联系我们【E-Mail:cb@itdo.tech】 我们会及时删除侵权内容,谢谢合作!
页: [1]
查看完整版本: CommunityToolkit.Mvvm8.1 viewmodel源生成器写法(3)