You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Avalonia中DataGrid内按钮的命令绑定问题求助

问题:Avalonia DataGrid内按钮命令绑定触发AVLN2000错误

在Avalonia框架开发中,普通按钮的命令绑定功能正常,但为DataGrid内的按钮绑定AddRowCommand时触发AVLN2000错误,提示无法在aa3.ViewModels.Item类型上解析名为'AddRowCommand'的属性或方法,即使移除方法参数仍报错。

相关代码

XAML代码

<Window xmlns="https://github.com/avaloniaui"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:vm="clr-namespace:aa3.ViewModels"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450"
        x:Class="aa3.Views.MainWindow"
        x:DataType="vm:MainWindowViewModel"
        Icon="/Assets/avalonia-logo.ico"
        Title="aa3">

    <Window.DataContext>
        <vm:MainWindowViewModel />
    </Window.DataContext>
    
    <Grid>      
        <StackPanel Orientation="Vertical" Margin="0" HorizontalAlignment="Left">
            <Button Content="btn01" Width="50" Height="30" Margin="0,0,0,0" Command="{Binding SomeCommand}"/>
            <Button Content="btn02" Width="50" Height="30" Margin="0,0,0,0"  Command="{Binding AnotherCommand}"/>
            <Button Content="btn03" Width="50" Height="30" Margin="0,0,0,0"/>
            
        <DataGrid ItemsSource="{Binding Items}" AutoGenerateColumns="False"
                    Margin="20"
                    IsReadOnly="True"
                    CanUserReorderColumns="True"
                    CanUserResizeColumns="True"
                    CanUserSortColumns="False"
                    GridLinesVisibility="All"
                    BorderThickness="1" BorderBrush="Gray">
            <DataGrid.Columns>
                <DataGridTextColumn Header="First Name"  Binding="{Binding Number}"/>
                <DataGridTextColumn Header="Last Name" />
                <DataGridTemplateColumn Header="Action" Width="*">
                    <DataGridTemplateColumn.CellTemplate>
                        <DataTemplate>
                            <Button Content="Add Row" Command="{Binding AddRowCommand}"/>
                        </DataTemplate>
                    </DataGridTemplateColumn.CellTemplate>
                </DataGridTemplateColumn>
            </DataGrid.Columns>
        </DataGrid>

        </StackPanel>
    </Grid>
</Window>

ViewModel代码

public partial class MainWindowViewModel : ObservableObject
{
    public ObservableCollection<Item> Items { get; set; }

    private int Counter { get; set; } = 1;

    public MainWindowViewModel()
    {
        Items = new ObservableCollection<Item>
        {
            new Item(Counter++),
            new Item(Counter++)
        };

        AddRowCommand = new RelayCommand<Object>(AddRow);
        SomeCommand = new RelayCommand(SomeAction);
        AnotherCommand = new RelayCommand<Object>(AnotherAction);
    }

    public IRelayCommand AddRowCommand { get; }
    private void AddRow(Object currentItem)
    {
        Item item = currentItem as Item;
        if (item == null)
        {
            Trace.WriteLine("error");
            return;
        }
        var index = Items.IndexOf(item);
        Items.Insert(index + 1, new Item (Counter++));
    }

    public IRelayCommand SomeCommand { get; }
    private void SomeAction()
    {
        Trace.WriteLine("Some command");
    }

    public IRelayCommand AnotherCommand { get; }
    private void AnotherAction(Object obj)
    {
        Trace.WriteLine("Another command");
    }
}
public class Item : ObservableObject
{
    public Item (int n)
    {
        Number = n;
    }
    public int Number { get; set; }
}

解决方案

错误核心原因:DataGrid的CellTemplate内部的DataContext是Items集合中的单个Item实例,而AddRowCommand定义在父级的MainWindowViewModel中,直接绑定会去Item类中查找该命令,导致找不到报错。

修改按钮的命令绑定,通过RelativeSource找到父级DataGrid的DataContext,从而访问到MainWindowViewModel中的命令,同时传递当前Item作为参数:

修改后的DataTemplate代码:

<DataTemplate>
    <Button Content="Add Row" 
            Command="{Binding DataContext.AddRowCommand, RelativeSource={RelativeSource AncestorType=DataGrid}}"
            CommandParameter="{Binding .}"/>
</DataTemplate>

如果需要类型安全的绑定,可以给DataTemplate指定x:DataType:

<DataTemplate x:DataType="vm:Item">
    <Button Content="Add Row" 
            Command="{Binding DataContext.AddRowCommand, RelativeSource={RelativeSource AncestorType=DataGrid}}"
            CommandParameter="{Binding .}"/>
</DataTemplate>

修改后,按钮会正确绑定到MainWindowViewModel中的AddRowCommand,并将当前行的Item对象作为参数传递给命令方法,解决AVLN2000错误。

内容的提问来源于stack exchange,提问作者oao

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.18 10:18:09