|
| 1 | +// SPDX-FileCopyrightText: 2018 Anne Barela for Adafruit Industries |
| 2 | +// |
| 3 | +// SPDX-License-Identifier: MIT |
| 4 | + |
| 5 | +/******************************************************************* |
| 6 | + SoftServo sketch for Adafruit Trinket. Turn the potentiometer knob |
| 7 | + to set the corresponding position on the servo |
| 8 | + (0 = zero degrees, full = 180 degrees) |
| 9 | + |
| 10 | + Required library is the Adafruit_SoftServo library |
| 11 | + available at https://github.com/adafruit/Adafruit_SoftServo |
| 12 | + The standard Arduino IDE servo library will not work with 8 bit |
| 13 | + AVR microcontrollers like Trinket and Gemma due to differences |
| 14 | + in available timer hardware and programming. We simply refresh |
| 15 | + by piggy-backing on the timer0 millis() counter |
| 16 | + |
| 17 | + Required hardware includes an Adafruit Trinket microcontroller |
| 18 | + a servo motor, and a potentiometer (nominally 1Kohm to 100Kohm |
| 19 | + |
| 20 | + As written, this is specifically for the Trinket although it should |
| 21 | + be Gemma or other boards (Arduino Uno, etc.) with proper pin mappings |
| 22 | + |
| 23 | + Trinket: USB+ Gnd Pin #0 Pin #2 A1 |
| 24 | + Connection: Servo+ - Servo1 Potentiometer wiper |
| 25 | + |
| 26 | + *******************************************************************/ |
| 27 | + |
| 28 | +#include <Adafruit_SoftServo.h> // SoftwareServo (works on non PWM pins) |
| 29 | + |
| 30 | +#define SERVO1PIN 0 // Servo control line (orange) on Trinket Pin #0 |
| 31 | + |
| 32 | +#define POTPIN 1 // Potentiometer sweep (center) on Trinket Pin #2 (Analog 1) |
| 33 | + |
| 34 | +Adafruit_SoftServo myServo1, myServo2; //create TWO servo objects |
| 35 | + |
| 36 | +void setup() { |
| 37 | + // Set up the interrupt that will refresh the servo for us automagically |
| 38 | + OCR0A = 0xAF; // any number is OK |
| 39 | + TIMSK |= _BV(OCIE0A); // Turn on the compare interrupt (below!) |
| 40 | + |
| 41 | + myServo1.attach(SERVO1PIN); // Attach the servo to pin 0 on Trinket |
| 42 | + myServo1.write(90); // Tell servo to go to position per quirk |
| 43 | + delay(15); // Wait 15ms for the servo to reach the position |
| 44 | +} |
| 45 | + |
| 46 | +void loop() { |
| 47 | + int potValue; // variable to read potentiometer |
| 48 | + int servoPos; // variable to convert voltage on pot to servo position |
| 49 | + potValue=analogRead(POTPIN); // Read voltage on potentiometer |
| 50 | + servoPos = map(potValue, 0, 1023, 0, 179); // scale it to use it with the servo (value between 0 and 180) |
| 51 | + myServo1.write(servoPos); // tell servo to go to position |
| 52 | + |
| 53 | + delay(15); // waits 15ms for the servo to reach the position |
| 54 | +} |
| 55 | + |
| 56 | +// We'll take advantage of the built in millis() timer that goes off |
| 57 | +// to keep track of time, and refresh the servo every 20 milliseconds |
| 58 | +// The SIGNAL(TIMER0_COMPA_vect) function is the interrupt that will be |
| 59 | +// Called by the microcontroller every 2 milliseconds |
| 60 | +volatile uint8_t counter = 0; |
| 61 | +SIGNAL(TIMER0_COMPA_vect) { |
| 62 | + // this gets called every 2 milliseconds |
| 63 | + counter += 2; |
| 64 | + // every 20 milliseconds, refresh the servos! |
| 65 | + if (counter >= 20) { |
| 66 | + counter = 0; |
| 67 | + myServo1.refresh(); |
| 68 | + } |
| 69 | +} |
0 commit comments