Xamarin 在点击时设置 StackLayout 的 BackgroundColor
Xamarin set BackgroundColor of StackLayout on tapped
StackLayout sl1 = this.FindByName<StackLayout>("myStackLayout");
sl1.GestureRecognizers.Add(
new TapGestureRecognizer() {
Command = new Command(() => {
Task.Run(() => {
// When this line hits, background is set...
sl1.BackgroundColor = Color.FromHex("CCCCCC");
//this.Refresh(); << force Refresh UI function or something????
Task.Delay(400);
// When this line hits, background is reset...
sl1.BackgroundColor = Color.FromHex("EEEEEE");
});
})
});
当我逐行调试这段代码时,上面的代码按预期工作。
但是,当我 运行 这段代码未经调试时,UI 将不会更新 BackgroundColor。
然后,当我尝试调试以查看发生了什么时,它似乎起作用了。
- 为什么不调试就不能工作?
- 是否有强制UI更新的功能?
- 还有其他想法可以达到同样的效果吗?
编辑:
第一次也行。
编辑 2(解决方案):
结合使用这两个答案,我使用以下代码让它工作:
StackLayout sl1 = this.FindByName<StackLayout>("myStackLayout");
sl1.GestureRecognizers.Add(
new TapGestureRecognizer()
{
Command = new Command(async () =>
{
sl1.BackgroundColor = Color.FromHex("#CCCCCC");
await Task.Run(async () => {
await Task.Delay(100);
Device.BeginInvokeOnMainThread(() => {
sl1.BackgroundColor = Color.FromHex("#EEEEEE");
});
});
})
});
刚刚用一个快速应用程序对此进行了测试,并且有效:
MainPage.xaml.cs
public partial class MainPage : ContentPage
{
public MainPage()
{
InitializeComponent();
StackLayout sl1 = this.FindByName<StackLayout>("myStackLayout");
sl1.GestureRecognizers.Add(
new TapGestureRecognizer()
{
Command = new Command(async () => {
// When this line hits, background is set...
sl1.BackgroundColor = Color.FromHex("#e50000");
//this.Refresh(); << force Refresh UI function or something????
await Task.Delay(400);
// When this line hits, background is reset...
sl1.BackgroundColor = Color.FromHex("#0be204");
})
});
}
}
MainPage.xaml
<?xml version="1.0" encoding="utf-8" ?>
<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
xmlns:local="clr-namespace:test"
x:Class="test.MainPage">
<StackLayout x:Name="myStackLayout" BackgroundColor="RoyalBlue">
<!-- Place new controls here -->
<Label Text="Welcome to Xamarin.Forms!"
HorizontalOptions="Center"
VerticalOptions="CenterAndExpand" BackgroundColor="Blue" />
</StackLayout>
</ContentPage>
您正在尝试从后台线程更新 UI,所有 UI 更改都应在主线程上完成。
Device.BeginInvokeOnMainThread(() =>
{
sl1.BackgroundColor = Color.FromHex("CCCCCC");
});
StackLayout sl1 = this.FindByName<StackLayout>("myStackLayout");
sl1.GestureRecognizers.Add(
new TapGestureRecognizer() {
Command = new Command(() => {
Task.Run(() => {
// When this line hits, background is set...
sl1.BackgroundColor = Color.FromHex("CCCCCC");
//this.Refresh(); << force Refresh UI function or something????
Task.Delay(400);
// When this line hits, background is reset...
sl1.BackgroundColor = Color.FromHex("EEEEEE");
});
})
});
当我逐行调试这段代码时,上面的代码按预期工作。
但是,当我 运行 这段代码未经调试时,UI 将不会更新 BackgroundColor。
然后,当我尝试调试以查看发生了什么时,它似乎起作用了。
- 为什么不调试就不能工作?
- 是否有强制UI更新的功能?
- 还有其他想法可以达到同样的效果吗?
编辑:
第一次也行。
编辑 2(解决方案):
结合使用这两个答案,我使用以下代码让它工作:
StackLayout sl1 = this.FindByName<StackLayout>("myStackLayout");
sl1.GestureRecognizers.Add(
new TapGestureRecognizer()
{
Command = new Command(async () =>
{
sl1.BackgroundColor = Color.FromHex("#CCCCCC");
await Task.Run(async () => {
await Task.Delay(100);
Device.BeginInvokeOnMainThread(() => {
sl1.BackgroundColor = Color.FromHex("#EEEEEE");
});
});
})
});
刚刚用一个快速应用程序对此进行了测试,并且有效:
MainPage.xaml.cs
public partial class MainPage : ContentPage
{
public MainPage()
{
InitializeComponent();
StackLayout sl1 = this.FindByName<StackLayout>("myStackLayout");
sl1.GestureRecognizers.Add(
new TapGestureRecognizer()
{
Command = new Command(async () => {
// When this line hits, background is set...
sl1.BackgroundColor = Color.FromHex("#e50000");
//this.Refresh(); << force Refresh UI function or something????
await Task.Delay(400);
// When this line hits, background is reset...
sl1.BackgroundColor = Color.FromHex("#0be204");
})
});
}
}
MainPage.xaml
<?xml version="1.0" encoding="utf-8" ?>
<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
xmlns:local="clr-namespace:test"
x:Class="test.MainPage">
<StackLayout x:Name="myStackLayout" BackgroundColor="RoyalBlue">
<!-- Place new controls here -->
<Label Text="Welcome to Xamarin.Forms!"
HorizontalOptions="Center"
VerticalOptions="CenterAndExpand" BackgroundColor="Blue" />
</StackLayout>
</ContentPage>
您正在尝试从后台线程更新 UI,所有 UI 更改都应在主线程上完成。
Device.BeginInvokeOnMainThread(() =>
{
sl1.BackgroundColor = Color.FromHex("CCCCCC");
});