Slide 1

Slide 1 text

MAKING ROBOTS

Slide 2

Slide 2 text

GONNA TALK ABOUT ▸ hardware ▸ software ▸ creativity

Slide 3

Slide 3 text

HARDWARE ▸ Arduino ▸ Tessel

Slide 4

Slide 4 text

THEY UNDERSTAND ▸ Javascript ▸ C/C++

Slide 5

Slide 5 text

No content

Slide 6

Slide 6 text

INPUT, OUTPUTS, SERIAL... (OH MY!)

Slide 7

Slide 7 text

MANY WAYS TO PROGRAM ▸ Compiled ▸ Firmata

Slide 8

Slide 8 text

TIME TO MAKE IT WORK!

Slide 9

Slide 9 text

No content

Slide 10

Slide 10 text

SIMPLE AND EFFECTIVE!

Slide 11

Slide 11 text

SOMETIMES CIRCUITS GET COMPLEX

Slide 12

Slide 12 text

LIMITS (LIKE CURRENT)

Slide 13

Slide 13 text

LET'S MAKE A NEW CIRCUIT, AND LEARN SOME NEW COMPONENTS...

Slide 14

Slide 14 text

RESISTOR

Slide 15

Slide 15 text

DIODE

Slide 16

Slide 16 text

TRANSISTOR

Slide 17

Slide 17 text

http://bit.ly/arduino-motors

Slide 18

Slide 18 text

WHAT CAN WE DO WITH THIS?

Slide 19

Slide 19 text

No content

Slide 20

Slide 20 text

USEFUL WITH AERYS

Slide 21

Slide 21 text

WHAT ELSE?

Slide 22

Slide 22 text

No content

Slide 23

Slide 23 text

interface Service { public function name(); public function colors(); public function query(); public function dismiss(); }

Slide 24

Slide 24 text

namespace Notifier\Service; use Notifier\Service; use Endroid\Twitter\Twitter as Client; class Twitter implements Service { private $client; private $new = false; private $since = null; public function __construct($consumerKey, $consumerSecret, $accessToken, $accessTokenSecret) { $this->client = new Client( $consumerKey, $consumerSecret, $accessToken, $accessTokenSecret ); } }

Slide 25

Slide 25 text

public function query() { if ($this->new) return true; $parameters = ["count" => 1]; if ($this->since) { $parameters["since_id"] = $this->since; } $response = $this->client->query( "statuses/mentions_timeline", "GET", "json", $parameters ); $tweets = json_decode($response->getContent()); if (count($tweets) > 0) { $this->new = true; $this->since = (int) $tweets[0]->id; } return $this->new; }

Slide 26

Slide 26 text

public function dismiss() { $this->new = false; } public function name() { return "twitter"; } public function colors() { return [1 - 0.11, 1 - 0.62, 1 - 0.94]; }

Slide 27

Slide 27 text

namespace Notifier\Service; use Notifier\Service; class Gmail implements Service { private $new = false; private $emails = []; private $username; private $password; public function __construct($username, $password) { $this->username = $username; $this->password = $password; } }

Slide 28

Slide 28 text

public function query() { if ($this->new) return true; $inbox = imap_open( "{imap.gmail.com:993/imap/ssl}INBOX", $this->username, $this->password ); if (!inbox) { return false; } // ...

Slide 29

Slide 29 text

$emails = imap_search($inbox, "ALL", SE_UID); if ($emails) { foreach ($emails as $email) { if (!in_array($email, $this->emails)) { $this->new = true; break; } } $this->emails = array_values($emails); } return $this->new; }

Slide 30

Slide 30 text

public function dismiss() { $this->new = false; } public function name() { return "gmail"; } public function colors() { return [1 - 0.89, 1 - 0.15, 1 - 0.15]; }

Slide 31

Slide 31 text

use Carica\Io; use Carica\Firmata; $loop = Io\Event\Loop\Factory::get(); $board = new Firmata\Board( Io\Stream\Serial\Factory::create( "/dev/cu.usbmodem14111", 57600 ) ); $board ->activate() ->done(function () use ($loop, $board) { // ...connect to services }); $loop->run();

Slide 32

Slide 32 text

// diode pins $board->pins[10]->mode = Firmata\Pin::MODE_PWM; $board->pins[10]->analog = 1; $board->pins[11]->mode = Firmata\Pin::MODE_PWM; $board->pins[11]->analog = 1; $board->pins[9]->mode = Firmata\Pin::MODE_PWM; $board->pins[9]->analog = 1; // sensor pins $board->pins[12]->mode = Firmata\Pin::MODE_OUTPUT; $board->pins[12]->digital = 1; $board->pins[14]->mode = Firmata\Pin::MODE_ANALOG;

Slide 33

Slide 33 text

$services = new SplQueue(); $services->enqueue([ new Notifier\Service\Twitter( getenv("SERVICE_TWITTER_CONSUMER_KEY"), getenv("SERVICE_TWITTER_CONSUMER_SECRET"), getenv("SERVICE_TWITTER_ACCESS_TOKEN"), getenv("SERVICE_TWITTER_ACCESS_TOKEN_SECRET") ), false ]); $services->enqueue([ new Notifier\Service\Gmail( getenv("SERVICE_GMAIL_USERNAME"), getenv("SERVICE_GMAIL_PASSWORD") ), false ]);

Slide 34

Slide 34 text

$loop->setInterval(function () use (&$services) { $remaining = count($services); while ($remaining--) { $next = $services->dequeue(); $next[1] = $next[0]->query(); $services->enqueue($next); } }, 1000 * 5);

Slide 35

Slide 35 text

$service = null; $next = function () use ($loop, $board, &$next, &$services, &$service) { $remaining = count($services); while ($remaining--) { $next = $services->dequeue(); $services->enqueue($next); if ($next[1]) { $service = $next; break; } } // ...no notifications if (!$service) return; // ...

Slide 36

Slide 36 text

$colors = $service[0]->colors(); $board->pins[10]->analog = $colors[0]; $board->pins[11]->analog = $colors[1]; $board->pins[9]->analog = $colors[2]; $loop->setTimeout(function () use ($board, &$service) { $board->pins[10]->analog = 1; $board->pins[11]->analog = 1; $board->pins[9]->analog = 1; $service = null; }, 1000 * 1.5); }; $loop->setInterval($next, 1000 * 4);

Slide 37

Slide 37 text

$loop->setInterval(function() use ($board, &$services, &$service) { if ($service !== null && $board->pins[14]->analog < 0.1) { $remaining = count($services); while ($remaining--) { $next = $services->dequeue(); // dismissing notification... if ($next[0]->name() === $service[0]->name()) { $service = null; $next[0]->dismiss(); $next[1] = false; } $services->enqueue($next); } } }, 50);

Slide 38

Slide 38 text

bit.ly/sitepoint-arduino-notifications

Slide 39

Slide 39 text

QUESTIONS? twitter.com/assertchris