Fling Gesture and Webview in Android

Rob Bushway picture Rob Bushway · Nov 19, 2010 · Viewed 15.1k times · Source

I have a webview control that needs to support the fling gesture in Android in order to bring up a new record (load new data). This is occuring in a class that extends Activity. All the examples I've seen show how to implement gesture support for a textview, but nothing for webview.

I need to execute different actions for both left and right flings. Any code help would be appreciated as this totally has me stumped.

Here's my basic onCreate and my class

import android.app.Activity;
import android.content.Intent;
import android.database.Cursor;
import android.database.SQLException;
import android.os.Bundle;
import android.text.Html;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.view.Window;

import android.webkit.WebView;

public class ArticleActivity extends Activity   {

public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);



    Window  w = getWindow();

     w.requestFeature(Window.FEATURE_LEFT_ICON);

     WebView webview = new WebView(this);
     setContentView(webview); 



     w.setFeatureDrawableResource(Window.FEATURE_LEFT_ICON,
     R.drawable.gq);




    setDefaultKeyMode(DEFAULT_KEYS_SEARCH_LOCAL);
    populateFields();
    webview.loadData(question + answer, "text/html", "utf-8");



  //   
}
private void populateFields() {

....


}

}

Answer

techiServices picture techiServices · Nov 19, 2010

Create a GestureListener and a GestureDetector. Call the GestureDetector.onTouchEvent by overriding the webview's onTouchEvent.

You can also just override the Activity onTouchEvent btw. I can post some code if you need.

Edit: Code as requested.

public class Main extends Activity {

    /** Called when the activity is first created. */
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        MyWebView webview = new MyWebView(this);
        setContentView(webview);
    }

    class MyWebView extends WebView {
        Context context;
        GestureDetector gd;

        public MyWebView(Context context) {
            super(context);

            this.context = context;
            gd = new GestureDetector(context, sogl);
        }

        @Override
        public boolean onTouchEvent(MotionEvent event) {
            return gd.onTouchEvent(event);
        }

        GestureDetector.SimpleOnGestureListener sogl = new GestureDetector.SimpleOnGestureListener() {
            public boolean onDown(MotionEvent event) {
                return true;
            }

            public boolean onFling(MotionEvent event1, MotionEvent event2, float velocityX, float velocityY) {
                if (event1.getRawX() > event2.getRawX()) {
                    show_toast("swipe left");
                } else {
                    show_toast("swipe right");
                }
                return true;
            }
        };

        void show_toast(final String text) {
            Toast t = Toast.makeText(context, text, Toast.LENGTH_SHORT);
            t.show();
        }
    }
}

@littleFluffyKitty. I presume by default WebView touch events you mean when it brings up the zoom controls etc? I didn't test that. I have found that implementing ones own gesture detection works best (not sure if it would work best on a WebView though). You need to look at a touch event as three distinct components. The press down, the movement (if any), and the press release, as the press down, move, release always happen.

If you do a return false on the onDown the action should get passed down to the WebView touch event handler but iirc it stops the subsequent events being passed to the GestureDetector. Which is half the reason why I implement my own which is based on the Android source. iirc I got the idea from the Sony Ericsson Tutorials which is downloadable off the market. It's the 3D list which shows the code and its pretty easy to adapt.