无法更改按钮的 IsEnabled 状态
CAN NOT get my button's IsEnabled state to change
我已经尝试了无数种方法到星期天让它工作,但我显然错过了一些东西,因为我的“Register
”按钮是没有无论我做什么都启用。
在我的 XAML:
<Button Text="Register"
Style="{StaticResource RegularButtonStyle}"
WidthRequest="280"
x:Name="RegisterButton">
<!-- I HAD the following, but it wasn't working so I finally decided to try DataTriggers -->
<!-- bindings:Bi.nd="Clicked RegisterButtonClickedCommand;IsEnabled IsRegisterButtonEnabled"> -->
<Button.Triggers>
<DataTrigger TargetType="Button"
Binding="{Binding IsRegisterButtonEnabled}"
Value="False">
<Setter Property="IsEnabled" Value="False"></Setter>
</DataTrigger>
<DataTrigger TargetType="Button"
Binding="{Binding IsRegisterButtonEnabled}"
Value="True">
<Setter Property="IsEnabled" Value="True"></Setter>
</DataTrigger>
</Button.Triggers>
</Button>
在视图模型中:
public class RegisterViewModel : MvxViewModel
{
...
private bool _isRegisterButtonEnabled;
public bool IsRegisterButtonEnabled
{
get => ShouldEnableRegisterButton();
set
{
_isRegisterButtonEnabled = value;
SetProperty(ref _isRegisterButtonEnabled, value);
}
}
...
public IMvxCommand RegisterButtonClickedCommand { get; private set; }
...
private void InitializeCommands()
{
...
RegisterButtonClickedCommand = new MvxCommand(RegisterUser);
}
...
private bool ShouldEnableRegisterButton()
{
var isValidUser = _userName.Validate();
var isValidPass = _password.Validate();
var isValidConfirmedPass = _confirmedPassword.Validate();
var shouldEnable = isValidUser && isValidPass && isValidConfirmedPass;
_mvxLogger.Log(MvxLogLevel.Trace, () => $"RegisterViewModel : ShouldEnableRegisterButton() called. Returning: {shouldEnable}");
return shouldEnable;
}
...
}
我已经阅读了 MvvmCross "Documentation",但它全都是会话式的,我找不到任何绑定到按钮的 IsEnabled 属性 的具体示例,并且具有足够的特异性让我到达那里。
当然希望得到一些帮助。 :)
家政信息:
我正在使用以下 NuGet 包 (/libraries)
- MvvmCross & MvvmCross.Forms v6.3.1
- Xamarin.Forms v4.0.0.497661
- Xamarin.Android.* 库都是 v28.0.0.1
然后想到我应该更新,因为有可用的更新,所以我更新到以下;
- MvvmCross & MvvmCross.Forms v6.4.1
- Xamarin.Forms v4.2.0.848062
- Xamarin.Android.* libs 现在都是 v28.0.0.3
共享内容也使用 .Net Standard v2.0.3。
你可以试试这个:
public class RegisterViewModel : INotifyPropertyChanged
{
public event PropertyChangedEventHandler PropertyChanged;
private bool _isRegisterButtonEnabled;
public bool IsRegisterButtonEnabled
{
set { _isRegisterButtonEnabled = value; PropertyChanged?.Invoke(this, new
PropertyChangedEventArgs(nameof(IsRegisterButtonEnabled))); }
get { return _isRegisterButtonEnabled; }
}
}
然后在 Xaml
<Button Text="Register"
Style="{StaticResource RegularButtonStyle}"
IsEnabled = "{Binding IsRegisterButtonEnabled}"
WidthRequest="280"
x:Name="RegisterButton">
</Button>
最终答案是一系列问题的结合,其中一个大问题可能需要在 SO 上重新 post/question。
这就是最终起作用的东西;
我将 Xaml 更新为以下内容;
<Button Text="Register"
Style="{StaticResource RegularButtonStyle}"
WidthRequest="280"
x:Name="RegisterButton"
Command="{Binding RegisterButtonClickedCommand}">
<Button.Triggers>
<DataTrigger TargetType="Button"
Binding="{Binding IsRegisterButtonEnabled}"
Value="False">
<Setter Property="IsEnabled" Value="False"></Setter>
</DataTrigger>
<DataTrigger TargetType="Button"
Binding="{Binding IsRegisterButtonEnabled}"
Value="True">
<Setter Property="IsEnabled" Value="True"></Setter>
</DataTrigger>
</Button.Triggers>
</Button>
还RegisterViewModel.cs更新为以下内容;
public class RegisterViewModel : MvxViewModel, INotifyPropertyChanged
{
...
// Added this (and the inheriting from INotify.. [per @Adlorem]
public event PropertyChangedEventHandler PropertyChanged;
private bool _isRegisterButtonEnabled;
public bool IsRegisterButtonEnabled
{
get
{
_mvxLogger.Log(MvxLogLevel.Trace,
() => $"RegisterViewModel : IsRegisterButtonEnabled property get called. Returning: {_isRegisterButtonEnabled}");
return _isRegisterButtonEnabled;
}
set
{
_isRegisterButtonEnabled = value;
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(nameof(IsRegisterButtonEnabled)));
_mvxLogger.Log(MvxLogLevel.Trace,
() => $"RegisterViewModel : IsRegisterButtonEnabled property set called. value: {value}");
}
}
...
private bool ShouldEnableRegisterButton()
{
var isValidUser = _userName.Validate();
var isValidPass = _password.Validate();
var isValidConfirmedPass = _confirmedPassword.Validate();
var shouldEnable = isValidUser && isValidPass && isValidConfirmedPass;
// Must set this or the PropertyChanged definitely won't fire!
IsRegisterButtonEnabled = shouldEnable;
_mvxLogger.Log(MvxLogLevel.Trace,
() => $"RegisterViewModel : ShouldEnableRegisterButton() called. Returning: {shouldEnable}");
return shouldEnable;
}
...
}
显然这不是最优的。 MvvmCross
的 SetProperty()
应该触发 PropertyChanged 事件,但由于某些原因它没有。
我已经尝试了无数种方法到星期天让它工作,但我显然错过了一些东西,因为我的“Register
”按钮是没有无论我做什么都启用。
在我的 XAML:
<Button Text="Register"
Style="{StaticResource RegularButtonStyle}"
WidthRequest="280"
x:Name="RegisterButton">
<!-- I HAD the following, but it wasn't working so I finally decided to try DataTriggers -->
<!-- bindings:Bi.nd="Clicked RegisterButtonClickedCommand;IsEnabled IsRegisterButtonEnabled"> -->
<Button.Triggers>
<DataTrigger TargetType="Button"
Binding="{Binding IsRegisterButtonEnabled}"
Value="False">
<Setter Property="IsEnabled" Value="False"></Setter>
</DataTrigger>
<DataTrigger TargetType="Button"
Binding="{Binding IsRegisterButtonEnabled}"
Value="True">
<Setter Property="IsEnabled" Value="True"></Setter>
</DataTrigger>
</Button.Triggers>
</Button>
在视图模型中:
public class RegisterViewModel : MvxViewModel
{
...
private bool _isRegisterButtonEnabled;
public bool IsRegisterButtonEnabled
{
get => ShouldEnableRegisterButton();
set
{
_isRegisterButtonEnabled = value;
SetProperty(ref _isRegisterButtonEnabled, value);
}
}
...
public IMvxCommand RegisterButtonClickedCommand { get; private set; }
...
private void InitializeCommands()
{
...
RegisterButtonClickedCommand = new MvxCommand(RegisterUser);
}
...
private bool ShouldEnableRegisterButton()
{
var isValidUser = _userName.Validate();
var isValidPass = _password.Validate();
var isValidConfirmedPass = _confirmedPassword.Validate();
var shouldEnable = isValidUser && isValidPass && isValidConfirmedPass;
_mvxLogger.Log(MvxLogLevel.Trace, () => $"RegisterViewModel : ShouldEnableRegisterButton() called. Returning: {shouldEnable}");
return shouldEnable;
}
...
}
我已经阅读了 MvvmCross "Documentation",但它全都是会话式的,我找不到任何绑定到按钮的 IsEnabled 属性 的具体示例,并且具有足够的特异性让我到达那里。
当然希望得到一些帮助。 :)
家政信息: 我正在使用以下 NuGet 包 (/libraries)- MvvmCross & MvvmCross.Forms v6.3.1
- Xamarin.Forms v4.0.0.497661
- Xamarin.Android.* 库都是 v28.0.0.1
- MvvmCross & MvvmCross.Forms v6.4.1
- Xamarin.Forms v4.2.0.848062
- Xamarin.Android.* libs 现在都是 v28.0.0.3
共享内容也使用 .Net Standard v2.0.3。
你可以试试这个:
public class RegisterViewModel : INotifyPropertyChanged
{
public event PropertyChangedEventHandler PropertyChanged;
private bool _isRegisterButtonEnabled;
public bool IsRegisterButtonEnabled
{
set { _isRegisterButtonEnabled = value; PropertyChanged?.Invoke(this, new
PropertyChangedEventArgs(nameof(IsRegisterButtonEnabled))); }
get { return _isRegisterButtonEnabled; }
}
}
然后在 Xaml
<Button Text="Register"
Style="{StaticResource RegularButtonStyle}"
IsEnabled = "{Binding IsRegisterButtonEnabled}"
WidthRequest="280"
x:Name="RegisterButton">
</Button>
最终答案是一系列问题的结合,其中一个大问题可能需要在 SO 上重新 post/question。
这就是最终起作用的东西;
我将 Xaml 更新为以下内容;
<Button Text="Register"
Style="{StaticResource RegularButtonStyle}"
WidthRequest="280"
x:Name="RegisterButton"
Command="{Binding RegisterButtonClickedCommand}">
<Button.Triggers>
<DataTrigger TargetType="Button"
Binding="{Binding IsRegisterButtonEnabled}"
Value="False">
<Setter Property="IsEnabled" Value="False"></Setter>
</DataTrigger>
<DataTrigger TargetType="Button"
Binding="{Binding IsRegisterButtonEnabled}"
Value="True">
<Setter Property="IsEnabled" Value="True"></Setter>
</DataTrigger>
</Button.Triggers>
</Button>
还RegisterViewModel.cs更新为以下内容;
public class RegisterViewModel : MvxViewModel, INotifyPropertyChanged
{
...
// Added this (and the inheriting from INotify.. [per @Adlorem]
public event PropertyChangedEventHandler PropertyChanged;
private bool _isRegisterButtonEnabled;
public bool IsRegisterButtonEnabled
{
get
{
_mvxLogger.Log(MvxLogLevel.Trace,
() => $"RegisterViewModel : IsRegisterButtonEnabled property get called. Returning: {_isRegisterButtonEnabled}");
return _isRegisterButtonEnabled;
}
set
{
_isRegisterButtonEnabled = value;
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(nameof(IsRegisterButtonEnabled)));
_mvxLogger.Log(MvxLogLevel.Trace,
() => $"RegisterViewModel : IsRegisterButtonEnabled property set called. value: {value}");
}
}
...
private bool ShouldEnableRegisterButton()
{
var isValidUser = _userName.Validate();
var isValidPass = _password.Validate();
var isValidConfirmedPass = _confirmedPassword.Validate();
var shouldEnable = isValidUser && isValidPass && isValidConfirmedPass;
// Must set this or the PropertyChanged definitely won't fire!
IsRegisterButtonEnabled = shouldEnable;
_mvxLogger.Log(MvxLogLevel.Trace,
() => $"RegisterViewModel : ShouldEnableRegisterButton() called. Returning: {shouldEnable}");
return shouldEnable;
}
...
}
显然这不是最优的。 MvvmCross
的 SetProperty()
应该触发 PropertyChanged 事件,但由于某些原因它没有。