summaryrefslogtreecommitdiff
path: root/Xamarin.Forms.Controls.Issues
diff options
context:
space:
mode:
authorSamantha Houts <samhouts@users.noreply.github.com>2017-08-15 18:18:57 (GMT)
committerRui Marinho <me@ruimarinho.net>2017-08-15 18:18:57 (GMT)
commit2747cdc7a6b34dd336d1a017f4653a6b43c58699 (patch)
tree412a488c1de9434482cadbf5c17b2ad7dd1c0f61 /Xamarin.Forms.Controls.Issues
parent71f08bf48a91e3c7f107d5c34c4e3d9d9f5ccd30 (diff)
downloadxamarin-forms-2747cdc7a6b34dd336d1a017f4653a6b43c58699.zip
xamarin-forms-2747cdc7a6b34dd336d1a017f4653a6b43c58699.tar.gz
xamarin-forms-2747cdc7a6b34dd336d1a017f4653a6b43c58699.tar.bz2
[Android] Eagerly dispose children of ListViews to prevent ObjectDisposed exception (#1063)
* Add repro for 57910 * [Android] Dispose cells explicitly * [Android] Add default constructors to prevent crash on dispose * [Android] Don't try to dispose headers and footers
Diffstat (limited to 'Xamarin.Forms.Controls.Issues')
-rw-r--r--Xamarin.Forms.Controls.Issues/Xamarin.Forms.Controls.Issues.Shared/Bugzilla57910.cs167
-rw-r--r--Xamarin.Forms.Controls.Issues/Xamarin.Forms.Controls.Issues.Shared/Xamarin.Forms.Controls.Issues.Shared.projitems1
2 files changed, 168 insertions, 0 deletions
diff --git a/Xamarin.Forms.Controls.Issues/Xamarin.Forms.Controls.Issues.Shared/Bugzilla57910.cs b/Xamarin.Forms.Controls.Issues/Xamarin.Forms.Controls.Issues.Shared/Bugzilla57910.cs
new file mode 100644
index 0000000..e76c8e2
--- /dev/null
+++ b/Xamarin.Forms.Controls.Issues/Xamarin.Forms.Controls.Issues.Shared/Bugzilla57910.cs
@@ -0,0 +1,167 @@
+´╗┐using Xamarin.Forms.CustomAttributes;
+using Xamarin.Forms.Internals;
+using System;
+using System.Linq;
+using System.ComponentModel;
+
+#if UITEST
+using Xamarin.UITest;
+using NUnit.Framework;
+#endif
+
+namespace Xamarin.Forms.Controls.Issues
+{
+ [Preserve(AllMembers = true)]
+ [Issue(IssueTracker.Bugzilla, 57910, "ObjectDisposedException in Xamarin.Forms.Platform.Android.Renderers.ProgressBarRenderer", PlatformAffected.Android)]
+ public class Bugzilla57910 : Bugzilla57910QuickCollectNavigationPage
+ {
+ const string ButtonId = "btnPush";
+ const string Button2Id = "btnPop";
+ const string Instructions = "Tap Push. Then quickly tap Pop on the subsequent screen. Do this several times. If there is no crash, then this test has passed.";
+ const string Instructions2 = "Tap Pop. Then quickly tap Push on the subsequent screen. Do this several times. If there is no crash, then this test has passed.";
+
+ protected override void Init()
+ {
+ Navigation.PushAsync(new HomePage());
+ }
+
+ [Preserve(AllMembers = true)]
+ class HomePage : ContentPage
+ {
+ public HomePage()
+ {
+ Button button = new Button { Text = "Push", AutomationId = ButtonId };
+
+ button.Clicked += Button_Clicked;
+
+ Content = new StackLayout { Children = { new Label { Text = Instructions }, button } };
+ }
+
+ async void Button_Clicked(object sender, EventArgs e)
+ {
+ await Navigation.PushAsync(new ListPage());
+ GC.Collect();
+ }
+ }
+
+ [Preserve(AllMembers = true)]
+ class ListItemView : ViewCell
+ {
+ public ListItemView()
+ {
+ ProgressBar progressBar = new ProgressBar { IsVisible = false };
+ progressBar.SetBinding(ProgressBar.ProgressProperty, nameof(ListItemViewModel.DownloadProgressPercentage));
+
+ // Need a trigger to set a property on a VisualElement. Not actually specific to ProgressBar.
+ DataTrigger newDataTrigger = new DataTrigger(typeof(ProgressBar)) { Binding = new Binding(nameof(ListItemViewModel.State)), Value = ListItemViewModel.InstallableState.Downloading };
+ newDataTrigger.Setters.Add(new Setter { Property = ProgressBar.IsVisibleProperty, Value = true });
+ progressBar.Triggers.Add(newDataTrigger);
+
+ View = new ContentView { Content = new StackLayout { Children = { progressBar } } };
+ }
+ }
+
+ [Preserve(AllMembers = true)]
+ class ListItemViewModel : INotifyPropertyChanged
+ {
+ double _downloadProgressPercentage;
+
+ InstallableState _state;
+
+ public ListItemViewModel()
+ {
+ DownloadProgressPercentage = 0d;
+ State = InstallableState.Downloading;
+
+ // Need an asynchronous action that happens sometime between creation of the Element and Pop of the containing page
+ Device.StartTimer(TimeSpan.FromMilliseconds((1000)), () =>
+ {
+ DownloadProgressPercentage += 0.05d;
+ if (DownloadProgressPercentage > 0.99d)
+ {
+ State = InstallableState.Local;
+ }
+
+ return DownloadProgressPercentage != 1.0d;
+ });
+ }
+
+ public event PropertyChangedEventHandler PropertyChanged;
+
+ public enum InstallableState
+ {
+ Local,
+ Downloading
+ }
+
+ public double DownloadProgressPercentage
+ {
+ get { return _downloadProgressPercentage; }
+ set
+ {
+ _downloadProgressPercentage = value;
+ OnPropertyChanged(nameof(DownloadProgressPercentage));
+ }
+ }
+
+ public InstallableState State
+ {
+ get { return _state; }
+ set
+ {
+ _state = value;
+ OnPropertyChanged(nameof(State));
+ }
+ }
+
+ protected virtual void OnPropertyChanged(string propertyName)
+ {
+ PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
+ }
+ }
+
+ [Preserve(AllMembers = true)]
+ class ListPage : ContentPage
+ {
+ public ListPage()
+ {
+ ListView listView = new ListView(ListViewCachingStrategy.RecycleElement)
+ {
+ RowHeight = 70,
+ ItemsSource = Enumerable.Range(0, 100).Select(c => new ListItemViewModel()),
+ ItemTemplate = new DataTemplate(typeof(ListItemView))
+ };
+ Button newButton = new Button { Text = "Pop", AutomationId = Button2Id };
+ newButton.Clicked += NewButton_Clicked;
+ Content = new StackLayout { Children = { new Label { Text = Instructions2 }, newButton, listView } };
+ }
+
+ void NewButton_Clicked(object sender, EventArgs e)
+ {
+ Navigation.PopAsync();
+ }
+ }
+
+#if UITEST
+ [Test]
+ public void Bugzilla57910Test()
+ {
+ for (int i = 0; i < 10; i++)
+ {
+ RunningApp.WaitForElement(q => q.Marked(ButtonId));
+ RunningApp.Tap(q => q.Marked(ButtonId));
+ RunningApp.WaitForElement(q => q.Marked(Button2Id));
+ RunningApp.Tap(q => q.Marked(Button2Id));
+ }
+ }
+#endif
+ }
+
+ [Preserve(AllMembers = true)]
+ public class Bugzilla57910QuickCollectNavigationPage : TestNavigationPage
+ {
+ protected override void Init()
+ {
+ }
+ }
+} \ No newline at end of file
diff --git a/Xamarin.Forms.Controls.Issues/Xamarin.Forms.Controls.Issues.Shared/Xamarin.Forms.Controls.Issues.Shared.projitems b/Xamarin.Forms.Controls.Issues/Xamarin.Forms.Controls.Issues.Shared/Xamarin.Forms.Controls.Issues.Shared.projitems
index 484fea9..672c8df 100644
--- a/Xamarin.Forms.Controls.Issues/Xamarin.Forms.Controls.Issues.Shared/Xamarin.Forms.Controls.Issues.Shared.projitems
+++ b/Xamarin.Forms.Controls.Issues/Xamarin.Forms.Controls.Issues.Shared/Xamarin.Forms.Controls.Issues.Shared.projitems
@@ -215,6 +215,7 @@
<Compile Include="$(MSBuildThisFileDirectory)Bugzilla57317.cs" />
<Compile Include="$(MSBuildThisFileDirectory)Bugzilla57114.cs" />
<Compile Include="$(MSBuildThisFileDirectory)Bugzilla57758.cs" />
+ <Compile Include="$(MSBuildThisFileDirectory)Bugzilla57910.cs" />
<Compile Include="$(MSBuildThisFileDirectory)Bugzilla58406.cs" />
<Compile Include="$(MSBuildThisFileDirectory)ButtonBackgroundColorTest.cs" />
<Compile Include="$(MSBuildThisFileDirectory)CarouselAsync.cs" />