-2

I'm trying to send a typedef object through Core Bluetooth that another device will have access to and be able to use. @implementation NeeAppDelegate typedef struct { float a, b, c,

    char    Name[20];
} MyObject;

So here I declared my typedef class that I want to send through Core Bluetooth which I think is okay. Then in a later method:

-(void) method
}
//declare the typedef object
MyObject myObject;

//cast it into a Byte Array
_byteArray = (Byte *) &object;

//Set all bins in the array to 0
memset(&object, 0, sizeof(MyObject));

//Assign the values to myObject
myObject.a = 1;
myObject.b = 2 ;
myObject.c = 3;

//This value could be changed that's why I have the array set to 20
NSString * name = @"Name";
strcpy(myObject.Name, [name UTF8String]);

_byteData = [NSData alloc] initWithBytes:_byteArray length: sizeof(MyObject)];
} 

Now I switch classes to a peripheral ViewController where I handle the data sending.

- (void) peripheralManager            : (CBPeripheralManager *) peripheral
     central                      : (CBCentral *) central
     didSubscribeToCharacteristic : (CBCharacteristic *) characteristic
{
   if (m_dataToSend != nil)
   {
       [m_dataToSend release];
   }

   m_dataToSend = [NeeAppDelegate sharedInstance].byteData;

   m_sendDataIndex = 0;

   [self sendData];
}

Here's the dataSend method I used in order to send the data to another device

    - (void) sendData
{
    if (m_sendDataIndex >= m_dataToSend.length)                     // Is there any left to send?
{
    // No data left.  send EOD

    [m_peripheralManager updateValue:[NSData data]
                              forCharacteristic:m_transferCharacteristic
                           onSubscribedCentrals:nil];

    [m_peripheralManager stopAdvertising];

    //Resume the beacon advertising

    [_viewControllerNeedle.needlePeripheralManager startAdvertising:_viewControllerNeedle.beaconSpecificPeripheralData];
}
else
{
    BOOL        bDidSend = YES;
    NSInteger   amountToSend = 0;

    // There's data left, so send until the callback fails, or we're done.

    while (bDidSend)
    {
        amountToSend = m_dataToSend.length - m_sendDataIndex;

        if (amountToSend > NOTIFY_MTU)
        {
            amountToSend = NOTIFY_MTU;
        }

        // Copy out the data we want

        bDidSend = [m_peripheralManager updateValue:[NSData dataWithBytes:m_dataToSend.bytes + m_sendDataIndex
                                                                   length:amountToSend]
                                  forCharacteristic:m_transferCharacteristic
                               onSubscribedCentrals:nil];

        if (bDidSend)
        {
            m_sendDataIndex += amountToSend;
        }
    }
}

}

Now in my CentralManager class How would I manage to get access to the data within the byteArray? I know the format to get a value from a byte array you need to use

*(float*)&[NeeAppDelegate sharedInstance].byteArray[0];
  • `NSLog()` _byteData, verify that the data is what you want and post the data. Ya really have to look at the data when there are problems. – zaph Jul 27 '14 at 19:02
  • Make a separate statement to get the data to send, and `NSLog()` it. That is: `[NSData dataWithBytes:m_dataToSend.bytes + m_sendDataIndex length:amountToSend]`. Better practice would be to use the `NSData` methods: `subdataWithRange:` and `appendBytes:length:` instead or laying with indexes. – zaph Jul 27 '14 at 19:10
  • Are you asking how to turn the bytes back into your structure on the receiving end? If you are programming both the central and peripheral roles then I think you are taking the wrong approach. The approach you are using is used when the peripheral is emulating a serial port. A better approach is to expose each of your values (`a` `b` and `c` in this case) as separate characteristics of your peripheral. You can then update them as required and if your central as subscribed to a notify it will get advised there are new values – Paulw11 Jul 27 '14 at 23:03

1 Answers1

0

The simplest way to checkout LGBluetooth -> https://github.com/SocialObjects-Software/LGBluetooth

After that, use this code (All stuff will be handled by LGBluetooth, even connection)

LGUtils writeData:self.transactData
                    charactUUID:FCBBLEPaymentTransactionCharUUID
                    serviceUUID:FCBBLEPaymentServiceUUID
                     peripheral:aPeripheral
                     completion:^(NSError *error)
              {
              }];

Here is a sample code, that will convert you NSString to equivalent NSData

         NSString *someString = @"123456789";
         const char *transactStr = [someString UTF8String];
         int8_t *transactBytes = malloc(strlen(transactStr) * sizeof(int8_t));

         size_t transactDataSize = (strlen(transactStr) * sizeof(int8_t)) / 2;

         int curssorOffset = 0;
         for (int i = 0; i < transactDataSize; i++) {
             transactBytes[i] = ((transactStr[curssorOffset] - '0') * 16) + (transactStr[curssorOffset + 1] - '0');
             curssorOffset += 2;
         }
         NSData *transactData = [NSData dataWithBytes:transactBytes
                                               length:transactDataSize];
         free(transactBytes);
         [LGUtils writeData:transactData
                charactUUID:@"5ec0"
                serviceUUID:@"4ca1"
                 peripheral:aPeripheral
                 completion:^(NSError *error)
          {
              aCallback(error);
              [aPeripheral disconnectWithCompletion:nil];
          }];
l0gg3r
  • 8,864
  • 3
  • 26
  • 46