web-dev-qa-db-ja.com

すべての上にビューを描画する方法は?

現在表示されているものの上に、画面上で通知を作成できるアプリを作りたいです。 Go SMSメッセージポップアップのようなもの、または次の図のChatHeadのようなもの:

enter image description here

タッチイベントを含めて動的に描くことができればなお良いでしょう。これを行うための従来の方法または標準的な方法は何ですか?

例:

ホーム画面、アプリドロワー、その他のアプリのいずれでもクリックまたはドラッグできるアイコンのようです。投稿された画像の画面の端にある円形のアイコンに注意してください。アプリ内のどこにでもドラッグできます。

19
Allahjane

あなたが探しているのはシステム警告ウィンドウです。

StandOut というライブラリがあります。そのようなアプリを作成するのに役立ちます。

10
rhoadster91

Toastやダイアログウィンドウなどの機能は次のとおりです。

追加または前面に移動するだけでは機能しない場合、たとえば、サービスが別のクライアントアクティビティまたはアプリケーションに独自のビューを追加している場合(FaceUnlockがこれを行う)、または階層に依存できない場合は、ウィンドウを使用する必要があります。マネージャーとトリックを行うためのウィンドウトークン。その後、レイアウトを作成し、以前と同様にアニメーションとハードウェアアクセラレーションを利用できます。

    WindowManager windowManager = (WindowManager) getBaseContext().getSystemService(Context.WINDOW_SERVICE);

    WindowManager.LayoutParams layoutParams = new WindowManager.LayoutParams(WindowManager.LayoutParams.FIRST_SUB_WINDOW);
    layoutParams.width = 300;
    layoutParams.height = 300;

    layoutParams.format = PixelFormat.RGBA_8888;
    layoutParams.flags =
            WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN
                    | WindowManager.LayoutParams.FLAG_HARDWARE_ACCELERATED;
    layoutParams.token = getWindow().getDecorView().getRootView().getWindowToken();

    //Feel free to inflate here
    mTestView = new View(this);
    mTestView.setBackgroundColor(Color.RED);

    //Must wire up back button, otherwise it's not sent to our activity
    mTestView.setOnKeyListener(new View.OnKeyListener() {
        @Override
        public boolean onKey(View v, int keyCode, KeyEvent event) {
            if (keyCode == KeyEvent.KEYCODE_BACK) {
                onBackPressed();
            }
            return true;
        }
    });
    windowManager.addView(mTestView, layoutParams);

次に、必ずonDestroy(またはonPause)ビューを削除してください。削除しないとクラッシュします。

   if (mTestView != null) {
       WindowManager windowManager = (WindowManager) getBaseContext().getSystemService(Context.WINDOW_SERVICE);
       if (mTestView.isShown()) {
            windowManager.removeViewImmediate(mTestView);
       }
   }
10
Joel Teply

これを行うために新しいアクティビティは必要ありません。必要なのは、既存のアクティビティに別のビューを追加して前面に表示し、そのビューに必要なものを描画/書き込むことだけです。

この追加のビューで特別なことをしたい場合は、独自のビュークラスを作成できます

class DrawOnTop extends View { 
    public DrawOnTop(Context activity) { 
        super(activity);
    }

    @Override 
    protected void onDraw(Canvas canvas) {
        // put your drawing commands here
    }

}

そして、あなたは次のようなことをします

DrawOnTop mDraw = new DrawOnTop(this);
addContentView(mDraw, new LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT));
mDraw.bringToFront();

次に、強制的に描画するには、mDraw.invalidate();を使用する必要があります。

9
Stochastically

レイアウト全体の親をRelativeLayoutにすることができます。メインレイアウトの「ルート」となる最初の子。それ以降は、気まぐれに配置できるオーバーレイと見なすことができます。

例:

<RelativeLayout>
  <LinearLayout>
    ... Main Layout here ...
  </LinearLayout>

  <TextView left="20dip" top="20dip" text="Overlay" alpha="0.7" />
</RelativeLayout>
1
Knossos

最善の方法は、アプリケーションでサービスを開始することです。 ImageViewを作成します。画像ビューのLayoutParamsを設定します。サービスの作成時に、ビューをパラメータとともにウィンドウマネージャに追加します。

ALL SETあなたの画像はあなたのウィンドウに付着します(あなたがアプリケーションを閉じるまで).

Onclicklistenersとontouchlistenersをイメージビューに追加することもできます。例えば。 OnClickリスナーがアクションを実行し、Ontouchlistenerが画像を画面に沿って移動します。

1
Sujith Royal