Сравнить коммиты

..
55 Коммитов
Автор SHA1 Сообщение Дата
Anton Tananaev 1b0559c98a Update version number 2018-10-18 16:05:48 +13:00
Anton Tananaev 2e0e7ea453 Fix merge issues 2018-10-18 15:44:58 +13:00
Anton Tananaev ac6d677ff4 Explicitly select location providers 2018-10-18 15:43:07 +13:00
Anton Tananaev cbfe90757d Disable advertising id collection 2018-09-22 08:51:41 +12:00
Anton Tananaev a9f4390ae4 Update app version 2018-09-15 08:54:32 +12:00
Anton Tananaev 8a938701c8 Improve service handling 2018-09-15 08:54:09 +12:00
Anton Tananaev 2319834c5b Handle runtime exceptions 2018-09-15 08:48:37 +12:00
Anton Tananaev 1b93619e64 Update app version 2018-09-13 12:08:05 +12:00
Anton Tananaev 2a36e1aa6d Remove Lost library 2018-09-12 13:55:30 +12:00
Anton Tananaev 64687b26c2 Merge pull request #357 from oliv3/bug_350
Gracefully handle package downgrade (fix #350)
2018-09-06 08:17:42 +12:00
Olivier Girondel dcb60ab75e Gracefully handle package downgrade (fix #350) 2018-09-04 14:30:09 +02:00
Anton Tananaev 0b4c4cccc6 Merge pull request #347 from oliv3/statusSeconds
Display seconds in the status activity
2018-08-28 08:40:57 +12:00
Olivier Girondel ef5bfff70a Display seconds in the status activity 2018-08-25 15:11:57 +02:00
Anton Tananaev 855efc7acb Merge pull request #345 from oliv3/distance
Remove DistanceCalculator class
2018-08-21 08:46:33 +12:00
Olivier Girondel 0ae47e65d4 Remove DistanceCalculator class 2018-08-20 15:57:01 +02:00
Anton Tananaev e8d5e5c99b Update robolectric library 2018-08-09 14:46:02 +12:00
Anton Tananaev c3980780d8 Update project and dependencies 2018-08-09 14:33:05 +12:00
Anton Tananaev 3c11216334 Check API version 2018-05-06 16:44:56 -07:00
Anton Tananaev bcde8388d6 Update database version 2018-05-01 10:01:57 +12:00
Anton Tananaev 7f18915514 Merge pull request #327 from oliv3/mock_locations
Report mock locations
2018-04-30 13:54:15 +12:00
Olivier Girondel 42ad669fca Tell if a location is a mock 2018-04-30 02:16:10 +02:00
Anton Tananaev 3e2b508ea7 Update version number 2018-03-19 22:23:05 +13:00
Anton Tananaev fd4d616812 Check permissions in service 2018-03-19 22:22:45 +13:00
Anton Tananaev 4f6571e572 Update app version number 2018-03-18 21:28:11 +13:00
Anton Tananaev d3025b437b Replace firebase old crash reporting 2018-03-18 21:27:27 +13:00
Anton Tananaev 1e861ef0ac Fix hidden app URL open issue (fix #321) 2018-02-19 09:49:50 +13:00
Anton Tananaev 43afc57114 Merge pull request #318 from garyvdm/online_status
Show online/offline in connection changed status messages
2018-02-15 23:03:55 +13:00
Gary van der Merwe d47783808f Show online/offline in connection changed status messages. 2018-02-15 12:03:09 +02:00
Anton Tananaev 3ef2272227 Merge pull request #320 from garyvdm/revert-301-vector
Revert "Use vector icons"
2018-02-15 22:24:54 +13:00
Gary van der Merwe 3625ee42db Revert "Use vector icons." 2018-02-15 11:04:38 +02:00
Anton Tananaev 385826c3c1 Merge pull request #301 from garyvdm/vector
Use vector icons
2018-02-14 09:42:29 +13:00
Gary van der Merwe 1426926c8e Use vector icons. 2018-02-13 18:33:01 +02:00
Anton Tananaev 4f680d33c9 Merge pull request #311 from Bubu/patch-1
Add google maven repo
2018-01-23 08:20:51 +13:00
Marcus Hoffmann 2dad912da5 Add google() repo
This is required to build the app outside of Android Studio.

Fixes:
 > Could not find com.android.tools.build:gradle:3.0.1.
     Searched in the following locations:
         https://jcenter.bintray.com/com/android/tools/build/gradle/3.0.1/gradle-3.0.1.pom
         https://jcenter.bintray.com/com/android/tools/build/gradle/3.0.1/gradle-3.0.1.jar
2018-01-22 20:15:20 +01:00
Anton Tananaev 290a7d80eb Update app version number 2018-01-19 17:43:43 +13:00
Anton Tananaev 44228feb2f Fix SOS functionality 2018-01-19 17:43:18 +13:00
Anton Tananaev d887bc4119 Update version number 2018-01-09 08:26:19 +13:00
Anton Tananaev c892a20104 Fix lost API connection logic 2018-01-09 08:25:57 +13:00
Anton Tananaev 2719b57f7c Use color code directly 2018-01-07 09:26:55 +13:00
Anton Tananaev cc6c8a23f6 Update project files 2018-01-07 09:23:14 +13:00
Anton Tananaev 1e82cbbbf6 Merge pull request #305 from Alpha200/fixAccuracy
Fix reading accuracy property
2017-12-30 10:40:06 +13:00
Daniel Sendzik 4b8fde36d7 Fix reading accuracy property 2017-12-29 19:34:14 +01:00
Anton Tananaev b8cd56439a Merge pull request #304 from garyvdm/restore_startWakefulForegroundService
Restore fix auto-start issue on Android O
2017-12-21 23:03:37 +13:00
Gary van der Merwe edb1f696df Restore fix auto-start issue on Android O.
Also rename startWakefulService to startWakefulForegroundService to highlight
that it's different to the SDK version.
2017-12-21 11:54:14 +02:00
Anton Tananaev 56d2f2ef53 Merge pull request #303 from garyvdm/cleanup
Remove unnecessary code
2017-12-21 09:52:43 +13:00
Gary van der Merwe 59e6a5ae65 Remove code that was originally included for supporting older SDK APIs that are now older than our minSdkVersion. 2017-12-20 14:17:51 +02:00
Anton Tananaev 319fab647b Merge pull request #302 from garyvdm/hidden_notification
For hidden flavor, make notificaion not open the app when clicked, use different icon
2017-12-16 09:47:04 +13:00
Gary van der Merwe 42429f3496 For hidden flavor, make notification open system settings activity. 2017-12-15 12:38:56 +02:00
Gary van der Merwe 841d3e581c For hidden flavor, make notificaion not open the app when clicked, use different icon.
This only apply to when the notificaion can't be hidden, i.e. SDK >= 25.
2017-12-15 09:09:25 +02:00
Anton Tananaev dac43ccbc1 Merge pull request #300 from garyvdm/notification
Get service notification to show. Tweek settings.
2017-12-14 13:53:22 +13:00
Gary van der Merwe 3c9ae512bd Get service notification to show. Tweek settings. 2017-12-13 08:11:11 +02:00
Anton Tananaev d3e600d81d Gracefully stop location updates 2017-11-23 00:03:17 +13:00
Anton Tananaev e0296a9c65 Use fused location provider 2017-11-22 23:59:52 +13:00
Anton Tananaev e51f590e19 Merge pull request #297 from Mantas0726/master
Update PositionProvider.java
2017-11-15 09:57:45 +13:00
Mantas0726 6e3812320c Update PositionProvider.java 2017-11-14 22:20:11 +02:00
25 изменённых файлов: 255 добавлений и 355 удалений
+16 -15
Просмотреть файл
@@ -1,22 +1,23 @@
apply plugin: 'com.android.application' apply plugin: 'com.android.application'
android { android {
compileSdkVersion 26 compileSdkVersion 28
buildToolsVersion '26.0.1' buildToolsVersion '28.0.2'
defaultConfig { defaultConfig {
applicationId "org.traccar.client" applicationId "org.traccar.client"
buildConfigField "boolean", "HIDDEN_APP", "false" buildConfigField "boolean", "HIDDEN_APP", "false"
minSdkVersion 14 minSdkVersion 15
targetSdkVersion 26 targetSdkVersion 28
versionCode 42 versionCode 52
versionName '5.5' versionName '5.15'
} }
lintOptions { lintOptions {
checkReleaseBuilds false checkReleaseBuilds false
} }
flavorDimensions "default"
productFlavors { productFlavors {
regular regular
google google
@@ -26,24 +27,24 @@ android {
} }
} }
buildTypes { testOptions {
release { unitTests {
minifyEnabled false includeAndroidResources = true
proguardFiles getDefaultProguardFile('proguard-android.txt')
} }
} }
} }
dependencies { dependencies {
compile 'com.android.support:design:26.0.1' implementation 'com.android.support:design:28.0.0-rc02'
testCompile 'junit:junit:4.12' testImplementation 'junit:junit:4.12'
testCompile 'org.robolectric:robolectric:3.4.2' testImplementation 'org.robolectric:robolectric:3.8'
googleCompile 'com.google.firebase:firebase-core:11.2.0' googleImplementation 'com.google.firebase:firebase-core:16.0.3'
googleCompile 'com.google.firebase:firebase-crash:11.2.0' googleImplementation 'com.crashlytics.sdk.android:crashlytics:2.9.5'
} }
if (getGradle().getStartParameter().getTaskRequests().toString().contains("Google")) { if (getGradle().getStartParameter().getTaskRequests().toString().contains("Google")) {
apply plugin: 'com.google.gms.google-services' apply plugin: 'com.google.gms.google-services'
apply plugin: 'io.fabric'
task copyJson(type: Copy) { task copyJson(type: Copy) {
from '../../traccar-shared/google-services' from '../../traccar-shared/google-services'
+1 -1
Просмотреть файл
@@ -9,7 +9,7 @@
tools:replace="android:label"> tools:replace="android:label">
<activity <activity
android:name=".MainActivity"> android:name="org.traccar.client.MainActivity">
<intent-filter android:label="@string/app_name"> <intent-filter android:label="@string/app_name">
<action android:name="android.intent.action.VIEW" /> <action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" /> <category android:name="android.intent.category.DEFAULT" />
+9
Просмотреть файл
@@ -0,0 +1,9 @@
<vector xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp"
android:height="24dp"
android:viewportWidth="24.0"
android:viewportHeight="24.0">
<path
android:fillColor="#FFFFFFFF"
android:pathData="M12,10c-1.1,0 -2,0.9 -2,2s0.9,2 2,2 2,-0.9 2,-2 -0.9,-2 -2,-2zM19,3L5,3c-1.11,0 -2,0.9 -2,2v14c0,1.1 0.89,2 2,2h14c1.11,0 2,-0.9 2,-2L21,5c0,-1.1 -0.89,-2 -2,-2zM17.25,12c0,0.23 -0.02,0.46 -0.05,0.68l1.48,1.16c0.13,0.11 0.17,0.3 0.08,0.45l-1.4,2.42c-0.09,0.15 -0.27,0.21 -0.43,0.15l-1.74,-0.7c-0.36,0.28 -0.76,0.51 -1.18,0.69l-0.26,1.85c-0.03,0.17 -0.18,0.3 -0.35,0.3h-2.8c-0.17,0 -0.32,-0.13 -0.35,-0.29l-0.26,-1.85c-0.43,-0.18 -0.82,-0.41 -1.18,-0.69l-1.74,0.7c-0.16,0.06 -0.34,0 -0.43,-0.15l-1.4,-2.42c-0.09,-0.15 -0.05,-0.34 0.08,-0.45l1.48,-1.16c-0.03,-0.23 -0.05,-0.46 -0.05,-0.69 0,-0.23 0.02,-0.46 0.05,-0.68l-1.48,-1.16c-0.13,-0.11 -0.17,-0.3 -0.08,-0.45l1.4,-2.42c0.09,-0.15 0.27,-0.21 0.43,-0.15l1.74,0.7c0.36,-0.28 0.76,-0.51 1.18,-0.69l0.26,-1.85c0.03,-0.17 0.18,-0.3 0.35,-0.3h2.8c0.17,0 0.32,0.13 0.35,0.29l0.26,1.85c0.43,0.18 0.82,0.41 1.18,0.69l1.74,-0.7c0.16,-0.06 0.34,0 0.43,0.15l1.4,2.42c0.09,0.15 0.05,0.34 -0.08,0.45l-1.48,1.16c0.03,0.23 0.05,0.46 0.05,0.69z"/>
</vector>
+6
Просмотреть файл
@@ -9,15 +9,21 @@
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" /> <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED" /> <uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED" />
<uses-permission android:name="android.permission.WAKE_LOCK" /> <uses-permission android:name="android.permission.WAKE_LOCK" />
<uses-permission android:name="android.permission.FOREGROUND_SERVICE" />
<uses-permission android:name="com.android.launcher.permission.INSTALL_SHORTCUT" /> <uses-permission android:name="com.android.launcher.permission.INSTALL_SHORTCUT" />
<application <application
android:allowBackup="true" android:allowBackup="true"
android:networkSecurityConfig="@xml/network_security_config"
android:icon="@mipmap/ic_launcher" android:icon="@mipmap/ic_launcher"
android:label="@string/app_name" android:label="@string/app_name"
android:theme="@style/AppTheme" android:theme="@style/AppTheme"
android:name=".MainApplication"> android:name=".MainApplication">
<meta-data
android:name="google_analytics_adid_collection_enabled"
android:value="false" />
<activity <activity
android:name=".MainActivity" android:name=".MainActivity"
android:launchMode="singleTask" /> android:launchMode="singleTask" />
+1 -1
Просмотреть файл
@@ -26,7 +26,7 @@ public class AutostartReceiver extends WakefulBroadcastReceiver {
public void onReceive(Context context, Intent intent) { public void onReceive(Context context, Intent intent) {
SharedPreferences sharedPreferences = PreferenceManager.getDefaultSharedPreferences(context); SharedPreferences sharedPreferences = PreferenceManager.getDefaultSharedPreferences(context);
if (sharedPreferences.getBoolean(MainFragment.KEY_STATUS, false)) { if (sharedPreferences.getBoolean(MainFragment.KEY_STATUS, false)) {
startWakefulService(context, new Intent(context, TrackingService.class)); startWakefulForegroundService(context, new Intent(context, TrackingService.class));
} }
} }
+11 -3
Просмотреть файл
@@ -27,7 +27,7 @@ import java.util.Date;
public class DatabaseHelper extends SQLiteOpenHelper { public class DatabaseHelper extends SQLiteOpenHelper {
public static final int DATABASE_VERSION = 2; public static final int DATABASE_VERSION = 3;
public static final String DATABASE_NAME = "traccar.db"; public static final String DATABASE_NAME = "traccar.db";
public interface DatabaseHandler<T> { public interface DatabaseHandler<T> {
@@ -80,7 +80,8 @@ public class DatabaseHelper extends SQLiteOpenHelper {
"speed REAL," + "speed REAL," +
"course REAL," + "course REAL," +
"accuracy REAL," + "accuracy REAL," +
"battery REAL)"); "battery REAL," +
"mock INTEGER)");
} }
@Override @Override
@@ -89,6 +90,11 @@ public class DatabaseHelper extends SQLiteOpenHelper {
onCreate(db); onCreate(db);
} }
public void onDowngrade(SQLiteDatabase db, int oldVersion, int newVersion) {
db.execSQL("DROP TABLE IF EXISTS position;");
onCreate(db);
}
public void insertPosition(Position position) { public void insertPosition(Position position) {
ContentValues values = new ContentValues(); ContentValues values = new ContentValues();
values.put("deviceId", position.getDeviceId()); values.put("deviceId", position.getDeviceId());
@@ -98,8 +104,9 @@ public class DatabaseHelper extends SQLiteOpenHelper {
values.put("altitude", position.getAltitude()); values.put("altitude", position.getAltitude());
values.put("speed", position.getSpeed()); values.put("speed", position.getSpeed());
values.put("course", position.getCourse()); values.put("course", position.getCourse());
values.put("accuracy", position.getCourse()); values.put("accuracy", position.getAccuracy());
values.put("battery", position.getBattery()); values.put("battery", position.getBattery());
values.put("mock", position.getMock() ? 1 : 0);
db.insertOrThrow("position", null, values); db.insertOrThrow("position", null, values);
} }
@@ -133,6 +140,7 @@ public class DatabaseHelper extends SQLiteOpenHelper {
position.setCourse(cursor.getDouble(cursor.getColumnIndex("course"))); position.setCourse(cursor.getDouble(cursor.getColumnIndex("course")));
position.setAccuracy(cursor.getDouble(cursor.getColumnIndex("accuracy"))); position.setAccuracy(cursor.getDouble(cursor.getColumnIndex("accuracy")));
position.setBattery(cursor.getDouble(cursor.getColumnIndex("battery"))); position.setBattery(cursor.getDouble(cursor.getColumnIndex("battery")));
position.setMock(cursor.getInt(cursor.getColumnIndex("mock")) > 0);
} else { } else {
return null; return null;
-33
Просмотреть файл
@@ -1,33 +0,0 @@
/*
* Copyright 2017 Anton Tananaev (anton@traccar.org)
*
* 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.traccar.client;
public final class DistanceCalculator {
private static final double EQUATORIAL_EARTH_RADIUS = 6378.1370;
private static final double DEG_TO_RAD = Math.PI / 180;
public static double distance(double lat1, double lon1, double lat2, double lon2) {
double dlong = (lon2 - lon1) * DEG_TO_RAD;
double dlat = (lat2 - lat1) * DEG_TO_RAD;
double a = Math.pow(Math.sin(dlat / 2), 2)
+ Math.cos(lat1 * DEG_TO_RAD) * Math.cos(lat2 * DEG_TO_RAD) * Math.pow(Math.sin(dlong / 2), 2);
double c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1 - a));
double d = EQUATORIAL_EARTH_RADIUS * c;
return d * 1000;
}
}
+6 -18
Просмотреть файл
@@ -58,7 +58,7 @@ public class MainFragment extends PreferenceFragment implements OnSharedPreferen
public static final String KEY_INTERVAL = "interval"; public static final String KEY_INTERVAL = "interval";
public static final String KEY_DISTANCE = "distance"; public static final String KEY_DISTANCE = "distance";
public static final String KEY_ANGLE = "angle"; public static final String KEY_ANGLE = "angle";
public static final String KEY_PROVIDER = "provider"; public static final String KEY_ACCURACY = "accuracy";
public static final String KEY_STATUS = "status"; public static final String KEY_STATUS = "status";
private static final int PERMISSIONS_REQUEST_LOCATION = 2; private static final int PERMISSIONS_REQUEST_LOCATION = 2;
@@ -150,13 +150,6 @@ public class MainFragment extends PreferenceFragment implements OnSharedPreferen
} }
} }
private boolean hasPermission(String permission) {
if (Build.VERSION.SDK_INT <= Build.VERSION_CODES.LOLLIPOP_MR1) {
return true;
}
return ContextCompat.checkSelfPermission(getActivity(), permission) == PackageManager.PERMISSION_GRANTED;
}
@Override @Override
public void onResume() { public void onResume() {
super.onResume(); super.onResume();
@@ -175,7 +168,7 @@ public class MainFragment extends PreferenceFragment implements OnSharedPreferen
findPreference(KEY_INTERVAL).setEnabled(enabled); findPreference(KEY_INTERVAL).setEnabled(enabled);
findPreference(KEY_DISTANCE).setEnabled(enabled); findPreference(KEY_DISTANCE).setEnabled(enabled);
findPreference(KEY_ANGLE).setEnabled(enabled); findPreference(KEY_ANGLE).setEnabled(enabled);
findPreference(KEY_PROVIDER).setEnabled(enabled); findPreference(KEY_ACCURACY).setEnabled(enabled);
} }
@Override @Override
@@ -223,10 +216,10 @@ public class MainFragment extends PreferenceFragment implements OnSharedPreferen
private void startTrackingService(boolean checkPermission, boolean permission) { private void startTrackingService(boolean checkPermission, boolean permission) {
if (checkPermission) { if (checkPermission) {
Set<String> missingPermissions = new HashSet<>(); Set<String> missingPermissions = new HashSet<>();
if (!hasPermission(Manifest.permission.ACCESS_FINE_LOCATION)) { if (ContextCompat.checkSelfPermission(getActivity(), Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
missingPermissions.add(Manifest.permission.ACCESS_FINE_LOCATION); missingPermissions.add(Manifest.permission.ACCESS_FINE_LOCATION);
} }
if (!hasPermission(Manifest.permission.ACCESS_COARSE_LOCATION)) { if (ContextCompat.checkSelfPermission(getActivity(), Manifest.permission.ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
missingPermissions.add(Manifest.permission.ACCESS_COARSE_LOCATION); missingPermissions.add(Manifest.permission.ACCESS_COARSE_LOCATION);
} }
if (missingPermissions.isEmpty()) { if (missingPermissions.isEmpty()) {
@@ -247,13 +240,8 @@ public class MainFragment extends PreferenceFragment implements OnSharedPreferen
ALARM_MANAGER_INTERVAL, ALARM_MANAGER_INTERVAL, alarmIntent); ALARM_MANAGER_INTERVAL, ALARM_MANAGER_INTERVAL, alarmIntent);
} else { } else {
sharedPreferences.edit().putBoolean(KEY_STATUS, false).apply(); sharedPreferences.edit().putBoolean(KEY_STATUS, false).apply();
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.ICE_CREAM_SANDWICH) { TwoStatePreference preference = (TwoStatePreference) findPreference(KEY_STATUS);
TwoStatePreference preference = (TwoStatePreference) findPreference(KEY_STATUS); preference.setChecked(false);
preference.setChecked(false);
} else {
CheckBoxPreference preference = (CheckBoxPreference) findPreference(KEY_STATUS);
preference.setChecked(false);
}
} }
} }
-126
Просмотреть файл
@@ -1,126 +0,0 @@
/*
* Copyright 2015 - 2017 Anton Tananaev (anton.tananaev@gmail.com)
*
* 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.traccar.client;
import android.content.Context;
import android.location.GpsStatus;
import android.location.Location;
import android.location.LocationListener;
import android.location.LocationManager;
import android.os.Bundle;
import android.util.Log;
@SuppressWarnings("MissingPermission")
public class MixedPositionProvider extends PositionProvider implements LocationListener, GpsStatus.Listener {
private static final int FIX_TIMEOUT = 30 * 1000;
private LocationListener backupListener;
private long lastFixTime;
public MixedPositionProvider(Context context, PositionListener listener) {
super(context, listener);
}
public void startUpdates() {
lastFixTime = System.currentTimeMillis();
locationManager.addGpsStatusListener(this);
try {
locationManager.requestLocationUpdates(LocationManager.GPS_PROVIDER, requestInterval, 0, this);
} catch (IllegalArgumentException e) {
Log.w(TAG, e);
}
}
public void stopUpdates() {
locationManager.removeUpdates(this);
locationManager.removeGpsStatusListener(this);
stopBackupProvider();
}
private void startBackupProvider() {
Log.i(TAG, "backup provider start");
if (backupListener == null) {
backupListener = new LocationListener() {
@Override
public void onLocationChanged(Location location) {
Log.i(TAG, "backup provider location");
updateLocation(location);
}
@Override
public void onStatusChanged(String s, int i, Bundle bundle) {
}
@Override
public void onProviderEnabled(String s) {
}
@Override
public void onProviderDisabled(String s) {
}
};
try {
locationManager.requestLocationUpdates(
LocationManager.NETWORK_PROVIDER, requestInterval, 0, backupListener);
} catch (IllegalArgumentException e) {
Log.w(TAG, e);
}
}
}
private void stopBackupProvider() {
Log.i(TAG, "backup provider stop");
if (backupListener != null) {
locationManager.removeUpdates(backupListener);
backupListener = null;
}
}
@Override
public void onLocationChanged(Location location) {
Log.i(TAG, "provider location");
stopBackupProvider();
lastFixTime = System.currentTimeMillis();
updateLocation(location);
}
@Override
public void onStatusChanged(String provider, int status, Bundle extras) {
}
@Override
public void onProviderEnabled(String provider) {
Log.i(TAG, "provider enabled");
stopBackupProvider();
}
@Override
public void onProviderDisabled(String provider) {
Log.i(TAG, "provider disabled");
startBackupProvider();
}
@Override
public void onGpsStatusChanged(int event) {
if (backupListener == null && System.currentTimeMillis() - lastFixTime - requestInterval > FIX_TIMEOUT) {
startBackupProvider();
}
}
}
+15 -1
Просмотреть файл
@@ -1,5 +1,5 @@
/* /*
* Copyright 2015 - 2017 Anton Tananaev (anton.tananaev@gmail.com) * Copyright 2015 - 2018 Anton Tananaev (anton.tananaev@gmail.com)
* *
* Licensed under the Apache License, Version 2.0 (the "License"); * Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License. * you may not use this file except in compliance with the License.
@@ -17,6 +17,7 @@ package org.traccar.client;
import android.location.Location; import android.location.Location;
import android.location.LocationManager; import android.location.LocationManager;
import android.os.Build;
import java.util.Date; import java.util.Date;
@@ -37,6 +38,9 @@ public class Position {
accuracy = location.getAccuracy(); accuracy = location.getAccuracy();
} }
this.battery = battery; this.battery = battery;
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR2) {
this.mock = location.isFromMockProvider();
}
} }
private long id; private long id;
@@ -139,4 +143,14 @@ public class Position {
this.battery = battery; this.battery = battery;
} }
private boolean mock;
public boolean getMock() {
return mock;
}
public void setMock(boolean mock) {
this.mock = mock;
}
} }
+52 -21
Просмотреть файл
@@ -15,19 +15,23 @@
*/ */
package org.traccar.client; package org.traccar.client;
import android.annotation.SuppressLint;
import android.content.Context; import android.content.Context;
import android.content.Intent; import android.content.Intent;
import android.content.IntentFilter; import android.content.IntentFilter;
import android.content.SharedPreferences; import android.content.SharedPreferences;
import android.location.Location; import android.location.Location;
import android.location.LocationListener;
import android.location.LocationManager; import android.location.LocationManager;
import android.os.BatteryManager; import android.os.BatteryManager;
import android.os.Bundle;
import android.preference.PreferenceManager; import android.preference.PreferenceManager;
import android.util.Log; import android.util.Log;
import android.widget.Toast;
public abstract class PositionProvider { public class PositionProvider implements LocationListener {
protected static final String TAG = PositionProvider.class.getSimpleName(); private static final String TAG = PositionProvider.class.getSimpleName();
private static final int MINIMUM_INTERVAL = 1000; private static final int MINIMUM_INTERVAL = 1000;
@@ -38,14 +42,13 @@ public abstract class PositionProvider {
private final PositionListener listener; private final PositionListener listener;
private final Context context; private final Context context;
protected final LocationManager locationManager; private SharedPreferences preferences;
private LocationManager locationManager;
private String deviceId; private String deviceId;
protected String type; private long interval;
protected long requestInterval; private double distance;
protected long interval; private double angle;
protected double distance;
protected double angle;
private Location lastLocation; private Location lastLocation;
@@ -53,31 +56,43 @@ public abstract class PositionProvider {
this.context = context; this.context = context;
this.listener = listener; this.listener = listener;
SharedPreferences preferences = PreferenceManager.getDefaultSharedPreferences(context);
locationManager = (LocationManager) context.getSystemService(Context.LOCATION_SERVICE); locationManager = (LocationManager) context.getSystemService(Context.LOCATION_SERVICE);
preferences = PreferenceManager.getDefaultSharedPreferences(context);
deviceId = preferences.getString(MainFragment.KEY_DEVICE, "undefined"); deviceId = preferences.getString(MainFragment.KEY_DEVICE, "undefined");
interval = Long.parseLong(preferences.getString(MainFragment.KEY_INTERVAL, "600")) * 1000; interval = Long.parseLong(preferences.getString(MainFragment.KEY_INTERVAL, "600")) * 1000;
distance = Integer.parseInt(preferences.getString(MainFragment.KEY_DISTANCE, "0")); distance = Integer.parseInt(preferences.getString(MainFragment.KEY_DISTANCE, "0"));
angle = Integer.parseInt(preferences.getString(MainFragment.KEY_ANGLE, "0")); angle = Integer.parseInt(preferences.getString(MainFragment.KEY_ANGLE, "0"));
if (distance > 0 || angle > 0) {
requestInterval = MINIMUM_INTERVAL;
} else {
requestInterval = interval;
}
type = preferences.getString(MainFragment.KEY_PROVIDER, "gps");
} }
public abstract void startUpdates(); @SuppressLint("MissingPermission")
public void startUpdates() {
try {
locationManager.requestLocationUpdates(
getProvider(preferences.getString(MainFragment.KEY_ACCURACY, "medium")),
distance > 0 || angle > 0 ? MINIMUM_INTERVAL : interval, 0, this);
} catch (RuntimeException e) {
Toast.makeText(context, e.getMessage(), Toast.LENGTH_LONG).show();
}
}
public abstract void stopUpdates(); public static String getProvider(String accuracy) {
switch (accuracy) {
case "high":
return LocationManager.GPS_PROVIDER;
case "low":
return LocationManager.PASSIVE_PROVIDER;
default:
return LocationManager.NETWORK_PROVIDER;
}
}
protected void updateLocation(Location location) { @Override
public void onLocationChanged(Location location) {
if (location != null && (lastLocation == null if (location != null && (lastLocation == null
|| location.getTime() - lastLocation.getTime() >= interval || location.getTime() - lastLocation.getTime() >= interval
|| distance > 0 && DistanceCalculator.distance(location.getLatitude(), location.getLongitude(), lastLocation.getLatitude(), location.getLongitude()) >= distance || distance > 0 && location.distanceTo(lastLocation) >= distance
|| angle > 0 && Math.abs(location.getBearing() - lastLocation.getBearing()) >= angle)) { || angle > 0 && Math.abs(location.getBearing() - lastLocation.getBearing()) >= angle)) {
Log.i(TAG, "location new"); Log.i(TAG, "location new");
lastLocation = location; lastLocation = location;
@@ -87,6 +102,22 @@ public abstract class PositionProvider {
} }
} }
@Override
public void onStatusChanged(String provider, int status, Bundle extras) {
}
@Override
public void onProviderEnabled(String provider) {
}
@Override
public void onProviderDisabled(String provider) {
}
public void stopUpdates() {
locationManager.removeUpdates(this);
}
public static double getBatteryLevel(Context context) { public static double getBatteryLevel(Context context) {
Intent batteryIntent = context.registerReceiver(null, new IntentFilter(Intent.ACTION_BATTERY_CHANGED)); Intent batteryIntent = context.registerReceiver(null, new IntentFilter(Intent.ACTION_BATTERY_CHANGED));
if (batteryIntent != null) { if (batteryIntent != null) {
+4
Просмотреть файл
@@ -36,6 +36,10 @@ public class ProtocolFormatter {
.appendQueryParameter("accuracy", String.valueOf(position.getAccuracy())) .appendQueryParameter("accuracy", String.valueOf(position.getAccuracy()))
.appendQueryParameter("batt", String.valueOf(position.getBattery())); .appendQueryParameter("batt", String.valueOf(position.getBattery()));
if (position.getMock()) {
builder.appendQueryParameter("mock", String.valueOf(position.getMock()));
}
if (alarm != null) { if (alarm != null) {
builder.appendQueryParameter("alarm", alarm); builder.appendQueryParameter("alarm", alarm);
} }
+58 -26
Просмотреть файл
@@ -18,9 +18,13 @@ package org.traccar.client;
import android.content.Context; import android.content.Context;
import android.content.Intent; import android.content.Intent;
import android.content.SharedPreferences; import android.content.SharedPreferences;
import android.content.pm.PackageManager;
import android.location.Criteria;
import android.location.Location; import android.location.Location;
import android.location.LocationListener;
import android.location.LocationManager; import android.location.LocationManager;
import android.os.Bundle; import android.os.Bundle;
import android.os.Looper;
import android.preference.PreferenceManager; import android.preference.PreferenceManager;
import android.support.annotation.DrawableRes; import android.support.annotation.DrawableRes;
import android.support.v4.content.ContextCompat; import android.support.v4.content.ContextCompat;
@@ -102,39 +106,62 @@ public class ShortcutActivity extends AppCompatActivity {
@SuppressWarnings("MissingPermission") @SuppressWarnings("MissingPermission")
private void sendAlarm() { private void sendAlarm() {
SharedPreferences preferences = PreferenceManager.getDefaultSharedPreferences(this); SharedPreferences preferences = PreferenceManager.getDefaultSharedPreferences(this);
LocationManager locationManager = (LocationManager) getSystemService(Context.LOCATION_SERVICE); LocationManager locationManager = (LocationManager) getSystemService(Context.LOCATION_SERVICE);
Location location = locationManager.getLastKnownLocation(LocationManager.GPS_PROVIDER); String provider = PositionProvider.getProvider(
if (location == null) { preferences.getString(MainFragment.KEY_ACCURACY, "medium"));
location = locationManager.getLastKnownLocation(LocationManager.NETWORK_PROVIDER);
}
if (location != null) { try {
Location location = locationManager.getLastKnownLocation(LocationManager.PASSIVE_PROVIDER);
Position position = new Position( if (location != null) {
preferences.getString(MainFragment.KEY_DEVICE, null), sendAlarmLocation(location);
location, PositionProvider.getBatteryLevel(this)); } else {
locationManager.requestSingleUpdate(provider, new LocationListener() {
String request = ProtocolFormatter.formatRequest( @Override
preferences.getString(MainFragment.KEY_URL, null), position, ALARM_SOS); public void onLocationChanged(Location location) {
sendAlarmLocation(location);
RequestManager.sendRequestAsync(request, new RequestManager.RequestHandler() {
@Override
public void onComplete(boolean success) {
if (success) {
Toast.makeText(ShortcutActivity.this, R.string.status_send_success, Toast.LENGTH_SHORT).show();
} else {
Toast.makeText(ShortcutActivity.this, R.string.status_send_fail, Toast.LENGTH_SHORT).show();
} }
}
});
} else { @Override
Toast.makeText(this, R.string.status_send_fail, Toast.LENGTH_SHORT).show(); public void onStatusChanged(String provider, int status, Bundle extras) {
}
@Override
public void onProviderEnabled(String provider) {
}
@Override
public void onProviderDisabled(String provider) {
}
}, Looper.myLooper());
}
} catch (RuntimeException e) {
Toast.makeText(this, e.getMessage(), Toast.LENGTH_LONG).show();
} }
} }
private void sendAlarmLocation(Location location) {
SharedPreferences preferences = PreferenceManager.getDefaultSharedPreferences(this);
Position position = new Position(
preferences.getString(MainFragment.KEY_DEVICE, null),
location, PositionProvider.getBatteryLevel(this));
String request = ProtocolFormatter.formatRequest(
preferences.getString(MainFragment.KEY_URL, null), position, ALARM_SOS);
RequestManager.sendRequestAsync(request, new RequestManager.RequestHandler() {
@Override
public void onComplete(boolean success) {
if (success) {
Toast.makeText(ShortcutActivity.this, R.string.status_send_success, Toast.LENGTH_SHORT).show();
} else {
Toast.makeText(ShortcutActivity.this, R.string.status_send_fail, Toast.LENGTH_SHORT).show();
}
}
});
}
private boolean executeAction(Intent intent) { private boolean executeAction(Intent intent) {
String action; String action;
if (intent.hasExtra("shortcutAction")) { if (intent.hasExtra("shortcutAction")) {
@@ -158,7 +185,12 @@ public class ShortcutActivity extends AppCompatActivity {
Toast.makeText(this, R.string.status_service_destroy, Toast.LENGTH_SHORT).show(); Toast.makeText(this, R.string.status_service_destroy, Toast.LENGTH_SHORT).show();
break; break;
case ACTION_SOS: case ACTION_SOS:
sendAlarm(); if (ContextCompat.checkSelfPermission(this, android.Manifest.permission.ACCESS_FINE_LOCATION) == PackageManager.PERMISSION_GRANTED
&& ContextCompat.checkSelfPermission(this, android.Manifest.permission.ACCESS_COARSE_LOCATION) == PackageManager.PERMISSION_GRANTED) {
sendAlarm();
} else {
Toast.makeText(this, R.string.status_send_fail, Toast.LENGTH_SHORT).show();
}
break; break;
} }
finish(); finish();
-64
Просмотреть файл
@@ -1,64 +0,0 @@
/*
* Copyright 2015 Anton Tananaev (anton.tananaev@gmail.com)
*
* 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.traccar.client;
import android.content.Context;
import android.location.Location;
import android.location.LocationListener;
import android.location.LocationManager;
import android.os.Bundle;
import android.util.Log;
@SuppressWarnings("MissingPermission")
public class SimplePositionProvider extends PositionProvider implements LocationListener {
public SimplePositionProvider(Context context, PositionListener listener) {
super(context, listener);
if (!type.equals(LocationManager.NETWORK_PROVIDER)) {
type = LocationManager.GPS_PROVIDER;
}
}
public void startUpdates() {
try {
locationManager.requestLocationUpdates(type, requestInterval, 0, this);
} catch (IllegalArgumentException e) {
Log.w(TAG, e);
}
}
public void stopUpdates() {
locationManager.removeUpdates(this);
}
@Override
public void onLocationChanged(Location location) {
updateLocation(location);
}
@Override
public void onStatusChanged(String provider, int status, Bundle extras) {
}
@Override
public void onProviderEnabled(String provider) {
}
@Override
public void onProviderDisabled(String provider) {
}
}
+1 -1
Просмотреть файл
@@ -43,7 +43,7 @@ public class StatusActivity extends AppCompatActivity {
} }
public static void addMessage(String message) { public static void addMessage(String message) {
DateFormat format = DateFormat.getTimeInstance(DateFormat.SHORT); DateFormat format = DateFormat.getTimeInstance(DateFormat.MEDIUM);
message = format.format(new Date()) + " - " + message; message = format.format(new Date()) + " - " + message;
messages.add(message); messages.add(message);
while (messages.size() > LIMIT) { while (messages.size() > LIMIT) {
+3 -6
Просмотреть файл
@@ -57,11 +57,7 @@ public class TrackingController implements PositionProvider.PositionListener, Ne
this.context = context; this.context = context;
handler = new Handler(); handler = new Handler();
preferences = PreferenceManager.getDefaultSharedPreferences(context); preferences = PreferenceManager.getDefaultSharedPreferences(context);
if (preferences.getString(MainFragment.KEY_PROVIDER, "gps").equals("mixed")) { positionProvider = new PositionProvider(context, this);
positionProvider = new MixedPositionProvider(context, this);
} else {
positionProvider = new SimplePositionProvider(context, this);
}
databaseHelper = new DatabaseHelper(context); databaseHelper = new DatabaseHelper(context);
networkManager = new NetworkManager(context, this); networkManager = new NetworkManager(context, this);
isOnline = networkManager.isOnline(); isOnline = networkManager.isOnline();
@@ -104,7 +100,8 @@ public class TrackingController implements PositionProvider.PositionListener, Ne
@Override @Override
public void onNetworkUpdate(boolean isOnline) { public void onNetworkUpdate(boolean isOnline) {
StatusActivity.addMessage(context.getString(R.string.status_connectivity_change)); int message = isOnline ? R.string.status_network_online : R.string.status_network_offline;
StatusActivity.addMessage(context.getString(message));
if (!this.isOnline && isOnline) { if (!this.isOnline && isOnline) {
read(); read();
} }
+27 -12
Просмотреть файл
@@ -21,6 +21,7 @@ import android.app.PendingIntent;
import android.app.Service; import android.app.Service;
import android.content.Context; import android.content.Context;
import android.content.Intent; import android.content.Intent;
import android.content.pm.PackageManager;
import android.os.Build; import android.os.Build;
import android.os.IBinder; import android.os.IBinder;
import android.support.v4.app.NotificationCompat; import android.support.v4.app.NotificationCompat;
@@ -35,16 +36,24 @@ public class TrackingService extends Service {
private TrackingController trackingController; private TrackingController trackingController;
private static Notification createNotification(Context context) { private static Notification createNotification(Context context) {
PendingIntent pendingIntent = PendingIntent.getActivity(context, 0, new Intent(context, MainActivity.class), 0); NotificationCompat.Builder builder = new NotificationCompat.Builder(context, MainApplication.PRIMARY_CHANNEL)
return new NotificationCompat.Builder(context, MainApplication.PRIMARY_CHANNEL) .setSmallIcon(R.drawable.ic_stat_notify)
.setContentTitle(context.getString(R.string.app_name)) .setPriority(NotificationCompat.PRIORITY_LOW)
.setContentText(context.getString(R.string.settings_status_on_summary)) .setCategory(Notification.CATEGORY_SERVICE);
.setContentIntent(pendingIntent) Intent intent;
.setPriority(NotificationCompat.PRIORITY_MIN) if (!BuildConfig.HIDDEN_APP) {
.build(); intent = new Intent(context, MainActivity.class);
builder
.setContentTitle(context.getString(R.string.settings_status_on_summary))
.setTicker(context.getString(R.string.settings_status_on_summary))
.setColor(ContextCompat.getColor(context, R.color.primary_dark));
} else {
intent = new Intent(android.provider.Settings.ACTION_SETTINGS);
}
builder.setContentIntent(PendingIntent.getActivity(context, 0, intent, 0));
return builder.build();
} }
@TargetApi(Build.VERSION_CODES.ECLAIR)
public static class HideNotificationService extends Service { public static class HideNotificationService extends Service {
@Override @Override
public IBinder onBind(Intent intent) { public IBinder onBind(Intent intent) {
@@ -69,11 +78,17 @@ public class TrackingService extends Service {
Log.i(TAG, "service create"); Log.i(TAG, "service create");
StatusActivity.addMessage(getString(R.string.status_service_create)); StatusActivity.addMessage(getString(R.string.status_service_create));
trackingController = new TrackingController(this);
trackingController.start();
startForeground(NOTIFICATION_ID, createNotification(this)); startForeground(NOTIFICATION_ID, createNotification(this));
ContextCompat.startForegroundService(this, new Intent(this, HideNotificationService.class));
if (ContextCompat.checkSelfPermission(this, android.Manifest.permission.ACCESS_FINE_LOCATION) == PackageManager.PERMISSION_GRANTED
&& ContextCompat.checkSelfPermission(this, android.Manifest.permission.ACCESS_COARSE_LOCATION) == PackageManager.PERMISSION_GRANTED) {
trackingController = new TrackingController(this);
trackingController.start();
}
if (Build.VERSION.SDK_INT < Build.VERSION_CODES.O) {
ContextCompat.startForegroundService(this, new Intent(this, HideNotificationService.class));
}
} }
@Override @Override
+1 -1
Просмотреть файл
@@ -26,7 +26,7 @@ public abstract class WakefulBroadcastReceiver extends BroadcastReceiver {
private static final SparseArray<PowerManager.WakeLock> mActiveWakeLocks = new SparseArray<>(); private static final SparseArray<PowerManager.WakeLock> mActiveWakeLocks = new SparseArray<>();
private static int mNextId = 1; private static int mNextId = 1;
public static void startWakefulService(Context context, Intent intent) { public static void startWakefulForegroundService(Context context, Intent intent) {
synchronized (mActiveWakeLocks) { synchronized (mActiveWakeLocks) {
int id = mNextId; int id = mNextId;
mNextId++; mNextId++;
+10
Просмотреть файл
@@ -0,0 +1,10 @@
<vector
android:width="24dp"
android:height="24dp"
android:viewportHeight="72.0"
android:viewportWidth="72.0"
xmlns:android="http://schemas.android.com/apk/res/android">
<path
android:fillColor="#FF000000"
android:pathData="M36,0A36,36 0,0 0,0 36A36,36 0,0 0,36 72A36,36 0,0 0,72 36A36,36 0,0 0,36 0zM50.51,14.66C53.41,16.89 55.93,19.68 57.88,23.05C59.83,26.42 60.99,30 61.46,33.63L55.09,34.55C54.72,31.74 53.87,28.85 52.36,26.24C50.85,23.63 48.78,21.45 46.53,19.72L50.51,14.66zM42.82,24.85C44.4,26.08 45.77,27.58 46.84,29.43C47.91,31.27 48.52,33.21 48.79,35.2L42.42,36.12C42.25,34.95 41.95,33.7 41.32,32.61C40.69,31.53 39.77,30.64 38.84,29.91L42.82,24.85zM18.38,31.13L24.76,42.17L31.13,53.21A12.75,12.75 37.68,0 1,18.38 53.21A12.75,12.75 37.68,0 1,12.01 42.17A12.75,12.75 37.68,0 1,18.38 31.13zM32.96,34.21A3.19,3.19 60,0 1,35.8 35.8A3.19,3.19 60,0 1,34.63 40.15A3.19,3.19 60,0 1,30.28 38.99A3.19,3.19 60,0 1,31.45 34.63A3.19,3.19 60,0 1,32.96 34.21z"/>
</vector>
+7 -6
Просмотреть файл
@@ -20,11 +20,11 @@
<string name="settings_status_on">Stop</string> <string name="settings_status_on">Stop</string>
<string name="settings_status_off_summary">Service stopped</string> <string name="settings_status_off_summary">Service stopped</string>
<string name="settings_status_on_summary">Service running</string> <string name="settings_status_on_summary">Service running</string>
<string name="settings_provider_title">Location provider</string> <string name="settings_accuracy_title">Location accuracy</string>
<string name="settings_provider_summary">Source of location data</string> <string name="settings_accuracy_summary">Desired location accuracy</string>
<string name="settings_provider_gps">GPS provider</string> <string name="settings_accuracy_high">High</string>
<string name="settings_provider_network">Network provider</string> <string name="settings_accuracy_medium">Medium</string>
<string name="settings_provider_mixed">Mixed provider</string> <string name="settings_accuracy_low">Low</string>
<string name="settings_foreground_title">Foreground service</string> <string name="settings_foreground_title">Foreground service</string>
<string name="settings_foreground_summary">Increase service priority</string> <string name="settings_foreground_summary">Increase service priority</string>
<string name="menu_status">Status</string> <string name="menu_status">Status</string>
@@ -39,7 +39,8 @@
<string name="status_send_success">Send successfully</string> <string name="status_send_success">Send successfully</string>
<string name="status_send_fail">Send failed</string> <string name="status_send_fail">Send failed</string>
<string name="status_location_update">Location update</string> <string name="status_location_update">Location update</string>
<string name="status_connectivity_change">Connectivity change</string> <string name="status_network_online">Network online</string>
<string name="status_network_offline">Network offline</string>
<string name="hidden_app_name">Device Settings</string> <string name="hidden_app_name">Device Settings</string>
<string name="hidden_alert">The app has been hidden. To open it again please dial 8722227 (TRACCAR).</string> <string name="hidden_alert">The app has been hidden. To open it again please dial 8722227 (TRACCAR).</string>
<string name="error_msg_invalid_url">Please enter a valid http:// or https:// URL</string> <string name="error_msg_invalid_url">Please enter a valid http:// or https:// URL</string>
+8 -8
Просмотреть файл
@@ -3,16 +3,16 @@
<string name="settings_url_default_value" translatable="false">http://demo.traccar.org:5055</string> <string name="settings_url_default_value" translatable="false">http://demo.traccar.org:5055</string>
<string-array name="settings_provider_values" translatable="false"> <string-array name="settings_accuracy_values" translatable="false">
<item>gps</item> <item>high</item>
<item>network</item> <item>medium</item>
<item>mixed</item> <item>low</item>
</string-array> </string-array>
<string-array name="settings_provider_names"> <string-array name="settings_accuracy_names">
<item>@string/settings_provider_gps</item> <item>@string/settings_accuracy_high</item>
<item>@string/settings_provider_network</item> <item>@string/settings_accuracy_medium</item>
<item>@string/settings_provider_mixed</item> <item>@string/settings_accuracy_low</item>
</string-array> </string-array>
</resources> </resources>
+4
Просмотреть файл
@@ -0,0 +1,4 @@
<?xml version="1.0" encoding="utf-8"?>
<network-security-config>
<base-config cleartextTrafficPermitted="true" />
</network-security-config>
+8 -8
Просмотреть файл
@@ -20,6 +20,14 @@
android:summary="@string/settings_url_summary" android:summary="@string/settings_url_summary"
android:title="@string/settings_url_title" /> android:title="@string/settings_url_title" />
<ListPreference
android:defaultValue="medium"
android:entries="@array/settings_accuracy_names"
android:entryValues="@array/settings_accuracy_values"
android:key="accuracy"
android:summary="@string/settings_accuracy_summary"
android:title="@string/settings_accuracy_title" />
<EditTextPreference <EditTextPreference
android:defaultValue="300" android:defaultValue="300"
android:key="interval" android:key="interval"
@@ -41,12 +49,4 @@
android:summary="@string/settings_angle_summary" android:summary="@string/settings_angle_summary"
android:title="@string/settings_angle_title" /> android:title="@string/settings_angle_title" />
<ListPreference
android:defaultValue="gps"
android:entries="@array/settings_provider_names"
android:entryValues="@array/settings_provider_values"
android:key="provider"
android:summary="@string/settings_provider_summary"
android:title="@string/settings_provider_title" />
</PreferenceScreen> </PreferenceScreen>
+6 -3
Просмотреть файл
@@ -1,16 +1,19 @@
buildscript { buildscript {
repositories { repositories {
google()
jcenter() jcenter()
maven { url 'https://maven.fabric.io/public' }
} }
dependencies { dependencies {
classpath 'com.android.tools.build:gradle:2.3.3' classpath 'com.android.tools.build:gradle:3.1.4'
classpath 'com.google.gms:google-services:3.1.0' classpath 'com.google.gms:google-services:4.0.2'
classpath 'io.fabric.tools:gradle:1.25.4'
} }
} }
allprojects { allprojects {
repositories { repositories {
jcenter()
google() google()
jcenter()
} }
} }
+1 -1
Просмотреть файл
@@ -2,4 +2,4 @@ distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists distributionPath=wrapper/dists
zipStoreBase=GRADLE_USER_HOME zipStoreBase=GRADLE_USER_HOME
zipStorePath=wrapper/dists zipStorePath=wrapper/dists
distributionUrl=https\://services.gradle.org/distributions/gradle-4.1-all.zip distributionUrl=https\://services.gradle.org/distributions/gradle-4.5.1-all.zip