ObservableCollection 导致无效的转换异常

ObservableCollection causing invalid cast exception

我是 XAML 的新手,一直在尝试根据此处 Microsoft 的示例构建一个小型 phone 应用程序:ListView binding。当我的代码 运行s 我在下面标记的点得到一个“指定的转换无效”异常。我不确定这有多少是相关的,但请耐心等待。

这是部分页面的 XAML 代码:

<ListView x:Name="ListCoords" ItemsSource="{Binding Coordinates}">
<ListView.ItemTemplate>
    <DataTemplate>
        <StackLayout Margin="0" Orientation="Horizontal">
            <Label x:Name="LabelA" HeightRequest="32" WidthRequest="100" Text="{Binding Path=angle, StringFormat='{0:F2}'}" />
            <Label x:Name="LabelX" HeightRequest="32" WidthRequest="100" Text="{Binding Path=x, StringFormat='{0:F2}'}" />
            <Label x:Name="LabelY" HeightRequest="32" WidthRequest="100" Text="{Binding Path=y, StringFormat='{0:F2}'}" />
        </StackLayout>
    </DataTemplate>
</ListView.ItemTemplate>

页面后面cs代码的相关部分是这样的:

public partial class PCDPage : ContentPage
{

    public ObservableCollection<Coordinate> CoordinateList = new ObservableCollection<Coordinate> ();
    public ObservableCollection<Coordinate> Coordinates { get { return CoordinateList; } }

    public PCDPage()
    {
        InitializeComponent();
        ListCoords.ItemsSource = CoordinateList;
    }

    ... Code here responds to a button press and calls the following ...
    
    //
    // Calculate and display a table of hole coordinates
    //
    private void CalculateCoordinates()
    {
        // Start a new list
        CoordinateList.Clear();

        double x, y, a, b;

        for (int i = 0; i < count; i++)
        {
            ... Calculate a, x, y
            
            // Add the corrdinate to the list
            CoordinateList.Add(new Coordinate(a, x, y));      <<<< - Exception
        }

        ... Finish off
    }

而小坐标class是:

    public class Coordinate
{
    public Coordinate()
    {

    }

    public Coordinate(double va, double vx, double vy)
    {
        angle = va;
        x = vx;
        y = vy;
    }

    public double angle { get; set; }
    public double x { get; set; }
    public double y { get; set; }
}

当我 运行 我的应用程序在将第一个坐标添加到列表时标记的点崩溃。当它在调试器中停止时,我可以将鼠标悬停在 CoordinateList 上并看到它包含预期的一项。在 XAML 中,我可以用绑定做同样的事情。所以在我看来,问题似乎发生在添加项目之后和返回我的代码之前。我是否遗漏了一些明显的东西,或者是否有我尚未了解的微妙之处?

提前致谢

Coordinate class 的属性是double 类型,但是Labels 的“Text” 属性 是string。您需要创建一个转换器

public  class DoubleToStringConverter : IValueConverter
{
    public object Convert(object value, Type targetType, 
        object parameter, CultureInfo culture)
    {
        return value!=null?((double)value).ToString():"";
    }
 
    public object ConvertBack(object value, Type targetType, 
        object parameter, CultureInfo culture)
    {
        return null;
    }
}

<ListView x:Name="ListCoords" ItemsSource="{Binding Coordinates}">
    <ListView.Resources>
        <l:DoubleToStringConverter x:Key="converter" />
    </ListView.Resources>
<ListView.ItemTemplate>
    <DataTemplate>
        <StackLayout Margin="0" Orientation="Horizontal">
            <Label x:Name="LabelA" HeightRequest="32" WidthRequest="100" Text="{Binding Path=angle, StringFormat='{0:F2}',Converter={StaticResource converter}}" />
            <Label x:Name="LabelX" HeightRequest="32" WidthRequest="100" Text="{Binding Path=x, StringFormat='{0:F2}',Converter={StaticResource converter}}" />
            <Label x:Name="LabelY" HeightRequest="32" WidthRequest="100" Text="{Binding Path=y, StringFormat='{0:F2}',Converter={StaticResource converter}}" />
        </StackLayout>
    </DataTemplate>
</ListView.ItemTemplate>

“l”将是指示 DoubleToStringConverter 命名空间的前缀 class。

xmlns:l="clr-namespace:MyNamespace"

namespace MyNamespace
{
    public class DoubleToStringConverter : IValueConverter
    {

但在这种情况下转换器不是必需的,这不是错误。

我发现有必要将内容包含在 ViewCell 的视图中

<ListView.ItemTemplate>
            <DataTemplate>
                <ViewCell>
                    <ViewCell.View>
                        <StackLayout Margin="0" Orientation="Horizontal">
                            <Label  x:Name="LabelA" HeightRequest="32" WidthRequest="100" Text="{Binding Path=angle, StringFormat='{0:F2}'}" />
                            <Label  x:Name="LabelX" HeightRequest="32" WidthRequest="100" Text="{Binding Path=x, StringFormat='{0:F2}'}" />
                            <Label  x:Name="LabelY" HeightRequest="32" WidthRequest="100" Text="{Binding Path=y, StringFormat='{0:F2}'}" />
                        </StackLayout>
                    </ViewCell.View>
                </ViewCell>
            </DataTemplate>
        </ListView.ItemTemplate>

抱歉我的英语不好。