2 #include <avr/interrupt.h>
5 #include <DallasTemperature.h>
8 //********************************************************************//
10 #define RF_DATA_OUT_PIN 13
11 #define IR_MOVEMENT_PIN 9
12 #define IR_MOVEMENT_PIN2 12
13 #define ONE_WIRE_PIN 8
14 #define PANIC_BUTTON_PIN 7
15 #define PANICLED_PWM_PIN 6
16 #define BLUELED_PWM_PIN 11
17 #define PHOTO_ANALOGPIN 0
18 //movement is reported if during IR_SAMPLE_DURATION at least IR_TRESHOLD ir signals are detectd
19 #define IR_SAMPLE_DURATION 8000
20 #define IR_TRESHOLD 7500
21 //duration PanicButton needs to be pressed before status change occurs (i.e. for two PanicButton Reports, the buttons needs to be pressed 1000 cycles, releases 1000 cycles and again pressed 1000 cycles)
22 #define PB_TRESHOLD 1000
23 #define PHOTO_SAMPLE_INTERVAL 4000
24 #define IRREMOTE_SEND_PIN 3 //hardcoded in library
25 //WARNING IRremote Lib uses TCCR2
27 OneWire onewire(ONE_WIRE_PIN);
28 DallasTemperature dallas_sensors(&onewire);
29 DeviceAddress onShieldTemp = { 0x10, 0xE7, 0x77, 0xD3, 0x01, 0x08, 0x00, 0x3F };
31 #define TEMPC_OFFSET_ARDUINO_GENEREATED_HEAT
33 //********************************************************************//
34 // IR Codes, 32 bit, NEC
35 const int YAMAHA_CODE_BITS = 32;
36 const unsigned long int YAMAHA_CODE_BASE = 0x0000000005EA10000;
38 const char YAMAHA_POWER_TOGGLE =0xF8; //Power On/Off
39 const char YAMAHA_POWER_OFF =0x78; //Power Off !!!
40 const char YAMAHA_SLEEP =0xEA; //Toggle Sleep 120/90/60/30min or Off
42 const char YAMAHA_CD =0xA8; //Input CD
43 const char YAMAHA_TUNER =0x68; //Input Tuner
44 const char YAMAHA_TAPE =0x18; //Input Toggle Tape/CD
45 const char YAMAHA_DVD_SPDIF =0xE8; //Input Toggle DVD Auto / DVD Analog
46 const char YAMAHA_SAT_SPDIFF =0x2A; //Input Toggle Sat-DTV Auto / Sat-DTV Analog
47 const char YAMAHA_AUX =0xAA; //Input AUX (mode)
48 const char YAMAHA_VCR =0xF0; //Input VCR
49 const char YAMAHA_EXT51DEC =0xE1; //Input Ext. Decoder On/Off
51 const char YAMAHA_TUNER_PLUS =0x08; //Tuner Next Station 1-7 (of A1 - E7)
52 const char YAMAHA_TUNER_MINUS =0x88; //Tuner Prev Station 1-7 (of A1 - E7)
53 const char YAMAHA_TUNER_ABCDE =0x48; //Tuner Next Station Row A-E (of A1 - E7)
55 const char YAMAHA_MUTE =0x38;
56 const char YAMAHA_VOLUME_UP =0x58;
57 const char YAMAHA_VOLUME_DOWN =0xD8;
59 //const char YAMAHA_FRONT_LEVEL_P =0x01; //no function
60 //const char YAMAHA_FRONT_LEVEL_M =0x81; //no function
61 //const char YAMAHA_CENTRE_LEVEL_P =0x41; //no function
62 //const char YAMAHA_CENTRE_LEVEL_M =0xC1; //no function
63 //const char YAMAHA_REAR_LEVEL_P =0x7A; //no function
64 //const char YAMAHA_REAR_LEVEL_M =0xFA; //no function
65 const char YAMAHA_PLUS =0x4A; //unteres Steuerkreuz: Taste Rechts (Plus)
66 const char YAMAHA_MINUS =0xCA; //unteres Steuerkreuz: Taste Links (Minus)
67 const char YAMAHA_MENU =0x39; // Menu: Settings
68 const char YAMAHA_TEST =0xA1; // Test Sounds
69 const char YAMAHA_TIME_LEVEL =0x19; //Settings for Delay, Subwfs, Right Surround, Left Surround, Center
70 const char YAMAHA_TIME_LEVEL2 =0x61; //(also) Settings for Delay, Subwfs, Right Surround, Left Surround, Center
71 const char YAMAHA_TIME_LEVEL3 =0x99; //(also) Settings for Delay, Subwfs, Right Surround, Left Surround, Center
73 const char YAMAHA_EFFECT_TOGGLE =0x6A; //Effect Toggle On/Off
74 const char YAMAHA_PRG_DOWN =0x9A; //Effect/DSP Programm Toggle in down direction
75 const char YAMAHA_PRG_UP =0x1A; //Effect/DSP Programm Toggle in up direction
76 const char YAMAHA_EFFECT1 =0x31; //Effect TV Sports
77 const char YAMAHA_EFFECT2 =0x71; //Effect Rock Concert
78 const char YAMAHA_EFFECT3 =0xB1; //Effect Disco
79 const char YAMAHA_EFFECT4 =0xD1; //Mono Movie
80 const char YAMAHA_EFFECT5 =0x91; //Effect Toggle 70mm Sci-Fi / 70mm Spectacle
81 const char YAMAHA_EFFECT6 =0x51; //Effect Toggle 70mm General / 70mm Adventure
82 const char YAMAHA_P5 =0xFB; //P5 PRT (1 Main Bypass)? (1587674115)
84 //********************************************************************//
91 // offset is number of alphas (0.08ms)
93 const rf_bit_t zero_bit[] = { { 4, 1 },
99 const rf_bit_t one_bit[] = { { 12, 1 },
105 const rf_bit_t float_bit[] = { { 4, 1 },
111 const rf_bit_t sync_bit[] = { { 4, 1 },
115 //WORKS @ alpha=0.0775ms
116 //const rf_bit_t pwm_0_bit[] = { {7, 1}, {24, 0}, { 0, 0 } }; // 1.86ms gesamt: { 0.46ms HIGH , 1.4ms LOW }
117 //const rf_bit_t pwm_1_bit[] = { {18, 1}, {24, 0}, { 0, 0 } }; // 1.86ms gesamt: { 1.4ms HIGH , 0.46ms LOW }
118 //const rf_bit_t pwm_pause_bit[] = { {168, 0}, { 0, 0 } }; // 13ms pause
120 //WORKS @ alpha=0.08ms
121 const rf_bit_t pwm_0_bit[] = { {6, 1}, {23, 0}, { 0, 0 } }; // 1.86ms gesamt: { 0.46ms HIGH , 1.4ms LOW }
122 const rf_bit_t pwm_1_bit[] = { {18, 1}, {23, 0}, { 0, 0 } }; // 1.86ms gesamt: { 1.4ms HIGH , 0.46ms LOW }
123 const rf_bit_t pwm_pause_bit[] = { {162, 0}, { 0, 0 } }; // 13ms pause
125 typedef enum { ZERO = 0, ONE , FLOAT , SYNC , PWM0, PWM1, PWM_PAUSE, WORD_END } adbit_t;
126 typedef byte ad_bit_t;
127 #define MAX_WORD_LEN 27
128 typedef ad_bit_t word_t[MAX_WORD_LEN];
130 const rf_bit_t* bit_defs[] = { zero_bit, one_bit, float_bit, sync_bit, pwm_0_bit, pwm_1_bit, pwm_pause_bit };
136 const ad_bit_t* current_word;
137 byte volatile frame_finished = 1;
161 #define BLACK_A1_ON 16
162 #define BLACK_A1_OFF 17
163 #define BLACK_A2_ON 18
164 #define BLACK_A2_OFF 19
165 #define BLACK_A3_ON 20
166 #define BLACK_A3_OFF 21
168 #define BLACK_B1_ON 22
169 #define BLACK_B1_OFF 23
170 #define BLACK_B2_ON 24
171 #define BLACK_B2_OFF 25
172 #define BLACK_B3_ON 26
173 #define BLACK_B3_OFF 27
175 #define BLACK_C1_ON 28
176 #define BLACK_C1_OFF 29
177 #define BLACK_C2_ON 30
178 #define BLACK_C2_OFF 31
179 #define BLACK_C3_ON 32
180 #define BLACK_C3_OFF 33
182 #define BLACK_D1_ON 34
183 #define BLACK_D1_OFF 35
184 #define BLACK_D2_ON 36
185 #define BLACK_D2_OFF 37
186 #define BLACK_D3_ON 38
187 #define BLACK_D3_OFF 39
189 //SW 0..3 / BT 0..3 / OFF? 1 ON? 0
190 //#define RSL336T_INDEX(SW,BT,OFF) 40+(2*4*SW)+(2*BT)+OFF
192 #define PWM_01 PWM0,PWM1
193 #define PWM_00 PWM0,PWM0
194 #define RSL336T_SWBT_1 PWM_00,PWM_01,PWM_01,PWM_01
195 #define RSL336T_SWBT_2 PWM_01,PWM_00,PWM_01,PWM_01
196 #define RSL336T_SWBT_3 PWM_01,PWM_01,PWM_00,PWM_01
197 #define RSL336T_SWBT_4 PWM_01,PWM_01,PWM_01,PWM_00
199 const word_t words[] = {
200 { ZERO, ZERO, FLOAT, FLOAT, ZERO, ZERO, FLOAT, FLOAT, ZERO, FLOAT, FLOAT, FLOAT, SYNC, WORD_END, WORD_END,WORD_END}, // A1_ON
201 { ZERO, ZERO, FLOAT, FLOAT, ZERO, ZERO, FLOAT, FLOAT, ZERO, FLOAT, FLOAT, ZERO, SYNC, WORD_END, WORD_END,WORD_END}, // A1_OFF
202 { ZERO, ZERO, FLOAT, FLOAT, FLOAT, ZERO, FLOAT, FLOAT, ZERO, FLOAT, FLOAT, FLOAT, SYNC, WORD_END, WORD_END,WORD_END }, // A2_ON
203 { ZERO, ZERO, FLOAT, FLOAT, FLOAT, ZERO, FLOAT, FLOAT, ZERO, FLOAT, FLOAT, ZERO, SYNC, WORD_END, WORD_END,WORD_END }, // A2_OFF
205 { FLOAT, ZERO, FLOAT, FLOAT, ZERO, ZERO, FLOAT, FLOAT, ZERO, FLOAT, FLOAT, FLOAT, SYNC, WORD_END, WORD_END,WORD_END }, // B1_ON
206 { FLOAT, ZERO, FLOAT, FLOAT, ZERO, ZERO, FLOAT, FLOAT, ZERO, FLOAT, FLOAT, ZERO, SYNC, WORD_END, WORD_END,WORD_END }, // B1_OFF
207 { FLOAT, ZERO, FLOAT, FLOAT, FLOAT, ZERO, FLOAT, FLOAT, ZERO, FLOAT, FLOAT, FLOAT, SYNC, WORD_END, WORD_END,WORD_END }, // B2_ON
208 { FLOAT, ZERO, FLOAT, FLOAT, FLOAT, ZERO, FLOAT, FLOAT, ZERO, FLOAT, FLOAT, ZERO, SYNC, WORD_END, WORD_END,WORD_END }, // B2_OFF
210 { ZERO, FLOAT, FLOAT, FLOAT, ZERO, ZERO, FLOAT, FLOAT, ZERO, FLOAT, FLOAT, FLOAT, SYNC, WORD_END, WORD_END,WORD_END }, // C1_ON
211 { ZERO, FLOAT, FLOAT, FLOAT, ZERO, ZERO, FLOAT, FLOAT, ZERO, FLOAT, FLOAT, ZERO, SYNC, WORD_END, WORD_END,WORD_END }, // C1_OFF
212 { ZERO, FLOAT, FLOAT, FLOAT, FLOAT, ZERO, FLOAT, FLOAT, ZERO, FLOAT, FLOAT, FLOAT, SYNC, WORD_END, WORD_END,WORD_END }, // C2_ON
213 { ZERO, FLOAT, FLOAT, FLOAT, FLOAT, ZERO, FLOAT, FLOAT, ZERO, FLOAT, FLOAT, ZERO, SYNC, WORD_END, WORD_END,WORD_END }, // C2_OFF
215 { FLOAT, FLOAT, FLOAT, FLOAT, ZERO, ZERO, FLOAT, FLOAT, ZERO, FLOAT, FLOAT, FLOAT, SYNC, WORD_END, WORD_END,WORD_END }, // D1_ON
216 { FLOAT, FLOAT, FLOAT, FLOAT, ZERO, ZERO, FLOAT, FLOAT, ZERO, FLOAT, FLOAT, ZERO, SYNC, WORD_END, WORD_END,WORD_END }, // D1_OFF
217 { FLOAT, FLOAT, FLOAT, FLOAT, FLOAT, ZERO, FLOAT, FLOAT, ZERO, FLOAT, FLOAT, FLOAT, SYNC, WORD_END, WORD_END,WORD_END }, // D2_ON
218 { FLOAT, FLOAT, FLOAT, FLOAT, FLOAT, ZERO, FLOAT, FLOAT, ZERO, FLOAT, FLOAT, ZERO, SYNC, WORD_END, WORD_END,WORD_END }, // D2_OFF
220 {PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM1,PWM1,PWM0,PWM0,PWM0, PWM_PAUSE, WORD_END}, // BLACK_A1_ON
221 {PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM1,PWM1,PWM0, PWM_PAUSE, WORD_END}, // BLACK_A1_OFF
222 {PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM1,PWM1,PWM0,PWM0,PWM0, PWM_PAUSE, WORD_END}, // BLACK_A2_ON
223 {PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM1,PWM1,PWM0, PWM_PAUSE, WORD_END}, // BLACK_A2_OFF
224 {PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM1,PWM1,PWM0,PWM0,PWM0, PWM_PAUSE, WORD_END}, // BLACK_A3_ON
225 {PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM1,PWM1,PWM0, PWM_PAUSE, WORD_END}, // BLACK_A3_OFF
227 {PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM1,PWM1,PWM0,PWM0,PWM0, PWM_PAUSE, WORD_END}, // BLACK_B1_ON
228 {PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM1,PWM1,PWM0, PWM_PAUSE, WORD_END}, // BLACK_B1_OFF
229 {PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM1,PWM1,PWM0,PWM0,PWM0, PWM_PAUSE, WORD_END}, // BLACK_B2_ON
230 {PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM1,PWM1,PWM0, PWM_PAUSE, WORD_END}, // BLACK_B2_OFF
231 {PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM1,PWM1,PWM0,PWM0,PWM0, PWM_PAUSE, WORD_END}, // BLACK_B3_ON
232 {PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM1,PWM1,PWM0, PWM_PAUSE, WORD_END}, // BLACK_B3_OFF
234 {PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM1,PWM1,PWM0,PWM0,PWM0, PWM_PAUSE, WORD_END}, // BLACK_C1_ON
235 {PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM1,PWM1,PWM0, PWM_PAUSE, WORD_END}, // BLACK_C1_OFF
236 {PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM1,PWM1,PWM0,PWM0,PWM0, PWM_PAUSE, WORD_END}, // BLACK_C2_ON
237 {PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM1,PWM1,PWM0, PWM_PAUSE, WORD_END}, // BLACK_C2_OFF
238 {PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM1,PWM1,PWM0,PWM0,PWM0, PWM_PAUSE, WORD_END}, // BLACK_C3_ON
239 {PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM1,PWM1,PWM0, PWM_PAUSE, WORD_END}, // BLACK_C3_OFF
241 {PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM1,PWM1,PWM0,PWM0,PWM0, PWM_PAUSE, WORD_END}, // BLACK_D1_ON
242 {PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM1,PWM1,PWM0, PWM_PAUSE, WORD_END}, // BLACK_D1_OFF
243 {PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM1,PWM1,PWM0,PWM0,PWM0, PWM_PAUSE, WORD_END}, // BLACK_D2_ON
244 {PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM1,PWM1,PWM0, PWM_PAUSE, WORD_END}, // BLACK_D2_OFF
245 {PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM1,PWM1,PWM0,PWM0,PWM0, PWM_PAUSE, WORD_END}, // BLACK_D3_ON
246 {PWM0,PWM1,PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM1,PWM0,PWM1,PWM1,PWM1,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM0,PWM1,PWM1,PWM0, PWM_PAUSE, WORD_END} // BLACK_D3_OFF
249 //SW 0..3 / BT 0..3 / OFF? 1 ON? 0
250 #define RSL336T_INDEX(SW,BT,OFF) (8*SW)+(2*BT)+OFF
252 #define PWM_01 PWM0,PWM1
253 #define PWM_00 PWM0,PWM0
254 #define RSL336T_SWBT_1 PWM_00,PWM_01,PWM_01,PWM_01
255 #define RSL336T_SWBT_2 PWM_01,PWM_00,PWM_01,PWM_01
256 #define RSL336T_SWBT_3 PWM_01,PWM_01,PWM_00,PWM_01
257 #define RSL336T_SWBT_4 PWM_01,PWM_01,PWM_01,PWM_00
260 // note: code on atmel breaks if array below becomes too big
261 const word_t rsl336T_words[] = {
262 {RSL336T_SWBT_1,RSL336T_SWBT_1,PWM_01,PWM_01,PWM_01,PWM_01,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_I_1_ON
263 {RSL336T_SWBT_1,RSL336T_SWBT_1,PWM_01,PWM_01,PWM_01,PWM_00,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_I_1_OFF
264 {RSL336T_SWBT_1,RSL336T_SWBT_2,PWM_01,PWM_01,PWM_01,PWM_01,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_I_2_ON
265 {RSL336T_SWBT_1,RSL336T_SWBT_2,PWM_01,PWM_01,PWM_01,PWM_00,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_I_2_OFF
266 {RSL336T_SWBT_1,RSL336T_SWBT_3,PWM_01,PWM_01,PWM_01,PWM_01,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_I_3_ON
267 {RSL336T_SWBT_1,RSL336T_SWBT_3,PWM_01,PWM_01,PWM_01,PWM_00,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_I_3_OFF
268 {RSL336T_SWBT_1,RSL336T_SWBT_4,PWM_01,PWM_01,PWM_01,PWM_01,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_I_4_ON
269 {RSL336T_SWBT_1,RSL336T_SWBT_4,PWM_01,PWM_01,PWM_01,PWM_00,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_I_4_OFF
271 {RSL336T_SWBT_2,RSL336T_SWBT_1,PWM_01,PWM_01,PWM_01,PWM_01,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_II_1_ON
272 {RSL336T_SWBT_2,RSL336T_SWBT_1,PWM_01,PWM_01,PWM_01,PWM_00,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_II_1_OFF
273 {RSL336T_SWBT_2,RSL336T_SWBT_2,PWM_01,PWM_01,PWM_01,PWM_01,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_II_2_ON
274 {RSL336T_SWBT_2,RSL336T_SWBT_2,PWM_01,PWM_01,PWM_01,PWM_00,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_II_2_OFF
275 //{RSL336T_SWBT_2,RSL336T_SWBT_3,PWM_01,PWM_01,PWM_01,PWM_01,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_II_3_ON
276 //{RSL336T_SWBT_2,RSL336T_SWBT_3,PWM_01,PWM_01,PWM_01,PWM_00,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_II_3_OFF
277 //{RSL336T_SWBT_2,RSL336T_SWBT_4,PWM_01,PWM_01,PWM_01,PWM_01,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_II_4_ON
278 //{RSL336T_SWBT_2,RSL336T_SWBT_4,PWM_01,PWM_01,PWM_01,PWM_00,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_II_4_OFF
280 //{RSL336T_SWBT_3,RSL336T_SWBT_1,PWM_01,PWM_01,PWM_01,PWM_01,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_III_1_ON
281 //{RSL336T_SWBT_3,RSL336T_SWBT_1,PWM_01,PWM_01,PWM_01,PWM_00,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_III_1_OFF
282 //{RSL336T_SWBT_3,RSL336T_SWBT_2,PWM_01,PWM_01,PWM_01,PWM_01,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_III_2_ON
283 //{RSL336T_SWBT_3,RSL336T_SWBT_2,PWM_01,PWM_01,PWM_01,PWM_00,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_III_2_OFF
284 //{RSL336T_SWBT_3,RSL336T_SWBT_3,PWM_01,PWM_01,PWM_01,PWM_01,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_III_3_ON
285 //{RSL336T_SWBT_3,RSL336T_SWBT_3,PWM_01,PWM_01,PWM_01,PWM_00,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_III_3_OFF
286 //{RSL336T_SWBT_3,RSL336T_SWBT_4,PWM_01,PWM_01,PWM_01,PWM_01,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_III_4_ON
287 //{RSL336T_SWBT_3,RSL336T_SWBT_4,PWM_01,PWM_01,PWM_01,PWM_00,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_III_4_OFF
289 //{RSL336T_SWBT_4,RSL336T_SWBT_1,PWM_01,PWM_01,PWM_01,PWM_01,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_IV_1_ON
290 //{RSL336T_SWBT_4,RSL336T_SWBT_1,PWM_01,PWM_01,PWM_01,PWM_00,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_IV_1_OFF
291 //{RSL336T_SWBT_4,RSL336T_SWBT_2,PWM_01,PWM_01,PWM_01,PWM_01,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_IV_2_ON
292 //{RSL336T_SWBT_4,RSL336T_SWBT_2,PWM_01,PWM_01,PWM_01,PWM_00,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_IV_2_OFF
293 //{RSL336T_SWBT_4,RSL336T_SWBT_3,PWM_01,PWM_01,PWM_01,PWM_01,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_IV_3_ON
294 //{RSL336T_SWBT_4,RSL336T_SWBT_3,PWM_01,PWM_01,PWM_01,PWM_00,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_IV_3_OFF
295 //{RSL336T_SWBT_4,RSL336T_SWBT_4,PWM_01,PWM_01,PWM_01,PWM_01,PWM0, PWM_PAUSE, WORD_END}, // RSL366T_IV_4_ON
296 //{RSL336T_SWBT_4,RSL336T_SWBT_4,PWM_01,PWM_01,PWM_01,PWM_00,PWM0, PWM_PAUSE, WORD_END} // RSL366T_IV_4_OFF
300 //********************************************************************//
305 TCCR1A = 0; // prescaler 1:8, WGM = 4 (CTC)
306 TCCR1B = 1<<WGM12 | 1<<CS11; //
307 // OCR1A = 39; // (1+39)*8 = 320 -> 0.02ms @ 16 MHz -> 1*alpha
308 //default: alpha=0.08
309 OCR1A = 159; // (1+159)*8 = 1280 -> 0.08ms @ 16 MHz -> 1*alpha
310 // OCR1A = 154; // (1+154)*8 = 1240 -> 0.0775ms @ 16 MHz -> 1*alpha
311 // OCR1A = 207; // (1+207)*8 = 1664 -> 0.104ms @ 16 MHz -> 1*alpha
312 TCNT1 = 0; // reseting timer
313 TIMSK1 = 1<<OCIE1A; // enable Interrupt
316 void stop_timer() // stop the timer
319 TCCR1B = 0; // no clock source
320 TIMSK1 = 0; // disable timer interrupt
323 void init_word(const word_t w)
330 if(bit_defs[current_word[bit_cnt]][chunk_cnt].state)
331 digitalWrite(RF_DATA_OUT_PIN, LOW); //neue 12V MosFET Verstärkung invertiert Logik !
333 digitalWrite(RF_DATA_OUT_PIN, HIGH);
338 ISR(TIMER1_COMPA_vect)
341 if(alpha_cnt < bit_defs[current_word[bit_cnt]][chunk_cnt].offset)
345 if(bit_defs[current_word[bit_cnt]][chunk_cnt].offset != 0) {
346 if(bit_defs[current_word[bit_cnt]][chunk_cnt].state)
347 digitalWrite(RF_DATA_OUT_PIN, LOW); //neue 12V MosFET Verstärkung invertiert Logik !
349 digitalWrite(RF_DATA_OUT_PIN, HIGH);
354 if(current_word[bit_cnt] != WORD_END && bit_cnt < MAX_WORD_LEN) {
357 if(bit_defs[current_word[bit_cnt]][chunk_cnt].state)
358 digitalWrite(RF_DATA_OUT_PIN, LOW); //neue 12V MosFET Verstärkung invertiert Logik !
360 digitalWrite(RF_DATA_OUT_PIN, HIGH);
364 digitalWrite(RF_DATA_OUT_PIN, HIGH);
367 if(word_cnt < FRAME_LEN)
368 init_word(current_word);
376 void send_frame(const word_t w)
378 if (frame_finished != 1)
379 for(;;) //wait until sending of previous frame finishes
390 void check_frame_done()
392 if (frame_finished==2)
394 Serial.println("Ok");
400 //********************************************************************//
402 void printTemperature(DeviceAddress deviceAddress)
404 dallas_sensors.requestTemperatures();
405 float tempC = dallas_sensors.getTempC(deviceAddress);
406 //Serial.print("Temp C: ");
407 Serial.println(tempC TEMPC_OFFSET_ARDUINO_GENEREATED_HEAT);
408 //Serial.print(" Temp F: ");
409 //Serial.println(DallasTemperature::toFahrenheit(tempC)); // Converts tempC to Fahrenheit
412 //********************************************************************//
414 unsigned int light_level_mean_ = 0;
415 unsigned int light_sample_time_ = 0;
417 void updateLightLevel(unsigned int pin)
419 light_sample_time_++;
420 if (light_sample_time_ < PHOTO_SAMPLE_INTERVAL)
422 light_sample_time_ = 0;
424 unsigned int value = analogRead(pin);
425 if (value == light_level_mean_)
428 unsigned int diff = abs(value - light_level_mean_);
430 light_level_mean_ = value;
432 light_level_mean_=(unsigned int) ( ((float) light_level_mean_) * 0.90 + ((float)value)*0.10 );
435 void printLightLevel()
437 //Serial.print("Photo: ");
438 Serial.println(light_level_mean_);
441 //********************************************************************//
443 unsigned long wm_start_[3]={0,0,0};
444 bool wait_millis(unsigned long *start_time, unsigned long ms)
448 else if (*start_time > 0)
450 if (millis() < *start_time || millis() > (*start_time) + ms)
460 *start_time=millis();
465 char flash_led_pins_[NUM_LEDS]={BLUELED_PWM_PIN,PANICLED_PWM_PIN};
466 unsigned int flash_led_time_[3]={0,0,0};
467 unsigned int flash_led_brightness_[3]={255,255,255};
468 unsigned int flash_led_delay_[3]={8,8,8};
469 unsigned int flash_led_initial_delay_[3]={0,0,0};
470 void calculate_led_level()
472 for (int ledid = 0; ledid < NUM_LEDS; ledid++)
474 if (flash_led_time_[ledid] == 0)
476 if (wait_millis(wm_start_ + ledid, flash_led_initial_delay_[ledid]))
478 flash_led_initial_delay_[ledid]=0;
479 if (wait_millis(wm_start_ + ledid, flash_led_delay_[ledid]))
481 flash_led_time_[ledid]--;
482 int c = abs(sin(float(flash_led_time_[ledid]) / 100.0)) * flash_led_brightness_[ledid];
483 //int d = abs(sin(float(flash_led_time_) / 100.0)) * flash_led_brightness_;
484 analogWrite(flash_led_pins_[ledid], 255-c);
488 // id: id of LED to flash (0,1)
489 // times: # of times the LED should flash
490 // brightness_divisor: 1: full brightness, 2: half brightness, ...
491 // delay_divisor: 1: slow... 8: fastest
492 // phase_divisor: 0.. same phase; 2.. pi/2 phase, 4.. pi phase, 6.. 3pi/2 phase
493 void flash_led(unsigned int id, unsigned int times, unsigned int brightness_divisor, unsigned int delay_divisor, unsigned int phase_divisor)
497 unsigned int new_flash_led_brightness = 255;
498 unsigned int new_flash_led_delay = 8;
501 analogWrite(flash_led_pins_[id],255); //off
504 if (brightness_divisor > 1) //guard against div by zero
505 new_flash_led_brightness /= brightness_divisor;
506 if (delay_divisor > 1) //guard against div by zero
507 new_flash_led_delay /= delay_divisor;
508 if (flash_led_time_[id] == 0 || new_flash_led_brightness > flash_led_brightness_[id])
509 flash_led_brightness_[id]=new_flash_led_brightness;
510 if (flash_led_time_[id] == 0 || new_flash_led_delay < flash_led_delay_[id])
511 flash_led_delay_[id]=new_flash_led_delay;
512 flash_led_time_[id] += 314*times;
513 flash_led_initial_delay_[id] = flash_led_delay_[id]*314*phase_divisor/8;
516 //********************************************************************//
524 TCCR2A = save_tccr2a; // normal mode
525 TCCR2B = save_tccr2b;
526 //TCNT2 = 256 - (50*(16000000/8/1000000)) + 5;
527 //TCCR2A = 0; // normal mode
531 void send_yamaha_ir_signal(char codebyte)
533 unsigned long int code = codebyte & 0xFF;
535 code |= (0xff ^ codebyte) & 0xFF;
536 code |= YAMAHA_CODE_BASE;
538 //irsend changes PWM Timer Frequency among other things
539 //.. doesn't go well with PWM output using the same timer
540 //.. thus we just set output to 255 so whatever frequency is used, led is off for the duration
541 //analogWrite(BLUELED_PWM_PIN,255); // switch led off
543 irsend.sendNEC(code,YAMAHA_CODE_BITS);
546 analogWrite(BLUELED_PWM_PIN,255); // switch off led again to be sure
547 //is actually not necessary, since we are not multitasking/using interrupts, but just to be sure in case this might change
549 Serial.println("Ok");
552 //********************************************************************//
556 pinMode(RF_DATA_OUT_PIN, OUTPUT);
557 digitalWrite(RF_DATA_OUT_PIN, HIGH);
558 pinMode(IR_MOVEMENT_PIN, INPUT); // set pin to input
559 digitalWrite(IR_MOVEMENT_PIN, LOW); // turn off pullup resistors
560 digitalWrite(IR_MOVEMENT_PIN2, LOW); // turn off pullup resistors
561 pinMode(PANIC_BUTTON_PIN, INPUT); // set pin to input
562 digitalWrite(PANIC_BUTTON_PIN, LOW); // turn of pullup resistors
563 analogWrite(PANICLED_PWM_PIN,255);
564 analogWrite(BLUELED_PWM_PIN,255); //pwm sink(-) instead of pwm + (better for mosfets)
565 pinMode(IRREMOTE_SEND_PIN, OUTPUT);
566 digitalWrite(IRREMOTE_SEND_PIN, HIGH);
571 onewire.reset_search();
572 dallas_sensors.begin();
573 //in case we change temp sensor:
574 if (!dallas_sensors.getAddress(onShieldTemp, 0))
575 Serial.println("Error: Unable to find address for Device 0");
576 dallas_sensors.setResolution(onShieldTemp, 9);
578 //save prev timer states:
580 save_tccr2a = TCCR2A; // normal mode
581 save_tccr2b = TCCR2B;
584 unsigned int ir_time=IR_SAMPLE_DURATION;
585 unsigned int ir_count=0;
586 unsigned int ir_count2=0;
587 boolean pb_last_state=0;
589 boolean pb_postth_state=0;
590 unsigned int pb_time=0;
592 void sensorEchoCommand(char command)
594 Serial.print("Sensor ");
595 Serial.print(command);
602 ir_count += (digitalRead(IR_MOVEMENT_PIN) == HIGH);
603 ir_count2 += (digitalRead(IR_MOVEMENT_PIN2) == HIGH);
605 if (pb_time < PB_TRESHOLD)
607 pb_state=(digitalRead(PANIC_BUTTON_PIN) == HIGH);
611 if (ir_count >= IR_TRESHOLD || ir_count2 >= IR_TRESHOLD)
613 flash_led(0, 1, 8, 1, 0 );
614 Serial.println("movement");
616 ir_time=IR_SAMPLE_DURATION;
621 if (pb_state == pb_last_state && pb_time >= PB_TRESHOLD)
623 if (pb_state && ! pb_postth_state)
626 Serial.println("PanicButton");
627 flash_led(0, 28, 1, 4, 0 );
628 flash_led(1, 28, 1, 4, 4 );
633 else if (pb_state != pb_last_state)
636 pb_last_state=pb_state;
639 updateLightLevel(PHOTO_ANALOGPIN);
640 calculate_led_level();
643 if(Serial.available()) {
644 char command = Serial.read();
647 send_frame(words[A1_ON]);
648 else if(command == 'a')
649 send_frame(words[A1_OFF]);
650 else if(command == 'B')
651 send_frame(words[A2_ON]);
652 else if(command == 'b')
653 send_frame(words[A2_OFF]);
655 else if(command == 'C')
656 send_frame(words[B1_ON]);
657 else if(command == 'c')
658 send_frame(words[B1_OFF]);
659 else if(command == 'D')
660 send_frame(words[B2_ON]);
661 else if(command == 'd')
662 send_frame(words[B2_OFF]);
664 else if(command == 'E')
665 send_frame(words[C1_ON]);
666 else if(command == 'e')
667 send_frame(words[C1_OFF]);
668 else if(command == 'F')
669 send_frame(words[C2_ON]);
670 else if(command == 'f')
671 send_frame(words[C2_OFF]);
673 else if(command == 'G')
674 send_frame(words[D1_ON]);
675 else if(command == 'g')
676 send_frame(words[D1_OFF]);
677 else if(command == 'H')
678 send_frame(words[D2_ON]);
679 else if(command == 'h')
680 send_frame(words[D2_OFF]);
682 else if(command == 'I')
683 send_frame(words[BLACK_A1_ON]);
684 else if(command == 'i')
685 send_frame(words[BLACK_A1_OFF]);
686 else if(command == 'J')
687 send_frame(words[BLACK_A2_ON]);
688 else if(command == 'j')
689 send_frame(words[BLACK_A2_OFF]);
690 else if(command == 'K')
691 send_frame(words[BLACK_A3_ON]);
692 else if(command == 'k')
693 send_frame(words[BLACK_A3_OFF]);
695 else if(command == 'L')
696 send_frame(words[BLACK_B1_ON]);
697 else if(command == 'l')
698 send_frame(words[BLACK_B1_OFF]);
699 else if(command == 'M')
700 send_frame(words[BLACK_B2_ON]);
701 else if(command == 'm')
702 send_frame(words[BLACK_B2_OFF]);
703 else if(command == 'N')
704 send_frame(words[BLACK_B3_ON]);
705 else if(command == 'n')
706 send_frame(words[BLACK_B3_OFF]);
708 else if(command == 'O')
709 send_frame(words[BLACK_C1_ON]);
710 else if(command == 'o')
711 send_frame(words[BLACK_C1_OFF]);
712 else if(command == 'P')
713 send_frame(words[BLACK_C2_ON]);
714 else if(command == 'p')
715 send_frame(words[BLACK_C2_OFF]);
716 else if(command == 'Q')
717 send_frame(words[BLACK_C3_ON]);
718 else if(command == 'q')
719 send_frame(words[BLACK_C3_OFF]);
721 else if(command == 'R')
722 send_frame(words[BLACK_D1_ON]);
723 else if(command == 'r')
724 send_frame(words[BLACK_D1_OFF]);
725 else if(command == 'S')
726 send_frame(words[BLACK_D2_ON]);
727 else if(command == 's')
728 send_frame(words[BLACK_D2_OFF]);
729 else if(command == 'T')
730 send_frame(words[BLACK_D3_ON]);
731 else if(command == 't')
732 send_frame(words[BLACK_D3_OFF]);
734 else if (command == 'U')
735 send_frame(rsl336T_words[RSL336T_INDEX(0,0,0)]);
736 else if (command == 'u')
737 send_frame(rsl336T_words[RSL336T_INDEX(0,0,1)]);
738 else if (command == 'V')
739 send_frame(rsl336T_words[RSL336T_INDEX(0,1,0)]);
740 else if (command == 'v')
741 send_frame(rsl336T_words[RSL336T_INDEX(0,1,1)]);
742 else if (command == 'W')
743 send_frame(rsl336T_words[RSL336T_INDEX(0,2,0)]);
744 else if (command == 'w')
745 send_frame(rsl336T_words[RSL336T_INDEX(0,2,1)]);
746 else if (command == 'X')
747 send_frame(rsl336T_words[RSL336T_INDEX(0,3,0)]);
748 else if (command == 'x')
749 send_frame(rsl336T_words[RSL336T_INDEX(0,3,1)]);
750 else if (command == 'Y')
751 send_frame(rsl336T_words[RSL336T_INDEX(1,0,0)]);
752 else if (command == 'y')
753 send_frame(rsl336T_words[RSL336T_INDEX(1,0,1)]);
754 else if (command == 'Z')
755 send_frame(rsl336T_words[RSL336T_INDEX(1,1,0)]);
756 else if (command == 'z')
757 send_frame(rsl336T_words[RSL336T_INDEX(1,1,1)]);
759 else if(command == '*')
761 sensorEchoCommand(command);
762 printTemperature(onShieldTemp);
764 else if(command == '?')
766 sensorEchoCommand(command);
769 else if (command == '^')
771 //flash_led(1, 1, 2, 1, 0);
772 flash_led(1, 1, 1, 1, 0);
773 Serial.println("Ok");
775 else if (command == '&')
777 flash_led(0, 1, 2, 1, 0);
778 Serial.println("Ok");
780 else if (command == '1')
781 send_yamaha_ir_signal(YAMAHA_CD);
782 else if (command == '2')
783 send_yamaha_ir_signal(YAMAHA_TUNER);
784 else if (command == '3')
785 send_yamaha_ir_signal(YAMAHA_TAPE);
786 else if (command == '4')
787 send_yamaha_ir_signal(YAMAHA_DVD_SPDIF);
788 else if (command == '5')
789 send_yamaha_ir_signal(YAMAHA_SAT_SPDIFF);
790 else if (command == '6')
791 send_yamaha_ir_signal(YAMAHA_VCR);
792 // else if (command == '7')
793 // send_yamaha_ir_signal();
794 else if (command == '8')
795 send_yamaha_ir_signal(YAMAHA_AUX);
796 else if (command == '9')
797 send_yamaha_ir_signal(YAMAHA_EXT51DEC);
798 else if (command == '0')
799 send_yamaha_ir_signal(YAMAHA_TEST);
800 else if (command == '/')
801 send_yamaha_ir_signal(YAMAHA_TUNER_ABCDE);
802 else if (command == '\\')
803 send_yamaha_ir_signal(YAMAHA_EFFECT_TOGGLE);
804 else if (command == '-')
805 send_yamaha_ir_signal(YAMAHA_TUNER_MINUS);
806 else if (command == '+')
807 send_yamaha_ir_signal(YAMAHA_TUNER_PLUS);
808 else if (command == ':')
809 send_yamaha_ir_signal(YAMAHA_POWER_OFF);
810 else if (command == '.')
811 send_yamaha_ir_signal(YAMAHA_POWER_TOGGLE);
812 else if (command == ';')
813 send_yamaha_ir_signal(YAMAHA_VOLUME_UP);
814 else if (command == ',')
815 send_yamaha_ir_signal(YAMAHA_VOLUME_DOWN);
816 else if (command == '_')
817 send_yamaha_ir_signal(YAMAHA_MUTE);
818 else if (command == '#')
819 send_yamaha_ir_signal(YAMAHA_MENU);
820 else if (command == '"')
821 send_yamaha_ir_signal(YAMAHA_PLUS);
822 else if (command == '!')
823 send_yamaha_ir_signal(YAMAHA_MINUS);
824 else if (command == '=')
825 send_yamaha_ir_signal(YAMAHA_TIME_LEVEL);
826 else if (command == '$')
827 send_yamaha_ir_signal(YAMAHA_PRG_DOWN);
828 else if (command == '%')
829 send_yamaha_ir_signal(YAMAHA_PRG_UP);
830 else if (command == '(')
831 send_yamaha_ir_signal(YAMAHA_SLEEP);
832 else if (command == ')')
833 send_yamaha_ir_signal(YAMAHA_P5);
835 Serial.println("Error: unknown command");