Search code examples
androidmapspoints

Android select closest points within a radius on long press


I'm using Mapsforge and I've got a MapView I've added some points to. Some of the points are too close for the user to be able to click them and get the right popup, even zoomed in all the way.

What I'm wanting to do is make it so they can longpress on an area of the map, and a scrollable dialog will appear listing the points within like x pixels of where they long pressed or something like that. I can figure out the dialog and long press stuff, but I'm curious if anyone knows how to capture "points within x pixels of where I clicked" without going through my app's database and running a calculation on every point I have saved there? There should be some mapsforge method I can call or use right?

EDIT: I've come back to this recently and added the following code to catch the long press events, I'm trying to figure out a way to grab surrounding points now. I think it needs to be based on where the points are on the screen, because if I do it based on lat and long from the database, I have to a different distance value for each zoom level, etc.

boolean ACTION_MOVED = false;
long beginTime;
@Override
public boolean onTouch(View view, MotionEvent motionEvent) {
    switch (motionEvent.getAction()) {
        case MotionEvent.ACTION_DOWN: {
            beginTime = System.currentTimeMillis();
            ACTION_MOVED = false;
            break;
        }
        case MotionEvent.ACTION_MOVE: {
            ACTION_MOVED = true;
            break;
        }
        case MotionEvent.ACTION_UP: {
            if (System.currentTimeMillis() - beginTime >= ViewConfiguration.getLongPressTimeout())
                if (!ACTION_MOVED) {
                    Toast.makeText(mapActivity, "long Press", Toast.LENGTH_SHORT).show();
                    ACTION_MOVED = false;
                    return true;
                }
            break;
        }
    }

    return view.onTouchEvent(motionEvent);
}

Solution

  • Since this has been viewed a few times, I figured I ought to post how I ended up getting this working. I basically go through the database and see if every point is inside some selection area I picked based on testing:

    public static boolean withinSelectionArea(GeoPoint myPointG, GeoPoint dbPointG, Context context) {
        Point myPoint = projection.toPixels(myPointG, null);
        Point dbPoint = projection.toPixels(dbPointG, null);
        float a = dbPoint.x - myPoint.x;
        float b = dbPoint.y - myPoint.y;
        double distance = Math.sqrt(a * a + b * b);
        return distance < context.getResources().getDisplayMetrics().densityDpi / 4;
    }
    

    I also overrode the onLongPress handler and called the above method in that.