changeset 927:7d4dec166822

garage arduino sends brite/* color changes out on virtualwire to a digispark now Ignore-this: c14e3bd188cb97b2a7e596bb494b1e7b darcs-hash:20130929060114-312f9-f91eb21e4db5e619f165e3d1bf06c74390d7b671
author drewp <drewp@bigasterisk.com>
date Sat, 28 Sep 2013 23:01:14 -0700
parents 22af7ea8c401
children 9d96882a742c
files service/garageArduino/bathroom_recv/bathroom_recv.ino service/garageArduino/garage/garage.ino service/garageArduino/garageArduino.py
diffstat 3 files changed, 136 insertions(+), 5 deletions(-) [+]
line wrap: on
line diff
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/service/garageArduino/bathroom_recv/bathroom_recv.ino	Sat Sep 28 23:01:14 2013 -0700
@@ -0,0 +1,89 @@
+/*
+  board: 'Digispark (Tiny Core)'
+  programmer: 'Digispark'
+  
+  pin 0 is the output to the LEDs
+  pin 2 is the input from garage arduino
+*/
+#include <VirtualWire.h>
+
+#include <Adafruit_NeoPixel.h>
+
+// Parameter 1 = number of pixels in strip
+// Parameter 2 = pin number (most are valid)
+// Parameter 3 = pixel type flags, add together as needed:
+//   NEO_RGB     Pixels are wired for RGB bitstream
+//   NEO_GRB     Pixels are wired for GRB bitstream
+//   NEO_KHZ400  400 KHz bitstream (e.g. FLORA pixels)
+//   NEO_KHZ800  800 KHz bitstream (e.g. High Density LED strip)
+Adafruit_NeoPixel strip = Adafruit_NeoPixel(4, 0, NEO_GRB + NEO_KHZ800);
+
+#define SET(i, r, g, b) strip.setPixelColor(i, strip.Color(r, g, b)); strip.show();
+
+int numLeds = 4;
+
+void wakeUpPattern() { 
+  for (int t = 0; t < 255; t += 2) {
+    for (int i = 0; i < numLeds; i++) {
+      //SET(i, 255 - t, max(0, 255 - t * 2), max(0, 255 - t * 3)); 
+      SET(i, 
+        (i % 2) ? (255 - t) : 0,
+        (i % 2) ? 0 : (255 - t),
+        (i % 2) ? (255 - t) : 0);
+    }
+    delay(10);
+  }
+  SET(0, 0, 0, 0);
+  SET(1, 0, 0, 0);
+  SET(2, 0, 0, 0);
+  SET(3, 0, 0, 0);
+}
+
+void blinkFailedMessageError() {
+  SET(0,0,0,255);
+  delay(100);
+  SET(0,0,0,0);
+}
+
+void blinkShortBufferError() {
+  SET(0,0,255,0);
+  delay(100);
+  SET(0,0,0,0);
+}
+
+void setup() {
+  vw_set_rx_pin(2);
+  vw_setup(2000);	 // Bits per sec
+
+  vw_rx_start();       // Start the receiver PLL running
+
+  strip.begin();
+  strip.show();
+
+  wakeUpPattern();
+}
+
+void loop() {
+  uint8_t buf[VW_MAX_MESSAGE_LEN];
+  uint8_t buflen = VW_MAX_MESSAGE_LEN;
+
+  vw_wait_rx();
+  int success = vw_get_message(buf, &buflen);
+  if (!success) {
+    blinkFailedMessageError();
+    return;
+  }
+  if (buflen < numLeds * 3) { 
+    blinkShortBufferError();
+    return;
+  }
+
+  for (int i=0; i < numLeds; i++) {
+    strip.setPixelColor(i, strip.Color(
+    buf[i * 3 + 0], 
+    buf[i * 3 + 1], 
+    buf[i * 3 + 2]));
+  }
+  strip.show();
+}
+
--- a/service/garageArduino/garage/garage.ino	Sun Sep 22 00:34:07 2013 -0700
+++ b/service/garageArduino/garage/garage.ino	Sat Sep 28 23:01:14 2013 -0700
@@ -1,3 +1,5 @@
+#include <VirtualWire.h>
+
 /*
 board is Arduino UNO with '328
  */
@@ -73,7 +75,18 @@
   pinMode(7, OUTPUT); // bathroom shiftbrite data
   pinMode(8, OUTPUT); // bathroom shiftbrite clk
   pinMode(9, OUTPUT); // bathroom shiftbrite latch
-
+  
+  vw_set_ptt_pin(11); // waste, but VW will be writing to this
+  vw_set_tx_pin(10); // bathroom new virtualwire out
+  
+  // Bits per sec. Match this in bathroom_recv. 
+  // The reason to have this anywhere high is to 
+  // make a color change block the sending arduino 
+  // for less time. 
+  // 2000bps -> 120ms PUT requests
+  // 8000bps -> 30ms PUT requests, but lots of message errors
+  vw_setup(2000); 
+  
   for (int i=0; i < 1; i++) {
     setCurrent(127, 127, 127);
   }
@@ -153,8 +166,22 @@
       }
       latch();
       Serial.print("{\"ok\":1}\n");
-
-    }   
+    } else if (cmd == 0x07) { // send virtualwire
+       // arg is the number of bytes in the message to send
+      uint8_t msg[99];
+      for (int i=0; i<arg; i++) {
+        while (Serial.available() == 0) NULL;
+        msg[i] = Serial.read();
+      }
+      if (!vw_send(msg, arg)) {
+        Serial.print("{\"err\":\"message too long for virtualwire\"}");
+        return;
+      }
+      vw_wait_tx();
+      Serial.print("{\"sent\":");
+      Serial.print(arg);
+      Serial.print("}\n");
+    } 
   }
 }
 
--- a/service/garageArduino/garageArduino.py	Sun Sep 22 00:34:07 2013 -0700
+++ b/service/garageArduino/garageArduino.py	Sat Sep 28 23:01:14 2013 -0700
@@ -66,6 +66,7 @@
     def setVideoSelect(self, chan):
         """set video select bits from 0..3"""
         self.ser.write("\x60\x05"+chr(chan))
+
         return self.ser.readJson()['videoSelect']
 
     def shiftbrite(self, colors):
@@ -83,6 +84,19 @@
         msg = self.ser.readJson()
         assert msg == {"ok":1}, msg
 
+    def virtualwire(self, colors):
+        """
+        send this sequence of (r,g,b) 8-bit triples
+        """
+        numLeds = 4
+        # vw receiver wants data for all leds every time
+        colors = (list(colors) + [(0,0,0)] * numLeds)[:numLeds]
+        msg = "".join("%s%s%s" % (chr(r), chr(g), chr(b)) for r,g,b in colors)
+        self.ser.write("\x60\x07" + chr(len(msg)) + msg)
+        msg = self.ser.readJson()
+        assert msg == {"sent": 12}, msg
+        
+
 class Index(PrettyErrorHandler, cyclone.web.RequestHandler):
     def get(self):
         """
@@ -176,7 +190,8 @@
     def put(self, chan):
         s = self.settings
         s.colors[int(chan)] = rgbFromHex(self.request.body)
-        s.arduino.shiftbrite(s.colors)
+        #s.arduino.shiftbrite(s.colors)
+        s.arduino.virtualwire([(r//4, g//4, b//4) for r,g,b in s.colors])
     post = put
 
 class Application(cyclone.web.Application):
@@ -192,7 +207,7 @@
             (r'/videoSelect', VideoSelect), 
             (r"/brite/(\d+)", Brite),
         ]
-        colors = [(0,0,0)] * 1 # stored 10-bit
+        colors = [(0,0,0)] * 4 # stored 10-bit for legacy (or future!) reasons
         settings = {"arduino" : ard, "poller" : poller, "colors" : colors}
         cyclone.web.Application.__init__(self, handlers, **settings)