EventToCommandBehavior 破坏 CheckBox 控件

问题描述 投票:0回答:1

在 Maui MvvM 项目中使用

EventToCommandBehaviors
此处),我尝试在选择
Checkbox
时触发方法,但出现此异常:

System.Reflection.TargetInitationException:“调用目标已引发异常”。

我在“真实”项目和沙盒解决方案上得到了完全相同的行为来重新创建问题。我还在项目的其他地方使用

EventToCommandBehaviors
,所以我知道我可以让它工作。

当代码尝试运行 XAML 时抛出异常。

问题可能出在我的 Binding 上,但我没有发现它有什么问题,除了它位于

CollectionView
深处。

我还在绑定到

DataTrigger
Frame
控件上使用
Checkbox
,但将其注释掉不会影响异常。

这是 XAML(很抱歉它太宽了):

<?xml version="1.0" encoding="utf-8" ?>
<ContentPage xmlns="http://schemas.microsoft.com/dotnet/2021/maui"
             xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
             xmlns:viewmodel="clr-namespace:Sandbox.ViewModel"
             xmlns:model="clr-namespace:Sandbox.Model"
             xmlns:toolkit="http://schemas.microsoft.com/dotnet/2022/maui/toolkit"
             x:DataType="viewmodel:CheckboxMethodPageViewModel"
             x:Class="Sandbox.View.CheckboxMethodPage"
             Title="CheckboxMethodPage">
            
      <Grid RowDefinitions="Auto,*">
            <Label Grid.Row="0" 
                   Margin="20,0,20,0" />

            <CollectionView Grid.Row="1" ItemsSource="{Binding Things}">
                  <CollectionView.ItemTemplate>
                        <DataTemplate >
                              <Grid Padding="5">
                                    <Frame Style="{StaticResource CardView}">
                                          <HorizontalStackLayout>
                                                <Label Text="{Binding Name}"/>

                                                <CheckBox>
                                                      <CheckBox.Behaviors>
                                                            <toolkit:EventToCommandBehavior EventName="CheckedChangedCommand"
                                                                                            Command="{Binding Source={RelativeSource AncestorType={x:Type viewmodel:CheckboxMethodPageViewModel}}, Path=CheckChanged}"/>
                                                      </CheckBox.Behaviors>
                                                </CheckBox>
                                          </HorizontalStackLayout>

                                          <Frame.Triggers>
                                                <DataTrigger TargetType="Frame"
                                                             Binding="{Binding Source={x:Reference checkBox}, Path=IsChecked}"
                                                             Value="true">
                                                      <Setter Property="Background"
                                                              Value="#dee7ef" />
                                                      <Setter Property="BorderColor"
                                                              Value="#952e31" />
                                                </DataTrigger>
                                          </Frame.Triggers>
                                    </Frame>
                              </Grid>
                        </DataTemplate>
                  </CollectionView.ItemTemplate>
            </CollectionView>
      </Grid>
</ContentPage>

下面是对应ViewModel中的相关代码:

    [RelayCommand]
    private void CheckChanged()
    {
        return;
    }

我还针对

Checkbox
XAML 代码和 C# 方法尝试了我能想到的所有变体,但我总是遇到相同的异常。

这是一个例子:

<CheckBox x:Name="checkBox">
      <CheckBox.Behaviors>
            <toolkit:EventToCommandBehavior EventName="CheckedChanged"
                                            Command="{Binding Source={RelativeSource AncestorType={x:Type viewmodel:CheckboxMethodPageViewModel}}, Path=CheckChangedCommand}"
                                            CommandParameter="{Binding .}"/>
      </CheckBox.Behaviors>
</CheckBox>
    [RelayCommand]
    private async Task CheckChanged(ThingamaBob thingamajig)
    {
        return;
    }

我在这个项目的其他地方使用了

EventToCommandBehavior
,所以我知道我可以让它工作。

我非常乐意接受解决方法的建议。我最初尝试使用

CommunityToolkit.MVVM
(参见 here),但我也无法让它发挥作用。

====================================================== ========

还是不行,但我可能更接近了

我认为,如果您尝试为其创建方法的控件已经有一个事件,则必须使用它。另外,当涉及到

EventToCommandBehavior
CheckBox
时,也很奇怪。

无论如何,我得到了解决方案这里

我不知道它到底是如何工作的,但这是我的

EventToCommandBehavior
命令,当
CheckBox
位于
CollectionView
内部时:

为您的内容页面命名:

<ContentPage xmlns="http://schemas.microsoft.com/dotnet/2021/maui"
  xmlns:toolkit="http://schemas.microsoft.com/dotnet/2022/maui/toolkit"
  ...  
  x:Name="this">

这是

CheckBox
控件。请注意,我使用的事件是
CheckedChange
,但您可以随意命名您的实际方法。
AddToCase
是一个布尔值,它是我在
CollectionView
中使用的模型对象的属性:

<CheckBox.Behaviors>
      <toolkit:EventToCommandBehavior  Command="{Binding Source={x:Reference this}, 
                                                         Path=BindingContext.AddToListCommand}"
                                       CommandParameter="{Binding AddToCase}" 
                                       EventName="CheckedChanged" />
</CheckBox.Behaviors>

这是我的方法:

    [RelayCommand]
    public static void AddToList(bool value)
    {
        if (value)
        {
            // do the thing
        }
        else
        {
             // do theother thing
        }
    }

我遇到的问题是我位于集合视图中,需要传递参数以及布尔值。所以,是的。

c# mvvm checkbox maui
1个回答
0
投票

出现此异常是因为 xaml 中的命令参数不是 bool。当您使用 eventtocommand 行为时,您还需要传递正确的参数。

CheckedChanged事件的参数是后面代码中的CheckedChangedEventArgs。当你想在viewmodel中绑定命令时,你可以自定义EventArgsContervor:

    public class CheckedChangedArgsConvertor : BaseConverterOneWay<CheckedChangedEventArgs?, bool>
    {
        public override bool DefaultConvertReturnValue { get; set; } = false;

        public override bool ConvertFrom(CheckedChangedEventArgs value, CultureInfo culture)
        {
            return value.Value;
        }
    }

然后在xaml中使用它:

<ContentPage.Resources>
     <local:CheckedChangedArgsConvertor x:Key="ArgsToInt"/>
 </ContentPage.Resources>
 <StackLayout x:Name="layout">
     <CheckBox >
         <CheckBox.Behaviors>
             <mct:EventToCommandBehavior EventName="CheckedChanged"
                       Command="{Binding AddToListCommand}" 
                       EventArgsConverter="{StaticResource ArgsToInt}"/>
         </CheckBox.Behaviors>
     </CheckBox>

我已经对此进行了测试,并且命令绑定有效。更多信息,您可以参考Binding value converters的官方文档和ItemTappedEventArgsConverter的源代码。

© www.soinside.com 2019 - 2024. All rights reserved.