diff options
Diffstat (limited to 'DOC/src/html/ex_ir_remote.html')
-rw-r--r-- | DOC/src/html/ex_ir_remote.html | 253 |
1 files changed, 253 insertions, 0 deletions
diff --git a/DOC/src/html/ex_ir_remote.html b/DOC/src/html/ex_ir_remote.html new file mode 100644 index 0000000..2400a11 --- /dev/null +++ b/DOC/src/html/ex_ir_remote.html @@ -0,0 +1,253 @@ +<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"> +<html> +<head> +<meta name="generator" content="Bluefish 2.2.10" > +<meta content="text/html; charset=utf-8" http-equiv="Content-Type"> +<title>IR remote example</title> +</head> +<body> +<p>The following code shows one way to read an infrared remote +control device (the sort used in TVs and stereo systems).</p> +<h3>SETUP</h3> +<img alt="fritzing diagram" style="width: 200px; height: 317px;" +src="images/ir-fritz.png" align="left" hspace="10">The device used +is a <span itemprop="name">SFH5110 (IR Receiver for remote control, +carrier 38 kHz).<br> +<br></span> Pin 1 (left from front) may be connected to any spare +gpio. Here it's connected via a 4K7 current limiting +resistor. This isn't really needed as the device has an +internal 23K resistor in-line. It does no harm though.<br> +<br> +Pin 2 should be connected to a Pi ground pin.<br> +<br> +Pin 3 should be connected to a Pi 5V pin.<br> +<p>Here pin 1 to gpio7 (P1-26) via a 4K7 resistor, pin 2 to ground +(P1-14), and pin 3 to 5V (P1-2).<br clear="all"></p> +<p><img src="images/ir-photo.jpg" style= +"width: 500px; height: 500px;" alt="photo of set-up"></p> +<h3>CODE</h3> +<code>#include <stdio.h><br> +<br> +#include <pigpio.h><br> +<br> +#define IR_PIN 7<br> +<br> +#define OUTSIDE_CODE 0<br> +#define INSIDE_CODE 1<br> +<br> +#define MIN_MESSAGE_GAP 3000<br> +#define MAX_MESSAGE_END 3000<br> +<br> +#define MAX_TRANSITIONS 500<br> +<br> +/*<br> + using the FNV-1a +hash <br> + + from +http://isthe.com/chongo/tech/comp/fnv/#FNV-param<br> +*/<br> +<br> +#define FNV_PRIME_32 16777619<br> +#define FNV_BASIS_32 2166136261U<br> +<br> +static volatile uint32_t ir_hash = 0;<br> +<br> +typedef struct<br> +{<br> + int state;<br> + int count;<br> + int level;<br> + uint16_t micros[MAX_TRANSITIONS];<br> +} decode_t;<br> +<br> +/* forward declarations */<br> +<br> +void alert(int gpio, int level, uint32_t +tick);<br> +uint32_t getHash(decode_t * decode);<br> +void updateState(decode_t * decode, int +level, uint32_t micros);<br> +<br> +int main(int argc, char * argv[])<br> +{<br> + if (gpioInitialise()<0)<br> + {<br> + return 1 ;<br> + }<br> +<br> + /* IR pin as input */<br> +<br> + gpioSetMode(IR_PIN, PI_INPUT);<br> +<br> + /* 5ms max gap after last pulse */<br> +<br> + gpioSetWatchdog(IR_PIN, 5);<br> +<br> + /* monitor IR level changes */<br> +<br> + gpioSetAlertFunc(IR_PIN, alert);<br> +<br> + while (1)<br> + {<br> + if (ir_hash)<br> + {<br> + /* non-zero means +new decode */<br> + printf("ir code is +%u\ ", ir_hash);<br> + ir_hash = 0;<br> + }<br> +<br> + gpioDelay(100000); /* check remote +10 times per second */<br> + }<br> +<br> + gpioTerminate();<br> +}<br> +<br> +void alert(int gpio, int level, uint32_t tick)<br> +{<br> + static int inited = 0;<br> +<br> + static decode_t activeHigh, activeLow;<br> +<br> + static uint32_t lastTick;<br> +<br> + uint32_t diffTick;<br> +<br> + if (!inited)<br> + {<br> + inited = 1;<br> +<br> + activeHigh.state = OUTSIDE_CODE; +activeHigh.level = PI_LOW;<br> + activeLow.state = +OUTSIDE_CODE; activeLow.level = PI_HIGH;<br> +<br> + lastTick = tick;<br> + return;<br> + }<br> +<br> + diffTick = tick - lastTick;<br> +<br> + if (level != PI_TIMEOUT) lastTick = tick;<br> +<br> + updateState(&activeHigh, level, diffTick);<br> + updateState(&activeLow, level, diffTick);<br> +}<br> +<br> +void updateState(decode_t * decode, int level, uint32_t micros)<br> +{<br> + /*<br> + We are dealing with active high as +well as active low<br> + remotes. Abstract the common +functionality.<br> + */<br> +<br> + if (decode->state == OUTSIDE_CODE)<br> + {<br> + if (level == decode->level)<br> + {<br> + if (micros > +MIN_MESSAGE_GAP)<br> + {<br> + +decode->state = INSIDE_CODE;<br> + +decode->count = 0;<br> + }<br> + }<br> + }<br> + else<br> + {<br> + if (micros > MAX_MESSAGE_END)<br> + {<br> + /* end of message +*/<br> +<br> + /* ignore if last +code not consumed */<br> +<br> + if (!ir_hash) +ir_hash = getHash(decode);<br> +<br> + decode->state = +OUTSIDE_CODE;<br> + }<br> + else<br> + {<br> + if +(decode->count < (MAX_TRANSITIONS-1))<br> + {<br> + +if (level != PI_TIMEOUT)<br> + +decode->micros[decode->count++] = micros;<br> + }<br> + }<br> + }<br> +}<br> +<br> +int compare(unsigned int oldval, unsigned int newval)<br> +{<br> + if (newval < (oldval +* 0.75)) {return 1;}<br> + else if (oldval < (newval * 0.75)) {return 2;}<br> + +else +{return 4;}<br> +}<br> +<br> +uint32_t getHash(decode_t * decode)<br> +{<br> + /* use FNV-1a */<br> +<br> + uint32_t hash;<br> + int i, value;<br> +<br> + if (decode->count < 6) {return 0;}<br> +<br> + hash = FNV_BASIS_32;<br> +<br> + for (i=0; i<(decode->count-2); i++)<br> + {<br> + value = +compare(decode->micros[i], decode->micros[i+2]);<br> +<br> + hash = hash ^ value;<br> + hash = (hash * FNV_PRIME_32);<br> + }<br> +<br> + return hash;<br> +}<br></code> +<h3>BUILD</h3> +<code>cc -o ir_remote ir_remote.c -lpigpio -lrt +-lpthread<br></code> +<h3>RUN</h3> +<code>sudo ./ir_remote</code><br> +<p>A hash code is formed from the level transitions detected during +a remote key press. This is likely to be unique over multiple +remotes and keys.</p> +<p>While the program is running you can capture the waveform using +the notification feature built in to pigpio. Issue the +following commands on the Pi.</p> +<code>pigs no<br> +pig2vcd </dev/pigpio0 >ir.vcd &<br> +pigs nb 0 0x80 # set bits for gpios 7 (0x80)<br></code> +<p>Press a few different remotes and keys. Then enter<br></p> +<code>pigs nc 0</code><br> +<p>The file ir.vcd will contain the captured waveform, which can be +viewed using GTKWave.</p> +<p>Overview</p> +<img src="images/ir-wave-1.png" style= +"width: 600px; height: 100px;" alt="ir remote waveform 1"><br> +<p>Remote A typical waveform</p> +<img src="images/ir-wave-2.png" style= +"width: 600px; height: 100px;" alt="ir remote waveform 2"><br> +<p>Remote B typical waveform</p> +<img style="width: 600px; height: 100px;" alt= +"ir remote waveform 3" src="images/ir-wave-3.png"> +</body> +</html> |