6

(この質問で説明されている動作は、私たちが行っていた他の何かとは無関係に見えるためにのみ表示されたことに注意してください。受け入れられた回答を参照してください。)

GridViewとのSlidingDrawer内部を持つAndroidアクティビティがありRelativeLayoutます。このアクティビティがトラックボール(またはカーソルキー)に応答する方法はかなり奇妙です。フォーカスはGridView内のアイテム間を移動しますが、カーソルがGridViewの「外側」の方向に移動するたびに移動します。(例えば、一番上にあるときは上に、すでに一番左のアイテムにあるときは左に)スライド式引き出しは開閉します。特に、フォーカスはGridViewの同じアイテムにとどまります---スライドドロワーには移動しません。

トラックボールの場合、これは特に恐ろしいことです。トラックボールを実際の目的地を超えて回転させると、スライド式の引き出しが繰り返し開閉するためです。

をオーバーライドすることで、トラックボールを完全にオフにできると判断しましたonTrackballEvent()。トラックボールとカーソルがGridViewで正常に機能するようにしたいのですが、スライドドロワーを開閉させないようにします。原則として、トラックボールは開いた状態でスライドドロワーのさまざまな内容に焦点を合わせてほしいと思います。

どのように?

4

3 に答える 3

3

およびのカスタム実装と、のカスタム実装を拡張GridViewおよびSlidingDrawer使用するカスタムビューを作成することを検討してください。でトリガーされる可能性のあるユーザーインタラクションによっては、カスタムを実装する必要がない場合があります。onInterceptTouchEventonTouchEventGridViewonInterceptTouchEventSlidingDrawerSlidingDrawerhandle

カスタムGridViewの場合は、次のように定義されたインターフェイスを指定します。

public interface MyGridViewListener {
    public boolean shouldPreventScroll();
}

カスタムSlidingDrawerが開いている場合は戻ります。この戻り値は、でアクションを実行する必要があるかどうか(onInterceptTouchEventおよびonTouchEventメソッド)を決定するために使用されGridViewます。したがって、SlidingDrawerが開かれると、で実行されたアクションはでGridView何もトリガーしませんSlidingDrawer

アクティビティ:

MyGridView gridView = (MyGridView) findViewById(R.id.gridView);
gridView.setMyGridViewListener(new MyGridViewListener() {
    @Override
    public boolean shouldPreventScroll() {
        return slidingDrawer.isOpened();
    }
});

MyCustomGridView: shouldInterceptでタッチ/トラックイベントが発生するたびに呼び出されGridViewます。

private boolean shouldIntercept() {
    boolean shouldIntercept = false;
    if(myGridViewListener != null) {
        shouldIntercept = myGridViewListener.shouldPreventScroll();
    }
    return shouldIntercept;
}
@Override
public boolean onInterceptTouchEvent(MotionEvent ev) {
    return shouldIntercept() ? true : super.onInterceptTouchEvent(ev);
}
@Override
public boolean onTouchEvent(MotionEvent ev) {
    return shouldIntercept() ? true : super.onTouchEvent(ev);
}
@Override
public boolean onTrackballEvent(MotionEvent event) {
    return shouldIntercept() ? true : super.onTrackballEvent(event);
}
public MyGridViewListener getMyGridViewListener() {
    return myGridViewListener;
}
public void setMyGridViewListener(
        MyGridViewListener myGridViewListener) {
    this.myGridViewListener = myGridViewListener;
}

これがあなたを正しい方向に向けるか、少なくとも助けになることを願っています

于 2011-12-01T20:56:05.833 に答える
1

カスタムのスライド式引き出しで遊んでいる間、ハンドルのレイアウトを奇妙な値に設定しました。

handle.layout(0, 0,0, 0);

ハンドルを消すために、画面の横から指をドラッグしてもスライド式の引き出しが開くので、これは私が望んでいなかったので、

handle.layout(10000, 10000, 10000, 10000); 

これにより、表示可能領域の外側に移動し、画面の横からドラッグして引き出しを手動で引き出すことができなくなりました。引き出しのスライドを決定するハンドルのソースコードを確認した後、ハンドルを取り除くと、問題が解決するはずです。

ドロワーを開閉する必要がある場合は、animateOpen()/ animateClose()を呼び出します。

于 2011-12-01T21:56:33.027 に答える
0

結局のところ、私たちはこの問題を無関係な少しの愚かさによって引き起こしました。MENUキーを開いたり閉じたりしたかったのSlidingDrawerです。これをオーバーライドして行いましたonPrepareOptionsMenu()

public boolean onPrepareOptionsMenu (Menu menu) {
    slidingDrawer.animateToggle();
    return true;
}

これは正常に機能します。しかし、メニューが開かれようとしていないときに呼び出すことができることがわかりました。特に、Activityを使用する場合setDefaultKeyMode(DEFAULT_KEYS_SHORTCUT)、未処理のキーイベントがメニューにアクセスすることになります。これには、画面の端から離れたトラックボールの動きが含まれます。

望ましい振る舞いを得るためのそれほど馬鹿げた方法は

public boolean onKeyUp(int keyCode, KeyEvent event) {
    if(keyCode==KeyEvent.KEYCODE_MENU) {
        slidingDrawer.animateToggle();
    }
    return super.onKeyUp(keyCode,event);
}

一方、トラックボールが開いているときに、コールSlidingDrawerするを設定することで、トラックボールを動かすことができますSlidingDrawer.OnDrawerOpenListener

slidingDrawer.getContent().requestFocus();

最後に、電話するのは良い考えのようです

slidingDrawer.getHandle().setFocusable(false);
于 2011-12-08T18:24:58.940 に答える