2 Over complicated desk LED dimmer
3 2016-01-10 Dobrica Pavlinusic <dpavlin@rot13.org>
6 const int led_pin = 13;
7 const int buzzer_pin = 4;
8 const int mosfet_pins[] = { 9, 10, 6 }; // PWM pins: 3,5,6,9,10,11
9 const int ldr_pin = A3; // LDR +5 -- A3 -[10K]- GND
10 const int pir_pin = A2;
13 #define TOUCHPAD 1 // set this to 0 if debugging without touchpad
15 int LDR_SIZE = 1; // 1 number of LDR reading to average
16 int LDR_NOISE = 6; // 6 calibrate LDR noise level
18 #define PIR_TIMEOUT 10 // s
22 PS2 mouse(8, 7); // PS2 synaptics clock, data
24 #define TP_LANDSCAPE 0
27 int mosfet_pwm[] = { 1, 1, 1 }; // initial and current state of mosfet pwm
29 void MOSFET_PWM(int i, int pwm) {
30 analogWrite(mosfet_pins[i], pwm);
31 Serial.print("MOSFET=");
40 Serial.println("setup");
42 pinMode(led_pin, OUTPUT);
43 digitalWrite(led_pin, HIGH); // signal reset
45 pinMode(buzzer_pin, OUTPUT);
47 for(int i=0; i<=2; i++) {
48 pinMode(mosfet_pins[i], OUTPUT);
49 analogWrite(mosfet_pins[i], 0);
52 pinMode(ldr_pin, INPUT);
54 pinMode(pir_pin, INPUT);
57 Serial.println("Synaptics touchpad init");
59 mouse.write(0xff); // reset
60 mouse.read(); // ack byte
61 mouse.read(); // blank */
63 mouse.read(); // blank */
64 mouse.write(0xf0); // remote mode -- send motion data only on $EB (read data) command
66 delayMicroseconds(100);
67 mouse.write(0xe8); // set resolution
68 mouse.read(); // ack byte
69 mouse.write(0x03); // rr ( rr * 64 + ss * 16 + tt * 4 + uu == modebyte )
70 mouse.read(); // ack byte
72 mouse.read(); // ack byte
73 mouse.write(0x00); // ss
74 mouse.read(); // ack byte
76 mouse.read(); // ack byte
77 mouse.write(0x01); // tt
78 mouse.read(); // ack byte
80 mouse.read(); // ack byte
81 mouse.write(0x00); // uu
82 mouse.read(); // ack byte
83 mouse.write(0xf3); // set samplerate 20 (stores mode)
84 mouse.read(); // ack byte
86 mouse.read(); // ack byte
87 delayMicroseconds(100);
91 Serial.print("Commands: b - beep, qwe/asd/zxc - MOSFETs\nLDR = ");
92 int ldr = analogRead(ldr_pin);
95 for(int i=0; i<=2; i++) {
96 analogWrite(mosfet_pins[i], 1);
98 int ldr = analogRead(ldr_pin);
100 analogWrite(mosfet_pins[i], 0);
103 // recall startup values
104 for(int i=0; i<=2; i++) {
105 analogWrite(mosfet_pins[i], mosfet_pwm[i]);
108 digitalWrite(led_pin, LOW);
112 void mosfet(int nr, int value) {
113 int pwm = mosfet_pwm[nr];
114 if ( pwm == value ) {
115 Serial.println("ignored");
118 int sleep = 200 / abs(pwm - value); // changes bigger than 200 (on/off) will be instant
119 int step = pwm < value ? 1 : -1;
120 for(int i=pwm + step; i != value; i += step) {
122 analogWrite(mosfet_pins[nr], i);
125 MOSFET_PWM(nr, value);
126 mosfet_pwm[nr] = value;
130 unsigned int last_cx = 0;
131 unsigned int last_cy = 0;
134 static int ldr_sum = 0;
135 static int ldr_count = 0;
138 long int pir_millis = millis();
140 int vi_nr = 0; // mosfet to fade with vi binadings
149 byte mx; //x coordinate
150 byte my; //y coordinate
151 byte mz; //z pressure value
155 mouse.write(0xeb); // read data
158 mstat1 = mouse.read();
161 mstat2 = mouse.read();
166 // collect the bits for x and y
167 cx = (((mstat2 & 0x10) << 8) | ((mxy & 0x0F) << 8) | mx ); // 1100-5800
168 cy = (((mstat2 & 0x20) << 7) | ((mxy & 0xF0) << 4) | my ); // 800-5000
170 if ( last_cx != cx || last_cy != cy ) {
174 Serial.print(cx, DEC);
175 Serial.print("\tY=");
176 Serial.print(cy, DEC);
177 Serial.print("\tZ=");
178 Serial.print(mz, DEC);
179 if ( cx > 1100 && cy > 800 ) {
181 int nr = ( cx - 1100 ) / (( 5800 - 1100 ) / 3);
182 int pwm = ( cy - 800 ) / (( 5000 - 800 ) / 255);
184 int pwm = ( cx - 1100 ) / (( 5800 - 1100 ) / 255);
185 int nr = ( cy - 800 ) / (( 5000 - 800 ) / 4);
186 if ( nr > 2 ) nr -= 1; // 0 [ 1 2 ] 3 -> 0 1 2
188 pwm -= 1; // allow off
189 Serial.print("\tmosfet = ");
191 Serial.print("\tpwm = ");
193 if ( nr >= 0 && nr <= 2 && pwm >= 0 && pwm <= 255 ) {
194 Serial.println("\tOK");
196 mosfet_pwm[nr] = pwm;
198 Serial.println("\tIGNORED");
205 if (Serial.available()) {
206 digitalWrite(led_pin, HIGH);
207 int in = Serial.read();
210 tone(buzzer_pin, 1800, 100);
212 tone(buzzer_pin, 2200, 100);
215 case 'q': mosfet(0, 255); break;
216 case 'a': mosfet(0, 127); break;
217 case 'z': mosfet(0, 0); break;
218 case 'w': mosfet(1, 255); break;
219 case 's': mosfet(1, 127); break;
220 case 'x': mosfet(1, 0); break;
221 case 'e': mosfet(2, 255); break;
222 case 'd': mosfet(2, 127); break;
223 case 'c': mosfet(2, 0); break;
226 case 'h': vi_nr = ( vi_nr - 1 + 3 ) % 3; Serial.println(vi_nr); break;
227 case 'j': mosfet(vi_nr, (mosfet_pwm[vi_nr]-1+255)%255 ); break;
228 case 'k': mosfet(vi_nr, (mosfet_pwm[vi_nr]+1)%255 ); break;
229 case 'l': vi_nr = ( vi_nr + 1 ) % 3; Serial.println(vi_nr); break;
232 m1 = (m1 + 10) % 255;
233 analogWrite(mosfet1_pin, m1);
234 Serial.print("MOSFET 1 = ");
238 m1 = (m1 - 10) % 255;
239 analogWrite(mosfet1_pin, m1);
240 Serial.print("MOSFET 1 = ");
245 Serial.print("unknown command ");
248 digitalWrite(led_pin, LOW);
251 int ldr = analogRead(ldr_pin);
254 if ( ldr_count > LDR_SIZE ) {
255 ldr = ldr_sum / ldr_count;
259 if ( abs(ldr-last_ldr) > LDR_NOISE ) {
260 Serial.print("LDR = ");
262 last_ldr = ( last_ldr + ldr ) / 2;
267 int pir = digitalRead(pir_pin);
268 if ( pir != last_pir) {
270 Serial.print("PIR = ");
274 long int ms = millis();
276 if (pir_millis > 0 && ms - pir_millis > PIR_TIMEOUT * 1000 ) {
277 Serial.println("PIR timeout, fade-out");
278 pir_millis = -1; // mark that we are in timeout
279 for(int i=0; i<=2; i++) {
284 if (pir_millis < 0) {
285 Serial.println("PIR fade-in after timeout");
286 for(int i=0; i<=2; i++) {
287 MOSFET_PWM(i, mosfet_pwm[i]);