dino 0.10.0 → 0.11.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (46) hide show
  1. data/CHANGELOG.md +67 -0
  2. data/README.md +24 -8
  3. data/bin/dino +108 -0
  4. data/dino.gemspec +2 -1
  5. data/examples/button/button.rb +3 -2
  6. data/examples/ethernet.rb +15 -0
  7. data/examples/{ir_receiver.rb → ir_receiver/ir_receiver.rb} +3 -2
  8. data/examples/led/led.rb +3 -3
  9. data/examples/{potentiometer.rb → potentiometer/potentiometer.rb} +4 -6
  10. data/examples/{rgb_led.rb → rgb_led/rgb_led.rb} +4 -6
  11. data/examples/{sensor.rb → sensor/sensor.rb} +5 -6
  12. data/examples/ser2net.rb +31 -0
  13. data/examples/servo/servo.rb +16 -0
  14. data/examples/stepper/stepper.rb +3 -3
  15. data/lib/dino/board.rb +69 -59
  16. data/lib/dino/components/base_component.rb +8 -7
  17. data/lib/dino/components/rgb_led.rb +19 -17
  18. data/lib/dino/components/sensor.rb +2 -2
  19. data/lib/dino/components/servo.rb +8 -5
  20. data/lib/dino/components/stepper.rb +9 -9
  21. data/lib/dino/tx_rx.rb +5 -4
  22. data/lib/dino/tx_rx/base.rb +64 -0
  23. data/lib/dino/tx_rx/serial.rb +44 -0
  24. data/lib/dino/tx_rx/tcp.rb +23 -0
  25. data/lib/dino/version.rb +1 -1
  26. data/spec/lib/board_spec.rb +53 -39
  27. data/spec/lib/components/led_spec.rb +1 -1
  28. data/spec/lib/components/rgb_led_spec.rb +49 -4
  29. data/spec/lib/components/sensor_spec.rb +14 -10
  30. data/spec/lib/components/servo_spec.rb +9 -4
  31. data/spec/lib/components/stepper_spec.rb +2 -2
  32. data/spec/lib/tx_rx/serial_spec.rb +111 -0
  33. data/spec/lib/tx_rx/tcp_spec.rb +37 -0
  34. data/spec/spec_helper.rb +10 -1
  35. data/src/du/du.ino +19 -0
  36. data/src/du_ethernet/du_ethernet.ino +71 -0
  37. data/src/lib/Dino.cpp +257 -0
  38. data/src/lib/Dino.h +85 -0
  39. metadata +25 -17
  40. data/examples/servo.rb +0 -13
  41. data/examples/telnet.rb +0 -28
  42. data/lib/dino/tx_rx/telnet.rb +0 -53
  43. data/lib/dino/tx_rx/usb_serial.rb +0 -69
  44. data/spec/lib/tx_rx/telnet_spec.rb +0 -66
  45. data/spec/lib/tx_rx/usb_serial_spec.rb +0 -101
  46. data/src/du.ino +0 -251
@@ -19,7 +19,7 @@ module Dino
19
19
  end
20
20
 
21
21
  it 'should set the pin to out' do
22
- board.should_receive(:set_pin_mode).with(13, :out)
22
+ board.should_receive(:set_pin_mode).with(13, :out, nil)
23
23
  Led.new(pin: 13, board: board)
24
24
  end
25
25
 
@@ -5,7 +5,7 @@ module Dino
5
5
  describe RgbLed do
6
6
  let(:board) { mock(:board, analog_write: true, set_pin_mode: true) }
7
7
  let(:pins) { {red: 1, green: 2, blue: 3} }
8
- let!(:rgb) {RgbLed.new(pins: pins, board: board)}
8
+ let(:rgb) { RgbLed.new(pins: pins, board: board)}
9
9
 
10
10
  describe '#initialize' do
11
11
  it 'should raise if it does not receive a pin' do
@@ -21,9 +21,9 @@ module Dino
21
21
  end
22
22
 
23
23
  it 'should set the pin to out' do
24
- board.should_receive(:set_pin_mode).with(1, :out)
25
- board.should_receive(:set_pin_mode).with(2, :out)
26
- board.should_receive(:set_pin_mode).with(3, :out)
24
+ board.should_receive(:set_pin_mode).with(1, :out, nil)
25
+ board.should_receive(:set_pin_mode).with(2, :out, nil)
26
+ board.should_receive(:set_pin_mode).with(3, :out, nil)
27
27
 
28
28
  RgbLed.new(pins: pins, board: board)
29
29
  end
@@ -64,6 +64,51 @@ module Dino
64
64
  end
65
65
  end
66
66
 
67
+ describe '#cyan' do
68
+ it 'should set blue and green to high, red to low' do
69
+ board.should_receive(:analog_write).with(1, Board::LOW)
70
+ board.should_receive(:analog_write).with(2, Board::HIGH)
71
+ board.should_receive(:analog_write).with(3, Board::HIGH)
72
+ rgb.cyan
73
+ end
74
+ end
75
+
76
+ describe '#yellow' do
77
+ it 'should set red and green to high, blue to low' do
78
+ board.should_receive(:analog_write).with(1, Board::HIGH)
79
+ board.should_receive(:analog_write).with(2, Board::HIGH)
80
+ board.should_receive(:analog_write).with(3, Board::LOW)
81
+ rgb.yellow
82
+ end
83
+ end
84
+
85
+ describe '#magenta' do
86
+ it 'should set red and blue to high, green to low' do
87
+ board.should_receive(:analog_write).with(1, Board::HIGH)
88
+ board.should_receive(:analog_write).with(2, Board::LOW)
89
+ board.should_receive(:analog_write).with(3, Board::HIGH)
90
+ rgb.magenta
91
+ end
92
+ end
93
+
94
+ describe '#white' do
95
+ it 'should set all to high' do
96
+ board.should_receive(:analog_write).with(1, Board::HIGH)
97
+ board.should_receive(:analog_write).with(2, Board::HIGH)
98
+ board.should_receive(:analog_write).with(3, Board::HIGH)
99
+ rgb.white
100
+ end
101
+ end
102
+
103
+ describe '#off' do
104
+ it 'should set all to low' do
105
+ board.should_receive(:analog_write).with(1, Board::LOW)
106
+ board.should_receive(:analog_write).with(2, Board::LOW)
107
+ board.should_receive(:analog_write).with(3, Board::LOW)
108
+ rgb.off
109
+ end
110
+ end
111
+
67
112
  describe '#blinky' do
68
113
  it 'should set blue to high, red and green to low' do
69
114
  Array.any_instance.should_receive(:cycle).and_yield(:red).and_yield(:green).and_yield(:blue)
@@ -32,25 +32,29 @@ module Dino
32
32
  end
33
33
 
34
34
  describe '#when_data_received' do
35
- it 'should add a callback back to the list of callbacks' do
35
+
36
+ it "should add a callback to the list of callbacks" do
36
37
  sensor = Sensor.new(board: board, pin: 'a pin')
37
- sensor.when_data_received 'Foo'
38
- sensor.instance_variable_get(:@data_callbacks).should == ['Foo']
38
+ sensor.when_data_received { "this is a block" }
39
+ sensor.instance_variable_get(:@data_callbacks).should_not be_empty
39
40
  end
40
41
  end
41
42
 
42
43
  describe '#update' do
43
44
  it 'should call all callbacks passing in the given data' do
44
- first_callback, second_callback = mock, mock
45
- first_callback.should_receive(:call).with('Some data')
46
- second_callback.should_receive(:call).with('Some data')
47
-
48
45
  sensor = Sensor.new(board: board, pin: 'a pin')
49
-
50
- sensor.when_data_received first_callback
51
- sensor.when_data_received second_callback
46
+
47
+ first_block_data = nil
48
+ second_block_data = nil
49
+ sensor.when_data_received do |data|
50
+ first_block_data = data
51
+ end
52
+ sensor.when_data_received do |data|
53
+ second_block_data = data
54
+ end
52
55
 
53
56
  sensor.update('Some data')
57
+ [first_block_data, second_block_data].each { |block_data| block_data.should == "Some data" }
54
58
  end
55
59
  end
56
60
  end
@@ -3,7 +3,7 @@ require 'spec_helper'
3
3
  module Dino
4
4
  module Components
5
5
  describe Servo do
6
- let(:board) { mock(:board, analog_write: true, set_pin_mode: true) }
6
+ let(:board) { mock(:board, analog_write: true, set_pin_mode: true, servo_toggle: true, servo_write: true) }
7
7
 
8
8
  describe '#initialize' do
9
9
  it 'should raise if it does not receive a pin' do
@@ -19,7 +19,7 @@ module Dino
19
19
  end
20
20
 
21
21
  it 'should set the pins to out' do
22
- board.should_receive(:set_pin_mode).with(13, :out)
22
+ board.should_receive(:set_pin_mode).with(13, :out, nil)
23
23
  Servo.new(pin: 13, board: board)
24
24
  end
25
25
 
@@ -37,13 +37,18 @@ module Dino
37
37
  servo.instance_variable_get(:@position).should == 90
38
38
  end
39
39
 
40
- it 'should modulate the position at 180' do
40
+ it 'should let you write up to 180' do
41
+ servo.position = 180
42
+ servo.instance_variable_get(:@position).should == 180
43
+ end
44
+
45
+ it 'should modulate when position > 180' do
41
46
  servo.position = 190
42
47
  servo.instance_variable_get(:@position).should == 10
43
48
  end
44
49
 
45
50
  it 'should write the new position to the board' do
46
- servo.should_receive(:analog_write).with(10)
51
+ board.should_receive(:servo_write).with(13, 10)
47
52
  servo.position = 190
48
53
  end
49
54
  end
@@ -25,8 +25,8 @@ module Dino
25
25
  end
26
26
 
27
27
  it 'should set the pins to out' do
28
- board.should_receive(:set_pin_mode).with(13, :out)
29
- board.should_receive(:set_pin_mode).with(12, :out)
28
+ board.should_receive(:set_pin_mode).with(13, :out, nil)
29
+ board.should_receive(:set_pin_mode).with(12, :out, nil)
30
30
  Stepper.new(pins: {step: 13, direction: 12}, board: board)
31
31
  end
32
32
 
@@ -0,0 +1,111 @@
1
+ require 'spec_helper'
2
+
3
+ module Dino
4
+ describe TxRx::Serial do
5
+ it { should be }
6
+
7
+ describe '#initialize' do
8
+ it 'should set first_write to true' do
9
+ TxRx::Serial.new.instance_variable_get(:@first_write).should == true
10
+ end
11
+
12
+ it 'should set the device and buad if specified' do
13
+ txrx = TxRx::Serial.new({device: "/dev/ttyACM0", baud: 9600})
14
+ txrx.instance_variable_get(:@baud).should == 9600
15
+ txrx.instance_variable_get(:@device).should == "/dev/ttyACM0"
16
+ end
17
+ end
18
+
19
+ describe '#io' do
20
+ context "on windows" do
21
+ it 'should instantiate a new SerialPort for the first available tty device' do
22
+ original_platform = RUBY_PLATFORM
23
+ Constants.redefine(:RUBY_PLATFORM, "mswin", :on => Object)
24
+ subject.should_receive(:tty_devices).and_return(["COM1", "COM2", "COM3"])
25
+
26
+ # COM2 is chosen as available for this test.
27
+ SerialPort.should_receive(:new).with("COM1", TxRx::Serial::BAUD).and_raise
28
+ SerialPort.should_receive(:new).with("COM2", TxRx::Serial::BAUD).and_return(mock_serial = mock)
29
+ SerialPort.should_not_receive(:new).with("COM3", TxRx::Serial::BAUD)
30
+
31
+ subject.io.should == mock_serial
32
+ Constants.redefine(:RUBY_PLATFORM, original_platform, :on => Object)
33
+ end
34
+ end
35
+
36
+ context "on unix" do
37
+ it 'should instantiate a new SerialPort for the first available tty device' do
38
+ subject.should_receive(:tty_devices).and_return(['/dev/ttyACM0', '/dev/tty.usbmodem1'])
39
+
40
+ # /dev/ttyACM0 is chosen as available for this test.
41
+ SerialPort.should_receive(:new).with('/dev/ttyACM0', TxRx::Serial::BAUD).and_return(mock_serial = mock)
42
+ SerialPort.should_not_receive(:new).with('/dev/tty.usbmodem1', TxRx::Serial::BAUD)
43
+
44
+ subject.io.should == mock_serial
45
+ end
46
+ end
47
+
48
+ it 'should connect to the specified device at the specified baud rate' do
49
+ subject.should_receive(:tty_devices).and_return(["/dev/ttyACM0"])
50
+ SerialPort.should_receive(:new).with('/dev/ttyACM0', 9600).and_return(mock_serial = mock)
51
+
52
+ subject.instance_variable_set(:@device, "/dev/ttyACM0")
53
+ subject.instance_variable_set(:@baud, 9600)
54
+
55
+ subject.io.should == mock_serial
56
+ end
57
+
58
+ it 'should use the existing io instance if set' do
59
+ subject.should_receive(:tty_devices).once.and_return(['/dev/tty.ACM0', '/dev/tty.usbmodem1'])
60
+ SerialPort.stub(:new).and_return(mock_serial = mock)
61
+
62
+ 3.times { subject.io }
63
+ subject.io.should == mock_serial
64
+ end
65
+
66
+ it 'should raise a BoardNotFound exception if there is no board connected' do
67
+ SerialPort.stub(:new).and_raise
68
+ expect { subject.io }.to raise_exception BoardNotFound
69
+ end
70
+ end
71
+
72
+ describe '#read' do
73
+ it 'should create a new thread' do
74
+ Thread.should_receive :new
75
+ subject.read
76
+ end
77
+
78
+ it 'should get messages from the device' do
79
+ subject.stub(:io).and_return(mock_serial = mock)
80
+
81
+ IO.should_receive(:select).and_return(true)
82
+ Thread.should_receive(:new).and_yield
83
+ subject.should_receive(:loop).and_yield
84
+ mock_serial.should_receive(:gets).and_return("02:00\n")
85
+ subject.should_receive(:changed).and_return(true)
86
+ subject.should_receive(:notify_observers).with('02','00')
87
+
88
+ subject.read
89
+ end
90
+ end
91
+
92
+ describe '#close_read' do
93
+ it 'should kill the reading thread' do
94
+ subject.instance_variable_set(:@thread, mock_thread = mock)
95
+ Thread.should_receive(:kill).with(mock_thread)
96
+ subject.read
97
+ subject.close_read
98
+ end
99
+ end
100
+
101
+ describe '#write' do
102
+ it 'should write to the device' do
103
+ IO.should_receive(:select).and_return(true)
104
+
105
+ subject.stub(:io).and_return(mock_serial = mock)
106
+ mock_serial.should_receive(:syswrite).with('a message')
107
+ subject.write('a message')
108
+ end
109
+ end
110
+ end
111
+ end
@@ -0,0 +1,37 @@
1
+ require 'spec_helper'
2
+
3
+ module Dino
4
+ describe TxRx::TCP do
5
+ before :each do
6
+ @host = "127.0.0.1"
7
+ @port = 3466
8
+ @instance = TxRx::TCP.new(@host, @port)
9
+ end
10
+
11
+ describe "#connect" do
12
+ it 'should raise a BoardNotFound exception if it cannot connect to the server' do
13
+ expect { @instance.io }.to raise_exception BoardNotFound
14
+ end
15
+
16
+ it 'should return the TCPSocket if connected' do
17
+ @server = TCPServer.new 3466
18
+ @instance.io.should be_a TCPSocket
19
+ @server.close
20
+ end
21
+ end
22
+
23
+ describe '#io' do
24
+ it 'should set io to a new TCPSocket with the specified host and port' do
25
+ TCPSocket.should_receive(:open).with(@host, @port)
26
+ @instance.io
27
+ end
28
+
29
+ it 'should use the existing io instance if set' do
30
+ @server = TCPServer.new 3466
31
+ socket = @instance.io
32
+ @instance.io.should be socket
33
+ @server.close
34
+ end
35
+ end
36
+ end
37
+ end
@@ -1,3 +1,12 @@
1
1
  require 'rspec'
2
2
 
3
- require File.expand_path(File.join('../..', 'lib/dino'), __FILE__)
3
+ require File.expand_path(File.join('../..', 'lib/dino'), __FILE__)
4
+
5
+ # Nice little helper module to redefine constants quietly.
6
+ module Constants
7
+ def self.redefine(const, value, opts={})
8
+ opts = {:on => self.class}.merge(opts)
9
+ opts[:on].send(:remove_const, const) if self.class.const_defined?(const)
10
+ opts[:on].const_set(const, value)
11
+ end
12
+ end
@@ -0,0 +1,19 @@
1
+ #include "Dino.h"
2
+ #include <Servo.h>
3
+ Dino dino;
4
+
5
+ // Dino.h doesn't handle TXRX. Setup a function to tell it to write to Serial.
6
+ void writeResponse(char *response) { Serial.print(response); Serial.print("\n"); }
7
+ void (*writeCallback)(char *str) = writeResponse;
8
+
9
+ void setup() {
10
+ Serial.begin(115200);
11
+ dino.setupWrite(writeCallback);
12
+ }
13
+
14
+ void loop() {
15
+ while(Serial.available() > 0) dino.parse(Serial.read());
16
+ dino.updateListeners();
17
+ Serial.flush();
18
+ }
19
+
@@ -0,0 +1,71 @@
1
+ #include "Dino.h"
2
+ #include <SPI.h>
3
+ #include <Ethernet.h>
4
+ #include <Servo.h>
5
+
6
+ // Configure your MAC address, IP address, and HTTP port here.
7
+ byte mac[] = { 0xDE, 0xAD, 0xBE, 0x30, 0x31, 0x32 };
8
+ IPAddress ip(192,168,0,77);
9
+ int port = 3466;
10
+
11
+ Dino dino;
12
+ EthernetServer server(port);
13
+ EthernetClient client;
14
+ char responseBuffer[65];
15
+
16
+
17
+ // Dino.h doesn't handle TXRX. Setup a callback to receive the responses and buffer them.
18
+ void bufferResponse(char *response) {
19
+ if (strlen(responseBuffer) > 56 ) {
20
+ writeResponses();
21
+ strcpy(responseBuffer, response);
22
+ } else {
23
+ strcat(responseBuffer, response);
24
+ }
25
+ strcat(responseBuffer, "\n");
26
+ }
27
+ void (*writeCallback)(char *str) = bufferResponse;
28
+
29
+ // Write the buffered responses to the client.
30
+ void writeResponses() {
31
+ if (responseBuffer[0] != '\0')
32
+ client.write(responseBuffer);
33
+ responseBuffer[0] = '\0';
34
+ }
35
+
36
+
37
+ void setup() {
38
+ // Explicitly disable the SD card.
39
+ pinMode(4,OUTPUT);
40
+ digitalWrite(4,HIGH);
41
+
42
+ // Start up the network connection and server.
43
+ Ethernet.begin(mac, ip);
44
+ server.begin();
45
+
46
+ // Start serial for debugging.
47
+ Serial.begin(9600);
48
+ Serial.print("Dino::TCP started at ");
49
+ Serial.print(Ethernet.localIP());
50
+ Serial.print(" on port ");
51
+ Serial.println(port);
52
+
53
+ // Attach the write callback.
54
+ dino.setupWrite(writeCallback);
55
+ }
56
+
57
+ void loop() {
58
+ // Listen for connections.
59
+ client = server.available();
60
+
61
+ // Handle a connection.
62
+ if (client) {
63
+ while (client.connected()) {
64
+ while (client.available()) dino.parse(client.read());
65
+ dino.updateListeners();
66
+ writeResponses();
67
+ }
68
+ }
69
+ client.stop();
70
+ }
71
+
@@ -0,0 +1,257 @@
1
+ /*
2
+ Library for dino ruby gem.
3
+ */
4
+
5
+ #include "Arduino.h"
6
+ #include "Dino.h"
7
+
8
+ Dino::Dino(){
9
+ reset();
10
+ }
11
+
12
+ void Dino::parse(char c) {
13
+ if (c == '!') index = 0; // Reset request
14
+ else if (c == '.') process(); // End request and process
15
+ else request[index++] = c; // Append to request
16
+ }
17
+
18
+ void Dino::process() {
19
+ response[0] = '\0';
20
+
21
+ // Parse the request.
22
+ strncpy(cmdStr, request, 2); cmdStr[2] = '\0';
23
+ strncpy(pinStr, request + 2, 2); pinStr[2] = '\0';
24
+ strncpy(valStr, request + 4, 3); valStr[3] = '\0';
25
+ cmd = atoi(cmdStr);
26
+ pin = atoi(pinStr);
27
+ val = atoi(valStr);
28
+
29
+ #ifdef debug
30
+ Serial.print("Received request - "); Serial.println(request);
31
+ Serial.print("Command - "); Serial.println(cmdStr);
32
+ Serial.print("Pin - "); Serial.println(pinStr);
33
+ Serial.print("Value - "); Serial.println(valStr);
34
+ #endif
35
+
36
+ // Call the command.
37
+ switch(cmd) {
38
+ case 0: setMode (); break;
39
+ case 1: dWrite (); break;
40
+ case 2: dRead (); break;
41
+ case 3: aWrite (); break;
42
+ case 4: aRead (); break;
43
+ case 5: addDigitalListener (); break;
44
+ case 6: addAnalogListener (); break;
45
+ case 7: removeListener (); break;
46
+ case 8: servoToggle (); break;
47
+ case 9: servoWrite (); break;
48
+ case 90: reset (); break;
49
+ case 97: setAnalogDivider (); break;
50
+ case 98: setHeartRate (); break;
51
+ default: break;
52
+ }
53
+
54
+ // Write the response.
55
+ if (response[0] != '\0') writeResponse();
56
+
57
+ #ifdef debug
58
+ Serial.print("Responded with - "); Serial.println(response);
59
+ Serial.println();
60
+ #endif
61
+ }
62
+
63
+
64
+
65
+ // WRITE CALLBACK
66
+ void Dino::setupWrite(void (*writeCallback)(char *str)) {
67
+ _writeCallback = writeCallback;
68
+ }
69
+ void Dino::writeResponse() {
70
+ _writeCallback(response);
71
+ }
72
+
73
+
74
+
75
+ // LISTNENERS
76
+ void Dino::updateListeners() {
77
+ if (timeSince(lastUpdate) > heartRate || timeSince(lastUpdate) < 0) {
78
+ lastUpdate = micros();
79
+ loopCount++;
80
+ updateDigitalListeners();
81
+ if (loopCount % analogDivider == 0) updateAnalogListeners();
82
+ }
83
+ }
84
+ void Dino::updateDigitalListeners() {
85
+ for (int i = 0; i < 22; i++) {
86
+ if (digitalListeners[i]) {
87
+ pin = i;
88
+ dRead();
89
+ if (rval != digitalListenerValues[i]) {
90
+ digitalListenerValues[i] = rval;
91
+ writeResponse();
92
+ }
93
+ }
94
+ }
95
+ }
96
+ void Dino::updateAnalogListeners() {
97
+ for (int i = 0; i < 22; i++) {
98
+ if (analogListeners[i]) {
99
+ pin = i;
100
+ aRead();
101
+ writeResponse();
102
+ }
103
+ }
104
+ }
105
+ long Dino::timeSince(long event) {
106
+ long time = micros() - event;
107
+ return time;
108
+ }
109
+
110
+
111
+
112
+ // API FUNCTIONS
113
+ // CMD = 00 // Pin Mode
114
+ void Dino::setMode() {
115
+ if (val == 0) {
116
+ removeListener();
117
+ pinMode(pin, OUTPUT);
118
+ #ifdef debug
119
+ Serial.print("Set pin "); Serial.print(pin); Serial.print(" to "); Serial.println("OUTPUT mode");
120
+ #endif
121
+ }
122
+ else {
123
+ pinMode(pin, INPUT);
124
+ #ifdef debug
125
+ Serial.print("Set pin "); Serial.print(pin); Serial.print(" to "); Serial.println("INPTUT mode");
126
+ #endif
127
+ }
128
+ }
129
+
130
+ // CMD = 01 // Digital Write
131
+ void Dino::dWrite() {
132
+ if (val == 0) {
133
+ digitalWrite(pin, LOW);
134
+ #ifdef debug
135
+ Serial.print("Digital write "); Serial.print(LOW); Serial.print(" to pin "); Serial.println(pin);
136
+ #endif
137
+ }
138
+ else {
139
+ digitalWrite(pin, HIGH);
140
+ #ifdef debug
141
+ Serial.print("Digital write "); Serial.print(HIGH); Serial.print(" to pin "); Serial.println(pin);
142
+ #endif
143
+ }
144
+ }
145
+
146
+ // CMD = 02 // Digital Read
147
+ void Dino::dRead() {
148
+ rval = digitalRead(pin);
149
+ sprintf(response, "%02d:%02d", pin, rval);
150
+ }
151
+
152
+ // CMD = 03 // Analog (PWM) Write
153
+ void Dino::aWrite() {
154
+ analogWrite(pin,val);
155
+ #ifdef debug
156
+ Serial.print("Analog write "); Serial.print(val); Serial.print(" to pin "); Serial.println(pin);
157
+ #endif
158
+ }
159
+
160
+ // CMD = 04 // Analog Read
161
+ void Dino::aRead() {
162
+ rval = analogRead(pin);
163
+ sprintf(response, "%02d:%02d", pin, rval);
164
+ }
165
+
166
+ // CMD = 05
167
+ // Listen for a digital signal on any pin.
168
+ void Dino::addDigitalListener() {
169
+ removeListener();
170
+ digitalListeners[pin] = true;
171
+ digitalListenerValues[pin] = 2;
172
+ #ifdef debug
173
+ Serial.print("Added digital listener on pin "); Serial.println(pin);
174
+ #endif
175
+ }
176
+
177
+ // CMD = 06
178
+ // Listen for an analog signal on analog pins only.
179
+ void Dino::addAnalogListener() {
180
+ removeListener();
181
+ analogListeners[pin] = true;
182
+ #ifdef debug
183
+ Serial.print("Added analog listener on pin "); Serial.println(pin);
184
+ #endif
185
+ }
186
+
187
+ // CMD = 07
188
+ // Remove analog and digital listeners from any pin.
189
+ void Dino::removeListener() {
190
+ analogListeners[pin] = false;
191
+ digitalListeners[pin] = false;
192
+ #ifdef debug
193
+ Serial.print("Removed listeners on pin "); Serial.println(pin);
194
+ #endif
195
+ }
196
+
197
+ // CMD = 08
198
+ // Attach the servo object to pin or detach it.
199
+ void Dino::servoToggle() {
200
+ if (val == 0) {
201
+ #ifdef debug
202
+ Serial.print("Detaching servo"); Serial.print(" on pin "); Serial.println(pin);
203
+ #endif
204
+ servos[pin - SERVO_OFFSET].detach();
205
+ }
206
+ else {
207
+ #ifdef debug
208
+ Serial.print("Attaching servo"); Serial.print(" on pin "); Serial.println(pin);
209
+ #endif
210
+ servos[pin - SERVO_OFFSET].attach(pin);
211
+ }
212
+ }
213
+
214
+ // CMD = 09
215
+ // Write a value to the servo object.
216
+ void Dino::servoWrite() {
217
+ #ifdef debug
218
+ Serial.print("Servo write "); Serial.print(val); Serial.print(" to pin "); Serial.println(pin);
219
+ #endif
220
+ servos[pin - SERVO_OFFSET].write(val);
221
+ }
222
+
223
+ // CMD = 90
224
+ void Dino::reset() {
225
+ heartRate = 4000; // Default heartRate is ~4ms.
226
+ loopCount = 0;
227
+ analogDivider = 4; // Update analog listeners every ~16ms.
228
+ for (int i = 0; i < 22; i++) digitalListeners[i] = false;
229
+ for (int i = 0; i < 22; i++) digitalListenerValues[i] = 2;
230
+ for (int i = 0; i < 22; i++) analogListeners[i] = false;
231
+ lastUpdate = micros();
232
+ index = 0;
233
+ #ifdef debug
234
+ Serial.println("Reset the board to defaults. pin ");
235
+ #endif
236
+ sprintf(response, "ACK:%02d", A0);
237
+ }
238
+
239
+ // CMD = 97
240
+ // Set the analog divider. Powers of 2 up to 128 are valid.
241
+ void Dino::setAnalogDivider() {
242
+ analogDivider = val;
243
+ #ifdef debug
244
+ Serial.print("Analog divider set to "); Serial.println(analogDivider);
245
+ #endif
246
+ }
247
+
248
+ // CMD = 98
249
+ // Set the heart rate in milliseconds. Store it in microseconds.
250
+ void Dino::setHeartRate() {
251
+ int rate = val;
252
+ heartRate = (rate * 1000);
253
+ #ifdef debug
254
+ Serial.print("Heart rate set to "); Serial.print(heartRate); Serial.println(" microseconds");
255
+ #endif
256
+ }
257
+