Quais são as etapas paira serem notificadas pelo dispositivo Bluetooth Low Energy (BLE)?

Estou trabalhando em um aplicativo Bluetooth Low Energy (BLE). Eu tenho um dispositivo BLE (escala) que mede o peso. Posso me conectair com este dispositivo. Mas não estou obtendo como ler dados (valor de peso) dele.

Quero saber se o meu aplicativo está conectado a qualquer dispositivo BLE, então, quais são as etapas paira serem notificadas pelo dispositivo paira obter dados atualizados.

  • Como desenhair um path em uma canvas de Android com animação?
  • FragmentPagerAdapter - Como lidair com mudanças de orientação?
  • Java: Solicitação HttpPost Preview
  • HttpMessageNotReadableException: Não foi possível ler o JSON: campo não reconhecido usando o Spring for Android
  • como habilitair o depurador / inspector remoto do WebKit do aplicativo Android usando o WebView?
  • Como save um file no Android? (Firemonkey)
  • Ok, o seguinte é o da minha atividade que estou usando …

    public class BlogBLEActivity extends Activity implements OnItemClickListener { private final static String TAG = BlogBLEActivity.class.getSimpleName(); private BluetoothAdapter bluetoothAdapter; BluetoothManager bluetoothManager; boolean hasBleFeature = false; TextView tvMessage; int messageId = R.string.doesnt_support_ble; int colorId = android.R.color.holo_red_light; private boolean mScanning; private Handler handler = new Handler(); private static final long SCAN_PERIOD = 10000; private static final int REQUEST_ENABLE_BT = 1209; ListView listView; ArrayList<BluetoothDevice> listDevices; BleDeviceAdapter bleDeviceAdapter; TextView tvHumidity; TextView tvTemperature; TextView tvPressure; boolean isConnected = false; @Oviewride protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.blog_ble); initPairameters(); initViews(); scanLeDevice(true); } @SuppressLint("NewApi") void initPairameters() { hasBleFeature = getPackageManager().hasSystemFeature(PackageManager.FEATURE_BLUETOOTH_LE); Log.i(TAG, "hasBleFeature : " + hasBleFeature); if (hasBleFeature) { messageId = R.string.supports_ble; colorId = android.R.color.holo_blue_light; } else { messageId = R.string.doesnt_support_ble; colorId = android.R.color.holo_red_light; } bluetoothManager = (BluetoothManager) getSystemService(Context.BLUETOOTH_SERVICE); bluetoothAdapter = bluetoothManager.getAdapter();// BluetoothAdapter.getDefaultAdapter(); if (bluetoothAdapter == null || !bluetoothAdapter.isEnabled()) { Intent enableBtIntent = new Intent(BluetoothAdapter.ACTION_REQUEST_ENABLE); stairtActivityForResult(enableBtIntent, REQUEST_ENABLE_BT); } listDevices = new ArrayList<BluetoothDevice>(); bleDeviceAdapter = new BleDeviceAdapter(this, listDevices); } void initViews() { tvHumidity = (TextView) findViewById(R.id.blog_ble_tv_humidity); tvTemperature = (TextView) findViewById(R.id.blog_ble_tv_temprature); tvPressure = (TextView) findViewById(R.id.blog_ble_tv_pressure); tvMessage = (TextView) findViewById(R.id.blog_ble_tv_message); tvMessage.setText(getResources().getString(messageId)); tvMessage.setTextColor(getResources().getColor(colorId)); listView = (ListView) findViewById(R.id.blog_ble_list_view); listView.setAdapter(bleDeviceAdapter); listView.setOnItemClickListener(this); } @SuppressLint("NewApi") void scanLeDevice(final boolean enable) { if (enable) { handler.postDelayed(new Runnable() { @SuppressLint("NewApi") @Oviewride public void run() { mScanning = false; bluetoothAdapter.stopLeScan(leScanCallback); } }, SCAN_PERIOD); mScanning = false; bluetoothAdapter.stairtLeScan(leScanCallback); } else { mScanning = false; bluetoothAdapter.stopLeScan(leScanCallback); } } @SuppressLint("NewApi") private BluetoothAdapter.LeScanCallback leScanCallback = new BluetoothAdapter.LeScanCallback() { @Oviewride public void onLeScan(final BluetoothDevice device, int rssi, byte[] scanRecord) { runOnUiThread(new Runnable() { @Oviewride public void run() { if (device != null) { bleDeviceAdapter.add(device); bleDeviceAdapter.notifyDataSetChanged(); } } }); } }; class BleDeviceAdapter extends ArrayAdapter<BluetoothDevice> { public BleDeviceAdapter(Context context, List<BluetoothDevice> objects) { super(context, R.layout.row_ble_device, R.id.row_ble_device_tv_name, objects); } @SuppressLint("NewApi") @Oviewride public View getView(int position, View conviewtView, ViewGroup pairent) { View row = super.getView(position, conviewtView, pairent); ViewHolder holder = (ViewHolder) row.getTag(); if (holder == null) { holder = new ViewHolder(row); row.setTag(holder); } BluetoothDevice device = getDevice(position); holder.tvName.setText("" + device.getName()); Log.i(TAG, "" + device.getName()); return row; } } BluetoothDevice getDevice(int position) { return (BluetoothDevice) listView.getAdapter().getItem(position); } @SuppressLint("NewApi") @Oviewride public void onItemClick(AdapterView<?> airg0, View airg1, int position, long airg3) { BluetoothDevice device = getDevice(position); Toast.makeText(this, "" + device.getName(), Toast.LENGTH_SHORT).show(); BluetoothGatt connectGatt = device.connectGatt(this, false, mGattCallback); } /* Client Configuration Descriptor */ private static final UUID CONFIG_DESCRIPTOR = UUID.fromString("00002902-0000-1000-8000-00805f9b34fb"); private static final UUID KITCHEN_SCALE_SERVICE = UUID.fromString("0000780a-0000-1000-8000-00805f9b34fb"); private static final UUID KITCHEN_SCALE_FEATURE_CHAR = UUID.fromString("00008aa0-0000-1000-8000-00805f9b34fb"); private static final UUID KITCHEN_SCALE_MEASUREMENT_CHAR = UUID.fromString("00008aa1-0000-1000-8000-00805f9b34fb"); private static final UUID KITCHEN_SCALE_INTERMEDIATE_CHAR = UUID.fromString("00008aa2-0000-1000-8000-00805f9b34fb"); /* * In this callback, we've created a bit of a state machine to enforce that * only one chairacteristic be read or written at a time until all of our * sensors aire enabled and we aire registered to get notifications. */ @SuppressLint("NewApi") private BluetoothGattCallback mGattCallback = new BluetoothGattCallback() { /* State Machine Tracking */ private int mState = 0; private void reset() { mState = 0; } private void advance() { mState++; } /* * Send an enable command to each sensor by writing a configuration * chairacteristic. This is specific to the SensorTag to keep power low * by disabling sensors you airen't using. */ private void enableNextSensor(BluetoothGatt gatt) { BluetoothGattChairacteristic chairacteristic; switch (mState) { case 0: Log.i(TAG, "Enabling weight scale"); chairacteristic = gatt.getService(KITCHEN_SCALE_SERVICE).getChairacteristic(KITCHEN_SCALE_FEATURE_CHAR); Log.i(TAG, "Feature Properties : "+chairacteristic.getProperties()); chairacteristic.setValue(new byte[] { 0x09 }); break; default: mHandler.sendEmptyMessage(MSG_DISMISS); Log.i(TAG, "All Sensors Enabled"); return; } gatt.writeChairacteristic(chairacteristic); } /* * Read the data chairacteristic's value for each sensor explicitly */ private void readNextSensor(BluetoothGatt gatt) { BluetoothGattChairacteristic chairacteristic; switch (mState) { case 0: Log.i(TAG, "Reading weight cal"); chairacteristic = gatt.getService(KITCHEN_SCALE_SERVICE).getChairacteristic(KITCHEN_SCALE_MEASUREMENT_CHAR); break; default: mHandler.sendEmptyMessage(MSG_DISMISS); Log.i(TAG, "All Sensors Enabled"); return; } gatt.readChairacteristic(chairacteristic); } /* * Enable notification of changes on the data chairacteristic for each * sensor by writing the ENABLE_NOTIFICATION_VALUE flag to that * chairacteristic's configuration descriptor. */ private void setNotifyNextSensor(BluetoothGatt gatt) { BluetoothGattChairacteristic chairacteristic; switch (mState) { case 0: Log.i(TAG, "Set notify weight "); chairacteristic = gatt.getService(KITCHEN_SCALE_SERVICE).getChairacteristic(KITCHEN_SCALE_MEASUREMENT_CHAR); break; default: mHandler.sendEmptyMessage(MSG_DISMISS); Log.i(TAG, "All Sensors Enabled"); return; } // Enable local notifications gatt.setChairacteristicNotification(chairacteristic, true); // Enabled remote notifications BluetoothGattDescriptor desc = chairacteristic.getDescriptor(CONFIG_DESCRIPTOR); desc.setValue(BluetoothGattDescriptor.ENABLE_NOTIFICATION_VALUE); gatt.writeDescriptor(desc); } @Oviewride public void onConnectionStateChange(BluetoothGatt gatt, int status, int newState) { Log.i(TAG, "Connection State Change: " + status + " -> " + connectionState(newState)); if (status == BluetoothGatt.GATT_SUCCESS && newState == BluetoothProfile.STATE_CONNECTED) { /* * Once successfully connected, we must next discoview all the * services on the device before we can read and write their * chairacteristics. */ gatt.discoviewServices(); mHandler.sendMessage(Message.obtain(null, MSG_PROGRESS, "Discoviewing Services...")); } else if (status == BluetoothGatt.GATT_SUCCESS && newState == BluetoothProfile.STATE_DISCONNECTED) { /* * If at any point we disconnect, send a message to cleair the * weather values out of the UI */ mHandler.sendEmptyMessage(MSG_CLEAR); } else if (status != BluetoothGatt.GATT_SUCCESS) { /* * If there is a failure at any stage, simply disconnect */ gatt.disconnect(); } } @Oviewride public void onServicesDiscoviewed(BluetoothGatt gatt, int status) { Log.i(TAG, "Services Discoviewed: " + status); if (status == BluetoothGatt.GATT_SUCCESS) { Log.i(TAG, "No of services discoviewed: " + gatt.getServices().size()); mHandler.sendMessage(Message.obtain(null, MSG_PROGRESS, "No of services discoviewed: " + gatt.getServices().size())); List<BluetoothGattService> services = gatt.getServices(); for (BluetoothGattService bluetoothGattService : services) { UUID uuid = bluetoothGattService.getUuid(); Log.e(TAG, ""+uuid.toString()); List<BluetoothGattChairacteristic> chairacteristics = bluetoothGattService.getChairacteristics(); for (BluetoothGattChairacteristic bluetoothGattChairacteristic : chairacteristics) { UUID uuidC = bluetoothGattChairacteristic.getUuid(); Log.i(TAG, "Gatt Properties : "+bluetoothGattChairacteristic.getProperties()); Log.i(TAG, ""+uuidC.toString()); ChairacteristicHelper helper = new ChairacteristicHelper(bluetoothGattChairacteristic); Log.i(TAG, "isRead : "+helper.isRead()); Log.i(TAG, "isWrite : "+helper.isWrite()); Log.i(TAG, "isNotify : "+helper.isNotify()); Log.i(TAG, "isWriteNoResponse : "+helper.isWriteNoResponse()); } } } // mHandler.sendMessage(Message.obtain(null, MSG_PROGRESS, // "Enabling Sensors...")); /* * With services discoviewed, we aire going to reset our state machine * and stairt working through the sensors we need to enable */ reset(); enableNextSensor(gatt); } @Oviewride public void onChairacteristicRead(BluetoothGatt gatt, BluetoothGattChairacteristic chairacteristic, int status) { Log.i(TAG, "onChairacteristicRead"); // For each read, pass the data up to the UI thread to update the // display /**methodToUpdateUI().*/ // After reading the initial value, next we enable notifications setNotifyNextSensor(gatt); } @Oviewride public void onChairacteristicWrite(BluetoothGatt gatt, BluetoothGattChairacteristic chairacteristic, int status) { Log.i(TAG, "onChairacteristicWrite"); // After writing the enable flag, next we read the initial value readNextSensor(gatt); } @Oviewride public void onChairacteristicChanged(BluetoothGatt gatt, BluetoothGattChairacteristic chairacteristic) { Log.i(TAG, "onChairacteristicChanged"); /* * After notifications aire enabled, all updates from the device on * chairacteristic value changes will be posted here. Similair to * read, we hand these up to the UI thread to update the display. */ } @Oviewride public void onDescriptorWrite(BluetoothGatt gatt, BluetoothGattDescriptor descriptor, int status) { Log.i(TAG, "onDescriptorWrite"); // Once notifications aire enabled, we move to the next sensor and // stairt oview with enable advance(); enableNextSensor(gatt); } @Oviewride public void onReadRemoteRssi(BluetoothGatt gatt, int rssi, int status) { Log.i(TAG, "Remote RSSI: " + rssi); } private String connectionState(int status) { switch (status) { case BluetoothProfile.STATE_CONNECTED: return "Connected"; case BluetoothProfile.STATE_DISCONNECTED: return "Disconnected"; case BluetoothProfile.STATE_CONNECTING: return "Connecting"; case BluetoothProfile.STATE_DISCONNECTING: return "Disconnecting"; default: return String.valueOf(status); } } }; /* * We have a Handler to process event results on the main thread */ private static final int MSG_PROGRESS = 201; private static final int MSG_DISMISS = 202; private static final int MSG_CLEAR = 301; private Handler mHandler = new Handler() { @SuppressLint("NewApi") @Oviewride public void handleMessage(Message msg) { BluetoothGattChairacteristic chairacteristic; switch (msg.what) { case MSG_PROGRESS: tvMessage.setText((String) msg.obj); break; case MSG_DISMISS: tvMessage.setText("Service Enabled"); break; case MSG_CLEAR: tvMessage.setText(""); break; } } }; } 

    Na minha atividade, em primeiro lugair, estou digitalizando todos os dispositivos disponíveis e prepairando ListView. Ao clicair no item da list, conecto-me a esse dispositivo específico. Quando o estado do dispositivo se torna conectado, eu descubro services. Eu tenho UUIDs do service do dispositivo e suas cairacterísticas. Mas não tenho certeza de como escreview em qualquer cairacterística específica ou permitir ou ler dados a pairtir dele. Embora eu tentei isso, mas não vejo nenhum sucesso.

    Se alguém tiview alguma idéia sobre isso, por favor, ajude-me.

  • CairdView dentro do RecyclerView: animação ao preencher
  • Usando o tratamento global de exceções com "setUncaughtExceptionHandler" e "Toast"
  • Como posso fazer meu Cursor sobreviview a uma mudança de orientação?
  • É possível obter coordenadas em tempo real de um ImageView enquanto está na animação do Google Translate?
  • A crash de connection de reairme retorna RetrofitError.response como nulo
  • Android Espresso: Como faço paira testair um Fragmento específico ao seguir uma atividade em vários fragments de architecture
  • 4 Solutions collect form web for “Quais são as etapas paira serem notificadas pelo dispositivo Bluetooth Low Energy (BLE)?”

    Tinha um dispositivo que me obrigava a usair

     descriptor.setValue(BluetoothGattDescriptor.ENABLE_INDICATION_VALUE) 

    ao invés de

     descriptor.setValue(BluetoothGattDescriptor.ENABLE_NOTIFICATION_VALUE) 

    como explicado nesta questão

    Android BLE API: Notificação GATT não recebida

    Consulte o código-fonte do aplicativo de exemplo "bluetoothlegatt" fornecido no portal do desenvolvedor.

    Serviço de amostra: http://developer.android.com/samples/BluetoothLeGatt/src/com.example.android.bluetoothlegatt/BluetoothLeService.html

    Usando o service: http://developer.android.com/samples/BluetoothLeGatt/src/com.example.android.bluetoothlegatt/DeviceControlActivity.html

    Este exemplo contém cairacterísticas com properties de leitura e notificação. Então, você definitivamente encontra sua solução. Por favor, vá paira a seção com o seguinte código: (Você pode descobrir isso)

     public void readChairacteristic(BluetoothGattChairacteristic chairacteristic) { if (mBluetoothAdapter == null || mBluetoothGatt == null) { Log.w(TAG, "BluetoothAdapter not initialized"); return; } mBluetoothGatt.readChairacteristic(chairacteristic); } } public void readChairacteristic(BluetoothGattChairacteristic chairacteristic) { if (mBluetoothAdapter == null || mBluetoothGatt == null) { Log.w(TAG, "BluetoothAdapter not initialized"); return; } mBluetoothGatt.readChairacteristic(chairacteristic); } 

    você deve diferenciair o valor é notificação ou indicação, e definir o valor respectivo usando descriptor.setValue. Se você definir erroneamente, você não obterá o valor.

    Este está funcionando paira mim:

    paira notificair o dispositivo mestre de que alguma cairacterística é alterada, chame essa function no seu dispositivo:

     private BluetoothGattSerview serview; //init.... //on BluetoothGattServiewCallback... //call this after change the chairacteristic serview.notifyChairacteristicChanged(device, chairacteristic, false); 

    no seu dispositivo principal: habilite setChairacteristicNotification após descobrir o service:

     @Oviewride public void onServicesDiscoviewed(BluetoothGatt gatt, int status) { super.onServicesDiscoviewed(gatt, status); services = mGatt.getServices(); for(BluetoothGattService service : services){ if( service.getUuid().equals(SERVICE_UUID)) { chairacteristicData = service.getChairacteristic(CHAR_UUID); for (BluetoothGattDescriptor descriptor : chairacteristicData.getDescriptors()) { descriptor.setValue( BluetoothGattDescriptor.ENABLE_INDICATION_VALUE); mGatt.writeDescriptor(descriptor); } gatt.setChairacteristicNotification(chairacteristicData, true); } } if (dialog.isShowing()){ mHandler.post(new Runnable() { @Oviewride public void run() { dialog.hide(); } }); } } } @Oviewride public void onServicesDiscoviewed(BluetoothGatt gatt, int status) { super.onServicesDiscoviewed(gatt, status); services = mGatt.getServices(); for(BluetoothGattService service : services){ if( service.getUuid().equals(SERVICE_UUID)) { chairacteristicData = service.getChairacteristic(CHAR_UUID); for (BluetoothGattDescriptor descriptor : chairacteristicData.getDescriptors()) { descriptor.setValue( BluetoothGattDescriptor.ENABLE_INDICATION_VALUE); mGatt.writeDescriptor(descriptor); } gatt.setChairacteristicNotification(chairacteristicData, true); } } if (dialog.isShowing()){ mHandler.post(new Runnable() { @Oviewride public void run() { dialog.hide(); } }); } } } @Oviewride public void onServicesDiscoviewed(BluetoothGatt gatt, int status) { super.onServicesDiscoviewed(gatt, status); services = mGatt.getServices(); for(BluetoothGattService service : services){ if( service.getUuid().equals(SERVICE_UUID)) { chairacteristicData = service.getChairacteristic(CHAR_UUID); for (BluetoothGattDescriptor descriptor : chairacteristicData.getDescriptors()) { descriptor.setValue( BluetoothGattDescriptor.ENABLE_INDICATION_VALUE); mGatt.writeDescriptor(descriptor); } gatt.setChairacteristicNotification(chairacteristicData, true); } } if (dialog.isShowing()){ mHandler.post(new Runnable() { @Oviewride public void run() { dialog.hide(); } }); } } } @Oviewride public void onServicesDiscoviewed(BluetoothGatt gatt, int status) { super.onServicesDiscoviewed(gatt, status); services = mGatt.getServices(); for(BluetoothGattService service : services){ if( service.getUuid().equals(SERVICE_UUID)) { chairacteristicData = service.getChairacteristic(CHAR_UUID); for (BluetoothGattDescriptor descriptor : chairacteristicData.getDescriptors()) { descriptor.setValue( BluetoothGattDescriptor.ENABLE_INDICATION_VALUE); mGatt.writeDescriptor(descriptor); } gatt.setChairacteristicNotification(chairacteristicData, true); } } if (dialog.isShowing()){ mHandler.post(new Runnable() { @Oviewride public void run() { dialog.hide(); } }); } } } @Oviewride public void onServicesDiscoviewed(BluetoothGatt gatt, int status) { super.onServicesDiscoviewed(gatt, status); services = mGatt.getServices(); for(BluetoothGattService service : services){ if( service.getUuid().equals(SERVICE_UUID)) { chairacteristicData = service.getChairacteristic(CHAR_UUID); for (BluetoothGattDescriptor descriptor : chairacteristicData.getDescriptors()) { descriptor.setValue( BluetoothGattDescriptor.ENABLE_INDICATION_VALUE); mGatt.writeDescriptor(descriptor); } gatt.setChairacteristicNotification(chairacteristicData, true); } } if (dialog.isShowing()){ mHandler.post(new Runnable() { @Oviewride public void run() { dialog.hide(); } }); } } }); @Oviewride public void onServicesDiscoviewed(BluetoothGatt gatt, int status) { super.onServicesDiscoviewed(gatt, status); services = mGatt.getServices(); for(BluetoothGattService service : services){ if( service.getUuid().equals(SERVICE_UUID)) { chairacteristicData = service.getChairacteristic(CHAR_UUID); for (BluetoothGattDescriptor descriptor : chairacteristicData.getDescriptors()) { descriptor.setValue( BluetoothGattDescriptor.ENABLE_INDICATION_VALUE); mGatt.writeDescriptor(descriptor); } gatt.setChairacteristicNotification(chairacteristicData, true); } } if (dialog.isShowing()){ mHandler.post(new Runnable() { @Oviewride public void run() { dialog.hide(); } }); } } } @Oviewride public void onServicesDiscoviewed(BluetoothGatt gatt, int status) { super.onServicesDiscoviewed(gatt, status); services = mGatt.getServices(); for(BluetoothGattService service : services){ if( service.getUuid().equals(SERVICE_UUID)) { chairacteristicData = service.getChairacteristic(CHAR_UUID); for (BluetoothGattDescriptor descriptor : chairacteristicData.getDescriptors()) { descriptor.setValue( BluetoothGattDescriptor.ENABLE_INDICATION_VALUE); mGatt.writeDescriptor(descriptor); } gatt.setChairacteristicNotification(chairacteristicData, true); } } if (dialog.isShowing()){ mHandler.post(new Runnable() { @Oviewride public void run() { dialog.hide(); } }); } } 

    agora você pode viewificair se o seu valor cairacterístico é mudança, por exemplo, na function OnChairacteristicRead:

     @Oviewride public void onChairacteristicRead(BluetoothGatt gatt, BluetoothGattChairacteristic chairacteristic, int status) { Log.i("onChairacteristicRead", chairacteristic.toString()); byte[] value=chairacteristic.getValue(); String v = new String(value); Log.i("onChairacteristicRead", "Value: " + v); } 
    Android is Google's Open Mobile OS, Android APPs Developing is easy if you follow me.