Skip to content

Commit 35b693c

Browse files
Copilotmattleibow
andcommitted
Complete RefreshView IsRefreshEnabled implementation with test cases and documentation
Co-authored-by: mattleibow <1096616+mattleibow@users.noreply.github.com>
1 parent 4bfe088 commit 35b693c

File tree

2 files changed

+261
-0
lines changed

2 files changed

+261
-0
lines changed
Lines changed: 150 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,150 @@
1+
using System.Linq;
2+
3+
namespace Maui.Controls.Sample.Issues
4+
{
5+
[Issue(IssueTracker.Github, 30690, "RefreshView IsRefreshEnabled Property and Consistent IsEnabled Behavior", PlatformAffected.All)]
6+
public class Issue30690 : TestContentPage
7+
{
8+
RefreshView _refreshView;
9+
Label _statusLabel;
10+
Entry _testEntry;
11+
12+
public Issue30690()
13+
{
14+
}
15+
16+
protected override void Init()
17+
{
18+
Title = "RefreshView IsRefreshEnabled Tests";
19+
20+
// Create status label to show current states
21+
_statusLabel = new Label
22+
{
23+
AutomationId = "StatusLabel",
24+
Text = "Ready to test",
25+
BackgroundColor = Colors.LightGray,
26+
Padding = 10
27+
};
28+
29+
// Create a test entry to verify child control interaction
30+
_testEntry = new Entry
31+
{
32+
AutomationId = "TestEntry",
33+
Placeholder = "Type here to test child interaction",
34+
BackgroundColor = Colors.LightBlue,
35+
Margin = 10
36+
};
37+
38+
// Create scrollable content
39+
var scrollViewContent = new StackLayout();
40+
scrollViewContent.Children.Add(_testEntry);
41+
42+
Enumerable
43+
.Range(0, 5)
44+
.Select(i => new Label()
45+
{
46+
HeightRequest = 100,
47+
Text = $"Item {i + 1} - Pull down to refresh",
48+
BackgroundColor = i % 2 == 0 ? Colors.LightGreen : Colors.LightYellow,
49+
VerticalTextAlignment = TextAlignment.Center,
50+
HorizontalTextAlignment = TextAlignment.Center
51+
})
52+
.ToList()
53+
.ForEach(scrollViewContent.Children.Add);
54+
55+
// Create refresh view
56+
_refreshView = new RefreshView()
57+
{
58+
AutomationId = "TestRefreshView",
59+
Content = new ScrollView()
60+
{
61+
Content = scrollViewContent,
62+
AutomationId = "ScrollViewContent"
63+
},
64+
Command = new Command(async () =>
65+
{
66+
UpdateStatusLabel("Refreshing...");
67+
await Task.Delay(1000);
68+
_refreshView.IsRefreshing = false;
69+
UpdateStatusLabel("Refresh completed");
70+
})
71+
};
72+
73+
// Update status when refresh state changes
74+
_refreshView.Refreshing += (sender, args) => UpdateStatusLabel("Refresh started");
75+
76+
Content = new StackLayout()
77+
{
78+
Padding = 10,
79+
Children =
80+
{
81+
_statusLabel,
82+
83+
// Control buttons
84+
new Button()
85+
{
86+
AutomationId = "ToggleIsRefreshEnabled",
87+
Text = "Toggle IsRefreshEnabled",
88+
Command = new Command(() =>
89+
{
90+
_refreshView.IsRefreshEnabled = !_refreshView.IsRefreshEnabled;
91+
UpdateStatusLabel($"IsRefreshEnabled: {_refreshView.IsRefreshEnabled}");
92+
})
93+
},
94+
95+
new Button()
96+
{
97+
AutomationId = "ToggleIsEnabled",
98+
Text = "Toggle IsEnabled",
99+
Command = new Command(() =>
100+
{
101+
_refreshView.IsEnabled = !_refreshView.IsEnabled;
102+
UpdateStatusLabel($"IsEnabled: {_refreshView.IsEnabled}");
103+
})
104+
},
105+
106+
new Button()
107+
{
108+
AutomationId = "StartRefresh",
109+
Text = "Start Refresh Programmatically",
110+
Command = new Command(() =>
111+
{
112+
_refreshView.IsRefreshing = true;
113+
})
114+
},
115+
116+
new Button()
117+
{
118+
AutomationId = "CheckStates",
119+
Text = "Check Current States",
120+
Command = new Command(() =>
121+
{
122+
UpdateStatusLabel($"IsEnabled: {_refreshView.IsEnabled}, IsRefreshEnabled: {_refreshView.IsRefreshEnabled}, IsRefreshing: {_refreshView.IsRefreshing}");
123+
})
124+
},
125+
126+
new Button()
127+
{
128+
AutomationId = "TestEntryFocus",
129+
Text = "Focus Entry",
130+
Command = new Command(() =>
131+
{
132+
_testEntry.Focus();
133+
UpdateStatusLabel("Entry focus attempted");
134+
})
135+
},
136+
137+
_refreshView
138+
}
139+
};
140+
141+
// Initial status
142+
UpdateStatusLabel($"Initial - IsEnabled: {_refreshView.IsEnabled}, IsRefreshEnabled: {_refreshView.IsRefreshEnabled}");
143+
}
144+
145+
private void UpdateStatusLabel(string message)
146+
{
147+
_statusLabel.Text = $"{DateTime.Now:HH:mm:ss} - {message}";
148+
}
149+
}
150+
}
Lines changed: 111 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,111 @@
1+
using NUnit.Framework;
2+
using UITest.Appium;
3+
using UITest.Core;
4+
5+
namespace Microsoft.Maui.TestCases.Tests.Issues
6+
{
7+
public class Issue30690 : _IssuesUITest
8+
{
9+
public Issue30690(TestDevice device) : base(device)
10+
{
11+
}
12+
13+
public override string Issue => "RefreshView IsRefreshEnabled Property and Consistent IsEnabled Behavior";
14+
15+
[Test]
16+
[Category(UITestCategories.RefreshView)]
17+
public void IsRefreshEnabledPreventsRefresh()
18+
{
19+
// Initially both properties should be true
20+
App.WaitForElement("CheckStates");
21+
App.Tap("CheckStates");
22+
Assert.That(GetStatusText().Contains("IsEnabled: True"), "IsEnabled should be true initially");
23+
Assert.That(GetStatusText().Contains("IsRefreshEnabled: True"), "IsRefreshEnabled should be true initially");
24+
25+
// Disable IsRefreshEnabled
26+
App.Tap("ToggleIsRefreshEnabled");
27+
Assert.That(GetStatusText().Contains("IsRefreshEnabled: False"), "IsRefreshEnabled should be false after toggle");
28+
29+
// Try to start refresh - should not work
30+
App.Tap("StartRefresh");
31+
App.Tap("CheckStates");
32+
Assert.That(GetStatusText().Contains("IsRefreshing: False"), "IsRefreshing should remain false when IsRefreshEnabled is false");
33+
}
34+
35+
[Test]
36+
[Category(UITestCategories.RefreshView)]
37+
public void IsEnabledDisablesEntireView()
38+
{
39+
// Initially entry should be interactive
40+
App.WaitForElement("TestEntry");
41+
App.Tap("TestEntry");
42+
App.EnterText("TestEntry", "test input");
43+
44+
// Disable IsEnabled
45+
App.Tap("ToggleIsEnabled");
46+
App.Tap("CheckStates");
47+
Assert.That(GetStatusText().Contains("IsEnabled: False"), "IsEnabled should be false after toggle");
48+
49+
// Entry should not be interactive when IsEnabled is false
50+
// Note: The specific behavior may vary by platform, but the RefreshView itself should be disabled
51+
App.Tap("StartRefresh");
52+
App.Tap("CheckStates");
53+
Assert.That(GetStatusText().Contains("IsRefreshing: False"), "IsRefreshing should remain false when IsEnabled is false");
54+
}
55+
56+
[Test]
57+
[Category(UITestCategories.RefreshView)]
58+
public void IsRefreshEnabledAllowsChildInteraction()
59+
{
60+
// Disable only IsRefreshEnabled, leave IsEnabled true
61+
App.WaitForElement("ToggleIsRefreshEnabled");
62+
App.Tap("ToggleIsRefreshEnabled");
63+
App.Tap("CheckStates");
64+
Assert.That(GetStatusText().Contains("IsEnabled: True"), "IsEnabled should remain true");
65+
Assert.That(GetStatusText().Contains("IsRefreshEnabled: False"), "IsRefreshEnabled should be false");
66+
67+
// Entry should still be interactive
68+
App.Tap("TestEntry");
69+
App.ClearText("TestEntry");
70+
App.EnterText("TestEntry", "refresh disabled but entry works");
71+
72+
// But refresh should not work
73+
App.Tap("StartRefresh");
74+
App.Tap("CheckStates");
75+
Assert.That(GetStatusText().Contains("IsRefreshing: False"), "IsRefreshing should remain false when IsRefreshEnabled is false");
76+
}
77+
78+
[Test]
79+
[Category(UITestCategories.RefreshView)]
80+
public void BothPropertiesEnabledAllowsRefresh()
81+
{
82+
// Ensure both properties are enabled
83+
App.WaitForElement("CheckStates");
84+
App.Tap("CheckStates");
85+
var status = GetStatusText();
86+
87+
// Enable IsRefreshEnabled if it's disabled
88+
if (status.Contains("IsRefreshEnabled: False"))
89+
{
90+
App.Tap("ToggleIsRefreshEnabled");
91+
}
92+
93+
// Enable IsEnabled if it's disabled
94+
if (status.Contains("IsEnabled: False"))
95+
{
96+
App.Tap("ToggleIsEnabled");
97+
}
98+
99+
// Now refresh should work
100+
App.Tap("StartRefresh");
101+
102+
// Wait for refresh to complete
103+
App.WaitForTextToBePresentInElement("StatusLabel", "Refresh completed", timeout: TimeSpan.FromSeconds(5));
104+
}
105+
106+
private string GetStatusText()
107+
{
108+
return App.FindElement("StatusLabel").GetText();
109+
}
110+
}
111+
}

0 commit comments

Comments
 (0)