This post is older than 2 years and might not be relevant anymore
More Info: Consider searching for newer posts

How to create a nRF8001 configuration for touch device with nRFgo

According to Microsoft's instruction on HID touch device, msdn.microsoft.com/.../dn672271(v=vs.85).aspx, a HID touch device should create a report (descriptor) as below,

0x05, 0x0d,                         // USAGE_PAGE (Digitizers)          
0x09, 0x04,                         // USAGE (Touch Screen)             
0xa1, 0x01,                         // COLLECTION (Application)         
0x85, 0x01,                        //   REPORT_ID (Touch)              
0x09, 0x22,                         //   USAGE (Finger)                 
0xa1, 0x02,                         //     COLLECTION (Logical)  
0x09, 0x42,                         //       USAGE (Tip Switch)           
0x15, 0x00,                         //       LOGICAL_MINIMUM (0)          
0x25, 0x01,                         //       LOGICAL_MAXIMUM (1)          
0x75, 0x01,                         //       REPORT_SIZE (1)              
0x95, 0x01,                         //       REPORT_COUNT (1)             
0x81, 0x02,                         //       INPUT (Data,Var,Abs) 
0x95, 0x07,                         //       REPORT_COUNT (7)  
0x81, 0x03,                         //       INPUT (Cnst,Ary,Abs)
0x75, 0x08,                         //       REPORT_SIZE (8)
0x09, 0x51,                         //       USAGE (Contact Identifier)
0x95, 0x01,                         //       REPORT_COUNT (1)             
0x81, 0x02,                         //       INPUT (Data,Var,Abs) 
0x05, 0x01,                         //       USAGE_PAGE (Generic Desk..
0x26, 0xff, 0x0f,                   //       LOGICAL_MAXIMUM (4095)         
0x75, 0x10,                         //       REPORT_SIZE (16)             
0x55, 0x0e,                         //       UNIT_EXPONENT (-2)           
0x65, 0x13,                         //       UNIT(Inch,EngLinear)                  
0x09, 0x30,                         //       USAGE (X)                    
0x35, 0x00,                         //       PHYSICAL_MINIMUM (0)         
0x46, 0xb5, 0x04,                   //       PHYSICAL_MAXIMUM (1205)
0x95, 0x02,                         //       REPORT_COUNT (2)         
0x81, 0x02,                         //       INPUT (Data,Var,Abs)         
0x46, 0x8a, 0x03,                   //       PHYSICAL_MAXIMUM (906)
0x09, 0x31,                         //       USAGE (Y)                    
0x81, 0x02,                         //       INPUT (Data,Var,Abs)
0x05, 0x0d,                         //       USAGE_PAGE (Digitizers)
0x09, 0x48,                         //       USAGE (Width)                
0x09, 0x49,                         //       USAGE (Height)               
0x81, 0x02,                         //       INPUT (Data,Var,Abs)
0x95, 0x01,                         //       REPORT_COUNT (1)
0x55, 0x0C,                         //       UNIT_EXPONENT (-4)           
0x65, 0x12,                         //       UNIT (Radians,SIROtation)        
0x35, 0x00,                         //       PHYSICAL_MINIMUM (0)         
0x47, 0x6f, 0xf5, 0x00, 0x00,        //      PHYSICAL_MAXIMUM (62831)      
0x15, 0x00,                         //       LOGICAL_MINIMUM (0)      
0x27, 0x6f, 0xf5, 0x00, 0x00,       //       LOGICAL_MAXIMUM (62831)        
0x09, 0x3f,                         //       USAGE (Azimuth[Orientation]) 
0x81, 0x02,                         //       INPUT (Data,Var,Abs)  
0xc0,                               //    END_COLLECTION
0x09, 0x22,                         //   USAGE (Finger)                 
0xa1, 0x02,                         //     COLLECTION (Logical)  
0x09, 0x42,                         //       USAGE (Tip Switch)           
0x15, 0x00,                         //       LOGICAL_MINIMUM (0)          
0x25, 0x01,                         //       LOGICAL_MAXIMUM (1)          
0x75, 0x01,                         //       REPORT_SIZE (1)              
0x95, 0x01,                         //       REPORT_COUNT (1)             
0x81, 0x02,                         //       INPUT (Data,Var,Abs) 
0x95, 0x07,                         //       REPORT_COUNT (7)  
0x81, 0x03,                         //       INPUT (Cnst,Ary,Abs)
0x75, 0x08,                         //       REPORT_SIZE (8)
0x09, 0x51,                         //       USAGE (Contact Identifier)
0x95, 0x01,                         //       REPORT_COUNT (1)             
0x81, 0x02,                         //       INPUT (Data,Var,Abs) 
0x05, 0x01,                         //       USAGE_PAGE (Generic Desk..
0x26, 0xff, 0x0f,                   //       LOGICAL_MAXIMUM (4095)         
0x75, 0x10,                         //       REPORT_SIZE (16)             
0x55, 0x0e,                         //       UNIT_EXPONENT (-2)           
0x65, 0x13,                         //       UNIT(Inch,EngLinear)                  
0x09, 0x30,                         //       USAGE (X)                    
0x35, 0x00,                         //       PHYSICAL_MINIMUM (0)         
0x46, 0xb5, 0x04,                   //       PHYSICAL_MAXIMUM (1205)
0x95, 0x02,                         //       REPORT_COUNT (2)         
0x81, 0x02,                         //       INPUT (Data,Var,Abs)         
0x46, 0x8a, 0x03,                   //       PHYSICAL_MAXIMUM (906)
0x09, 0x31,                         //       USAGE (Y)                    
0x81, 0x02,                         //       INPUT (Data,Var,Abs)
0x05, 0x0d,                         //       USAGE_PAGE (Digitizers)
0x09, 0x48,                         //       USAGE (Width)                
0x09, 0x49,                         //       USAGE (Height)               
0x81, 0x02,                         //       INPUT (Data,Var,Abs)
0x95, 0x01,                         //       REPORT_COUNT (1)
0x55, 0x0C,                         //       UNIT_EXPONENT (-4)           
0x65, 0x12,                         //       UNIT (Radians,SIROtation)        
0x35, 0x00,                         //       PHYSICAL_MINIMUM (0)         
0x47, 0x6f, 0xf5, 0x00, 0x00,        //      PHYSICAL_MAXIMUM (62831)      
0x15, 0x00,                         //       LOGICAL_MINIMUM (0)      
0x27, 0x6f, 0xf5, 0x00, 0x00,       //       LOGICAL_MAXIMUM (62831)        
0x09, 0x3f,                         //       USAGE (Azimuth[Orientation]) 
0x81, 0x02,                         //       INPUT (Data,Var,Abs)  
0xc0,                               //    END_COLLECTION
0x05, 0x0d,                         //    USAGE_PAGE (Digitizers)
0x55, 0x0C,                         //     UNIT_EXPONENT (-4)           
0x66, 0x01, 0x10,                   //     UNIT (Seconds)        
0x47, 0xff, 0xff, 0x00, 0x00,      //       PHYSICAL_MAXIMUM (65535)
0x27, 0xff, 0xff, 0x00, 0x00,         //   LOGICAL_MAXIMUM (65535) 
0x75, 0x10,                           //   REPORT_SIZE (16)             
0x95, 0x01,                           //   REPORT_COUNT (1) 
0x09, 0x56,                         //   USAGE (Scan Time)    
0x81, 0x02,                           //   INPUT (Data,Var,Abs)         
0x09, 0x54,                         //   USAGE (Contact count)
0x25, 0x7f,                           //   LOGICAL_MAXIMUM (127) 
0x95, 0x01,                         //   REPORT_COUNT (1)
0x75, 0x08,                         //   REPORT_SIZE (8)    
0x81, 0x02,                         //   INPUT (Data,Var,Abs)
0x85, REPORTID_MAX_COUNT,            //   REPORT_ID (Feature)              
0x09, 0x55,                         //   USAGE(Contact Count Maximum)
0x95, 0x01,                         //   REPORT_COUNT (1)
0x25, 0x02,                         //   LOGICAL_MAXIMUM (2)
0xb1, 0x02,                         //   FEATURE (Data,Var,Abs)
0x85, 0x44,                      //   REPORT_ID (Feature)
0x06, 0x00, 0xff,                   //   USAGE_PAGE (Vendor Defined)  
0x09, 0xC5,                         //   USAGE (Vendor Usage 0xC5)    
0x15, 0x00,                         //   LOGICAL_MINIMUM (0)          
0x26, 0xff, 0x00,                   //   LOGICAL_MAXIMUM (0xff) 
0x75, 0x08,                         //   REPORT_SIZE (8)             
0x96, 0x00,  0x01,                  //   REPORT_COUNT (0x100 (256))             
0xb1, 0x02,                         //   FEATURE (Data,Var,Abs) 
0xc0,                               // END_COLLECTIONÂ  Â Â 

How can I create a nRF8001 configuration with nRFgo which meets the above requirements? I tried days but still could not get it right. Please help! Thanks!

Parents Reply Children
  • Hi, Hung,

    I have read nRF8001 SDK for Arduino and read all the documents, but it did not tell enough information of how to create a different configuration other than the examples. For example, I have no idea how the initial Value, 05010906A101050719e029e715002501750195088102950175088101950575010508190129059102950175039101950675081500256505071900296581000905150026FF0075089502B102C0, in Report Descriptor of HID_Keyboard_template comes from? Or in another word, how to create configuration according to the descriptor? I guess the Initial value in the Report Descriptor is the same stuff as I listed in the question which is required by Windows Digitizer, so should this value be created manually and added into the Report Map? If so, how do I create a HID service matching the descriptor? There are a lot of Usage Pages/Usages, and Report Values. I think a guide of Usage Pages/Usages/Report Value to configuration mapping table would be helpful. Thank you!

  • Have you watched the .mp4 video ? It shows you how to create that configuration code from the descriptor. Simply remove the 0x hex prefix and put them together.

  • Hi, Hung, thank you for following up. Yes, I did and I did create the descriptor by removing 0x and kept only the hex, but I do not know how to create corresponding characteristics in nRFgo to match the report descriptor and I cannot tell the relationship between nRFgo Report and Descrptor hex.

    For example, in hid_keyboard_template, there is a generated file, USB HID Report Descriptor - Keyboard.txt, which interpret the hex code to the Usage Pages/Usage/Report - just like the above descriptor. I can see there are many report in this example, but why and how should the HID_Report field (ACI: PIPE_HID_SERVICE_HID_REPORT_TX) corresponded to them?

  • Hi, Hung, after read again HID over GATT maps USB HID to the Bluetooth Generic Attribute Profile.doc, I kind of get the idea. The Initial Value in Report Reference is the reference ID to Report ID. In hid_keyboard_template, there is no Report ID field in descriptor, so I kind of confused. But then I learned the Input Report reference ID is 0001 which refers to the only one report in the descriptor. I hope I am understanding this correctly.

  • Further to this question, in hid_keyboard_template, the HID_Report data size is set to 8 bytes, however, if I count the total bytes in the descriptor it should be 11 bytes, so it means the last 3 bytes is not used? And please kindly help me to understand how to interpret the data format in the report (as in below example). Is the data segmented by Usage Page? (Please see my notes in the example) If my understanding was wrong, please kindly correct me. Thank you very much!

    0xA1, 0x01,                         // Collection (Application)
    0x05, 0x07,                         //     Usage Page (Key Codes)  <== first data starts here?
    0x19, 0xe0,                         //     Usage Minimum (224)
    0x29, 0xe7,                         //     Usage Maximum (231)
    0x15, 0x00,                         //     Logical Minimum (0)
    0x25, 0x01,                         //     Logical Maximum (1)
    0x75, 0x01,                         //     Report Size (1)
    0x95, 0x08,                         //     Report Count (8)
    0x81, 0x02,                         //     Input (Data, Variable, Absolute)
    
    0x95, 0x01,                         //     Report Count (1)
    0x75, 0x08,                         //     Report Size (8)
    0x81, 0x01,                         //     Input (Constant) reserved byte(1)
    
    0x95, 0x05,                         //     Report Count (5)
    0x75, 0x01,                         //     Report Size (1)    <== first data ends here? what are the 5 bits means?
    0x05, 0x08,                         //     Usage Page (Page# for LEDs) <== second data starts here?
    0x19, 0x01,                         //     Usage Minimum (1)
    0x29, 0x05,                         //     Usage Maximum (5)
    0x91, 0x02,                         //     Output (Data, Variable, Absolute), Led report
    0x95, 0x01,                         //     Report Count (1)
    0x75, 0x03,                         //     Report Size (3)
    0x91, 0x01,                         //     Output (Data, Variable, Absolute), Led report padding
    
Related