Avatar for sammachin

sammachin

Member since Nov 2016 • Last active Dec 2017
  • 3 conversations
  • 10 comments

Most recent activity

  • in Puck.js
    Avatar for sammachin

    It looks like there's an ANCS client for the nRF52 in the Nordic SDK, https://infocenter.nordicsemi.com/index.­jsp?topic=%2Fcom.nordic.infocenter.sdk52­.v0.9.2%2Fble_sdk_app_ancs.html would be VERY cool if this was part of espruino one day with some nice high level API calls to respond to alerts

  • in Puck.js
    Avatar for sammachin

    Yeah, its certainly far easier from a UX perspective to initiate the pairing from the iPhone and ust have the embedded device accept whatever tried to connect.

    No that XML is from the nRF8001 Arduino example https://github.com/NordicSemiconductor/b­le-sdk-arduino/tree/master/libraries/BLE­/examples/ble_ANCS_template It looks like you run that through an nRF app on your machine (nrfGo ??) to generate a services.h file that then gets flashed onto the 8001

  • in Puck.js
    Avatar for sammachin

    I don't think so, I've tried having everything else turned off to reduce the various BLE options in the room, from what I can see the iPhone just doesn't accept unsolicited connections.

    Over the weekend I got ANCS working on an Arduino with an nRF 8001 board as there are some pre-built libraries for that (also the contest I'm working on is Arduino centered so I need to use that!)

    It looks as if the Arduino is advertising some other services (battery etc) which the iPhone then sees in the Bluetooth devices and I can initiate the connection from the iPhone at which point the Arduino requests pairing (bonding)

    I'll need to go back and take a look at the services it advertises to see if I can re-create these on the Puck.
    This is the xml file that the nRF uses to expose services, I'm guessing this might make sense to you?

    <?xml version="1.0" encoding="UTF-8"?>
    <!DOCTYPE AttributeServer>
    <Profile Version="1.3">
        <SetupId>1</SetupId>
        <Device>nRF8001_Dx</Device>
        <Service Type="local" PrimaryService="true">
            <Name>TX Power</Name>
            <Uuid>1804</Uuid>
            <Characteristic>
                <Name>TX Power Level</Name>
                <Uuid>2a07</Uuid>
                <DefaultValue>0</DefaultValue>
                <UsePresentationFormat>0</UsePresentatio­nFormat>
                <MaxDataLength>1</MaxDataLength>
                <AttributeLenType>1</AttributeLenType>
                <ForceOpen>false</ForceOpen>
                <Properties>
                    <WriteWithoutResponse>false</WriteWithou­tResponse>
                    <Write>false</Write>
                    <Notify>false</Notify>
                    <Indicate>false</Indicate>
                    <Broadcast>false</Broadcast>
                </Properties>
                <SetPipe>true</SetPipe>
                <AckIsAuto>true</AckIsAuto>
                <PresentationFormatDescriptor Value="0000" Exponent="0" Format="1" NameSpace="01" Unit="0000"/>
                <PeriodForReadingThisCharacteristic>0</P­eriodForReadingThisCharacteristic>
                <PeriodForProperties/>
            </Characteristic>
        </Service>
        <Service Type="local" PrimaryService="true">
            <Name>Immediate Alert</Name>
            <Uuid>1802</Uuid>
            <Characteristic>
                <Name>Alert Level</Name>
                <Uuid>2a06</Uuid>
                <DefaultValue></DefaultValue>
                <UsePresentationFormat>0</UsePresentatio­nFormat>
                <MaxDataLength>1</MaxDataLength>
                <AttributeLenType>1</AttributeLenType>
                <ForceOpen>false</ForceOpen>
                <Properties>
                    <WriteWithoutResponse>true</WriteWithout­Response>
                    <Write>false</Write>
                    <Notify>false</Notify>
                    <Indicate>false</Indicate>
                    <Broadcast>false</Broadcast>
                </Properties>
                <SetPipe>false</SetPipe>
                <AckIsAuto>true</AckIsAuto>
                <PresentationFormatDescriptor Value="0000" Exponent="0" Format="1" NameSpace="01" Unit="0000"/>
                <PeriodForReadingThisCharacteristic>0</P­eriodForReadingThisCharacteristic>
                <PeriodForProperties/>
            </Characteristic>
        </Service>
        <Service Type="local" PrimaryService="true">
            <Name>Link Loss Alert</Name>
            <Uuid>1803</Uuid>
            <Characteristic>
                <Name>Alert Level</Name>
                <Uuid>2a06</Uuid>
                <DefaultValue>0</DefaultValue>
                <UsePresentationFormat>0</UsePresentatio­nFormat>
                <MaxDataLength>1</MaxDataLength>
                <AttributeLenType>1</AttributeLenType>
                <ForceOpen>false</ForceOpen>
                <Properties>
                    <WriteWithoutResponse>false</WriteWithou­tResponse>
                    <Write>true</Write>
                    <Notify>false</Notify>
                    <Indicate>false</Indicate>
                    <Broadcast>false</Broadcast>
                </Properties>
                <SetPipe>false</SetPipe>
                <AckIsAuto>true</AckIsAuto>
                <PresentationFormatDescriptor Value="0000" Exponent="0" Format="1" NameSpace="01" Unit="0000"/>
                <PeriodForReadingThisCharacteristic>0</P­eriodForReadingThisCharacteristic>
                <PeriodForProperties/>
            </Characteristic>
        </Service>
        <Service Type="local" PrimaryService="true">
            <Name>Battery</Name>
            <Uuid>180f</Uuid>
            <Characteristic>
                <Name>Battery Level</Name>
                <Uuid>2a19</Uuid>
                <DefaultValue>64</DefaultValue>
                <UsePresentationFormat>0</UsePresentatio­nFormat>
                <MaxDataLength>1</MaxDataLength>
                <AttributeLenType>1</AttributeLenType>
                <ForceOpen>false</ForceOpen>
                <Properties>
                    <WriteWithoutResponse>false</WriteWithou­tResponse>
                    <Write>false</Write>
                    <Notify>true</Notify>
                    <Indicate>false</Indicate>
                    <Broadcast>false</Broadcast>
                </Properties>
                <SetPipe>true</SetPipe>
                <AckIsAuto>false</AckIsAuto>
                <PresentationFormatDescriptor Value="0000" Exponent="0" Format="4" NameSpace="01" Unit="27AD"/>
                <PeriodForReadingThisCharacteristic>0</P­eriodForReadingThisCharacteristic>
                <PeriodForProperties/>
            </Characteristic>
        </Service>
        <Service Type="remote" PrimaryService="true">
            <Name>Immediate Alert</Name>
            <Uuid>1802</Uuid>
            <Characteristic>
                <Name>Alert Level</Name>
                <Uuid>2a06</Uuid>
                <DefaultValue>0</DefaultValue>
                <UsePresentationFormat>0</UsePresentatio­nFormat>
                <MaxDataLength>1</MaxDataLength>
                <AttributeLenType>1</AttributeLenType>
                <ForceOpen>false</ForceOpen>
                <Properties>
                    <Read>false</Read>
                    <WriteWithoutResponse>true</WriteWithout­Response>
                    <Write>false</Write>
                    <Notify>false</Notify>
                    <Indicate>false</Indicate>
                    <Broadcast>false</Broadcast>
                </Properties>
                <AckIsAuto>true</AckIsAuto>
                <PresentationFormatDescriptor Value="0000" Exponent="0" Format="1" NameSpace="01" Unit="0000"/>
                <PeriodForReadingThisCharacteristic>0</P­eriodForReadingThisCharacteristic>
                <PeriodForProperties/>
            </Characteristic>
        </Service>
        <Service Type="local" PrimaryService="true">
            <Name>Device Information</Name>
            <Uuid>180a</Uuid>
            <Characteristic>
                <Name>Hardware Revision String</Name>
                <Uuid>2a27</Uuid>
                <DefaultValue></DefaultValue>
                <UsePresentationFormat>0</UsePresentatio­nFormat>
                <MaxDataLength>9</MaxDataLength>
                <AttributeLenType>2</AttributeLenType>
                <ForceOpen>false</ForceOpen>
                <Properties>
                    <WriteWithoutResponse>false</WriteWithou­tResponse>
                    <Write>false</Write>
                    <Notify>false</Notify>
                    <Indicate>false</Indicate>
                    <Broadcast>false</Broadcast>
                </Properties>
                <SetPipe>true</SetPipe>
                <AckIsAuto>false</AckIsAuto>
                <PresentationFormatDescriptor Value="0000" Exponent="0" Format="25" NameSpace="01" Unit="0000"/>
                <PeriodForReadingThisCharacteristic>0</P­eriodForReadingThisCharacteristic>
                <PeriodForProperties/>
            </Characteristic>
        </Service>
        <Service Type="remote" PrimaryService="true">
            <Name>ANCS</Name>
            <Uuid BaseUUID="79050000B5CE4E99A40F4B1E122D00­D0" BaseUUIDName="ANCS">f431</Uuid>
            <Characteristic>
                <Name>Notification Source</Name>
                <Uuid BaseUUID="9fbf0000630142d98c5825e699A21D­BD" BaseUUIDName="ANCS Notification Source">120d</Uuid>
                <DefaultValue></DefaultValue>
                <UsePresentationFormat>0</UsePresentatio­nFormat>
                <MaxDataLength>20</MaxDataLength>
                <AttributeLenType>1</AttributeLenType>
                <ForceOpen>false</ForceOpen>
                <Properties>
                    <Read>false</Read>
                    <WriteWithoutResponse>false</WriteWithou­tResponse>
                    <Write>false</Write>
                    <Notify>true</Notify>
                    <Indicate>false</Indicate>
                    <Broadcast>false</Broadcast>
                </Properties>
                <AckIsAuto>false</AckIsAuto>
                <PresentationFormatDescriptor Value="0000" Exponent="0" Format="1" NameSpace="01" Unit="0000"/>
                <PeriodForReadingThisCharacteristic>0</P­eriodForReadingThisCharacteristic>
                <PeriodForProperties/>
            </Characteristic>
            <Characteristic>
                <Name>Control Point</Name>
                <Uuid BaseUUID="69D1000045E149A898219BBDFDAAD9­D9" BaseUUIDName="ANCS Control Point">d8f3</Uuid>
                <DefaultValue></DefaultValue>
                <UsePresentationFormat>0</UsePresentatio­nFormat>
                <MaxDataLength>20</MaxDataLength>
                <AttributeLenType>1</AttributeLenType>
                <ForceOpen>false</ForceOpen>
                <Properties>
                    <Read>false</Read>
                    <WriteWithoutResponse>false</WriteWithou­tResponse>
                    <Write>true</Write>
                    <Notify>false</Notify>
                    <Indicate>false</Indicate>
                    <Broadcast>false</Broadcast>
                </Properties>
                <AckIsAuto>false</AckIsAuto>
                <PresentationFormatDescriptor Value="0000" Exponent="0" Format="1" NameSpace="01" Unit="0000"/>
                <PeriodForReadingThisCharacteristic>0</P­eriodForReadingThisCharacteristic>
                <PeriodForProperties/>
            </Characteristic>
            <Characteristic>
                <Name>Data Source</Name>
                <Uuid BaseUUID="22EA000024D64BB5BE44B36ACE7C7B­FB" BaseUUIDName="ANCS Data Source">c6e9</Uuid>
                <DefaultValue></DefaultValue>
                <UsePresentationFormat>0</UsePresentatio­nFormat>
                <MaxDataLength>20</MaxDataLength>
                <AttributeLenType>1</AttributeLenType>
                <ForceOpen>false</ForceOpen>
                <Properties>
                    <Read>false</Read>
                    <WriteWithoutResponse>false</WriteWithou­tResponse>
                    <Write>false</Write>
                    <Notify>true</Notify>
                    <Indicate>false</Indicate>
                    <Broadcast>false</Broadcast>
                </Properties>
                <AckIsAuto>false</AckIsAuto>
                <PresentationFormatDescriptor Value="0000" Exponent="0" Format="1" NameSpace="01" Unit="0000"/>
                <PeriodForReadingThisCharacteristic>0</P­eriodForReadingThisCharacteristic>
                <PeriodForProperties/>
            </Characteristic>
        </Service>
        <Gapsettings>
            <Name>ANCS Rusk</Name>
            <DeviceNameWriteLength>0</DeviceNameWrit­eLength>
            <LocalPipeOnDeviceName>false</LocalPipeO­nDeviceName>
            <DeviceNameShortLength>3</DeviceNameShor­tLength>
            <Apperance>0240</Apperance>
            <SecurityLevel>1</SecurityLevel>
            <AuthenticationReq>0</AuthenticationReq>­
            <IoCapabilities>0</IoCapabilities>
            <BondTimeout>600</BondTimeout>
            <SecurityRequestDelay>99</SecurityReques­tDelay>
            <MinimumKeySize>7</MinimumKeySize>
            <MaximumKeySize>16</MaximumKeySize>
            <AdvertisingDataBondedBitmap>10</Adverti­singDataBondedBitmap>
            <AdvertisingDataGeneralBitmap>10</Advert­isingDataGeneralBitmap>
            <AdvertisingDataBrodcastBitmap>0</Advert­isingDataBrodcastBitmap>
            <AdvertisingDataBondedScanResponseBitmap­>2c40</AdvertisingDataBondedScanResponse­Bitmap>
            <AdvertisingDataGeneralScanResponseBitma­p>2c40</AdvertisingDataGeneralScanRespon­seBitmap>
            <AdvertisingDataBrodcastScanResponseBitm­ap>0</AdvertisingDataBrodcastScanRespons­eBitmap>
            <AdvertisingDataBondedBitmapCustom>1</Ad­vertisingDataBondedBitmapCustom>
            <AdvertisingDataGeneralBitmapCustom>1</A­dvertisingDataGeneralBitmapCustom>
            <AdvertisingDataBrodcastBitmapCustom>0</­AdvertisingDataBrodcastBitmapCustom>
            <AdvertisingDataBondedScanResponseBitmap­Custom>0</AdvertisingDataBondedScanRespo­nseBitmapCustom>
            <AdvertisingDataGeneralScanResponseBitma­pCustom>0</AdvertisingDataGeneralScanRes­ponseBitmapCustom>
            <AdvertisingDataBrodcastScanResponseBitm­apCustom>0</AdvertisingDataBrodcastScanR­esponseBitmapCustom>
            <TxPowerLevelOffset>0</TxPowerLevelOffse­t>
            <MinimumConnectionInterval>400</MinimumC­onnectionInterval>
            <MaximumConnectionInterval>800</MaximumC­onnectionInterval>
            <SlaveLatency>0</SlaveLatency>
            <TimeoutMultipler>600</TimeoutMultipler>­
            <AddServiceUpdateCharacteristic>true</Ad­dServiceUpdateCharacteristic>
            <AddServiceUpdateCharacteristicPipe>true­</AddServiceUpdateCharacteristicPipe>
            <SercieToSolicitate>
                <Uuid BaseUUID="79050000B5CE4E99A40F4B1E122D00­D0" BaseUUIDName="ANCS">f431</Uuid>
            </SercieToSolicitate>
            <CustomAdTypes>
                <AdType index="1">
                    <Type>19</Type>
                    <Value>4002</Value>
                </AdType>
                <AdType index="2">
                    <Type>18</Type>
                    <Value></Value>
                </AdType>
            </CustomAdTypes>
        </Gapsettings>
        <Hardwaresettings>
            <Clocksource>1</Clocksource>
            <ClockAccuracy>1</ClockAccuracy>
            <InitialTxPower>3</InitialTxPower>
            <HfClkSource>0</HfClkSource>
            <DcDcConverter>0</DcDcConverter>
            <ActiveSignalModeIndex>0</ActiveSignalMo­deIndex>
            <ActiveSignalToTickDistance>0</ActiveSig­nalToTickDistance>
            <DynamicWindowLimitingEnabled>true</Dyna­micWindowLimitingEnabled>
        </Hardwaresettings>
        <CurrentInput>
            <BatteryCharge>220</BatteryCharge>
            <Master32KhzClockAccuracy>10</Master32Kh­zClockAccuracy>
            <ConnectionInterval>1000</ConnectionInte­rval>
            <PercentOfTimeSleeping>0</PercentOfTimeS­leeping>
            <PercentOfTimeAdvertising>0</PercentOfTi­meAdvertising>
            <AdvertisingInterval>1280</AdvertisingIn­terval>
        </CurrentInput>
    </Profile>
    
  • in Puck.js
    Avatar for sammachin

    I'm working on implementing ANCS (Apple Notification Service) on the Puck so that when my iPhone gets an alert its sent over BLE to the puck. I've had some success using the nRF toolbox on my Android phone to connect to the iPhone and I can see alerts coming over. Therefore I know the iPhone side is working.

    However I can't seem to implement it on the puck, from what I can tell I first need to bond the Puck to the iPhone and then I can connect to the ANCS service and subscribe to the Notification Service.
    However the puck doesn't seem to be able to initiate a connection to the iPhone let alone get as far as bonding, I've tried both discovering the device and then connecting as well as responding to an incomming connection, both of which the NRF.connect fails with a connection timeout.
    I'm using a serial console now so that the pucks BLE device is free to connect to the iPhone and I can debug on the console, code is below,

    var devices;
    var ios;
    
    //Discover BLE Devices
    NRF.findDevices(function(d) {
      devices = d;
      console.log(devices);
    }, 5000);
        
    
    // Find one with the ANCS Service
    for (var i = 0; i < devices.length; i++) {
        if (devices[i].services.indexOf("7905f431-b­5ce-4e33-a455-4b1e122d00d0") != -1){
          ios = devices[i];
        }         
    }
    
    //Bond to it
    ios.gatt.connect().then(function(g) {
      gatt = g;
      console.log("connected");
      return gatt.startBonding();
    }).then(function() {
      console.log("bonded", gatt.getSecurityStatus());
      LED2.set();
      gatt.disconnect();
    }).catch(function(e) {
        LED1.set();
        console.log("ERROR",e);
    });
    
    
  • in Puck.js
    Avatar for sammachin

    Just thought I'd share the finished code for sending a word with a click of the button as a BLE HID Keyboard, not yet tried linking to the RasPi but works great with my iMac

    var kb = require("ble_hid_keyboard");
    NRF.setServices(undefined, { hid : kb.report });
    var reset_timer;
    var char_timer;
    var arr;
    
    var word = "Hello";
    
    
    function send(){
      LED3.set();
      arr = word.split("");
      char_timer = setInterval("sendChar()", 100);
      LED2.set();
      setTimeout("LED2.reset()",1000);
      LED3.reset();
    }
    
    function onTimeout() {
      setTimeout("LED1.reset()",5000);
      LED1.set();
      LED3.reset();
    }
    
    function sendChar(){
        if (arr.length !== 0){
            var char = arr.shift();
            if (char == char.toLowerCase())
            {
                sk = 0;
            }
            else
            {
                sk = 0x02;
            }
            kb.tap(kb.KEY[char.toUpperCase()], sk);
        }
        else{
            clearInterval(char_timer);
        }
    }
    
    setWatch(function() {
      send();
      }, BTN, {edge:"rising", debounce:50, repeat:true});
    
  • in Puck.js
    Avatar for sammachin

    ah yeah that worked (shift+alt) click on the bluetooth icon in the menu bar then select remove for the Puck and then reconnect via the WebIDE, now its sending the character :)

    Next challenge is to get this connected to my RasPi as a keyboard, any tips?

    :)

  • in Puck.js
    Avatar for sammachin

    hmm ok I'll have another go, I've taken out the 2nd character for now just to keep it simple.
    I've been having lots of problems with re-connecting tothe puck usually involving removing the battery and starting over

  • in Puck.js
    Avatar for sammachin

    I'm trying to setup my puck as a single button keyboard to send a character (or two) when the button is pressed, I'm not having much luck and struggling with how to debug it, as I understand it I have to disconnect the web bluetooth IDE before the puck can connect as a keyboard?
    I've flashed the code below to the puck then disconnect and press the button, the BLUE LED comes on for 10sec then the red one flashes as I would expect indicating its failed, I've tried scanning for new bluetooth devices (keyboards) from my Mac and iPhone after I disconnect but nothing is found.

    var kb = require("ble_hid_keyboard");
    NRF.setServices(undefined, { hid : kb.report });
    var reset_timer;
    
    function sendKB(){
      LED3.set();
      kb.tap(kb.KEY.H, kb.MODIFY.SHIFT, function() {
        kb.tap(kb.KEY.i, 0);
        });
      clearTimeout(reset_timer);
      LED2.set();
      setTimeout("LED2.reset()",1000);
      LED3.reset();
    }
    
    function onTimeout() {
      setTimeout("LED1.reset()",1000);
      LED1.set();
      LED3.reset();
    }
    
    setWatch(function() {
      reset_timer = setTimeout("onTimeout()",10000);
      sendKB();
      }, BTN, {edge:"rising", debounce:50, repeat:true});
    

    I'm running 1.9.1 on my puck, updated to that this morning

Actions