2

你好朋友,我在我的 Windows 商店应用程序的异步方法中使用ObservableCollection遇到了非常奇怪的问题。我正在尝试在异步方法中的 ObservableCollection 中添加项目,如果我在 await 关键字所在的行上方定义 ObservableCollection 但我在此行下方初始化它不起作用,则它工作正常。我已经为这个问题制作了样本。我的xml代码是..

<Page
x:Class="observableCollectionTest.MainPage"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="using:observableCollectionTest"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d">

<Grid Background="{StaticResource ApplicationPageBackgroundThemeBrush}">
    <ListView ItemsSource="{Binding SomeCollection}" Background="Pink" HorizontalAlignment="Left" Width="500" >
        <ListView.ItemTemplate>
            <DataTemplate>
                <Grid Width="200" Height="200" Background="Red" >
                    <Button Content="click me" Name="btn" ></Button>
                </Grid>
            </DataTemplate>
        </ListView.ItemTemplate>            
    </ListView>
</Grid>

我的主页反手工作代码是..

public sealed partial class MainPage : Page
{
    public ObservableCollection<string> SomeCollection { get; set; }

    public MainPage()
    {
        this.InitializeComponent();


        FillCollection();
        this.DataContext = this;
    }

    public async Task FillCollection()
    {
        SomeCollection = new ObservableCollection<string>(); // it is working..
        HttpClient client = new HttpClient();
        HttpResponseMessage message = await client.GetAsync("https://www.google.co.in/");

        SomeCollection.Add("asd");
        SomeCollection.Add("asd");
        SomeCollection.Add("asd");
        SomeCollection.Add("asd");
        SomeCollection.Add("asd");
        SomeCollection.Add("asd");
        SomeCollection.Add("asd");
        SomeCollection.Add("asd");
        SomeCollection.Add("asd");
        SomeCollection.Add("asd");

    }

我的主页反手 FillCollection 代码不起作用..

 public async Task FillCollection()
    {

        HttpClient client = new HttpClient();
        HttpResponseMessage message = await client.GetAsync("https://www.google.co.in/");
        SomeCollection = new ObservableCollection<string>(); // this is not working
        SomeCollection.Add("asd");
        SomeCollection.Add("asd");
        SomeCollection.Add("asd");
        SomeCollection.Add("asd");
        SomeCollection.Add("asd");
        SomeCollection.Add("asd");
        SomeCollection.Add("asd");
        SomeCollection.Add("asd");
        SomeCollection.Add("asd");
        SomeCollection.Add("asd");

    }

我不明白为什么会这样。我在这里遗漏了一些概念,请告诉我..任何帮助或建议表示赞赏..

4

1 回答 1

2

您缺少从您的SomeCollection属性触发的属性更改事件 - 请参阅以了解如何实现该事件。

需要它的原因是FillCollection在分配属性之前执行异步之前的方法部分,DataContext而在 Web 请求完成之后执行另一半。因此,在您不工作的示例中,View不知道整个集合已更改。

另一方面,考虑一下您ObservableCollection在每次列表刷新时分配新实例时失去了什么(您想在某个时候刷新它?)。此类的基础是提供 UI 方法来优化 ItemsControls 中项目的刷新,方法是知道如果您创建一个新集合整体ListView将重新呈现哪些元素添加/删除/移动,这可能会很昂贵。出于代码清晰的原因,我建议在调用之前将您的分配移至构造函数FillCollection并很好地处理内容更改 - 这对您来说工作量更大,但如果视图很复杂,这是值得的。

于 2013-09-30T05:44:28.727 回答