AMS, Franklin Lightning Sensor "AS3935" Library

Franklin Lightning Sensor

雷(落雷)センサー AS3935 用のライブラリです。

Sample

I2C接続

for LPC1114

main.cpp

#include "mbed.h"
#include "AS3935.h"

Serial pc(USBTX, USBRX);
DigitalOut led1(LED1);

AS3935 as(dp5, dp27, dp26); // sda, scl, irq
//I2C i2c(dp5, dp27);
//AS3935 as(i2c, dp26); // i2c, irq

void lightning () {
    int energy, distance;
    as.read(energy, distance);
    pc.printf("Lightning energy=%d distance=%d\r\n", energy, distance);
}

int main() {
    pc.baud(115200);
    pc.printf("*** AS3935\r\n");
    as.init();
    as.attach(&lightning);
    for (;;) {
        led1 = ! led1;
        wait(0.2);
    }
}
Revision:
0:5a6d7a605d26
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/AS3935.cpp	Mon Apr 13 00:52:04 2015 +0000
@@ -0,0 +1,119 @@
+/*
+ * AMS, Franklin Lightning Sensor "AS3935" Library
+ * Copyright (c) 2015 Hiroshi Suga
+ * Released under the MIT License: http://mbed.org/license/mit
+ */
+// http://ams.com/eng/Products/Lightning-Sensor/Franklin-Lightning-Sensor/AS3935
+
+#include "AS3935.h"
+
+//#define DBG(...) printf("" __VA_ARGS__) 
+#define DBG(...)
+
+#define AS3935_ADDR 0x00
+
+AS3935::AS3935 (I2C &i2c, PinName irq) : _i2c(i2c), _irq(irq) {
+    _irq.mode(PullUp);
+    _mode = 0;
+    _type = 0;
+}
+
+AS3935::AS3935 (PinName sda, PinName scl, PinName irq) : _i2c(sda, scl), _irq(irq) {
+    _irq.mode(PullUp);
+    _mode = 0;
+    _type = 0;
+}
+
+void AS3935::init () {
+    char cmd[2];
+
+    cmd[0] = 0x3c;
+    cmd[1] = 0x96; // PRESET_DEFAULT
+    _i2c.write(AS3935_ADDR, cmd, 2);
+    cmd[0] = 0x3d;
+    cmd[1] = 0x96; // CALIB_RCO
+    _i2c.write(AS3935_ADDR, cmd, 2);
+    cmd[0] = 0x00;
+    cmd[1] = (0x12<<1); // AFE_GB=12(Indoor)
+    _i2c.write(AS3935_ADDR, cmd, 2);
+    cmd[0] = 0x01;
+    cmd[1] = (0x02<<4)|(0x02<<0); // NF_LEV, WDTH
+    _i2c.write(AS3935_ADDR, cmd, 2);
+    cmd[0] = 0x03;
+    cmd[1] = 0x00; // LCO_FDIV = 1/16
+    _i2c.write(AS3935_ADDR, cmd, 2);
+
+    calib_lco();
+
+    _irq.fall(this, &AS3935::isr_lightning);
+}
+
+// Antenna Tuning (500kHz)
+void AS3935::calib_lco () {
+    int i, n, m = 10000, r = 0;
+    char cmd[2];
+    Timer t;
+
+    _mode = 0;
+    _irq.fall(this, &AS3935::isr_freq);
+    for (i = 0; i < 0x10; i ++) {
+        cmd[0] = 0x08;
+        cmd[1] = 0x80 | i;
+        _i2c.write(AS3935_ADDR, cmd, 2);
+        wait_ms(10);
+        t.reset();
+        t.start();
+        _freq = 0;
+        _mode = 1;
+        while (t.read_ms() < 100);
+        _mode = 0;
+        n = abs(_freq - 3125);
+        if (m > n) {
+            r = i;
+        } else {
+            break;
+        }
+        m = n;
+    }
+    _irq.fall(NULL);
+    t.stop();
+    cmd[0] = 0x08;
+    cmd[1] = r;
+    _i2c.write(AS3935_ADDR, cmd, 2);
+    DBG("- init %d %d\r\n", r, _freq * 16 * 10);
+}
+
+void AS3935::read (int &energy, int &distance) {
+    char cmd[4];
+
+    cmd[0] = 0x04;
+    _i2c.write(AS3935_ADDR, cmd, 1, true);
+    _i2c.read(AS3935_ADDR, cmd, 4);
+    energy = ((cmd[2] & 0x1f) << 16) | (cmd[1] << 8) | cmd[0];
+    distance = cmd[3] & 0x3f;
+}
+
+void AS3935::isr_freq () {
+    if (_mode == 1) {
+        _freq ++;
+    }
+}
+
+void AS3935::isr_lightning () {
+    char cmd[2];
+
+    cmd[0] = 0x03;
+    _i2c.write(AS3935_ADDR, cmd, 1, true);
+    _i2c.read(AS3935_ADDR, cmd, 1);
+    DBG("- irq %02x\r\n", cmd[0]);
+    _type = cmd[0] & 0x0f;
+    switch (_type) {
+    case 0x01: // Noise level too high
+        break;
+    case 0x04: // Disturber detected
+        break;
+    case 0x08: // Lightning interrupt
+        _func.call();
+        break;
+    }
+}