BluetoothGatt — ایک Android کلاس ہے جو BLE کنکشن پر GATT (Generic Attribute Profile) کلائنٹ آپریشنز کے لیے API فراہم کرتی ہے۔ BluetoothGatt ریموٹ GATT سرور (پیری فیرل BLE ڈیوائس) سے کنکشن کو انکیپسولیٹ کرتا ہے اور تمام پروفائل آپریشنز کا انتظام کرتا ہے: سروسز کی دریافت، خصوصیات کو پڑھنا اور لکھنا، اطلاعات اور اشارے کو سبسکرائب کرنا۔ BluetoothGatt کی ایک مثال BluetoothDevice.connectGatt() کے ذریعے BluetoothGattCallback کے ساتھ حاصل کی جاتی ہے۔ Android Developers, 2026 کے مطابق، BluetoothGatt دو طرفہ BLE مواصلات کے لیے مرکزی کلاس ہے، جو BLE 4.0 سے BLE 5.4 تک GATT آپریشنز کو سپورٹ کرتی ہے۔
اہم نکات
BluetoothGatt — ایک پراکسی آبجیکٹ ہے جو Android ڈیوائس (مرکزی) اور BLE پیری فیرل (سرور) کے درمیان GATT کنکشن کی نمائندگی کرتا ہے۔ ہر BluetoothGatt مثال ایک فعال BLE کنکشن سے مطابقت رکھتی ہے۔ تمام GATT پروفائل آپریشنز اس کے ذریعے انجام دیے جاتے ہیں: دریافت، پڑھنا، لکھنا، اطلاعات۔ BluetoothGatt براہ راست نہیں بنایا جاتا — یہ BluetoothDevice.connectGatt() طریقہ سے واپس کیا جاتا ہے۔
BluetoothGatt بنانے کے لیے چار پیرامیٹرز درکار ہیں۔ Context — ایپلیکیشن کا سیاق و سباق (Activity یا Application)۔ autoConnect — اگر false ہے، Android فوری طور پر براہ راست کنکشن شروع کرتا ہے؛ اگر true ہے، Android ڈیوائس کے دریافت ہونے پر خود بخود جڑ جاتا ہے (پس منظر کنکشن کے لیے مفید)۔ BluetoothGattCallback — تمام GATT واقعات کے لیے لازمی کال بیک۔ transport — BluetoothDevice.TRANSPORT_LE (BLE) یا TRANSPORT_BREDR (Classic)۔ BLE ڈیوائسز پر ہمیشہ TRANSPORT_LE استعمال کریں۔
BluetoothGatt لائف سائیکل پانچ حالتوں پر مشتمل ہے۔ DISCONNECTED — ابتدائی حالت۔ CONNECTING — connectGatt کال کرنے کے بعد، تصدیق سے پہلے۔ CONNECTED — STATE_CONNECTED کے ساتھ onConnectionStateChange کے بعد۔ کنکشن کے بعد GATT درجہ بندی حاصل کرنے کے لیے discoverServices() کال کیا جاتا ہے۔ کام ختم ہونے کے بعد — سسٹم وسائل کو آزاد کرنے کے لیے disconnect() اور close()۔ close() کال کیے بغیر، ایپلیکیشن Android BLE کنکشن کی حد (عام طور پر 4–8) ختم کر سکتی ہے۔
// BluetoothGatt کنکشن بنا رہا ہے
import android.bluetooth.*
class GattConnector(private val context: Context) {
private var bluetoothGatt: BluetoothGatt? = null
fun connect(device: BluetoothDevice): BluetoothGatt? {
// پچھلا کنکشن موجود ہونے پر بند کریں
close()
bluetoothGatt = device.connectGatt(
context,
false, // autoConnect = false ( )
object : BluetoothGattCallback() {
override fun onConnectionStateChange(
gatt: BluetoothGatt, status: Int, newState: Int
) {
when (newState) {
BluetoothProfile.STATE_CONNECTED -> {
// 2. کنکشن قائم → دریافت
gatt.discoverServices()
}
BluetoothProfile.STATE_DISCONNECTED -> {
// 3. کنکشن ختم ہو گیا
close()
}
}
}
override fun onServicesDiscovered(
gatt: BluetoothGatt, status: Int
) {
if (status == BluetoothGatt.GATT_SUCCESS) {
// 4. GATT درجہ بندی موصول ہوئی
onGattReady(gatt)
}
}
},
BluetoothDevice.TRANSPORT_LE
)
return bluetoothGatt
}
private fun onGattReady(gatt: BluetoothGatt) {
// GATT پڑھنے/لکھنے کے آپریشنز کے لیے تیار
}
fun close() {
bluetoothGatt?.disconnect()
bluetoothGatt?.close()
bluetoothGatt = null
}
}
GattConnector کلاس درست BluetoothGatt تخلیق کو ظاہر کرتی ہے۔ autoConnect=false پیرامیٹر کا مطلب براہ راست کنکشن ہے (سکین شدہ ڈیوائسز کے لیے)۔ STATE_CONNECTED کے ساتھ onConnectionStateChange پر، فوری طور پر discoverServices() کال کیا جاتا ہے۔ onServicesDiscovered اشارہ کرتا ہے کہ GATT تیار ہے۔ close() ترتیب سے disconnect() اور close() کال کرتا ہے — close() کے بغیر سسٹم وسائل آزاد نہیں ہوتے، جس سے BLE کنکشن لیک ہوتے ہیں۔
discoverServices() — کنکشن کے بعد کال کی جانے والی پہلی GATT طریقہ ہے۔ یہ BLE پیری فیرل پر تمام سروسز کی غیر متزامن تلاش شروع کرتی ہے۔ نتیجہ onServicesDiscovered() میں اسٹیٹس کوڈ کے ساتھ آتا ہے: GATT_SUCCESS (0) — کامیاب، 133 — GATT_ERROR، 8 — GATT_CONNECTION_TIMEOUT۔ کامیاب دریافت کے بعد، BluetoothGatt getServices() کے ذریعے دستیاب سروسز کی فہرست بھرتا ہے۔
ہر BluetoothGattService میں BluetoothGattCharacteristic کی فہرست ہوتی ہے۔ ایک خصوصیت میں UUID، خصوصیات (PROPERTY_READ، PROPERTY_WRITE، PROPERTY_NOTIFY) اور اختیاری ڈسکرپٹر ہوتے ہیں۔ خصوصیات یہ طے کرتی ہیں کہ کون سے آپریشنز کی اجازت ہے: اگر کسی خصوصیت میں PROPERTY_READ نہیں ہے، readCharacteristic کال کرنے پر خرابی واپس آئے گی۔ خصوصیت کے ڈسکرپٹر حاصل کرنے کے لیے getDescriptors() استعمال کریں۔
// سروس دریافت اور خصوصیت کی تلاش
class GattServiceExplorer {
// UUID کے ذریعے سروس تلاش کریں
fun findService(gatt: BluetoothGatt, uuid: UUID): BluetoothGattService? {
return gatt.services?.firstOrNull { it.uuid == uuid }
}
// سروس میں خصوصیت تلاش کریں
fun findCharacteristic(
service: BluetoothGattService,
uuid: UUID
): BluetoothGattCharacteristic? {
return service.characteristics?.firstOrNull { it.uuid == uuid }
}
// تمام معاون خصوصیت کے آپریشنز حاصل کریں
fun getCharacteristicProperties(chars: BluetoothGattCharacteristic): List<String> {
val props = mutableListOf<String>()
with(chars.properties) {
if (and(BluetoothGattCharacteristic.PROPERTY_READ) != 0) props.add("READ")
if (and(BluetoothGattCharacteristic.PROPERTY_WRITE) != 0) props.add("لکھیں")
if (and(BluetoothGattCharacteristic.PROPERTY_WRITE_NO_RESPONSE) != 0) props.add("بغیر_جواب_لکھیں")
if (and(BluetoothGattCharacteristic.PROPERTY_NOTIFY) != 0) props.add("NOTIFY")
if (and(BluetoothGattCharacteristic.PROPERTY_INDICATE) != 0) props.add("INDICATE")
}
return props
}
// مکمل GATT درجہ بندی لاگ کریں
fun dumpGattTree(gatt: BluetoothGatt) {
gatt.services?.forEach { service ->
print("Service: ${service.uuid}")
service.characteristics?.forEach { char ->
print(" Characteristic: ${char.uuid}, properties: ${char.properties}")
char.descriptors?.forEach { desc ->
print(" Descriptor: ${desc.uuid}")
}
}
}
}
}
GattServiceExplorer کلاس GATT درجہ بندی میں نیویگیشن کے لیے افادیت فراہم کرتی ہے۔ findService اور findCharacteristic UUID کے ذریعے سروسز اور خصوصیات تلاش کرتے ہیں۔ getCharacteristicProperties and() کے ذریعے خصوصیات کے بٹ ماسک چیک کرتی ہے۔ dumpGattTree لاگ میں مکمل درجہ بندی پرنٹ کرتی ہے — BLE ڈیوائسز کو ڈیبگ کرتے وقت مفید۔ BluetoothGatt پر تمام آپریشنز کامیاب onServicesDiscovered کے بعد ہی انجام دینے چاہییں، ورنہ getServices() خالی فہرست واپس کرے گا۔
readCharacteristic() — ریموٹ BLE ڈیوائس سے خصوصیت کی قدر پڑھنے کے لیے BluetoothGatt کا غیر متزامن طریقہ ہے۔ نتیجہ BluetoothGattCallback کے onCharacteristicRead() میں آتا ہے۔ اگر کسی ڈیوائس میں 2+ مماثل خصوصیات ہیں (غیر متوقع لیکن ممکن)، readCharacteristic() غیر ہدف پڑھ سکتا ہے — UUID کے بجائے BluetoothGattCharacteristic مثال پر readCharacteristic() کال کرنا زیادہ محفوظ ہے۔
readDescriptor() — خصوصیت کے ڈسکرپٹر کی قدر پڑھنے کا طریقہ ہے۔ ایک عام ڈسکرپٹر CCCD (Client Characteristic Configuration Descriptor، UUID 0x2902) ہے، جو طے کرتا ہے کہ اطلاعات فعال ہیں یا نہیں۔ نتیجہ onDescriptorRead() میں ہے۔ عملی طور پر ڈسکرپٹر پڑھنا شاذ و نادر ہی ضروری ہوتا ہے — CCCD کا انتظام setCharacteristicNotification() کرتا ہے، لیکن کسٹم ڈسکرپٹر (User Description 0x2901، Presentation Format 0x2904) کے لیے readDescriptor() میٹا ڈیٹا حاصل کرنے کا واحد طریقہ ہے۔
MTU اور بڑا ڈیٹا پڑھنا — اگر خصوصیت کی قدر MTU (BLE 4.0 کے لیے 23 بائٹ) سے تجاوز کرتی ہے، Android خود بخود BLE اسٹیک کے ذریعے پڑھنے کی درخواستوں کے سلسلے سے ڈیٹا کو ٹکڑوں میں تقسیم اور دوبارہ جمع کرتا ہے۔ توسیعی MTU (251 بائٹ تک) کے ساتھ BLE 5.0+ کے لیے، تقسیم کی ضرورت نہیں ہے — ایک بار پڑھنے سے مکمل ڈیٹا واپس آتا ہے۔ پڑھنے سے پہلے، آپ زیادہ سے زیادہ MTU پر گفت و شنید کے لیے requestMtu() کال کر سکتے ہیں۔
// BluetoothGatt کے ذریعے خصوصیت اور ڈسکرپٹر پڑھیں
class GattReader {
fun readHeartRate(gatt: BluetoothGatt) {
// دل کی دھڑکن سروس UUID = 0x180D
val service = gatt.getService(UUID.fromString("0000180D-0000-1000-8000-00805F9B34FB"))
?: return
// دل کی دھڑکن کی پیمائش UUID = 0x2A37
val characteristic = service.getCharacteristic(
UUID.fromString("00002A37-0000-1000-8000-00805F9B34FB")
) ?: return
if (hasProperty(characteristic, BluetoothGattCharacteristic.PROPERTY_READ)) {
gatt.readCharacteristic(characteristic)
}
}
fun readDescriptor(gatt: BluetoothGatt, characteristic: BluetoothGattCharacteristic) {
// CCCD (0x2902)
val cccd = characteristic.getDescriptor(
UUID.fromString("00002902-0000-1000-8000-00805F9B34FB")
)
cccd?.let { gatt.readDescriptor(it) }
}
// onCharacteristicRead کال بیک میں ڈیٹا پراسیس کریں:
fun parseHeartRate(value: ByteArray): Int {
// BLE دل کی دھڑکن: bytes = flags, second = bpm
return if (value.isNotEmpty()) value[1].toInt() and 0xFF else 0
}
private fun hasProperty(char: BluetoothGattCharacteristic, prop: Int): Boolean {
return char.properties and prop != 0
}
}
GattReader کلاس دل کی دھڑکن کی خصوصیت پڑھنے کو ظاہر کرتی ہے۔ سروس 0x180D میں خصوصیت 0x2A37 (Heart Rate Measurement) ہے — Bluetooth SIG کا معیاری BLE پروفائل۔ پڑھنے سے پہلے، hasProperty کے ذریعے PROPERTY_READ خصوصیت چیک کی جاتی ہے۔ parseHeartRate BLE نبض کی فارمیٹ کو پارس کرتا ہے: پہلا بائٹ — flags (ڈیٹا فارمیٹ)، دوسرا — bpm قدر۔ CCCD ڈسکرپٹر (0x2902) اطلاعات کی حالت چیک کرنے کے لیے پڑھا جاتا ہے۔
writeCharacteristic() — BLE پیری فیرل پر ڈیٹا لکھنے کے لیے BluetoothGatt کا طریقہ ہے۔ Android API 33+ پر، writeCharacteristic() کو writeCharacteristic(request) سے بدل دیا گیا ہے، جہاں BluetoothGattCharacteristicWriteRequest ایک درخواست آبجیکٹ ہے جس میں خصوصیت، بائٹ صف اور WriteType ہوتا ہے۔ setValue() کے ساتھ پرانا writeCharacteristic(characteristic) طریقہ فرسودہ ہے۔ WriteType درخواست کے رویے کا تعین کرتا ہے: WRITE_TYPE_DEFAULT (خصوصیت کی خصوصیات پر منحصر)، WRITE_TYPE_NO_RESPONSE (بغیر جواب) اور WRITE_TYPE_SIGNED (اختیار)۔
WriteType کا انتخاب رفتار اور بھروسے کو متاثر کرتا ہے۔ WRITE_TYPE_DEFAULT عام طور پر withResponse (اگر خصوصیت میں PROPERTY_WRITE ہے) یا withoutResponse (اگر PROPERTY_WRITE_NO_RESPONSE ہے) سے مطابقت رکھتا ہے۔ سٹریمنگ ڈیٹا (OTA اپ ڈیٹس، لاگز) کے لیے WRITE_TYPE_NO_RESPONSE استعمال کریں — زیادہ سے زیادہ تھرو پٹ۔ ترسیل کی ضمانت والے کمانڈز (فعال کرنا، ترتیب دینا) کے لیے — onCharacteristicWrite کے ذریعے تصدیق کے ساتھ WRITE_TYPE_DEFAULT۔
// Android API 33+ پر BLE خصوصیت لکھنا
class GattWriter {
// جواب کے ساتھ لکھیں (withResponse)
fun writeWithResponse(gatt: BluetoothGatt, characteristic: BluetoothGattCharacteristic, data: ByteArray) {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.TIRAMISU) {
// API 33+: writeCharacteristic
val request = BluetoothGattCharacteristicWriteRequest(
characteristic,
data,
BluetoothGattCharacteristicWriteRequest.WRITE_TYPE_DEFAULT,
@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)
)
gatt.writeCharacteristic(request)
} else {
// API < 33: (deprecated)
characteristic.setValue(data)
gatt.writeCharacteristic(characteristic)
}
}
// جواب کے بغیر لکھیں (زیادہ سے زیادہ رفتار)
fun writeWithoutResponse(gatt: BluetoothGatt, characteristic: BluetoothGattCharacteristic, data: ByteArray) {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.TIRAMISU) {
val request = BluetoothGattCharacteristicWriteRequest(
characteristic,
data,
BluetoothGattCharacteristicWriteRequest.WRITE_TYPE_NO_RESPONSE,
@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)
)
gatt.writeCharacteristic(request)
} else {
characteristic.setValue(data)
characteristic.writeType = BluetoothGattCharacteristic.WRITE_TYPE_NO_RESPONSE
gatt.writeCharacteristic(characteristic)
}
}
// onCharacteristicWrite کال بیک (API 33+)
private val writeCallback = object : BluetoothGattCallback() {
override fun onCharacteristicWrite(
gatt: BluetoothGatt,
characteristic: BluetoothGattCharacteristic,
value: ByteArray,
status: Int,
callbackType: Int
) {
if (status == BluetoothGatt.GATT_SUCCESS) {
print("Write success: ${value.size} bytes")
}
}
}
}
GattWriter کلاس مختلف API لیولز کے لیے دونوں WriteTypes کو سپورٹ کرتی ہے۔ writeWithResponse WRITE_TYPE_DEFAULT استعمال کرتا ہے — BLE ڈیوائس onCharacteristicWrite کے ذریعے تحریر کی تصدیق کرتا ہے۔ writeWithoutResponse WRITE_TYPE_NO_RESPONSE استعمال کرتا ہے — ڈیٹا تصدیق کے بغیر بھیجا جاتا ہے، زیادہ سے زیادہ تھرو پٹ۔ API 33+ پر، BluetoothGattCharacteristicWriteRequest کے ساتھ نیا writeCharacteristic(request) استعمال ہوتا ہے۔ API < 33 پر — پرانا setValue() + writeCharacteristic().
setCharacteristicNotification() — پیری فیرل پر خصوصیت کی تبدیلیوں کے بارے میں اطلاعات سبسکرائب کرنے کے لیے BluetoothGatt کا طریقہ ہے۔ سبسکرپشن فعال کرنے کے بعد، BLE ڈیوائس onCharacteristicChanged() کے ذریعے نئی قدریں بھیجتا ہے۔ تاہم، setCharacteristicNotification() صرف مقامی Android اطلاع کو فعال کرتا ہے — BLE ڈیوائس پر ہی اطلاعات فعال کرنے کے لیے، آپ کو CCCD ڈسکرپٹر (0x2902) میں قدر 0x0100 بھی لکھنی ہوگی۔
CCCD (Client Characteristic Configuration Descriptor) — ایک ڈسکرپٹر ہے جو BLE پیری فیرل سے اطلاعات بھیجنے کو کنٹرول کرتا ہے۔ قدر 0x0000 — اطلاعات غیر فعال، 0x0100 — اطلاعات فعال، 0x0200 — اشارے فعال۔ CCCD میں تحریر setCharacteristicNotification() کال کرنے کے بعد BluetoothGatt پر writeDescriptor() کے ذریعے کی جاتی ہے۔ Android خود بخود CCCD نہیں لکھتا — یہ ذمہ داری ڈویلپر پر ہے۔
// درست BLE اطلاع سبسکرپشن
class GattNotificationManager {
// 1. اطلاعات فعال کریں
fun enableNotification(gatt: BluetoothGatt, characteristic: BluetoothGattCharacteristic) {
// مرحلہ 1: مقامی Android سبسکرپشن
val success = gatt.setCharacteristicNotification(characteristic, true)
if (!success) {
print("سبسکرائب کرنے میں ناکام")
return
}
// مرحلہ 2: BLE ڈیوائس پر CCCD (0x2902) لکھیں
val cccdDescriptor = characteristic.getDescriptor(
UUID.fromString("00002902-0000-1000-8000-00805F9B34FB")
) ?: return
// 0x0100 = اطلاع، 0x0200 = اشارہ
val cccdValue = if (characteristic.properties
and BluetoothGattCharacteristic.PROPERTY_NOTIFY != 0) {
BluetoothGattDescriptor.ENABLE_NOTIFICATION_VALUE // [0x01, 0x00]
} else {
BluetoothGattDescriptor.ENABLE_INDICATION_VALUE // [0x02, 0x00]
}
cccdDescriptor.setValue(cccdValue)
gatt.writeDescriptor(cccdDescriptor)
}
// 2. خصوصیت کی دریافت
fun disableNotification(gatt: BluetoothGatt, characteristic: BluetoothGattCharacteristic) {
gatt.setCharacteristicNotification(characteristic, false)
val cccdDescriptor = characteristic.getDescriptor(
UUID.fromString("00002902-0000-1000-8000-00805F9B34FB")
) ?: return
cccdDescriptor.setValue(BluetoothGattDescriptor.DISABLE_NOTIFICATION_VALUE)
gatt.writeDescriptor(cccdDescriptor)
}
// 3. اطلاع کال بیک
private val notificationCallback = object : BluetoothGattCallback() {
override fun onCharacteristicChanged(
gatt: BluetoothGatt,
characteristic: BluetoothGattCharacteristic,
value: ByteArray,
callbackType: Int
) {
// BLE پیری فیرل سے نئی قدر
print("Notification: ${value.size} bytes")
}
}
}
GattNotificationManager کلاس درست دو قدمی BLE اطلاع سبسکرپشن پروٹوکول کو نافذ کرتی ہے۔ enableNotification پہلے Android پر setCharacteristicNotification(true) کال کرتا ہے، پھر writeDescriptor کے ذریعے CCCD ڈسکرپٹر میں 0x0100 لکھتا ہے۔ disableNotification الٹی کارروائیاں کرتا ہے۔ CCCD تحریر کے بغیر، BLE ڈیوائس اطلاعات نہیں بھیجتا — Android پر BLE ڈویلپرز کی یہ سب سے عام غلطی ہے۔
مکمل مثال Kotlin میں GATT کلائنٹ کی جو غیر متزامن پروسیسنگ کے لیے کوروٹین استعمال کرتے ہوئے ایک مینیجر میں BluetoothGatt تخلیق، دریافت، پڑھنے اور اطلاع سبسکرپشن کو یکجا کرتی ہے۔
// Kotlin میں کوروٹین کے ساتھ مکمل GATT کلائنٹ
class GattClient(context: Context) {
private val context = context.applicationContext
private var gatt: BluetoothGatt? = null
// کوروٹین سے جڑیں
suspend fun connect(device: BluetoothDevice): Boolean =
suspendCoroutine { continuation ->
gatt = device.connectGatt(
context, false,
object : BluetoothGattCallback() {
override fun onConnectionStateChange(
gatt: BluetoothGatt, status: Int, newState: Int
) {
if (newState == BluetoothProfile.STATE_CONNECTED) {
gatt.discoverServices()
} else {
continuation.resume(false)
}
}
override fun onServicesDiscovered(gatt: BluetoothGatt, status: Int) {
continuation.resume(status == BluetoothGatt.GATT_SUCCESS)
}
},
BluetoothDevice.TRANSPORT_LE
)
}
// کوروٹین کے ذریعے خصوصیت پڑھیں
suspend fun readCharacteristicValue(char: BluetoothGattCharacteristic): ByteArray? =
suspendCoroutine { continuation ->
gatt?.let { gatt ->
// کال بیک شناخت کے لیے خصوصیت کا ٹیگ محفوظ کریں
gatt.setCharacteristic(char, null) // API کے لیے < 33
gatt.readCharacteristic(char)
}
}
// کنکشن بند کریں
fun release() {
gatt?.disconnect()
gatt?.close()
gatt = null
}
}
GATT کلائنٹ GattClient کال بیک پر مبنی BluetoothGatt API کو ترتیب وار کالز میں تبدیل کرنے کے لیے کوروٹین (suspendCoroutine) استعمال کرتا ہے۔ connect() onServicesDiscovered کا انتظار کرتا ہے، جس کے بعد GATT درجہ بندی دستیاب ہے۔ readCharacteristicValue() onCharacteristicRead کا انتظار کرتا ہے۔ یہ طریقہ کال بیک نیسٹنگ کو ختم کرتا ہے اور BLE کوڈ کو لکیری بناتا ہے۔ release() وسائل کی صفائی کی ضمانت دیتا ہے — Activity کے onDestroy یا ViewModel.onCleared میں لازمی کال۔
اکثر پوچھے گئے سوالات
BluetoothGatt — Android میں GATT کلائنٹ کے لیے کلاس ہے جو پیری فیرل ڈیوائس کے ساتھ BLE کنکشن کا انتظام کرتی ہے۔ یہ BluetoothDevice.connectGatt() کے ذریعے بنائی جاتی ہے، جو discoverServices()، readCharacteristic()، writeCharacteristic()، setCharacteristicNotification() طریقے فراہم کرتی ہے۔ تمام آپریشنز کے نتائج BluetoothGattCallback کے ذریعے غیر متزامن طور پر آتے ہیں۔ BluetoothGatt کے بغیر، Android پر دو طرفہ BLE مواصلات ناممکن ہے۔
اسٹیٹس 133 (GATT_ERROR) Android BLE اسٹیک کی اندرونی خرابی کی نشاندہی کرتا ہے۔ وجوہات: دریافت کے دوران ڈیوائس منقطع ہو گیا، MTU کم از کم (23 بائٹ) سے کم ہے، یا BLE اسٹیک اوورلوڈ ہے۔ حل: 500 ms تاخیر کے ساتھ discoverServices() دوبارہ کریں، ڈیوائس RSSI چیک کریں اور یقینی بنائیں کہ پیری فیرل اپنی موجودہ حالت میں GATT دریافت کو سپورٹ کرتا ہے۔
تصدیق کے ساتھ لکھنے کے لیے، WRITE_TYPE_DEFAULT (API 33+: BluetoothGattCharacteristicWriteRequest) کے ساتھ writeCharacteristic() کال کریں۔ کامیابی پر، BLE ڈیوائس تصدیق بھیجتا ہے اور Android GATT_SUCCESS کے ساتھ onCharacteristicWrite کال کرتا ہے۔ اگر ڈیوائس 30 سیکنڈ (اسٹیک ٹائم آؤٹ) کے اندر جواب نہیں دیتی، کال بیک خرابی اسٹیٹس واپس کرتا ہے۔ واچ ڈاگ کے لیے postDelayed کے ساتھ Handler استعمال کریں۔
Android 13+ (API 33) پر، BluetoothGatt کے طریقے بدل گئے ہیں: writeCharacteristic() اب BluetoothGattCharacteristicWriteRequest قبول کرتا ہے، readCharacteristic() — BluetoothGattCharacteristicReadRequest۔ پرانے setValue()/writeCharacteristic() فرسودہ ہیں۔ BluetoothGattCallback بھی بدل گیا ہے: onCharacteristicRead()، onCharacteristicWrite()، onCharacteristicChanged() ByteArray value اور callbackType وصول کرتے ہیں۔ برانچنگ کے لیے Build.VERSION.SDK_INT استعمال کریں۔
Android 4–8 بیک وقت BLE GATT کنکشنز کو سپورٹ کرتا ہے (مینوفیکچرر اور Android ورژن پر منحصر ہے)۔ Pixel/Google: 7 تک، Samsung: 5 تک، Xiaomi: 4 تک۔ حد سے تجاوز کرنے پر، connectGatt null یا onConnectionStateChange خرابی کے ساتھ واپس کرتا ہے۔ بڑی تعداد میں ڈیوائسز کے ساتھ کام کرنے کے لیے، چکری کنکشن یا Bluetooth Mesh استعمال کریں۔
خلاصہ
ہم ایک موبائل ایپلیکیشن ٹرنکی تیار کریں گے
IT Sectr 2017 سے اسٹارٹ اپس اور کاروبار کے لیے iOS اور Android ایپلیکیشنز بناتا ہے۔ ہم آپ کو مشورہ دیں گے اور بہترین حل تجویز کریں گے۔
مزید پڑھیں