Merge branch 'master' into armills-cast-mvp
3
.gitmodules
vendored
@ -10,9 +10,6 @@
|
||||
[submodule "extern/GmsLib"]
|
||||
path = extern/GmsLib
|
||||
url = https://github.com/microg/android_external_GmsLib.git
|
||||
[submodule "extern/vtm"]
|
||||
path = extern/vtm
|
||||
url = https://github.com/microg/android_external_vtm.git
|
||||
[submodule "extern/RemoteDroidGuard"]
|
||||
path = extern/RemoteDroidGuard
|
||||
url = https://github.com/microg/android_packages_apps_RemoteDroidGuard.git
|
||||
|
@ -10,8 +10,7 @@ android:
|
||||
components:
|
||||
- tools
|
||||
- platform-tools
|
||||
- build-tools-27.0.3
|
||||
- build-tools-28.0.3
|
||||
- android-27
|
||||
- android-28
|
||||
- extra-android-m2repository
|
||||
before_install:
|
||||
- yes | sdkmanager "platforms;android-27"
|
||||
|
@ -9,7 +9,7 @@ microG GmsCore is a FLOSS (Free/Libre Open Source Software) framework to allow a
|
||||
|
||||
License
|
||||
-------
|
||||
Copyright 2014-2016 microG Project Team
|
||||
Copyright 2013-2019 microG Project Team
|
||||
|
||||
Licensed under the Apache License, Version 2.0 (the "License");
|
||||
you may not use this file except in compliance with the License.
|
||||
|
16
build.gradle
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-2017 microG Project Team
|
||||
* Copyright 2013-2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@ -15,29 +15,31 @@
|
||||
*/
|
||||
|
||||
buildscript {
|
||||
ext.kotlin_version = '1.3.21'
|
||||
repositories {
|
||||
jcenter()
|
||||
google()
|
||||
}
|
||||
dependencies {
|
||||
classpath 'com.android.tools.build:gradle:3.1.3'
|
||||
classpath 'com.android.tools.build:gradle:3.3.2'
|
||||
classpath 'com.github.dcendents:android-maven-gradle-plugin:2.0'
|
||||
classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version"
|
||||
}
|
||||
}
|
||||
|
||||
allprojects {
|
||||
apply plugin: 'idea'
|
||||
ext.androidBuildVersionTools = "27.0.3"
|
||||
ext.supportLibraryVersion = "27.1.0"
|
||||
ext.androidBuildVersionTools = "28.0.3"
|
||||
ext.supportLibraryVersion = "28.0.0"
|
||||
ext.isReleaseVersion = false
|
||||
ext.slf4jVersion = "1.7.25"
|
||||
}
|
||||
|
||||
def androidCompileSdk() { return 27 }
|
||||
def androidCompileSdk() { return 28 }
|
||||
|
||||
def androidTargetSdk() { return 27 }
|
||||
def androidTargetSdk() { return 28 }
|
||||
|
||||
def androidMinSdk() { return 9 }
|
||||
def androidMinSdk() { return 14 }
|
||||
|
||||
def versionCode() {
|
||||
def stdout = new ByteArrayOutputStream()
|
||||
|
2
extern/GmsApi
vendored
@ -1 +1 @@
|
||||
Subproject commit feeff75ab10072c89cd17832bf53e859b946cfae
|
||||
Subproject commit 7197b8320b4e6d55d15b76d4faf05adaba36bf72
|
1
extern/vtm
vendored
@ -1 +0,0 @@
|
||||
Subproject commit a47215d9848d5f0ebd1be7e281b48e531026a47f
|
2
gradle/wrapper/gradle-wrapper.properties
vendored
@ -2,4 +2,4 @@ distributionBase=GRADLE_USER_HOME
|
||||
distributionPath=wrapper/dists
|
||||
zipStoreBase=GRADLE_USER_HOME
|
||||
zipStorePath=wrapper/dists
|
||||
distributionUrl=https\://services.gradle.org/distributions/gradle-4.8-all.zip
|
||||
distributionUrl=https\://services.gradle.org/distributions/gradle-5.2.1-all.zip
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-2015 microG Project Team
|
||||
* Copyright 2013-2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@ -16,13 +16,20 @@
|
||||
|
||||
apply plugin: 'com.android.application'
|
||||
|
||||
def useMapbox() {
|
||||
Properties properties = new Properties()
|
||||
properties.load(project.rootProject.file('local.properties').newDataInputStream())
|
||||
return properties.getProperty("mapbox.enabled", "false") == "true"
|
||||
}
|
||||
|
||||
dependencies {
|
||||
implementation "com.android.support:support-v4:$supportLibraryVersion"
|
||||
implementation "com.android.support:appcompat-v7:$supportLibraryVersion"
|
||||
implementation "com.android.support:mediarouter-v7:$supportLibraryVersion"
|
||||
implementation "com.squareup.wire:wire-runtime:1.6.1"
|
||||
implementation "com.takisoft.fix:preference-v7:$supportLibraryVersion.0"
|
||||
implementation "de.hdodenhof:circleimageview:1.3.0"
|
||||
implementation "com.squareup.wire:wire-runtime:1.6.1"
|
||||
implementation "org.conscrypt:conscrypt-android:2.0.0"
|
||||
// TODO: Switch to upstream once raw requests are merged
|
||||
// https://github.com/vitalidze/chromecast-java-api-v2/pull/99
|
||||
// implementation "su.litvak.chromecast:api-v2:0.10.4"
|
||||
@ -41,11 +48,11 @@ dependencies {
|
||||
implementation project(':wearable-lib')
|
||||
|
||||
implementation project(':remote-droid-guard-lib')
|
||||
|
||||
implementation project(':vtm-android')
|
||||
implementation project(':vtm-extras')
|
||||
implementation project(':vtm-jts')
|
||||
implementation project(':vtm-microg-theme')
|
||||
if (useMapbox()) {
|
||||
implementation project(':play-services-maps-core-mapbox')
|
||||
} else {
|
||||
implementation project(':play-services-maps-core-vtm')
|
||||
}
|
||||
}
|
||||
|
||||
def execResult(...args) {
|
||||
@ -57,16 +64,16 @@ def execResult(...args) {
|
||||
return stdout.toString().trim()
|
||||
}
|
||||
|
||||
def gmsVersion = "13.2.80"
|
||||
def gmsVersion = "17.4.55"
|
||||
def gmsVersionCode = Integer.parseInt(gmsVersion.replaceAll('\\.', ''))
|
||||
def gitVersionBase = execResult('git', 'describe', '--tags', '--abbrev=0').substring(1)
|
||||
def gitVersionBase = execResult('git', 'describe', '--tags', '--abbrev=0', '--match=v[0-9]*').substring(1)
|
||||
def gitCommitCount = Integer.parseInt(execResult('git', 'rev-list', '--count', "v$gitVersionBase..HEAD"))
|
||||
def gitCommitId = execResult('git', 'show-ref', '--abbrev=7', '--head', 'HEAD').split(' ')[0]
|
||||
def gitDirty = execResult('git', 'status', '--porcelain').size() > 0
|
||||
def ourVersionBase = gitVersionBase.substring(0, gitVersionBase.lastIndexOf('.'))
|
||||
def ourVersionMinor = Integer.parseInt(ourVersionBase.substring(ourVersionBase.lastIndexOf('.') + 1))
|
||||
def ourVersionCode = gmsVersionCode * 1000 + ourVersionMinor * 2 + (gitCommitCount > 0 || gitDirty ? 1 : 0)
|
||||
def ourVersionName = "$ourVersionBase.$gmsVersionCode" + (gitCommitCount > 0 && !gitDirty ? "-$gitCommitCount" : "") + (gitDirty ? "-dirty" : "") + (gitCommitCount > 0 && !gitDirty ? " ($gitCommitId)" : "")
|
||||
def ourVersionName = "$ourVersionBase.$gmsVersionCode" + (gitCommitCount > 0 && !gitDirty ? "-$gitCommitCount" : "") + (gitDirty ? "-dirty" : "") + (useMapbox() ? "-mapbox" : "") + (gitCommitCount > 0 && !gitDirty ? " ($gitCommitId)" : "")
|
||||
logger.lifecycle('Starting build for version {} ({})...', ourVersionName, ourVersionCode)
|
||||
|
||||
android {
|
||||
@ -88,14 +95,11 @@ android {
|
||||
sourceSets {
|
||||
main {
|
||||
java.srcDirs += 'src/main/protos-java'
|
||||
file("${rootDir}/vtm-android/natives").eachDir() { dir ->
|
||||
jniLibs.srcDirs += "${dir.path}/lib"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
lintOptions {
|
||||
disable 'MissingTranslation', 'InvalidPackage', 'BatteryLife', 'ImpliedQuantity', 'MissingQuantity'
|
||||
disable 'MissingTranslation', 'InvalidPackage', 'BatteryLife', 'ImpliedQuantity', 'MissingQuantity', 'InvalidWakeLockTag'
|
||||
}
|
||||
|
||||
buildTypes {
|
||||
|
@ -90,6 +90,7 @@
|
||||
|
||||
<uses-permission android:name="android.permission.REQUEST_IGNORE_BATTERY_OPTIMIZATIONS"/>
|
||||
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED"/>
|
||||
<uses-permission android:name="android.permission.CHANGE_DEVICE_IDLE_TEMP_WHITELIST" tools:ignore="ProtectedPermissions"/>
|
||||
|
||||
<uses-sdk tools:overrideLibrary="
|
||||
com.takisoft.fix.support.v7.preference,
|
||||
@ -258,20 +259,14 @@
|
||||
|
||||
<receiver android:name="org.microg.gms.gcm.UnregisterReceiver">
|
||||
<intent-filter>
|
||||
<action android:name="android.intent.action.PACKAGE_ADDED"/>
|
||||
<action android:name="android.intent.action.PACKAGE_DATA_CLEARED"/>
|
||||
<action android:name="android.intent.action.PACKAGE_FULLY_REMOVED"/>
|
||||
<action android:name="android.intent.action.PACKAGE_REMOVED"/>
|
||||
|
||||
<data android:scheme="package"/>
|
||||
</intent-filter>
|
||||
</receiver>
|
||||
|
||||
<!-- Map -->
|
||||
<provider
|
||||
android:name="org.microg.gms.maps.data.SharedTileProvider"
|
||||
android:authorities="org.microg.gms.map.tile"
|
||||
android:enabled="true"
|
||||
android:exported="true"/>
|
||||
|
||||
<!-- DroidGuard -->
|
||||
|
||||
<service android:name="org.microg.gms.droidguard.DroidGuardService">
|
||||
|
@ -17,10 +17,41 @@
|
||||
package com.google.android.gms.common.security;
|
||||
|
||||
import android.content.Context;
|
||||
import android.os.Process;
|
||||
import android.util.Log;
|
||||
|
||||
import org.conscrypt.OpenSSLProvider;
|
||||
import org.microg.gms.common.PackageUtils;
|
||||
|
||||
import java.security.Security;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
|
||||
import javax.net.ssl.HttpsURLConnection;
|
||||
import javax.net.ssl.SSLContext;
|
||||
|
||||
public class ProviderInstallerImpl {
|
||||
private static final String TAG = "GmsProviderInstaller";
|
||||
private static final List<String> DISABLED = Collections.singletonList("com.discord");
|
||||
|
||||
public static void insertProvider(Context context) {
|
||||
Log.d("ProviderInstallerImpl", "yep, i should do something with Security here...");
|
||||
try {
|
||||
String packageName = PackageUtils.packageFromProcessId(context, Process.myPid());
|
||||
Log.d(TAG, "Provider installer invoked for " + packageName);
|
||||
if (DISABLED.contains(packageName)) {
|
||||
Log.d(TAG, "Package is excluded from usage of provider installer");
|
||||
} else if (Security.insertProviderAt(new OpenSSLProvider("GmsCore_OpenSSL"), 1) == 1) {
|
||||
Security.setProperty("ssl.SocketFactory.provider", "org.conscrypt.OpenSSLSocketFactoryImpl");
|
||||
Security.setProperty("ssl.ServerSocketFactory.provider", "org.conscrypt.OpenSSLServerSocketFactoryImpl");
|
||||
|
||||
SSLContext.setDefault(SSLContext.getInstance("Default"));
|
||||
HttpsURLConnection.setDefaultSSLSocketFactory(SSLContext.getDefault().getSocketFactory());
|
||||
Log.d(TAG, "SSL provider installed");
|
||||
} else {
|
||||
Log.w(TAG, "Did not insert the new SSL provider");
|
||||
}
|
||||
} catch (Exception e) {
|
||||
Log.w(TAG, e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -197,6 +197,7 @@ public class AuthManager {
|
||||
}
|
||||
}
|
||||
AuthRequest request = new AuthRequest().fromContext(context)
|
||||
.source("android")
|
||||
.app(packageName, getPackageSignature())
|
||||
.email(accountName)
|
||||
.token(getAccountManager().getPassword(account))
|
||||
|
@ -30,8 +30,8 @@ import static org.microg.gms.common.HttpFormClient.RequestContent;
|
||||
import static org.microg.gms.common.HttpFormClient.RequestHeader;
|
||||
|
||||
public class AuthRequest extends HttpFormClient.Request {
|
||||
private static final String SERVICE_URL = "https://android.clients.google.com/auth";
|
||||
private static final String USER_AGENT = "GoogleAuth/1.4 (%s %s)";
|
||||
private static final String SERVICE_URL = "https://android.googleapis.com/auth";
|
||||
private static final String USER_AGENT = "GoogleAuth/1.4 (%s %s); gzip";
|
||||
|
||||
@RequestHeader("User-Agent")
|
||||
private String userAgent;
|
||||
@ -59,13 +59,13 @@ public class AuthRequest extends HttpFormClient.Request {
|
||||
@RequestContent("google_play_services_version")
|
||||
public int gmsVersion = Constants.MAX_REFERENCE_VERSION;
|
||||
@RequestContent("accountType")
|
||||
public String accountType = "HOSTED_OR_GOOGLE";
|
||||
public String accountType;
|
||||
@RequestContent("Email")
|
||||
public String email;
|
||||
@RequestContent("service")
|
||||
public String service;
|
||||
@RequestContent("source")
|
||||
public String source = "android";
|
||||
public String source;
|
||||
@RequestContent({"is_called_from_account_manager", "_opt_is_called_from_account_manager"})
|
||||
public boolean isCalledFromAccountManager;
|
||||
@RequestContent("Token")
|
||||
@ -97,10 +97,15 @@ public class AuthRequest extends HttpFormClient.Request {
|
||||
return this;
|
||||
}
|
||||
|
||||
public AuthRequest source(String source) {
|
||||
this.source = source;
|
||||
return this;
|
||||
}
|
||||
|
||||
public AuthRequest locale(Locale locale) {
|
||||
this.locale = locale.toString();
|
||||
this.countryCode = locale.getCountry();
|
||||
this.operatorCountryCode = locale.getCountry();
|
||||
this.countryCode = locale.getCountry().toLowerCase();
|
||||
this.operatorCountryCode = locale.getCountry().toLowerCase();
|
||||
return this;
|
||||
}
|
||||
|
||||
|
@ -21,19 +21,17 @@ import android.accounts.AccountManager;
|
||||
import android.annotation.SuppressLint;
|
||||
import android.annotation.TargetApi;
|
||||
import android.content.Context;
|
||||
import android.content.SharedPreferences;
|
||||
import android.graphics.Bitmap;
|
||||
import android.graphics.Color;
|
||||
import android.net.ConnectivityManager;
|
||||
import android.net.NetworkInfo;
|
||||
import android.net.Uri;
|
||||
import android.os.Build;
|
||||
import android.os.Bundle;
|
||||
import android.preference.PreferenceManager;
|
||||
import android.support.annotation.StringRes;
|
||||
import android.support.v4.view.LayoutInflaterCompat;
|
||||
import android.text.TextUtils;
|
||||
import android.util.Log;
|
||||
import android.view.KeyEvent;
|
||||
import android.view.LayoutInflater;
|
||||
import android.view.View;
|
||||
import android.view.ViewGroup;
|
||||
import android.view.inputmethod.InputMethodManager;
|
||||
@ -73,7 +71,6 @@ import static android.view.View.VISIBLE;
|
||||
import static android.view.inputmethod.InputMethodManager.SHOW_IMPLICIT;
|
||||
import static org.microg.gms.common.Constants.GMS_PACKAGE_NAME;
|
||||
import static org.microg.gms.common.Constants.MAX_REFERENCE_VERSION;
|
||||
import android.os.Build;
|
||||
|
||||
public class LoginActivity extends AssistantActivity {
|
||||
public static final String TMPL_NEW_ACCOUNT = "new_account";
|
||||
@ -85,6 +82,7 @@ public class LoginActivity extends AssistantActivity {
|
||||
private static final String TAG = "GmsAuthLoginBrowser";
|
||||
private static final String EMBEDDED_SETUP_URL = "https://accounts.google.com/EmbeddedSetup";
|
||||
private static final String PROGRAMMATIC_AUTH_URL = "https://accounts.google.com/o/oauth2/programmatic_auth";
|
||||
private static final String GOOGLE_SUITE_URL = "https://accounts.google.com/signin/continue";
|
||||
private static final String MAGIC_USER_AGENT = " MinuteMaid";
|
||||
private static final String COOKIE_OAUTH_TOKEN = "oauth_token";
|
||||
|
||||
@ -109,16 +107,23 @@ public class LoginActivity extends AssistantActivity {
|
||||
webView.setWebViewClient(new WebViewClient() {
|
||||
@Override
|
||||
public void onPageFinished(WebView view, String url) {
|
||||
Log.d(TAG, "pageFinished: " + url);
|
||||
if ("identifier".equals(Uri.parse(url).getFragment()))
|
||||
runOnUiThread(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
webView.setVisibility(VISIBLE);
|
||||
}
|
||||
});
|
||||
if ("close".equals(Uri.parse(url).getFragment()))
|
||||
Log.d(TAG, "pageFinished: " + view.getUrl());
|
||||
Uri uri = Uri.parse(view.getUrl());
|
||||
|
||||
// Begin login.
|
||||
// Only required if client code does not invoke showView() via JSBridge
|
||||
if ("identifier".equals(uri.getFragment()) || uri.getPath().endsWith("/identifier"))
|
||||
runOnUiThread(() -> webView.setVisibility(VISIBLE));
|
||||
|
||||
// Normal login.
|
||||
if ("close".equals(uri.getFragment()))
|
||||
closeWeb(false);
|
||||
|
||||
// Google Suite login.
|
||||
if (url.startsWith(GOOGLE_SUITE_URL))
|
||||
closeWeb(false);
|
||||
|
||||
// IDK when this is called.
|
||||
if (url.startsWith(PROGRAMMATIC_AUTH_URL))
|
||||
closeWeb(true);
|
||||
}
|
||||
@ -172,12 +177,7 @@ public class LoginActivity extends AssistantActivity {
|
||||
setMessage(R.string.auth_connecting);
|
||||
CookieManager.getInstance().setAcceptCookie(true);
|
||||
if (SDK_INT >= LOLLIPOP) {
|
||||
CookieManager.getInstance().removeAllCookies(new ValueCallback<Boolean>() {
|
||||
@Override
|
||||
public void onReceiveValue(Boolean value) {
|
||||
start();
|
||||
}
|
||||
});
|
||||
CookieManager.getInstance().removeAllCookies(value -> start());
|
||||
} else {
|
||||
//noinspection deprecation
|
||||
CookieManager.getInstance().removeAllCookie();
|
||||
@ -218,23 +218,10 @@ public class LoginActivity extends AssistantActivity {
|
||||
NetworkInfo networkInfo = cm.getActiveNetworkInfo();
|
||||
if (networkInfo != null && networkInfo.isConnected()) {
|
||||
if (LastCheckinInfo.read(this).androidId == 0) {
|
||||
new Thread(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
Runnable next;
|
||||
next = checkin(false) ? new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
loadLoginPage();
|
||||
}
|
||||
} : new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
showError(R.string.auth_general_error_desc);
|
||||
}
|
||||
};
|
||||
LoginActivity.this.runOnUiThread(next);
|
||||
}
|
||||
new Thread(() -> {
|
||||
Runnable next;
|
||||
next = checkin(false) ? this::loadLoginPage : () -> showError(R.string.auth_general_error_desc);
|
||||
LoginActivity.this.runOnUiThread(next);
|
||||
}).start();
|
||||
} else {
|
||||
loadLoginPage();
|
||||
@ -250,7 +237,7 @@ public class LoginActivity extends AssistantActivity {
|
||||
setMessage(errorRes);
|
||||
}
|
||||
|
||||
private void setMessage(@StringRes int res) {
|
||||
private void setMessage(@StringRes int res) {
|
||||
setMessage(getText(res));
|
||||
}
|
||||
|
||||
@ -265,12 +252,7 @@ public class LoginActivity extends AssistantActivity {
|
||||
|
||||
private void closeWeb(boolean programmaticAuth) {
|
||||
setMessage(R.string.auth_finalize);
|
||||
runOnUiThread(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
webView.setVisibility(INVISIBLE);
|
||||
}
|
||||
});
|
||||
runOnUiThread(() -> webView.setVisibility(INVISIBLE));
|
||||
String cookies = CookieManager.getInstance().getCookie(programmaticAuth ? PROGRAMMATIC_AUTH_URL : EMBEDDED_SETUP_URL);
|
||||
String[] temp = cookies.split(";");
|
||||
for (String ar1 : temp) {
|
||||
@ -286,12 +268,11 @@ public class LoginActivity extends AssistantActivity {
|
||||
private void retrieveRtToken(String oAuthToken) {
|
||||
new AuthRequest().fromContext(this)
|
||||
.appIsGms()
|
||||
.callerIsGms()
|
||||
.service("ac2dm")
|
||||
.token(oAuthToken).isAccessToken()
|
||||
.addAccount()
|
||||
.getAccountId()
|
||||
.systemPartition()
|
||||
.hasPermission()
|
||||
.droidguardResults(null /*TODO*/)
|
||||
.getResponseAsync(new HttpFormClient.Callback<AuthResponse>() {
|
||||
@Override
|
||||
@ -312,12 +293,9 @@ public class LoginActivity extends AssistantActivity {
|
||||
setResult(RESULT_OK);
|
||||
} else {
|
||||
Log.w(TAG, "Account NOT created!");
|
||||
runOnUiThread(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
showError(R.string.auth_general_error_desc);
|
||||
setNextButtonText(android.R.string.ok);
|
||||
}
|
||||
runOnUiThread(() -> {
|
||||
showError(R.string.auth_general_error_desc);
|
||||
setNextButtonText(android.R.string.ok);
|
||||
});
|
||||
state = -2;
|
||||
}
|
||||
@ -335,6 +313,7 @@ public class LoginActivity extends AssistantActivity {
|
||||
authManager.setPermitted(true);
|
||||
new AuthRequest().fromContext(this)
|
||||
.appIsGms()
|
||||
.callerIsGms()
|
||||
.service(authManager.getService())
|
||||
.email(account.name)
|
||||
.token(AccountManager.get(this).getPassword(account))
|
||||
@ -392,9 +371,28 @@ public class LoginActivity extends AssistantActivity {
|
||||
}
|
||||
|
||||
private class JsBridge {
|
||||
|
||||
@JavascriptInterface
|
||||
public final void addAccount(String json) {
|
||||
Log.d(TAG, "JSBridge: addAccount " + json);
|
||||
}
|
||||
|
||||
@JavascriptInterface
|
||||
public final void closeView() {
|
||||
Log.d(TAG, "JSBridge: closeView");
|
||||
closeWeb(false);
|
||||
}
|
||||
|
||||
@JavascriptInterface
|
||||
public final String fetchVerifiedPhoneNumber() {
|
||||
Log.d(TAG, "JSBridge: fetchVerifiedPhoneNumber");
|
||||
return null;
|
||||
}
|
||||
|
||||
@SuppressWarnings("MissingPermission")
|
||||
@JavascriptInterface
|
||||
public final String getAccounts() {
|
||||
Log.d(TAG, "JSBridge: getAccounts");
|
||||
Account[] accountsByType = accountManager.getAccountsByType(accountType);
|
||||
JSONArray json = new JSONArray();
|
||||
for (Account account : accountsByType) {
|
||||
@ -405,16 +403,23 @@ public class LoginActivity extends AssistantActivity {
|
||||
|
||||
@JavascriptInterface
|
||||
public final String getAllowedDomains() {
|
||||
Log.d(TAG, "JSBridge: getAllowedDomains");
|
||||
return new JSONArray().toString();
|
||||
}
|
||||
|
||||
@JavascriptInterface
|
||||
public final String getAndroidId() {
|
||||
long androidId = LastCheckinInfo.read(LoginActivity.this).androidId;
|
||||
Log.d(TAG, "JSBridge: getAndroidId " + androidId);
|
||||
if (androidId == 0 || androidId == -1) return null;
|
||||
return Long.toHexString(androidId);
|
||||
}
|
||||
|
||||
@JavascriptInterface
|
||||
public final int getAuthModuleVersionCode() {
|
||||
return 1;
|
||||
}
|
||||
|
||||
@JavascriptInterface
|
||||
public final int getBuildVersionSdk() {
|
||||
return SDK_INT;
|
||||
@ -425,6 +430,11 @@ public class LoginActivity extends AssistantActivity {
|
||||
Log.d(TAG, "JSBridge: getDroidGuardResult: " + s);
|
||||
}
|
||||
|
||||
@JavascriptInterface
|
||||
public final int getDeviceDataVersionInfo() {
|
||||
return 1;
|
||||
}
|
||||
|
||||
@JavascriptInterface
|
||||
public final String getFactoryResetChallenges() {
|
||||
return new JSONArray().toString();
|
||||
@ -471,14 +481,29 @@ public class LoginActivity extends AssistantActivity {
|
||||
inputMethodManager.hideSoftInputFromWindow(webView.getWindowToken(), 0);
|
||||
}
|
||||
|
||||
@JavascriptInterface
|
||||
public final boolean isUserOwner() {
|
||||
return true;
|
||||
}
|
||||
|
||||
@JavascriptInterface
|
||||
public final void launchEmergencyDialer() {
|
||||
Log.d(TAG, "JSBridge: launchEmergencyDialer");
|
||||
}
|
||||
|
||||
@JavascriptInterface
|
||||
public final void log(String s) {
|
||||
Log.d(TAG, "JSBridge: log " + s);
|
||||
}
|
||||
|
||||
@JavascriptInterface
|
||||
public final void notifyOnTermsOfServiceAccepted() {
|
||||
Log.d(TAG, "Terms of service accepted. (who cares?)");
|
||||
Log.d(TAG, "JSBridge: notifyOnTermsOfServiceAccepted");
|
||||
}
|
||||
|
||||
@JavascriptInterface
|
||||
public final void setAccountIdentifier(String accountIdentifier) {
|
||||
Log.d(TAG, "JSBridge: setAccountIdentifier " + accountIdentifier);
|
||||
}
|
||||
|
||||
@TargetApi(HONEYCOMB)
|
||||
@ -497,7 +522,7 @@ public class LoginActivity extends AssistantActivity {
|
||||
|
||||
@JavascriptInterface
|
||||
public final void setNewAccountCreated() {
|
||||
Log.d(TAG, "New account created. (who cares?)");
|
||||
Log.d(TAG, "JSBridge: setNewAccountCreated");
|
||||
}
|
||||
|
||||
@JavascriptInterface
|
||||
@ -509,12 +534,7 @@ public class LoginActivity extends AssistantActivity {
|
||||
@JavascriptInterface
|
||||
public final void showView() {
|
||||
Log.d(TAG, "JSBridge: showView");
|
||||
runOnUiThread(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
webView.setVisibility(VISIBLE);
|
||||
}
|
||||
});
|
||||
runOnUiThread(() -> webView.setVisibility(VISIBLE));
|
||||
}
|
||||
|
||||
@JavascriptInterface
|
||||
|
@ -16,6 +16,7 @@
|
||||
|
||||
package org.microg.gms.common;
|
||||
|
||||
import android.app.ActivityManager;
|
||||
import android.app.PendingIntent;
|
||||
import android.content.Context;
|
||||
import android.content.pm.PackageInfo;
|
||||
@ -119,6 +120,16 @@ public class PackageUtils {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public static String packageFromProcessId(Context context, int pid) {
|
||||
ActivityManager manager = (ActivityManager) context.getSystemService(Context.ACTIVITY_SERVICE);
|
||||
if (manager == null) return null;
|
||||
for (ActivityManager.RunningAppProcessInfo processInfo : manager.getRunningAppProcesses()) {
|
||||
if (processInfo.pid == pid) return processInfo.processName;
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
@SuppressWarnings("deprecation")
|
||||
public static String packageFromPendingIntent(PendingIntent pi) {
|
||||
if (pi == null) return null;
|
||||
|
@ -18,6 +18,7 @@ package org.microg.gms.common;
|
||||
|
||||
import android.content.Context;
|
||||
import android.support.v4.content.ContextCompat;
|
||||
import android.util.Log;
|
||||
import android.widget.Toast;
|
||||
|
||||
import com.google.android.gms.R;
|
||||
@ -53,8 +54,12 @@ public class Utils {
|
||||
}
|
||||
|
||||
public static boolean hasSelfPermissionOrNotify(Context context, String permission) {
|
||||
if (ContextCompat.checkSelfPermission(context, permission) != PERMISSION_GRANTED) {
|
||||
Toast.makeText(context, context.getString(R.string.lacking_permission_toast, permission), Toast.LENGTH_SHORT).show();
|
||||
if (context.checkCallingOrSelfPermission(permission) != PERMISSION_GRANTED) {
|
||||
try {
|
||||
Toast.makeText(context, context.getString(R.string.lacking_permission_toast, permission), Toast.LENGTH_SHORT).show();
|
||||
} catch (RuntimeException e) {
|
||||
Log.w("GmsUtils", "Lacking permission to " + permission + " for pid:" + android.os.Process.myPid() + " uid:" + android.os.Process.myUid());
|
||||
}
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
|
@ -35,6 +35,7 @@ import android.os.Messenger;
|
||||
import android.os.Parcelable;
|
||||
import android.os.PowerManager;
|
||||
import android.os.SystemClock;
|
||||
import android.os.UserHandle;
|
||||
import android.support.v4.content.WakefulBroadcastReceiver;
|
||||
import android.util.Log;
|
||||
|
||||
@ -52,6 +53,8 @@ import org.microg.gms.gcm.mcs.LoginResponse;
|
||||
import org.microg.gms.gcm.mcs.Setting;
|
||||
|
||||
import java.io.Closeable;
|
||||
import java.lang.reflect.Field;
|
||||
import java.lang.reflect.Method;
|
||||
import java.net.Socket;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
@ -132,6 +135,10 @@ public class McsService extends Service implements Handler.Callback {
|
||||
|
||||
private static int maxTtl = 24 * 60 * 60;
|
||||
|
||||
private Object deviceIdleController;
|
||||
private Method getUserIdMethod;
|
||||
private Method addPowerSaveTempWhitelistAppMethod;
|
||||
|
||||
private class HandlerThread extends Thread {
|
||||
|
||||
public HandlerThread() {
|
||||
@ -166,6 +173,22 @@ public class McsService extends Service implements Handler.Callback {
|
||||
heartbeatIntent = PendingIntent.getService(this, 0, new Intent(ACTION_HEARTBEAT, null, this, McsService.class), 0);
|
||||
alarmManager = (AlarmManager) getSystemService(ALARM_SERVICE);
|
||||
powerManager = (PowerManager) getSystemService(POWER_SERVICE);
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
|
||||
try {
|
||||
Field field = Context.class.getField("DEVICE_IDLE_CONTROLLER");
|
||||
IBinder binder = (IBinder) Class.forName("android.os.ServiceManager")
|
||||
.getMethod("getService", String.class).invoke(null, field.get(null));
|
||||
if (binder != null) {
|
||||
deviceIdleController = Class.forName("android.os.IDeviceIdleController$Stub")
|
||||
.getMethod("asInterface", IBinder.class).invoke(null, binder);
|
||||
getUserIdMethod = UserHandle.class.getMethod("getUserId", int.class);
|
||||
addPowerSaveTempWhitelistAppMethod = deviceIdleController.getClass()
|
||||
.getMethod("addPowerSaveTempWhitelistApp", String.class, long.class, int.class, String.class);
|
||||
}
|
||||
} catch (Exception e) {
|
||||
Log.w(TAG, e);
|
||||
}
|
||||
}
|
||||
synchronized (McsService.class) {
|
||||
if (handlerThread == null) {
|
||||
handlerThread = new HandlerThread();
|
||||
@ -452,13 +475,15 @@ public class McsService extends Service implements Handler.Callback {
|
||||
}
|
||||
|
||||
private void handleAppMessage(DataMessageStanza msg) {
|
||||
database.noteAppMessage(msg.category, msg.getSerializedSize());
|
||||
GcmDatabase.App app = database.getApp(msg.category);
|
||||
String packageName = msg.category;
|
||||
database.noteAppMessage(packageName, msg.getSerializedSize());
|
||||
GcmDatabase.App app = database.getApp(packageName);
|
||||
|
||||
Intent intent = new Intent();
|
||||
intent.setAction(ACTION_C2DM_RECEIVE);
|
||||
intent.setPackage(msg.category);
|
||||
intent.setPackage(packageName);
|
||||
intent.putExtra(EXTRA_FROM, msg.from);
|
||||
intent.putExtra(EXTRA_MESSAGE_ID, msg.id);
|
||||
if (app.wakeForDelivery) {
|
||||
intent.addFlags(Intent.FLAG_INCLUDE_STOPPED_PACKAGES);
|
||||
} else {
|
||||
@ -471,7 +496,7 @@ public class McsService extends Service implements Handler.Callback {
|
||||
|
||||
String receiverPermission;
|
||||
try {
|
||||
String name = msg.category + ".permission.C2D_MESSAGE";
|
||||
String name = packageName + ".permission.C2D_MESSAGE";
|
||||
getPackageManager().getPermissionInfo(name, 0);
|
||||
receiverPermission = name;
|
||||
} catch (PackageManager.NameNotFoundException e) {
|
||||
@ -485,6 +510,17 @@ public class McsService extends Service implements Handler.Callback {
|
||||
for (ResolveInfo resolveInfo : infos) {
|
||||
logd("Target: " + resolveInfo);
|
||||
Intent targetIntent = new Intent(intent);
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M && app.wakeForDelivery) {
|
||||
try {
|
||||
if (getUserIdMethod != null && addPowerSaveTempWhitelistAppMethod != null && deviceIdleController != null) {
|
||||
int userId = (int) getUserIdMethod.invoke(null, getPackageManager().getApplicationInfo(packageName, 0).uid);
|
||||
logd("Adding app " + packageName + " for userId " + userId + " to the temp whitelist");
|
||||
addPowerSaveTempWhitelistAppMethod.invoke(deviceIdleController, packageName, 10000, userId, "GCM Push");
|
||||
}
|
||||
} catch (Exception e) {
|
||||
Log.w(TAG, e);
|
||||
}
|
||||
}
|
||||
targetIntent.setComponent(new ComponentName(resolveInfo.activityInfo.packageName, resolveInfo.activityInfo.name));
|
||||
sendOrderedBroadcast(targetIntent, receiverPermission);
|
||||
}
|
||||
|
@ -8,7 +8,10 @@ import android.util.Log;
|
||||
import java.util.List;
|
||||
|
||||
import static android.content.Intent.ACTION_PACKAGE_REMOVED;
|
||||
import static android.content.Intent.ACTION_PACKAGE_DATA_CLEARED;
|
||||
import static android.content.Intent.ACTION_PACKAGE_FULLY_REMOVED;
|
||||
import static android.content.Intent.EXTRA_DATA_REMOVED;
|
||||
import static android.content.Intent.EXTRA_REPLACING;
|
||||
|
||||
public class UnregisterReceiver extends BroadcastReceiver {
|
||||
private static final String TAG = "GmsGcmUnregisterRcvr";
|
||||
@ -16,10 +19,13 @@ public class UnregisterReceiver extends BroadcastReceiver {
|
||||
@Override
|
||||
public void onReceive(final Context context, Intent intent) {
|
||||
Log.d(TAG, "Package changed: " + intent);
|
||||
if (ACTION_PACKAGE_REMOVED.contains(intent.getAction()) && intent.getBooleanExtra(EXTRA_DATA_REMOVED, false)) {
|
||||
if ((ACTION_PACKAGE_REMOVED.contains(intent.getAction()) && intent.getBooleanExtra(EXTRA_DATA_REMOVED, false) &&
|
||||
!intent.getBooleanExtra(EXTRA_REPLACING, false)) ||
|
||||
ACTION_PACKAGE_FULLY_REMOVED.contains(intent.getAction()) ||
|
||||
ACTION_PACKAGE_DATA_CLEARED.contains(intent.getAction())) {
|
||||
final GcmDatabase database = new GcmDatabase(context);
|
||||
final String packageName = intent.getData().getSchemeSpecificPart();
|
||||
Log.d(TAG, "Package removed: " + packageName);
|
||||
Log.d(TAG, "Package removed or data cleared: " + packageName);
|
||||
final GcmDatabase.App app = database.getApp(packageName);
|
||||
if (app != null) {
|
||||
new Thread(new Runnable() {
|
||||
|
@ -28,6 +28,7 @@ import com.google.android.gms.location.LocationRequest;
|
||||
import com.google.android.gms.location.internal.FusedLocationProviderResult;
|
||||
import com.google.android.gms.location.internal.LocationRequestUpdateData;
|
||||
|
||||
import org.microg.gms.common.PackageUtils;
|
||||
import org.microg.gms.common.Utils;
|
||||
|
||||
import java.util.ArrayList;
|
||||
@ -42,6 +43,7 @@ import static com.google.android.gms.location.LocationRequest.PRIORITY_HIGH_ACCU
|
||||
import static com.google.android.gms.location.LocationRequest.PRIORITY_NO_POWER;
|
||||
|
||||
public class GoogleLocationManager implements LocationChangeListener {
|
||||
private static final String TAG = "GmsLocManager";
|
||||
private static final String MOCK_PROVIDER = "mock";
|
||||
private static final long SWITCH_ON_FRESHNESS_CLIFF_MS = 30000; // 30 seconds
|
||||
private static final String ACCESS_MOCK_LOCATION = "android.permission.ACCESS_MOCK_LOCATION";
|
||||
@ -155,8 +157,11 @@ public class GoogleLocationManager implements LocationChangeListener {
|
||||
}
|
||||
|
||||
public void updateLocationRequest(LocationRequestUpdateData data) {
|
||||
String packageName = null;
|
||||
if (data.pendingIntent != null)
|
||||
packageName = PackageUtils.packageFromPendingIntent(data.pendingIntent);
|
||||
if (data.opCode == LocationRequestUpdateData.REQUEST_UPDATES) {
|
||||
requestLocationUpdates(new LocationRequestHelper(context, hasFineLocationPermission(), hasCoarseLocationPermission(), null, data));
|
||||
requestLocationUpdates(new LocationRequestHelper(context, hasFineLocationPermission(), hasCoarseLocationPermission(), packageName, data));
|
||||
if (data.fusedLocationProviderCallback != null) {
|
||||
try {
|
||||
data.fusedLocationProviderCallback.onFusedLocationProviderResult(FusedLocationProviderResult.SUCCESS);
|
||||
|
@ -19,6 +19,7 @@ package org.microg.gms.location;
|
||||
import android.app.PendingIntent;
|
||||
import android.content.Context;
|
||||
import android.location.Location;
|
||||
import android.os.Binder;
|
||||
import android.os.IBinder;
|
||||
import android.os.Parcel;
|
||||
import android.os.RemoteException;
|
||||
@ -52,6 +53,8 @@ import com.google.android.gms.location.places.internal.PlacesParams;
|
||||
import com.google.android.gms.maps.model.LatLng;
|
||||
import com.google.android.gms.maps.model.LatLngBounds;
|
||||
|
||||
import org.microg.gms.common.PackageUtils;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
|
||||
@ -75,23 +78,27 @@ public class GoogleLocationManagerServiceImpl extends IGoogleLocationManagerServ
|
||||
public void addGeofencesList(List<ParcelableGeofence> geofences, PendingIntent pendingIntent,
|
||||
IGeofencerCallbacks callbacks, String packageName) throws RemoteException {
|
||||
Log.d(TAG, "addGeofencesList: " + geofences);
|
||||
PackageUtils.checkPackageUid(context, packageName, Binder.getCallingUid());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void removeGeofencesByIntent(PendingIntent pendingIntent, IGeofencerCallbacks callbacks,
|
||||
String packageName) throws RemoteException {
|
||||
Log.d(TAG, "removeGeofencesByIntent: " + pendingIntent);
|
||||
PackageUtils.checkPackageUid(context, packageName, Binder.getCallingUid());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void removeGeofencesById(String[] geofenceRequestIds, IGeofencerCallbacks callbacks,
|
||||
String packageName) throws RemoteException {
|
||||
Log.d(TAG, "removeGeofencesById: " + Arrays.toString(geofenceRequestIds));
|
||||
PackageUtils.checkPackageUid(context, packageName, Binder.getCallingUid());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void removeAllGeofences(IGeofencerCallbacks callbacks, String packageName) throws RemoteException {
|
||||
Log.d(TAG, "removeAllGeofences");
|
||||
PackageUtils.checkPackageUid(context, packageName, Binder.getCallingUid());
|
||||
}
|
||||
|
||||
@Override
|
||||
@ -108,6 +115,7 @@ public class GoogleLocationManagerServiceImpl extends IGoogleLocationManagerServ
|
||||
@Override
|
||||
public ActivityRecognitionResult getLastActivity(String packageName) throws RemoteException {
|
||||
Log.d(TAG, "getLastActivity");
|
||||
PackageUtils.checkPackageUid(context, packageName, Binder.getCallingUid());
|
||||
return null;
|
||||
}
|
||||
|
||||
@ -138,35 +146,35 @@ public class GoogleLocationManagerServiceImpl extends IGoogleLocationManagerServ
|
||||
@Override
|
||||
public Location getLastLocation() throws RemoteException {
|
||||
Log.d(TAG, "getLastLocation");
|
||||
return getLocationManager().getLastLocation(null);
|
||||
return getLocationManager().getLastLocation(PackageUtils.packageFromProcessId(context, Binder.getCallingPid()));
|
||||
}
|
||||
|
||||
@Override
|
||||
public void requestLocationUpdatesWithListener(LocationRequest request,
|
||||
final ILocationListener listener) throws RemoteException {
|
||||
Log.d(TAG, "requestLocationUpdatesWithListener: " + request);
|
||||
getLocationManager().requestLocationUpdates(request, listener, null);
|
||||
getLocationManager().requestLocationUpdates(request, listener, PackageUtils.packageFromProcessId(context, Binder.getCallingPid()));
|
||||
}
|
||||
|
||||
@Override
|
||||
public void requestLocationUpdatesWithIntent(LocationRequest request,
|
||||
PendingIntent callbackIntent) throws RemoteException {
|
||||
Log.d(TAG, "requestLocationUpdatesWithIntent: " + request);
|
||||
getLocationManager().requestLocationUpdates(request, callbackIntent, null);
|
||||
getLocationManager().requestLocationUpdates(request, callbackIntent, PackageUtils.packageFromPendingIntent(callbackIntent));
|
||||
}
|
||||
|
||||
@Override
|
||||
public void removeLocationUpdatesWithListener(ILocationListener listener)
|
||||
throws RemoteException {
|
||||
Log.d(TAG, "removeLocationUpdatesWithListener: " + listener);
|
||||
getLocationManager().removeLocationUpdates(listener, null);
|
||||
getLocationManager().removeLocationUpdates(listener, PackageUtils.packageFromProcessId(context, Binder.getCallingPid()));
|
||||
}
|
||||
|
||||
@Override
|
||||
public void removeLocationUpdatesWithIntent(PendingIntent callbackIntent)
|
||||
throws RemoteException {
|
||||
Log.d(TAG, "removeLocationUpdatesWithIntent: " + callbackIntent);
|
||||
getLocationManager().removeLocationUpdates(callbackIntent, null);
|
||||
getLocationManager().removeLocationUpdates(callbackIntent, PackageUtils.packageFromPendingIntent(callbackIntent));
|
||||
}
|
||||
|
||||
@Override
|
||||
@ -226,12 +234,14 @@ public class GoogleLocationManagerServiceImpl extends IGoogleLocationManagerServ
|
||||
public void requestLocationUpdatesWithPackage(LocationRequest request, ILocationListener listener,
|
||||
String packageName) throws RemoteException {
|
||||
Log.d(TAG, "requestLocationUpdatesWithPackage: " + request);
|
||||
PackageUtils.checkPackageUid(context, packageName, Binder.getCallingUid());
|
||||
getLocationManager().requestLocationUpdates(request, listener, packageName);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Location getLastLocationWithPackage(String packageName) throws RemoteException {
|
||||
Log.d(TAG, "getLastLocationWithPackage: " + packageName);
|
||||
PackageUtils.checkPackageUid(context, packageName, Binder.getCallingUid());
|
||||
return getLocationManager().getLastLocation(packageName);
|
||||
}
|
||||
|
||||
@ -248,6 +258,7 @@ public class GoogleLocationManagerServiceImpl extends IGoogleLocationManagerServ
|
||||
@Override
|
||||
public LocationAvailability getLocationAvailabilityWithPackage(String packageName) throws RemoteException {
|
||||
Log.d(TAG, "getLocationAvailabilityWithPackage: " + packageName);
|
||||
PackageUtils.checkPackageUid(context, packageName, Binder.getCallingUid());
|
||||
return new LocationAvailability();
|
||||
}
|
||||
|
||||
@ -295,6 +306,7 @@ public class GoogleLocationManagerServiceImpl extends IGoogleLocationManagerServ
|
||||
@Override
|
||||
public void requestLocationSettingsDialog(LocationSettingsRequest settingsRequest, ISettingsCallbacks callback, String packageName) throws RemoteException {
|
||||
Log.d(TAG, "requestLocationSettingsDialog: " + settingsRequest);
|
||||
PackageUtils.checkPackageUid(context, packageName, Binder.getCallingUid());
|
||||
callback.onLocationSettingsResult(new LocationSettingsResult(new LocationSettingsStates(true, true, false, true, true, false), Status.CANCELED));
|
||||
}
|
||||
|
||||
@ -302,14 +314,14 @@ public class GoogleLocationManagerServiceImpl extends IGoogleLocationManagerServ
|
||||
public void requestLocationUpdatesInternalWithListener(LocationRequestInternal request,
|
||||
ILocationListener listener) throws RemoteException {
|
||||
Log.d(TAG, "requestLocationUpdatesInternalWithListener: " + request);
|
||||
getLocationManager().requestLocationUpdates(request.request, listener, null);
|
||||
getLocationManager().requestLocationUpdates(request.request, listener, PackageUtils.packageFromProcessId(context, Binder.getCallingPid()));
|
||||
}
|
||||
|
||||
@Override
|
||||
public void requestLocationUpdatesInternalWithIntent(LocationRequestInternal request,
|
||||
PendingIntent callbackIntent) throws RemoteException {
|
||||
Log.d(TAG, "requestLocationUpdatesInternalWithIntent: " + request);
|
||||
getLocationManager().requestLocationUpdates(request.request, callbackIntent, null);
|
||||
getLocationManager().requestLocationUpdates(request.request, callbackIntent, PackageUtils.packageFromPendingIntent(callbackIntent));
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -99,6 +99,10 @@ public class GcmAppFragment extends ResourceSettingsFragment {
|
||||
|
||||
private void updateAppDetails() {
|
||||
GcmDatabase.App app = database.getApp(packageName);
|
||||
if (app == null) {
|
||||
getActivity().finish();
|
||||
return;
|
||||
}
|
||||
PreferenceScreen root = getPreferenceScreen();
|
||||
|
||||
SwitchPreference wakeForDelivery = (SwitchPreference) root.findPreference(PREF_WAKE_FOR_DELIVERY);
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (C) 2013-2017 microG Project Team
|
||||
* Copyright (C) 2013-2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@ -46,12 +46,12 @@ import com.google.android.gms.maps.model.LatLng;
|
||||
import com.google.android.gms.maps.model.LatLngBounds;
|
||||
|
||||
import org.microg.gms.location.LocationConstants;
|
||||
import org.microg.gms.maps.BackendMapView;
|
||||
import org.microg.gms.maps.GmsMapsTypeHelper;
|
||||
//import org.microg.gms.maps.vtm.BackendMapView;
|
||||
//import org.microg.gms.maps.vtm.GmsMapsTypeHelper;
|
||||
import org.microg.safeparcel.SafeParcelUtil;
|
||||
import org.oscim.core.MapPosition;
|
||||
import org.oscim.event.Event;
|
||||
import org.oscim.map.Map;
|
||||
//import org.oscim.core.MapPosition;
|
||||
//import org.oscim.event.Event;
|
||||
//import org.oscim.map.Map;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.concurrent.atomic.AtomicBoolean;
|
||||
@ -61,13 +61,16 @@ import static android.Manifest.permission.ACCESS_FINE_LOCATION;
|
||||
import static android.content.pm.PackageManager.PERMISSION_GRANTED;
|
||||
import static org.microg.gms.location.LocationConstants.EXTRA_PRIMARY_COLOR;
|
||||
import static org.microg.gms.location.LocationConstants.EXTRA_PRIMARY_COLOR_DARK;
|
||||
import static org.microg.gms.maps.GmsMapsTypeHelper.fromLatLngBounds;
|
||||
//import static org.microg.gms.maps.vtm.GmsMapsTypeHelper.fromLatLngBounds;
|
||||
|
||||
public class PlacePickerActivity extends AppCompatActivity implements Map.UpdateListener {
|
||||
public class
|
||||
|
||||
|
||||
PlacePickerActivity extends AppCompatActivity /*implements Map.UpdateListener*/ {
|
||||
private static final String TAG = "GmsPlacePicker";
|
||||
|
||||
private PlaceImpl place;
|
||||
private BackendMapView mapView;
|
||||
// private BackendMapView mapView;
|
||||
private Intent resultIntent;
|
||||
private AtomicBoolean geocoderInProgress = new AtomicBoolean(false);
|
||||
|
||||
@ -91,17 +94,17 @@ public class PlacePickerActivity extends AppCompatActivity implements Map.Update
|
||||
((TextView) findViewById(R.id.place_picker_title)).setTextColor(getIntent().getIntExtra(EXTRA_PRIMARY_COLOR_DARK, 0));
|
||||
}
|
||||
|
||||
mapView = (BackendMapView) findViewById(R.id.map);
|
||||
mapView.map().getEventLayer().enableRotation(false);
|
||||
mapView.map().getEventLayer().enableTilt(false);
|
||||
mapView.map().events.bind(this);
|
||||
// mapView = (BackendMapView) findViewById(R.id.map);
|
||||
// mapView.map().getEventLayer().enableRotation(false);
|
||||
// mapView.map().getEventLayer().enableTilt(false);
|
||||
// mapView.map().events.bind(this);
|
||||
|
||||
LatLngBounds latLngBounds = getIntent().getParcelableExtra(LocationConstants.EXTRA_BOUNDS);
|
||||
if (latLngBounds != null) {
|
||||
place.viewport = latLngBounds;
|
||||
MapPosition mp = new MapPosition();
|
||||
mp.setByBoundingBox(fromLatLngBounds(latLngBounds), mapView.map().getWidth(), mapView.map().getHeight());
|
||||
mapView.map().getMapPosition(mp);
|
||||
// MapPosition mp = new MapPosition();
|
||||
// mp.setByBoundingBox(fromLatLngBounds(latLngBounds), mapView.map().getWidth(), mapView.map().getHeight());
|
||||
// mapView.map().getMapPosition(mp);
|
||||
} else {
|
||||
if (ActivityCompat.checkSelfPermission(PlacePickerActivity.this, ACCESS_FINE_LOCATION) != PERMISSION_GRANTED) {
|
||||
ActivityCompat.requestPermissions(PlacePickerActivity.this, new String[]{ACCESS_COARSE_LOCATION, ACCESS_FINE_LOCATION}, 0);
|
||||
@ -136,7 +139,7 @@ public class PlacePickerActivity extends AppCompatActivity implements Map.Update
|
||||
}
|
||||
Log.d(TAG, "Set location to " + last);
|
||||
if (last != null) {
|
||||
mapView.map().setMapPosition(new MapPosition(last.getLatitude(), last.getLongitude(), 4096));
|
||||
// mapView.map().setMapPosition(new MapPosition(last.getLatitude(), last.getLongitude(), 4096));
|
||||
}
|
||||
}
|
||||
|
||||
@ -163,12 +166,12 @@ public class PlacePickerActivity extends AppCompatActivity implements Map.Update
|
||||
@Override
|
||||
protected void onResume() {
|
||||
super.onResume();
|
||||
mapView.onResume();
|
||||
// mapView.onResume();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onPause() {
|
||||
mapView.onPause();
|
||||
// mapView.onPause();
|
||||
super.onPause();
|
||||
}
|
||||
|
||||
@ -186,11 +189,12 @@ public class PlacePickerActivity extends AppCompatActivity implements Map.Update
|
||||
super.onDestroy();
|
||||
}
|
||||
|
||||
/*
|
||||
@Override
|
||||
public void onMapEvent(Event event, MapPosition position) {
|
||||
place.viewport = GmsMapsTypeHelper.toLatLngBounds(mapView.map().viewport().getBBox(null, 0));
|
||||
resultIntent.putExtra(LocationConstants.EXTRA_FINAL_BOUNDS, place.viewport);
|
||||
place.latLng = GmsMapsTypeHelper.toLatLng(position.getGeoPoint());
|
||||
// place.viewport = GmsMapsTypeHelper.toLatLngBounds(mapView.map().viewport().getBBox(null, 0));
|
||||
// resultIntent.putExtra(LocationConstants.EXTRA_FINAL_BOUNDS, place.viewport);
|
||||
// place.latLng = GmsMapsTypeHelper.toLatLng(position.getGeoPoint());
|
||||
place.name = "";
|
||||
place.address = "";
|
||||
updateInfoText();
|
||||
@ -235,7 +239,7 @@ public class PlacePickerActivity extends AppCompatActivity implements Map.Update
|
||||
}
|
||||
}).start();
|
||||
}
|
||||
}
|
||||
}*/
|
||||
|
||||
private void updateInfoText() {
|
||||
if (TextUtils.isEmpty(place.address)) {
|
||||
|
@ -0,0 +1,13 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="24dp"
|
||||
android:height="24dp"
|
||||
android:viewportWidth="24"
|
||||
android:viewportHeight="24">
|
||||
|
||||
<path
|
||||
android:pathData="M0,0 L24,0 L24,24 L0,24 Z" />
|
||||
<path
|
||||
android:fillColor="#ff000000"
|
||||
android:pathData="M15,12 C17.21,12,19,10.21,19,8 S17.21,4,15,4 S11,5.79,11,8 S12.79,12,15,12 Z M6,10 L6,7 L4,7 L4,10 L1,10 L1,12 L4,12 L4,15 L6,15 L6,12 L9,12 L9,10 L6,10 Z M15,14 C12.33,14,7,15.34,7,18 L7,20 L23,20 L23,18 C23,15.34,17.67,14,15,14 Z" />
|
||||
</vector>
|
BIN
play-services-core/src/main/res/drawable-ldpi/add_account.png
Normal file
After Width: | Height: | Size: 169 B |
BIN
play-services-core/src/main/res/drawable-mdpi/add_account.png
Normal file
After Width: | Height: | Size: 195 B |
BIN
play-services-core/src/main/res/drawable-xhdpi/add_account.png
Normal file
After Width: | Height: | Size: 328 B |
BIN
play-services-core/src/main/res/drawable-xxhdpi/add_account.png
Normal file
After Width: | Height: | Size: 428 B |
BIN
play-services-core/src/main/res/drawable-xxxhdpi/add_account.png
Normal file
After Width: | Height: | Size: 586 B |
@ -37,7 +37,7 @@
|
||||
android:layout_marginLeft="15dip"
|
||||
android:layout_marginRight="6dip">
|
||||
|
||||
<TextView android:id="@+android:id/title"
|
||||
<TextView android:id="@android:id/title"
|
||||
android:gravity="center"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
|
@ -27,7 +27,7 @@
|
||||
android:layout_height="0dip"
|
||||
android:layout_weight="1">
|
||||
|
||||
<org.microg.gms.maps.BackendMapView
|
||||
<!-- <org.microg.gms.maps.vtm.BackendMapView
|
||||
android:id="@+id/map"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"/>
|
||||
@ -37,7 +37,7 @@
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_centerInParent="true"
|
||||
android:paddingBottom="41dip"
|
||||
android:src="@drawable/maps_default_marker"/>
|
||||
android:src="@drawable/maps_default_marker"/>-->
|
||||
</RelativeLayout>
|
||||
|
||||
<LinearLayout
|
||||
@ -130,4 +130,4 @@
|
||||
</RelativeLayout>
|
||||
</LinearLayout>
|
||||
|
||||
</LinearLayout>
|
||||
</LinearLayout>
|
||||
|
@ -125,6 +125,8 @@ Dies kann einige Minuten dauern."</string>
|
||||
|
||||
<string name="pref_more_settings">Mehr</string>
|
||||
|
||||
<string name="pref_add_account_title">Konto</string>
|
||||
<string name="pref_add_account_summary">Google Konto hinzufügen</string>
|
||||
<string name="pref_gcm_enable_mcs_summary">Google Cloud Messaging ist ein Push-Nachrichten-Dienst, der von vielen Apps genutzt wird. Zur Benutzung muss Geräte Check-In aktiviert werden.</string>
|
||||
<string name="pref_gcm_apps_title">Apps die Cloud Messaging benutzen</string>
|
||||
<string name="pref_gcm_confirm_new_apps_title">Neue Apps bestätigen</string>
|
||||
|
@ -133,6 +133,8 @@
|
||||
|
||||
<string name="pref_more_settings">Ещё</string>
|
||||
|
||||
<string name="pref_add_account_title">Аккаунт</string>
|
||||
<string name="pref_add_account_summary">Добавить аккаунт Google</string>
|
||||
<string name="pref_gcm_enable_mcs_summary">Google Cloud Messaging предоставляет push-уведомления, которые используются во многих в сторонних приложениях. Чтобы использовать их, вы должны включить регистрацию устройства.</string>
|
||||
<string name="pref_gcm_heartbeat_title">Интервал соединения Cloud Messaging</string>
|
||||
<string name="pref_gcm_heartbeat_summary">"Интервал в секундах, для использования серверов Google. Увеличение этого числа сократит потребление батареи, но может привести к задержкам push-сообщений.\nУстарело, будет изменено в следующем релизе."</string>
|
||||
|
@ -133,6 +133,8 @@ This can take a couple of minutes."</string>
|
||||
|
||||
<string name="pref_more_settings">More</string>
|
||||
|
||||
<string name="pref_add_account_title">Account</string>
|
||||
<string name="pref_add_account_summary">Add Google account</string>
|
||||
<string name="pref_gcm_enable_mcs_summary">Google Cloud Messaging is a push notification provider used by many third-party applications. To use it you must enable device registration.</string>
|
||||
<string name="pref_gcm_heartbeat_title">Cloud Messaging heartbeat interval</string>
|
||||
<string name="pref_gcm_heartbeat_summary">The interval in seconds for the system to heartbeat the Google servers. Increasing this number will reduce battery consumption, but might cause delays on push messages.\nDeprecated, will be replaced in future release.</string>
|
||||
|
@ -26,6 +26,14 @@
|
||||
</org.microg.tools.ui.TintIconPreference>
|
||||
</PreferenceCategory>
|
||||
<PreferenceCategory android:title="@string/prefcat_google_services">
|
||||
<org.microg.tools.ui.TintIconPreference
|
||||
android:icon="@drawable/add_account"
|
||||
android:summary="@string/pref_add_account_summary"
|
||||
android:title="@string/pref_add_account_title">
|
||||
<intent
|
||||
android:targetClass="org.microg.gms.auth.login.LoginActivity"
|
||||
android:targetPackage="com.google.android.gms"/>
|
||||
</org.microg.tools.ui.TintIconPreference>
|
||||
<org.microg.tools.ui.TintIconPreference
|
||||
android:icon="@drawable/device_login"
|
||||
android:key="pref_checkin"
|
||||
|
83
play-services-maps-core-mapbox/build.gradle
Normal file
@ -0,0 +1,83 @@
|
||||
/*
|
||||
* Copyright 2013-2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
apply plugin: 'com.android.library'
|
||||
apply plugin: 'kotlin-android-extensions'
|
||||
apply plugin: 'kotlin-android'
|
||||
|
||||
dependencies {
|
||||
implementation project(':play-services-api')
|
||||
implementation "com.mapbox.mapboxsdk:mapbox-android-sdk:7.3.0"
|
||||
implementation "com.mapbox.mapboxsdk:mapbox-android-plugin-annotation-v7:0.6.0"
|
||||
implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk7:$kotlin_version"
|
||||
}
|
||||
|
||||
def execResult(...args) {
|
||||
def stdout = new ByteArrayOutputStream()
|
||||
exec {
|
||||
commandLine args
|
||||
standardOutput = stdout
|
||||
}
|
||||
return stdout.toString().trim()
|
||||
}
|
||||
|
||||
def mapboxKey() {
|
||||
Properties properties = new Properties()
|
||||
properties.load(project.rootProject.file('local.properties').newDataInputStream())
|
||||
return properties.getProperty("mapbox.key", "invalid")
|
||||
}
|
||||
|
||||
android {
|
||||
compileSdkVersion androidCompileSdk()
|
||||
buildToolsVersion "$androidBuildVersionTools"
|
||||
|
||||
defaultConfig {
|
||||
versionName "temp"
|
||||
versionCode 1
|
||||
|
||||
minSdkVersion androidMinSdk()
|
||||
targetSdkVersion androidTargetSdk()
|
||||
buildConfigField "String", "MAPBOX_KEY", "\"${mapboxKey()}\""
|
||||
|
||||
ndk {
|
||||
abiFilters "armeabi", "armeabi-v7a", "arm64-v8a", "x86", "x86_64"
|
||||
}
|
||||
}
|
||||
|
||||
sourceSets {
|
||||
main.java.srcDirs += 'src/main/kotlin'
|
||||
}
|
||||
|
||||
lintOptions {
|
||||
disable 'GradleCompatible'
|
||||
}
|
||||
|
||||
buildTypes {
|
||||
release {
|
||||
minifyEnabled true
|
||||
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
|
||||
}
|
||||
}
|
||||
|
||||
compileOptions {
|
||||
sourceCompatibility JavaVersion.VERSION_1_8
|
||||
targetCompatibility JavaVersion.VERSION_1_8
|
||||
}
|
||||
}
|
||||
|
||||
if (file('user.gradle').exists()) {
|
||||
apply from: 'user.gradle'
|
||||
}
|
34
play-services-maps-core-mapbox/src/main/AndroidManifest.xml
Normal file
@ -0,0 +1,34 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<!--
|
||||
~ Copyright (C) 2013-2019 microG Project Team
|
||||
~
|
||||
~ Licensed under the Apache License, Version 2.0 (the "License");
|
||||
~ you may not use this file except in compliance with the License.
|
||||
~ You may obtain a copy of the License at
|
||||
~
|
||||
~ http://www.apache.org/licenses/LICENSE-2.0
|
||||
~
|
||||
~ Unless required by applicable law or agreed to in writing, software
|
||||
~ distributed under the License is distributed on an "AS IS" BASIS,
|
||||
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
~ See the License for the specific language governing permissions and
|
||||
~ limitations under the License.
|
||||
-->
|
||||
<manifest package="org.microg.gms.maps.mapbox"
|
||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:tools="http://schemas.android.com/tools">
|
||||
|
||||
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>
|
||||
<uses-permission android:name="android.permission.INTERNET"/>
|
||||
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION"/>
|
||||
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>
|
||||
<uses-permission android:name="android.permission.READ_PHONE_STATE"/>
|
||||
<uses-permission android:name="android.permission.WAKE_LOCK"/>
|
||||
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
|
||||
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
|
||||
<uses-permission android:name="android.permission.REQUEST_IGNORE_BATTERY_OPTIMIZATIONS"/>
|
||||
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED"/>
|
||||
|
||||
<application />
|
||||
|
||||
</manifest>
|
@ -0,0 +1,79 @@
|
||||
/*
|
||||
* Copyright (C) 2013-2017 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package com.google.android.gms.maps.internal;
|
||||
|
||||
import android.app.Activity;
|
||||
import android.content.Context;
|
||||
import android.content.res.Resources;
|
||||
import android.os.Parcel;
|
||||
import android.os.RemoteException;
|
||||
import android.support.annotation.Keep;
|
||||
import android.util.Log;
|
||||
|
||||
import com.google.android.gms.dynamic.IObjectWrapper;
|
||||
import com.google.android.gms.dynamic.ObjectWrapper;
|
||||
import com.google.android.gms.maps.GoogleMapOptions;
|
||||
import com.google.android.gms.maps.model.internal.IBitmapDescriptorFactoryDelegate;
|
||||
|
||||
import org.microg.gms.maps.mapbox.CameraUpdateFactoryImpl;
|
||||
import org.microg.gms.maps.mapbox.MapFragmentImpl;
|
||||
import org.microg.gms.maps.mapbox.MapViewImpl;
|
||||
import org.microg.gms.maps.mapbox.model.BitmapDescriptorFactoryImpl;
|
||||
|
||||
@Keep
|
||||
public class CreatorImpl extends ICreator.Stub {
|
||||
private static final String TAG = "GmsMapCreator";
|
||||
|
||||
@Override
|
||||
public void init(IObjectWrapper resources) {
|
||||
initV2(resources, 0);
|
||||
}
|
||||
|
||||
@Override
|
||||
public IMapFragmentDelegate newMapFragmentDelegate(IObjectWrapper activity) {
|
||||
return new MapFragmentImpl(ObjectWrapper.unwrapTyped(activity, Activity.class));
|
||||
}
|
||||
|
||||
@Override
|
||||
public IMapViewDelegate newMapViewDelegate(IObjectWrapper context, GoogleMapOptions options) {
|
||||
return new MapViewImpl(ObjectWrapper.unwrapTyped(context, Context.class), options);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ICameraUpdateFactoryDelegate newCameraUpdateFactoryDelegate() {
|
||||
return new CameraUpdateFactoryImpl();
|
||||
}
|
||||
|
||||
@Override
|
||||
public IBitmapDescriptorFactoryDelegate newBitmapDescriptorFactoryDelegate() {
|
||||
return BitmapDescriptorFactoryImpl.INSTANCE;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void initV2(IObjectWrapper resources, int flags) {
|
||||
BitmapDescriptorFactoryImpl.INSTANCE.initialize(ObjectWrapper.unwrapTyped(resources, Resources.class));
|
||||
//ResourcesContainer.set((Resources) ObjectWrapper.unwrap(resources));
|
||||
Log.d(TAG, "initV2");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean onTransact(int code, Parcel data, Parcel reply, int flags) throws RemoteException {
|
||||
if (super.onTransact(code, data, reply, flags)) return true;
|
||||
Log.d(TAG, "onTransact [unknown]: " + code + ", " + data + ", " + flags);
|
||||
return false;
|
||||
}
|
||||
}
|
@ -0,0 +1,83 @@
|
||||
/*
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.mapbox
|
||||
|
||||
import com.mapbox.mapboxsdk.camera.CameraPosition
|
||||
import com.mapbox.mapboxsdk.camera.CameraUpdate
|
||||
import com.mapbox.mapboxsdk.geometry.LatLngBounds
|
||||
import com.mapbox.mapboxsdk.maps.MapboxMap
|
||||
import java.util.*
|
||||
|
||||
internal class CameraBoundsWithSizeUpdate(val bounds: LatLngBounds, val width: Int, val height: Int, val padding: IntArray) : CameraUpdate {
|
||||
|
||||
constructor(bounds: LatLngBounds, width: Int, height: Int, paddingLeft: Int, paddingTop: Int = paddingLeft, paddingRight: Int = paddingLeft, paddingBottom: Int = paddingTop) : this(bounds, width, height, intArrayOf(paddingLeft, paddingTop, paddingRight, paddingBottom)) {}
|
||||
|
||||
override fun getCameraPosition(map: MapboxMap): CameraPosition? {
|
||||
val padding = this.padding.clone()
|
||||
val widthPad = (map.padding[0] + map.padding[2])/2
|
||||
val heightPad = (map.padding[1] + map.padding[3])/2
|
||||
padding[0] += widthPad
|
||||
padding[1] += heightPad
|
||||
padding[2] += widthPad
|
||||
padding[3] += heightPad
|
||||
return map.getCameraForLatLngBounds(bounds, padding)
|
||||
}
|
||||
|
||||
override fun equals(other: Any?): Boolean {
|
||||
if (this === other) {
|
||||
return true
|
||||
}
|
||||
if (other == null || other !is CameraBoundsWithSizeUpdate?) {
|
||||
return false
|
||||
}
|
||||
|
||||
val that = other as CameraBoundsWithSizeUpdate? ?: return false
|
||||
|
||||
if (bounds != that.bounds) {
|
||||
return false
|
||||
}
|
||||
|
||||
if (Arrays.equals(padding, that.padding)) {
|
||||
return false
|
||||
}
|
||||
|
||||
if (height != that.height || width != that.width) {
|
||||
return false
|
||||
}
|
||||
|
||||
return true
|
||||
}
|
||||
|
||||
override fun hashCode(): Int {
|
||||
var result = bounds.hashCode()
|
||||
result = 31 * result + Arrays.hashCode(padding)
|
||||
result = 31 * result + height.hashCode()
|
||||
result = 31 * result + width.hashCode()
|
||||
return result
|
||||
}
|
||||
|
||||
override fun toString(): String {
|
||||
return ("CameraBoundsWithSizeUpdate{"
|
||||
+ "bounds=" + bounds
|
||||
+ ", padding=" + Arrays.toString(padding)
|
||||
+ '}'.toString())
|
||||
}
|
||||
|
||||
companion object {
|
||||
val TAG = "GmsCameraBounds"
|
||||
}
|
||||
}
|
@ -0,0 +1,87 @@
|
||||
/*
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.mapbox
|
||||
|
||||
import android.graphics.Point
|
||||
import android.os.Parcel
|
||||
import android.util.Log
|
||||
import com.google.android.gms.dynamic.IObjectWrapper
|
||||
import com.google.android.gms.dynamic.ObjectWrapper
|
||||
import com.google.android.gms.maps.internal.ICameraUpdateFactoryDelegate
|
||||
import com.google.android.gms.maps.model.CameraPosition
|
||||
import com.google.android.gms.maps.model.LatLng
|
||||
import com.google.android.gms.maps.model.LatLngBounds
|
||||
import com.mapbox.mapboxsdk.camera.CameraUpdate
|
||||
import com.mapbox.mapboxsdk.camera.CameraUpdateFactory
|
||||
import com.mapbox.mapboxsdk.maps.MapboxMap
|
||||
import org.microg.gms.maps.mapbox.utils.toMapbox
|
||||
|
||||
class CameraUpdateFactoryImpl : ICameraUpdateFactoryDelegate.Stub() {
|
||||
|
||||
override fun zoomIn(): IObjectWrapper = ObjectWrapper.wrap(CameraUpdateFactory.zoomIn())
|
||||
override fun zoomOut(): IObjectWrapper = ObjectWrapper.wrap(CameraUpdateFactory.zoomOut())
|
||||
|
||||
override fun zoomTo(zoom: Float): IObjectWrapper =
|
||||
ObjectWrapper.wrap(CameraUpdateFactory.zoomTo(zoom.toDouble() - 1.0))
|
||||
|
||||
override fun zoomBy(zoomDelta: Float): IObjectWrapper =
|
||||
ObjectWrapper.wrap(CameraUpdateFactory.zoomBy(zoomDelta.toDouble()))
|
||||
|
||||
override fun zoomByWithFocus(zoomDelta: Float, x: Int, y: Int): IObjectWrapper =
|
||||
ObjectWrapper.wrap(CameraUpdateFactory.zoomBy(zoomDelta.toDouble(), Point(x, y)))
|
||||
|
||||
override fun newCameraPosition(cameraPosition: CameraPosition): IObjectWrapper =
|
||||
ObjectWrapper.wrap(CameraUpdateFactory.newCameraPosition(cameraPosition.toMapbox()))
|
||||
|
||||
override fun newLatLng(latLng: LatLng): IObjectWrapper =
|
||||
ObjectWrapper.wrap(CameraUpdateFactory.newLatLng(latLng.toMapbox()))
|
||||
|
||||
override fun newLatLngZoom(latLng: LatLng, zoom: Float): IObjectWrapper =
|
||||
ObjectWrapper.wrap(CameraUpdateFactory.newLatLngZoom(latLng.toMapbox(), zoom.toDouble() - 1.0))
|
||||
|
||||
override fun newLatLngBounds(bounds: LatLngBounds, padding: Int): IObjectWrapper =
|
||||
ObjectWrapper.wrap(CameraUpdateFactory.newLatLngBounds(bounds.toMapbox(), padding))
|
||||
|
||||
override fun scrollBy(x: Float, y: Float): IObjectWrapper {
|
||||
Log.d(TAG, "unimplemented Method: scrollBy")
|
||||
return ObjectWrapper.wrap(NoCameraUpdate())
|
||||
}
|
||||
|
||||
override fun newLatLngBoundsWithSize(bounds: LatLngBounds, width: Int, height: Int, padding: Int): IObjectWrapper {
|
||||
Log.d(TAG, "unimplemented Method: newLatLngBoundsWithSize")
|
||||
|
||||
return ObjectWrapper.wrap(CameraBoundsWithSizeUpdate(bounds.toMapbox(), width, height, padding))
|
||||
}
|
||||
|
||||
override fun onTransact(code: Int, data: Parcel?, reply: Parcel?, flags: Int): Boolean =
|
||||
if (super.onTransact(code, data, reply, flags)) {
|
||||
true
|
||||
} else {
|
||||
Log.d(TAG, "onTransact [unknown]: $code, $data, $flags"); false
|
||||
}
|
||||
|
||||
private inner class NoCameraUpdate : CameraUpdate {
|
||||
override fun getCameraPosition(mapboxMap: MapboxMap): com.mapbox.mapboxsdk.camera.CameraPosition? =
|
||||
mapboxMap.cameraPosition
|
||||
}
|
||||
|
||||
companion object {
|
||||
private val TAG = "GmsCameraUpdate"
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -0,0 +1,479 @@
|
||||
/*
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.mapbox
|
||||
|
||||
import android.content.Context
|
||||
import android.location.Location
|
||||
import android.os.Bundle
|
||||
import android.os.Parcel
|
||||
import android.os.RemoteException
|
||||
import android.support.annotation.IdRes
|
||||
import android.support.annotation.Keep
|
||||
import android.support.v4.util.LongSparseArray
|
||||
import android.util.DisplayMetrics
|
||||
import android.util.Log
|
||||
import android.view.View
|
||||
import android.widget.FrameLayout
|
||||
import com.google.android.gms.dynamic.IObjectWrapper
|
||||
import com.google.android.gms.maps.GoogleMapOptions
|
||||
import com.google.android.gms.maps.internal.*
|
||||
import com.google.android.gms.maps.model.*
|
||||
import com.google.android.gms.maps.model.CircleOptions
|
||||
import com.google.android.gms.maps.model.internal.*
|
||||
import com.mapbox.mapboxsdk.LibraryLoader
|
||||
import com.mapbox.mapboxsdk.Mapbox
|
||||
import com.mapbox.mapboxsdk.R
|
||||
import com.mapbox.mapboxsdk.camera.CameraUpdate
|
||||
import com.mapbox.mapboxsdk.maps.MapView
|
||||
import com.mapbox.mapboxsdk.maps.MapboxMap
|
||||
import com.mapbox.mapboxsdk.maps.Style
|
||||
import com.mapbox.mapboxsdk.plugins.annotation.*
|
||||
import com.mapbox.mapboxsdk.plugins.annotation.Annotation
|
||||
import com.mapbox.mapboxsdk.style.layers.Property.LINE_CAP_ROUND
|
||||
import com.mapbox.mapboxsdk.utils.ColorUtils
|
||||
import org.microg.gms.kotlin.unwrap
|
||||
import org.microg.gms.maps.MapsConstants.*
|
||||
import org.microg.gms.maps.mapbox.model.*
|
||||
import org.microg.gms.maps.mapbox.utils.MapContext
|
||||
import org.microg.gms.maps.mapbox.utils.MultiArchLoader
|
||||
import org.microg.gms.maps.mapbox.utils.toGms
|
||||
import org.microg.gms.maps.mapbox.utils.toMapbox
|
||||
|
||||
fun <T : Any> LongSparseArray<T>.values() = (0..size()).map { valueAt(it) }.mapNotNull { it }
|
||||
|
||||
class GoogleMapImpl(private val context: Context, private val options: GoogleMapOptions) : IGoogleMapDelegate.Stub() {
|
||||
|
||||
val view: FrameLayout
|
||||
var map: MapboxMap? = null
|
||||
private set
|
||||
val dpiFactor: Float
|
||||
get() = context.resources.displayMetrics.densityDpi.toFloat() / DisplayMetrics.DENSITY_DEFAULT
|
||||
|
||||
private var mapView: MapView?
|
||||
private var initialized = false
|
||||
private val initializedCallbackList = mutableListOf<IOnMapReadyCallback>()
|
||||
private val mapLock = Object()
|
||||
val markers = mutableMapOf<Long, MarkerImpl>()
|
||||
|
||||
private var cameraChangeListener: IOnCameraChangeListener? = null
|
||||
private var cameraMoveListener: IOnCameraMoveListener? = null
|
||||
private var cameraMoveCanceledListener: IOnCameraMoveCanceledListener? = null
|
||||
private var cameraMoveStartedListener: IOnCameraMoveStartedListener? = null
|
||||
private var cameraIdleListener: IOnCameraIdleListener? = null
|
||||
private var mapClickListener: IOnMapClickListener? = null
|
||||
private var mapLongClickListener: IOnMapLongClickListener? = null
|
||||
private var markerClickListener: IOnMarkerClickListener? = null
|
||||
private var markerDragListener: IOnMarkerDragListener? = null
|
||||
|
||||
var circleManager: CircleManager? = null
|
||||
var lineManager: LineManager? = null
|
||||
var fillManager: FillManager? = null
|
||||
var symbolManager: SymbolManager? = null
|
||||
var storedMapType: Int = MAP_TYPE_NORMAL
|
||||
|
||||
init {
|
||||
val mapContext = MapContext(context)
|
||||
LibraryLoader.setLibraryLoader(MultiArchLoader(mapContext, context))
|
||||
Mapbox.getInstance(mapContext, BuildConfig.MAPBOX_KEY)
|
||||
|
||||
this.view = object : FrameLayout(mapContext) {
|
||||
@Keep
|
||||
fun <T : View> findViewTraversal(@IdRes id: Int): T? {
|
||||
return null
|
||||
}
|
||||
}
|
||||
this.mapView = MapView(mapContext)
|
||||
this.view.addView(this.mapView)
|
||||
}
|
||||
|
||||
override fun getCameraPosition(): CameraPosition? = map?.cameraPosition?.toGms()
|
||||
override fun getMaxZoomLevel(): Float = map?.maxZoomLevel?.toFloat() ?: 20f
|
||||
override fun getMinZoomLevel(): Float = map?.minZoomLevel?.toFloat() ?: 1f
|
||||
|
||||
override fun moveCamera(cameraUpdate: IObjectWrapper?) =
|
||||
cameraUpdate.unwrap<CameraUpdate>()?.let { map?.moveCamera(it) } ?: Unit
|
||||
|
||||
override fun animateCamera(cameraUpdate: IObjectWrapper?) =
|
||||
cameraUpdate.unwrap<CameraUpdate>()?.let { map?.animateCamera(it) } ?: Unit
|
||||
|
||||
override fun animateCameraWithCallback(cameraUpdate: IObjectWrapper?, callback: ICancelableCallback?) =
|
||||
cameraUpdate.unwrap<CameraUpdate>()?.let { map?.animateCamera(it, callback?.toMapbox()) }
|
||||
?: Unit
|
||||
|
||||
override fun animateCameraWithDurationAndCallback(cameraUpdate: IObjectWrapper?, duration: Int, callback: ICancelableCallback?) =
|
||||
cameraUpdate.unwrap<CameraUpdate>()?.let { map?.animateCamera(it, duration, callback?.toMapbox()) }
|
||||
?: Unit
|
||||
|
||||
override fun stopAnimation() = map?.cancelTransitions() ?: Unit
|
||||
|
||||
override fun addPolyline(options: PolylineOptions): IPolylineDelegate? {
|
||||
val lineOptions = LineOptions()
|
||||
.withLatLngs(options.points.map { it.toMapbox() })
|
||||
.withLineWidth(options.width / dpiFactor)
|
||||
.withLineColor(ColorUtils.colorToRgbaString(options.color))
|
||||
.withLineOpacity(if (options.isVisible) 1f else 0f)
|
||||
return lineManager?.let { PolylineImpl(this, it.create(lineOptions)) }
|
||||
}
|
||||
|
||||
|
||||
override fun addPolygon(options: PolygonOptions): IPolygonDelegate? {
|
||||
Log.d(TAG, "unimplemented Method: addPolygon")
|
||||
return null
|
||||
}
|
||||
|
||||
override fun addMarker(options: MarkerOptions): IMarkerDelegate? {
|
||||
var intBits = java.lang.Float.floatToIntBits(options.zIndex)
|
||||
if (intBits < 0) intBits = intBits xor 0x7fffffff
|
||||
|
||||
val symbolOptions = SymbolOptions()
|
||||
.withIconOpacity(if (options.isVisible) options.alpha else 0f)
|
||||
.withIconRotate(options.rotation)
|
||||
.withZIndex(intBits)
|
||||
.withDraggable(options.isDraggable)
|
||||
|
||||
options.position?.let { symbolOptions.withLatLng(it.toMapbox()) }
|
||||
options.icon?.remoteObject.unwrap<BitmapDescriptorImpl>()?.applyTo(symbolOptions, floatArrayOf(options.anchorU, options.anchorV), dpiFactor)
|
||||
|
||||
val symbol = symbolManager?.create(symbolOptions) ?: return null
|
||||
val marker = MarkerImpl(this, symbol, floatArrayOf(options.anchorU, options.anchorV), options.icon?.remoteObject.unwrap<BitmapDescriptorImpl>(), options.alpha, options.title, options.snippet)
|
||||
markers.put(symbol.id, marker)
|
||||
return marker
|
||||
}
|
||||
|
||||
override fun addGroundOverlay(options: GroundOverlayOptions): IGroundOverlayDelegate? {
|
||||
Log.d(TAG, "unimplemented Method: addGroundOverlay")
|
||||
return null
|
||||
}
|
||||
|
||||
override fun addTileOverlay(options: TileOverlayOptions): ITileOverlayDelegate? {
|
||||
Log.d(TAG, "unimplemented Method: addTileOverlay")
|
||||
return null
|
||||
}
|
||||
|
||||
override fun addCircle(options: CircleOptions): ICircleDelegate? {
|
||||
val circleOptions = com.mapbox.mapboxsdk.plugins.annotation.CircleOptions()
|
||||
.withLatLng(options.center.toMapbox())
|
||||
.withCircleColor(ColorUtils.colorToRgbaString(options.fillColor))
|
||||
.withCircleRadius(options.radius.toFloat())
|
||||
.withCircleStrokeColor(ColorUtils.colorToRgbaString(options.strokeColor))
|
||||
.withCircleStrokeWidth(options.strokeWidth / dpiFactor)
|
||||
.withCircleOpacity(if (options.isVisible) 1f else 0f)
|
||||
.withCircleStrokeOpacity(if (options.isVisible) 1f else 0f)
|
||||
|
||||
return circleManager?.let { CircleImpl(this, it.create(circleOptions)) }
|
||||
}
|
||||
|
||||
override fun clear() {
|
||||
circleManager?.let { clear(it) }
|
||||
lineManager?.let { clear(it) }
|
||||
fillManager?.let { clear(it) }
|
||||
symbolManager?.let { clear(it) }
|
||||
}
|
||||
|
||||
fun <T : Annotation<*>> clear(manager: AnnotationManager<*, T, *, *, *, *>) {
|
||||
val annotations = manager.getAnnotations()
|
||||
for (i in 0..annotations.size()) {
|
||||
val key = annotations.keyAt(i)
|
||||
val value = annotations[key];
|
||||
if (value is T) manager.delete(value)
|
||||
}
|
||||
}
|
||||
|
||||
override fun getMapType(): Int {
|
||||
return storedMapType
|
||||
}
|
||||
|
||||
override fun setMapType(type: Int) {
|
||||
storedMapType = type
|
||||
applyMapType()
|
||||
}
|
||||
|
||||
fun applyMapType() {
|
||||
val circles = circleManager?.annotations?.values()
|
||||
val lines = lineManager?.annotations?.values()
|
||||
val fills = fillManager?.annotations?.values()
|
||||
val symbols = symbolManager?.annotations?.values()
|
||||
val update: (Style) -> Unit = {
|
||||
circles?.let { circleManager?.update(it) }
|
||||
lines?.let { lineManager?.update(it) }
|
||||
fills?.let { fillManager?.update(it) }
|
||||
symbols?.let { symbolManager?.update(it) }
|
||||
}
|
||||
|
||||
when (storedMapType) {
|
||||
MAP_TYPE_NORMAL -> map?.setStyle(Style.Builder().fromUrl("mapbox://styles/microg/cjui4020201oo1fmca7yuwbor"), update)
|
||||
MAP_TYPE_SATELLITE -> map?.setStyle(Style.SATELLITE, update)
|
||||
MAP_TYPE_TERRAIN -> map?.setStyle(Style.OUTDOORS, update)
|
||||
MAP_TYPE_HYBRID -> map?.setStyle(Style.SATELLITE_STREETS, update)
|
||||
else -> map?.setStyle(Style.LIGHT, update)
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
override fun isTrafficEnabled(): Boolean {
|
||||
Log.d(TAG, "unimplemented Method: isTrafficEnabled")
|
||||
return false
|
||||
}
|
||||
|
||||
override fun setTrafficEnabled(traffic: Boolean) {
|
||||
Log.d(TAG, "unimplemented Method: setTrafficEnabled")
|
||||
|
||||
}
|
||||
|
||||
override fun isIndoorEnabled(): Boolean {
|
||||
Log.d(TAG, "unimplemented Method: isIndoorEnabled")
|
||||
return false
|
||||
}
|
||||
|
||||
override fun setIndoorEnabled(indoor: Boolean) {
|
||||
Log.d(TAG, "unimplemented Method: setIndoorEnabled")
|
||||
|
||||
}
|
||||
|
||||
override fun isMyLocationEnabled(): Boolean {
|
||||
Log.d(TAG, "unimplemented Method: isMyLocationEnabled")
|
||||
return false
|
||||
}
|
||||
|
||||
override fun setMyLocationEnabled(myLocation: Boolean) {
|
||||
Log.d(TAG, "unimplemented Method: setMyLocationEnabled")
|
||||
|
||||
}
|
||||
|
||||
override fun getMyLocation(): Location? {
|
||||
Log.d(TAG, "unimplemented Method: getMyLocation")
|
||||
return null
|
||||
}
|
||||
|
||||
override fun setLocationSource(locationSource: ILocationSourceDelegate) {
|
||||
Log.d(TAG, "unimplemented Method: setLocationSource")
|
||||
|
||||
}
|
||||
|
||||
override fun getUiSettings(): IUiSettingsDelegate? = map?.uiSettings?.let { UiSettingsImpl(it) }
|
||||
|
||||
override fun getProjection(): IProjectionDelegate? = map?.projection?.let { ProjectionImpl(it) }
|
||||
|
||||
override fun setOnCameraChangeListener(listener: IOnCameraChangeListener?) {
|
||||
cameraChangeListener = listener
|
||||
}
|
||||
|
||||
override fun setOnMapClickListener(listener: IOnMapClickListener?) {
|
||||
mapClickListener = listener
|
||||
}
|
||||
|
||||
override fun setOnMapLongClickListener(listener: IOnMapLongClickListener?) {
|
||||
mapLongClickListener = listener
|
||||
}
|
||||
|
||||
override fun setOnMarkerClickListener(listener: IOnMarkerClickListener?) {
|
||||
markerClickListener = listener
|
||||
}
|
||||
|
||||
override fun setOnMarkerDragListener(listener: IOnMarkerDragListener?) {
|
||||
markerDragListener = listener
|
||||
}
|
||||
|
||||
override fun setOnInfoWindowClickListener(listener: IOnInfoWindowClickListener?) {
|
||||
Log.d(TAG, "unimplemented Method: setOnInfoWindowClickListener")
|
||||
|
||||
}
|
||||
|
||||
override fun setInfoWindowAdapter(adapter: IInfoWindowAdapter?) {
|
||||
Log.d(TAG, "unimplemented Method: setInfoWindowAdapter")
|
||||
|
||||
}
|
||||
|
||||
override fun getTestingHelper(): IObjectWrapper? {
|
||||
Log.d(TAG, "unimplemented Method: getTestingHelper")
|
||||
return null
|
||||
}
|
||||
|
||||
override fun setOnMyLocationChangeListener(listener: IOnMyLocationChangeListener?) {
|
||||
Log.d(TAG, "unimplemented Method: setOnMyLocationChangeListener")
|
||||
|
||||
}
|
||||
|
||||
override fun setOnMyLocationButtonClickListener(listener: IOnMyLocationButtonClickListener?) {
|
||||
Log.d(TAG, "unimplemented Method: setOnMyLocationButtonClickListener")
|
||||
|
||||
}
|
||||
|
||||
override fun snapshot(callback: ISnapshotReadyCallback, bitmap: IObjectWrapper) {
|
||||
Log.d(TAG, "unimplemented Method: snapshot")
|
||||
|
||||
}
|
||||
|
||||
override fun setPadding(left: Int, top: Int, right: Int, bottom: Int) {
|
||||
Log.d(TAG, "padding: $left, $top, $right, $bottom")
|
||||
map?.setPadding(left, top, right, bottom)
|
||||
val fourDp = mapView?.context?.resources?.getDimension(R.dimen.mapbox_four_dp)?.toInt() ?: 0
|
||||
val ninetyTwoDp = mapView?.context?.resources?.getDimension(R.dimen.mapbox_ninety_two_dp)?.toInt()
|
||||
?: 0
|
||||
map?.uiSettings?.setLogoMargins(left + fourDp, top + fourDp, right + fourDp, bottom + fourDp)
|
||||
map?.uiSettings?.setCompassMargins(left + fourDp, top + fourDp, right + fourDp, bottom + fourDp)
|
||||
map?.uiSettings?.setAttributionMargins(left + ninetyTwoDp, top + fourDp, right + fourDp, bottom + fourDp)
|
||||
}
|
||||
|
||||
override fun isBuildingsEnabled(): Boolean {
|
||||
Log.d(TAG, "unimplemented Method: isBuildingsEnabled")
|
||||
return false
|
||||
}
|
||||
|
||||
override fun setBuildingsEnabled(buildings: Boolean) {
|
||||
Log.d(TAG, "unimplemented Method: setBuildingsEnabled")
|
||||
|
||||
}
|
||||
|
||||
override fun setOnMapLoadedCallback(callback: IOnMapLoadedCallback?) {
|
||||
Log.d(TAG, "unimplemented Method: setOnMapLoadedCallback")
|
||||
|
||||
}
|
||||
|
||||
override fun setCameraMoveStartedListener(listener: IOnCameraMoveStartedListener?) {
|
||||
cameraMoveStartedListener = listener
|
||||
}
|
||||
|
||||
override fun setCameraMoveListener(listener: IOnCameraMoveListener?) {
|
||||
cameraMoveListener = listener
|
||||
}
|
||||
|
||||
override fun setCameraMoveCanceledListener(listener: IOnCameraMoveCanceledListener?) {
|
||||
cameraMoveCanceledListener = listener
|
||||
}
|
||||
|
||||
override fun setCameraIdleListener(listener: IOnCameraIdleListener?) {
|
||||
cameraIdleListener = listener
|
||||
}
|
||||
|
||||
fun onCreate(savedInstanceState: Bundle) {
|
||||
mapView?.onCreate(savedInstanceState.toMapbox())
|
||||
mapView?.getMapAsync(this::initMap)
|
||||
}
|
||||
|
||||
private fun hasSymbolAt(latlng: com.mapbox.mapboxsdk.geometry.LatLng): Boolean {
|
||||
val point = map?.projection?.toScreenLocation(latlng) ?: return false
|
||||
val features = map?.queryRenderedFeatures(point, SymbolManager.ID_GEOJSON_LAYER)
|
||||
?: return false
|
||||
return !features.isEmpty()
|
||||
}
|
||||
|
||||
private fun initMap(map: MapboxMap) {
|
||||
if (this.map != null) return
|
||||
this.map = map
|
||||
|
||||
applyMapType()
|
||||
map.getStyle {
|
||||
mapView?.let { view ->
|
||||
BitmapDescriptorFactoryImpl.registerMap(map)
|
||||
circleManager = CircleManager(view, map, it)
|
||||
lineManager = LineManager(view, map, it)
|
||||
lineManager?.lineCap = LINE_CAP_ROUND
|
||||
fillManager = FillManager(view, map, it)
|
||||
symbolManager = SymbolManager(view, map, it)
|
||||
symbolManager?.iconAllowOverlap = true
|
||||
symbolManager?.addClickListener { markers[it.id]?.let { markerClickListener?.onMarkerClick(it) } }
|
||||
symbolManager?.addDragListener(object : OnSymbolDragListener {
|
||||
override fun onAnnotationDragStarted(annotation: Symbol?) {
|
||||
markers[annotation?.id]?.let { markerDragListener?.onMarkerDragStart(it) }
|
||||
}
|
||||
|
||||
override fun onAnnotationDrag(annotation: Symbol?) {
|
||||
markers[annotation?.id]?.let { markerDragListener?.onMarkerDrag(it) }
|
||||
}
|
||||
|
||||
override fun onAnnotationDragFinished(annotation: Symbol?) {
|
||||
markers[annotation?.id]?.let { markerDragListener?.onMarkerDragEnd(it) }
|
||||
}
|
||||
|
||||
})
|
||||
map.addOnCameraIdleListener { cameraChangeListener?.onCameraChange(map.cameraPosition.toGms()) }
|
||||
map.addOnCameraIdleListener { cameraIdleListener?.onCameraIdle() }
|
||||
map.addOnCameraMoveListener { cameraMoveListener?.onCameraMove() }
|
||||
map.addOnCameraMoveStartedListener { cameraMoveStartedListener?.onCameraMoveStarted(it) }
|
||||
map.addOnCameraMoveCancelListener { cameraMoveCanceledListener?.onCameraMoveCanceled() }
|
||||
map.addOnMapClickListener {
|
||||
val latlng = it
|
||||
mapClickListener?.let { if (!hasSymbolAt(latlng)) it.onMapClick(latlng.toGms()); }
|
||||
false
|
||||
}
|
||||
map.addOnMapLongClickListener {
|
||||
val latlng = it
|
||||
mapLongClickListener?.let { if (!hasSymbolAt(latlng)) it.onMapLongClick(latlng.toGms()); }
|
||||
false
|
||||
}
|
||||
|
||||
synchronized(mapLock) {
|
||||
for (callback in initializedCallbackList) {
|
||||
try {
|
||||
callback.onMapReady(this)
|
||||
} catch (e: RemoteException) {
|
||||
Log.w(TAG, e)
|
||||
}
|
||||
}
|
||||
initialized = true
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fun onResume() = mapView?.onResume()
|
||||
fun onPause() = mapView?.onPause()
|
||||
fun onDestroy() {
|
||||
circleManager?.onDestroy()
|
||||
circleManager = null
|
||||
lineManager?.onDestroy()
|
||||
lineManager = null
|
||||
fillManager?.onDestroy()
|
||||
fillManager = null
|
||||
symbolManager?.onDestroy()
|
||||
symbolManager = null
|
||||
BitmapDescriptorFactoryImpl.unregisterMap(map)
|
||||
view.removeView(mapView)
|
||||
// TODO can crash?
|
||||
mapView?.onDestroy()
|
||||
mapView = null
|
||||
}
|
||||
|
||||
fun onLowMemory() = mapView?.onLowMemory()
|
||||
fun onSaveInstanceState(outState: Bundle) {
|
||||
val newBundle = Bundle()
|
||||
mapView?.onSaveInstanceState(newBundle)
|
||||
outState.putAll(newBundle.toGms())
|
||||
}
|
||||
|
||||
fun getMapAsync(callback: IOnMapReadyCallback) {
|
||||
synchronized(mapLock) {
|
||||
if (initialized) {
|
||||
callback.onMapReady(this)
|
||||
} else {
|
||||
initializedCallbackList.add(callback)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
override fun onTransact(code: Int, data: Parcel?, reply: Parcel?, flags: Int): Boolean =
|
||||
if (super.onTransact(code, data, reply, flags)) {
|
||||
true
|
||||
} else {
|
||||
Log.d(TAG, "onTransact [unknown]: $code, $data, $flags"); false
|
||||
}
|
||||
|
||||
companion object {
|
||||
private val TAG = "GmsMap"
|
||||
}
|
||||
}
|
@ -0,0 +1,97 @@
|
||||
/*
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.mapbox
|
||||
|
||||
import android.app.Activity
|
||||
import android.os.Bundle
|
||||
import android.os.Parcel
|
||||
import android.util.Log
|
||||
import android.view.ViewGroup
|
||||
import com.google.android.gms.dynamic.IObjectWrapper
|
||||
import com.google.android.gms.dynamic.ObjectWrapper
|
||||
import com.google.android.gms.maps.GoogleMapOptions
|
||||
import com.google.android.gms.maps.internal.IGoogleMapDelegate
|
||||
import com.google.android.gms.maps.internal.IMapFragmentDelegate
|
||||
import com.google.android.gms.maps.internal.IOnMapReadyCallback
|
||||
|
||||
class MapFragmentImpl(private val activity: Activity) : IMapFragmentDelegate.Stub() {
|
||||
|
||||
private var map: GoogleMapImpl? = null
|
||||
private var options: GoogleMapOptions? = null
|
||||
|
||||
override fun onInflate(activity: IObjectWrapper, options: GoogleMapOptions, savedInstanceState: Bundle) {
|
||||
this.options = options
|
||||
}
|
||||
|
||||
override fun onCreate(savedInstanceState: Bundle) {
|
||||
if (options == null) {
|
||||
options = savedInstanceState.getParcelable("MapOptions")
|
||||
}
|
||||
if (options == null) {
|
||||
options = GoogleMapOptions()
|
||||
}
|
||||
}
|
||||
|
||||
override fun onCreateView(layoutInflater: IObjectWrapper, container: IObjectWrapper, savedInstanceState: Bundle): IObjectWrapper {
|
||||
if (map == null) {
|
||||
map = GoogleMapImpl(activity, options ?: GoogleMapOptions())
|
||||
map!!.onCreate(savedInstanceState)
|
||||
return ObjectWrapper.wrap(map!!.view)
|
||||
} else {
|
||||
val view = map!!.view
|
||||
val parent = view?.parent as ViewGroup
|
||||
parent.removeView(view)
|
||||
return ObjectWrapper.wrap(view)
|
||||
}
|
||||
}
|
||||
|
||||
override fun getMap(): IGoogleMapDelegate? = map
|
||||
override fun onResume() = map?.onResume() ?: Unit
|
||||
override fun onPause() = map?.onPause() ?: Unit
|
||||
override fun onLowMemory() = map?.onLowMemory() ?: Unit
|
||||
override fun isReady(): Boolean = this.map != null
|
||||
override fun getMapAsync(callback: IOnMapReadyCallback) = map?.getMapAsync(callback) ?: Unit
|
||||
|
||||
override fun onDestroyView() {
|
||||
map?.onDestroy()
|
||||
map = null
|
||||
}
|
||||
|
||||
override fun onDestroy() {
|
||||
map?.onDestroy()
|
||||
map = null
|
||||
options = null
|
||||
}
|
||||
|
||||
override fun onSaveInstanceState(outState: Bundle) {
|
||||
if (options != null) {
|
||||
outState.putParcelable("MapOptions", options)
|
||||
}
|
||||
map?.onSaveInstanceState(outState)
|
||||
}
|
||||
|
||||
override fun onTransact(code: Int, data: Parcel?, reply: Parcel?, flags: Int): Boolean =
|
||||
if (super.onTransact(code, data, reply, flags)) {
|
||||
true
|
||||
} else {
|
||||
Log.d(TAG, "onTransact [unknown]: $code, $data, $flags"); false
|
||||
}
|
||||
|
||||
companion object {
|
||||
private val TAG = "GmsMapFragment"
|
||||
}
|
||||
}
|
@ -0,0 +1,65 @@
|
||||
/*
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.mapbox
|
||||
|
||||
import android.content.Context
|
||||
import android.os.Bundle
|
||||
import android.os.Parcel
|
||||
import android.util.Log
|
||||
import com.google.android.gms.dynamic.IObjectWrapper
|
||||
import com.google.android.gms.dynamic.ObjectWrapper
|
||||
import com.google.android.gms.maps.GoogleMapOptions
|
||||
import com.google.android.gms.maps.internal.IGoogleMapDelegate
|
||||
import com.google.android.gms.maps.internal.IMapViewDelegate
|
||||
import com.google.android.gms.maps.internal.IOnMapReadyCallback
|
||||
|
||||
class MapViewImpl(private val context: Context, options: GoogleMapOptions?) : IMapViewDelegate.Stub() {
|
||||
private val options: GoogleMapOptions
|
||||
private var map: GoogleMapImpl? = null
|
||||
|
||||
init {
|
||||
this.options = options ?: GoogleMapOptions()
|
||||
}
|
||||
|
||||
override fun onCreate(savedInstanceState: Bundle) {
|
||||
map = GoogleMapImpl(context, options)
|
||||
map?.onCreate(savedInstanceState)
|
||||
}
|
||||
|
||||
override fun getMap(): IGoogleMapDelegate? = map
|
||||
override fun onResume() = map?.onResume() ?: Unit
|
||||
override fun onPause() = map?.onPause() ?: Unit
|
||||
override fun onDestroy() {
|
||||
map?.onDestroy()
|
||||
map = null
|
||||
}
|
||||
override fun onLowMemory() = map?.onLowMemory() ?: Unit
|
||||
override fun onSaveInstanceState(outState: Bundle) = map?.onSaveInstanceState(outState) ?: Unit
|
||||
override fun getView(): IObjectWrapper = ObjectWrapper.wrap(map?.view)
|
||||
override fun getMapAsync(callback: IOnMapReadyCallback) = map?.getMapAsync(callback) ?: Unit
|
||||
|
||||
override fun onTransact(code: Int, data: Parcel?, reply: Parcel?, flags: Int): Boolean =
|
||||
if (super.onTransact(code, data, reply, flags)) {
|
||||
true
|
||||
} else {
|
||||
Log.d(TAG, "onTransact [unknown]: $code, $data, $flags"); false
|
||||
}
|
||||
|
||||
companion object {
|
||||
private val TAG = "GmsMapView"
|
||||
}
|
||||
}
|
@ -0,0 +1,45 @@
|
||||
/*
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.mapbox
|
||||
|
||||
import android.graphics.Point
|
||||
import android.graphics.PointF
|
||||
import com.google.android.gms.dynamic.IObjectWrapper
|
||||
import com.google.android.gms.dynamic.ObjectWrapper
|
||||
import com.google.android.gms.maps.internal.IProjectionDelegate
|
||||
import com.google.android.gms.maps.model.LatLng
|
||||
import com.google.android.gms.maps.model.LatLngBounds
|
||||
import com.google.android.gms.maps.model.VisibleRegion
|
||||
import com.mapbox.mapboxsdk.maps.Projection
|
||||
import org.microg.gms.kotlin.unwrap
|
||||
import org.microg.gms.maps.mapbox.utils.toGms
|
||||
import org.microg.gms.maps.mapbox.utils.toMapbox
|
||||
|
||||
class ProjectionImpl(private val projection: Projection) : IProjectionDelegate.Stub() {
|
||||
override fun fromScreenLocation(obj: IObjectWrapper?): LatLng? =
|
||||
obj.unwrap<Point>()?.let { projection.fromScreenLocation(PointF(it)) }?.toGms()
|
||||
|
||||
override fun toScreenLocation(latLng: LatLng?): IObjectWrapper =
|
||||
ObjectWrapper.wrap(latLng?.toMapbox()?.let { projection.toScreenLocation(it) }?.let { Point(it.x.toInt(), it.y.toInt()) })
|
||||
|
||||
override fun getVisibleRegion(): VisibleRegion = try {
|
||||
projection.visibleRegion.toGms()
|
||||
} catch (e: Exception) {
|
||||
VisibleRegion(LatLngBounds(LatLng(0.0, 0.0), LatLng(0.0, 0.0)))
|
||||
}
|
||||
|
||||
}
|
@ -0,0 +1,91 @@
|
||||
/*
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.mapbox
|
||||
|
||||
import android.os.Parcel
|
||||
import android.os.RemoteException
|
||||
import android.util.Log
|
||||
|
||||
import com.google.android.gms.maps.internal.IUiSettingsDelegate
|
||||
import com.mapbox.mapboxsdk.maps.UiSettings
|
||||
|
||||
class UiSettingsImpl(private val uiSettings: UiSettings) : IUiSettingsDelegate.Stub() {
|
||||
|
||||
override fun setZoomControlsEnabled(zoom: Boolean) {
|
||||
Log.d(TAG, "unimplemented Method: setZoomControlsEnabled")
|
||||
}
|
||||
|
||||
override fun setCompassEnabled(compass: Boolean) {
|
||||
uiSettings.isCompassEnabled = compass
|
||||
}
|
||||
|
||||
override fun setMyLocationButtonEnabled(locationButton: Boolean) {
|
||||
Log.d(TAG, "unimplemented Method: setMyLocationButtonEnabled")
|
||||
|
||||
}
|
||||
|
||||
override fun setScrollGesturesEnabled(scrollGestures: Boolean) {
|
||||
uiSettings.isScrollGesturesEnabled = scrollGestures
|
||||
}
|
||||
|
||||
override fun setZoomGesturesEnabled(zoomGestures: Boolean) {
|
||||
uiSettings.isZoomGesturesEnabled = zoomGestures
|
||||
}
|
||||
|
||||
override fun setTiltGesturesEnabled(tiltGestures: Boolean) {
|
||||
uiSettings.isTiltGesturesEnabled = tiltGestures
|
||||
}
|
||||
|
||||
override fun setRotateGesturesEnabled(rotateGestures: Boolean) {
|
||||
uiSettings.isRotateGesturesEnabled = rotateGestures
|
||||
}
|
||||
|
||||
override fun setAllGesturesEnabled(gestures: Boolean) {
|
||||
uiSettings.setAllGesturesEnabled(gestures)
|
||||
}
|
||||
|
||||
override fun isZoomControlsEnabled(): Boolean {
|
||||
Log.d(TAG, "unimplemented Method: isZoomControlsEnabled")
|
||||
return false
|
||||
}
|
||||
|
||||
override fun isCompassEnabled(): Boolean = uiSettings.isCompassEnabled
|
||||
|
||||
override fun isMyLocationButtonEnabled(): Boolean {
|
||||
Log.d(TAG, "unimplemented Method: isMyLocationButtonEnabled")
|
||||
return false
|
||||
}
|
||||
|
||||
override fun isScrollGesturesEnabled(): Boolean = uiSettings.isScrollGesturesEnabled
|
||||
|
||||
override fun isZoomGesturesEnabled(): Boolean = uiSettings.isZoomGesturesEnabled
|
||||
|
||||
override fun isTiltGesturesEnabled(): Boolean = uiSettings.isTiltGesturesEnabled
|
||||
|
||||
override fun isRotateGesturesEnabled(): Boolean = uiSettings.isRotateGesturesEnabled
|
||||
|
||||
override fun onTransact(code: Int, data: Parcel?, reply: Parcel?, flags: Int): Boolean =
|
||||
if (super.onTransact(code, data, reply, flags)) {
|
||||
true
|
||||
} else {
|
||||
Log.d(TAG, "onTransact [unknown]: $code, $data, $flags"); false
|
||||
}
|
||||
|
||||
companion object {
|
||||
private val TAG = "GmsMapsUi"
|
||||
}
|
||||
}
|
@ -0,0 +1,45 @@
|
||||
/*
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.mapbox.model
|
||||
|
||||
import android.graphics.Color
|
||||
import android.graphics.PointF
|
||||
import android.util.Log
|
||||
import com.mapbox.mapboxsdk.plugins.annotation.Symbol
|
||||
import com.mapbox.mapboxsdk.plugins.annotation.SymbolOptions
|
||||
import com.mapbox.mapboxsdk.style.layers.Property.ICON_ANCHOR_TOP_LEFT
|
||||
import com.mapbox.mapboxsdk.utils.ColorUtils
|
||||
|
||||
open class BitmapDescriptorImpl(private val id: String, private val size: FloatArray) {
|
||||
open fun applyTo(options: SymbolOptions, anchor: FloatArray, dpiFactor: Float): SymbolOptions {
|
||||
return options.withIconImage(id).withIconAnchor(ICON_ANCHOR_TOP_LEFT).withIconOffset(arrayOf(-anchor[0] * size[0] / dpiFactor, -anchor[1] * size[1] / dpiFactor))
|
||||
}
|
||||
|
||||
open fun applyTo(symbol: Symbol, anchor: FloatArray, dpiFactor: Float) {
|
||||
symbol.iconAnchor = ICON_ANCHOR_TOP_LEFT
|
||||
symbol.iconOffset = PointF(-anchor[0] * size[0] / dpiFactor, -anchor[1] * size[1] / dpiFactor)
|
||||
symbol.iconImage = id
|
||||
}
|
||||
}
|
||||
|
||||
class ColorBitmapDescriptorImpl(id: String, size: FloatArray, val hue: Float) : BitmapDescriptorImpl(id, size) {
|
||||
override fun applyTo(options: SymbolOptions, anchor: FloatArray, dpiFactor: Float): SymbolOptions = super.applyTo(options, anchor, dpiFactor).withIconColor(ColorUtils.colorToRgbaString(Color.HSVToColor(floatArrayOf(hue, 1.0f, 0.5f))))
|
||||
override fun applyTo(symbol: Symbol, anchor: FloatArray, dpiFactor: Float) {
|
||||
super.applyTo(symbol, anchor, dpiFactor)
|
||||
symbol.setIconColor(Color.HSVToColor(floatArrayOf(hue, 1.0f, 0.5f)))
|
||||
}
|
||||
}
|
@ -0,0 +1,112 @@
|
||||
/*
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.mapbox.model
|
||||
|
||||
import android.content.res.Resources
|
||||
import android.graphics.Bitmap
|
||||
import android.graphics.BitmapFactory
|
||||
import android.os.Parcel
|
||||
import android.util.Log
|
||||
import com.google.android.gms.dynamic.IObjectWrapper
|
||||
import com.google.android.gms.dynamic.ObjectWrapper
|
||||
import com.google.android.gms.maps.model.internal.IBitmapDescriptorFactoryDelegate
|
||||
import com.mapbox.mapboxsdk.maps.MapboxMap
|
||||
|
||||
object BitmapDescriptorFactoryImpl : IBitmapDescriptorFactoryDelegate.Stub() {
|
||||
private val TAG = "GmsMapBitmap"
|
||||
private var resources: Resources? = null
|
||||
private val maps = hashSetOf<MapboxMap>()
|
||||
private val bitmaps = hashMapOf<String, Bitmap>()
|
||||
|
||||
fun initialize(resources: Resources) {
|
||||
BitmapDescriptorFactoryImpl.resources = resources
|
||||
}
|
||||
|
||||
fun registerMap(map: MapboxMap) {
|
||||
map.getStyle {
|
||||
it.addImages(bitmaps)
|
||||
maps.add(map)
|
||||
}
|
||||
}
|
||||
|
||||
fun unregisterMap(map: MapboxMap?) {
|
||||
maps.remove(map)
|
||||
// TODO: cleanup bitmaps?
|
||||
}
|
||||
|
||||
fun bitmapSize(id: String): FloatArray =
|
||||
bitmaps[id]?.let { floatArrayOf(it.width.toFloat(), it.height.toFloat()) }
|
||||
?: floatArrayOf(0f, 0f)
|
||||
|
||||
private fun registerBitmap(id: String, bitmapCreator: () -> Bitmap?) {
|
||||
if (bitmaps.contains(id)) return
|
||||
val bitmap = bitmapCreator() ?: return
|
||||
bitmaps[id] = bitmap
|
||||
for (map in maps) {
|
||||
map.getStyle { it.addImage(id, bitmap) }
|
||||
}
|
||||
}
|
||||
|
||||
override fun fromResource(resourceId: Int): IObjectWrapper? {
|
||||
val id = "resource-$resourceId"
|
||||
registerBitmap(id) { BitmapFactory.decodeResource(resources, resourceId) }
|
||||
return ObjectWrapper.wrap(BitmapDescriptorImpl(id, bitmapSize(id)))
|
||||
}
|
||||
|
||||
override fun fromAsset(assetName: String): IObjectWrapper? {
|
||||
val id = "asset-$assetName"
|
||||
registerBitmap(id) { resources?.assets?.open(assetName)?.let { BitmapFactory.decodeStream(it) } }
|
||||
return ObjectWrapper.wrap(BitmapDescriptorImpl(id, bitmapSize(id)))
|
||||
}
|
||||
|
||||
override fun fromFile(fileName: String): IObjectWrapper? {
|
||||
val id = "file-$fileName"
|
||||
registerBitmap(id) { BitmapFactory.decodeFile(fileName) }
|
||||
return ObjectWrapper.wrap(BitmapDescriptorImpl(id, bitmapSize(id)))
|
||||
}
|
||||
|
||||
override fun defaultMarker(): IObjectWrapper? {
|
||||
Log.d(TAG, "unimplemented Method: defaultMarker")
|
||||
val id = "marker"
|
||||
return ObjectWrapper.wrap(BitmapDescriptorImpl("marker", bitmapSize(id)))
|
||||
}
|
||||
|
||||
override fun defaultMarkerWithHue(hue: Float): IObjectWrapper? {
|
||||
val id = "marker"
|
||||
Log.d(TAG, "unimplemented Method: defaultMarkerWithHue")
|
||||
return ObjectWrapper.wrap(ColorBitmapDescriptorImpl("marker", bitmapSize(id), hue))
|
||||
}
|
||||
|
||||
override fun fromBitmap(bitmap: Bitmap): IObjectWrapper? {
|
||||
val id = "bitmap-${bitmap.hashCode()}"
|
||||
registerBitmap(id) { bitmap }
|
||||
return ObjectWrapper.wrap(BitmapDescriptorImpl(id, bitmapSize(id)))
|
||||
}
|
||||
|
||||
override fun fromPath(absolutePath: String): IObjectWrapper? {
|
||||
val id = "path-$absolutePath"
|
||||
registerBitmap(id) { BitmapFactory.decodeFile(absolutePath) }
|
||||
return ObjectWrapper.wrap(BitmapDescriptorImpl(id, bitmapSize(id)))
|
||||
}
|
||||
|
||||
override fun onTransact(code: Int, data: Parcel?, reply: Parcel?, flags: Int): Boolean =
|
||||
if (super.onTransact(code, data, reply, flags)) {
|
||||
true
|
||||
} else {
|
||||
Log.d(TAG, "onTransact [unknown]: $code, $data, $flags"); false
|
||||
}
|
||||
}
|
@ -0,0 +1,108 @@
|
||||
/*
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.mapbox.model
|
||||
|
||||
import android.os.Parcel
|
||||
import android.util.Log
|
||||
import com.google.android.gms.maps.model.LatLng
|
||||
import com.google.android.gms.maps.model.internal.ICircleDelegate
|
||||
import com.mapbox.mapboxsdk.plugins.annotation.Circle
|
||||
import org.microg.gms.maps.mapbox.GoogleMapImpl
|
||||
import org.microg.gms.maps.mapbox.utils.toGms
|
||||
import org.microg.gms.maps.mapbox.utils.toMapbox
|
||||
|
||||
class CircleImpl(private val map: GoogleMapImpl, private val circle: Circle) : ICircleDelegate.Stub() {
|
||||
override fun remove() {
|
||||
map.circleManager?.delete(circle)
|
||||
}
|
||||
|
||||
override fun getId(): String = "c" + circle.id.toString()
|
||||
|
||||
override fun setCenter(center: LatLng) {
|
||||
circle.latLng = center.toMapbox()
|
||||
map.circleManager?.update(circle)
|
||||
}
|
||||
|
||||
override fun getCenter(): LatLng = circle.latLng.toGms()
|
||||
|
||||
override fun setRadius(radius: Double) {
|
||||
circle.circleRadius = radius.toFloat()
|
||||
map.circleManager?.update(circle)
|
||||
}
|
||||
|
||||
override fun getRadius(): Double = circle.circleRadius.toDouble()
|
||||
|
||||
override fun setStrokeWidth(width: Float) {
|
||||
circle.circleStrokeWidth = width / map.dpiFactor
|
||||
map.circleManager?.update(circle)
|
||||
}
|
||||
|
||||
override fun getStrokeWidth(): Float = circle.circleStrokeWidth * map.dpiFactor
|
||||
|
||||
override fun setStrokeColor(color: Int) {
|
||||
circle.setCircleStrokeColor(color)
|
||||
map.circleManager?.update(circle)
|
||||
}
|
||||
|
||||
override fun getStrokeColor(): Int = circle.circleStrokeColorAsInt
|
||||
|
||||
override fun setFillColor(color: Int) {
|
||||
circle.setCircleColor(color)
|
||||
map.circleManager?.update(circle)
|
||||
}
|
||||
|
||||
override fun getFillColor(): Int = circle.circleColorAsInt
|
||||
|
||||
override fun setZIndex(zIndex: Float) {
|
||||
Log.d(TAG, "unimplemented Method: setZIndex")
|
||||
}
|
||||
|
||||
override fun getZIndex(): Float {
|
||||
Log.d(TAG, "unimplemented Method: getZIndex")
|
||||
return 0f
|
||||
}
|
||||
|
||||
override fun setVisible(visible: Boolean) {
|
||||
circle.circleOpacity = if (visible) 1f else 0f
|
||||
circle.circleStrokeOpacity = if (visible) 1f else 0f
|
||||
map.circleManager?.update(circle)
|
||||
}
|
||||
|
||||
override fun isVisible(): Boolean = circle.circleOpacity != 0f || circle.circleStrokeOpacity != 0f
|
||||
|
||||
override fun equalsRemote(other: ICircleDelegate?): Boolean = equals(other)
|
||||
|
||||
override fun hashCodeRemote(): Int = hashCode()
|
||||
|
||||
override fun equals(other: Any?): Boolean {
|
||||
if (other is CircleImpl) {
|
||||
return other.circle == circle
|
||||
}
|
||||
return false
|
||||
}
|
||||
|
||||
override fun onTransact(code: Int, data: Parcel?, reply: Parcel?, flags: Int): Boolean =
|
||||
if (super.onTransact(code, data, reply, flags)) {
|
||||
true
|
||||
} else {
|
||||
Log.d(TAG, "onTransact [unknown]: $code, $data, $flags"); false
|
||||
}
|
||||
|
||||
companion object {
|
||||
val TAG = "GmsMapCircle"
|
||||
}
|
||||
}
|
@ -0,0 +1,171 @@
|
||||
/*
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.mapbox.model
|
||||
|
||||
import android.util.Log
|
||||
import com.google.android.gms.dynamic.IObjectWrapper
|
||||
import com.google.android.gms.maps.model.LatLng
|
||||
import com.google.android.gms.maps.model.internal.IMarkerDelegate
|
||||
import com.mapbox.mapboxsdk.plugins.annotation.Symbol
|
||||
import org.microg.gms.kotlin.unwrap
|
||||
import org.microg.gms.maps.mapbox.GoogleMapImpl
|
||||
import org.microg.gms.maps.mapbox.utils.toGms
|
||||
import org.microg.gms.maps.mapbox.utils.toMapbox
|
||||
|
||||
class MarkerImpl(private val map: GoogleMapImpl,
|
||||
private val symbol: Symbol,
|
||||
private var anchor: FloatArray,
|
||||
private var icon: BitmapDescriptorImpl?,
|
||||
private var alpha: Float = symbol.iconOpacity,
|
||||
private var title: String? = null,
|
||||
private var snippet: String? = null) : IMarkerDelegate.Stub() {
|
||||
private var tag: IObjectWrapper? = null
|
||||
|
||||
override fun remove() {
|
||||
map.symbolManager?.delete(symbol)
|
||||
map.markers.remove(symbol.id)
|
||||
}
|
||||
|
||||
override fun getId(): String = "m" + symbol.id.toString()
|
||||
|
||||
override fun setPosition(pos: LatLng?) {
|
||||
pos?.let { symbol.latLng = it.toMapbox() }
|
||||
map.symbolManager?.update(symbol)
|
||||
}
|
||||
|
||||
override fun getPosition(): LatLng = symbol.latLng.toGms()
|
||||
|
||||
override fun setTitle(title: String?) {
|
||||
this.title = title
|
||||
}
|
||||
|
||||
override fun getTitle(): String? = title
|
||||
|
||||
override fun setSnippet(snippet: String?) {
|
||||
this.snippet = snippet
|
||||
}
|
||||
|
||||
override fun getSnippet(): String? = snippet
|
||||
|
||||
override fun setDraggable(drag: Boolean) {
|
||||
symbol.isDraggable = drag
|
||||
map.symbolManager?.update(symbol)
|
||||
}
|
||||
|
||||
override fun isDraggable(): Boolean = symbol.isDraggable
|
||||
|
||||
override fun showInfoWindow() {
|
||||
Log.d(TAG, "unimplemented Method: showInfoWindow")
|
||||
}
|
||||
|
||||
override fun hideInfoWindow() {
|
||||
Log.d(TAG, "unimplemented Method: hideInfoWindow")
|
||||
}
|
||||
|
||||
override fun isInfoWindowShown(): Boolean {
|
||||
Log.d(TAG, "unimplemented Method: isInfoWindowShow")
|
||||
return false
|
||||
}
|
||||
|
||||
override fun setVisible(visible: Boolean) {
|
||||
symbol.iconOpacity = if (visible) 0f else alpha
|
||||
map.symbolManager?.update(symbol)
|
||||
}
|
||||
|
||||
override fun isVisible(): Boolean = symbol.iconOpacity != 0f
|
||||
|
||||
override fun equals(other: Any?): Boolean {
|
||||
if (this === other) return true
|
||||
if (other is IMarkerDelegate) return other.id == id
|
||||
return false
|
||||
}
|
||||
|
||||
override fun equalsRemote(other: IMarkerDelegate?): Boolean = equals(other)
|
||||
|
||||
override fun hashCode(): Int {
|
||||
return id.hashCode()
|
||||
}
|
||||
|
||||
override fun toString(): String {
|
||||
return "$id ($title)"
|
||||
}
|
||||
|
||||
override fun hashCodeRemote(): Int = hashCode()
|
||||
|
||||
override fun setIcon(obj: IObjectWrapper?) {
|
||||
obj.unwrap<BitmapDescriptorImpl>()?.let { icon = it }
|
||||
icon?.applyTo(symbol, anchor, map.dpiFactor)
|
||||
map.symbolManager?.update(symbol)
|
||||
}
|
||||
|
||||
override fun setAnchor(x: Float, y: Float) {
|
||||
anchor = floatArrayOf(x, y)
|
||||
icon?.applyTo(symbol, anchor, map.dpiFactor)
|
||||
map.symbolManager?.update(symbol)
|
||||
}
|
||||
|
||||
override fun setFlat(flat: Boolean) {
|
||||
Log.d(TAG, "unimplemented Method: setFlat")
|
||||
}
|
||||
|
||||
override fun isFlat(): Boolean {
|
||||
Log.d(TAG, "unimplemented Method: isFlat")
|
||||
return false
|
||||
}
|
||||
|
||||
override fun setRotation(rotation: Float) {
|
||||
symbol.iconRotate = rotation
|
||||
map.symbolManager?.update(symbol)
|
||||
}
|
||||
|
||||
override fun getRotation(): Float = symbol.iconRotate
|
||||
|
||||
override fun setInfoWindowAnchor(x: Float, y: Float) {
|
||||
Log.d(TAG, "unimplemented Method: setInfoWindowAnchor")
|
||||
}
|
||||
|
||||
override fun setAlpha(alpha: Float) {
|
||||
this.alpha = alpha
|
||||
symbol.iconOpacity = alpha
|
||||
map.symbolManager?.update(symbol)
|
||||
}
|
||||
|
||||
override fun getAlpha(): Float = alpha
|
||||
|
||||
override fun setZIndex(zIndex: Float) {
|
||||
var intBits = java.lang.Float.floatToIntBits(zIndex)
|
||||
if (intBits < 0) intBits = intBits xor 0x7fffffff
|
||||
symbol.zIndex = intBits
|
||||
map.symbolManager?.update(symbol)
|
||||
}
|
||||
|
||||
override fun getZIndex(): Float {
|
||||
var intBits = symbol.zIndex
|
||||
if (intBits < 0) intBits = intBits xor 0x7fffffff
|
||||
return java.lang.Float.intBitsToFloat(intBits)
|
||||
}
|
||||
|
||||
override fun setTag(obj: IObjectWrapper?) {
|
||||
this.tag = obj
|
||||
}
|
||||
|
||||
override fun getTag(): IObjectWrapper? = tag
|
||||
|
||||
companion object {
|
||||
private val TAG = "GmsMapMarker"
|
||||
}
|
||||
}
|
@ -0,0 +1,102 @@
|
||||
/*
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.mapbox.model
|
||||
|
||||
import android.os.Parcel
|
||||
import android.util.Log
|
||||
import com.google.android.gms.maps.model.LatLng
|
||||
import com.google.android.gms.maps.model.internal.IPolylineDelegate
|
||||
import com.mapbox.mapboxsdk.plugins.annotation.Line
|
||||
import org.microg.gms.maps.mapbox.GoogleMapImpl
|
||||
import org.microg.gms.maps.mapbox.utils.toGms
|
||||
import org.microg.gms.maps.mapbox.utils.toMapbox
|
||||
|
||||
class PolylineImpl(private val map: GoogleMapImpl, private val line: Line) : IPolylineDelegate.Stub() {
|
||||
override fun remove() {
|
||||
map.lineManager?.delete(line)
|
||||
}
|
||||
|
||||
override fun getId(): String = "l" + line.id.toString()
|
||||
|
||||
override fun setPoints(points: MutableList<LatLng>) {
|
||||
line.latLngs = points.map { it.toMapbox() }
|
||||
map.lineManager?.update(line)
|
||||
}
|
||||
|
||||
override fun getPoints(): List<LatLng> = line.latLngs.map { it.toGms() }
|
||||
|
||||
override fun setWidth(width: Float) {
|
||||
line.lineWidth = width / map.dpiFactor
|
||||
map.lineManager?.update(line)
|
||||
}
|
||||
|
||||
override fun getWidth(): Float = line.lineWidth * map.dpiFactor
|
||||
|
||||
override fun setColor(color: Int) {
|
||||
line.setLineColor(color)
|
||||
map.lineManager?.update(line)
|
||||
}
|
||||
|
||||
override fun getColor(): Int = line.lineColorAsInt
|
||||
|
||||
override fun setZIndex(zIndex: Float) {
|
||||
Log.d(TAG, "unimplemented Method: setZIndex")
|
||||
}
|
||||
|
||||
override fun getZIndex(): Float {
|
||||
Log.d(TAG, "unimplemented Method: getZIndex")
|
||||
return 0f
|
||||
}
|
||||
|
||||
override fun setVisible(visible: Boolean) {
|
||||
line.lineOpacity = if (visible) 1f else 0f
|
||||
map.lineManager?.update(line)
|
||||
}
|
||||
|
||||
override fun isVisible(): Boolean = line.lineOpacity != 0f
|
||||
|
||||
override fun setGeodesic(geod: Boolean) {
|
||||
Log.d(TAG, "unimplemented Method: setGeodesic")
|
||||
}
|
||||
|
||||
override fun isGeodesic(): Boolean {
|
||||
Log.d(TAG, "unimplemented Method: isGeodesic")
|
||||
return false
|
||||
}
|
||||
|
||||
override fun equalsRemote(other: IPolylineDelegate?): Boolean = equals(other)
|
||||
|
||||
override fun hashCodeRemote(): Int = hashCode()
|
||||
|
||||
override fun equals(other: Any?): Boolean {
|
||||
if (other is PolylineImpl) {
|
||||
return other.line == line
|
||||
}
|
||||
return false
|
||||
}
|
||||
|
||||
override fun onTransact(code: Int, data: Parcel?, reply: Parcel?, flags: Int): Boolean =
|
||||
if (super.onTransact(code, data, reply, flags)) {
|
||||
true
|
||||
} else {
|
||||
Log.d(TAG, "onTransact [unknown]: $code, $data, $flags"); false
|
||||
}
|
||||
|
||||
companion object {
|
||||
private val TAG = "GmsMapPolyline"
|
||||
}
|
||||
}
|
@ -0,0 +1,80 @@
|
||||
/*
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.mapbox.utils
|
||||
|
||||
import android.content.Context
|
||||
import android.content.ContextWrapper
|
||||
import android.content.Intent
|
||||
import android.content.SharedPreferences
|
||||
import android.view.LayoutInflater
|
||||
import org.microg.gms.common.Constants
|
||||
import java.io.File
|
||||
|
||||
class MapContext(private val context: Context) : ContextWrapper(context.createPackageContext(Constants.GMS_PACKAGE_NAME, Context.CONTEXT_INCLUDE_CODE and Context.CONTEXT_IGNORE_SECURITY)) {
|
||||
private var layoutInflater: LayoutInflater? = null
|
||||
private val appContext: Context
|
||||
get() = context.applicationContext ?: context
|
||||
|
||||
override fun getApplicationContext(): Context {
|
||||
return this
|
||||
}
|
||||
|
||||
override fun getCacheDir(): File {
|
||||
val cacheDir = File(appContext.cacheDir, "com.google.android.gms")
|
||||
cacheDir.mkdirs()
|
||||
return cacheDir
|
||||
}
|
||||
|
||||
override fun getFilesDir(): File {
|
||||
val filesDir = File(appContext.filesDir, "com.google.android.gms")
|
||||
filesDir.mkdirs()
|
||||
return filesDir
|
||||
}
|
||||
|
||||
override fun getPackageName(): String {
|
||||
return appContext.packageName
|
||||
}
|
||||
|
||||
override fun getClassLoader(): ClassLoader {
|
||||
return MapContext::class.java.classLoader
|
||||
}
|
||||
|
||||
override fun getSharedPreferences(name: String?, mode: Int): SharedPreferences {
|
||||
return appContext.getSharedPreferences("com.google.android.gms_$name", mode)
|
||||
}
|
||||
|
||||
override fun getSystemService(name: String): Any? {
|
||||
if (name == Context.LAYOUT_INFLATER_SERVICE) {
|
||||
if (layoutInflater == null) {
|
||||
layoutInflater = super.getSystemService(name) as LayoutInflater
|
||||
layoutInflater?.cloneInContext(this)?.let { layoutInflater = it }
|
||||
}
|
||||
if (layoutInflater != null) {
|
||||
return layoutInflater
|
||||
}
|
||||
}
|
||||
return context.getSystemService(name)
|
||||
}
|
||||
|
||||
override fun startActivity(intent: Intent?) {
|
||||
context.startActivity(intent)
|
||||
}
|
||||
|
||||
companion object {
|
||||
val TAG = "GmsMapContext"
|
||||
}
|
||||
}
|
@ -0,0 +1,79 @@
|
||||
/*
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.mapbox.utils
|
||||
|
||||
import android.annotation.SuppressLint
|
||||
import android.content.Context
|
||||
import android.content.pm.ApplicationInfo
|
||||
import android.util.Log
|
||||
import com.mapbox.mapboxsdk.LibraryLoader
|
||||
import java.io.*
|
||||
import java.util.zip.ZipFile
|
||||
|
||||
class MultiArchLoader(private val mapContext: Context, private val appContext: Context) : LibraryLoader() {
|
||||
@SuppressLint("UnsafeDynamicallyLoadedCode")
|
||||
override fun load(name: String) {
|
||||
try {
|
||||
val otherAppInfo = mapContext.packageManager.getApplicationInfo(appContext.packageName, 0)
|
||||
val primaryCpuAbi = ApplicationInfo::class.java.getField("primaryCpuAbi").get(otherAppInfo) as String?
|
||||
if (primaryCpuAbi != null) {
|
||||
val path = "lib/$primaryCpuAbi/lib$name.so"
|
||||
val cacheFile = File("${appContext.cacheDir.absolutePath}/.gmscore/$path")
|
||||
cacheFile.parentFile.mkdirs()
|
||||
val apkFile = File(mapContext.packageCodePath)
|
||||
if (!cacheFile.exists() || cacheFile.lastModified() < apkFile.lastModified()) {
|
||||
val zipFile = ZipFile(apkFile)
|
||||
val entry = zipFile.getEntry(path)
|
||||
if (entry != null) {
|
||||
copyInputStream(zipFile.getInputStream(entry), FileOutputStream(cacheFile))
|
||||
} else {
|
||||
Log.d(TAG, "Can't load native library: $path does not exist in $apkFile")
|
||||
val entries = zipFile.entries()
|
||||
while (entries.hasMoreElements()) {
|
||||
Log.d(TAG, "but: ${entries.nextElement()}")
|
||||
}
|
||||
}
|
||||
}
|
||||
Log.d(TAG, "Loading $name from ${cacheFile.getPath()}")
|
||||
System.load(cacheFile.absolutePath)
|
||||
return
|
||||
}
|
||||
} catch (e: Exception) {
|
||||
Log.w(TAG, e)
|
||||
}
|
||||
Log.d(TAG, "Loading native $name")
|
||||
System.loadLibrary(name)
|
||||
}
|
||||
|
||||
@Throws(IOException::class)
|
||||
private fun copyInputStream(inp: InputStream, out: OutputStream) {
|
||||
val buffer = ByteArray(1024)
|
||||
var len: Int = inp.read(buffer)
|
||||
while (len >= 0) {
|
||||
out.write(buffer, 0, len)
|
||||
len = inp.read(buffer)
|
||||
}
|
||||
|
||||
inp.close()
|
||||
out.close()
|
||||
}
|
||||
|
||||
companion object {
|
||||
private val TAG = "GmsMultiArchLoader"
|
||||
}
|
||||
|
||||
}
|
@ -0,0 +1,95 @@
|
||||
/*
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.mapbox.utils
|
||||
|
||||
import android.os.Bundle
|
||||
import com.google.android.gms.maps.internal.ICancelableCallback
|
||||
import com.google.android.gms.maps.model.CircleOptions
|
||||
import com.google.android.gms.maps.model.MarkerOptions
|
||||
import com.google.android.gms.maps.model.PolylineOptions
|
||||
import com.mapbox.mapboxsdk.camera.CameraPosition
|
||||
import com.mapbox.mapboxsdk.geometry.LatLng
|
||||
import com.mapbox.mapboxsdk.geometry.LatLngBounds
|
||||
import com.mapbox.mapboxsdk.geometry.VisibleRegion
|
||||
import com.mapbox.mapboxsdk.maps.MapboxMap
|
||||
import com.mapbox.mapboxsdk.plugins.annotation.LineOptions
|
||||
import com.mapbox.mapboxsdk.plugins.annotation.SymbolOptions
|
||||
import com.mapbox.mapboxsdk.style.layers.Property.ICON_ANCHOR_TOP_LEFT
|
||||
import com.mapbox.mapboxsdk.utils.ColorUtils
|
||||
import org.microg.gms.kotlin.unwrap
|
||||
import org.microg.gms.maps.mapbox.model.BitmapDescriptorImpl
|
||||
|
||||
fun com.google.android.gms.maps.model.LatLng.toMapbox(): LatLng =
|
||||
LatLng(latitude, longitude)
|
||||
|
||||
fun com.google.android.gms.maps.model.LatLngBounds.toMapbox(): LatLngBounds =
|
||||
LatLngBounds.from(this.northeast.latitude, this.northeast.longitude, this.southwest.latitude, this.southwest.longitude)
|
||||
|
||||
fun com.google.android.gms.maps.model.CameraPosition.toMapbox(): CameraPosition =
|
||||
CameraPosition.Builder()
|
||||
.target(target.toMapbox())
|
||||
.zoom(zoom.toDouble() - 1.0)
|
||||
.tilt(tilt.toDouble())
|
||||
.bearing(bearing.toDouble())
|
||||
.build()
|
||||
|
||||
fun ICancelableCallback.toMapbox(): MapboxMap.CancelableCallback =
|
||||
object : MapboxMap.CancelableCallback {
|
||||
override fun onFinish() = this@toMapbox.onFinish()
|
||||
override fun onCancel() = this@toMapbox.onCancel()
|
||||
}
|
||||
|
||||
|
||||
fun Bundle.toMapbox(): Bundle {
|
||||
val newBundle = Bundle(this)
|
||||
for (key in newBundle.keySet()) {
|
||||
val value = newBundle.get(key)
|
||||
when (value) {
|
||||
is com.google.android.gms.maps.model.CameraPosition -> newBundle.putParcelable(key, value.toMapbox())
|
||||
is com.google.android.gms.maps.model.LatLng -> newBundle.putParcelable(key, value.toMapbox())
|
||||
is com.google.android.gms.maps.model.LatLngBounds -> newBundle.putParcelable(key, value.toMapbox())
|
||||
is Bundle -> newBundle.putBundle(key, value.toMapbox())
|
||||
}
|
||||
}
|
||||
return newBundle
|
||||
}
|
||||
|
||||
fun LatLng.toGms(): com.google.android.gms.maps.model.LatLng =
|
||||
com.google.android.gms.maps.model.LatLng(latitude, longitude)
|
||||
|
||||
fun LatLngBounds.toGms(): com.google.android.gms.maps.model.LatLngBounds =
|
||||
com.google.android.gms.maps.model.LatLngBounds(southWest.toGms(), northEast.toGms())
|
||||
|
||||
fun CameraPosition.toGms(): com.google.android.gms.maps.model.CameraPosition =
|
||||
com.google.android.gms.maps.model.CameraPosition(target.toGms(), zoom.toFloat() + 1.0f, tilt.toFloat(), bearing.toFloat())
|
||||
|
||||
fun Bundle.toGms(): Bundle {
|
||||
val newBundle = Bundle(this)
|
||||
for (key in newBundle.keySet()) {
|
||||
val value = newBundle.get(key)
|
||||
when (value) {
|
||||
is CameraPosition -> newBundle.putParcelable(key, value.toGms())
|
||||
is LatLng -> newBundle.putParcelable(key, value.toGms())
|
||||
is LatLngBounds -> newBundle.putParcelable(key, value.toGms())
|
||||
is Bundle -> newBundle.putBundle(key, value.toGms())
|
||||
}
|
||||
}
|
||||
return newBundle
|
||||
}
|
||||
|
||||
fun VisibleRegion.toGms(): com.google.android.gms.maps.model.VisibleRegion =
|
||||
com.google.android.gms.maps.model.VisibleRegion(nearLeft.toGms(), nearRight.toGms(), farLeft.toGms(), farRight.toGms(), latLngBounds.toGms())
|
78
play-services-maps-core-vtm/build.gradle
Normal file
@ -0,0 +1,78 @@
|
||||
/*
|
||||
* Copyright 2013-2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
apply plugin: "com.android.library"
|
||||
|
||||
dependencies {
|
||||
implementation project(":microg-ui-tools")
|
||||
implementation project(":play-services-api")
|
||||
|
||||
implementation "org.microg:vtm-android:0.9.1-mod"
|
||||
implementation "org.microg:vtm-android:0.9.1-mod:natives-armeabi"
|
||||
implementation "org.microg:vtm-android:0.9.1-mod:natives-armeabi-v7a"
|
||||
implementation "org.microg:vtm-android:0.9.1-mod:natives-arm64-v8a"
|
||||
implementation "org.microg:vtm-android:0.9.1-mod:natives-x86"
|
||||
implementation "org.microg:vtm-android:0.9.1-mod:natives-x86_64"
|
||||
implementation "org.microg:vtm-extras:0.9.1-mod"
|
||||
implementation "org.microg:vtm-jts:0.9.1-mod"
|
||||
implementation project(":vtm-microg-theme")
|
||||
}
|
||||
|
||||
def execResult(...args) {
|
||||
def stdout = new ByteArrayOutputStream()
|
||||
exec {
|
||||
commandLine args
|
||||
standardOutput = stdout
|
||||
}
|
||||
return stdout.toString().trim()
|
||||
}
|
||||
|
||||
android {
|
||||
compileSdkVersion androidCompileSdk()
|
||||
buildToolsVersion "$androidBuildVersionTools"
|
||||
|
||||
defaultConfig {
|
||||
versionName "temp"
|
||||
versionCode 1
|
||||
|
||||
minSdkVersion androidMinSdk()
|
||||
targetSdkVersion androidTargetSdk()
|
||||
|
||||
ndk {
|
||||
abiFilters "armeabi", "armeabi-v7a", "arm64-v8a", "x86", "x86_64"
|
||||
}
|
||||
}
|
||||
|
||||
lintOptions {
|
||||
disable "MissingTranslation", "InvalidPackage", "BatteryLife", "ImpliedQuantity", "MissingQuantity"
|
||||
}
|
||||
|
||||
buildTypes {
|
||||
release {
|
||||
minifyEnabled true
|
||||
proguardFiles getDefaultProguardFile("proguard-android.txt"), "proguard-rules.pro"
|
||||
}
|
||||
}
|
||||
|
||||
compileOptions {
|
||||
sourceCompatibility JavaVersion.VERSION_1_8
|
||||
targetCompatibility JavaVersion.VERSION_1_8
|
||||
}
|
||||
}
|
||||
|
||||
if (file("user.gradle").exists()) {
|
||||
apply from: "user.gradle"
|
||||
}
|
40
play-services-maps-core-vtm/src/main/AndroidManifest.xml
Normal file
@ -0,0 +1,40 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<!--
|
||||
~ Copyright (C) 2013-2019 microG Project Team
|
||||
~
|
||||
~ Licensed under the Apache License, Version 2.0 (the "License");
|
||||
~ you may not use this file except in compliance with the License.
|
||||
~ You may obtain a copy of the License at
|
||||
~
|
||||
~ http://www.apache.org/licenses/LICENSE-2.0
|
||||
~
|
||||
~ Unless required by applicable law or agreed to in writing, software
|
||||
~ distributed under the License is distributed on an "AS IS" BASIS,
|
||||
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
~ See the License for the specific language governing permissions and
|
||||
~ limitations under the License.
|
||||
-->
|
||||
<manifest package="org.microg.gms.maps.vtm"
|
||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:tools="http://schemas.android.com/tools">
|
||||
|
||||
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>
|
||||
<uses-permission android:name="android.permission.INTERNET"/>
|
||||
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION"/>
|
||||
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>
|
||||
<uses-permission android:name="android.permission.READ_PHONE_STATE"/>
|
||||
<uses-permission android:name="android.permission.WAKE_LOCK"/>
|
||||
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
|
||||
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
|
||||
<uses-permission android:name="android.permission.REQUEST_IGNORE_BATTERY_OPTIMIZATIONS"/>
|
||||
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED"/>
|
||||
|
||||
<application>
|
||||
<provider
|
||||
android:name=".data.SharedTileProvider"
|
||||
android:authorities="org.microg.gms.maps.vtm.tile"
|
||||
android:enabled="true"
|
||||
android:exported="true"/>
|
||||
</application>
|
||||
|
||||
</manifest>
|
@ -21,6 +21,7 @@ import android.content.Context;
|
||||
import android.content.res.Resources;
|
||||
import android.os.Parcel;
|
||||
import android.os.RemoteException;
|
||||
import android.support.annotation.Keep;
|
||||
import android.util.Log;
|
||||
|
||||
import com.google.android.gms.dynamic.IObjectWrapper;
|
||||
@ -28,12 +29,13 @@ import com.google.android.gms.dynamic.ObjectWrapper;
|
||||
import com.google.android.gms.maps.GoogleMapOptions;
|
||||
import com.google.android.gms.maps.model.internal.IBitmapDescriptorFactoryDelegate;
|
||||
|
||||
import org.microg.gms.maps.MapFragmentImpl;
|
||||
import org.microg.gms.maps.MapViewImpl;
|
||||
import org.microg.gms.maps.ResourcesContainer;
|
||||
import org.microg.gms.maps.bitmap.BitmapDescriptorFactoryImpl;
|
||||
import org.microg.gms.maps.camera.CameraUpdateFactoryImpl;
|
||||
import org.microg.gms.maps.vtm.MapFragmentImpl;
|
||||
import org.microg.gms.maps.vtm.MapViewImpl;
|
||||
import org.microg.gms.maps.vtm.ResourcesContainer;
|
||||
import org.microg.gms.maps.vtm.bitmap.BitmapDescriptorFactoryImpl;
|
||||
import org.microg.gms.maps.vtm.camera.CameraUpdateFactoryImpl;
|
||||
|
||||
@Keep
|
||||
public class CreatorImpl extends ICreator.Stub {
|
||||
private static final String TAG = "GmsMapCreator";
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (C) 2013-2017 microG Project Team
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps;
|
||||
package org.microg.gms.maps.vtm;
|
||||
|
||||
import android.content.Context;
|
||||
import android.content.ContextWrapper;
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (C) 2013-2017 microG Project Team
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps;
|
||||
package org.microg.gms.maps.vtm;
|
||||
|
||||
import android.content.Context;
|
||||
import android.graphics.Bitmap;
|
||||
@ -27,10 +27,10 @@ import android.view.View;
|
||||
import com.google.android.gms.maps.internal.ISnapshotReadyCallback;
|
||||
import com.google.android.gms.maps.model.CameraPosition;
|
||||
|
||||
import org.microg.gms.maps.camera.CameraUpdate;
|
||||
import org.microg.gms.maps.markup.DrawableMarkup;
|
||||
import org.microg.gms.maps.markup.MarkerItemMarkup;
|
||||
import org.microg.gms.maps.markup.Markup;
|
||||
import org.microg.gms.maps.vtm.camera.CameraUpdate;
|
||||
import org.microg.gms.maps.vtm.markup.DrawableMarkup;
|
||||
import org.microg.gms.maps.vtm.markup.MarkerItemMarkup;
|
||||
import org.microg.gms.maps.vtm.markup.Markup;
|
||||
import org.oscim.backend.GL;
|
||||
import org.oscim.backend.GLAdapter;
|
||||
import org.oscim.core.MapPosition;
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (C) 2013-2017 microG Project Team
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps;
|
||||
package org.microg.gms.maps.vtm;
|
||||
|
||||
import android.content.Context;
|
||||
import android.content.ContextWrapper;
|
||||
@ -23,14 +23,12 @@ import android.graphics.BitmapFactory;
|
||||
import android.util.AttributeSet;
|
||||
import android.util.Log;
|
||||
|
||||
import com.google.android.gms.R;
|
||||
|
||||
import org.microg.gms.maps.data.SharedTileCache;
|
||||
import org.microg.gms.maps.markup.ClearableVectorLayer;
|
||||
import org.microg.gms.maps.vtm.data.SharedTileCache;
|
||||
import org.microg.gms.maps.vtm.markup.ClearableVectorLayer;
|
||||
import org.microg.gms.maps.vtm.R;
|
||||
import org.oscim.android.AndroidAssets;
|
||||
import org.oscim.android.MapView;
|
||||
import org.oscim.android.canvas.AndroidBitmap;
|
||||
import org.oscim.backend.AssetAdapter;
|
||||
import org.oscim.layers.marker.ItemizedLayer;
|
||||
import org.oscim.layers.marker.MarkerItem;
|
||||
import org.oscim.layers.marker.MarkerSymbol;
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (C) 2013-2017 microG Project Team
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps;
|
||||
package org.microg.gms.maps.vtm;
|
||||
|
||||
import android.content.Context;
|
||||
import android.widget.FrameLayout;
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (C) 2013-2017 microG Project Team
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps;
|
||||
package org.microg.gms.maps.vtm;
|
||||
|
||||
import com.google.android.gms.maps.model.CameraPosition;
|
||||
import com.google.android.gms.maps.model.LatLng;
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (C) 2013-2017 microG Project Team
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps;
|
||||
package org.microg.gms.maps.vtm;
|
||||
|
||||
import android.content.Context;
|
||||
import android.graphics.Bitmap;
|
||||
@ -68,15 +68,15 @@ import com.google.android.gms.maps.model.internal.IPolygonDelegate;
|
||||
import com.google.android.gms.maps.model.internal.IPolylineDelegate;
|
||||
import com.google.android.gms.maps.model.internal.ITileOverlayDelegate;
|
||||
|
||||
import org.microg.gms.maps.camera.CameraUpdate;
|
||||
import org.microg.gms.maps.camera.MapPositionCameraUpdate;
|
||||
import org.microg.gms.maps.markup.CircleImpl;
|
||||
import org.microg.gms.maps.markup.GroundOverlayImpl;
|
||||
import org.microg.gms.maps.markup.MarkerImpl;
|
||||
import org.microg.gms.maps.markup.Markup;
|
||||
import org.microg.gms.maps.markup.PolygonImpl;
|
||||
import org.microg.gms.maps.markup.PolylineImpl;
|
||||
import org.microg.gms.maps.markup.TileOverlayImpl;
|
||||
import org.microg.gms.maps.vtm.camera.CameraUpdate;
|
||||
import org.microg.gms.maps.vtm.camera.MapPositionCameraUpdate;
|
||||
import org.microg.gms.maps.vtm.markup.CircleImpl;
|
||||
import org.microg.gms.maps.vtm.markup.GroundOverlayImpl;
|
||||
import org.microg.gms.maps.vtm.markup.MarkerImpl;
|
||||
import org.microg.gms.maps.vtm.markup.Markup;
|
||||
import org.microg.gms.maps.vtm.markup.PolygonImpl;
|
||||
import org.microg.gms.maps.vtm.markup.PolylineImpl;
|
||||
import org.microg.gms.maps.vtm.markup.TileOverlayImpl;
|
||||
|
||||
import static android.Manifest.permission.ACCESS_COARSE_LOCATION;
|
||||
import static android.Manifest.permission.ACCESS_FINE_LOCATION;
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (C) 2013-2017 microG Project Team
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@ -14,13 +14,12 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps;
|
||||
package org.microg.gms.maps.vtm;
|
||||
|
||||
import android.app.Activity;
|
||||
import android.content.Context;
|
||||
import android.os.Bundle;
|
||||
import android.os.Handler;
|
||||
import android.os.Looper;
|
||||
import android.os.Parcel;
|
||||
import android.os.RemoteException;
|
||||
import android.util.Log;
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (C) 2013-2017 microG Project Team
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps;
|
||||
package org.microg.gms.maps.vtm;
|
||||
|
||||
import android.content.Context;
|
||||
import android.os.Bundle;
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (C) 2013-2017 microG Project Team
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps;
|
||||
package org.microg.gms.maps.vtm;
|
||||
|
||||
import android.os.RemoteException;
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (C) 2013-2017 microG Project Team
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps;
|
||||
package org.microg.gms.maps.vtm;
|
||||
|
||||
import android.content.res.Resources;
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (C) 2013-2017 microG Project Team
|
||||
* Copyright (C) 2019 microG Project Team
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps;
|
||||
package org.microg.gms.maps.vtm;
|
||||
|
||||
import android.os.RemoteException;
|
||||
import com.google.android.gms.maps.internal.IUiSettingsDelegate;
|
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.bitmap;
|
||||
package org.microg.gms.maps.vtm.bitmap;
|
||||
|
||||
import android.content.Context;
|
||||
import android.graphics.Bitmap;
|
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.bitmap;
|
||||
package org.microg.gms.maps.vtm.bitmap;
|
||||
|
||||
import android.content.Context;
|
||||
import android.graphics.Bitmap;
|
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.bitmap;
|
||||
package org.microg.gms.maps.vtm.bitmap;
|
||||
|
||||
import android.content.Context;
|
||||
import android.graphics.Bitmap;
|
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.bitmap;
|
||||
package org.microg.gms.maps.vtm.bitmap;
|
||||
|
||||
import android.graphics.Bitmap;
|
||||
import android.os.Parcel;
|
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.bitmap;
|
||||
package org.microg.gms.maps.vtm.bitmap;
|
||||
|
||||
import android.content.Context;
|
||||
import android.graphics.Bitmap;
|
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.bitmap;
|
||||
package org.microg.gms.maps.vtm.bitmap;
|
||||
|
||||
import android.content.Context;
|
||||
import android.graphics.Bitmap;
|
||||
@ -25,10 +25,10 @@ import android.graphics.ColorMatrix;
|
||||
import android.graphics.ColorMatrixColorFilter;
|
||||
import android.graphics.Paint;
|
||||
|
||||
import com.google.android.gms.R;
|
||||
import com.google.android.gms.dynamic.ObjectWrapper;
|
||||
|
||||
import org.microg.gms.maps.ResourcesContainer;
|
||||
import org.microg.gms.maps.vtm.ResourcesContainer;
|
||||
import org.microg.gms.maps.vtm.R;
|
||||
|
||||
public class DefaultBitmapDescriptor extends AbstractBitmapDescriptor {
|
||||
public static final DefaultBitmapDescriptor DEFAULT_DESCRIPTOR = new DefaultBitmapDescriptor(0);
|
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.bitmap;
|
||||
package org.microg.gms.maps.vtm.bitmap;
|
||||
|
||||
import android.content.Context;
|
||||
import android.graphics.Bitmap;
|
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.bitmap;
|
||||
package org.microg.gms.maps.vtm.bitmap;
|
||||
|
||||
public class PathBitmapDescriptor {
|
||||
public PathBitmapDescriptor(String absolutePath) {
|
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.bitmap;
|
||||
package org.microg.gms.maps.vtm.bitmap;
|
||||
|
||||
import android.content.Context;
|
||||
import android.graphics.Bitmap;
|
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.camera;
|
||||
package org.microg.gms.maps.vtm.camera;
|
||||
|
||||
import org.oscim.map.Map;
|
||||
|
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.camera;
|
||||
package org.microg.gms.maps.vtm.camera;
|
||||
|
||||
import android.os.RemoteException;
|
||||
import android.util.Log;
|
||||
@ -26,7 +26,7 @@ import com.google.android.gms.maps.model.CameraPosition;
|
||||
import com.google.android.gms.maps.model.LatLng;
|
||||
import com.google.android.gms.maps.model.LatLngBounds;
|
||||
|
||||
import org.microg.gms.maps.GmsMapsTypeHelper;
|
||||
import org.microg.gms.maps.vtm.GmsMapsTypeHelper;
|
||||
import org.oscim.core.MapPosition;
|
||||
import org.oscim.map.Map;
|
||||
|
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.camera;
|
||||
package org.microg.gms.maps.vtm.camera;
|
||||
|
||||
import org.oscim.core.MapPosition;
|
||||
import org.oscim.map.Map;
|
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.camera;
|
||||
package org.microg.gms.maps.vtm.camera;
|
||||
|
||||
import org.oscim.map.Map;
|
||||
|
@ -14,12 +14,11 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.data;
|
||||
package org.microg.gms.maps.vtm.data;
|
||||
|
||||
import android.content.ContentValues;
|
||||
import android.content.Context;
|
||||
import android.database.Cursor;
|
||||
import android.net.Uri;
|
||||
|
||||
import org.oscim.core.Tile;
|
||||
import org.oscim.tiling.ITileCache;
|
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.data;
|
||||
package org.microg.gms.maps.vtm.data;
|
||||
|
||||
import android.content.ContentProvider;
|
||||
import android.content.ContentValues;
|
||||
@ -29,7 +29,7 @@ import android.net.Uri;
|
||||
*/
|
||||
public class SharedTileProvider extends ContentProvider {
|
||||
private static final String DB_NAME = "tilecache.db";
|
||||
public static final String PROVIDER_NAME = "org.microg.gms.map.tile";
|
||||
public static final String PROVIDER_NAME = "org.microg.gms.maps.vtm.tile";
|
||||
public static final Uri PROVIDER_URI = Uri.parse("content://" + PROVIDER_NAME);
|
||||
|
||||
private SQLiteHelper sqLiteHelper;
|
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.markup;
|
||||
package org.microg.gms.maps.vtm.markup;
|
||||
|
||||
import android.os.RemoteException;
|
||||
|
||||
@ -22,7 +22,7 @@ import com.google.android.gms.maps.model.CircleOptions;
|
||||
import com.google.android.gms.maps.model.LatLng;
|
||||
import com.google.android.gms.maps.model.internal.ICircleDelegate;
|
||||
|
||||
import org.microg.gms.maps.GmsMapsTypeHelper;
|
||||
import org.microg.gms.maps.vtm.GmsMapsTypeHelper;
|
||||
import org.oscim.layers.vector.geometries.CircleDrawable;
|
||||
import org.oscim.layers.vector.geometries.Drawable;
|
||||
import org.oscim.layers.vector.geometries.Style;
|
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.markup;
|
||||
package org.microg.gms.maps.vtm.markup;
|
||||
|
||||
import org.oscim.layers.vector.VectorLayer;
|
||||
import org.oscim.map.Map;
|
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.markup;
|
||||
package org.microg.gms.maps.vtm.markup;
|
||||
|
||||
import org.oscim.layers.vector.geometries.Drawable;
|
||||
import org.oscim.map.Map;
|
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.markup;
|
||||
package org.microg.gms.maps.vtm.markup;
|
||||
|
||||
import android.os.RemoteException;
|
||||
import com.google.android.gms.dynamic.IObjectWrapper;
|
@ -14,18 +14,17 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.markup;
|
||||
package org.microg.gms.maps.vtm.markup;
|
||||
|
||||
import android.content.Context;
|
||||
import android.os.Build;
|
||||
import android.view.View;
|
||||
import android.widget.FrameLayout;
|
||||
import android.widget.LinearLayout;
|
||||
import android.widget.TextView;
|
||||
import com.google.android.gms.R;
|
||||
import com.google.android.gms.maps.model.internal.IMarkerDelegate;
|
||||
import org.microg.gms.maps.GoogleMapImpl;
|
||||
import org.microg.gms.maps.ResourcesContainer;
|
||||
import org.microg.gms.maps.vtm.GoogleMapImpl;
|
||||
import org.microg.gms.maps.vtm.ResourcesContainer;
|
||||
import org.microg.gms.maps.vtm.R;
|
||||
|
||||
import static android.os.Build.VERSION.SDK_INT;
|
||||
import static android.os.Build.VERSION_CODES.ICE_CREAM_SANDWICH_MR1;
|
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.markup;
|
||||
package org.microg.gms.maps.vtm.markup;
|
||||
|
||||
import android.content.Context;
|
||||
import android.graphics.Bitmap;
|
||||
@ -27,9 +27,9 @@ import com.google.android.gms.maps.model.LatLng;
|
||||
import com.google.android.gms.maps.model.MarkerOptions;
|
||||
import com.google.android.gms.maps.model.internal.IMarkerDelegate;
|
||||
|
||||
import org.microg.gms.maps.GmsMapsTypeHelper;
|
||||
import org.microg.gms.maps.bitmap.BitmapDescriptorImpl;
|
||||
import org.microg.gms.maps.bitmap.DefaultBitmapDescriptor;
|
||||
import org.microg.gms.maps.vtm.GmsMapsTypeHelper;
|
||||
import org.microg.gms.maps.vtm.bitmap.BitmapDescriptorImpl;
|
||||
import org.microg.gms.maps.vtm.bitmap.DefaultBitmapDescriptor;
|
||||
import org.oscim.android.canvas.AndroidBitmap;
|
||||
import org.oscim.layers.marker.MarkerItem;
|
||||
import org.oscim.layers.marker.MarkerSymbol;
|
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.markup;
|
||||
package org.microg.gms.maps.vtm.markup;
|
||||
|
||||
import android.content.Context;
|
||||
|
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.markup;
|
||||
package org.microg.gms.maps.vtm.markup;
|
||||
|
||||
public interface Markup {
|
||||
String getId();
|
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.markup;
|
||||
package org.microg.gms.maps.vtm.markup;
|
||||
|
||||
import android.os.RemoteException;
|
||||
|
||||
@ -22,7 +22,7 @@ import com.google.android.gms.maps.model.LatLng;
|
||||
import com.google.android.gms.maps.model.PolygonOptions;
|
||||
import com.google.android.gms.maps.model.internal.IPolygonDelegate;
|
||||
|
||||
import org.microg.gms.maps.GmsMapsTypeHelper;
|
||||
import org.microg.gms.maps.vtm.GmsMapsTypeHelper;
|
||||
import org.oscim.core.GeoPoint;
|
||||
import org.oscim.layers.vector.geometries.Drawable;
|
||||
import org.oscim.layers.vector.geometries.PolygonDrawable;
|
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.markup;
|
||||
package org.microg.gms.maps.vtm.markup;
|
||||
|
||||
import android.os.RemoteException;
|
||||
import android.util.Log;
|
||||
@ -23,7 +23,7 @@ import com.google.android.gms.maps.model.LatLng;
|
||||
import com.google.android.gms.maps.model.PolylineOptions;
|
||||
import com.google.android.gms.maps.model.internal.IPolylineDelegate;
|
||||
|
||||
import org.microg.gms.maps.GmsMapsTypeHelper;
|
||||
import org.microg.gms.maps.vtm.GmsMapsTypeHelper;
|
||||
import org.oscim.core.GeoPoint;
|
||||
import org.oscim.layers.vector.geometries.Drawable;
|
||||
import org.oscim.layers.vector.geometries.LineDrawable;
|
@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.microg.gms.maps.markup;
|
||||
package org.microg.gms.maps.vtm.markup;
|
||||
|
||||
import com.google.android.gms.maps.model.internal.ITileOverlayDelegate;
|
||||
|
Before Width: | Height: | Size: 4.2 KiB After Width: | Height: | Size: 4.2 KiB |
Before Width: | Height: | Size: 1.3 KiB After Width: | Height: | Size: 1.3 KiB |
Before Width: | Height: | Size: 169 B After Width: | Height: | Size: 169 B |
@ -17,14 +17,12 @@ include ':play-services-base'
|
||||
include ':play-services-tasks'
|
||||
include ':play-services-wearable'
|
||||
|
||||
include ':play-services-maps-core-mapbox'
|
||||
include ':play-services-maps-core-vtm'
|
||||
include ':play-services-core'
|
||||
|
||||
include ':microg-ui-tools'
|
||||
|
||||
include ':vtm'
|
||||
include ':vtm-android'
|
||||
include ':vtm-extras'
|
||||
include ':vtm-jts'
|
||||
include ':vtm-microg-theme'
|
||||
|
||||
include ':remote-droid-guard-lib'
|
||||
|
@ -1 +0,0 @@
|
||||
extern/vtm/vtm-android
|
@ -1 +0,0 @@
|
||||
extern/vtm/vtm-extras
|
@ -2,7 +2,7 @@ apply plugin: 'java'
|
||||
apply plugin: 'maven'
|
||||
|
||||
dependencies {
|
||||
compile project(':vtm')
|
||||
compile "org.microg:vtm:0.9.1-mod"
|
||||
}
|
||||
|
||||
sourceSets {
|
||||
|