sc7a20.lua 7.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189
  1. --[[
  2. @module sc7a20
  3. @summary sc7a20
  4. @version 1.0
  5. @date 2022.04.11
  6. @author Dozingfiretruck
  7. @usage
  8. --注意:因使用了sys.wait()所有api需要在协程中使用
  9. -- 用法实例
  10. local sc7a20 = require "sc7a20"
  11. i2cid = 0
  12. i2c_speed = i2c.FAST
  13. sys.taskInit(function()
  14. i2c.setup(i2cid,i2c_speed)
  15. sc7a20.init(i2cid)--初始化,传入i2c_id
  16. while 1 do
  17. local sc7a20_data = sc7a20.get_data()
  18. log.info("sc7a20_data", "sc7a20_data.x"..(sc7a20_data.x),"sc7a20_data.y"..(sc7a20_data.y),"sc7a20_data.z"..(sc7a20_data.z))
  19. sys.wait(1000)
  20. end
  21. end)
  22. ]]
  23. local sc7a20 = {}
  24. local sys = require "sys"
  25. local i2cid
  26. local SC7A20_ADDRESS_ADR -- sc7a20设备地址
  27. local SC7A20_ADDRESS_ADR_LOW = 0x18
  28. local SC7A20_ADDRESS_ADR_HIGH = 0x19
  29. local SC7A20_CHIP_ID_CHECK = 0x0f -- 器件ID检测
  30. local SC7A20_CHIP_ID = 0x11 -- 器件ID
  31. local SC7A20_REG_CTRL_REG1 = 0x20 -- 控制寄存器1
  32. local SC7A20_REG_CTRL_REG2 = 0x21 -- 控制寄存器2
  33. local SC7A20_REG_CTRL_REG3 = 0x22 -- 控制寄存器3
  34. local SC7A20_REG_CTRL_REG4 = 0x23 -- 控制寄存器4
  35. local SC7A20_REG_CTRL_REG5 = 0x24 -- 控制寄存器5
  36. local SC7A20_REG_CTRL_REG6 = 0x25 -- 控制寄存器6
  37. local SC7A20_REG_REFERENCE = 0x26 -- 参考寄存器
  38. local SC7A20_REG_STATUS_REG = 0x27 -- 状态寄存器
  39. local SC7A20_REG_OUT_X_L = 0x28 -- X轴数据低字节
  40. local SC7A20_REG_OUT_X_H = 0x29 -- X轴数据高字节
  41. local SC7A20_REG_OUT_Y_L = 0x2A -- Y轴数据低字节
  42. local SC7A20_REG_OUT_Y_H = 0x2B -- Y轴数据高字节
  43. local SC7A20_REG_OUT_Z_L = 0x2C -- Z轴数据低字节
  44. local SC7A20_REG_OUT_Z_H = 0x2D -- Z轴数据高字节
  45. local SC7A20_REG_FIFO_CTRL_REG = 0x2E -- FIFO控制寄存器
  46. local SC7A20_REG_FIFO_SRC_REG = 0x2F -- FIFO源寄存器
  47. local SC7A20_REG_INT1_CFG = 0x30 -- 中断1配置寄存器
  48. local SC7A20_REG_INT1_SRC = 0x31 -- 中断1源寄存器
  49. local SC7A20_REG_INT1_THS = 0x32 -- 中断1阈值寄存器
  50. local SC7A20_REG_INT1_DURATION = 0x33 -- 中断1持续时间寄存器
  51. local SC7A20_REG_INT2_CFG = 0x34 -- 中断2配置寄存器
  52. local SC7A20_REG_INT2_SRC = 0x35 -- 中断2源寄存器
  53. local SC7A20_REG_INT2_THS = 0x36 -- 中断2阈值寄存器
  54. local SC7A20_REG_INT2_DURATION = 0x37 -- 中断2持续时间寄存器
  55. local SC7A20_REG_CLICK_CFG = 0x38 -- 单击配置寄存器
  56. local SC7A20_REG_CLICK_SRC = 0x39 -- 单击源寄存器
  57. local SC7A20_REG_CLICK_THS = 0x3A -- 单击阈值寄存器
  58. local SC7A20_REG_TIME_LIMIT = 0x3B -- 单击时间限制寄存器
  59. local SC7A20_REG_TIME_LATENCY = 0x3C -- 单击时间延迟寄存器
  60. local SC7A20_REG_TIME_WINDOW = 0x3D -- 单击时间窗口寄存器
  61. local SC7A20_REG_ACT_THS = 0x3E -- 活动阈值寄存器
  62. local SC7A20_REG_ACT_DUR = 0x3F -- 活动持续时间寄存器
  63. --器件ID检测
  64. local function chip_check()
  65. i2c.send(i2cid, SC7A20_ADDRESS_ADR_LOW, SC7A20_CHIP_ID_CHECK)--读器件地址
  66. local revData = i2c.recv(i2cid, SC7A20_ADDRESS_ADR_LOW, 1)
  67. if revData:byte() ~= nil then
  68. SC7A20_ADDRESS_ADR = SC7A20_ADDRESS_ADR_LOW
  69. else
  70. i2c.send(i2cid, SC7A20_ADDRESS_ADR_HIGH, SC7A20_CHIP_ID_CHECK)--读器件地址
  71. sys.wait(50)
  72. local revData = i2c.recv(i2cid, SC7A20_ADDRESS_ADR_HIGH, 1)
  73. if revData:byte() ~= nil then
  74. SC7A20_ADDRESS_ADR = SC7A20_ADDRESS_ADR_HIGH
  75. else
  76. log.info("i2c", "Can't find sc7a20 device")
  77. return false
  78. end
  79. end
  80. i2c.send(i2cid, SC7A20_ADDRESS_ADR, SC7A20_CHIP_ID_CHECK)--读器件地址
  81. sys.wait(50)
  82. local revData = i2c.recv(i2cid, SC7A20_ADDRESS_ADR, 1)
  83. if revData:byte() == SC7A20_CHIP_ID then
  84. log.info("Device i2c id is: SC7A20")
  85. else
  86. log.info("i2c", "Can't find sc7a20 device")
  87. return false
  88. end
  89. return true
  90. end
  91. --[[
  92. sc7a20 初始化
  93. @api sc7a20.init(i2c_id)
  94. @number i2c id
  95. @return bool 成功返回true
  96. @usage
  97. sc7a20.init(0)
  98. ]]
  99. function sc7a20.init(i2c_id)
  100. i2cid = i2c_id
  101. sys.wait(20)--20 毫秒等待设备稳定
  102. if chip_check() then
  103. i2c.send(i2cid, SC7A20_ADDRESS_ADR, {SC7A20_REG_CTRL_REG1,0X47})
  104. i2c.send(i2cid, SC7A20_ADDRESS_ADR, {SC7A20_REG_CTRL_REG2,0X00})
  105. i2c.send(i2cid, SC7A20_ADDRESS_ADR, {SC7A20_REG_CTRL_REG3,0X00})
  106. i2c.send(i2cid, SC7A20_ADDRESS_ADR, {SC7A20_REG_CTRL_REG4,0X88})
  107. i2c.send(i2cid, SC7A20_ADDRESS_ADR, {SC7A20_REG_CTRL_REG6,0X00})
  108. log.info("sc7a20 init_ok")
  109. sys.wait(20)
  110. return true
  111. end
  112. return false
  113. end
  114. --[[
  115. 获取 sc7a20 数据
  116. @api sc7a20.get_data()
  117. @return table sc7a20 数据
  118. @usage
  119. local sc7a20_data = sc7a20.get_data()
  120. log.info("sc7a20_data", "sc7a20_data.x"..(sc7a20_data.x),"sc7a20_data.y"..(sc7a20_data.y),"sc7a20_data.z"..(sc7a20_data.z))
  121. ]]
  122. function sc7a20.get_data()
  123. local accel={x=nil,y=nil,z=nil}
  124. i2c.send(i2cid, SC7A20_ADDRESS_ADR,SC7A20_REG_OUT_X_L)
  125. _,accel.x = pack.unpack(i2c.recv(i2cid, SC7A20_ADDRESS_ADR, 2),">h")
  126. i2c.send(i2cid, SC7A20_ADDRESS_ADR,SC7A20_REG_OUT_Y_L)
  127. _,accel.y = pack.unpack(i2c.recv(i2cid, SC7A20_ADDRESS_ADR, 2),">h")
  128. i2c.send(i2cid, SC7A20_ADDRESS_ADR,SC7A20_REG_OUT_Z_L)
  129. _,accel.z = pack.unpack(i2c.recv(i2cid, SC7A20_ADDRESS_ADR, 2),">h")
  130. return accel
  131. end
  132. --[[
  133. 设置 sc7a20 活动阀值
  134. @api sc7a20.set_thresh (i2cid, activity, time_inactivity)
  135. @number i2c id
  136. @number 活动阀值
  137. @number 活动持续时间
  138. @usage
  139. sc7a20.set_thresh(0, string.char(0x05), string.char(0x05))
  140. ]]
  141. function sc7a20.set_thresh(i2cid, activity, time_inactivity)
  142. i2c.writeReg(i2cid, SC7A20_ADDRESS_ADR, SC7A20_REG_ACT_THS, activity)
  143. i2c.writeReg(i2cid, SC7A20_ADDRESS_ADR, SC7A20_REG_ACT_DUR, time_inactivity)
  144. end
  145. --[[
  146. 设置 sc7a20 中断设置
  147. @api sc7a20.set_irqf(i2cid, int, irqf_ths, irqf_duration, irqf_cfg)
  148. @number i2c id
  149. @number 中断脚 传入1及配置INT1脚,传入2及配置INT2脚
  150. @number 中断阀值
  151. @number 中断持续时间
  152. @number 中断配置
  153. @usage
  154. sc7a20.set_irqf(0, 1, string.char(0x05), string.char(0x05), string.char(0x00))
  155. ]]
  156. function sc7a20.set_irqf(i2cid, int, irqf_ths, irqf_duration, irqf_cfg)
  157. if int == 1 then
  158. i2c.send(i2cid, SC7A20_ADDRESS_ADR, {SC7A20_REG_CTRL_REG3,0X40}) -- AOI1中断映射到INT1上
  159. i2c.writeReg(i2cid, SC7A20_ADDRESS_ADR, SC7A20_REG_INT1_THS, irqf_ths)
  160. i2c.writeReg(i2cid, SC7A20_ADDRESS_ADR, SC7A20_REG_INT1_DURATION, irqf_duration)
  161. i2c.writeReg(i2cid, SC7A20_ADDRESS_ADR, SC7A20_REG_INT1_CFG, irqf_cfg)
  162. elseif int == 2 then
  163. i2c.send(i2cid, SC7A20_ADDRESS_ADR, {SC7A20_REG_CTRL_REG6,0X42}) -- AOI2中断映射到INT2上 并且配置低电平触发中断
  164. i2c.writeReg(i2cid, SC7A20_ADDRESS_ADR, SC7A20_REG_INT2_THS, irqf_ths)
  165. i2c.writeReg(i2cid, SC7A20_ADDRESS_ADR, SC7A20_REG_INT2_DURATION, irqf_duration)
  166. i2c.writeReg(i2cid, SC7A20_ADDRESS_ADR, SC7A20_REG_INT2_CFG, irqf_cfg)
  167. else
  168. log.info("sc7a20", "int Parameter error")
  169. end
  170. end
  171. return sc7a20