mirror of
https://code.briarproject.org/briar/briar.git
synced 2026-02-19 14:19:53 +01:00
Ask for coarse location permission before adding a contact.
This commit is contained in:
@@ -7,6 +7,7 @@
|
|||||||
<uses-feature android:name="android.hardware.camera" android:required="false"/>
|
<uses-feature android:name="android.hardware.camera" android:required="false"/>
|
||||||
<uses-feature android:name="android.hardware.touchscreen" android:required="false" />
|
<uses-feature android:name="android.hardware.touchscreen" android:required="false" />
|
||||||
|
|
||||||
|
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
|
||||||
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
|
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
|
||||||
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />
|
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />
|
||||||
<uses-permission android:name="android.permission.BLUETOOTH" />
|
<uses-permission android:name="android.permission.BLUETOOTH" />
|
||||||
|
|||||||
@@ -9,7 +9,7 @@ public interface RequestCodes {
|
|||||||
int REQUEST_WRITE_BLOG_POST = 5;
|
int REQUEST_WRITE_BLOG_POST = 5;
|
||||||
int REQUEST_SHARE_BLOG = 6;
|
int REQUEST_SHARE_BLOG = 6;
|
||||||
int REQUEST_RINGTONE = 7;
|
int REQUEST_RINGTONE = 7;
|
||||||
int REQUEST_PERMISSION_CAMERA = 8;
|
int REQUEST_PERMISSION_CAMERA_LOCATION = 8;
|
||||||
int REQUEST_DOZE_WHITELISTING = 9;
|
int REQUEST_DOZE_WHITELISTING = 9;
|
||||||
int REQUEST_BLUETOOTH_DISCOVERABLE = 10;
|
int REQUEST_BLUETOOTH_DISCOVERABLE = 10;
|
||||||
int REQUEST_UNLOCK = 11;
|
int REQUEST_UNLOCK = 11;
|
||||||
|
|||||||
@@ -3,7 +3,6 @@ package org.briarproject.briar.android.keyagreement;
|
|||||||
import android.bluetooth.BluetoothAdapter;
|
import android.bluetooth.BluetoothAdapter;
|
||||||
import android.content.BroadcastReceiver;
|
import android.content.BroadcastReceiver;
|
||||||
import android.content.Context;
|
import android.content.Context;
|
||||||
import android.content.DialogInterface.OnClickListener;
|
|
||||||
import android.content.Intent;
|
import android.content.Intent;
|
||||||
import android.content.IntentFilter;
|
import android.content.IntentFilter;
|
||||||
import android.os.Bundle;
|
import android.os.Bundle;
|
||||||
@@ -37,19 +36,21 @@ import java.util.logging.Logger;
|
|||||||
import javax.annotation.Nullable;
|
import javax.annotation.Nullable;
|
||||||
import javax.inject.Inject;
|
import javax.inject.Inject;
|
||||||
|
|
||||||
|
import static android.Manifest.permission.ACCESS_COARSE_LOCATION;
|
||||||
import static android.Manifest.permission.CAMERA;
|
import static android.Manifest.permission.CAMERA;
|
||||||
import static android.bluetooth.BluetoothAdapter.ACTION_REQUEST_DISCOVERABLE;
|
import static android.bluetooth.BluetoothAdapter.ACTION_REQUEST_DISCOVERABLE;
|
||||||
import static android.bluetooth.BluetoothAdapter.ACTION_SCAN_MODE_CHANGED;
|
import static android.bluetooth.BluetoothAdapter.ACTION_SCAN_MODE_CHANGED;
|
||||||
import static android.bluetooth.BluetoothAdapter.ACTION_STATE_CHANGED;
|
import static android.bluetooth.BluetoothAdapter.ACTION_STATE_CHANGED;
|
||||||
import static android.bluetooth.BluetoothAdapter.EXTRA_SCAN_MODE;
|
import static android.bluetooth.BluetoothAdapter.EXTRA_SCAN_MODE;
|
||||||
import static android.bluetooth.BluetoothAdapter.EXTRA_STATE;
|
import static android.bluetooth.BluetoothAdapter.EXTRA_STATE;
|
||||||
|
import static android.bluetooth.BluetoothAdapter.SCAN_MODE_CONNECTABLE;
|
||||||
import static android.bluetooth.BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE;
|
import static android.bluetooth.BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE;
|
||||||
import static android.bluetooth.BluetoothAdapter.STATE_ON;
|
import static android.bluetooth.BluetoothAdapter.STATE_ON;
|
||||||
import static android.content.pm.PackageManager.PERMISSION_GRANTED;
|
import static android.content.pm.PackageManager.PERMISSION_GRANTED;
|
||||||
import static android.os.Build.VERSION.SDK_INT;
|
import static android.os.Build.VERSION.SDK_INT;
|
||||||
import static android.widget.Toast.LENGTH_LONG;
|
import static android.widget.Toast.LENGTH_LONG;
|
||||||
import static org.briarproject.briar.android.activity.RequestCodes.REQUEST_BLUETOOTH_DISCOVERABLE;
|
import static org.briarproject.briar.android.activity.RequestCodes.REQUEST_BLUETOOTH_DISCOVERABLE;
|
||||||
import static org.briarproject.briar.android.activity.RequestCodes.REQUEST_PERMISSION_CAMERA;
|
import static org.briarproject.briar.android.activity.RequestCodes.REQUEST_PERMISSION_CAMERA_LOCATION;
|
||||||
|
|
||||||
@MethodsNotNullByDefault
|
@MethodsNotNullByDefault
|
||||||
@ParametersNotNullByDefault
|
@ParametersNotNullByDefault
|
||||||
@@ -68,7 +69,7 @@ public abstract class KeyAgreementActivity extends BriarActivity implements
|
|||||||
EventBus eventBus;
|
EventBus eventBus;
|
||||||
|
|
||||||
private boolean isResumed = false, wasAdapterEnabled = false;
|
private boolean isResumed = false, wasAdapterEnabled = false;
|
||||||
private boolean continueClicked, gotCameraPermission;
|
private boolean continueClicked, gotCameraPermission, gotLocationPermission;
|
||||||
private BluetoothState bluetoothState = BluetoothState.UNKNOWN;
|
private BluetoothState bluetoothState = BluetoothState.UNKNOWN;
|
||||||
private BroadcastReceiver bluetoothReceiver = null;
|
private BroadcastReceiver bluetoothReceiver = null;
|
||||||
|
|
||||||
@@ -155,12 +156,12 @@ public abstract class KeyAgreementActivity extends BriarActivity implements
|
|||||||
BluetoothAdapter bt = BluetoothAdapter.getDefaultAdapter();
|
BluetoothAdapter bt = BluetoothAdapter.getDefaultAdapter();
|
||||||
if (bt == null) {
|
if (bt == null) {
|
||||||
setBluetoothState(BluetoothState.NO_ADAPTER);
|
setBluetoothState(BluetoothState.NO_ADAPTER);
|
||||||
return;
|
} else {
|
||||||
|
setBluetoothState(BluetoothState.WAITING);
|
||||||
|
wasAdapterEnabled = bt.isEnabled();
|
||||||
|
Intent i = new Intent(ACTION_REQUEST_DISCOVERABLE);
|
||||||
|
startActivityForResult(i, REQUEST_BLUETOOTH_DISCOVERABLE);
|
||||||
}
|
}
|
||||||
setBluetoothState(BluetoothState.WAITING);
|
|
||||||
wasAdapterEnabled = bt.isEnabled();
|
|
||||||
Intent i = new Intent(ACTION_REQUEST_DISCOVERABLE);
|
|
||||||
startActivityForResult(i, REQUEST_BLUETOOTH_DISCOVERABLE);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private void setBluetoothState(BluetoothState bluetoothState) {
|
private void setBluetoothState(BluetoothState bluetoothState) {
|
||||||
@@ -202,62 +203,83 @@ public abstract class KeyAgreementActivity extends BriarActivity implements
|
|||||||
}
|
}
|
||||||
|
|
||||||
private boolean checkPermissions() {
|
private boolean checkPermissions() {
|
||||||
if (ContextCompat.checkSelfPermission(this, CAMERA) !=
|
gotCameraPermission = checkPermission(CAMERA);
|
||||||
PERMISSION_GRANTED) {
|
gotLocationPermission = checkPermission(ACCESS_COARSE_LOCATION);
|
||||||
// Should we show an explanation?
|
if (gotCameraPermission && gotLocationPermission) return true;
|
||||||
if (ActivityCompat.shouldShowRequestPermissionRationale(this,
|
// Should we show an explanation for one or both permissions?
|
||||||
CAMERA)) {
|
boolean cameraRationale = shouldShowRationale(CAMERA);
|
||||||
OnClickListener continueListener =
|
boolean locationRationale = shouldShowRationale(ACCESS_COARSE_LOCATION);
|
||||||
(dialog, which) -> requestPermission();
|
if (cameraRationale && locationRationale) {
|
||||||
Builder builder = new Builder(this, style.BriarDialogTheme);
|
showRationale(string.permission_camera_location_title,
|
||||||
builder.setTitle(string.permission_camera_title);
|
string.permission_camera_location_request_body);
|
||||||
builder.setMessage(string.permission_camera_request_body);
|
} else if (cameraRationale) {
|
||||||
builder.setNeutralButton(string.continue_button,
|
showRationale(string.permission_camera_title,
|
||||||
continueListener);
|
string.permission_camera_request_body);
|
||||||
builder.show();
|
} else if (locationRationale) {
|
||||||
} else {
|
showRationale(string.permission_location_title,
|
||||||
requestPermission();
|
string.permission_location_request_body);
|
||||||
}
|
} else if (gotCameraPermission) {
|
||||||
gotCameraPermission = false;
|
// Location permission has been permanently denied but we can
|
||||||
return false;
|
// continue without it
|
||||||
} else {
|
|
||||||
gotCameraPermission = true;
|
|
||||||
return true;
|
return true;
|
||||||
|
} else {
|
||||||
|
requestPermissions();
|
||||||
}
|
}
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
private void requestPermission() {
|
private boolean checkPermission(String permission) {
|
||||||
ActivityCompat.requestPermissions(this, new String[] {CAMERA},
|
return ContextCompat.checkSelfPermission(this, permission)
|
||||||
REQUEST_PERMISSION_CAMERA);
|
== PERMISSION_GRANTED;
|
||||||
|
}
|
||||||
|
|
||||||
|
private boolean shouldShowRationale(String permission) {
|
||||||
|
return ActivityCompat.shouldShowRequestPermissionRationale(this,
|
||||||
|
permission);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void showRationale(@StringRes int title, @StringRes int body) {
|
||||||
|
Builder builder = new Builder(this, style.BriarDialogTheme);
|
||||||
|
builder.setTitle(title);
|
||||||
|
builder.setMessage(body);
|
||||||
|
builder.setNeutralButton(string.continue_button,
|
||||||
|
(dialog, which) -> requestPermissions());
|
||||||
|
builder.show();
|
||||||
|
}
|
||||||
|
|
||||||
|
private void requestPermissions() {
|
||||||
|
ActivityCompat.requestPermissions(this,
|
||||||
|
new String[] {CAMERA, ACCESS_COARSE_LOCATION},
|
||||||
|
REQUEST_PERMISSION_CAMERA_LOCATION);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@UiThread
|
@UiThread
|
||||||
public void onRequestPermissionsResult(int requestCode,
|
public void onRequestPermissionsResult(int requestCode,
|
||||||
String permissions[], int[] grantResults) {
|
String permissions[], int[] grantResults) {
|
||||||
if (requestCode == REQUEST_PERMISSION_CAMERA) {
|
if (requestCode == REQUEST_PERMISSION_CAMERA_LOCATION) {
|
||||||
// If request is cancelled, the result arrays are empty.
|
// If request is cancelled, the result arrays are empty
|
||||||
if (grantResults.length > 0 &&
|
gotCameraPermission = grantResults.length > 0
|
||||||
grantResults[0] == PERMISSION_GRANTED) {
|
&& grantResults[0] == PERMISSION_GRANTED;
|
||||||
gotCameraPermission = true;
|
gotLocationPermission = grantResults.length > 1
|
||||||
|
&& grantResults[1] == PERMISSION_GRANTED;
|
||||||
|
if (gotCameraPermission) {
|
||||||
showNextScreen();
|
showNextScreen();
|
||||||
} else {
|
} else {
|
||||||
if (!ActivityCompat.shouldShowRequestPermissionRationale(this,
|
if (shouldShowRationale(CAMERA)) {
|
||||||
CAMERA)) {
|
Toast.makeText(this, string.permission_camera_denied_toast,
|
||||||
|
LENGTH_LONG).show();
|
||||||
|
supportFinishAfterTransition();
|
||||||
|
} else {
|
||||||
// The user has permanently denied the request
|
// The user has permanently denied the request
|
||||||
OnClickListener cancelListener =
|
|
||||||
(dialog, which) -> supportFinishAfterTransition();
|
|
||||||
Builder builder = new Builder(this, style.BriarDialogTheme);
|
Builder builder = new Builder(this, style.BriarDialogTheme);
|
||||||
builder.setTitle(string.permission_camera_title);
|
builder.setTitle(string.permission_camera_title);
|
||||||
builder.setMessage(string.permission_camera_denied_body);
|
builder.setMessage(string.permission_camera_denied_body);
|
||||||
builder.setPositiveButton(string.ok,
|
builder.setPositiveButton(string.ok,
|
||||||
UiUtils.getGoToSettingsListener(this));
|
UiUtils.getGoToSettingsListener(this));
|
||||||
builder.setNegativeButton(string.cancel, cancelListener);
|
builder.setNegativeButton(string.cancel,
|
||||||
|
(dialog, which) -> supportFinishAfterTransition());
|
||||||
builder.show();
|
builder.show();
|
||||||
} else {
|
|
||||||
Toast.makeText(this, string.permission_camera_denied_toast,
|
|
||||||
LENGTH_LONG).show();
|
|
||||||
supportFinishAfterTransition();
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -274,9 +296,11 @@ public abstract class KeyAgreementActivity extends BriarActivity implements
|
|||||||
setBluetoothState(BluetoothState.ENABLED);
|
setBluetoothState(BluetoothState.ENABLED);
|
||||||
else setBluetoothState(BluetoothState.UNKNOWN);
|
else setBluetoothState(BluetoothState.UNKNOWN);
|
||||||
} else if (ACTION_SCAN_MODE_CHANGED.equals(action)) {
|
} else if (ACTION_SCAN_MODE_CHANGED.equals(action)) {
|
||||||
int scanMode = intent.getIntExtra(EXTRA_SCAN_MODE, -1);
|
int scanMode = intent.getIntExtra(EXTRA_SCAN_MODE, 0);
|
||||||
if (scanMode == SCAN_MODE_CONNECTABLE_DISCOVERABLE)
|
if (scanMode == SCAN_MODE_CONNECTABLE_DISCOVERABLE)
|
||||||
setBluetoothState(BluetoothState.DISCOVERABLE);
|
setBluetoothState(BluetoothState.DISCOVERABLE);
|
||||||
|
else if (scanMode == SCAN_MODE_CONNECTABLE)
|
||||||
|
setBluetoothState(BluetoothState.ENABLED);
|
||||||
else setBluetoothState(BluetoothState.UNKNOWN);
|
else setBluetoothState(BluetoothState.UNKNOWN);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -467,6 +467,10 @@
|
|||||||
<!-- Permission Requests -->
|
<!-- Permission Requests -->
|
||||||
<string name="permission_camera_title">Camera permission</string>
|
<string name="permission_camera_title">Camera permission</string>
|
||||||
<string name="permission_camera_request_body">To scan the QR code, Briar needs access to the camera.</string>
|
<string name="permission_camera_request_body">To scan the QR code, Briar needs access to the camera.</string>
|
||||||
|
<string name="permission_location_title">Location permission</string>
|
||||||
|
<string name="permission_location_request_body">To discover Bluetooth devices, Briar needs permission to access your location.\n\nBriar does not store your location or share it with anyone.</string>
|
||||||
|
<string name="permission_camera_location_title">Camera and location</string>
|
||||||
|
<string name="permission_camera_location_request_body">To scan the QR code, Briar needs access to the camera.\n\nTo discover Bluetooth devices, Briar needs permission to access your location.\n\nBriar does not store your location or share it with anyone.</string>
|
||||||
<string name="permission_camera_denied_body">You have denied access to the camera, but adding contacts requires using the camera.\n\nPlease consider granting access.</string>
|
<string name="permission_camera_denied_body">You have denied access to the camera, but adding contacts requires using the camera.\n\nPlease consider granting access.</string>
|
||||||
<string name="permission_camera_denied_toast">Camera permission was not granted</string>
|
<string name="permission_camera_denied_toast">Camera permission was not granted</string>
|
||||||
<string name="qr_code">QR code</string>
|
<string name="qr_code">QR code</string>
|
||||||
|
|||||||
Reference in New Issue
Block a user