Skip to content
This repository has been archived by the owner on Aug 8, 2023. It is now read-only.

fixes #1969: support for marker tapping in Android #2201

Merged
merged 1 commit into from
Aug 28, 2015
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
104 changes: 104 additions & 0 deletions android/cpp/jni.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,13 @@ jfieldID latLngZoomLatitudeId = nullptr;
jfieldID latLngZoomLongitudeId = nullptr;
jfieldID latLngZoomZoomId = nullptr;

jclass bboxClass = nullptr;
jmethodID bboxConstructorId = nullptr;
jfieldID bboxLatNorthId = nullptr;
jfieldID bboxLatSouthId = nullptr;
jfieldID bboxLonEastId = nullptr;
jfieldID bboxLonWestId = nullptr;

jclass markerClass = nullptr;
jmethodID markerConstructorId = nullptr;
jfieldID markerPositionId = nullptr;
Expand Down Expand Up @@ -970,6 +977,50 @@ void JNICALL nativeRemoveAnnotations(JNIEnv *env, jobject obj, jlong nativeMapVi
nativeMapView->getMap().removeAnnotations(ids);
}

jlongArray JNICALL nativeGetAnnotationsInBounds(JNIEnv *env, jobject obj, jlong nativeMapViewPtr, jobject bbox) {
mbgl::Log::Debug(mbgl::Event::JNI, "nativeGetAnnotationsInBounds");
assert(nativeMapViewPtr != 0);
NativeMapView *nativeMapView = reinterpret_cast<NativeMapView *>(nativeMapViewPtr);

if (env->ExceptionCheck() || (bbox == nullptr)) {
env->ExceptionDescribe();
return nullptr;
}

jdouble swLat = env->GetDoubleField(bbox, bboxLatSouthId);
if (env->ExceptionCheck()) {
env->ExceptionDescribe();
return nullptr;
}

jdouble swLon = env->GetDoubleField(bbox, bboxLonWestId);
if (env->ExceptionCheck()) {
env->ExceptionDescribe();
return nullptr;
}

jdouble neLat = env->GetDoubleField(bbox, bboxLatNorthId);
if (env->ExceptionCheck()) {
env->ExceptionDescribe();
return nullptr;
}

jdouble neLon = env->GetDoubleField(bbox, bboxLonEastId);
if (env->ExceptionCheck()) {
env->ExceptionDescribe();
return nullptr;
}

mbgl::LatLngBounds bounds;
bounds.sw = { swLat, swLon };
bounds.ne = { neLat, neLon };

// assume only points for now
std::vector<uint32_t> annotations = nativeMapView->getMap().getAnnotationsInBounds(bounds, mbgl::AnnotationType::Point);

return std_vector_uint_to_jobject(env, annotations);
}

void JNICALL nativeSetSprite(JNIEnv *env, jobject obj, jlong nativeMapViewPtr,
jstring symbol, jint width, jint height, jfloat scale, jbyteArray jpixels) {
mbgl::Log::Debug(mbgl::Event::JNI, "nativeSetSprite");
Expand Down Expand Up @@ -1246,6 +1297,42 @@ extern "C" JNIEXPORT jint JNICALL JNI_OnLoad(JavaVM *vm, void *reserved) {
return JNI_ERR;
}

bboxClass = env->FindClass("com/mapbox/mapboxgl/geometry/BoundingBox");
if (bboxClass == nullptr) {
env->ExceptionDescribe();
return JNI_ERR;
}

bboxConstructorId = env->GetMethodID(bboxClass, "<init>", "(DDDD)V");
if (bboxConstructorId == nullptr) {
env->ExceptionDescribe();
return JNI_ERR;
}

bboxLatNorthId = env->GetFieldID(bboxClass, "mLatNorth", "D");
if (bboxLatNorthId == nullptr) {
env->ExceptionDescribe();
return JNI_ERR;
}

bboxLatSouthId = env->GetFieldID(bboxClass, "mLatSouth", "D");
if (bboxLatSouthId == nullptr) {
env->ExceptionDescribe();
return JNI_ERR;
}

bboxLonEastId = env->GetFieldID(bboxClass, "mLonEast", "D");
if (bboxLonEastId == nullptr) {
env->ExceptionDescribe();
return JNI_ERR;
}

bboxLonWestId = env->GetFieldID(bboxClass, "mLonWest", "D");
if (bboxLonWestId == nullptr) {
env->ExceptionDescribe();
return JNI_ERR;
}

markerClass = env->FindClass("com/mapbox/mapboxgl/annotations/Marker");
if (markerClass == nullptr) {
env->ExceptionDescribe();
Expand Down Expand Up @@ -1596,6 +1683,8 @@ extern "C" JNIEXPORT jint JNICALL JNI_OnLoad(JavaVM *vm, void *reserved) {
reinterpret_cast<void *>(&nativeAddPolygons)},
{"nativeRemoveAnnotation", "(JJ)V", reinterpret_cast<void *>(&nativeRemoveAnnotation)},
{"nativeRemoveAnnotations", "(J[J)V", reinterpret_cast<void *>(&nativeRemoveAnnotations)},
{"nativeGetAnnotationsInBounds", "(JLcom/mapbox/mapboxgl/geometry/BoundingBox;)[J",
reinterpret_cast<void *>(&nativeGetAnnotationsInBounds)},
{"nativeSetSprite", "(JLjava/lang/String;IIF[B)V", reinterpret_cast<void *>(&nativeSetSprite)},
{"nativeOnLowMemory", "(J)V", reinterpret_cast<void *>(&nativeOnLowMemory)},
{"nativeSetDebug", "(JZ)V", reinterpret_cast<void *>(&nativeSetDebug)},
Expand Down Expand Up @@ -1639,6 +1728,13 @@ extern "C" JNIEXPORT jint JNICALL JNI_OnLoad(JavaVM *vm, void *reserved) {
return JNI_ERR;
}

bboxClass = reinterpret_cast<jclass>(env->NewGlobalRef(bboxClass));
if (bboxClass == nullptr) {
env->ExceptionDescribe();
env->DeleteGlobalRef(bboxClass);
return JNI_ERR;
}

markerClass = reinterpret_cast<jclass>(env->NewGlobalRef(markerClass));
if (markerClass == nullptr) {
env->ExceptionDescribe();
Expand Down Expand Up @@ -1795,6 +1891,14 @@ extern "C" JNIEXPORT void JNICALL JNI_OnUnload(JavaVM *vm, void *reserved) {
latLngZoomLatitudeId = nullptr;
latLngZoomZoomId = nullptr;

env->DeleteGlobalRef(bboxClass);
bboxClass = nullptr;
bboxConstructorId = nullptr;
bboxLatNorthId = nullptr;
bboxLatSouthId = nullptr;
bboxLonEastId = nullptr;
bboxLonWestId = nullptr;

env->DeleteGlobalRef(markerClass);
markerClass = nullptr;
markerConstructorId = nullptr;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,7 @@
import com.mapbox.mapboxgl.annotations.PolygonOptions;
import com.mapbox.mapboxgl.annotations.Polyline;
import com.mapbox.mapboxgl.annotations.PolylineOptions;
import com.mapbox.mapboxgl.geometry.BoundingBox;
import com.mapbox.mapboxgl.geometry.LatLng;
import com.mapbox.mapboxgl.geometry.LatLngZoom;
import com.mapzen.android.lost.api.LocationListener;
Expand Down Expand Up @@ -428,6 +429,25 @@ public List<Annotation> getAnnotations() {
return Collections.unmodifiableList(mAnnotations);
}

public List<Annotation> getAnnotationsInBounds(BoundingBox bbox) {
List<Annotation> annotations = new ArrayList<>();
long[] ids = mNativeMapView.getAnnotationsInBounds(bbox);
List<Long> idsList = new ArrayList<>();
for(int i = 0; i < ids.length; i++) {
idsList.add(new Long(ids[i]));
}
for(int i = 0; i < mAnnotations.size(); i++) {
Annotation annotation = mAnnotations.get(i);
if (annotation instanceof Marker && idsList.contains(annotation.getId())) {
annotations.add(annotation);
}
}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Since mAnnotations is defined using Generics List<Annotation> it can be iterated easier and safer via:

for (Annotation annotation : mAnnotations) {
...
}

for(int i = 0; i < annotations.size(); i++) {
Log.d(TAG, "tapped: " + Long.toString(annotations.get(i).getId()));
}
return annotations;
}

//
// Property methods
//
Expand Down Expand Up @@ -919,6 +939,22 @@ public boolean onSingleTapUp(MotionEvent e) {
// Cancel any animation
mNativeMapView.cancelTransitions();

// Select or deselect point annotations
PointF tapPoint = new PointF(e.getX(), e.getY());

float toleranceWidth = 60 * mScreenDensity;
float toleranceHeight = 80 * mScreenDensity;

PointF tr = new PointF(tapPoint.x + toleranceWidth / 2, tapPoint.y + 2 * toleranceHeight / 3);
PointF bl = new PointF(tapPoint.x - toleranceWidth / 2, tapPoint.y - 1 * toleranceHeight / 3);

LatLng sw = fromScreenLocation(bl);
LatLng ne = fromScreenLocation(tr);

BoundingBox bbox = new BoundingBox(ne, sw);

List<Annotation> annotations = getAnnotationsInBounds(bbox);

return true;
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,13 +3,16 @@
import android.graphics.PointF;
import android.view.Surface;

import com.mapbox.mapboxgl.annotations.Annotation;
import com.mapbox.mapboxgl.annotations.Marker;
import com.mapbox.mapboxgl.annotations.Polygon;
import com.mapbox.mapboxgl.annotations.Polyline;
import com.mapbox.mapboxgl.geometry.BoundingBox;
import com.mapbox.mapboxgl.geometry.LatLng;
import com.mapbox.mapboxgl.geometry.LatLngZoom;
import com.mapbox.mapboxgl.geometry.ProjectedMeters;

import java.util.ArrayList;
import java.util.List;

// Class that wraps the native methods for convenience
Expand Down Expand Up @@ -353,6 +356,10 @@ public void removeAnnotations(long[] ids) {
nativeRemoveAnnotations(mNativeMapViewPtr, ids);
}

public long[] getAnnotationsInBounds(BoundingBox bbox) {
return nativeGetAnnotationsInBounds(mNativeMapViewPtr, bbox);
}

public void setSprite(String symbol, int width, int height, float scale, byte[] pixels) {
nativeSetSprite(mNativeMapViewPtr, symbol, width, height, scale, pixels);
}
Expand Down Expand Up @@ -563,6 +570,8 @@ private native void nativeSetBearing(long nativeMapViewPtr, double degrees,

private native void nativeRemoveAnnotations(long nativeMapViewPtr, long[] id);

private native long[] nativeGetAnnotationsInBounds(long mNativeMapViewPtr, BoundingBox bbox);

private native void nativeSetSprite(long nativeMapViewPtr, String symbol,
int width, int height, float scale, byte[] pixels);

Expand Down
7 changes: 7 additions & 0 deletions include/mbgl/android/jni.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,13 @@ extern jfieldID latLngZoomLatitudeId;
extern jfieldID latLngZoomLongitudeId;
extern jfieldID latLngZoomZoomId;

extern jclass bboxClass;
extern jmethodID bboxConstructorId;
extern jfieldID bboxLatNorthId;
extern jfieldID bboxLatSouthId;
extern jfieldID bboxLonEastId;
extern jfieldID bboxLonWestId;

extern jclass markerClass;
extern jmethodID markerConstructorId;
extern jfieldID markerPositionId;
Expand Down