Having issues making a servo motor work with the press of a button, the sweep example works fine so I know it's not the servo and I can receive LED feedback using the remote.
The code I currently have is one found online but it's not exactly what I want as I would prefer that when the 0xBA45FF00 button is pressed (IR receiver on pin 2), I want the servo (pin 3) to rotate 100 degrees anti-clockwise, wait 3 seconds and then return to it's default state which I assume would be 0 and stay at this until the same button is pressed again and the sequence repeats.
I have been trying to figure this out for days and I'm not getting anywhere. Any help would be appreciated.
#include <IRremote.hpp>
#include <Servo.h>
const byte RECV_PIN = 2;
IRrecv irrecv(RECV_PIN);
Servo myservo;
int pos = 0; // variable to store the servo position
byte position = 90; // range 0-180
boolean newIRdata = false;
unsigned long IRinput;
decode_results results;
void setup()
{
Serial.begin(115200);
myservo.attach(3);
irrecv.enableIRIn(); // Start the receiver
}
void loop() {
if (irrecv.decode(&results))
{
IRinput = results.value;
irrecv.resume(); // Receive the next value
newIRdata = true;
}
if(newIRdata == true)
{
Serial.println(IRinput, HEX);
switch(IRinput)
{
// go to 200
case(0xBA45FF00): // off button
position = 160;
Serial.println(position);
break;
// go to 70
case(0xB847FF00): // mute button
position = 75;
Serial.println(position);
break;
}
IRinput = 0;
newIRdata = false;
}
myservo.write(position);
}
The events you need to deal with are obviously the IR code when you are waiting for the command and then just time passing using millis.
This could be either a very sequential code (in pseudo code)
void loop() {
if (IR signal received) {
move servo to 100°
delay 3000ms
move servo to 0°
}
}
or if you want non blocking code (so that you could still do other stuff while waiting for 3s) you might benefit from studying state machines. Here is a small introduction to the topic: Yet another Finite State Machine introduction
Thank you for your reply. I don't need to do other stuff while waiting for the 3s, so the first code seems to be the answer. I am however confused where this fits in with the code in my first post as I can't get that to work at all at the moment.
well - this is the part where you test if an IR signal was received
and this would be the comparison with 0xBA45FF00
if (results.value == 0xBA45FF00) {
...
}
so something like this (typed here, fully untested)
void loop() {
if (irrecv.decode(&results)) { // we got a command
if (results.value == 0xBA45FF00) { // is it the one expected?
// if yes, perform the expected movement (blocking code, nothing else happens while you are there)
myservo.write(100);
delay(3000);
myservo.write(0);
}
irrecv.resume(); // get ready to receive the next IR value
}
}
Thank you, I've tried adding this on my code but receive the error below, code also below this.
In the serial monitor, it shows that 0xBA45FF00 has been pressed, however the servo doesn't move.
/var/folders/f6/ct6b76g97k1bppnhsz9zgchh0000gn/T//ccIxYInn.ltrans0.ltrans.o: In function `loop':
/private/var/folders/f6/ct6b76g97k1bppnhsz9zgchh0000gn/T/.arduinoIDE-unsaved2024822-31589-2qzgwy.t4y6w/sketch_sep22a/sketch_sep22a.ino:24: undefined reference to `IRrecv::decode(decode_results*)'
collect2: error: ld returned 1 exit status
Multiple libraries were found for "Servo.h"
Used: /Users/*****/Documents/Arduino/libraries/Servo
Not used: /Users/*****/Library/Arduino15/libraries/Servo
exit status 1
Compilation error: exit status 1
#include <IRremote.hpp>
#include <Servo.h>
const byte RECV_PIN = 2;
IRrecv irrecv(RECV_PIN);
Servo myservo;
int pos = 0; // variable to store the servo position
byte position = 90; // range 0-180
boolean newIRdata = false;
unsigned long IRinput;
decode_results results;
void setup()
{
Serial.begin(115200);
myservo.attach(3);
irrecv.enableIRIn(); // Start the receiver
}
void loop() {
if (irrecv.decode(&results)) { // we got a command
if (results.value == 0xBA45FF00) { // is it the one expected?
// if yes, perform the expected movement (blocking code, nothing else happens while you are there)
myservo.write(100);
delay(3000);
myservo.write(0);
}
irrecv.resume(); // get ready to receive the next IR value
}
}
I changed the top of the code to the below and the error doesn't show, however still no luck moving the servo. When I upload, I can hear the servo 'ticking' and once I hit the button, it stops the tick but still no movement.
It says this in the serial monitor:
It seems, that you are using a old version 2.0 code / example.
This version is no longer supported!
#include <IRremote.h>
#include <Servo.h>
const byte RECV_PIN = 2;
IRrecv irrecv(RECV_PIN);
Servo myservo;
int pos = 0; // variable to store the servo position
byte position = 90; // range 0-180
boolean newIRdata = false;
unsigned long IRinput;
decode_results results;
void setup() {
Serial.begin(115200);
myservo.attach(3);
irrecv.enableIRIn(); // Start the receiver
}
void loop() {
if (irrecv.decode(&results)) { // we got a command
if (results.value == 0xBA45FF00) { // is it the one expected?
// if yes, perform the expected movement (blocking code, nothing else happens while you are there)
myservo.write(100);
delay(3000);
myservo.write(0);
}
irrecv.resume(); // get ready to receive the next IR value
}
}
compile the code and launch the simulation and then when you press the power button, it will launch the servo animation
click to see the code
/* ============================================
code is placed under the MIT license
Copyright (c) 2024 J-M-L
For the Arduino Forum : https://forum.arduino.cc/u/j-m-l
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.
===============================================
*/
#include <IRremote.hpp>
#include <Servo.h>
const byte IR_RECEIVE_PIN = 2;
const byte SERVO_PIN = 3;
Servo servo;
void doNothing() {}
void animation() {
Serial.println(F("MOVING TO 100°"));
servo.write(100);
Serial.println(F("WAITING FOR 3s"));
delay(3000);
Serial.println(F("MOVING TO 0°"));
servo.write(0);
Serial.println(F("DONE"));
}
void handleCommand() {
if (IrReceiver.decode()) {
switch (IrReceiver.decodedIRData.command) {
case 162: Serial.println("POWER ➜ ANIMATION"); animation(); break;
case 226: Serial.println("MENU"); doNothing(); break;
case 34: Serial.println("TEST"); doNothing(); break;
case 2: Serial.println("PLUS"); doNothing(); break;
case 194: Serial.println("BACK"); doNothing(); break;
case 224: Serial.println("PREV"); doNothing(); break;
case 168: Serial.println("PLAY"); doNothing(); break;
case 144: Serial.println("NEXT"); doNothing(); break;
case 104: Serial.println("num: 0"); doNothing(); break;
case 152: Serial.println("MINUS"); doNothing(); break;
case 176: Serial.println("key: C"); doNothing(); break;
case 48: Serial.println("num: 1"); doNothing(); break;
case 24: Serial.println("num: 2"); doNothing(); break;
case 122: Serial.println("num: 3"); doNothing(); break;
case 16: Serial.println("num: 4"); doNothing(); break;
case 56: Serial.println("num: 5"); doNothing(); break;
case 90: Serial.println("num: 6"); doNothing(); break;
case 66: Serial.println("num: 7"); doNothing(); break;
case 74: Serial.println("num: 8"); doNothing(); break;
case 82: Serial.println("num: 9"); doNothing(); break;
default: break;
}
IrReceiver.resume();
}
}
void setup() {
Serial.begin(115200);
servo.write(0);
servo.attach(SERVO_PIN);
IrReceiver.begin(IR_RECEIVE_PIN);
Serial.println(F("PRESS THE POWER BUTTON TO LAUNCH THE SERVO ANIMATION"));
}
void loop() {
handleCommand();
}
you'll have to adjust the command codes for your remote.
I've given this code a go on the simulator and it works perfectly, but still no luck with my setup after changing the command code. I can't figure out where this is going wrong.
The servo still makes the clicking sound after I upload to the board.
0 is all the way to one end of servo travel. 180 is all the way to the other. 90 is the midpoint and closest to default, or starting position, which corresponds roughly to 1500 microseconds on a typical servo
Yeah at the moment both are plugged in as I'm forever uploading edited code trying to get it work.
How would I work out the voltage on the jack? The power adaptor is the one below if that helps, could this be a problem then? The sweep example code works with no issue as does the IR decoding, just can't seem to get them to function together.