30

myToast.cancel()新しいトーストを発行する前に" を使用する一般的な "myToast" を使用してきました。Android v2.3以前の場合、これはうまく機能します。画面はキャンセルされ (すぐに消えます)、新しいトーストに置き換えられます. これにより、ユーザーがアラート (およびその他の条件) を必要とするキーを複数回押した場合に、トーストが山積みになるのを回避できます. 私の実際のケースでは、トーストが 1 つ表示されます間違ったキーが押された場合に表示され、Clear キーが押されていない場合に別の表示が表示されます。

Android 4.0 および 4.1 の場合、次のトーストのmyToast.cancel()前に を発行すると、現在のトーストと次のトーストの両方が強制終了されます。現在のcancel()APIは、現在のトーストと次のトーストをキャンセルすることを示しています(これはかなりばかげているようです)。乾杯したい乾杯をキャンセルするのはなぜですか?

キャンセルを Android バージョン間で一貫して機能させるためのアイデア (および v2.3 以前での動作方法) はありますか?

どのトーストが使用されているかを追跡する洗練されていないデュアル トースト システムを試してみますが、古い Android バージョンで完全かつ論理的に機能するものを取得するために、4.x でこの悪い動作を回避するのは非常に面倒なようです。


わかりました、解決しましたが、私が望んでいたほどきれいではありません。2 つのトーストを交互に使用するデュアル トースト アプローチを実装しました。最初に、 の前にアクティビティのトーストを定義しますOnCreate

Toast toast0;
Toast toast1;
private static boolean lastToast0 = true;

OnCreate で:

toast0 = new Toast(getApplicationContext());
toast0.cancel();
toast1 = new Toast(getApplicationContext());
toast1.cancel();

最後に、トーストを表示すると同時に前のトーストをキャンセルする必要がある場合は、次のようなものを使用します。

if (lastToast0) {
    toast0.cancel();
    toast1.setDuration(Toast.LENGTH_LONG);
    toast1.setText("new message");
    toast1.show();
    lastToast0 = false;
} else {
    toast1.cancel();
    toast0.setDuration(Toast.LENGTH_LONG);
    toast0.setText("new message");
    toast0.show();
    lastToast0 = true;
}

既存のトーストを (タイムアウトする前に) キャンセルする必要がある場合は、次を使用します。

toast0.cancel();
toast1.cancel();

Nexus 7 (4.1)、エミュレータ 4.0、および Android 2.2、2.3 を搭載した複数のデバイスでテスト済み。

4

8 に答える 8

52

を呼び出す代わりにcancel()。テキストをリセットして を呼び出してみてくださいshow()。これにより、最後のトーストが自動的にキャンセルされます

myToast.setText("wrong key")
myToast.show();

myToast毎回作成するのではなく、同じものを使い続けると、スタックしないと思います。

于 2012-10-16T20:28:25.420 に答える
3

nandeesh のソリューションはうまくいきませんでしたか? 彼のソリューションは、2 つの異なるトーストを使用するよりもクリーンです。

たとえば、(彼/彼女の回答を拡張して) onCreate の前に、トーストを宣言します。

private Toast myToast;

onCreate では、makeToast を使用して初期化する必要があります (そうしないと、エラーが発生します)。

myToast = Toast.makeText(getApplicationContext(), null, Toast.LENGTH_SHORT);

トーストを表示したいときはいつでも、次のように呼び出します。

myToast.setText("some text");
myToast.show();

これにより、以前のトーストが適切に置き換えられます。

于 2012-11-16T22:33:26.130 に答える
3

ここに別の同様の質問からコピーされた私の答えがあります:

クラスはBoastまさにあなたが必要とするものを達成します。


秘訣は、最後に表示されたものを追跡しToast、それをキャンセルすることです。

私が行ったことはToast、最後に表示された Toast への静的参照を含むラッパーを作成することです。

新しいものを表示する必要がある場合は、まず静的参照をキャンセルしてから、新しいものを表示します (そして静的に保存します)。

私が作成したラッパーの完全なコードを次に示しBoastます。これは、Toast メソッドを十分に模倣しており、使用することができます。デフォルトでは、Boastは前のトーストをキャンセルするので、表示されるのを待っているトーストのキューを構築しません。

アプリを終了するときに通知をキャンセルする方法を知りたい場合は、そこに多くのヘルプがあります。


package mobi.glowworm.lib.ui.widget;

import android.annotation.SuppressLint;
import android.content.Context;
import android.content.res.Resources;
import android.support.annotation.Nullable;
import android.widget.Toast;

import java.lang.ref.WeakReference;

/**
 * {@link Toast} decorator allowing for easy cancellation of notifications. Use this class if you
 * want subsequent Toast notifications to overwrite current ones. </p>
 * <p/>
 * By default, a current {@link Boast} notification will be cancelled by a subsequent notification.
 * This default behaviour can be changed by calling certain methods like {@link #show(boolean)}.
 */
public class Boast {
    /**
     * Keeps track of certain Boast notifications that may need to be cancelled. This functionality
     * is only offered by some of the methods in this class.
     * <p>
     * Uses a {@link WeakReference} to avoid leaking the activity context used to show the original {@link Toast}.
     */
    @Nullable
    private volatile static WeakReference<Boast> weakBoast = null;

    @Nullable
    private static Boast getGlobalBoast() {
        if (weakBoast == null) {
            return null;
        }

        return weakBoast.get();
    }

    private static void setGlobalBoast(@Nullable Boast globalBoast) {
        Boast.weakBoast = new WeakReference<>(globalBoast);
    }


    // ////////////////////////////////////////////////////////////////////////////////////////////////////////

    /**
     * Internal reference to the {@link Toast} object that will be displayed.
     */
    private Toast internalToast;

    // ////////////////////////////////////////////////////////////////////////////////////////////////////////

    /**
     * Private constructor creates a new {@link Boast} from a given {@link Toast}.
     *
     * @throws NullPointerException if the parameter is <code>null</code>.
     */
    private Boast(Toast toast) {
        // null check
        if (toast == null) {
            throw new NullPointerException("Boast.Boast(Toast) requires a non-null parameter.");
        }

        internalToast = toast;
    }

    // ////////////////////////////////////////////////////////////////////////////////////////////////////////

    /**
     * Make a standard {@link Boast} that just contains a text view.
     *
     * @param context  The context to use. Usually your {@link android.app.Application} or
     *                 {@link android.app.Activity} object.
     * @param text     The text to show. Can be formatted text.
     * @param duration How long to display the message. Either {@link Toast#LENGTH_SHORT} or
     *                 {@link Toast#LENGTH_LONG}
     */
    @SuppressLint("ShowToast")
    public static Boast makeText(Context context, CharSequence text, int duration) {
        return new Boast(Toast.makeText(context, text, duration));
    }

    /**
     * Make a standard {@link Boast} that just contains a text view with the text from a resource.
     *
     * @param context  The context to use. Usually your {@link android.app.Application} or
     *                 {@link android.app.Activity} object.
     * @param resId    The resource id of the string resource to use. Can be formatted text.
     * @param duration How long to display the message. Either {@link Toast#LENGTH_SHORT} or
     *                 {@link Toast#LENGTH_LONG}
     * @throws Resources.NotFoundException if the resource can't be found.
     */
    @SuppressLint("ShowToast")
    public static Boast makeText(Context context, int resId, int duration)
            throws Resources.NotFoundException {
        return new Boast(Toast.makeText(context, resId, duration));
    }

    /**
     * Make a standard {@link Boast} that just contains a text view. Duration defaults to
     * {@link Toast#LENGTH_SHORT}.
     *
     * @param context The context to use. Usually your {@link android.app.Application} or
     *                {@link android.app.Activity} object.
     * @param text    The text to show. Can be formatted text.
     */
    @SuppressLint("ShowToast")
    public static Boast makeText(Context context, CharSequence text) {
        return new Boast(Toast.makeText(context, text, Toast.LENGTH_SHORT));
    }

    /**
     * Make a standard {@link Boast} that just contains a text view with the text from a resource.
     * Duration defaults to {@link Toast#LENGTH_SHORT}.
     *
     * @param context The context to use. Usually your {@link android.app.Application} or
     *                {@link android.app.Activity} object.
     * @param resId   The resource id of the string resource to use. Can be formatted text.
     * @throws Resources.NotFoundException if the resource can't be found.
     */
    @SuppressLint("ShowToast")
    public static Boast makeText(Context context, int resId) throws Resources.NotFoundException {
        return new Boast(Toast.makeText(context, resId, Toast.LENGTH_SHORT));
    }

    // ////////////////////////////////////////////////////////////////////////////////////////////////////////

    /**
     * Show a standard {@link Boast} that just contains a text view.
     *
     * @param context  The context to use. Usually your {@link android.app.Application} or
     *                 {@link android.app.Activity} object.
     * @param text     The text to show. Can be formatted text.
     * @param duration How long to display the message. Either {@link Toast#LENGTH_SHORT} or
     *                 {@link Toast#LENGTH_LONG}
     */
    public static void showText(Context context, CharSequence text, int duration) {
        Boast.makeText(context, text, duration).show();
    }

    /**
     * Show a standard {@link Boast} that just contains a text view with the text from a resource.
     *
     * @param context  The context to use. Usually your {@link android.app.Application} or
     *                 {@link android.app.Activity} object.
     * @param resId    The resource id of the string resource to use. Can be formatted text.
     * @param duration How long to display the message. Either {@link Toast#LENGTH_SHORT} or
     *                 {@link Toast#LENGTH_LONG}
     * @throws Resources.NotFoundException if the resource can't be found.
     */
    public static void showText(Context context, int resId, int duration)
            throws Resources.NotFoundException {
        Boast.makeText(context, resId, duration).show();
    }

    /**
     * Show a standard {@link Boast} that just contains a text view. Duration defaults to
     * {@link Toast#LENGTH_SHORT}.
     *
     * @param context The context to use. Usually your {@link android.app.Application} or
     *                {@link android.app.Activity} object.
     * @param text    The text to show. Can be formatted text.
     */
    public static void showText(Context context, CharSequence text) {
        Boast.makeText(context, text, Toast.LENGTH_SHORT).show();
    }

    /**
     * Show a standard {@link Boast} that just contains a text view with the text from a resource.
     * Duration defaults to {@link Toast#LENGTH_SHORT}.
     *
     * @param context The context to use. Usually your {@link android.app.Application} or
     *                {@link android.app.Activity} object.
     * @param resId   The resource id of the string resource to use. Can be formatted text.
     * @throws Resources.NotFoundException if the resource can't be found.
     */
    public static void showText(Context context, int resId) throws Resources.NotFoundException {
        Boast.makeText(context, resId, Toast.LENGTH_SHORT).show();
    }

    // ////////////////////////////////////////////////////////////////////////////////////////////////////////

    /**
     * Close the view if it's showing, or don't show it if it isn't showing yet. You do not normally
     * have to call this. Normally view will disappear on its own after the appropriate duration.
     */
    public void cancel() {
        internalToast.cancel();
    }

    /**
     * Show the view for the specified duration. By default, this method cancels any current
     * notification to immediately display the new one. For conventional {@link Toast#show()}
     * queueing behaviour, use method {@link #show(boolean)}.
     *
     * @see #show(boolean)
     */
    public void show() {
        show(true);
    }

    /**
     * Show the view for the specified duration. This method can be used to cancel the current
     * notification, or to queue up notifications.
     *
     * @param cancelCurrent <code>true</code> to cancel any current notification and replace it with this new
     *                      one
     * @see #show()
     */
    public void show(boolean cancelCurrent) {
        // cancel current
        if (cancelCurrent) {
            final Boast cachedGlobalBoast = getGlobalBoast();
            if ((cachedGlobalBoast != null)) {
                cachedGlobalBoast.cancel();
            }
        }

        // save an instance of this current notification
        setGlobalBoast(this);

        internalToast.show();
    }

}
于 2013-04-19T08:04:11.557 に答える
2

cancel()怖くて何もしません。

Crouton https://github.com/keyboardsurfer/Croutonを使用することをお勧めします

于 2012-10-16T20:30:51.793 に答える
1

トースト オブジェクトを作成します。

Toast toastobject=null;

以下のコードを使用して、トーストを表示します。これは私のために見つけることができます

    int index = clickCounter-1;


    if(toastobject!= null)
            {
                toastobject.cancel();
            }
            toastobject = Toast.makeText(this,"Toast Text" , Toast.LENGTH_SHORT);
            listItems.remove(index);
            toastobject.show();
于 2015-07-16T06:06:54.513 に答える
0

新しい関数を作成し、これを呼び出します。

ImageButton ABtn = (ImageButton) findViewById(R.id.Btn);
ABtn.setOnClickListener(new View.OnClickListener() {
public void onClick(View v)
{       
SETToast("mytext");
}
});

    private Toast toast = null;

public void SETToast( String text)
{
  if(toast==null)
  {
     toast = Toast.makeText(getApplicationContext(), text, Toast.LENGTH_SHORT); 
     toast.show();
     final Handler handler = new Handler(); 
     handler.postDelayed(new Runnable() {
        @Override
        public void run() {
            toast=null;
        }
     }, 2000);
  }
  else
  {
      toast.setText(text);
  }   
}
于 2014-03-17T13:14:26.893 に答える