MVVM - 点击按钮时调用函数的位置?

时间:2017-05-06 21:23:33

标签: c# ios xaml xamarin mvvm

所以我对MVVM架构如何帮助我以及如何在这种情况下使用它感到困惑:

我正在使用Xamarin,并在iOS中创建了我的视图和视图控制器作为示例。我也实现了MVVMLight工具包,并为视图和视图控制器创建了我的ViewModel。

我正在创建一个登录屏幕,因此用户输入他们的用户名和密码,并通过RaisePropertyChanged()事件在模型中更新它们。我的问题是我需要调用该函数来验证这些信息并将它们实际记录到系统中吗?

我已经实现了一个RelayCommand,只要点击按钮就会在ViewModel上调用一个方法,就像我在其他教程中看到的那样,但是我不确定我是否应该在这里调用验证代码。

我所拥有的一些例子:

LoginViewModel.cs:

public class LoginViewModel : ViewModelBase
{
    private string _username;
    private string _password;

    public RelayCommand LoginButtonCommand { get; private set; }
    public bool CanExecuteLoginCommand { get; set; }

    public LoginViewModel()
    {
        LoginButtonCommand = new RelayCommand(HandleLoginButtonCommand, () => CanExecuteLoginCommand);
        CanExecuteLoginCommand = true;
    }

    public string Username
    {
        get
        {
            return _username;
        }
        set
        {
            _username = value;
            RaisePropertyChanged(() => Username);
        }
    }

    public string Password
    {
        get
        {
            return _password;
        }
        set
        {
            _password = value;
            RaisePropertyChanged(() => Password);
        }
    }

    private void HandleLoginButtonCommand()
    {
        CanExecuteLoginCommand = false;

        //Validate login?

        CanExecuteLoginCommand = true;
    }
}

LoginViewController.cs:

public partial class LoginViewController : UIViewController
{
    private Binding _usernameTextFieldBinding;
    private Binding _passwordTextFieldBinding;
    private LoginViewModel _viewModel;

    public LoginViewController(IntPtr handle) : base(handle)
    {           
    }

    public override void ViewDidLoad()
    {
        base.ViewDidLoad();
        _viewModel = Application.Locator.Login;

        HideKeyboardHandling(UsernameTextField);
        HideKeyboardHandling(PasswordTextField);

        _usernameTextFieldBinding = this.SetBinding(
            () => _viewModel.Username)
            .ObserveSourceEvent("EditingDidEnd")
            .WhenSourceChanges(() => _viewModel.Username = UsernameTextField.Text);
        _passwordTextFieldBinding = this.SetBinding(
            () => _viewModel.Username)
            .ObserveSourceEvent("EditingDidEnd")
            .WhenSourceChanges(() => _viewModel.Password = PasswordTextField.Text);

        Loginbutton.SetCommand("TouchUpInside", _viewModel.LoginButtonCommand);
    }

    public override void DidReceiveMemoryWarning()
    {
        base.DidReceiveMemoryWarning();
        // Release any cached data, images, etc that aren't in use.     
    }

    void HideKeyboardHandling(UITextField textField)
    {
        textField.ShouldReturn = TextField =>
        {
            TextField.ResignFirstResponder();
            return true;
        };

        var gesture = new UITapGestureRecognizer(() => View.EndEditing(true));
        gesture.CancelsTouchesInView = false;
        View.AddGestureRecognizer(gesture);
    }
}

1 个答案:

答案 0 :(得分:3)

这完全取决于您希望单一责任原则(SPR)的严格程度。而这又取决于您的应用程序的复杂程度。应用程序越复杂,责任就越分散。

典型的MVVM实现处理ViewModel中的命令。 ViewModel将调用转发到Model中。但他仍然将两个职责(例如演示和命令处理)放入一个组件中,a.k.a ViewModel。

更严格的方法是让ViewModel只处理表示逻辑。创建一个单独的控制器来托管所有命令处理程序。并让命令处理程序转发对模型的调用。

更轻松的方法是在ViewModel中简单地实现业务逻辑。这意味着您没有业务逻辑层。如果您的应用程序足够简单,以至于业务逻辑层不值得付出努力,那么这很好。