Android BLE Bluetooth 검색 실패 데이터 및 해결 방법

저소모 블루투스(BLE) 개발 과정에서 적지 않은 구덩이에 부딪힌 적이 있다. 개발 과정에서 스캐닝을 켜는 데 겪은 문제점을 기록으로 정리한다.
저소모 블루투스를 개발하는 과정에서 안드로이드 시스템의 끊임없는 업그레이드와 최적화로 인해 BLE에 대한 개발도 업그레이드 과정에서 서로 다른 문제에 부딪힐 수 있다.검색 열기에 대한 요약은 다음과 같습니다.
  • 개발 과정에서 스캔을 닫고 다시 시작하면 스캔이 성공하지 못함
  • 개발 과정에서 스캔을 닫고 스캔을 시작하는 등 반복되는 문제가 불가피하지만, 어떤 때는 닫힌 후에 스캔을 다시 열 수 없는 문제가 발생할 수 있습니다.
    E/BtGatt.GattService: App 'com.bluetooth.app' is scanning too frequently 

            这时问题就是你开启扫描功能太频繁了,导致系统吃不消导致的,遇到这种情况你需要在关闭扫描之后至少停止2秒钟,然后再次调用开启扫描方法,开启成功。

    • 在Android 6.0及以上版本中开启蓝牙扫描后扫描不到数据问题

            在Android 6.0之前的版本中能够完美运行,但换到Android 6.0 及以上系统的手机运行时搜索不到数据。

            这是因为在Android 6.0及以上系统中低功耗蓝牙添加了距离检测功能,所以扫描时需要开启定位功能权限,在更高版本中甚至需要开启精准定位权限

     

        
        

    코드에서도 동적 권한을 신청해야 한다
     //           
            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M &&
                    checkSelfPermission(Manifest.permission.ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED &&
                    checkSelfPermission(Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED &&
                    checkSelfPermission(Manifest.permission.CAMERA) != PackageManager.PERMISSION_GRANTED ) {
                requestPermissions(new String[]{Manifest.permission.ACCESS_COARSE_LOCATION, Manifest.permission.ACCESS_FINE_LOCATION ,
                                Manifest.permission.CAMERA,}, PERMISSIONS_REQUEST_CODE_ACCESS);
            }

    각종 권한 문제를 해결한 후 안드로이드 6.0 이전에 스캔해도 문제가 없고 이후에 스캔하지 않아도 문제가 해결된다
  • 안드로이드 8.1 및 그 이상의 시스템 백그라운드 모드에서 검색 문제를 열 수 없음
  • Android 8.1 이상 시스템에서 Bluetooth 검색은 문제가 없지만 Application이 백그라운드에 있을 때 검색 방법을 켤 수 없으며 다음과 같은 프롬프트가 표시됩니다.
            BtGatt.ScanManager: Cannot start unfiltered scan in screen-off. This scan will be resumed later: 9
    이것은 당신이 설정한 스캔 방법이 스캔 필터를 설정하지 않은 문제이기 때문입니다. 안드로이드 8.1 및 이상 시스템에서 백엔드 모드에서 스캔을 하려면 반드시 관련 스캔 필터를 연결해야 백엔드 모드에서 완벽하게 실행할 수 있습니다.
        //           
        private List scanFilterList;
        //         
        private ScanFilter.Builder scanFilterBuilder;
        //        
        private ScanSettings.Builder  scanSettingBuilder;
    
      
        private List buildScanFilters() {
            scanFilterList = new ArrayList<>();
            //      uuid                   GATT  UUID
            scanFilterBuilder = new ScanFilter.Builder();
            ParcelUuid parcelUuidMask = ParcelUuid.fromString("FFFFFFFF-FFFF-FFFF-FFFF-FFFFFFFFFFFF");
            ParcelUuid parcelUuid = ParcelUuid.fromString("00001800-0000-1000-8000-00805f9b34fb");
            scanFilterBuilder.setServiceUuid(parcelUuid, parcelUuidMask);
            scanFilterList.add(scanFilterBuilder.build());
            return scanFilterList;
        }
    
        private ScanSettings buildScanSettings() {
            scanSettingBuilder = new ScanSettings.Builder();
            //    LE       。
            //           。                        
            scanSettingBuilder.setScanMode(ScanSettings.SCAN_MODE_LOW_LATENCY);
            //    LE              
            //      ,        ,hw         .           /  。
            scanSettingBuilder.setMatchMode(ScanSettings.MATCH_MODE_AGGRESSIVE);
            //    LE       
            //                     。           ,         
            scanSettingBuilder.setCallbackType(ScanSettings.CALLBACK_TYPE_ALL_MATCHES);
            return scanSettingBuilder.build();
        }
    
    
        //        
        mBluetoothAdapter.getBluetoothLeScanner().startScan(buildScanFilters(), buildScanSettings(), mLeScanCallback);

    실제 상황에 따라 상응하는 매개 변수 설정을 설정하고 필터 설정과 스캐닝 설정을 추가하는 스캐닝 방법을 호출한다. 즉, 백엔드 상태에서 스캐닝 기능을 시작할 수 있다.
    본고를 통해 개발 과정에서 겪은 오픈 스캐너가 서로 다른 버전에서 겪은 문제점과 해결 방법을 기록한다.

    좋은 웹페이지 즐겨찾기