dino 0.10.0 → 0.11.2
Sign up to get free protection for your applications and to get access to all the features.
- data/CHANGELOG.md +67 -0
- data/README.md +24 -8
- data/bin/dino +108 -0
- data/dino.gemspec +2 -1
- data/examples/button/button.rb +3 -2
- data/examples/ethernet.rb +15 -0
- data/examples/{ir_receiver.rb → ir_receiver/ir_receiver.rb} +3 -2
- data/examples/led/led.rb +3 -3
- data/examples/{potentiometer.rb → potentiometer/potentiometer.rb} +4 -6
- data/examples/{rgb_led.rb → rgb_led/rgb_led.rb} +4 -6
- data/examples/{sensor.rb → sensor/sensor.rb} +5 -6
- data/examples/ser2net.rb +31 -0
- data/examples/servo/servo.rb +16 -0
- data/examples/stepper/stepper.rb +3 -3
- data/lib/dino/board.rb +69 -59
- data/lib/dino/components/base_component.rb +8 -7
- data/lib/dino/components/rgb_led.rb +19 -17
- data/lib/dino/components/sensor.rb +2 -2
- data/lib/dino/components/servo.rb +8 -5
- data/lib/dino/components/stepper.rb +9 -9
- data/lib/dino/tx_rx.rb +5 -4
- data/lib/dino/tx_rx/base.rb +64 -0
- data/lib/dino/tx_rx/serial.rb +44 -0
- data/lib/dino/tx_rx/tcp.rb +23 -0
- data/lib/dino/version.rb +1 -1
- data/spec/lib/board_spec.rb +53 -39
- data/spec/lib/components/led_spec.rb +1 -1
- data/spec/lib/components/rgb_led_spec.rb +49 -4
- data/spec/lib/components/sensor_spec.rb +14 -10
- data/spec/lib/components/servo_spec.rb +9 -4
- data/spec/lib/components/stepper_spec.rb +2 -2
- data/spec/lib/tx_rx/serial_spec.rb +111 -0
- data/spec/lib/tx_rx/tcp_spec.rb +37 -0
- data/spec/spec_helper.rb +10 -1
- data/src/du/du.ino +19 -0
- data/src/du_ethernet/du_ethernet.ino +71 -0
- data/src/lib/Dino.cpp +257 -0
- data/src/lib/Dino.h +85 -0
- metadata +25 -17
- data/examples/servo.rb +0 -13
- data/examples/telnet.rb +0 -28
- data/lib/dino/tx_rx/telnet.rb +0 -53
- data/lib/dino/tx_rx/usb_serial.rb +0 -69
- data/spec/lib/tx_rx/telnet_spec.rb +0 -66
- data/spec/lib/tx_rx/usb_serial_spec.rb +0 -101
- data/src/du.ino +0 -251
data/CHANGELOG.md
ADDED
@@ -0,0 +1,67 @@
|
|
1
|
+
# Changelog
|
2
|
+
|
3
|
+
## 0.11.2
|
4
|
+
|
5
|
+
* Make servos work better by using the existing Arduino Servo library.
|
6
|
+
* Up to 12 servos can be controlled.
|
7
|
+
* On MEGA boards, servos may be used on pins 22-33 ONLY.
|
8
|
+
* On other boards, servos may be used on pins 2-13 ONLY.
|
9
|
+
* Flashing the updated sketch to the board is required.
|
10
|
+
|
11
|
+
## 0.11.1
|
12
|
+
|
13
|
+
### New Features
|
14
|
+
|
15
|
+
* Support for the Arduino Ethernet shield and compatibles (Wiznet W5100 chipset).
|
16
|
+
|
17
|
+
* Added a `dino` command-line tool for generating and customizing the different Arduino sketches.
|
18
|
+
|
19
|
+
* Instead of reading the value of a pin by repeatedly sending messages to ask for its value, we can now set up "listeners". We tell the board which pin we'd like to listen to, and it will periodically send us the pin's value.
|
20
|
+
* By default, digital listeners are polled every ~4ms (~250Hz).
|
21
|
+
* Analog listeners are on a 4x divider, so they update every ~16ms (~63Hz).
|
22
|
+
* These can be changed with the `Board#heart_rate=` and `Board#analog_divider=` methods respectively.
|
23
|
+
* Digital listeners only send a message if the value has changed since the last check.
|
24
|
+
* Analog listeners always send a message.
|
25
|
+
* Digital listeners can be set up on any pin, including analog pins. Analog listeners should only be set up on analog pins.
|
26
|
+
|
27
|
+
* Registering a listener is now the default for read components such as `Sensor` and `Button`. No changes need to be made for existing or future components. Anything using `Board#add_analog_hardware` or `Board#add_digital_hardware` will set up a listener.
|
28
|
+
|
29
|
+
__NOTE__: Because of these changes, you'll need to upload the newest version of the sketch to your board for this version of the gem to work properly.
|
30
|
+
|
31
|
+
* Support for all 70 pins on the Arduino Mega boards.
|
32
|
+
|
33
|
+
* Built-in pullup resistors on the Arduino are now configurable in Ruby. Disabled by default.
|
34
|
+
|
35
|
+
* Support up to COM9 on Windows.
|
36
|
+
|
37
|
+
* Connect to a specific serial device by setting `device:` in the options hash when calling `Dino::TxRx::Serial.new`.
|
38
|
+
|
39
|
+
* Baud rate for serial connections is now configurable. Use the `--baud XXXXXX` option for `dino` to set the rate before uploading the sketch. Set `baud: XXXXXX` in the options hash for Dino::TxRx::Serial.new` to set the rate when connecting. Both values need to match.
|
40
|
+
|
41
|
+
* Added color methods to `RgbLed` for cyan, yellow, magenta, white and off.
|
42
|
+
|
43
|
+
### Major Changes
|
44
|
+
|
45
|
+
* All Arduino code that interacts with components has been extracted into an Arduino library. The sketches now only handle communication between a `Dino::TxRx::` class in Ruby and this library. Writing new sketches for arbitray protocols should be simpler.
|
46
|
+
|
47
|
+
* Arduino-level debug messages now use preprocessor directives instead of `if(debug)` statements. The performance and memory usage of sketches with debugging disabled is improved.
|
48
|
+
|
49
|
+
* As a result, enabling and disabling Arduino-level debug messages can no longer be done in Ruby. You'll need to enable debug messages before uploading a sketch by using the `--debug` option when generating the sketch with `dino`.
|
50
|
+
|
51
|
+
* Removed `TxRx::Telnet`. `TxRx::TCP`, written for the Ethernet shield, works even better for ser2net.
|
52
|
+
|
53
|
+
### Minor Changes
|
54
|
+
|
55
|
+
* Handshake protocol: The first command sent to the Arduino resets the board to defaults. It acknowledges and responds with the raw pin number of its first analog pin, 'A0' (pin 14 on an UNO).
|
56
|
+
|
57
|
+
* When sending messages between Ruby and the Arduino, all pins are now referenced by this numerical syntax. The value received in the handshake is used by `Dino::Board` to calculate values on the fly, so the more friendly 'A0' syntax may be used everywhere else in Ruby. This was done mostly to replace some complicated Arduino code and support > 10 analog pins.
|
58
|
+
|
59
|
+
* The Arduino's read and write operations no longer implicitly set the mode of a pin. Calling `board#set_pin_mode` when initializing a component is now required. `board#add_analog_hardware` or `board#add_digital_hardware` for read components will take care of this as well.
|
60
|
+
|
61
|
+
* The syntax of the messages sent from the Arduino to Ruby has changed slightly from "PP::VVVV\r\n" to "PP:VVVV\n" where PP and VVVV represent the pin and value respectively. The increase in (serial) throughput is usable when many analog listeners are set or polling at high rates.
|
62
|
+
|
63
|
+
* Sensors accept blocks instead of procs now.
|
64
|
+
|
65
|
+
### Fixes
|
66
|
+
|
67
|
+
* `Board#set_pin_mode` works correctly now. Input and output were swapped previously and this error was being hidden by the implicit operations mentioned above.
|
data/README.md
CHANGED
@@ -1,23 +1,39 @@
|
|
1
|
-
#
|
1
|
+
# Dino 0.11.2
|
2
2
|
[![Build Status](https://secure.travis-ci.org/austinbv/dino.png)](http://travis-ci.org/austinbv/dino)
|
3
3
|
|
4
4
|
## Get Started In No Time
|
5
5
|
|
6
|
-
Dino
|
6
|
+
Dino lets you start programming your Arduino with Ruby in minutes.
|
7
7
|
|
8
8
|
#### Install the Gem
|
9
9
|
|
10
|
-
```
|
10
|
+
```shell
|
11
11
|
gem install dino
|
12
12
|
```
|
13
13
|
|
14
|
-
####
|
14
|
+
#### Prepare the Bootstrapper
|
15
|
+
|
16
|
+
Use the included command line tool to create a folder with the Arduino sketch you want to use and optionally configure it.
|
17
|
+
|
18
|
+
```shell
|
19
|
+
# If connecting via serial, USB or ser2net, this is all you should need:
|
20
|
+
dino generate-sketch serial
|
21
|
+
|
22
|
+
# If usng the ethernet shield, you'll want to specify unique MAC and IP addresses:
|
23
|
+
dino generate-sketch ethernet --mac XX:XX:XX:XX:XX:XX --ip XXX.XXX.XXX.XXX
|
24
|
+
|
25
|
+
# For more options:
|
26
|
+
dino help
|
27
|
+
```
|
28
|
+
|
29
|
+
__Note:__ Current Ethernet shields come with a sticker indicating the MAC address you should use with them. For older shields without a dedicated MAC address, inventing a random one should work, but don't use the same one for multiple boards. Valid IP addresses depend on the configuration of your network.
|
30
|
+
|
31
|
+
#### Upload The Bootstrapper
|
15
32
|
|
33
|
+
* Connect the Arduino to a USB port on your machine, regardless of which sketch you're using.
|
16
34
|
* Open [the normal Arduino IDE](http://arduino.cc/en/Main/Software)
|
17
|
-
*
|
18
|
-
*
|
19
|
-
* Plug in your Arduino via USB
|
20
|
-
* Click the upload button (an arrow)
|
35
|
+
* Open the `.ino` file in the sketch folder you just generated.
|
36
|
+
* Click the upload button (an arrow).
|
21
37
|
|
22
38
|
#### Verify Install
|
23
39
|
|
data/bin/dino
ADDED
@@ -0,0 +1,108 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
require "pathname"
|
3
|
+
require "fileutils"
|
4
|
+
|
5
|
+
$options = {}
|
6
|
+
$options[:sketch_names] = []
|
7
|
+
|
8
|
+
def error(message)
|
9
|
+
$stderr.puts "Error: " + message
|
10
|
+
usage
|
11
|
+
end
|
12
|
+
|
13
|
+
def usage
|
14
|
+
$stderr.puts "Usage: #{File.basename($0)} COMMAND [command-specific-options]"
|
15
|
+
$stderr.puts
|
16
|
+
$stderr.puts "Commands:"
|
17
|
+
$stderr.puts " generate-sketch SKETCH [options]"
|
18
|
+
$stderr.puts
|
19
|
+
$stderr.puts " Sketches:"
|
20
|
+
$stderr.puts " serial"
|
21
|
+
$stderr.puts " ethernet"
|
22
|
+
$stderr.puts
|
23
|
+
$stderr.puts " Options:"
|
24
|
+
$stderr.puts " --baud BAUD"
|
25
|
+
$stderr.puts " --mac XX:XX:XX:XX:XX:XX"
|
26
|
+
$stderr.puts " --ip XXX.XXX.XXX.XXX"
|
27
|
+
$stderr.puts " --port PORT"
|
28
|
+
$stderr.puts " --debug"
|
29
|
+
$stderr.puts
|
30
|
+
exit(2)
|
31
|
+
end
|
32
|
+
|
33
|
+
# Command must be the first argument.
|
34
|
+
$options[:command] = ARGV.shift
|
35
|
+
usage if $options[:command].match /help/
|
36
|
+
|
37
|
+
# Parse the rest loosely.
|
38
|
+
loop do
|
39
|
+
case ARGV[0]
|
40
|
+
when 'serial'
|
41
|
+
ARGV.shift; $options[:sketch_names] << "du" unless $options[:sketch_names].include? "du"
|
42
|
+
when 'ethernet'
|
43
|
+
ARGV.shift; $options[:sketch_names] << "du_ethernet" unless $options[:sketch_names].include? "du_ethernet"
|
44
|
+
when '--baud'
|
45
|
+
ARGV.shift; $options[:baud] = ARGV.shift
|
46
|
+
when '--mac'
|
47
|
+
ARGV.shift; $options[:mac] = ARGV.shift
|
48
|
+
when '--ip'
|
49
|
+
ARGV.shift; $options[:ip] = ARGV.shift
|
50
|
+
when '--port'
|
51
|
+
ARGV.shift; $options[:port] = ARGV.shift
|
52
|
+
when '--debug'
|
53
|
+
ARGV.shift; $options[:debug] = true
|
54
|
+
when /^-/
|
55
|
+
error "Invalid argument '#{ARGV[0]}'"
|
56
|
+
else break
|
57
|
+
end
|
58
|
+
end
|
59
|
+
|
60
|
+
error "Invalid command '#{$options[:command]}'" unless $options[:command] == "generate-sketch"
|
61
|
+
error "No sketches or invalid sketches specified" if $options[:sketch_names].empty?
|
62
|
+
|
63
|
+
$options[:sketch_names].each do |sketch_name|
|
64
|
+
# Define the sources.
|
65
|
+
sketch_dir = sketch_name
|
66
|
+
sketch_file = sketch_name + ".ino"
|
67
|
+
src_dir = Pathname.new(__FILE__).realpath.to_s.chomp("/bin/dino") + "/src"
|
68
|
+
src_header = File.join src_dir, "lib", "Dino.h"
|
69
|
+
src_implementation = File.join src_dir, "lib", "Dino.cpp"
|
70
|
+
src_sketch = File.join src_dir, sketch_dir, sketch_file
|
71
|
+
|
72
|
+
# Read the files.
|
73
|
+
header = File.read(src_header)
|
74
|
+
implementation = File.read(src_implementation)
|
75
|
+
sketch = File.read(src_sketch)
|
76
|
+
|
77
|
+
# Modify them based on the arguments.
|
78
|
+
if $options[:baud]
|
79
|
+
sketch.gsub! "115200", $options[:baud]
|
80
|
+
end
|
81
|
+
if $options[:mac]
|
82
|
+
octets = $options[:mac].split(':')
|
83
|
+
bytes = octets.map { |o| "0x#{o.upcase}" }
|
84
|
+
sketch.gsub! "{ 0xDE, 0xAD, 0xBE, 0x30, 0x31, 0x32 }", bytes.inspect.gsub("[", "{").gsub("]", "}").gsub("\"", "")
|
85
|
+
end
|
86
|
+
if $options[:ip]
|
87
|
+
sketch.gsub! "192,168,0,77", $options[:ip].gsub(".", ",")
|
88
|
+
end
|
89
|
+
if $options[:port]
|
90
|
+
sketch.gsub! "int port = 3466", "int port = #{$options[:port]}"
|
91
|
+
end
|
92
|
+
if $options[:debug]
|
93
|
+
header.gsub! "// #define debug true", "#define debug true"
|
94
|
+
end
|
95
|
+
|
96
|
+
# Define the destinations.
|
97
|
+
working_dir = Dir.pwd
|
98
|
+
dest_dir = File.join working_dir, sketch_dir
|
99
|
+
Dir::mkdir dest_dir
|
100
|
+
dest_header = File.join dest_dir, "Dino.h"
|
101
|
+
dest_implementation = File.join dest_dir, "Dino.cpp"
|
102
|
+
dest_sketch = File.join dest_dir, sketch_file
|
103
|
+
|
104
|
+
# Write the files.
|
105
|
+
File.open(dest_header, 'w') { |f| f.write header }
|
106
|
+
File.open(dest_implementation, 'w') { |f| f.write implementation }
|
107
|
+
File.open(dest_sketch, 'w') { |f| f.write sketch }
|
108
|
+
end
|
data/dino.gemspec
CHANGED
@@ -6,7 +6,7 @@ Gem::Specification.new do |gem|
|
|
6
6
|
gem.email = ["austinbv@gmail.com"]
|
7
7
|
gem.description = %q{A utility library for interfacting with an Arduino.
|
8
8
|
Designed for control, expansion, and with love.}
|
9
|
-
gem.summary = %q{Control your
|
9
|
+
gem.summary = %q{Control your Arduino with Ruby.}
|
10
10
|
gem.homepage = 'https://github.com/austinbv/dino'
|
11
11
|
|
12
12
|
gem.files = `git ls-files`.split($\)
|
@@ -14,6 +14,7 @@ Gem::Specification.new do |gem|
|
|
14
14
|
gem.name = "dino"
|
15
15
|
gem.require_paths = ["lib"]
|
16
16
|
gem.version = Dino::VERSION
|
17
|
+
gem.executables = ["dino"]
|
17
18
|
|
18
19
|
gem.add_dependency 'serialport'
|
19
20
|
end
|
data/examples/button/button.rb
CHANGED
@@ -4,9 +4,10 @@
|
|
4
4
|
# sleep or in someway keep running or your program
|
5
5
|
# will exit before any callbacks can be called
|
6
6
|
#
|
7
|
-
require
|
7
|
+
require 'bundler/setup'
|
8
|
+
require 'dino'
|
8
9
|
|
9
|
-
board = Dino::Board.new(Dino::TxRx.new)
|
10
|
+
board = Dino::Board.new(Dino::TxRx::Serial.new)
|
10
11
|
button = Dino::Components::Button.new(pin: 13, board: board)
|
11
12
|
|
12
13
|
button.down do
|
@@ -0,0 +1,15 @@
|
|
1
|
+
#
|
2
|
+
# This example shows how to use an Arduino with an Ethernet shield and the du_ethernet.ino sketch loaded.
|
3
|
+
# Replace the IP address in this example with the IP you used when uploading the sketch.
|
4
|
+
# The Ethernet shield uses up pin 13, so you'll need an LED on pin 5 to make sure it's working.
|
5
|
+
#
|
6
|
+
require File.expand_path('../../lib/dino', __FILE__)
|
7
|
+
|
8
|
+
connection = Dino::TxRx::TCP.new("192.168.0.77")
|
9
|
+
board = Dino::Board.new(connection)
|
10
|
+
led = Dino::Components::Led.new(pin: 5, board: board)
|
11
|
+
|
12
|
+
[:on, :off].cycle do |switch|
|
13
|
+
led.send(switch)
|
14
|
+
sleep 0.5
|
15
|
+
end
|
@@ -4,9 +4,10 @@
|
|
4
4
|
# sleep or in someway keep running or your program
|
5
5
|
# will exit before any callbacks can be called
|
6
6
|
#
|
7
|
-
require
|
7
|
+
require 'bundler/setup'
|
8
|
+
require 'dino'
|
8
9
|
|
9
|
-
board = Dino::Board.new(Dino::TxRx.new)
|
10
|
+
board = Dino::Board.new(Dino::TxRx::Serial.new)
|
10
11
|
ir = Dino::Components::IrReceiver.new(pin: 2, board: board)
|
11
12
|
led = Dino::Components::Led.new(pin: 13, board: board)
|
12
13
|
|
data/examples/led/led.rb
CHANGED
@@ -2,10 +2,10 @@
|
|
2
2
|
# This is a simple example to blink an led
|
3
3
|
# every half a second
|
4
4
|
#
|
5
|
+
require 'bundler/setup'
|
6
|
+
require 'dino'
|
5
7
|
|
6
|
-
|
7
|
-
|
8
|
-
board = Dino::Board.new(Dino::TxRx.new)
|
8
|
+
board = Dino::Board.new(Dino::TxRx::Serial.new)
|
9
9
|
led = Dino::Components::Led.new(pin: 13, board: board)
|
10
10
|
|
11
11
|
[:on, :off].cycle do |switch|
|
@@ -4,21 +4,19 @@
|
|
4
4
|
# LED. The set_delay callback reads from the potentiometer
|
5
5
|
# and changes the sleep delay for the LED on/off cycle.
|
6
6
|
#
|
7
|
+
require 'bundler/setup'
|
8
|
+
require 'dino'
|
7
9
|
|
8
|
-
|
9
|
-
|
10
|
-
board = Dino::Board.new(Dino::TxRx.new)
|
10
|
+
board = Dino::Board.new(Dino::TxRx::Serial.new)
|
11
11
|
led = Dino::Components::Led.new(pin: 13, board: board)
|
12
12
|
potentiometer = Dino::Components::Sensor.new(pin: 'A0', board: board)
|
13
13
|
|
14
14
|
delay = 500.0
|
15
15
|
|
16
|
-
|
16
|
+
potentiometer.when_data_received do |data|
|
17
17
|
puts "DATA: #{delay = data.to_i}"
|
18
18
|
end
|
19
19
|
|
20
|
-
potentiometer.when_data_received(set_delay)
|
21
|
-
|
22
20
|
[:on, :off].cycle do |switch|
|
23
21
|
puts "DELAY: #{seconds = (delay / 1000.0)}"
|
24
22
|
led.send(switch)
|
@@ -2,23 +2,21 @@
|
|
2
2
|
# This is a simple example to blink an led
|
3
3
|
# every half a second
|
4
4
|
#
|
5
|
+
require 'bundler/setup'
|
6
|
+
require 'dino'
|
5
7
|
|
6
|
-
|
7
|
-
|
8
|
-
board = Dino::Board.new(Dino::TxRx.new)
|
8
|
+
board = Dino::Board.new(Dino::TxRx::Serial.new)
|
9
9
|
led = Dino::Components::RgbLed.new(pins: {red: 11, green: 10, blue: 9}, board: board)
|
10
10
|
potentiometer = Dino::Components::Sensor.new(pin: 'A0', board: board)
|
11
11
|
|
12
12
|
|
13
13
|
delay = 500.0
|
14
14
|
|
15
|
-
|
15
|
+
potentiometer.when_data_received do |data|
|
16
16
|
sleep 0.5
|
17
17
|
puts "DATA: #{delay = data.to_i}"
|
18
18
|
end
|
19
19
|
|
20
|
-
potentiometer.when_data_received(set_delay)
|
21
|
-
|
22
20
|
sleep(2)
|
23
21
|
loop do
|
24
22
|
puts "DELAY: #{seconds = (delay / 1000.0)}"
|
@@ -4,15 +4,14 @@
|
|
4
4
|
# sleep or in someway keep running or your program
|
5
5
|
# will exit before any callbacks can be called
|
6
6
|
#
|
7
|
-
require
|
7
|
+
require 'bundler/setup'
|
8
|
+
require 'dino'
|
8
9
|
|
9
|
-
board = Dino::Board.new(Dino::TxRx.new)
|
10
|
+
board = Dino::Board.new(Dino::TxRx::Serial.new)
|
10
11
|
sensor = Dino::Components::Sensor.new(pin: 'A0', board: board)
|
11
12
|
|
12
|
-
|
13
|
-
|
13
|
+
sensor.when_data_received do |data|
|
14
|
+
puts data
|
14
15
|
end
|
15
16
|
|
16
|
-
sensor.when_data_received(on_data)
|
17
|
-
|
18
17
|
sleep
|
data/examples/ser2net.rb
ADDED
@@ -0,0 +1,31 @@
|
|
1
|
+
#
|
2
|
+
# This example shows how to use an Arduino on a remote machine via ser2net.
|
3
|
+
# Running ser2net serves up the serial connection over the network interface,
|
4
|
+
# so you can communicate with the Arduino over your local network or the Internet.
|
5
|
+
#
|
6
|
+
# Example ser2net command for an Arduino UNO on Mac:
|
7
|
+
# ser2net -u -C "3466:raw:0:/dev/cu.usbmodem621:115200"
|
8
|
+
#
|
9
|
+
# Note that we're using ser2net in raw TCP mode and not telnet mode which is more common.
|
10
|
+
#
|
11
|
+
# Replace /dev/cu.usbmodem621 with your Arduino device.
|
12
|
+
# Arduino UNOs are usually /dev/ttyACM0 under Linux.
|
13
|
+
#
|
14
|
+
# ser2net is preinstalled on many Linuxes. Install ser2net at the Mac Terminal with:
|
15
|
+
# brew install ser2net
|
16
|
+
#
|
17
|
+
# http://sourceforge.net/projects/ser2net/ for more info on installing and configuring ser2net.
|
18
|
+
#
|
19
|
+
|
20
|
+
require File.expand_path('../../lib/dino', __FILE__)
|
21
|
+
|
22
|
+
# The remote ser2net host is the first argument for a new TxRx::TCP.
|
23
|
+
# The second argument, port number, is optional. 3466 is default. This must match the port ser2net uses on the remote machine.
|
24
|
+
connection = Dino::TxRx::TCP.new("127.0.0.1", 3466)
|
25
|
+
board = Dino::Board.new(connection)
|
26
|
+
led = Dino::Components::Led.new(pin: 13, board: board)
|
27
|
+
|
28
|
+
[:on, :off].cycle do |switch|
|
29
|
+
led.send(switch)
|
30
|
+
sleep 0.5
|
31
|
+
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
#
|
2
|
+
# This is an example of how to use the servo class
|
3
|
+
#
|
4
|
+
require 'bundler/setup'
|
5
|
+
require 'dino'
|
6
|
+
|
7
|
+
board = Dino::Board.new(Dino::TxRx::Serial.new)
|
8
|
+
servo = Dino::Components::Servo.new(pin: 9, board: board)
|
9
|
+
|
10
|
+
# Add different angles (in degrees) to the array below to try out your servo.
|
11
|
+
# Note: Some servos may not have a full 180 degree sweep.
|
12
|
+
|
13
|
+
[0, 90].cycle do |angle|
|
14
|
+
servo.position = angle
|
15
|
+
sleep 0.5
|
16
|
+
end
|
data/examples/stepper/stepper.rb
CHANGED
@@ -1,10 +1,10 @@
|
|
1
1
|
#
|
2
2
|
# This is a simple example to move a stepper motor using the sparkfun easydriver shield: https://www.sparkfun.com/products/10267?
|
3
3
|
#
|
4
|
+
require 'bundler/setup'
|
5
|
+
require 'dino'
|
4
6
|
|
5
|
-
|
6
|
-
|
7
|
-
board = Dino::Board.new(Dino::TxRx.new)
|
7
|
+
board = Dino::Board.new(Dino::TxRx::Serial.new)
|
8
8
|
stepper = Dino::Components::Stepper.new(board: board, pins: { step: 10, direction: 8 })
|
9
9
|
|
10
10
|
1600.times do
|
data/lib/dino/board.rb
CHANGED
@@ -1,37 +1,28 @@
|
|
1
1
|
module Dino
|
2
2
|
class Board
|
3
|
-
attr_reader :digital_hardware, :analog_hardware
|
3
|
+
attr_reader :digital_hardware, :analog_hardware, :analog_zero
|
4
4
|
LOW, HIGH = 000, 255
|
5
5
|
|
6
6
|
def initialize(io)
|
7
7
|
@io, @digital_hardware, @analog_hardware = io, [], []
|
8
8
|
io.add_observer(self)
|
9
|
-
|
10
|
-
start_heart_beat
|
9
|
+
handshake
|
11
10
|
end
|
12
11
|
|
13
|
-
def
|
14
|
-
|
15
|
-
part.update(msg) if normalize_pin(pin) == normalize_pin(part.pin)
|
16
|
-
end
|
17
|
-
end
|
18
|
-
|
19
|
-
def add_digital_hardware(part)
|
20
|
-
set_pin_mode(part.pin, :in)
|
21
|
-
@digital_hardware << part
|
22
|
-
end
|
23
|
-
|
24
|
-
def remove_digital_hardware(part)
|
25
|
-
@digital_hardware.delete(part)
|
12
|
+
def handshake
|
13
|
+
@analog_zero = @io.handshake
|
26
14
|
end
|
27
15
|
|
28
|
-
def
|
29
|
-
|
30
|
-
|
16
|
+
def analog_divider=(value)
|
17
|
+
unless [1, 2, 4, 8, 16, 32, 64, 128].include? value
|
18
|
+
puts "Analog divider must be in 1, 2, 4, 8, 16, 32, 64, 128"
|
19
|
+
else
|
20
|
+
write "9700#{normalize_value(value)}"
|
21
|
+
end
|
31
22
|
end
|
32
23
|
|
33
|
-
def
|
34
|
-
|
24
|
+
def heart_rate=(value)
|
25
|
+
write "9800#{normalize_value(value)}"
|
35
26
|
end
|
36
27
|
|
37
28
|
def start_read
|
@@ -47,39 +38,76 @@ module Dino
|
|
47
38
|
@io.write(formatted_msg)
|
48
39
|
end
|
49
40
|
|
50
|
-
def
|
51
|
-
|
52
|
-
|
41
|
+
def update(pin, msg)
|
42
|
+
(@digital_hardware + @analog_hardware).each do |part|
|
43
|
+
part.update(msg) if normalize_pin(pin) == normalize_pin(part.pin)
|
44
|
+
end
|
53
45
|
end
|
54
46
|
|
55
|
-
def
|
56
|
-
pin,
|
57
|
-
|
47
|
+
def add_digital_hardware(part)
|
48
|
+
set_pin_mode(part.pin, :in, part.pullup)
|
49
|
+
digital_listen(part.pin)
|
50
|
+
@digital_hardware << part
|
58
51
|
end
|
59
52
|
|
60
|
-
def
|
61
|
-
|
62
|
-
|
53
|
+
def remove_digital_hardware(part)
|
54
|
+
stop_listener(part.pin)
|
55
|
+
@digital_hardware.delete(part)
|
63
56
|
end
|
64
57
|
|
65
|
-
def
|
66
|
-
|
67
|
-
|
58
|
+
def add_analog_hardware(part)
|
59
|
+
set_pin_mode(part.pin, :in)
|
60
|
+
analog_listen(part.pin)
|
61
|
+
@analog_hardware << part
|
68
62
|
end
|
69
63
|
|
70
|
-
def
|
71
|
-
|
72
|
-
|
64
|
+
def remove_analog_hardware(part)
|
65
|
+
stop_listener(part.pin)
|
66
|
+
@analog_hardware.delete(part)
|
73
67
|
end
|
74
68
|
|
75
|
-
def
|
76
|
-
pin, value = normalize_pin(
|
77
|
-
write("
|
69
|
+
def set_pin_mode(pin, mode, pullup=nil)
|
70
|
+
pin, value = normalize_pin(pin), normalize_value(mode == :out ? 0 : 1)
|
71
|
+
write("00#{pin}#{value}")
|
72
|
+
set_pullup(pin, pullup) if mode == :in
|
73
|
+
end
|
74
|
+
|
75
|
+
def set_pullup(pin, pullup)
|
76
|
+
pullup ? digital_write(pin, HIGH) : digital_write(pin, LOW)
|
77
|
+
end
|
78
|
+
|
79
|
+
PIN_COMMANDS = {
|
80
|
+
digital_write: '01',
|
81
|
+
digital_read: '02',
|
82
|
+
analog_write: '03',
|
83
|
+
analog_read: '04',
|
84
|
+
digital_listen: '05',
|
85
|
+
analog_listen: '06',
|
86
|
+
stop_listener: '07',
|
87
|
+
servo_toggle: '08',
|
88
|
+
servo_write: '09'
|
89
|
+
}
|
90
|
+
|
91
|
+
PIN_COMMANDS.each_key do |command|
|
92
|
+
define_method(command) do |pin, value=nil|
|
93
|
+
cmd = normalize_cmd(PIN_COMMANDS[command])
|
94
|
+
write "#{cmd}#{normalize_pin(pin)}#{normalize_value(value)}"
|
95
|
+
end
|
78
96
|
end
|
79
97
|
|
80
98
|
def normalize_pin(pin)
|
81
|
-
|
82
|
-
|
99
|
+
if pin.to_s.match /\Aa/i
|
100
|
+
int_pin = @analog_zero + pin.to_s.gsub(/\Aa/i, '').to_i
|
101
|
+
else
|
102
|
+
int_pin = pin
|
103
|
+
end
|
104
|
+
raise Exception.new('pin number must be in 0-99') if int_pin.to_i > 99
|
105
|
+
return normalize(int_pin, 2)
|
106
|
+
end
|
107
|
+
|
108
|
+
def normalize_cmd(cmd)
|
109
|
+
raise Exception.new('commands can only be two digits') if cmd.to_s.length > 2
|
110
|
+
normalize(cmd, 2)
|
83
111
|
end
|
84
112
|
|
85
113
|
def normalize_value(value)
|
@@ -89,26 +117,8 @@ module Dino
|
|
89
117
|
|
90
118
|
private
|
91
119
|
|
92
|
-
def start_heart_beat
|
93
|
-
@heart_beat ||= Thread.new do
|
94
|
-
loop do
|
95
|
-
sleep 0.005
|
96
|
-
@digital_hardware.each do |part|
|
97
|
-
digital_read(part.pin)
|
98
|
-
end
|
99
|
-
@analog_hardware.each do |part|
|
100
|
-
analog_read(part.pin)
|
101
|
-
end
|
102
|
-
end
|
103
|
-
end
|
104
|
-
end
|
105
|
-
|
106
120
|
def normalize(pin, spaces)
|
107
121
|
pin.to_s.rjust(spaces, '0')
|
108
122
|
end
|
109
|
-
|
110
|
-
def send_clearing_bytes
|
111
|
-
write('00000000', no_wrap: true)
|
112
|
-
end
|
113
123
|
end
|
114
124
|
end
|