Skip to content

Instantly share code, notes, and snippets.

@twolfson
Last active July 31, 2019 09:35
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save twolfson/05cc4bdd7a77f41b3a7977545793cbe0 to your computer and use it in GitHub Desktop.
Save twolfson/05cc4bdd7a77f41b3a7977545793cbe0 to your computer and use it in GitHub Desktop.
Proof of concept (potentially final) files for ConeDown sensors

gist-conedown-sensor

Proof of concept (potentially final) files for ConeDown sensors

We're using force-sensitive resistors (FSRs) as sensors to detect presence on our dancefloor tiles. This is an integration between those sensors, an Arduino, and our computer

Getting started

Sensor testing with Arduino

We have a simple Arduino test for multiple sensors. This can be loaded directly into Arduino via the gist-conedown-sensor.ino file

Our circuit is a voltage divider circuit in the following form:

Once the circuit is built and the Arduino sketch is live, look at the Serial Monitor for output

Theory

Resulting voltage when FSR to is open (i.e. infinite resistance):

V_out = 0

Resulting voltage when FSR has slight weight (0.22lbs) (i.e. very high resistance):

V_out = V_in * R_2/(R_1 + R_2)
V_out = 5 * 3.3e3/(7e3 + 3.3e3)
V_out = 1.60 (considered LOW/0)

Resulting voltage when FSR has full weight (22lbs) (i.e. very high resistance):

V_out = V_in * R_2/(R_1 + R_2)
V_out = 5 * 3.3e3/(250 + 3.3e3)
V_out = 4.64 (considered HIGH/1)

Reading sensors via Python

We use the Firmata protocol to use the Arduino directly from our computer

To get an example integration working with Python, perform the following:

  • Inside of Arduino IDE, upload "File -> Examples -> Firmata -> StandardFirmata" to the Arduino UNO
  • Set up a virtual environment for Python to keep dependencies self-contained
    • We recommend virtualenvwrapper which would be used like:
      • Initial creation of virtuale environment: mkvirtualenv gist-conedown-sensor
      • Switching to virtual environment in other shells: workon gist-conedown-sensor
  • Install our dependencies (currently skipping requirements.txt due to simplicity)
    • pip install pyfirmata
  • Run our program (currently using Python 2.7, should work with Python 3.3 or later)
    • python main.py
// Based on https://www.arduino.cc/en/Tutorial/AnalogInput
// Define our variables
int sensorSquarePin = A0;
int sensorLongPin = A1;
bool sensorSquareValue = false;
bool sensorLongValue = false;
void setup() {
// Open serial channel for future printing
Serial.begin(9600);
}
void loop() {
// read the value from the sensor:
sensorSquareValue = digitalRead(sensorSquarePin);
sensorLongValue = digitalRead(sensorLongPin);
Serial.print("Square: ");
Serial.print(sensorSquareValue);
Serial.println();
Serial.print("Long: ");
Serial.print(sensorLongValue);
Serial.println();
}
# Set up via `mkvirtualenv` + `pip install pyfirmata`
# Load our dependencies
import time
from pyfirmata import Arduino, util
# Define our constants
# DEV: If getting "could not open port errors, try `chmod` in https://stackoverflow.com/a/27886201
ARDUINO_PORT = "/dev/ttyACM0"
# Analog values range from 0.0 to 1.0, here's our cutoff
# There's probably a well-defined cutoff somewhere
ANALOG_TO_DIGITAL_LOWER_BOUND = 0.6
# Define our main function
def main():
# Create our board
board = Arduino(ARDUINO_PORT)
# Start an iterator thread to avoid overflowing from data
# https://pypi.org/project/pyFirmata/
it = util.Iterator(board)
it.start()
# Read our pins
# analog_0 = board.get_pin("a:0:i")
pins = [
board.get_pin("d:4:i"),
board.get_pin("d:5:i"),
board.get_pin("d:6:i"),
board.get_pin("d:7:i"),
]
while True:
# Analog reads always return number, can't change easily
# Range is from 0.0 (0V) to 1.0 (5V)
# print("A0: ", analog_0.read() >= ANALOG_TO_DIGITAL_LOWER_BOUND)
# Digital reads always return bool, as we'd like
# DEV: Use int so True/False have constant width (i.e. 0/1 vs True/False (1 character vs 4-5 characters)
print("State: ", [int(pin.read() or False) for pin in pins])
time.sleep(0.250)
# If our program is being run directly, run our `main` function
if __name__ == "__main__":
main()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment