Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Dependencies: mbed Adafruit_GFX
Revision 0:22391cd705e2, committed 2019-06-15
- Comitter:
- 21400688
- Date:
- Sat Jun 15 20:52:15 2019 +0000
- Commit message:
- vb
Changed in this revision
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/Adafruit_GFX.lib Sat Jun 15 20:52:15 2019 +0000 @@ -0,0 +1,1 @@ +http://developer.mbed.org/users/nkhorman/code/Adafruit_GFX/#7fb1d4d3525d
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/PixelArray/PixelArray.cpp Sat Jun 15 20:52:15 2019 +0000
@@ -0,0 +1,127 @@
+#include "PixelArray.h"
+
+PixelArray::PixelArray(int size)
+{
+ pbufsize = size;
+ pbuf = new int[pbufsize];
+ SetAll(0x0); // initialise memory to zeros
+
+}
+
+PixelArray::~PixelArray()
+{
+ delete[] pbuf;
+}
+
+void PixelArray::SetAll(unsigned int value)
+{
+ // for each pixel
+ for (int i=0 ; i < pbufsize; i++) {
+ __set_pixel(i,value);
+ }
+}
+
+
+void PixelArray::SetAllI(unsigned char value)
+{
+ // for each pixel
+ for (int i=0 ; i < pbufsize; i++) {
+ __set_pixel_component(i,3,value);
+ }
+}
+
+
+
+void PixelArray::SetAllR(unsigned char value)
+{
+ // for each pixel
+ for (int i=0 ; i < pbufsize; i++) {
+ __set_pixel_component(i,2,value);
+ }
+}
+
+void PixelArray::SetAllG(unsigned char value)
+{
+ // for each pixel
+ for (int i=0 ; i < pbufsize; i++) {
+ __set_pixel_component(i,1,value);
+ }
+}
+
+void PixelArray::SetAllB(unsigned char value)
+{
+ // for each pixel
+ for (int i=0 ; i < pbufsize; i++) {
+ __set_pixel_component(i,0,value);
+ }
+}
+
+
+
+
+
+void PixelArray::Set(int i, unsigned int value)
+{
+ if ((i >= 0) && (i < pbufsize)) {
+ __set_pixel(i,value);
+ }
+}
+
+
+
+void PixelArray::SetI(int i, unsigned char value)
+{
+ if ((i >= 0) && (i < pbufsize)) {
+ __set_pixel_component(i,3,value);
+ }
+}
+
+
+void PixelArray::SetR(int i, unsigned char value)
+{
+ if ((i >= 0) && (i < pbufsize)) {
+ __set_pixel_component(i,2,value);
+ }
+}
+
+void PixelArray::SetG(int i, unsigned char value)
+{
+ if ((i >= 0) && (i < pbufsize)) {
+ __set_pixel_component(i,1,value);
+ }
+}
+
+void PixelArray::SetB(int i, unsigned char value)
+{
+ if ((i >= 0) && (i < pbufsize)) {
+ __set_pixel_component(i,0,value);
+ }
+}
+
+
+int* PixelArray::getBuf()
+{
+ return (pbuf);
+}
+
+
+// set either the I,R,G,B value of specific pixel channel
+void PixelArray::__set_pixel_component(int index, int channel, int value)
+{
+
+ // AND with 0x00 shifted to the right location to clear the bits
+ pbuf[index] &= ~(0xFF << (8 * channel));
+
+ // Set the bits with an OR
+ pbuf[index] |= (value << (8 * channel));
+}
+
+
+// set either the I,R,G,B value of specific pixel channel
+void PixelArray::__set_pixel(int index, int value)
+{
+ // AND with 0x00 shifted to the right location to clear the bits
+ pbuf[index] = value;
+}
+
+
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/PixelArray/PixelArray.h Sat Jun 15 20:52:15 2019 +0000
@@ -0,0 +1,68 @@
+/* Copyright (c) 2012 cstyles, MIT License
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy of this software
+ * and associated documentation files (the "Software"), to deal in the Software without restriction,
+ * including without limitation the rights to use, copy, modify, merge, publish, distribute,
+ * sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all copies or
+ * substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+ * BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+ * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef PixelArray_H
+#define PixelArray_H
+
+#include "mbed.h"
+
+//!Library for the WS2812 RGB LED with integrated controller
+/*!
+PixelArray
+*/
+class PixelArray
+{
+public:
+ //!Creates an instance of the class.
+ /*!
+ Pixel Array
+ */
+ PixelArray(int);
+
+ /*!
+ Destroys instance.
+ */
+ ~PixelArray();
+
+ int* getBuf();
+
+ void SetAll(unsigned int);
+ void SetAllI(unsigned char);
+ void SetAllR(unsigned char);
+ void SetAllG(unsigned char);
+ void SetAllB(unsigned char);
+
+ // location, value
+ void Set(int, unsigned int);
+ void SetI(int, unsigned char);
+ void SetR(int, unsigned char);
+ void SetG(int, unsigned char);
+ void SetB(int, unsigned char);
+
+private:
+
+ int *pbuf;
+ int pbufsize;
+
+ void __set_pixel_component(int index, int channel, int value);
+ void __set_pixel(int index, int value);
+
+};
+
+#endif
+
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/RemoteIR/ReceiverIR.cpp Sat Jun 15 20:52:15 2019 +0000
@@ -0,0 +1,330 @@
+/**
+ * IR receiver (Version 0.0.4)
+ *
+ * Copyright (C) 2010 Shinichiro Nakamura (CuBeatSystems)
+ * http://shinta.main.jp/
+ */
+
+#include "ReceiverIR.h"
+
+#define LOCK()
+#define UNLOCK()
+
+#define InRange(x,y) ((((y) * 0.7) < (x)) && ((x) < ((y) * 1.3)))
+
+/**
+ * Constructor.
+ *
+ * @param rxpin Pin for receive IR signal.
+ */
+ReceiverIR::ReceiverIR(PinName rxpin) : evt(rxpin) {
+ init_state();
+ evt.fall(this, &ReceiverIR::isr_fall);
+ evt.rise(this, &ReceiverIR::isr_rise);
+ evt.mode(PullUp);
+ ticker.attach_us(this, &ReceiverIR::isr_wdt, 10 * 1000);
+}
+
+/**
+ * Destructor.
+ */
+ReceiverIR::~ReceiverIR() {
+}
+
+/**
+ * Get state.
+ *
+ * @return Current state.
+ */
+ReceiverIR::State ReceiverIR::getState() {
+ LOCK();
+ State s = work.state;
+ UNLOCK();
+ return s;
+}
+
+/**
+ * Get data.
+ *
+ * @param format Pointer to format.
+ * @param buf Buffer of a data.
+ * @param bitlength Bit length of the buffer.
+ *
+ * @return Data bit length.
+ */
+int ReceiverIR::getData(RemoteIR::Format *format, uint8_t *buf, int bitlength) {
+ LOCK();
+
+ if (bitlength < data.bitcount) {
+ UNLOCK();
+ return -1;
+ }
+
+ const int nbits = data.bitcount;
+ const int nbytes = data.bitcount / 8 + (((data.bitcount % 8) != 0) ? 1 : 0);
+ *format = data.format;
+ for (int i = 0; i < nbytes; i++) {
+ buf[i] = data.buffer[i];
+ }
+
+ init_state();
+
+ UNLOCK();
+ return nbits;
+}
+
+void ReceiverIR::init_state(void) {
+ work.c1 = -1;
+ work.c2 = -1;
+ work.c3 = -1;
+ work.d1 = -1;
+ work.d2 = -1;
+ work.state = Idle;
+ data.format = RemoteIR::UNKNOWN;
+ data.bitcount = 0;
+ timer.stop();
+ timer.reset();
+ for (int i = 0; i < sizeof(data.buffer); i++) {
+ data.buffer[i] = 0;
+ }
+}
+
+void ReceiverIR::isr_wdt(void) {
+ LOCK();
+ static int cnt = 0;
+ if ((Idle != work.state) || ((0 <= work.c1) || (0 <= work.c2) || (0 <= work.c3) || (0 <= work.d1) || (0 <= work.d2))) {
+ cnt++;
+ if (cnt > 50) {
+#if 0
+ printf("# WDT [c1=%d, c2=%d, c3=%d, d1=%d, d2=%d, state=%d, format=%d, bitcount=%d]\n",
+ work.c1,
+ work.c2,
+ work.c3,
+ work.d1,
+ work.d2,
+ work.state,
+ data.format,
+ data.bitcount);
+#endif
+ init_state();
+ cnt = 0;
+ }
+ } else {
+ cnt = 0;
+ }
+ UNLOCK();
+}
+
+void ReceiverIR::isr_fall(void) {
+ LOCK();
+ switch (work.state) {
+ case Idle:
+ if (work.c1 < 0) {
+ timer.start();
+ work.c1 = timer.read_us();
+ } else {
+ work.c3 = timer.read_us();
+ int a = work.c2 - work.c1;
+ int b = work.c3 - work.c2;
+ if (InRange(a, RemoteIR::TUS_NEC * 16) && InRange(b, RemoteIR::TUS_NEC * 8)) {
+ /*
+ * NEC.
+ */
+ data.format = RemoteIR::NEC;
+ work.state = Receiving;
+ data.bitcount = 0;
+ } else if (InRange(a, RemoteIR::TUS_NEC * 16) && InRange(b, RemoteIR::TUS_NEC * 4)) {
+ /*
+ * NEC Repeat.
+ */
+ data.format = RemoteIR::NEC_REPEAT;
+ work.state = Received;
+ data.bitcount = 0;
+ work.c1 = -1;
+ work.c2 = -1;
+ work.c3 = -1;
+ work.d1 = -1;
+ work.d2 = -1;
+ } else if (InRange(a, RemoteIR::TUS_AEHA * 8) && InRange(b, RemoteIR::TUS_AEHA * 4)) {
+ /*
+ * AEHA.
+ */
+ data.format = RemoteIR::AEHA;
+ work.state = Receiving;
+ data.bitcount = 0;
+ } else if (InRange(a, RemoteIR::TUS_AEHA * 8) && InRange(b, RemoteIR::TUS_AEHA * 8)) {
+ /*
+ * AEHA Repeat.
+ */
+ data.format = RemoteIR::AEHA_REPEAT;
+ work.state = Received;
+ data.bitcount = 0;
+ work.c1 = -1;
+ work.c2 = -1;
+ work.c3 = -1;
+ work.d1 = -1;
+ work.d2 = -1;
+ } else {
+ init_state();
+ }
+ }
+ break;
+ case Receiving:
+ if (RemoteIR::NEC == data.format) {
+ work.d2 = timer.read_us();
+ int a = work.d2 - work.d1;
+ if (InRange(a, RemoteIR::TUS_NEC * 3)) {
+ data.buffer[data.bitcount / 8] |= (1 << (data.bitcount % 8));
+ } else if (InRange(a, RemoteIR::TUS_NEC * 1)) {
+ data.buffer[data.bitcount / 8] &= ~(1 << (data.bitcount % 8));
+ }
+ data.bitcount++;
+#if 0
+ /*
+ * Length of NEC is always 32 bits.
+ */
+ if (32 <= data.bitcount) {
+ data.state = Received;
+ work.c1 = -1;
+ work.c2 = -1;
+ work.c3 = -1;
+ work.d1 = -1;
+ work.d2 = -1;
+ }
+#else
+ /*
+ * Set timeout for tail detection automatically.
+ */
+ timeout.detach();
+ timeout.attach_us(this, &ReceiverIR::isr_timeout, RemoteIR::TUS_NEC * 5);
+#endif
+ } else if (RemoteIR::AEHA == data.format) {
+ work.d2 = timer.read_us();
+ int a = work.d2 - work.d1;
+ if (InRange(a, RemoteIR::TUS_AEHA * 3)) {
+ data.buffer[data.bitcount / 8] |= (1 << (data.bitcount % 8));
+ } else if (InRange(a, RemoteIR::TUS_AEHA * 1)) {
+ data.buffer[data.bitcount / 8] &= ~(1 << (data.bitcount % 8));
+ }
+ data.bitcount++;
+#if 0
+ /*
+ * Typical length of AEHA is 48 bits.
+ * Please check a specification of your remote controller if you find a problem.
+ */
+ if (48 <= data.bitcount) {
+ data.state = Received;
+ work.c1 = -1;
+ work.c2 = -1;
+ work.c3 = -1;
+ work.d1 = -1;
+ work.d2 = -1;
+ }
+#else
+ /*
+ * Set timeout for tail detection automatically.
+ */
+ timeout.detach();
+ timeout.attach_us(this, &ReceiverIR::isr_timeout, RemoteIR::TUS_AEHA * 5);
+#endif
+ } else if (RemoteIR::SONY == data.format) {
+ work.d1 = timer.read_us();
+ }
+ break;
+ case Received:
+ break;
+ default:
+ break;
+ }
+ UNLOCK();
+}
+
+void ReceiverIR::isr_rise(void) {
+ LOCK();
+ switch (work.state) {
+ case Idle:
+ if (0 <= work.c1) {
+ work.c2 = timer.read_us();
+ int a = work.c2 - work.c1;
+ if (InRange(a, RemoteIR::TUS_SONY * 4)) {
+ data.format = RemoteIR::SONY;
+ work.state = Receiving;
+ data.bitcount = 0;
+ } else {
+ static const int MINIMUM_LEADER_WIDTH = 150;
+ if (a < MINIMUM_LEADER_WIDTH) {
+ init_state();
+ }
+ }
+ } else {
+ init_state();
+ }
+ break;
+ case Receiving:
+ if (RemoteIR::NEC == data.format) {
+ work.d1 = timer.read_us();
+ } else if (RemoteIR::AEHA == data.format) {
+ work.d1 = timer.read_us();
+ } else if (RemoteIR::SONY == data.format) {
+ work.d2 = timer.read_us();
+ int a = work.d2 - work.d1;
+ if (InRange(a, RemoteIR::TUS_SONY * 2)) {
+ data.buffer[data.bitcount / 8] |= (1 << (data.bitcount % 8));
+ } else if (InRange(a, RemoteIR::TUS_SONY * 1)) {
+ data.buffer[data.bitcount / 8] &= ~(1 << (data.bitcount % 8));
+ }
+ data.bitcount++;
+#if 0
+ /*
+ * How do I know the correct length? (6bits, 12bits, 15bits, 20bits...)
+ * By a model only?
+ * Please check a specification of your remote controller if you find a problem.
+ */
+ if (12 <= data.bitcount) {
+ data.state = Received;
+ work.c1 = -1;
+ work.c2 = -1;
+ work.c3 = -1;
+ work.d1 = -1;
+ work.d2 = -1;
+ }
+#else
+ /*
+ * Set timeout for tail detection automatically.
+ */
+ timeout.detach();
+ timeout.attach_us(this, &ReceiverIR::isr_timeout, RemoteIR::TUS_SONY * 4);
+#endif
+ }
+ break;
+ case Received:
+ break;
+ default:
+ break;
+ }
+ UNLOCK();
+}
+
+void ReceiverIR::isr_timeout(void) {
+ LOCK();
+#if 0
+ printf("# TIMEOUT [c1=%d, c2=%d, c3=%d, d1=%d, d2=%d, state=%d, format=%d, bitcount=%d]\n",
+ work.c1,
+ work.c2,
+ work.c3,
+ work.d1,
+ work.d2,
+ work.state,
+ data.format,
+ data.bitcount);
+#endif
+ if (work.state == Receiving) {
+ work.state = Received;
+ work.c1 = -1;
+ work.c2 = -1;
+ work.c3 = -1;
+ work.d1 = -1;
+ work.d2 = -1;
+ }
+ UNLOCK();
+}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/RemoteIR/ReceiverIR.h Sat Jun 15 20:52:15 2019 +0000
@@ -0,0 +1,98 @@
+/**
+ * IR receiver (Version 0.0.4)
+ *
+ * Copyright (C) 2010 Shinichiro Nakamura (CuBeatSystems)
+ * http://shinta.main.jp/
+ */
+
+#ifndef _RECEIVER_IR_H_
+#define _RECEIVER_IR_H_
+
+#include <mbed.h>
+
+#include "RemoteIR.h"
+
+/**
+ * IR receiver class.
+ */
+class ReceiverIR {
+public:
+
+ /**
+ * Constructor.
+ *
+ * @param rxpin Pin for receive IR signal.
+ */
+ explicit ReceiverIR(PinName rxpin);
+
+ /**
+ * Destructor.
+ */
+ ~ReceiverIR();
+
+ /**
+ * State.
+ */
+ typedef enum {
+ Idle,
+ Receiving,
+ Received
+ } State;
+
+ /**
+ * Get state.
+ *
+ * @return Current state.
+ */
+ State getState();
+
+ /**
+ * Get data.
+ *
+ * @param format Pointer to format.
+ * @param buf Buffer of a data.
+ * @param bitlength Bit length of the buffer.
+ *
+ * @return Data bit length.
+ */
+ int getData(RemoteIR::Format *format, uint8_t *buf, int bitlength);
+
+private:
+
+ typedef struct {
+ RemoteIR::Format format;
+ int bitcount;
+ uint8_t buffer[64];
+ } data_t;
+
+ typedef struct {
+ State state;
+ int c1;
+ int c2;
+ int c3;
+ int d1;
+ int d2;
+ } work_t;
+
+ InterruptIn evt; /**< Interrupt based input for input. */
+ Timer timer; /**< Timer for WDT. */
+ Ticker ticker; /**< Tciker for tick. */
+ Timeout timeout; /**< Timeout for tail. */
+
+ data_t data;
+ work_t work;
+
+ void init_state(void);
+
+ void isr_wdt(void);
+ void isr_fall(void);
+ void isr_rise(void);
+
+ /**
+ * ISR timeout for tail detection.
+ */
+ void isr_timeout(void);
+
+};
+
+#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/RemoteIR/RemoteIR.h Sat Jun 15 20:52:15 2019 +0000
@@ -0,0 +1,31 @@
+/**
+ * IR remote common class (Version 0.0.4)
+ *
+ * Copyright (C) 2010 Shinichiro Nakamura (CuBeatSystems)
+ * http://shinta.main.jp/
+ */
+
+#ifndef _REMOTE_IR_H_
+#define _REMOTE_IR_H_
+
+class RemoteIR {
+public:
+
+ typedef enum {
+ UNKNOWN,
+ NEC,
+ NEC_REPEAT,
+ AEHA,
+ AEHA_REPEAT,
+ SONY
+ } Format;
+
+ static const int TUS_NEC = 562;
+ static const int TUS_AEHA = 425;
+ static const int TUS_SONY = 600;
+
+private:
+ RemoteIR();
+};
+
+#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/RemoteIR/TransmitterIR.cpp Sat Jun 15 20:52:15 2019 +0000
@@ -0,0 +1,300 @@
+/**
+ * IR transmitter (Version 0.0.4)
+ *
+ * Copyright (C) 2010 Shinichiro Nakamura (CuBeatSystems)
+ * http://shinta.main.jp/
+ */
+
+#include "TransmitterIR.h"
+
+#define LOCK()
+#define UNLOCK()
+
+/**
+ * Constructor.
+ *
+ * @param txpin Pin for transmit IR signal.
+ */
+TransmitterIR::TransmitterIR(PinName txpin) : tx(txpin) {
+ tx.write(0.0);
+ tx.period_us(26.3);
+
+ work.state = Idle;
+ work.bitcount = 0;
+ work.leader = 0;
+ work.data = 0;
+ work.trailer = 0;
+
+ data.format = RemoteIR::UNKNOWN;
+ data.bitlength = 0;
+}
+
+/**
+ * Destructor.
+ */
+TransmitterIR::~TransmitterIR() {
+}
+
+/**
+ * Get state.
+ *
+ * @return Current state.
+ */
+TransmitterIR::State TransmitterIR::getState(void) {
+ LOCK();
+ State s = work.state;
+ UNLOCK();
+ return s;
+}
+
+/**
+ * Set data.
+ *
+ * @param format Format.
+ * @param buf Buffer of a data.
+ * @param bitlength Bit length of the data.
+ *
+ * @return Data bit length.
+ */
+int TransmitterIR::setData(RemoteIR::Format format, uint8_t *buf, int bitlength) {
+ LOCK();
+ if (work.state != Idle) {
+ UNLOCK();
+ return -1;
+ }
+
+ work.state = Leader;
+ work.bitcount = 0;
+ work.leader = 0;
+ work.data = 0;
+ work.trailer = 0;
+
+ data.format = format;
+ data.bitlength = bitlength;
+ const int n = bitlength / 8 + (((bitlength % 8) != 0) ? 1 : 0);
+ for (int i = 0; i < n; i++) {
+ data.buffer[i] = buf[i];
+ }
+
+ switch (format) {
+ case RemoteIR::NEC:
+ ticker.detach();
+ ticker.attach_us(this, &TransmitterIR::tick, RemoteIR::TUS_NEC);
+ break;
+ case RemoteIR::AEHA:
+ ticker.detach();
+ ticker.attach_us(this, &TransmitterIR::tick, RemoteIR::TUS_AEHA);
+ break;
+ case RemoteIR::SONY:
+ ticker.detach();
+ ticker.attach_us(this, &TransmitterIR::tick, RemoteIR::TUS_SONY);
+ break;
+ }
+
+ UNLOCK();
+ return bitlength;
+}
+
+void TransmitterIR::tick(void) {
+ LOCK();
+ switch (work.state) {
+ case Idle:
+ work.bitcount = 0;
+ work.leader = 0;
+ work.data = 0;
+ work.trailer = 0;
+ break;
+ case Leader:
+ if (data.format == RemoteIR::NEC) {
+ /*
+ * NEC.
+ */
+ static const int LEADER_NEC_HEAD = 16;
+ static const int LEADER_NEC_TAIL = 8;
+ if (work.leader < LEADER_NEC_HEAD) {
+ tx.write(0.5);
+ } else {
+ tx.write(0.0);
+ }
+ work.leader++;
+ if ((LEADER_NEC_HEAD + LEADER_NEC_TAIL) <= work.leader) {
+ work.state = Data;
+ }
+ } else if (data.format == RemoteIR::AEHA) {
+ /*
+ * AEHA.
+ */
+ static const int LEADER_AEHA_HEAD = 8;
+ static const int LEADER_AEHA_TAIL = 4;
+ if (work.leader < LEADER_AEHA_HEAD) {
+ tx.write(0.5);
+ } else {
+ tx.write(0.0);
+ }
+ work.leader++;
+ if ((LEADER_AEHA_HEAD + LEADER_AEHA_TAIL) <= work.leader) {
+ work.state = Data;
+ }
+ } else if (data.format == RemoteIR::SONY) {
+ /*
+ * SONY.
+ */
+ static const int LEADER_SONY_HEAD = 4;
+ static const int LEADER_SONY_TAIL = 0;
+ if (work.leader < LEADER_SONY_HEAD) {
+ tx.write(0.5);
+ } else {
+ tx.write(0.0);
+ }
+ work.leader++;
+ if ((LEADER_SONY_HEAD + LEADER_SONY_TAIL) <= work.leader) {
+ work.state = Data;
+ }
+ } else {
+ }
+ break;
+ case Data:
+ if (data.format == RemoteIR::NEC) {
+ /*
+ * NEC.
+ */
+ if (work.data == 0) {
+ tx.write(0.5);
+ work.data++;
+ } else {
+ tx.write(0.0);
+ if (0 != (data.buffer[work.bitcount / 8] & (1 << work.bitcount % 8))) {
+ if (3 <= work.data) {
+ work.bitcount++;
+ work.data = 0;
+ } else {
+ work.data++;
+ }
+ } else {
+ if (1 <= work.data) {
+ work.bitcount++;
+ work.data = 0;
+ } else {
+ work.data++;
+ }
+ }
+ }
+ if (data.bitlength <= work.bitcount) {
+ work.state = Trailer;
+ }
+ } else if (data.format == RemoteIR::AEHA) {
+ /*
+ * AEHA.
+ */
+ if (work.data == 0) {
+ tx.write(0.5);
+ work.data++;
+ } else {
+ tx.write(0.0);
+ if (0 != (data.buffer[work.bitcount / 8] & (1 << work.bitcount % 8))) {
+ if (3 <= work.data) {
+ work.bitcount++;
+ work.data = 0;
+ } else {
+ work.data++;
+ }
+ } else {
+ if (1 <= work.data) {
+ work.bitcount++;
+ work.data = 0;
+ } else {
+ work.data++;
+ }
+ }
+ }
+ if (data.bitlength <= work.bitcount) {
+ work.state = Trailer;
+ }
+ } else if (data.format == RemoteIR::SONY) {
+ /*
+ * SONY.
+ */
+ if (work.data == 0) {
+ tx.write(0.0);
+ work.data++;
+ } else {
+ tx.write(0.5);
+ if (0 != (data.buffer[work.bitcount / 8] & (1 << work.bitcount % 8))) {
+ if (2 <= work.data) {
+ work.bitcount++;
+ work.data = 0;
+ } else {
+ work.data++;
+ }
+ } else {
+ if (1 <= work.data) {
+ work.bitcount++;
+ work.data = 0;
+ } else {
+ work.data++;
+ }
+ }
+ }
+ if (data.bitlength <= work.bitcount) {
+ work.state = Trailer;
+ }
+ } else {
+ }
+ break;
+ case Trailer:
+ if (data.format == RemoteIR::NEC) {
+ /*
+ * NEC.
+ */
+ static const int TRAILER_NEC_HEAD = 1;
+ static const int TRAILER_NEC_TAIL = 2;
+ if (work.trailer < TRAILER_NEC_HEAD) {
+ tx.write(0.5);
+ } else {
+ tx.write(0.0);
+ }
+ work.trailer++;
+ if ((TRAILER_NEC_HEAD + TRAILER_NEC_TAIL) <= work.trailer) {
+ work.state = Idle;
+ //ticker.detach();
+ }
+ } else if (data.format == RemoteIR::AEHA) {
+ /*
+ * AEHA.
+ */
+ static const int TRAILER_AEHA_HEAD = 1;
+ static const int TRAILER_AEHA_TAIL = 8000 / RemoteIR::TUS_AEHA;
+ if (work.trailer < TRAILER_AEHA_HEAD) {
+ tx.write(0.5);
+ } else {
+ tx.write(0.0);
+ }
+ work.trailer++;
+ if ((TRAILER_AEHA_HEAD + TRAILER_AEHA_TAIL) <= work.trailer) {
+ work.state = Idle;
+ //ticker.detach();
+ }
+ } else if (data.format == RemoteIR::SONY) {
+ /*
+ * SONY.
+ */
+ static const int TRAILER_SONY_HEAD = 0;
+ static const int TRAILER_SONY_TAIL = 0;
+ if (work.trailer < TRAILER_SONY_HEAD) {
+ tx.write(0.5);
+ } else {
+ tx.write(0.0);
+ }
+ work.trailer++;
+ if ((TRAILER_SONY_HEAD + TRAILER_SONY_TAIL) <= work.trailer) {
+ work.state = Idle;
+ //ticker.detach();
+ }
+ } else {
+ }
+ break;
+ default:
+ break;
+ }
+ UNLOCK();
+}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/RemoteIR/TransmitterIR.h Sat Jun 15 20:52:15 2019 +0000
@@ -0,0 +1,83 @@
+/**
+ * IR transmitter (Version 0.0.4)
+ *
+ * Copyright (C) 2010 Shinichiro Nakamura (CuBeatSystems)
+ * http://shinta.main.jp/
+ */
+
+#ifndef _TRANSMITTER_IR_H_
+#define _TRANSMITTER_IR_H_
+
+#include <mbed.h>
+
+#include "RemoteIR.h"
+
+/**
+ * IR transmitter class.
+ */
+class TransmitterIR {
+public:
+
+ /**
+ * Constructor.
+ *
+ * @param txpin Pin for transmit IR signal.
+ */
+ explicit TransmitterIR(PinName txpin);
+
+ /**
+ * Destructor.
+ */
+ ~TransmitterIR();
+
+ typedef enum {
+ Idle,
+ Leader,
+ Data,
+ Trailer
+ } State;
+
+ /**
+ * Get state.
+ *
+ * @return Current state.
+ */
+ State getState(void);
+
+ /**
+ * Set data.
+ *
+ * @param format Format.
+ * @param buf Buffer of a data.
+ * @param bitlength Bit length of the data.
+ *
+ * @return Data bit length.
+ */
+ int setData(RemoteIR::Format format, uint8_t *buf, int bitlength);
+
+private:
+
+ typedef struct {
+ State state;
+ int bitcount;
+ int leader;
+ int data;
+ int trailer;
+ } work_t;
+
+ typedef struct {
+ RemoteIR::Format format;
+ int bitlength;
+ uint8_t buffer[64];
+ } data_t;
+
+ PwmOut tx;
+ Ticker ticker;
+ data_t data;
+ work_t work;
+
+ void tick();
+
+};
+
+#endif
\ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/TB6612FNG/TB6612FNG.cpp Sat Jun 15 20:52:15 2019 +0000
@@ -0,0 +1,118 @@
+/* File: TB6612FNG.h
+ * Author: Robert Abad Copyright (c) 2013
+ *
+ * Desc: driver for TB6612FNG Motor Driver. For further details see
+ * header file, TB6612FNG.h
+ */
+
+#include "mbed.h"
+#include "TB6612FNG.h"
+
+#define SIGNAL_HIGH (1)
+#define SIGNAL_LOW (0)
+
+TB6612FNG::TB6612FNG( PinName pinPwmA, PinName pinAin1, PinName pinAin2,
+ PinName pinPwmB, PinName pinBin1, PinName pinBin2,
+ PinName pinNStby ) :
+pwmA(pinPwmA),
+Ain1(pinAin1),
+Ain2(pinAin2),
+pwmB(pinPwmB),
+Bin1(pinBin1),
+Bin2(pinBin2),
+nStby(pinNStby)
+{
+ Ain1 = SIGNAL_LOW;
+ Ain2 = SIGNAL_LOW;
+ Bin1 = SIGNAL_LOW;
+ Bin2 = SIGNAL_LOW;
+ pwmA.period(TB6612FNG_PWM_PERIOD_DEFAULT);
+ pwmA = TB6612FNG_PWM_PULSEWIDTH_DEFAULT;
+ pwmB.period(TB6612FNG_PWM_PERIOD_DEFAULT);
+ pwmB = TB6612FNG_PWM_PULSEWIDTH_DEFAULT;
+ nStby = SIGNAL_LOW;
+}
+
+void TB6612FNG::setPwmA(float fPeriod, float fPulsewidth)
+{
+ pwmA.period(fPeriod);
+ pwmA = fPulsewidth;
+}
+
+void TB6612FNG::setPwmAperiod(float fPeriod)
+{
+ pwmA.period(fPeriod);
+}
+
+void TB6612FNG::setPwmApulsewidth(float fPulsewidth)
+{
+ pwmA = fPulsewidth;
+}
+float TB6612FNG::getPwmA()
+{
+ return pwmA;
+}
+float TB6612FNG::getPwmB()
+{
+ return pwmB;
+}
+void TB6612FNG::setPwmB(float fPeriod, float fPulsewidth)
+{
+ pwmB.period(fPeriod);
+ pwmB = fPulsewidth;
+}
+
+void TB6612FNG::setPwmBperiod(float fPeriod)
+{
+ pwmB.period(fPeriod);
+}
+
+void TB6612FNG::setPwmBpulsewidth(float fPulsewidth)
+{
+ pwmB = fPulsewidth;
+}
+
+void TB6612FNG::standby(void)
+{
+ nStby = SIGNAL_LOW;
+}
+
+void TB6612FNG::motorA_stop(void)
+{
+ Ain1 = SIGNAL_LOW;
+ Ain2 = SIGNAL_LOW;
+}
+
+void TB6612FNG::motorA_ccw(void)
+{
+ Ain1 = SIGNAL_LOW;
+ Ain2 = SIGNAL_HIGH;
+ nStby = SIGNAL_HIGH;
+}
+
+void TB6612FNG::motorA_cw(void)
+{
+ Ain1 = SIGNAL_HIGH;
+ Ain2 = SIGNAL_LOW;
+ nStby = SIGNAL_HIGH;
+}
+
+void TB6612FNG::motorB_stop(void)
+{
+ Bin1 = SIGNAL_LOW;
+ Bin2 = SIGNAL_LOW;
+}
+
+void TB6612FNG::motorB_ccw(void)
+{
+ Bin1 = SIGNAL_LOW;
+ Bin2 = SIGNAL_HIGH;
+ nStby = SIGNAL_HIGH;
+}
+
+void TB6612FNG::motorB_cw(void)
+{
+ Bin1 = SIGNAL_HIGH;
+ Bin2 = SIGNAL_LOW;
+ nStby = SIGNAL_HIGH;
+}
\ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/TB6612FNG/TB6612FNG.h Sat Jun 15 20:52:15 2019 +0000
@@ -0,0 +1,98 @@
+/* File: TB6612FNG.h
+ * Author: Robert Abad Copyright (c) 2013
+ *
+ * Desc: driver for Toshiiba TB6612FNG Motor Driver. Though this motor driver
+ * can be used to drive two motors (A and B), it can be used to drive
+ * just one. Member functions can be used to set period and pulsewidth
+ * but are not necessary as the constructor does set default values).
+ * The datasheet for this device can be found here:
+ * http://www.toshiba.com/taec/components2/Datasheet_Sync/261/27197.pdf
+ *
+ * Below is some sample code:
+ *
+ * #include "mbed.h"
+ * #include "TB6612FNG.h"
+ *
+ * #define TB6612FNG_PIN_PWMA (p22)
+ * #define TB6612FNG_PIN_AIN1 (p17)
+ * #define TB6612FNG_PIN_AIN2 (p16)
+ * #define TB6612FNG_PIN_PWMB (p21)
+ * #define TB6612FNG_PIN_BIN1 (p19)
+ * #define TB6612FNG_PIN_BIN2 (p20)
+ * #define TB6612FNG_PIN_NSTBY (p18)
+ * TB6612FNG motorDriver( TB6612FNG_PIN_PWMA, TB6612FNG_PIN_AIN1, TB6612FNG_PIN_AIN2,
+ * TB6612FNG_PIN_PWMB, TB6612FNG_PIN_BIN1, TB6612FNG_PIN_BIN2,
+ * TB6612FNG_PIN_NSTBY );
+ * float fPwmPeriod;
+ * float fPwmPulsewidth;
+ *
+ * int main()
+ * {
+ * fPwmPeriod = 0.00002f; // 50KHz
+ * fPwmPulsewidth = 0.50; // 50% duty cycle
+ * motorDriver.setPwmAperiod(fPwmPeriod);
+ * motorDriver.setPwmBperiod(fPwmPeriod);
+ * motorDriver.setPwmApulsewidth(fPwmPulsewidth);
+ * motorDriver.setPwmBpulsewidth(fPwmPulsewidth);
+ *
+ * while(1)
+ * {
+ * motorDriver.motorA_ccw();
+ * wait(2);
+ * motorDriver.motorA_cw();
+ * wait(2);
+ * motorDriver.motorA_stop();
+ * wait(2);
+ * motorDriver.motorB_ccw();
+ * wait(2);
+ * motorDriver.motorB_cw();
+ * wait(2);
+ * motorDriver.motorB_stop();
+ * wait(2);
+ * }
+ * }
+ */
+
+#ifndef __TB6612FNG_H__
+#define __TB6612FNG_H__
+
+#include "mbed.h"
+
+#define TB6612FNG_PWM_PERIOD_DEFAULT (0.00002) // 50KHz
+#define TB6612FNG_PWM_PULSEWIDTH_DEFAULT (0.50) // 속도 이거다!
+
+class TB6612FNG
+{
+public:
+ TB6612FNG( PinName pinPwmA, PinName pinAin1, PinName pinAin2,
+ PinName pinPwmB, PinName pinBin1, PinName pinBin2,
+ PinName pinNStby );
+ void setPwmA(float fPeriod, float fPulsewidth);
+ void setPwmAperiod(float fPeriod);
+ void setPwmApulsewidth(float fPulsewidth);
+ void setPwmB(float fPeriod, float fPulsewidth);
+ void setPwmBperiod(float fPeriod);
+ void setPwmBpulsewidth(float fPulsewidth);
+ void standby(void);
+ void motorA_stop(void);
+ void motorA_ccw(void);
+ void motorA_cw(void);
+ void motorB_stop(void);
+ void motorB_ccw(void);
+ void motorB_cw(void);
+ void upPulsewidth(void);
+ void downPulsewidth(void);
+ float getPwmA(void);
+ float getPwmB(void);
+
+private:
+ PwmOut pwmA;
+ DigitalOut Ain1;
+ DigitalOut Ain2;
+ PwmOut pwmB;
+ DigitalOut Bin1;
+ DigitalOut Bin2;
+ DigitalOut nStby;
+};
+
+#endif /* __TB6612FNG_H__ */
\ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/Ultrasonic.cpp Sat Jun 15 20:52:15 2019 +0000
@@ -0,0 +1,70 @@
+#include "Ultrasonic.h"
+
+Ultrasonic::Ultrasonic(PinName trigPin, PinName echoPin, float tick, bool repeat)
+ : _trig(trigPin), _echo(echoPin), _toVal(tick), _repeat(repeat)
+{
+ _done = 0;
+ _timer.reset();
+ _echo.rise(this, &Ultrasonic::_startT);
+ _echo.fall(this, &Ultrasonic::_endT);
+ if (_repeat) _ticker.attach(this, &Ultrasonic::_ticker_cb, _toVal);
+}
+
+Ultrasonic::~Ultrasonic() {}
+
+void Ultrasonic::_startT(void)
+{
+ _timer.start();
+}
+void Ultrasonic::_endT(void)
+{
+ _timer.stop();
+ _pulseDuration = _timer.read_us();
+ _distance = _pulseDuration / 58;
+ _timer.reset();
+ _done = 1;
+}
+
+
+void Ultrasonic::trig()
+{
+ _echo.enable_irq();
+ wait_us(2);
+ _trig = 1;
+ wait_us(10);
+ _trig = 0;
+}
+void Ultrasonic::_ticker_cb(void)
+{
+ this->trig();
+}
+
+int Ultrasonic::getDistance(void)
+{
+ return _distance;
+}
+int Ultrasonic::getPulseDuration(void)
+{
+ return _pulseDuration;
+}
+
+void Ultrasonic::pauseMeasure(void)
+{
+ _repeat = false;
+ _ticker.detach();
+}
+void Ultrasonic::setMode(bool mode)
+{
+ _repeat = mode;
+ if (_repeat) _ticker.attach(this, &Ultrasonic::_ticker_cb, _toVal);
+ else _ticker.detach();
+}
+
+int Ultrasonic::getStatus()
+{
+ return _done;
+}
+void Ultrasonic::clearStatus(void)
+{
+ _done = 0;
+}
\ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/Ultrasonic.h Sat Jun 15 20:52:15 2019 +0000
@@ -0,0 +1,40 @@
+#ifndef MBED_ULTRASONIC_H
+#define MBED_ULTRASONIC_H
+
+#include "mbed.h"
+
+class Ultrasonic
+{
+public:
+ Ultrasonic(PinName trigPin, PinName echoPin, float tick = 0.1, bool repeat = false);
+ ~Ultrasonic();
+
+ void trig();
+ int getDistance(void);
+ int getPulseDuration(void);
+
+ //the ultrasonic sensor will stop after measuring once, use clear to clear the value
+ int getStatus(void);
+ void clearStatus(void);
+
+ void pauseMeasure(void);
+ void setMode(bool mode);
+private:
+ DigitalOut _trig;
+ InterruptIn _echo;
+
+ Timer _timer;
+ Ticker _ticker;
+ float _toVal;
+ bool _repeat;
+
+ int _distance;
+ int _pulseDuration;
+
+ void _startT(void);
+ void _endT(void);
+ void _ticker_cb(void);
+ int _done;
+};
+
+#endif MBED_ULTRASONIC_H
\ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/WS2812/WS2812.cpp Sat Jun 15 20:52:15 2019 +0000
@@ -0,0 +1,130 @@
+#include "WS2812.h"
+
+WS2812::WS2812(PinName pin, int size, int zeroHigh, int zeroLow, int oneHigh, int oneLow) : __gpo(pin)
+{
+ __size = size;
+ __transmitBuf = new bool[size * FRAME_SIZE];
+ __use_II = OFF;
+ __II = 0xFF; // set global intensity to full
+ __outPin = pin;
+
+ // Default values designed for K64f. Assumes GPIO toggle takes ~0.4us
+ setDelays(zeroHigh, zeroLow, oneHigh, oneLow);
+}
+
+
+WS2812::~WS2812()
+{
+ delete[] __transmitBuf;
+}
+
+void WS2812::setDelays(int zeroHigh, int zeroLow, int oneHigh, int oneLow) {
+ __zeroHigh = zeroHigh;
+ __zeroLow = zeroLow;
+ __oneHigh = oneHigh;
+ __oneLow = oneLow;
+}
+
+void WS2812::__loadBuf(int buf[],int r_offset, int g_offset, int b_offset) {
+ for (int i = 0; i < __size; i++) {
+ int color = 0;
+
+ color |= ((buf[(i+g_offset)%__size] & 0x0000FF00));
+ color |= ((buf[(i+r_offset)%__size] & 0x00FF0000));
+ color |= (buf[(i+b_offset)%__size] & 0x000000FF);
+ color |= (buf[i] & 0xFF000000);
+
+ // Outut format : GGRRBB
+ // Inout format : IIRRGGBB
+ unsigned char agrb[4] = {0x0, 0x0, 0x0, 0x0};
+
+ unsigned char sf; // scaling factor for II
+
+ // extract colour fields from incoming
+ // 0 = green, 1 = red, 2 = blue, 3 = brightness
+ agrb[0] = (color & 0x0000FF00) >> 8;
+ agrb[1] = (color & 0x00FF0000) >> 16;
+ agrb[2] = color & 0x000000FF;
+ agrb[3] = (color & 0xFF000000) >> 24;
+
+ // set the intensity scaling factor (global, per pixel, none)
+ if (__use_II == GLOBAL) {
+ sf = __II;
+ } else if (__use_II == PER_PIXEL) {
+ sf = agrb[3];
+ } else {
+ sf = 0xFF;
+ }
+
+ // Apply the scaling factor to each othe colour components
+ for (int clr = 0; clr < 3; clr++) {
+ agrb[clr] = ((agrb[clr] * sf) >> 8);
+
+ for (int j = 0; j < 8; j++) {
+ if (((agrb[clr] << j) & 0x80) == 0x80) {
+ // Bit is set (checks MSB fist)
+ __transmitBuf[(i * FRAME_SIZE) + (clr * 8) + j] = 1;
+ } else {
+ // Bit is clear
+ __transmitBuf[(i * FRAME_SIZE) + (clr * 8) + j] = 0;
+ }
+ }
+ }
+ }
+}
+
+void WS2812::write(int buf[]) {
+ write_offsets(buf, 0, 0, 0);
+}
+
+void WS2812::write_offsets (int buf[],int r_offset, int g_offset, int b_offset) {
+ int i, j;
+
+ // Load the transmit buffer
+ __loadBuf(buf, r_offset, g_offset, b_offset);
+
+ // Entering timing critical section, so disabling interrupts
+ __disable_irq();
+
+ // Begin bit-banging
+ for (i = 0; i < FRAME_SIZE * __size; i++) {
+ j = 0;
+ if (__transmitBuf[i]){
+ __gpo = 1;
+ for (; j < __oneHigh; j++) {
+ __nop();
+ }
+ __gpo = 0;
+ for (; j < __oneLow; j++) {
+ __nop();
+ }
+ } else {
+ __gpo = 1;
+ for (; j < __zeroHigh; j++) {
+ __nop();
+ }
+ __gpo = 0;
+ for (; j < __zeroLow; j++) {
+ __nop();
+ }
+ }
+ }
+
+ // Exiting timing critical section, so enabling interrutps
+ __enable_irq();
+}
+
+
+void WS2812::useII(BrightnessControl bc)
+{
+ if (bc > OFF) {
+ __use_II = bc;
+ } else {
+ __use_II = OFF;
+ }
+}
+
+void WS2812::setII(unsigned char II)
+{
+ __II = II;
+}
\ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/WS2812/WS2812.h Sat Jun 15 20:52:15 2019 +0000
@@ -0,0 +1,116 @@
+/* Copyright (c) 2012 cstyles, MIT License
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy of this software
+ * and associated documentation files (the "Software"), to deal in the Software without restriction,
+ * including without limitation the rights to use, copy, modify, merge, publish, distribute,
+ * sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all copies or
+ * substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+ * BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+ * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef WS2812_H
+#define WS2812_H
+
+#include "mbed.h"
+
+#define FRAME_SIZE 24
+
+//!Library for the WS2812 RGB LED with integrated controller
+/*!
+The WS2812 is controller that is built into a range of LEDs
+*/
+class WS2812
+{
+public:
+ enum BrightnessControl { OFF, GLOBAL, PER_PIXEL };
+
+ /**
+ * Constructor
+ *
+ * @param pin Output pin. Connect to "Din" on the first WS2812 in the strip
+ * @param size Number of LEDs in your strip
+ * @param zeroHigh How many NOPs to insert to ensure TOH is properly generated. See library description for more information.
+ * @param zeroLow How many NOPs to insert to ensure TOL is properly generated. See library description for more information.
+ * @param oneHigh How many NOPs to insert to ensure T1H is properly generated. See library description for more information.
+ * @param oneLow How many NOPs to insert to ensure T1L is properly generated. See library description for more information.
+ *
+ */
+ WS2812(PinName pin, int size, int zeroHigh, int zeroLow, int oneHigh, int oneLow);
+
+ /*!
+ Destroys instance.
+ */
+ ~WS2812();
+
+ /**
+ * Sets the timing parameters for the bit-banged signal
+ *
+ * @param zeroHigh How many NOPs to insert to ensure TOH is properly generated. See library description for more information.
+ * @param zeroLow How many NOPs to insert to ensure TOL is properly generated. See library description for more information.
+ * @param oneHigh How many NOPs to insert to ensure T1H is properly generated. See library description for more information.
+ * @param oneLow How many NOPs to insert to ensure T1L is properly generated. See library description for more information.
+ *
+ */
+ void setDelays(int zeroHigh, int zeroLow, int oneHigh, int oneLow);
+
+ /**
+ * Writes the given buffer to the LED strip with the given offsets.
+ * NOTE: This function is timing critical, therefore interrupts are disabled during the transmission section.
+ *
+ * @param buf Pointer to the PixelArray buffer
+ * @param r_offset The offset where each each pixel pulls its red component. Wraps to beginning if end is reached.
+ * @param g_offset The offset where each each pixel pulls its green component. Wraps to beginning if end is reached.
+ * @param b_offset The offset where each each pixel pulls its blue component. Wraps to beginning if end is reached.
+ *
+ */
+ void write_offsets(int buf[], int r_offset = 0, int g_offset = 0, int b_offset = 0);
+
+
+ /**
+ * Writes the given buffer to the LED strip
+ * NOTE: This function is timing critical, therefore interrupts are disabled during the transmission section.
+ *
+ * @param buf Pointer to the PixelArray buffer
+ *
+ */
+ void write(int buf[]);
+
+ /**
+ * Sets the brightness mode
+ *
+ * @param bc The brightness control. Defaults to OFF. Possible values include OFF, GLOBAL, and PER_PIXEL
+ *
+ */
+ void useII(BrightnessControl bc);
+
+ /**
+ * Sets the global brightness level.
+ *
+ * @param II The brightness level. Possible values include 0 - 255 (0x00 - 0xFF).
+ *
+ */
+ void setII(unsigned char II);
+
+
+
+private:
+
+ int __size;
+ int __zeroHigh, __zeroLow, __oneHigh, __oneLow;
+ unsigned char __II;
+ BrightnessControl __use_II;
+ bool *__transmitBuf;
+ void __loadBuf(int buf[],int r_offset=0, int g_offset=0, int b_offset=0);
+ PinName __outPin;
+ DigitalOut __gpo;
+};
+
+#endif
\ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/main.cpp Sat Jun 15 20:52:15 2019 +0000
@@ -0,0 +1,404 @@
+#include "mbed.h"
+#include "ReceiverIR.h"
+#include "TB6612FNG.h"
+#include "Ultrasonic.h"
+
+#include "Adafruit_SSD1306.h"
+#include "Adafruit_GFX.h"
+#include "glcdfont.h"
+#define SSD1306_DISPLAYON 0xAF
+#include "WS2812.h"
+#include "PixelArray.h"
+
+#define WS2812_BUF 150
+#define NUM_COLORS 6
+#define NUM_LEDS_PER_COLOR 10
+#define button2 18
+
+// PWMA, AIN1, AIN2, PWMBm, BIN1, BIN2, STBY
+TB6612FNG motorDriver(D6, A0, A1, D5, A3, A2, A5);
+ReceiverIR ir_rx(D4);
+Serial pc(USBTX, USBRX);
+SPI spi(D11,D12,D13);
+DigitalOut spi_cs(D10,1);
+Ultrasonic ultra(D3, D2);
+PixelArray px(WS2812_BUF);
+WS2812 ws(D7, WS2812_BUF, 7, 15, 10, 15);
+
+I2C i2c(D14, D15);
+Adafruit_SSD1306_I2c oled(i2c, D9, 0x78, 64, 128);
+
+Timer timer;
+Timer btimer;
+int cal[5]; //센서 입력 모아놓은 배열
+int maxv = 0; //칼리브레이션 최대값
+int minv = 999; //칼리브레이션 최소값
+float fPwmPeriod; //모터 주기
+float fPwmPulsewidth; //모터 속도
+RemoteIR::Format format;
+uint8_t buf[32]; //리모컨 입력받는 버퍼
+int num; //리모컨 입력 숫자
+int bitcount, decoded; //리모컨 입력 필요변수
+
+float aspeed=0.19;
+float speed=0.19; //모터 속도
+float lspd=0.17; //최소 속도
+float mspd=0.25; //최대 속도
+float tspeed; //임시 속도 변
+
+void setspeed(float a){
+ speed=a;
+ motorDriver.setPwmApulsewidth(speed);
+ motorDriver.setPwmBpulsewidth(speed);
+}
+
+int going=0; //주행 중인지 아닌지 판별
+
+int maxcal(int a[], int k){
+ int q;
+ int maxone = 2;
+ int range = 150;
+ if(a[2]- a[0]>range) maxone = 0;
+ else if(a[2]- a[1]>range) maxone = 1;
+ else if(a[2]- a[3]>range) maxone = 3;
+ else if(a[2]- a[4]>range) maxone = 4;
+ int maxa2 = 250;
+ int mina2 = 100;
+ //if(timer.read() > 15 && maxa2 > a[0] && maxa2 > a[1] && mina2 < a[0] && mina2 < a[1]){
+// if(maxa2 > a[3] && mina2 < a[3] && maxa2 >a[4] && mina2 < a[4]){
+// maxone = 6;
+// }
+// maxone = 5;
+// }
+
+ return maxone;
+}
+
+void moveStop(void){
+ motorDriver.motorB_stop();
+ motorDriver.motorA_stop();
+}
+
+void moveBackward(void){
+ setspeed(speed);
+ motorDriver.motorA_ccw();
+ motorDriver.motorB_ccw();
+ //wait(0.3);
+ //moveStop();
+}
+
+void moveForward(void){
+ setspeed(speed);
+ motorDriver.motorA_cw();
+ motorDriver.motorB_cw();
+ //wait(0.3);
+ //moveStop();
+}
+
+void moveLeft(void){
+ setspeed(speed);
+ motorDriver.motorA_ccw();
+ motorDriver.motorB_cw();
+ wait(0.08);
+ moveStop();
+}
+
+void moveRight(void){
+ setspeed(speed);
+ motorDriver.motorA_cw();
+ motorDriver.motorB_ccw();
+ wait(0.08);
+ moveStop();
+}
+void finishlight(void)
+{
+ ws.useII(WS2812::PER_PIXEL); // use per-pixel intensity scaling
+
+ int colorbuf[NUM_COLORS] = {0x2f0000,0x2f2f00,0x002f00,0x002f2f,0x00002f,0x2f002f};
+
+ for (int i = 0; i < WS2812_BUF; i++) {
+ px.Set(i, colorbuf[(i / NUM_LEDS_PER_COLOR) % NUM_COLORS]);
+ }
+
+ for (int j=0; j<WS2812_BUF; j++) {
+ px.SetI(j%WS2812_BUF, 0xf+(0xf*(j%NUM_LEDS_PER_COLOR)));
+ }
+
+ while (1) {
+ for (int z=WS2812_BUF; z >= 0 ; z--) {
+ ws.write_offsets(px.getBuf(),z,z,z);
+ wait(0.075);
+ }
+ }
+}
+int value;
+int ch = 0;
+int status;
+void drive(void){
+ spi_cs = 0;
+ ultra.trig();
+ ultra.setMode(true);
+ value = spi.write(ch<<12);
+ pc.printf("calibration..\r\n");
+ timer.start();
+
+ //주행시작
+ motorDriver.setPwmApulsewidth(speed);
+ motorDriver.setPwmBpulsewidth(speed);
+ moveForward();
+ while(1){
+ oled.clearDisplay();
+ oled.setTextCursor(0,0);
+ oled.printf("speed: %f\r\n",speed);
+ oled.printf("0: %d, 1: %d\r\n2: %d, 3: %d\r\n4: %d st: %d\r\n",cal[0],cal[1],cal[2],cal[3],cal[4],status);
+ oled.printf("time: %.3f\r\n",timer.read_ms()/1000);
+ oled.display();
+
+ status = maxcal(cal,5);
+ pc.printf("status:%d\r\n");
+ switch(status){
+ //●○○○○, 오른쪽으로 가야함
+ case 4 :
+ setspeed(aspeed);
+ motorDriver.motorA_cw();
+ motorDriver.motorB_ccw();
+ wait(0.08);
+ moveStop();
+ wait(0.08);
+ break;
+
+ //○●○○○, 오른쪽으로 가야함
+ case 3 :
+ setspeed(aspeed);
+ motorDriver.motorA_cw();
+ motorDriver.motorB_ccw();
+ wait(0.08);
+ moveStop();
+ wait(0.08);
+ break;
+
+ //○○●○○, 정주행
+ // 중앙 값이 가장 낮지만 검은 줄이 아니면 (<350) 뒤로 0.5초간 가본다. 그 뒤에 다시 직진.
+ case 2 :
+ speed=aspeed;
+ if(speed<mspd){speed+=0.02;}
+ motorDriver.setPwmApulsewidth(speed);
+ motorDriver.setPwmBpulsewidth(speed);
+ if(cal[2]<350 || btimer.read_ms()>500){moveForward();btimer.reset();btimer.start();}
+ else{
+ if(btimer.read_ms()<500){
+ moveBackward();
+ btimer.reset();
+ btimer.start();
+ }
+
+ }
+
+ break;
+
+ //○○○●○, 왼쪽으로 가야함
+ case 1 :
+ setspeed(aspeed);
+ motorDriver.motorA_ccw();
+ motorDriver.motorB_cw();
+ wait(0.08);
+ moveStop();
+ wait(0.08);
+ break;
+
+ //○○○○●, 왼쪽으로 가야함
+ case 0 :
+ setspeed(aspeed);
+ motorDriver.motorA_ccw();
+ motorDriver.motorB_cw();
+ wait(0.08);
+ moveStop();
+ wait(0.08);
+ break;
+
+// case 5 :
+// speed=1.5;
+// motorDriver.setPwmApulsewidth(speed);
+// motorDriver.setPwmBpulsewidth(speed);
+// moveLeft();
+// moveForward();
+// break;
+
+ case 6 :
+ moveStop();
+ finishlight();
+
+ default :
+ motorDriver.setPwmApulsewidth(speed);
+ motorDriver.setPwmBpulsewidth(speed);
+ }
+
+ //센서 입력 받기
+ for(ch=0;ch<6;ch++){
+ spi_cs = 0;
+ spi.format(16, 0);
+ spi.frequency(2000000);
+ wait_us(2);
+ value = spi.write(ch<<12);
+ value >>= 6;
+ spi_cs = 1;
+ wait_us(21);
+ switch(ch)
+ {
+ case 1 : cal[0] = value;break;
+ case 2 : cal[1] = value;break;
+ case 3 : cal[2] = value;break;
+ case 4 : cal[3] = value;break;
+ case 5 : cal[4] = value;break;
+ }
+ }
+
+ //각종 프린트
+ //if(timer.read()>1){
+ for(ch=0;ch<5;ch++){
+ pc.printf("cal[%d]: %d, ",ch, cal[ch]);
+ if(cal[ch] < minv) minv = cal[ch];
+ if(cal[ch] > maxv) maxv = cal[ch];
+ }
+ pc.printf("\r\n");
+ pc.printf("maxv: %d, minv: %d,\r\n",maxv, minv);
+ pc.printf("maxcal : %d\r\n",status);
+ pc.printf("\r\n");
+ //}
+
+ //장애물 만나면 스탑!!
+ if(ultra.getDistance()<8)
+ {
+ pc.printf("WARNING!\r\n");
+ tspeed = speed;
+ speed=0.2;
+ motorDriver.setPwmApulsewidth(speed);
+ motorDriver.setPwmBpulsewidth(speed);
+ moveBackward();
+ wait(0.2);
+ moveStop();
+ speed=tspeed;
+ motorDriver.setPwmApulsewidth(speed);
+ motorDriver.setPwmBpulsewidth(speed);
+ }
+
+ //리모컨 입력받기
+ if (ir_rx.getState() == ReceiverIR::Received) {
+ bitcount = ir_rx.getData(&format, buf, sizeof(buf) * 8);
+ if (bitcount>0) {
+ decoded=buf[3];
+ num = buf[2];
+ //pc.printf("\r\nDecoded: %X %X %X %X ", buf[0],buf[1],num,buf[3]);
+ pc.printf("\r\nnum: %X %d", num, num);
+ switch(num){
+ case 24:
+ moveForward();
+ break;
+ case 90:
+ moveRight();
+ break;
+ case 82:
+ moveBackward();
+ break;
+ case 8:
+ moveLeft();
+ break;
+ case 21: //속도상승
+ speed+=0.05;
+ motorDriver.setPwmApulsewidth(speed);
+ motorDriver.setPwmBpulsewidth(speed);
+ break;
+ case 7: //속도저하
+ speed-=0.05;
+ motorDriver.setPwmApulsewidth(speed);
+ motorDriver.setPwmBpulsewidth(speed);
+ break;
+ case 28:
+ pc.printf("stop");
+ moveStop();
+ going=0;
+ break;
+ case 68:
+ pc.printf("stop drive\n\r");
+ going=0;
+ break;
+ }
+ }
+ }
+ }
+}
+
+/*
+1 = 12
+2 = 24
+3 = 94
+4 = 8
+5 = 28
+6 = 90
+7 = 66
+8 = 82
+9 = 74
+0 = 22
++100 = 25
++200 = 13
+next = 64
+prev = 68
+vol+ = 21
+vol- = 7
+*/
+int main()
+{
+ pc.printf("HEllO\r\n\r\n");
+ pc.printf("maxv: %d, minv: %d,\r\n",maxv, minv);
+
+ while(1) {
+ if (ir_rx.getState() == ReceiverIR::Received) {
+ bitcount = ir_rx.getData(&format, buf, sizeof(buf) * 8);
+ if (bitcount>0) {
+ decoded=buf[3];
+ num = buf[2];
+ //pc.printf("\r\nDecoded: %X %X %X %X ", buf[0],buf[1],num,buf[3]);
+ pc.printf("\r\nnum: %X %d", num, num);
+ switch(num){
+ case 24:
+ moveForward();
+ break;
+ case 90:
+ moveRight();
+ break;
+ case 82:
+ moveBackward();
+ break;
+ case 8:
+ moveLeft();
+ break;
+ case 21: //속도상승
+ speed+=0.1;
+ motorDriver.setPwmApulsewidth(speed);
+ motorDriver.setPwmBpulsewidth(speed);
+ break;
+ case 7: //속도저하
+ speed-=0.1;
+ motorDriver.setPwmApulsewidth(speed);
+ motorDriver.setPwmBpulsewidth(speed);
+ break;
+ case 28:
+ pc.printf("stop");
+ moveStop();
+ going=0;
+ break;
+ case 64:
+ pc.printf("drive\n\r");
+ going=1;
+ timer.reset();
+ drive();
+ break;
+ case 68:
+ pc.printf("stop drive\n\r");
+ going=0;
+ break;
+ }
+ }
+ }
+ }
+}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/mbed.bld Sat Jun 15 20:52:15 2019 +0000 @@ -0,0 +1,1 @@ +https://os.mbed.com/users/mbed_official/code/mbed/builds/65be27845400 \ No newline at end of file