Arduino mega 2560: IR sensor not recognising signal in long running loops - Page 1
Forum section: electronics / general

author: CableTangle
author_rank: Newbie
timestamp: June 16, 2015, 08:47:19 am
content: Hi there,For my project i don't have enough space for buttons, but i want to be able to choose different operating modes, change variables etc. - so the TSOP382 IR photo sensor, an old tv remote and thehttps://github.com/shirriff/Arduino-IRremoteIR library seems like the obvious choice. It's al wired up, the example code for the IR library works as it should and i can receive the different codes without any issues in the example setup.Now, if i upload my actual code it stops working. This is part of my code that fetches the IR signal, and the part of the code is the same as on IRrecvDemo.ino (https://github.com/shirriff/Arduino-IRremote/blob/master/examples/IRrecvDemo/IRrecvDemo.ino)Code:void loop() {// other parts of my own the code here: polling a GPS with tinyGPS, writinng data to an// LCD etc. - polling the GPS and another serial device might take up to ~500 ms sometimes...if (irrecv.decode(&results)) {Serial.println(results.value, HEX);irrecv.resume(); // Receive the next value}}Most of the time it ignores the remote commands all together, sometimes I get the "ffff" signal (= "repeat previous command" if using a NEC remote) and very rarely I get the expected and correct result.I assume this happens because the irrecv.decode is running only about 1/10 of the time Arduino takes to finish each loop and is simply busy with the long running code when the IR command comes in?After looking into the problem a bit further i tried using interrupts (http://www.arduino.cc/en/Reference/AttachInterrupt), hoping it would prioritize my IR commands. However, according to the docs the interrupt service routines must be "short"(?), cannot serve any serial handlers, cannot return anything and seems to be designed to handle a single signal change on a pin only, while the IR remote sends a burst. I tried to avoid the limitations by detaching the interrupt when the signal comes in, storing the ir command in a global variable (to evaluate it in the next loop) and in and then reattach the interrupt again:Code:void setup(){attachInterrupt(1, receiveIr, CHANGE);}static void receiveIr() {detachInterrupt(1); //detach interrup until done listening, otherwise the interrupt gets flooded while receiving IR messagesif (irrecv.decode(&results)) {previousIrCommand = results.value; // store received command in global variable, so it can be evaluated insine the loop later.irrecv.resume(); // Receive the next value}attachInterrupt(1, receiveIr, CHANGE); //done here, get ready for next command}Now it will actually receive something when i press a button on the remote, but it all comes out as "ffff" 90% of the time, no matter which button i push.I tried attaching the IR data pin to the digital pin #3 (Interrupt 1) and #21 (Interrupt 2), both times with the same result.Can i use interrupts here at all, or is the Arduino-IRremote libary already using interrupts internally and i'm just messing it up by attaching my own? Am i missing something obvious, or what would i have to do to reliably receive any IR commands here?

author: DJohn
author_rank: Regular Contributor
timestamp: June 17, 2015, 03:09:10 pm
content: I had a quick look at the code for that library. They're already using interrupts, so you don't need to worry about signals being missed while your code is doing other things (unless any of that code disables the interrupt it's using). It appears to store the time of transitions on the input into a buffer, which decode() (called from your main loop) processes later. It stores transitions until it reaches the end of a message, then stops waiting for you to tell it to resume. If there's more than one message between calls to decode/resume, you'll only get the first.If anything else uses timer 2, that's probably going to be bad. Apart from that, I can't see anything obvious.What happens if you remove the rest of your code, and replace it with the equivalent delay? That'd at least tell you whether the problem is the timing, or some other code doing something that upsets IRremote.

author: linux-works
author_rank: Super Contributor
timestamp: June 17, 2015, 05:20:35 pm
content: don't use interrupts. it already does all the timing it needs.I use the ir library quite a lot (one that I hacked a bit to remove floating point, saving me quite a bit of space).keep your main loop short and be sure not to spend too much time doing any one thing.what ir sender are you using? I've found the sony remotes to be the best for reliability and distance.are you using a 38khz ir receiver? do you have it bypassed with .1 and maybe even 10uf at the ir leads? how long is your cable run from the ir-out to the arduino?is it possible you have pwm or other timers that conflict?