diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml index 5b34df692..5b671beee 100644 --- a/app/src/main/AndroidManifest.xml +++ b/app/src/main/AndroidManifest.xml @@ -65,10 +65,6 @@ - - - - services = getSupportedGattServices(); if (null == services || services.isEmpty()) { Log.w(TAG, "No BLE Services found for read"); throw new TagLostException(); } - for (BluetoothGattService mCustomService : services) { - Log.d("GattReadService", mCustomService.getUuid().toString()); + for (BluetoothGattService customService : services) { + Log.d("GattReadService", customService.getUuid().toString()); /*get the read characteristic from the service*/ BluetoothGattCharacteristic mReadCharacteristic = - mCustomService.getCharacteristic(FlaskRX); + customService.getCharacteristic(FlaskRX); try { if (mBluetoothGatt.readCharacteristic(mReadCharacteristic)) { - serviceRead = mCustomService.getUuid(); + mCustomService = mBluetoothGatt.getService(customService.getUuid()); break; } } catch (NullPointerException ignored) { } } - if (null == serviceRead) { + } + + if (null != mCustomService) { + BluetoothGattCharacteristic mReadCharacteristic = + mCustomService.getCharacteristic(FlaskRX); + if (!mBluetoothGatt.readCharacteristic(mReadCharacteristic)) { Log.w(TAG, "Failed to read characteristic"); throw new TagLostException(); } + } else { + Log.w(TAG, "Failed to read characteristic"); + throw new TagLostException(); } } @@ -330,46 +325,45 @@ public void writeCustomCharacteristic(int value) throws TagLostException { throw new TagLostException(); } - if (null != serviceWrite) { - BluetoothGattService mCustomService = mBluetoothGatt.getService(serviceWrite); - /*check if the service is available on the device*/ - if (mCustomService == null) { - serviceWrite = null; - Log.w(TAG, "BLE Service not found for write"); - return; - } - BluetoothGattCharacteristic mWriteCharacteristic = mCustomService.getCharacteristic(FlaskTX); - - mWriteCharacteristic.setValue(value, BluetoothGattCharacteristic.FORMAT_UINT8, 0); - if (mBluetoothGatt.writeCharacteristic(mWriteCharacteristic)) { - Log.w(TAG, "Failed to write characteristic"); - throw new TagLostException(); - } - } else { + BluetoothGattService mCustomService = mBluetoothGatt.getService(FlaskNUS); + /*check if the service is available on the device*/ + if (null == mCustomService) { List services = getSupportedGattServices(); if (null == services || services.isEmpty()) { Log.w(TAG, "No BLE Services found for write"); throw new TagLostException(); } - for (BluetoothGattService mCustomService : services) { - Log.d("GattWriteService", mCustomService.getUuid().toString()); + for (BluetoothGattService customService : services) { + Log.d("GattWriteService", customService.getUuid().toString()); /*get the read characteristic from the service*/ - BluetoothGattCharacteristic mWriteCharacteristic = mCustomService.getCharacteristic(FlaskTX); + BluetoothGattCharacteristic mWriteCharacteristic = + customService.getCharacteristic(FlaskTX); - mWriteCharacteristic.setValue(value, BluetoothGattCharacteristic.FORMAT_UINT8, 0); + mWriteCharacteristic.setValue(value, + BluetoothGattCharacteristic.FORMAT_UINT8, 0); try { if (mBluetoothGatt.writeCharacteristic(mWriteCharacteristic)) { - serviceWrite = mCustomService.getUuid(); + mCustomService = mBluetoothGatt.getService(customService.getUuid()); break; } } catch (NullPointerException ignored) { } } + } + + if (null != mCustomService) { + BluetoothGattCharacteristic mWriteCharacteristic = + mCustomService.getCharacteristic(FlaskTX); - if (null == serviceWrite) { + mWriteCharacteristic.setValue(value, + BluetoothGattCharacteristic.FORMAT_UINT8, 0); + if (mBluetoothGatt.writeCharacteristic(mWriteCharacteristic)) { Log.w(TAG, "Failed to write characteristic"); throw new TagLostException(); } + } else { + Log.w(TAG, "Failed to write characteristic"); + throw new TagLostException(); } } } diff --git a/app/src/main/java/com/hiddenramblings/tagmo/FlaskFragment.java b/app/src/main/java/com/hiddenramblings/tagmo/FlaskFragment.java index 612d54f27..1aac93788 100644 --- a/app/src/main/java/com/hiddenramblings/tagmo/FlaskFragment.java +++ b/app/src/main/java/com/hiddenramblings/tagmo/FlaskFragment.java @@ -6,19 +6,21 @@ import android.bluetooth.BluetoothAdapter; import android.bluetooth.BluetoothDevice; import android.bluetooth.BluetoothManager; -import android.content.ActivityNotFoundException; -import android.content.BroadcastReceiver; +import android.bluetooth.le.BluetoothLeScanner; +import android.bluetooth.le.ScanCallback; +import android.bluetooth.le.ScanFilter; +import android.bluetooth.le.ScanResult; +import android.bluetooth.le.ScanSettings; import android.content.ComponentName; import android.content.Context; import android.content.Intent; -import android.content.IntentFilter; import android.content.ServiceConnection; import android.content.pm.PackageManager; import android.nfc.TagLostException; import android.os.Build; import android.os.Bundle; import android.os.IBinder; -import android.provider.Settings; +import android.os.ParcelUuid; import android.util.Log; import android.view.LayoutInflater; import android.view.View; @@ -36,14 +38,12 @@ import androidx.fragment.app.Fragment; import com.google.android.material.snackbar.Snackbar; -import com.hiddenramblings.tagmo.eightbit.charset.CharsetCompat; -import com.hiddenramblings.tagmo.eightbit.io.Debug; import com.hiddenramblings.tagmo.eightbit.material.IconifiedSnackbar; import com.hiddenramblings.tagmo.widget.Toasty; -import java.util.Locale; +import java.util.Collections; import java.util.Map; -import java.util.Set; +import java.util.UUID; @RequiresApi(api = Build.VERSION_CODES.JELLY_BEAN_MR2) @SuppressLint("MissingPermission") @@ -55,6 +55,7 @@ public class FlaskFragment extends Fragment { private ProgressBar progressBar; private Snackbar statusBar; private BluetoothAdapter mBluetoothAdapter; + private BluetoothAdapter.LeScanCallback scanCallback; private BluetoothLeService flaskService; private String flaskAddress; @@ -236,61 +237,39 @@ private BluetoothAdapter getBluetoothAdapter() { return null; } - ActivityResultLauncher onRequestPairing = registerForActivityResult( - new ActivityResultContracts.StartActivityForResult(), result -> selectBluetoothDevice()); - - @RequiresApi(api = Build.VERSION_CODES.KITKAT) - private final BroadcastReceiver pairingRequest = new BroadcastReceiver() { - @Override - public void onReceive(Context context, Intent intent) { - if (intent.getAction().equals("android.bluetooth.device.action.PAIRING_REQUEST")) { - try { - BluetoothDevice device = intent - .getParcelableExtra(BluetoothDevice.EXTRA_DEVICE); - if (device.getName().toLowerCase(Locale.ROOT).startsWith("flask")) { - device.setPin((String.valueOf(intent.getIntExtra( - "android.bluetooth.device.extra.PAIRING_KEY", 0 - ))).getBytes(CharsetCompat.UTF_8)); - device.setPairingConfirmation(true); - flaskAddress = device.getAddress(); - dismissFlaskDiscovery(); - showConnectionNotice(true); - startFlaskService(); - } else { - View bonded = getLayoutInflater().inflate(R.layout.bluetooth_device, - fragmentView, false); - bonded.setOnClickListener(view1 -> { - device.setPin((String.valueOf(intent.getIntExtra( - "android.bluetooth.device.extra.PAIRING_KEY", 0 - ))).getBytes(CharsetCompat.UTF_8)); - device.setPairingConfirmation(true); - flaskAddress = device.getAddress(); - dismissFlaskDiscovery(); - showConnectionNotice(false); - startFlaskService(); - }); - setButtonText(bonded, device); - } - } catch (Exception ex) { - Debug.Log(ex); - new Toasty(requireActivity()).Short(R.string.flask_failed); + private void scanBluetoothServices() { + progressBar.setVisibility(View.VISIBLE); + if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.LOLLIPOP) { + BluetoothLeScanner scanner = mBluetoothAdapter.getBluetoothLeScanner(); + ParcelUuid FlaskUUID = new ParcelUuid(BluetoothLeService.FlaskNUS); + ScanFilter filter = new ScanFilter.Builder().setServiceUuid(FlaskUUID).build(); + ScanSettings settings = new ScanSettings.Builder().build(); + ScanCallback callback = new ScanCallback() { + @Override + public void onScanResult(int callbackType, ScanResult result) { + super.onScanResult(callbackType, result); + flaskAddress = result.getDevice().getAddress(); + dismissFlaskDiscovery(); + showConnectionNotice(true); + startFlaskService(); } - } + }; + scanner.startScan(Collections.singletonList(filter), settings, callback); + } else { + scanCallback = (bluetoothDevice, i, bytes) -> { + flaskAddress = bluetoothDevice.getAddress(); + dismissFlaskDiscovery(); + showConnectionNotice(true); + startFlaskService(); + }; + mBluetoothAdapter.startLeScan(new UUID[]{ BluetoothLeService.FlaskNUS }, scanCallback); } - }; + } private void selectBluetoothDevice() { deviceList.removeAllViews(); - Set pairedDevices = mBluetoothAdapter.getBondedDevices(); - for (BluetoothDevice device : pairedDevices) { -// if (device.getName().toLowerCase(Locale.ROOT).startsWith("flask")) { -// flaskAddress = device.getAddress(); -// dismissFlaskDiscovery(); -// showConnectionNotice(true); -// startFlaskService(); -// break; -// } + for (BluetoothDevice device : mBluetoothAdapter.getBondedDevices()) { View bonded = getLayoutInflater().inflate(R.layout.bluetooth_device, fragmentView, false); bonded.setOnClickListener(view1 -> { @@ -301,26 +280,11 @@ private void selectBluetoothDevice() { }); setButtonText(bonded, device); } - View paired = getLayoutInflater().inflate(R.layout.bluetooth_device, + View scan = getLayoutInflater().inflate(R.layout.bluetooth_device, fragmentView, false); - paired.setOnClickListener(view1 -> { - try { - onRequestPairing.launch(new Intent(Settings.ACTION_BLUETOOTH_SETTINGS)); - } catch (ActivityNotFoundException anf) { - if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) { - IntentFilter filter = new IntentFilter( - "android.bluetooth.device.action.PAIRING_REQUEST" - ); - requireActivity().registerReceiver(pairingRequest, filter); - if (mBluetoothAdapter.isDiscovering()) - mBluetoothAdapter.cancelDiscovery(); - mBluetoothAdapter.startDiscovery(); - progressBar.setVisibility(View.VISIBLE); - } - } - }); - ((TextView) paired.findViewById(R.id.bluetooth_text)).setText(R.string.bluetooth_pair); - deviceList.addView(paired, 0); + scan.setOnClickListener(view1 -> scanBluetoothServices()); + ((TextView) scan.findViewById(R.id.bluetooth_text)).setText(R.string.bluetooth_scan); + deviceList.addView(scan, 0); } private void setButtonText(View button, BluetoothDevice device) { @@ -354,15 +318,10 @@ public void stopFlaskService() { } private void dismissFlaskDiscovery() { - if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) { - try { - requireActivity().unregisterReceiver(pairingRequest); - } catch (Exception ignored) { } - } if (null != mBluetoothAdapter) { - if (mBluetoothAdapter.isDiscovering()) - mBluetoothAdapter.cancelDiscovery(); progressBar.setVisibility(View.INVISIBLE); + if (null != scanCallback) + mBluetoothAdapter.stopLeScan(scanCallback); } } diff --git a/app/src/main/res/values-de/strings.xml b/app/src/main/res/values-de/strings.xml index 15578fb27..cc1f1133b 100644 --- a/app/src/main/res/values-de/strings.xml +++ b/app/src/main/res/values-de/strings.xml @@ -328,7 +328,7 @@ Device storage inaccessible! Switch to N2 Elite Options Switch to amiibo™ Details - Pair new Bluetooth device + Scan BLE for Bluup Flask Required permission denied! Back to TagMo Flask pairing failed! diff --git a/app/src/main/res/values-es/strings.xml b/app/src/main/res/values-es/strings.xml index 292f5336b..7d54a1512 100644 --- a/app/src/main/res/values-es/strings.xml +++ b/app/src/main/res/values-es/strings.xml @@ -328,7 +328,7 @@ Device storage inaccessible! Switch to N2 Elite Options Switch to amiibo™ Details - Pair new Bluetooth device + Scan BLE for Bluup Flask Required permission denied! Bluetooth adapter unavailable! Bluup Flask connected! diff --git a/app/src/main/res/values-fr/strings.xml b/app/src/main/res/values-fr/strings.xml index 2b0edab5b..872aa6e4b 100644 --- a/app/src/main/res/values-fr/strings.xml +++ b/app/src/main/res/values-fr/strings.xml @@ -328,7 +328,7 @@ Device storage inaccessible! Switch to N2 Elite Options Switch to amiibo™ Details - Pair new Bluetooth device + Scan BLE for Bluup Flask Required permission denied! Bluetooth adapter unavailable! Bluup Flask connected! diff --git a/app/src/main/res/values-ja/strings.xml b/app/src/main/res/values-ja/strings.xml index 5e638bba9..e741e822c 100644 --- a/app/src/main/res/values-ja/strings.xml +++ b/app/src/main/res/values-ja/strings.xml @@ -328,7 +328,7 @@ Device storage inaccessible! Switch to N2 Elite Options Switch to amiibo™ Details - Pair new Bluetooth device + Scan BLE for Bluup Flask Required permission denied! Back to TagMo Flask pairing failed! diff --git a/app/src/main/res/values-ko/strings.xml b/app/src/main/res/values-ko/strings.xml index f39696b90..4ac471aee 100644 --- a/app/src/main/res/values-ko/strings.xml +++ b/app/src/main/res/values-ko/strings.xml @@ -328,7 +328,7 @@ Device storage inaccessible! Switch to N2 Elite Options Switch to amiibo™ Details - Pair new Bluetooth device + Scan BLE for Bluup Flask Back to TagMo Flask pairing failed! Not a valid Flask device! diff --git a/app/src/main/res/values-pl/strings.xml b/app/src/main/res/values-pl/strings.xml index 58f9eeb9b..d37ebe419 100644 --- a/app/src/main/res/values-pl/strings.xml +++ b/app/src/main/res/values-pl/strings.xml @@ -328,7 +328,7 @@ Device storage inaccessible! Switch to N2 Elite Options Switch to amiibo™ Details - Pair new Bluetooth device + Scan BLE for Bluup Flask Back to TagMo Flask pairing failed! Not a valid Flask device! diff --git a/app/src/main/res/values-ru/strings.xml b/app/src/main/res/values-ru/strings.xml index b83f81dba..b56130eec 100644 --- a/app/src/main/res/values-ru/strings.xml +++ b/app/src/main/res/values-ru/strings.xml @@ -328,7 +328,7 @@ Device storage inaccessible! Switch to N2 Elite Options Switch to amiibo™ Details - Pair new Bluetooth device + Scan BLE for Bluup Flask Required permission denied! Bluetooth adapter unavailable! Bluup Flask connected! diff --git a/app/src/main/res/values-zh-rCN/string.xml b/app/src/main/res/values-zh-rCN/string.xml index b48a06b45..5ae0eb11f 100644 --- a/app/src/main/res/values-zh-rCN/string.xml +++ b/app/src/main/res/values-zh-rCN/string.xml @@ -329,7 +329,6 @@ Device storage inaccessible! Switch to N2 Elite Options Switch to amiibo™ Details - Pair new Bluetooth device Required permission denied! Bluetooth adapter unavailable! Bluup Flask connected! @@ -343,4 +342,5 @@ Bluup Flask  ᴮᴸᴱ Bluup Flask  ᵂᵂᵂ Device cannot be located! + Scan BLE for Bluup Flask diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index 51ef69342..290f4db25 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -241,7 +241,7 @@ Bluup Flask connected! Bluetooth adapter unavailable! Required permission denied! - Pair new Bluetooth device + Scan BLE for Bluup Flask Wrote main data Wrote password