summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorIvo van Dongen <info@ivovandongen.nl>2017-09-14 21:23:07 +0300
committerIvo van Dongen <ivovandongen@users.noreply.github.com>2017-09-22 23:33:56 +0300
commit5d12503302dff168137d6f3b1444e4dc32ad44dd (patch)
tree98128bdddb287c30b2c1445eb88d44e9a97d57ab
parent15a47d116a0fc15d249b37574fcd932ce88909df (diff)
downloadqtlocation-mapboxgl-5d12503302dff168137d6f3b1444e4dc32ad44dd.tar.gz
[android] self-contained map renderer
- Isolates the GL thread in a MapRenderer class with a native peer
-rw-r--r--platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/MapView.java32
-rwxr-xr-xplatform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/NativeMapView.java137
-rw-r--r--platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/renderer/GlSurfaceViewRenderThread.java25
-rw-r--r--platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/renderer/MapRenderer.java119
-rw-r--r--platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/renderer/MapRendererRunnable.java29
-rw-r--r--platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/renderer/MapRendererScheduler.java13
-rw-r--r--platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/renderer/RenderThread.java12
-rw-r--r--platform/android/config.cmake4
-rw-r--r--platform/android/src/android_gl_thread.hpp74
-rw-r--r--platform/android/src/android_renderer_frontend.cpp92
-rw-r--r--platform/android/src/android_renderer_frontend.hpp35
-rwxr-xr-xplatform/android/src/jni.cpp4
-rw-r--r--platform/android/src/map_renderer.cpp137
-rw-r--r--platform/android/src/map_renderer.hpp95
-rw-r--r--platform/android/src/map_renderer_runnable.cpp49
-rw-r--r--platform/android/src/map_renderer_runnable.hpp50
-rwxr-xr-xplatform/android/src/native_map_view.cpp62
-rwxr-xr-xplatform/android/src/native_map_view.hpp26
18 files changed, 560 insertions, 435 deletions
diff --git a/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/MapView.java b/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/MapView.java
index 086f57abf6..6612110649 100644
--- a/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/MapView.java
+++ b/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/MapView.java
@@ -28,7 +28,7 @@ import com.mapbox.mapboxsdk.annotations.MarkerViewManager;
import com.mapbox.mapboxsdk.constants.MapboxConstants;
import com.mapbox.mapboxsdk.constants.Style;
import com.mapbox.mapboxsdk.egl.EGLConfigChooser;
-import com.mapbox.mapboxsdk.maps.renderer.GlSurfaceViewRenderThread;
+import com.mapbox.mapboxsdk.maps.renderer.MapRenderer;
import com.mapbox.mapboxsdk.maps.widgets.CompassView;
import com.mapbox.mapboxsdk.maps.widgets.MyLocationView;
import com.mapbox.mapboxsdk.maps.widgets.MyLocationViewSettings;
@@ -286,35 +286,31 @@ public class MapView extends FrameLayout {
glSurfaceView.setZOrderMediaOverlay(mapboxMapOptions.getRenderSurfaceOnTop());
glSurfaceView.setEGLContextClientVersion(2);
glSurfaceView.setEGLConfigChooser(new EGLConfigChooser());
- glSurfaceView.setRenderer(new GLSurfaceView.Renderer() {
+ MapRenderer mapRenderer = new MapRenderer(getContext(), glSurfaceView) {
@Override
public void onSurfaceCreated(GL10 gl, EGLConfig config) {
MapView.this.post(new Runnable() {
@Override
public void run() {
- initialiseMap();
- mapboxMap.onStart();
+ // Initialise only once
+ if (mapboxMap == null) {
+ initialiseMap();
+ mapboxMap.onStart();
+ }
}
});
- nativeMapView.onSurfaceCreated(gl, config);
- }
-
- @Override
- public void onSurfaceChanged(GL10 gl, int width, int height) {
- nativeMapView.onSurfaceChanged(gl, width, height);
+ super.onSurfaceCreated(gl, config);
}
+ };
- @Override
- public void onDrawFrame(GL10 gl) {
- nativeMapView.onDrawFrame(gl);
- }
- });
+ glSurfaceView.setRenderer(mapRenderer);
glSurfaceView.setRenderMode(RENDERMODE_WHEN_DIRTY);
glSurfaceView.setVisibility(View.VISIBLE);
- nativeMapView.setRenderThread(new GlSurfaceViewRenderThread(glSurfaceView));
+ nativeMapView = new NativeMapView(this, mapRenderer);
+ nativeMapView.resizeView(getMeasuredWidth(), getMeasuredHeight());
}
/**
@@ -527,9 +523,7 @@ public class MapView extends FrameLayout {
return;
}
- if (nativeMapView == null) {
- nativeMapView = new NativeMapView(this);
- } else if (mapZoomButtonController != null) {
+ if (mapZoomButtonController != null) {
mapZoomButtonController.setVisible(visibility == View.VISIBLE);
}
}
diff --git a/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/NativeMapView.java b/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/NativeMapView.java
index 240e68bf13..62fe2be0c3 100755
--- a/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/NativeMapView.java
+++ b/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/NativeMapView.java
@@ -4,7 +4,6 @@ import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.PointF;
import android.graphics.RectF;
-import android.opengl.GLSurfaceView;
import android.support.annotation.IntRange;
import android.support.annotation.NonNull;
import android.support.annotation.Nullable;
@@ -20,7 +19,8 @@ import com.mapbox.mapboxsdk.camera.CameraPosition;
import com.mapbox.mapboxsdk.geometry.LatLng;
import com.mapbox.mapboxsdk.geometry.LatLngBounds;
import com.mapbox.mapboxsdk.geometry.ProjectedMeters;
-import com.mapbox.mapboxsdk.maps.renderer.RenderThread;
+import com.mapbox.mapboxsdk.maps.renderer.MapRenderer;
+import com.mapbox.mapboxsdk.maps.renderer.MapRendererScheduler;
import com.mapbox.mapboxsdk.storage.FileSource;
import com.mapbox.mapboxsdk.style.layers.CannotAddLayerException;
import com.mapbox.mapboxsdk.style.layers.Filter;
@@ -36,13 +36,10 @@ import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
-import javax.microedition.khronos.egl.EGLConfig;
-import javax.microedition.khronos.opengles.GL10;
-
import timber.log.Timber;
// Class that wraps the native methods for convenience
-final class NativeMapView implements GLSurfaceView.Renderer {
+final class NativeMapView {
// Flag to indicating destroy was called
private boolean destroyed = false;
@@ -53,12 +50,12 @@ final class NativeMapView implements GLSurfaceView.Renderer {
// Used for callbacks
private MapView mapView;
- // Used to schedule work on the render thread
- private RenderThread renderThread;
-
//Hold a reference to prevent it from being GC'd as long as it's used on the native side
private final FileSource fileSource;
+ // Used to schedule work on the MapRenderer Thread
+ private MapRendererScheduler scheduler;
+
// Device density
private final float pixelRatio;
@@ -73,25 +70,21 @@ final class NativeMapView implements GLSurfaceView.Renderer {
// Constructors
//
- public NativeMapView(final MapView mapView) {
+ public NativeMapView(final MapView mapView, MapRenderer mapRenderer) {
+ this.scheduler = mapRenderer;
+ this.mapView = mapView;
+
Context context = mapView.getContext();
fileSource = FileSource.getInstance(context);
-
pixelRatio = context.getResources().getDisplayMetrics().density;
- this.mapView = mapView;
- String programCacheDir = context.getCacheDir().getAbsolutePath();
- nativeInitialize(this, fileSource, pixelRatio, programCacheDir);
+ nativeInitialize(this, fileSource, mapRenderer, pixelRatio);
}
//
// Methods
//
- public void setRenderThread(RenderThread renderThread) {
- this.renderThread = renderThread;
- }
-
private boolean isDestroyedOn(String callingMethod) {
if (destroyed && !TextUtils.isEmpty(callingMethod)) {
Timber.e(
@@ -113,14 +106,7 @@ final class NativeMapView implements GLSurfaceView.Renderer {
return;
}
- requestRender();
- }
-
- public void render() {
- if (isDestroyedOn("render")) {
- return;
- }
- nativeRender();
+ scheduler.requestRender();
}
public void resizeView(int width, int height) {
@@ -151,31 +137,8 @@ final class NativeMapView implements GLSurfaceView.Renderer {
+ "capping value at 65535 instead of %s", height);
height = 65535;
}
- nativeResizeView(width, height);
- }
-
- private void resizeFramebuffer(int fbWidth, int fbHeight) {
- if (isDestroyedOn("resizeFramebuffer")) {
- return;
- }
- if (fbWidth < 0) {
- throw new IllegalArgumentException("fbWidth cannot be negative.");
- }
- if (fbHeight < 0) {
- throw new IllegalArgumentException("fbHeight cannot be negative.");
- }
-
- if (fbWidth > 65535) {
- throw new IllegalArgumentException(
- "fbWidth cannot be greater than 65535.");
- }
-
- if (fbHeight > 65535) {
- throw new IllegalArgumentException(
- "fbHeight cannot be greater than 65535.");
- }
- nativeResizeFramebuffer(fbWidth, fbHeight);
+ nativeResizeView(width, height);
}
public void setStyleUrl(String url) {
@@ -873,31 +836,6 @@ final class NativeMapView implements GLSurfaceView.Renderer {
// Callbacks
//
- /**
- * Called from JNI whenever the native map
- * needs rendering.
- */
- protected void requestRender() {
- if (renderThread != null) {
- renderThread.requestRender();
- }
- }
-
- /**
- * Called from JNI when work needs to be processed on
- * the Renderer Thread.
- */
- protected void requestProcessing() {
- if (renderThread != null) {
- renderThread.queueEvent(new Runnable() {
- @Override
- public void run() {
- nativeProcess();
- }
- });
- }
- }
-
protected void onMapChanged(int rawChange) {
if (mapView != null) {
mapView.onMapChange(rawChange);
@@ -928,33 +866,13 @@ final class NativeMapView implements GLSurfaceView.Renderer {
private native void nativeInitialize(NativeMapView nativeMapView,
FileSource fileSource,
- float pixelRatio,
- String programCacheDir);
+ MapRenderer mapRenderer,
+ float pixelRatio);
private native void nativeDestroy();
- private native void nativeProcess();
-
- private native void nativeInitializeDisplay();
-
- private native void nativeTerminateDisplay();
-
- private native void nativeInitializeContext();
-
- private native void nativeTerminateContext();
-
- private native void nativeCreateSurface(Object surface);
-
- private native void nativeDestroySurface();
-
- private native void nativeUpdate();
-
- private native void nativeRender();
-
private native void nativeResizeView(int width, int height);
- private native void nativeResizeFramebuffer(int fbWidth, int fbHeight);
-
private native void nativeSetStyleUrl(String url);
private native String nativeGetStyleUrl();
@@ -1160,30 +1078,7 @@ final class NativeMapView implements GLSurfaceView.Renderer {
void addSnapshotCallback(@NonNull MapboxMap.SnapshotReadyCallback callback) {
snapshotReadyCallback = callback;
scheduleTakeSnapshot();
- renderThread.requestRender();
- }
-
- //
- // GLSurfaceView.Renderer
- //
-
- @Override
- public void onSurfaceCreated(GL10 gl, EGLConfig config) {
- Timber.i("[%s] onSurfaceCreated", Thread.currentThread().getName());
- //TODO: callback to map to re-create renderer?
+ scheduler.requestRender();
}
- @Override
- public void onSurfaceChanged(GL10 gl, int width, int height) {
- Timber.i("[%s] onSurfaceChanged %sx%s", Thread.currentThread().getName(), width, height);
- // Sets the current view port to the new size.
- gl.glViewport(0, 0, width, height);
- resizeFramebuffer(width, height);
- // resizeView(width, height); Done from MapView#onSizeChanged
- }
-
- @Override
- public void onDrawFrame(GL10 gl) {
- nativeRender();
- }
}
diff --git a/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/renderer/GlSurfaceViewRenderThread.java b/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/renderer/GlSurfaceViewRenderThread.java
deleted file mode 100644
index 4b8df51dbe..0000000000
--- a/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/renderer/GlSurfaceViewRenderThread.java
+++ /dev/null
@@ -1,25 +0,0 @@
-package com.mapbox.mapboxsdk.maps.renderer;
-
-import android.opengl.GLSurfaceView;
-
-/**
- * {@link RenderThread} implementation that schedules using the
- * {@link GLSurfaceView} thread.
- */
-public class GlSurfaceViewRenderThread implements RenderThread {
- private final GLSurfaceView surfaceView;
-
- public GlSurfaceViewRenderThread(GLSurfaceView surfaceView) {
- this.surfaceView = surfaceView;
- }
-
- @Override
- public void requestRender() {
- surfaceView.requestRender();
- }
-
- @Override
- public void queueEvent(Runnable runnable) {
- surfaceView.queueEvent(runnable);
- }
-}
diff --git a/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/renderer/MapRenderer.java b/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/renderer/MapRenderer.java
new file mode 100644
index 0000000000..772ecb79fb
--- /dev/null
+++ b/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/renderer/MapRenderer.java
@@ -0,0 +1,119 @@
+package com.mapbox.mapboxsdk.maps.renderer;
+
+import android.content.Context;
+import android.opengl.GLSurfaceView;
+
+import com.mapbox.mapboxsdk.storage.FileSource;
+
+import javax.microedition.khronos.egl.EGLConfig;
+import javax.microedition.khronos.opengles.GL10;
+
+/**
+ * The {@link MapRenderer} encapsulates the GL thread.
+ * <p>
+ * Performs actions on the GL thread to manage the GL resources and
+ * render on the one end and acts as a scheduler to request work to
+ * be performed on the GL thread on the other.
+ */
+public class MapRenderer implements GLSurfaceView.Renderer, MapRendererScheduler {
+
+ // Holds the pointer to the native peer after initialisation
+ private long nativePtr = 0;
+
+ private final GLSurfaceView glSurfaceView;
+
+ public MapRenderer(Context context, GLSurfaceView glSurfaceView) {
+ this.glSurfaceView = glSurfaceView;
+
+ FileSource fileSource = FileSource.getInstance(context);
+ float pixelRatio = context.getResources().getDisplayMetrics().density;
+ String programCacheDir = context.getCacheDir().getAbsolutePath();
+
+ // Initialise native peer
+ nativeInitialize(this, fileSource, pixelRatio, programCacheDir);
+ }
+
+ @Override
+ public void onSurfaceCreated(GL10 gl, EGLConfig config) {
+ nativeOnSurfaceCreated();
+ }
+
+ @Override
+ public void onSurfaceChanged(GL10 gl, int width, int height) {
+ if (width < 0) {
+ throw new IllegalArgumentException("fbWidth cannot be negative.");
+ }
+
+ if (height < 0) {
+ throw new IllegalArgumentException("fbHeight cannot be negative.");
+ }
+
+ if (width > 65535) {
+ throw new IllegalArgumentException(
+ "fbWidth cannot be greater than 65535.");
+ }
+
+ if (height > 65535) {
+ throw new IllegalArgumentException(
+ "fbHeight cannot be greater than 65535.");
+ }
+
+ gl.glViewport(0, 0, width, height);
+ nativeOnSurfaceChanged(width, height);
+ }
+
+ @Override
+ public void onDrawFrame(GL10 gl) {
+ nativeRender();
+ }
+
+ /**
+ * May be called from any thread.
+ * <p>
+ * Called from the renderer frontend to schedule a render.
+ */
+ @Override
+ public void requestRender() {
+ glSurfaceView.requestRender();
+ }
+
+ /**
+ * May be called from any thread.
+ * <p>
+ * Schedules work to be performed on the MapRenderer thread.
+ *
+ * @param runnable the runnable to execute
+ */
+ @Override
+ public void queueEvent(Runnable runnable) {
+ glSurfaceView.queueEvent(runnable);
+ }
+
+ /**
+ * May be called from any thread.
+ * <p>
+ * Called from the native peer to schedule work on the GL
+ * thread. Explicit override for easier to read jni code.
+ *
+ * @param runnable the runnable to execute
+ * @see MapRendererRunnable
+ */
+ void queueEvent(MapRendererRunnable runnable) {
+ this.queueEvent((Runnable) runnable);
+ }
+
+ private native void nativeInitialize(MapRenderer self,
+ FileSource fileSource,
+ float pixelRatio,
+ String programCacheDir);
+
+ @Override
+ protected native void finalize() throws Throwable;
+
+ private native void nativeOnSurfaceCreated();
+
+ private native void nativeOnSurfaceChanged(int width, int height);
+
+ private native void nativeRender();
+
+}
diff --git a/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/renderer/MapRendererRunnable.java b/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/renderer/MapRendererRunnable.java
new file mode 100644
index 0000000000..28246fe578
--- /dev/null
+++ b/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/renderer/MapRendererRunnable.java
@@ -0,0 +1,29 @@
+package com.mapbox.mapboxsdk.maps.renderer;
+
+/**
+ * Peer class for {@link Runnable}s to be scheduled on the {@link MapRenderer} thread.
+ * The actual work is performed in the native peer.
+ */
+class MapRendererRunnable implements Runnable {
+
+ // Holds the pointer to the native peer after initialisation
+ private final long nativePtr;
+
+ /**
+ * Constructed from the native peer constructor
+ *
+ * @param nativePtr the native peer's memory address
+ */
+ MapRendererRunnable(long nativePtr) {
+ this.nativePtr = nativePtr;
+ }
+
+ @Override
+ public native void run();
+
+ @Override
+ protected native void finalize() throws Throwable;
+
+ private native void nativeInitialize();
+
+}
diff --git a/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/renderer/MapRendererScheduler.java b/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/renderer/MapRendererScheduler.java
new file mode 100644
index 0000000000..7ad4f124d8
--- /dev/null
+++ b/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/renderer/MapRendererScheduler.java
@@ -0,0 +1,13 @@
+package com.mapbox.mapboxsdk.maps.renderer;
+
+/**
+ * Can be used to schedule work on the map renderer
+ * thread or request a render.
+ */
+public interface MapRendererScheduler {
+
+ void requestRender();
+
+ void queueEvent(Runnable runnable);
+
+}
diff --git a/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/renderer/RenderThread.java b/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/renderer/RenderThread.java
deleted file mode 100644
index 3b9f0f2151..0000000000
--- a/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/renderer/RenderThread.java
+++ /dev/null
@@ -1,12 +0,0 @@
-package com.mapbox.mapboxsdk.maps.renderer;
-
-/**
- * Created by ivo on 11/09/2017.
- */
-
-public interface RenderThread {
-
- void requestRender();
-
- void queueEvent(Runnable runnable);
-}
diff --git a/platform/android/config.cmake b/platform/android/config.cmake
index 539515a6e5..227334e0b5 100644
--- a/platform/android/config.cmake
+++ b/platform/android/config.cmake
@@ -205,6 +205,10 @@ add_library(mbgl-android STATIC
# Native map
platform/android/src/native_map_view.cpp
platform/android/src/native_map_view.hpp
+ platform/android/src/map_renderer.cpp
+ platform/android/src/map_renderer.hpp
+ platform/android/src/map_renderer_runnable.cpp
+ platform/android/src/map_renderer_runnable.hpp
# Java core classes
platform/android/src/java/util.cpp
diff --git a/platform/android/src/android_gl_thread.hpp b/platform/android/src/android_gl_thread.hpp
deleted file mode 100644
index 78777aa475..0000000000
--- a/platform/android/src/android_gl_thread.hpp
+++ /dev/null
@@ -1,74 +0,0 @@
-#pragma once
-
-#include <mbgl/actor/actor.hpp>
-#include <mbgl/actor/mailbox.hpp>
-#include <mbgl/actor/scheduler.hpp>
-#include <mbgl/renderer/renderer.hpp>
-
-#include <functional>
-#include <memory>
-#include <mutex>
-#include <queue>
-#include <utility>
-
-namespace mbgl {
-namespace android {
-
-class AndroidGLThread : public Scheduler {
-public:
- using InvalidateCallback = std::function<void ()>;
-
- template <class... Args>
- AndroidGLThread(InvalidateCallback callback_, Args&&... args)
- : renderer(std::make_unique<Renderer>(std::forward<Args>(args)...))
- , mailbox(std::make_shared<Mailbox>(*this))
- , callback(callback_)
- , rendererRef(*renderer, mailbox) {
- }
-
- ~AndroidGLThread() override = default;
-
- ActorRef<Renderer> actor() const {
- return rendererRef;
- }
-
- void schedule(std::weak_ptr<Mailbox> scheduled) override {
- {
- std::lock_guard<std::mutex> lock(mutex);
- queue.push(scheduled);
- }
-
- // Invalidate so we get processing time later
- callback();
- }
-
- // Only safe on the GL Thread
- void process() {
- std::unique_lock<std::mutex> lock(mutex);
-
- if (queue.empty()) {
- return;
- }
-
- auto scheduled = queue.front();
- queue.pop();
-
- lock.unlock();
-
- Mailbox::maybeReceive(scheduled);
- }
-
- // Only safe to access on the GL Thread
- std::unique_ptr<Renderer> renderer;
-
-private:
- std::mutex mutex;
- std::queue<std::weak_ptr<Mailbox>> queue;
-
- std::shared_ptr<Mailbox> mailbox;
- InvalidateCallback callback;
- ActorRef<Renderer> rendererRef;
-};
-
-} // namespace android
-} // namespace mbgl
diff --git a/platform/android/src/android_renderer_frontend.cpp b/platform/android/src/android_renderer_frontend.cpp
index 0619ba4cb5..38b1ff252b 100644
--- a/platform/android/src/android_renderer_frontend.cpp
+++ b/platform/android/src/android_renderer_frontend.cpp
@@ -54,124 +54,62 @@ private:
ActorRef<RendererObserver> delegate;
};
-AndroidRendererFrontend::AndroidRendererFrontend(float pixelRatio,
- FileSource& fileSource,
- Scheduler& scheduler,
- std::string programCacheDir,
- RequestRenderCallback requestRender,
- RequestProcessingCallback requestProcessing)
- : backend(std::make_unique<AndroidRendererBackend>())
- , glThread(std::make_unique<AndroidGLThread>(
- std::move(requestProcessing),
- *backend,
- pixelRatio,
- fileSource,
- scheduler,
- GLContextMode::Unique,
- programCacheDir
- ))
- , asyncInvalidate([requestRender=std::move(requestRender)]() {
- requestRender();
- })
+AndroidRendererFrontend::AndroidRendererFrontend(MapRenderer& mapRenderer_)
+ : mapRenderer(mapRenderer_)
, mapRunLoop(util::RunLoop::Get()) {
}
AndroidRendererFrontend::~AndroidRendererFrontend() = default;
void AndroidRendererFrontend::reset() {
- assert(glThread);
- glThread.reset();
+ mapRenderer.reset();
+ rendererObserver.reset();
}
void AndroidRendererFrontend::setObserver(RendererObserver& observer) {
- assert (glThread);
assert (util::RunLoop::Get());
rendererObserver = std::make_unique<ForwardingRendererObserver>(*mapRunLoop, observer);
- glThread->actor().invoke(&Renderer::setObserver, rendererObserver.get());
+ mapRenderer.actor().invoke(&Renderer::setObserver, rendererObserver.get());
}
void AndroidRendererFrontend::update(std::shared_ptr<UpdateParameters> params) {
- {
- // Lock on the parameters
- std::lock_guard<std::mutex> lock(updateMutex);
- updateParameters = std::move(params);
- }
- asyncInvalidate.send();
-}
-
-// Called on OpenGL thread
-void AndroidRendererFrontend::render() {
- assert (glThread);
-
- std::shared_ptr<UpdateParameters> params;
- {
- // Lock on the parameters
- std::unique_lock<std::mutex> lock(updateMutex);
- if (!updateParameters) return;
-
- // Hold on to the update parameters during render
- params = updateParameters;
- }
-
- // Activate the backend
- BackendScope backendGuard { *backend };
-
- // Ensure that the "current" scheduler on the render thread is
- // actually the scheduler from the orchestration thread
- Scheduler::SetCurrent(glThread.get());
-
- if (framebufferSizeChanged) {
- backend->updateViewPort();
- framebufferSizeChanged = false;
- }
-
- glThread->renderer->render(*params);
-}
-
-void AndroidRendererFrontend::process() {
- // Process the gl thread mailbox
- glThread->process();
+ mapRenderer.update(std::move(params));
+ mapRenderer.requestRender();
}
void AndroidRendererFrontend::onLowMemory() {
- assert (glThread);
- glThread->actor().invoke(&Renderer::onLowMemory);
+ mapRenderer.actor().invoke(&Renderer::onLowMemory);
}
std::vector<Feature> AndroidRendererFrontend::querySourceFeatures(const std::string& sourceID,
const SourceQueryOptions& options) const {
- assert (glThread);
// Waits for the result from the orchestration thread and returns
- return glThread->actor().ask(&Renderer::querySourceFeatures, sourceID, options).get();
+ return mapRenderer.actor().ask(&Renderer::querySourceFeatures, sourceID, options).get();
}
std::vector<Feature> AndroidRendererFrontend::queryRenderedFeatures(const ScreenBox& box,
const RenderedQueryOptions& options) const {
- assert (glThread);
// Select the right overloaded method
std::vector<Feature> (Renderer::*fn)(const ScreenBox&, const RenderedQueryOptions&) const = &Renderer::queryRenderedFeatures;
// Waits for the result from the orchestration thread and returns
- return glThread->actor().ask(fn, box, options).get();
+ return mapRenderer.actor().ask(fn, box, options).get();
}
std::vector<Feature> AndroidRendererFrontend::queryRenderedFeatures(const ScreenCoordinate& point,
const RenderedQueryOptions& options) const {
- assert (glThread);
// Select the right overloaded method
std::vector<Feature> (Renderer::*fn)(const ScreenCoordinate&, const RenderedQueryOptions&) const = &Renderer::queryRenderedFeatures;
// Waits for the result from the orchestration thread and returns
- return glThread->actor().ask(fn, point, options).get();
+ return mapRenderer.actor().ask(fn, point, options).get();
}
AnnotationIDs AndroidRendererFrontend::queryPointAnnotations(const ScreenBox& box) const {
- assert (glThread);
-
// Waits for the result from the orchestration thread and returns
- return glThread->actor().ask(&Renderer::queryPointAnnotations, box).get();
+ return mapRenderer.actor().ask(&Renderer::queryPointAnnotations, box).get();
}
void AndroidRendererFrontend::requestSnapshot(SnapshotCallback callback_) {
@@ -182,12 +120,6 @@ void AndroidRendererFrontend::requestSnapshot(SnapshotCallback callback_) {
});
}
-void AndroidRendererFrontend::resizeFramebuffer(int width, int height) {
- backend->resizeFramebuffer(width, height);
- framebufferSizeChanged = true;
- asyncInvalidate.send();
-}
-
} // namespace android
} // namespace mbgl
diff --git a/platform/android/src/android_renderer_frontend.hpp b/platform/android/src/android_renderer_frontend.hpp
index 57bfd62b26..598327838e 100644
--- a/platform/android/src/android_renderer_frontend.hpp
+++ b/platform/android/src/android_renderer_frontend.hpp
@@ -1,13 +1,9 @@
-
#pragma once
-#include "android_gl_thread.hpp"
-
#include <mbgl/actor/actor.hpp>
#include <mbgl/annotation/annotation.hpp>
#include <mbgl/renderer/renderer_backend.hpp>
#include <mbgl/renderer/renderer_frontend.hpp>
-#include <mbgl/util/async_task.hpp>
#include <mbgl/util/geo.hpp>
#include <mbgl/util/image.hpp>
#include <mbgl/util/run_loop.hpp>
@@ -17,6 +13,8 @@
#include <vector>
#include <string>
+#include "map_renderer.hpp"
+
namespace mbgl {
class FileSource;
@@ -30,15 +28,8 @@ class AndroidRendererBackend;
class AndroidRendererFrontend : public RendererFrontend {
public:
- using RequestRenderCallback = std::function<void ()>;
- using RequestProcessingCallback = std::function<void ()>;
-
- AndroidRendererFrontend(float pixelRatio,
- mbgl::FileSource&,
- mbgl::Scheduler&,
- std::string programCacheDir,
- RequestRenderCallback,
- RequestProcessingCallback);
+
+ AndroidRendererFrontend(MapRenderer&);
~AndroidRendererFrontend() override;
void reset() override;
@@ -46,19 +37,12 @@ public:
void update(std::shared_ptr<UpdateParameters>) override;
- // Called from OpenGL Thread
- void render();
- void process();
-
// Feature querying
std::vector<Feature> queryRenderedFeatures(const ScreenCoordinate&, const RenderedQueryOptions&) const;
std::vector<Feature> queryRenderedFeatures(const ScreenBox&, const RenderedQueryOptions&) const;
std::vector<Feature> querySourceFeatures(const std::string& sourceID, const SourceQueryOptions&) const;
AnnotationIDs queryPointAnnotations(const ScreenBox& box) const;
- // RenderBackend proxy - Called from OpenGL Thread
- void resizeFramebuffer(int width, int height);
-
// Memory
void onLowMemory();
@@ -67,19 +51,12 @@ public:
void requestSnapshot(SnapshotCallback);
private:
- std::unique_ptr<AndroidRendererBackend> backend;
- std::unique_ptr<AndroidGLThread> glThread;
std::unique_ptr<RendererObserver> rendererObserver;
-
- std::mutex updateMutex;
- std::shared_ptr<UpdateParameters> updateParameters;
-
-
- util::AsyncTask asyncInvalidate;
+ MapRenderer& mapRenderer;
util::RunLoop* mapRunLoop;
- bool framebufferSizeChanged = true;
+ // TODO
std::unique_ptr<SnapshotCallback> snapshotCallback;
};
diff --git a/platform/android/src/jni.cpp b/platform/android/src/jni.cpp
index f7d1e4afbc..6acb6a3664 100755
--- a/platform/android/src/jni.cpp
+++ b/platform/android/src/jni.cpp
@@ -32,6 +32,8 @@
#include "gson/json_object.hpp"
#include "gson/json_primitive.hpp"
#include "java_types.hpp"
+#include "map_renderer.hpp"
+#include "map_renderer_runnable.hpp"
#include "native_map_view.hpp"
#include "offline/offline_manager.hpp"
#include "offline/offline_region.hpp"
@@ -144,6 +146,8 @@ void registerNatives(JavaVM *vm) {
Polyline::registerNative(env);
// Map
+ MapRenderer::registerNative(env);
+ MapRendererRunnable::registerNative(env);
NativeMapView::registerNative(env);
// Http
diff --git a/platform/android/src/map_renderer.cpp b/platform/android/src/map_renderer.cpp
new file mode 100644
index 0000000000..8346d2f139
--- /dev/null
+++ b/platform/android/src/map_renderer.cpp
@@ -0,0 +1,137 @@
+#include "map_renderer.hpp"
+
+#include <mbgl/renderer/renderer.hpp>
+#include <mbgl/util/shared_thread_pool.hpp>
+
+#include <string>
+
+#include "attach_env.hpp"
+#include "android_renderer_backend.hpp"
+#include "map_renderer_runnable.hpp"
+#include "file_source.hpp"
+
+namespace mbgl {
+namespace android {
+
+MapRenderer::MapRenderer(jni::JNIEnv& _env,
+ jni::Object<MapRenderer> obj,
+ jni::Object<FileSource> fileSource,
+ jni::jfloat pixelRatio,
+ jni::String programCacheDir)
+ : javaPeer(SeizeGenericWeakRef(_env, jni::Object<MapRenderer>(jni::NewWeakGlobalRef(_env, obj.Get()).release())))
+ , threadPool(sharedThreadPool())
+ , backend(std::make_unique<AndroidRendererBackend>())
+ , renderer(std::make_unique<Renderer>(*backend, pixelRatio, FileSource::getDefaultFileSource(_env, fileSource),
+ *threadPool, GLContextMode::Unique, jni::Make<std::string>(_env, programCacheDir)))
+ , mailbox(std::make_shared<Mailbox>(*this))
+ , rendererRef(*renderer, mailbox) {
+}
+
+MapRenderer::~MapRenderer() = default;
+
+void MapRenderer::reset() {
+ assert (renderer);
+ renderer.reset();
+}
+
+ActorRef<Renderer> MapRenderer::actor() const {
+ return rendererRef;
+}
+
+void MapRenderer::schedule(std::weak_ptr<Mailbox> scheduled) {
+ // Create a runnable and schedule it on the gl thread
+ android::UniqueEnv _env = android::AttachEnv();
+ auto runnable = std::make_unique<MapRendererRunnable>(*_env, std::move(scheduled));
+
+ static auto queueEvent = javaClass.GetMethod<void (jni::Object<MapRendererRunnable>)>(*_env, "queueEvent");
+ javaPeer->Call(*_env, queueEvent, runnable->getPeer());
+
+ // Release the object as it will be destroyed on GC of the Java Peer
+ runnable.release();
+}
+
+void MapRenderer::requestRender() {
+ android::UniqueEnv _env = android::AttachEnv();
+ static auto onInvalidate = javaClass.GetMethod<void ()>(*_env, "requestRender");
+ javaPeer->Call(*_env, onInvalidate);
+}
+
+void MapRenderer::update(std::shared_ptr<UpdateParameters> params) {
+ // Lock on the parameters
+ std::lock_guard<std::mutex> lock(updateMutex);
+ updateParameters = std::move(params);
+}
+
+// Called on OpenGL thread //
+
+void MapRenderer::render(JNIEnv&) {
+ assert (renderer);
+
+ std::shared_ptr<UpdateParameters> params;
+ {
+ // Lock on the parameters
+ std::unique_lock<std::mutex> lock(updateMutex);
+ if (!updateParameters) return;
+
+ // Hold on to the update parameters during render
+ params = updateParameters;
+ }
+
+ // Activate the backend
+ BackendScope backendGuard { *backend };
+
+ // Ensure that the "current" scheduler on the render thread is
+ // this scheduler.
+ Scheduler::SetCurrent(this);
+
+ if (framebufferSizeChanged) {
+ backend->updateViewPort();
+ framebufferSizeChanged = false;
+ }
+
+ renderer->render(*params);
+}
+
+void MapRenderer::onSurfaceCreated(JNIEnv&) {
+ // TODO (re-)create Context, Backend and Renderer
+}
+
+void MapRenderer::onSurfaceChanged(JNIEnv&, jint width, jint height) {
+ backend->resizeFramebuffer(width, height);
+ framebufferSizeChanged = true;
+ requestRender();
+}
+
+// Static methods //
+
+jni::Class<MapRenderer> MapRenderer::javaClass;
+
+void MapRenderer::registerNative(jni::JNIEnv& env) {
+ // Lookup the class
+ MapRenderer::javaClass = *jni::Class<MapRenderer>::Find(env).NewGlobalRef(env).release();
+
+#define METHOD(MethodPtr, name) jni::MakeNativePeerMethod<decltype(MethodPtr), (MethodPtr)>(name)
+
+ // Register the peer
+ jni::RegisterNativePeer<MapRenderer>(
+ env,
+ MapRenderer::javaClass,
+ "nativePtr",
+ std::make_unique<MapRenderer, JNIEnv&, jni::Object<MapRenderer>, jni::Object<FileSource>, jni::jfloat, jni::String>,
+ "nativeInitialize",
+ "finalize",
+ METHOD(&MapRenderer::render, "nativeRender"),
+ METHOD(&MapRenderer::onSurfaceCreated, "nativeOnSurfaceCreated"),
+ METHOD(&MapRenderer::onSurfaceChanged, "nativeOnSurfaceChanged")
+ );
+}
+
+MapRenderer& MapRenderer::getNativePeer(JNIEnv& env, jni::Object<MapRenderer> jObject) {
+ static auto field = MapRenderer::javaClass.GetField<jlong>(env, "nativePtr");
+ MapRenderer* mapRenderer = reinterpret_cast<MapRenderer *>(jObject.Get(env, field));
+ assert(mapRenderer != nullptr);
+ return *mapRenderer;
+}
+
+} // namespace android
+} // namespace mbgl
diff --git a/platform/android/src/map_renderer.hpp b/platform/android/src/map_renderer.hpp
new file mode 100644
index 0000000000..51fca48ee6
--- /dev/null
+++ b/platform/android/src/map_renderer.hpp
@@ -0,0 +1,95 @@
+#pragma once
+
+#include <mbgl/actor/actor_ref.hpp>
+#include <mbgl/actor/mailbox.hpp>
+#include <mbgl/actor/scheduler.hpp>
+#include <mbgl/renderer/renderer.hpp>
+
+#include <memory>
+#include <utility>
+
+#include <jni/jni.hpp>
+
+#include "jni/generic_global_ref_deleter.hpp"
+
+namespace mbgl {
+
+class Renderer;
+class RendererBackend;
+class ThreadPool;
+class UpdateParameters;
+
+namespace android {
+
+class AndroidRendererBackend;
+class FileSource;
+
+/**
+ * The MapRenderer is a peer class that encapsulates the actions
+ * performed on the GL Thread.
+ *
+ * The public methods are safe to call from the main thread, others are not.
+ */
+class MapRenderer : public Scheduler {
+public:
+
+ static constexpr auto Name() { return "com/mapbox/mapboxsdk/maps/renderer/MapRenderer"; };
+
+ static jni::Class<MapRenderer> javaClass;
+
+ static void registerNative(jni::JNIEnv&);
+
+ static MapRenderer& getNativePeer(JNIEnv&, jni::Object<MapRenderer>);
+
+ MapRenderer(jni::JNIEnv& _env,
+ jni::Object<MapRenderer>,
+ jni::Object<FileSource>,
+ jni::jfloat pixelRatio,
+ jni::String programCacheDir);
+
+ ~MapRenderer() override;
+
+ // Resets the renderer to clean up on the calling thread
+ void reset();
+
+ // Sets the new update parameters to use on subsequent
+ // renders. Be sure to trigger a render with
+ // requestRender().
+ void update(std::shared_ptr<UpdateParameters>);
+
+ // Gives a handle to the Renderer to enable actions on
+ // any thread.
+ ActorRef<Renderer> actor() const;
+
+ // From Scheduler. Schedules by using callbacks to the
+ // JVM to process the mailbox on the right thread.
+ void schedule(std::weak_ptr<Mailbox> scheduled) override;
+
+ void requestRender();
+
+private:
+ // Called from the GL Thread //
+
+ // Renders a frame.
+ void render(JNIEnv&);
+
+ void onSurfaceCreated(JNIEnv&);
+
+ void onSurfaceChanged(JNIEnv&, jint width, jint height);
+
+private:
+ GenericUniqueWeakObject<MapRenderer> javaPeer;
+ std::shared_ptr<ThreadPool> threadPool;
+ std::unique_ptr<AndroidRendererBackend> backend;
+ std::unique_ptr<Renderer> renderer;
+ std::shared_ptr<Mailbox> mailbox;
+ ActorRef<Renderer> rendererRef;
+
+ std::shared_ptr<UpdateParameters> updateParameters;
+ std::mutex updateMutex;
+
+ bool framebufferSizeChanged = false;
+};
+
+} // namespace android
+} // namespace mbgl
diff --git a/platform/android/src/map_renderer_runnable.cpp b/platform/android/src/map_renderer_runnable.cpp
new file mode 100644
index 0000000000..df8cba5e55
--- /dev/null
+++ b/platform/android/src/map_renderer_runnable.cpp
@@ -0,0 +1,49 @@
+#include "map_renderer_runnable.hpp"
+
+#include <mbgl/util/logging.hpp>
+
+namespace mbgl {
+namespace android {
+
+MapRendererRunnable::MapRendererRunnable(jni::JNIEnv& env, std::weak_ptr<Mailbox> mailbox_)
+ : mailbox(std::move(mailbox_)) {
+
+ // Create the Java peer
+ jni::UniqueLocalFrame frame = jni::PushLocalFrame(env, 5);
+ static auto constructor = javaClass.GetConstructor<jlong>(env);
+ auto instance = javaClass.New(env, constructor, reinterpret_cast<jlong>(this));
+ javaPeer = SeizeGenericWeakRef(env, jni::Object<MapRendererRunnable>(jni::NewWeakGlobalRef(env, instance.Get()).release()));
+}
+
+MapRendererRunnable::~MapRendererRunnable() = default;
+
+void MapRendererRunnable::run(jni::JNIEnv&) {
+ Mailbox::maybeReceive(mailbox);
+}
+
+jni::Object<MapRendererRunnable> MapRendererRunnable::getPeer() {
+ return *javaPeer;
+}
+
+// Static methods //
+
+jni::Class<MapRendererRunnable> MapRendererRunnable::javaClass;
+
+void MapRendererRunnable::registerNative(jni::JNIEnv& env) {
+ // Lookup the class
+ MapRendererRunnable::javaClass = *jni::Class<MapRendererRunnable>::Find(env).NewGlobalRef(env).release();
+
+#define METHOD(MethodPtr, name) jni::MakeNativePeerMethod<decltype(MethodPtr), (MethodPtr)>(name)
+
+ jni::RegisterNativePeer<MapRendererRunnable>(
+ env,
+ MapRendererRunnable::javaClass,
+ "nativePtr",
+ std::make_unique<MapRendererRunnable, JNIEnv&>,
+ "nativeInitialize",
+ "finalize",
+ METHOD(&MapRendererRunnable::run, "run"));
+}
+
+} // namespace android
+} // namespace mbgl
diff --git a/platform/android/src/map_renderer_runnable.hpp b/platform/android/src/map_renderer_runnable.hpp
new file mode 100644
index 0000000000..75646a442d
--- /dev/null
+++ b/platform/android/src/map_renderer_runnable.hpp
@@ -0,0 +1,50 @@
+#pragma once
+
+#include <mbgl/actor/mailbox.hpp>
+#include <mbgl/actor/scheduler.hpp>
+
+#include <memory>
+#include <utility>
+
+#include <jni/jni.hpp>
+
+#include "jni/generic_global_ref_deleter.hpp"
+
+namespace mbgl {
+namespace android {
+
+/**
+ * The MapRendererRunnable is a peer class that encapsulates
+ * a scheduled mailbox in a Java Runnable so it can be
+ * scheduled on the map renderer thread.
+ *
+ */
+class MapRendererRunnable {
+public:
+
+ static constexpr auto Name() { return "com/mapbox/mapboxsdk/maps/renderer/MapRendererRunnable"; };
+
+ static jni::Class<MapRendererRunnable> javaClass;
+
+ static void registerNative(jni::JNIEnv&);
+
+ MapRendererRunnable(jni::JNIEnv&, std::weak_ptr<Mailbox>);
+
+ // Only for jni registration, unused
+ MapRendererRunnable(jni::JNIEnv&) {
+ assert(false);
+ }
+
+ ~MapRendererRunnable();
+
+ void run(jni::JNIEnv&);
+
+ jni::Object<MapRendererRunnable> getPeer();
+
+private:
+ GenericUniqueWeakObject<MapRendererRunnable> javaPeer;
+ std::weak_ptr<Mailbox> mailbox;
+};
+
+} // namespace android
+} // namespace mbgl
diff --git a/platform/android/src/native_map_view.cpp b/platform/android/src/native_map_view.cpp
index 51edd8079f..f7f487f227 100755
--- a/platform/android/src/native_map_view.cpp
+++ b/platform/android/src/native_map_view.cpp
@@ -9,12 +9,10 @@
#include <sys/system_properties.h>
-#include <EGL/egl.h>
#include <android/native_window_jni.h>
#include <jni/jni.hpp>
-#include <mbgl/renderer/backend_scope.hpp>
#include <mbgl/math/minmax.hpp>
#include <mbgl/util/constants.hpp>
#include <mbgl/util/event.hpp>
@@ -28,7 +26,6 @@
#include <mbgl/style/style.hpp>
#include <mbgl/style/image.hpp>
#include <mbgl/style/filter.hpp>
-#include <mbgl/renderer/renderer.hpp>
// Java -> C++ conversion
#include "style/android_conversion.hpp"
@@ -43,8 +40,9 @@
#include "jni.hpp"
#include "attach_env.hpp"
-#include "android_renderer_backend.hpp"
+#include "map_renderer.hpp"
#include "android_renderer_frontend.hpp"
+#include "file_source.hpp"
#include "bitmap.hpp"
#include "run_loop_impl.hpp"
#include "java/util.hpp"
@@ -59,8 +57,8 @@ namespace android {
NativeMapView::NativeMapView(jni::JNIEnv& _env,
jni::Object<NativeMapView> _obj,
jni::Object<FileSource> jFileSource,
- jni::jfloat _pixelRatio,
- jni::String _programCacheDir)
+ jni::Object<MapRenderer> jMapRenderer,
+ jni::jfloat _pixelRatio)
: javaPeer(_obj.NewWeakGlobalRef(_env)),
pixelRatio(_pixelRatio),
threadPool(sharedThreadPool()) {
@@ -71,15 +69,12 @@ NativeMapView::NativeMapView(jni::JNIEnv& _env,
return;
}
+ // Get native peers
mbgl::FileSource& fileSource = mbgl::android::FileSource::getDefaultFileSource(_env, jFileSource);
+ MapRenderer& mapRenderer = MapRenderer::getNativePeer(_env, jMapRenderer);
// Create a renderer frontend
- rendererFrontend = std::make_unique<AndroidRendererFrontend>(pixelRatio, fileSource,
- *threadPool,
- jni::Make<std::string>(_env,
- _programCacheDir),
- [this] { this->requestRender(); },
- [this] { this->requestProcessing(); });
+ rendererFrontend = std::make_unique<AndroidRendererFrontend>(mapRenderer);
// Create the core map
map = std::make_unique<mbgl::Map>(*rendererFrontend, *this,
@@ -98,24 +93,6 @@ NativeMapView::~NativeMapView() {
}
/**
- * Callback to java NativeMapView#requestRender().
- *
- * Called to schedule a render on the next
- * runloop iteration.
- */
-void NativeMapView::requestRender() {
- android::UniqueEnv _env = android::AttachEnv();
- static auto onInvalidate = javaClass.GetMethod<void ()>(*_env, "requestRender");
- javaPeer->Call(*_env, onInvalidate);
-}
-
-void NativeMapView::requestProcessing() {
- android::UniqueEnv _env = android::AttachEnv();
- static auto requestProcessing = javaClass.GetMethod<void ()>(*_env, "requestProcessing");
- javaPeer->Call(*_env, requestProcessing);
-}
-
-/**
* From mbgl::RendererBackend. Callback to java NativeMapView#onMapChanged(int).
*
* May be called from any thread
@@ -194,31 +171,12 @@ void NativeMapView::onSourceChanged(mbgl::style::Source&) {
// JNI Methods //
-// Called from the OpenGL renderer thread
-void NativeMapView::render(jni::JNIEnv& ) {
- rendererFrontend->render();
-
- // TODO
- updateFps();
-}
-
-// Called from the OpenGL renderer thread
-void NativeMapView::process(jni::JNIEnv&) {
- rendererFrontend->process();
-}
-
void NativeMapView::resizeView(jni::JNIEnv&, int w, int h) {
width = util::max(64, w);
height = util::max(64, h);
map->setSize({ static_cast<uint32_t>(width), static_cast<uint32_t>(height) });
}
-void NativeMapView::resizeFramebuffer(jni::JNIEnv&, int w, int h) {
- rendererFrontend->resizeFramebuffer(w, h);
-// framebufferSizeChanged = true;
-// invalidate();
-}
-
jni::String NativeMapView::getStyleUrl(jni::JNIEnv& env) {
return jni::Make<jni::String>(env, map->getStyle().getURL());
}
@@ -969,6 +927,7 @@ jni::jboolean NativeMapView::getPrefetchesTiles(JNIEnv&) {
// Private methods //
+// TODO
void NativeMapView::updateFps() {
if (!fpsEnabled) {
return;
@@ -1008,13 +967,10 @@ void NativeMapView::registerNative(jni::JNIEnv& env) {
// Register the peer
jni::RegisterNativePeer<NativeMapView>(env, NativeMapView::javaClass, "nativePtr",
- std::make_unique<NativeMapView, JNIEnv&, jni::Object<NativeMapView>, jni::Object<FileSource>, jni::jfloat, jni::String>,
+ std::make_unique<NativeMapView, JNIEnv&, jni::Object<NativeMapView>, jni::Object<FileSource>, jni::Object<MapRenderer>, jni::jfloat>,
"nativeInitialize",
"nativeDestroy",
- METHOD(&NativeMapView::render, "nativeRender"),
- METHOD(&NativeMapView::process, "nativeProcess"),
METHOD(&NativeMapView::resizeView, "nativeResizeView"),
- METHOD(&NativeMapView::resizeFramebuffer, "nativeResizeFramebuffer"),
METHOD(&NativeMapView::getStyleUrl, "nativeGetStyleUrl"),
METHOD(&NativeMapView::setStyleUrl, "nativeSetStyleUrl"),
METHOD(&NativeMapView::getStyleJson, "nativeGetStyleJson"),
diff --git a/platform/android/src/native_map_view.hpp b/platform/android/src/native_map_view.hpp
index 7376f82c24..d88647914e 100755
--- a/platform/android/src/native_map_view.hpp
+++ b/platform/android/src/native_map_view.hpp
@@ -1,6 +1,5 @@
#pragma once
-#include <mbgl/renderer/renderer_backend.hpp>
#include <mbgl/map/change.hpp>
#include <mbgl/map/camera.hpp>
#include <mbgl/map/map.hpp>
@@ -10,7 +9,6 @@
#include <mbgl/storage/default_file_source.hpp>
#include <mbgl/storage/network_status.hpp>
-#include "file_source.hpp"
#include "annotation/marker.hpp"
#include "annotation/polygon.hpp"
#include "annotation/polyline.hpp"
@@ -37,6 +35,8 @@ namespace mbgl {
namespace android {
class AndroidRendererFrontend;
+class FileSource;
+class MapRenderer;
class NativeMapView : public MapObserver {
public:
@@ -50,8 +50,8 @@ public:
NativeMapView(jni::JNIEnv&,
jni::Object<NativeMapView>,
jni::Object<FileSource>,
- jni::jfloat pixelRatio,
- jni::String programCacheDir);
+ jni::Object<MapRenderer>,
+ jni::jfloat pixelRatio);
virtual ~NativeMapView();
@@ -72,28 +72,10 @@ public:
void onDidFinishLoadingStyle() override;
void onSourceChanged(mbgl::style::Source&) override;
- // Signal the view system, we want to redraw
- void requestRender();
-
- // Request processing on the GL Thread
- void requestProcessing();
-
// JNI //
- // Called on OpenGL Thread
- void onSurfaceCreated(jni::JNIEnv&);
-
- // Called on OpenGL Thread
- void process(jni::JNIEnv&);
-
- // Called on OpenGL Thread
- void render(jni::JNIEnv&);
-
void resizeView(jni::JNIEnv&, int, int);
- // Called on OpenGL Thread
- void resizeFramebuffer(jni::JNIEnv&, int, int);
-
jni::String getStyleUrl(jni::JNIEnv&);
void setStyleUrl(jni::JNIEnv&, jni::String);