NikosD
NikosD

Reputation: 125

Xamarin Android custom thread class blocks UI

I am trying to create a custom thread class, but when I call its functions it blocks my UI thread. What I mean is that when I press the button, it stays pressed until the task completes.

This is the Main Activity:

using Android.App;
using Android.Widget;
using Android.OS;
using Java.Lang;

namespace ThreadTest08 {
    [Activity(Label = "ThreadTest08", MainLauncher = true, Icon = "@drawable/icon")]
    public class MainActivity : Activity {

        protected override void OnCreate(Bundle bundle) {
            base.OnCreate(bundle);

            SetContentView(Resource.Layout.Main);
            Button button = FindViewById<Button>(Resource.Id.MyButton);

            button.Click += delegate {
                MyThreadClass mtc = new MyThreadClass();
                mtc.Start();
                mtc.DoSomething();    
            };    
        }
    }
}

And this is the class:

using Java.Lang;

namespace ThreadTest08 {
    class MyThreadClass : Thread {    
        public void DoSomething() {
            Thread.Sleep(3000);
        }
    }
}

Why is this happening? Thanks for reading.

Upvotes: 1

Views: 1570

Answers (2)

Yuri S
Yuri S

Reputation: 5370

You can do as the following code

button.Click += MyButtonClick;

private async void MyButtonClick(object sender, EventArgs e)
{
    button.Text="Working";
    await Task.Run(async () =>
    {
        await Task.Delay(3000); //or whatever you need
         Device.BeginInvokeOnMainThread(() => {
           button.Text="Done";
         });

    });
}

Upvotes: 0

476rick
476rick

Reputation: 2795

Thread.Sleep should be avoided while using almost all UI frameworks (WinForms/WPF/Xamarin.Forms/Silverlight/...) as it freezes the UI thread and hangs the UI.

If you want to wait

asynchronously: await Task.Delay(10000);

synchronously: Task.Delay(10000).Wait();

But please try to avoid blocking the UI thread to ensure a good user experience and keep your app responsive.

Using Thread.Sleep in Xamarin.Forms

There are two Xamarin.Forms templates:

Xamarin.Forms Portable Class Library

Because of the PCL subset mechanism, you have no chance to get Thread.Sleep. Xamarin.Forms Shared Project

This Template contains different platforms that do not support Thread.Sleep. Windows UWP, Xamarin.Android and Xamarin.iOS support it, Windows Phone 8.1, and Windows 8.1 not. If you unload/delete the 2 projects, the solution builds. (don't forget using System.Threading; in your App.cs)

source

EDIT: The UI thread freezes because your custom thread makes your UI thread wait. The actions you do in your custom thread run on the UI thread.

You could use async methods to execute the code you showed in your comment. I think that would accomplish what you need.

Upvotes: 2

Related Questions