Microsoft-ui-xaml: ItemsRepeater throws AccessViolationException when DataTemplate is empty

Created on 30 May 2019  路  19Comments  路  Source: microsoft/microsoft-ui-xaml

Describe the bug
I got AccessViolationException when return new DataTemplate() from DataTemplateSelector. ListView and GridView deals well with it by just rendering nothing, but ItemsRepeater throws Exception.

Steps to reproduce the bug
this code

<muxc:ItemsRepeater ItemsSource="{Binding SomeItems}">
    <muxc:ItemsRepeater.ItemTemplate>
        <DataTemplate/>
    </muxc:ItemsRepeater.ItemTemplate>
</muxc:ItemsRepeater>

throws AccessViolationException.

Expected behavior
Do not throw Exception, just don't render this item.

Additional context
My guess is that AccessViolation appears here as selectedTemplate.LoadContent() returns null.

area-ItemsRepeater bug team-Controls

All 19 comments

Good find, thanks!

I was unable to reproduce the issue with WinUI version 2.2.190830001. With the code provided in this issue, the ItemsRepeater just renders nothing just as expected.
I think this issue can be closed if we can not reproduce the bug.

Thanks for trying the repro on latest bits, @chingucoding. @ad1Dima let me know if you still see this and we can reactivate.

It's still there. With provided sample...
Nothing changed there

I was unable to reproduce the issue with WinUI version 2.2.190830001. With the code provided in this issue, the ItemsRepeater just renders nothing just as expected.

May be you had no items in your items source?

Please, try this solution: ItemsRepeaterTest.zip

I was unable to reproduce the issue with WinUI version 2.2.190830001. With the code provided in this issue, the ItemsRepeater just renders nothing just as expected.

May be you had no items in your items source?

My test, which resulted in no exception, was the following:

    <muxc:ItemsRepeater ItemsSource="{Binding SomeItems}" x:Name="myItemRepeater">
        <muxc:ItemsRepeater.ItemTemplate>
            <DataTemplate/>
        </muxc:ItemsRepeater.ItemTemplate>
    </muxc:ItemsRepeater>

```c#
public ObservableCollection SomeItems;
public MainPage()
{
this.InitializeComponent();
SomeItems = new ObservableCollection();
SomeItems.Add("some awesome string");
SomeItems.Add("some awesome string");
SomeItems.Add("some awesome string");
SomeItems.Add("some awesome string");

        //myItemRepeater.ItemsSource = SomeItems;
    }

```
However when setting the ItemsSource again (though I already specified that in the XAML) the app crashes. My expectation was that since I used an ObersableCollection, the ItemsRepeater would notice that there are elements but apparently it does not. 馃

Thank you for your follow up on this issue. Since the issue is not fixed you can reopen it again. I will try to find a fix for this issue.

@jevansaks Is it expected that adding items to an ObservableCollection does not trigger that behaviour?

Is it expected that adding items to an ObservableCollection does not trigger that behaviour?

ObservableCollection triggers only changes within collction, not changes of SomeItems. So binding didn't know SomeItems was changed

I guess this code would work as you expect:

public MainPage()
{
    SomeItems =  new ObservableCollection<string>();
    this.InitializeComponent();
    SomeItems.Add("some awesome string");
    SomeItems.Add("some awesome string");
    SomeItems.Add("some awesome string");
    SomeItems.Add("some awesome string");
}

I guess this code would work as you expect:

public MainPage()
{
    SomeItems =  new ObservableCollection<string>();
    this.InitializeComponent();
    SomeItems.Add("some awesome string");
    SomeItems.Add("some awesome string");
    SomeItems.Add("some awesome string");
    SomeItems.Add("some awesome string");
}

Weirdly, this does not crash the application either.

And neither does this:
c# public MainPage() { SomeItems = new ObservableCollection<string>(); this.InitializeComponent(); SomeItems.Add("some awesome string"); SomeItems.Add("some awesome string"); SomeItems.Add("some awesome string"); SomeItems.Add("some awesome string"); SomeItems[1] = "Text"; Console.WriteLine(SomeItems[1]); // Prints "Text" }

Re-opening to investigate further.

There is another case, more useful: you can provide DataTemplateSelector that return empty DataTemplate for some datatype. PR #1358 doesn't consider that.

Should I open new issue?

I think that would be better.

Hmm... Description of this bug already contains this case. I just made sample code simpler...
Let's wait for MS staff...

Is there a valid scenario with DataTemplateSelector ? What if one of the templates is empty and the other is not ? Should the empty template just insert items that take up no space ? If we do that then, we could end up de-virtualizing the entire list trying to fill the viewport. I would like to understand the scenario with DataTemplateSelector and the expected behavior in different cases. Yes, opening a separate bug to discuss that would be best. I merged these changes in since the two fixes are independent. Thanks!

What if one of the templates is empty and the other is not ?
This IS The case.
Should the empty template just insert items that take up no space ?
ListView do this
If we do that then, we could end up de-virtualizing the entire list trying to fill the viewport.
I guess this is aceptable
Yes, opening a separate bug to discuss that would be best
Ok

:tada:This issue was addressed in #1358, which has now been successfully released as Microsoft.UI.Xaml v2.3.191007001-prerelease.:tada:

Handy links:

:tada:This issue was addressed in #1358, which has now been successfully released as Microsoft.UI.Xaml v2.3.191129002.:tada:

Handy links:

Was this page helpful?
0 / 5 - 0 ratings