0

I'm attempting to implement a fling gesture. Ultimately it will have the same function as the native android contact app, you'll swipe the listview and it'll open up the dialer. I'm having an issue getting everything 100% though. As of now the listview loads as it should, but after much Googling, and tutorials i've come up with this and need help.

SimpleGestureFilter

public final static int SWIPE_UP    = 1;
 public final static int SWIPE_DOWN  = 2;
 public final static int SWIPE_LEFT  = 3;
 public final static int SWIPE_RIGHT = 4;

 public final static int MODE_TRANSPARENT = 0;
 public final static int MODE_SOLID       = 1;
 public final static int MODE_DYNAMIC     = 2;

 private final static int ACTION_FAKE = -13; //just an unlikely number
 private int swipe_Min_Distance = 100;
 private int swipe_Max_Distance = 350;
 private int swipe_Min_Velocity = 100;

 private int mode      = MODE_DYNAMIC;
 private boolean running = true;
 private boolean tapIndicator = false;

 private Activity context;
 private GestureDetector detector;
 private SimpleGestureListener listener;


 public SimpleGestureFilter(Activity context,SimpleGestureListener sgl) {

  this.context = context;
  this.detector = new GestureDetector(context, this);
  this.listener = sgl; 
 }

 public void onTouchEvent(MotionEvent event){

   if(!this.running)
  return;  

   boolean result = this.detector.onTouchEvent(event); 

   if(this.mode == MODE_SOLID)
    event.setAction(MotionEvent.ACTION_CANCEL);
   else if (this.mode == MODE_DYNAMIC) {

     if(event.getAction() == ACTION_FAKE) 
       event.setAction(MotionEvent.ACTION_UP);
     else if (result)
       event.setAction(MotionEvent.ACTION_CANCEL); 
     else if(this.tapIndicator){
      event.setAction(MotionEvent.ACTION_DOWN);
      this.tapIndicator = false;
     }

   }
   //else just do nothing, it's Transparent
 }

 public void setMode(int m){
  this.mode = m;
 }

 public int getMode(){
  return this.mode;
 }

 public void setEnabled(boolean status){
  this.running = status;
 }

 public void setSwipeMaxDistance(int distance){
  this.swipe_Max_Distance = distance;
 }

 public void setSwipeMinDistance(int distance){
  this.swipe_Min_Distance = distance;
 }

 public void setSwipeMinVelocity(int distance){
  this.swipe_Min_Velocity = distance;
 }

 public int getSwipeMaxDistance(){
  return this.swipe_Max_Distance;
 }

 public int getSwipeMinDistance(){
  return this.swipe_Min_Distance;
 }

 public int getSwipeMinVelocity(){
  return this.swipe_Min_Velocity;
 }


 @Override
 public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX,
   float velocityY) {

  final float xDistance = Math.abs(e1.getX() - e2.getX());
  final float yDistance = Math.abs(e1.getY() - e2.getY());

  if(xDistance > this.swipe_Max_Distance || yDistance > this.swipe_Max_Distance)
   return false;

  velocityX = Math.abs(velocityX);
  velocityY = Math.abs(velocityY);
        boolean result = false;

  if(velocityX > this.swipe_Min_Velocity && xDistance > this.swipe_Min_Distance){
   if(e1.getX() > e2.getX()) // right to left
    this.listener.onSwipe(SWIPE_LEFT);
   else
    this.listener.onSwipe(SWIPE_RIGHT);

   result = true;
  }
  else if(velocityY > this.swipe_Min_Velocity && yDistance > this.swipe_Min_Distance){
   if(e1.getY() > e2.getY()) // bottom to up 
    this.listener.onSwipe(SWIPE_UP);
   else
    this.listener.onSwipe(SWIPE_DOWN);

   result = true;
  }

   return result;
 }

 @Override
 public boolean onSingleTapUp(MotionEvent e) {
  this.tapIndicator = true;
  return false;
 }

 @Override
 public boolean onDoubleTap(MotionEvent arg0) {
  this.listener.onDoubleTap();;
  return true;
 }

 @Override
 public boolean onDoubleTapEvent(MotionEvent arg0) {
  return true;
 }

 @Override
 public boolean onSingleTapConfirmed(MotionEvent arg0) {

  if(this.mode == MODE_DYNAMIC){        // we owe an ACTION_UP, so we fake an       
     arg0.setAction(ACTION_FAKE);      //action which will be converted to an ACTION_UP later.                                    
     this.context.dispatchTouchEvent(arg0);  
  }   

  return false;
 }


    static interface SimpleGestureListener{
     void onSwipe(int direction);
     void onDoubleTap();
 }

}

DisplayCompanies.java

public class DisplayCompanies extends ListActivity {
    //JSONArrays?
    JSONArray directory;
    private SimpleGestureFilter detector;


    //JSON Node names
    private static String TAG_ID = "id";
    private static String TAG_COMPANY= "organization";
    private static String TAG_PHONE= "number";
    private static String TAG_CATEGORY= "companies";

    private final static String url= "API URL BASE HERE";
    JSONObject json;
    CompanyListJSONParser jParser = new CompanyListJSONParser();
    ArrayList<HashMap<String, String>> directoryList;

    @SuppressLint("NewApi")
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.service);

        directoryList = new ArrayList<HashMap<String, String>>();
        Request request = new Request();
        request.execute();


        // Make sure we're running on Honeycomb or higher to use ActionBar APIs
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB) {
            // Show the Up button in the action bar.
            getActionBar().setDisplayHomeAsUpEnabled(true);
            setTitle("Available Companies");

        }
    }// end of onCreate Method
    @SuppressWarnings("unused")
    public class Request extends AsyncTask<String, Void, JSONObject> {

        private static final int REGISTRATION_TIMEOUT = 3 * 1000;
        private static final int WAIT_TIMEOUT = 30 * 1000;
        private ProgressDialog dialog = 
                new ProgressDialog(DisplayCompanies.this);


        protected void onPreExecute() {
            dialog = new ProgressDialog(DisplayCompanies.this);
            dialog.setMessage("Getting Available Companies... Please wait...");
            dialog.show();
        }

        protected JSONObject doInBackground(String... params) {
            String cat = null;
            Bundle extras = getIntent().getExtras();
            if (extras != null) {
                cat = extras.getString("catID");
            }
            String fullUrl = url + cat;
            json = jParser.getJSONfromURL(fullUrl);

            return json;

        }

        protected void onPostExecute(JSONObject s) {          
            super.onPostExecute(s);
            String name = null;
            String id = null;
            String phone = null;
            dialog.dismiss();

            try {
                directory = s.getJSONArray(TAG_CATEGORY);
            } catch (JSONException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
            for(int i = 0; i < directory.length(); i++){;
            try {
                id = directory.getJSONObject(i).getString(TAG_ID);
                name = directory.getJSONObject(i).getString(TAG_COMPANY);
                phone = directory.getJSONObject(i).getString(TAG_PHONE);
            } catch (JSONException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
            displayCatList(id, name, phone);

            }

        }

    }

    public void displayCatList(String id, String name, String phone){                 
        //create new HashMap
        HashMap<String,String> map = new HashMap<String, String>();

        //add each child node to HashMap key
        map.put(TAG_ID, id);
        map.put(TAG_COMPANY, name);
        map.put(TAG_PHONE, phone);

        //adding HashList to ArrarList
        directoryList.add(map);

        MySimpleAdapter adapter = new MySimpleAdapter(this, R.layout.list_item, android.R.id.text1, directoryList);
        setListAdapter(adapter);

        adapter.notifyDataSetChanged();
    }



    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        switch (item.getItemId()) {
        case android.R.id.home:
            NavUtils.navigateUpFromSameTask(this);
            return true;
        }
        return super.onOptionsItemSelected(item);
    }


    public class MySimpleAdapter extends ArrayAdapter<HashMap<String, String>> {

        List<HashMap<String, String>> listItems;

        public MySimpleAdapter(Context context, int resource,
                int textViewResourceId, List<HashMap<String, String>> objects) {
            super(context, resource, textViewResourceId, objects);
            listItems = objects;
        }

        @Override
        public View getView(final int position, View convertView, ViewGroup parent) {
            // TODO Auto-generated method stub
            if(convertView == null) {
                LayoutInflater inflator = (LayoutInflater)  getSystemService(Context.LAYOUT_INFLATER_SERVICE);
                convertView = inflator.inflate(R.layout.list_item, null);
            }

            TextView listName = (TextView) convertView.findViewById(R.id.listName);

            listName.setTag(listItems.get(position).get(TAG_ID));
            listName.setText(listItems.get(position).get(TAG_COMPANY));

            //for use with onClick
            listName.setOnClickListener(new OnClickListener() {
                @Override
                /**
                 * Method provides action when the selected item in list view is clicked.
                 */
                public void onClick(View v){
                    Log.i("Click", "id # " + listItems.get(position).get(TAG_ID) + " Company: " + listItems.get(position).get(TAG_COMPANY)+ " Phone #: " + listItems.get(position).get(TAG_PHONE));
                    //Intent DisplayCompanies = new Intent (DisplayServiceActivity.this, DisplayCompanies.class);
                    //DisplayServiceActivity.this.startActivity(DisplayCompanies);
                }
            });

            //Gesture or fling implementation
            detector = new SimpleGestureFilter(this,this);


            return convertView;
        }


        public boolean dispatchTouchEvent(MotionEvent me){ 
            detector.onTouchEvent(me);
            return super.dispatchTouchEvent(me); 
        }
        public void onSwipe(int direction) {
            String str = "";

            switch (direction) {

            case SimpleGestureFilter.SWIPE_RIGHT : str = "Swipe Right";
            break;
            case SimpleGestureFilter.SWIPE_LEFT :  str = "Swipe Left";
            break;
            case SimpleGestureFilter.SWIPE_DOWN :  str = "Swipe Down";
            break;
            case SimpleGestureFilter.SWIPE_UP :    str = "Swipe Up";
            break;

            } 
            Toast.makeText(this, str, Toast.LENGTH_SHORT).show();
        }

        public void onDoubleTap() {
            Toast.makeText(this, "Double Tap", Toast.LENGTH_SHORT).show(); 
        }

    }

}

}

At this point Eclipse won't compile and these are what are underlined:

public boolean dispatchTouchEvent(MotionEvent me){ 
            detector.onTouchEvent(me);
            return super.dispatchTouchEvent(me); 
        }

Because: he method dispatchTouchEvent(MotionEvent) is undefined for the type ArrayAdapter>

And

Toast.makeText(this, "Double Tap", Toast.LENGTH_SHORT).show();

Because: The method makeText(Context, CharSequence, int) in the type Toast is not applicable for the arguments (DisplayCompanies.MySimpleAdapter, String, int)

Any help on this would be great. Thank you guys in advance!

user1890328
  • 1,222
  • 1
  • 13
  • 21

1 Answers1

0

You keep making new gesture filters and assigning them over and over to the same thing with this code.

//Gesture or fling implementation
    detector = new SimpleGestureFilter(this,this);

You should make a gesture detector for each view, instead of one for the ListView

HalR
  • 11,411
  • 5
  • 48
  • 80