Skip to content

Instantly share code, notes, and snippets.

@donovankeith
Last active October 19, 2017 23:29
Show Gist options
  • Select an option

  • Save donovankeith/7691d7370c1066a68e5a80b6bcc75efb to your computer and use it in GitHub Desktop.

Select an option

Save donovankeith/7691d7370c1066a68e5a80b6bcc75efb to your computer and use it in GitHub Desktop.
Unity Arduino Input/Output
/* Arduino Serial I/O
* Allows you to send simple commands to an arduino and to receive data back.
*
* Source based on: https://www.alanzucconi.com/2015/10/07/how-to-integrate-arduino-with-unity/
*
* ## Setup
* 1. Edit > Player Settings
* 2. .NET Compatibility Level = `.NET 2.0`
*/
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using System.IO.Ports;
public class ArduinoIO : MonoBehaviour {
// User Inputs
[Tooltip("Open Arduino serial monitor, and look for the name of the port at the end of the phrase 'Arduino/Genuino Uno at...")]
public string portName = "COM5";
[Tooltip("The baudrate of the serial port")]
public int baudrate = 9600;
public int outputValue = 0;
// Storage & I/O
private SerialPort stream;
public void Open () {
// Opens the serial port
stream = new SerialPort(portName, baudrate);
stream.ReadTimeout = 20;
stream.Open();
WriteToArduino ("INIT");
//this.stream.DataReceived += new SerialDataReceivedEventHandler(DataReceivedHandler);
}
public void WriteToArduino(string message)
{
// Send the request
stream.WriteLine(message + '\n');
stream.BaseStream.Flush();
}
public string ReadFromArduino()
{
try
{
return stream.ReadLine();
}
catch
{
return null;
}
}
// Use this for initialization
void Start () {
Open ();
}
// Update is called once per frame
void Update () {
WriteToArduino ("DIST");
try{
string arduinoOutput = ReadFromArduino();
outputValue = int.Parse (arduinoOutput);
}
catch{
}
if (outputValue != -1) {
Vector3 immediatePostion = new Vector3 (0.0f, (float)outputValue * 0.1f, 0.0f);
transform.position = Vector3.Lerp(transform.position, immediatePostion, 0.75f);
}
}
}
/* SerialOutput.ino
Outputs simple commands to the Serial port based on the readings from an Ultrasonic Range Sensor
Using: HCS-SRO4
## Commands
- `INIT`: Flashes the Arduino's built-in LED 3, 2, 1 times.
- `DEBUG`: Writes sensor data to Serial in an unending stream.
- `END`: Stops `DEBUG` mode.
- `DIST`: Writes the current distance reading to the stream once.
*/
// Library Imports
#include <NewPing.h> // This is the Ultrasonic Sensor library
#include <RunningMedian.h> // This is a running median filter library
// Hardware Setup
#define BAUD_RATE 9600
const int TRIGGER_PIN = 2; //The pin attached to trig
const int ECHO_PIN = 3; // the pin attached to echco
const int MAX_DISTANCE = 65; // Measured in Centimeters
long distance; // I hope there aren't extra charges! :-P
// Message Properties
const char eomChar = '\n'; // The end of message terminator. Necessary for serial.readStringUntil to prevent timeout
String message;
// Setup Connection
NewPing sonar(TRIGGER_PIN, ECHO_PIN, MAX_DISTANCE); // Define "sonar" instance of Newping with parameters
// Data Smoothing
RunningMedian samples = RunningMedian(15); // Define "samples" instance of RunningMedian with 15 sample parameter
// Debug
bool debug = false;
void setup() {
// Open Serial Connection
Serial.begin(BAUD_RATE);
pinMode(LED_BUILTIN, OUTPUT);
}
void loop()
{
// Reads input from Ultrasonic Rangefinder
// Read bytes from serial buffer if any
if (Serial.available()) {
message = Serial.readStringUntil(eomChar);
if (message == "DIST"){
printDistance();
}
else if (message == "INIT"){
ledCountDown();
}
else if (message == "DEBUG"){
debug = true;
}
else if (message == "END"){
debug = false;
}
}
if (debug) {
printDistance();
}
// Return the current distance measurement in cm
distance = sonar.ping_cm();
// Add current distance measurement to median filter
samples.add(distance);
}
void ledCountDown(){
// Countdown
int flashCount = 3;
int flashPeriod = 200;
int flashBreak = 500;
for (int count=flashCount; count>0; count--)
{
for (int j=0; j<count; j++){
digitalWrite(LED_BUILTIN, HIGH); // turn the LED on (HIGH is the voltage level)
delay(flashPeriod);
digitalWrite(LED_BUILTIN, LOW); // turn the LED off by making the voltage LOW
delay(flashPeriod);
}
delay(flashBreak);
}
}
void printDistance () {
/* Retrieves distance from cached values. Outputs it to the serial port.
* Message code: "DIST"
*/
int cm = samples.getMedian(); //return median distance from filter
if (cm <= MAX_DISTANCE)
Serial.println(cm); //send value if less than 65
else
Serial.println(-1); //else send string
}
@donovankeith

Copy link
Copy Markdown
Author

Added comments. Some minor refactoring. Removed the while(); block in setup().

@donovankeith

Copy link
Copy Markdown
Author

Added realtime printing when "DEBUG" command is sent.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment