web-dev-qa-db-ja.com

runOnUiThreadがクラスに対して未定義

バックグラウンドスレッドからUIスレッドにダイアログをスローして警告しようとしていますが、runOnUiThreadが未定義であるという問題があります。 _FindLocation.this.runOnUiThread_とrunOnUiThreadを試しましたが、どちらも同じエラーThe method runOnUiThread(new Runnable(){}) is undefined for the type new LocationListener(){}(または_...the type FindLocation_)をスローしているようです。なぜ何かアイデアはありますか?これが私のFindLocation.Javaクラスのスニペットです。これは私の主な活動によって呼び出されます。

_public class FindLocation extends Thread {

public boolean inJurisdiction;
public boolean AlertNotice = false;
private LocationManager locManager;
private LocationListener locListener;

Context ctx;
public String userId;

public FindLocation(Context ctx) {
     this.ctx = ctx;
}

 public void start(String userId) {
        this.userId = userId;
        super.start();

      }

@Override
public void run() {
     Looper.prepare();
    final String usr = userId;  

    //get a reference to the LocationManager
    locManager = (LocationManager) ctx.getSystemService(Context.LOCATION_SERVICE);

    //checked to receive updates from the position
    locListener = new LocationListener() {
        public void onLocationChanged(Location loc) {

            String lat = String.valueOf(loc.getLatitude()); 
            String lon = String.valueOf(loc.getLongitude());

            Double latitude = loc.getLatitude();
            Double longitude = loc.getLongitude();

            if (latitude >= 39.15296 && longitude >= -86.547546 && latitude <= 39.184901 && longitude <= -86.504288 || inJurisdiction != false) {
                Log.i("Test", "Yes");  

                inJurisdiction = true;

                FindLocation.this.runOnUiThread(new Runnable() { ///****error here****
                    public void run() {
                        AlertDialog.Builder alert = new AlertDialog.Builder(ctx);
                        alert.setTitle("Sent");
                        alert.setMessage("You will be contacted shortly.");
                        alert.setPositiveButton("OK", new DialogInterface.OnClickListener() {
                           public void onClick(DialogInterface dialog, int which) {
                           }
                        });
                    }
                });
_
14
mkyong

runOnUIThread()Activityのメソッドであるため、コンストラクターでアクティビティの呼び出しへの参照を渡すことができます。

_...
Context ctx;
Activity act;
public String userId;
...

public FindLocation(Context ctx, Activity act) {
    this.ctx = ctx;
    this.act = act;
}
_

runOnUIThread()を次のように使用します

_act.runOnUiThread(new Runnable() {...});
_

ただし、これは安全ではないと思います。runOnUiThreadに電話をかけるときは、アクティビティがまだそこにあることを確認するための予防措置を講じる必要があります。

31
Vladimir
Another better approach..

Activityを取得するためのコンストラクターを作成する必要はありません。

コンテキストをActivityクラスにタイプキャストするだけです。

((Activity)context).runOnUiThread(new Runnable()
    {
        public void run()
        { 
             Toast.makeText(context, toast, Toast.LENGTH_SHORT).show();
        }
    });
13
Xar E Ahmer

runOnUIThread()Activityに属するメソッドです。SOスレッドから呼び出すことはできません。

したがって、Contextの代わりに、コンストラクターでActivityインスタンスを取得し、それを使用して呼び出します。

activity.runOnUIThread();
3
ngesh

このようなアクティビティを含めるようにクラスを拡張できます

public class YourClass extends Activity {}

これにより、「runOnUiThread」が使用可能になります。

また、アクティビティをインポートすることを忘れないでください

import Android.app.Activity;
1
viikatez

私はこれを行うためのよりきちんとした、よりモジュール化された方法を見つけました。このためには、Application Contextを定義しておく必要があります。それができたら、RunOnUIThreadへの参照を煩わせることなく、任意のクラスライブラリからActivityを呼び出すことができます。

クラスライブラリ内のどこからでも呼び出し:

Handler handler = new Handler(Application.Context.MainLooper);
handler.Post(() => doStuff());

私はMonoDroidを使用しているため、これはC#で記述されていることに注意してください。ただし、Javaと非常によく似ていると思います。 ApplicationContextを作成する方法については、これを見てください thread

1
Has AlTaiar