Close Menu
  • Articles
    • Learn Electronics
    • Product Review
    • Tech Articles
  • Electronics Circuits
    • 555 Timer Projects
    • Op-Amp Circuits
    • Power Electronics
  • Microcontrollers
    • Arduino Projects
    • STM32 Projects
    • AMB82-Mini IoT AI Camera
    • BLE Projects
  • IoT Projects
    • ESP8266 Projects
    • ESP32 Projects
    • ESP32 MicroPython
    • ESP32-CAM Projects
    • LoRa/LoRaWAN Projects
  • Raspberry Pi
    • Raspberry Pi Projects
    • Raspberry Pi Pico Projects
    • Raspberry Pi Pico W Projects
  • Electronics Calculator
Facebook X (Twitter) Instagram
  • About Us
  • Disclaimer
  • Privacy Policy
  • Contact Us
  • Advertise With Us
Facebook X (Twitter) Instagram Pinterest YouTube LinkedIn
How To Electronics
  • Articles
    • Learn Electronics
    • Product Review
    • Tech Articles
  • Electronics Circuits
    • 555 Timer Projects
    • Op-Amp Circuits
    • Power Electronics
  • Microcontrollers
    • Arduino Projects
    • STM32 Projects
    • AMB82-Mini IoT AI Camera
    • BLE Projects
  • IoT Projects
    • ESP8266 Projects
    • ESP32 Projects
    • ESP32 MicroPython
    • ESP32-CAM Projects
    • LoRa/LoRaWAN Projects
  • Raspberry Pi
    • Raspberry Pi Projects
    • Raspberry Pi Pico Projects
    • Raspberry Pi Pico W Projects
  • Electronics Calculator
How To Electronics
Home » Interfacing APDS9960 Gesture & RGB Color Sensor with Arduino
Arduino Projects

Interfacing APDS9960 Gesture & RGB Color Sensor with Arduino

Mamtaz AlamBy Mamtaz AlamUpdated:January 14, 20232 Comments4 Mins Read
Share Facebook Twitter LinkedIn Telegram Reddit WhatsApp
APDS9960 Arduino Interfacing
Share
Facebook Twitter LinkedIn Pinterest Email Reddit Telegram WhatsApp

Overview: APDS9960 Gesture RGB Proximity Sensor & Arduino Interfacing

In this post, we will learn Interfacing of APDS9960 Gesture, RGB & Proximity Sensor with Arduino and OLED Display. The APDS9960 Sensor offers ambient light and color (as clear, red, green, and blue) measuring as well as proximity detection, and gesture sensing.

The Touchless gestures are the new frontier in the world of human-machine interfaces. By swiping your hand over a sensor, you can control a computer, microcontroller, robot, etc. Earlier we learned about the Gesture Mechanism using Gesture Controlled Robot. Similarly we used TC3200 Color Sensor for RGB Color Detection & also the PAJ7620 sensor for 9 Gesture Detection. The Proximity Sensor can also be used for Distance Sensing.

In this tutorial, we will learn an overview of the APDS9960 sensor and interfacing it with Arduino UNO Board. To begin, we’ll go over each of the pins on the breakout board and their function. Then we will interface the sensor via I2C pins. We will measure the Gestures directions like left, right, up, down, near, and far. We will then use this sensor as an RGB Color Detector and also Proximity Sensing.


Bill of Materials

The following are the components required for making APDS9960 Arduino based project. All the components can be easily purchased from Amazon. The component purchase link is given as well.

S.N.Components NameQuantityPurchase Links
1Arduino Nano Board1Amazon | AliExpress
20.96" I2C OLED Display1Amazon | AliExpress
3APDS9960 Sensor1Amazon | AliExpress
4Connecting Wires10Amazon | AliExpress
5Breadboard1Amazon | AliExpress



APDS9960 Proximity, Light, RGB & Gesture Sensor

Overview

The APDS-9960 is a multifunction sensor which can detect gestures, ambient light, RGB Color & values in light.

APDS9960 Sensor

This sensor consists of four photodiodes. These photodiodes detect the reflected IR energy which is transmitted by an on-board LED. So whenever any gesture is performed then this IR energy gets obstructed and reflects back to the sensor, now the sensor detects the velocity and direction information and converts it into digital information. APDS-9960 also has a detection range of 4 to 8 inches (10 to 20 cm).

Architecture

This sensor works on I2C communication protocol. It consumes 1µA current and powered by 3.3V so be careful and do not connect it with 5V pin. The INT pin here is interrupt pin, which is used to drive the I2C communication.

APDS9960 Architecture

The architecture of the gesture engine features automatic activation (based on Proximity engine results), ambient light subtraction, cross-talk cancelation, dual 8-bit data converters, power-saving inter-conversion delay, 32-dataset FIFO, and interrupt-driven I2C communication. Power consumption and noise are minimized with adjustable IR LED timing.

APDS9960 Circuit

Pinouts

The APDS9960 sensor has 6 pins. Following are the function of pins.



Interfacing APDS9960 Sensor with Arduino

We will be using the Arduino UNO Board for interfacing the APDS9960 Sensor. We must use 3.3V to power the sensor. If we try to use a 5V power supply we may risk damaging the APDS-9960.

APDS9960 RGB Color Sensor Arduino

Connect the SDA Pin to A4 of Arduino & SCL to A5. Connect its INT pin to D2. We are leaving VL on the breakout board unconnected.

Gesture Sensor Arduino

Note: The APDS9960 Sensor doesn’t work with few Arduino Boards like Arduino Nano.


Installing APDS9960 on Arduino IDE

The Arduino library for APDS9960 is created by Sparkfun. The library makes the APDS-9960 easy to use.

To install the library, go to the Library Manager in Arduino IDE & install the following Sparkfun library as shown in the image below.


Gesture Sensing Example Code

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
#include <Wire.h>
#include <SparkFun_APDS9960.h>
 
#define APDS9960_INT    2 // Needs to be an interrupt pin
 
// Global Variables
SparkFun_APDS9960 apds = SparkFun_APDS9960();
int isr_flag = 0;
 
void setup() {
 
  // Initialize Serial port
  Serial.begin(9600);
  Serial.println();
  Serial.println(F("--------------------------------"));
  Serial.println(F("APDS-9960 - GestureTest"));
  Serial.println(F("--------------------------------"));
 
  // Initialize interrupt service routine
  attachInterrupt(0, interruptRoutine, FALLING);
 
  // Initialize APDS-9960 (configure I2C and initial values)
  if ( apds.init() ) {
    Serial.println(F("APDS-9960 initialization complete"));
  } else {
    Serial.println(F("Something went wrong during APDS-9960 init!"));
  }
 
  // Start running the APDS-9960 gesture sensor engine
  if ( apds.enableGestureSensor(true) ) {
    Serial.println(F("Gesture sensor is now running"));
  } else {
    Serial.println(F("Something went wrong during gesture sensor init!"));
  }
}
 
void loop() {
  if( isr_flag == 1 ) {
    detachInterrupt(0);
    handleGesture();
    isr_flag = 0;
    attachInterrupt(0, interruptRoutine, FALLING);
  }
}
 
void interruptRoutine() {
  isr_flag = 1;
}
 
void handleGesture() {
    if ( apds.isGestureAvailable() ) {
    switch ( apds.readGesture() ) {
      case DIR_UP:
        Serial.println("UP");
        break;
      case DIR_DOWN:
        Serial.println("DOWN");
        break;
      case DIR_LEFT:
        Serial.println("LEFT");
        break;
      case DIR_RIGHT:
        Serial.println("RIGHT");
        break;
      case DIR_NEAR:
        Serial.println("NEAR");
        break;
      case DIR_FAR:
        Serial.println("FAR");
        break;
      default:
        Serial.println("NONE");
    }
  }
}

After uploading the code swipe your hand to left, right, forward, backward, near, far. The Serial Monitor will display the Gesture data whenever an interrupt is detected.




Color Sensing Example Code

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
#include <Wire.h>
#include <SparkFun_APDS9960.h>
 
// Global Variables
SparkFun_APDS9960 apds = SparkFun_APDS9960();
uint16_t ambient_light = 0;
uint16_t red_light = 0;
uint16_t green_light = 0;
uint16_t blue_light = 0;
 
void setup() {
  
  // Initialize Serial port
  Serial.begin(9600);
  Serial.println();
  Serial.println(F("--------------------------------"));
  Serial.println(F("APDS-9960 - ColorSensor"));
  Serial.println(F("--------------------------------"));
  
  // Initialize APDS-9960 (configure I2C and initial values)
  if ( apds.init() ) {
    Serial.println(F("APDS-9960 initialization complete"));
  } else {
    Serial.println(F("Something went wrong during APDS-9960 init!"));
  }
  
  // Start running the APDS-9960 light sensor (no interrupts)
  if ( apds.enableLightSensor(false) ) {
    Serial.println(F("Light sensor is now running"));
  } else {
    Serial.println(F("Something went wrong during light sensor init!"));
  }
  
  // Wait for initialization and calibration to finish
  delay(500);
}
 
void loop() {
  
  // Read the light levels (ambient, red, green, blue)
  if (  !apds.readAmbientLight(ambient_light) ||
        !apds.readRedLight(red_light) ||
        !apds.readGreenLight(green_light) ||
        !apds.readBlueLight(blue_light) ) {
    Serial.println("Error reading light values");
  } else {
    Serial.print("Ambient: ");
    Serial.print(ambient_light);
    Serial.print(" Red: ");
    Serial.print(red_light);
    Serial.print(" Green: ");
    Serial.print(green_light);
    Serial.print(" Blue: ");
    Serial.println(blue_light);
  }
  
  // Wait 1 second before next reading
  delay(1000);
}

Now in order to see the change in color frequency, keep different color objects in front of the Sensor. The Serial Monitor will display the value of Red, Green, Blue Color along with the Ambient Color value.


Proximity Sensing Example Code

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
#include <Wire.h>
#include <SparkFun_APDS9960.h>
 
// Global Variables
SparkFun_APDS9960 apds = SparkFun_APDS9960();
uint8_t proximity_data = 0;
 
void setup() {
  
  // Initialize Serial port
  Serial.begin(9600);
  Serial.println();
  Serial.println(F("------------------------------------"));
  Serial.println(F("APDS-9960 - ProximitySensor"));
  Serial.println(F("------------------------------------"));
  
  // Initialize APDS-9960 (configure I2C and initial values)
  if ( apds.init() ) {
    Serial.println(F("APDS-9960 initialization complete"));
  } else {
    Serial.println(F("Something went wrong during APDS-9960 init!"));
  }
  
  // Adjust the Proximity sensor gain
  if ( !apds.setProximityGain(PGAIN_2X) ) {
    Serial.println(F("Something went wrong trying to set PGAIN"));
  }
  
  // Start running the APDS-9960 proximity sensor (no interrupts)
  if ( apds.enableProximitySensor(false) ) {
    Serial.println(F("Proximity sensor is now running"));
  } else {
    Serial.println(F("Something went wrong during sensor init!"));
  }
}
 
void loop() {
  
  // Read the proximity value
  if ( !apds.readProximity(proximity_data) ) {
    Serial.println("Error reading proximity value");
  } else {
    Serial.print("Proximity: ");
    Serial.println(proximity_data);
  }
  
  // Wait 250 ms before next reading
  delay(250);
}

Now you can use the sensor as Proximity Distance Detection as well. For that, put your hand near and far and at a particular distance from the Sensor, the distance will be displayed on the Serial Monitor.




Interfacing APDS9960 Gesture Sensor with Arduino OLED Display

Now let us add an extra I2C OLED Display to the circuit, so that we can view the Gesture Data on OLED Screen. So make a connection as shown in the figure below.

APDS9960 Gesture Sensor with Arduino OLED Display

Source Code

Before uploading code add these two library for OLED Display.

  1. Adafruit GFX Library: Download
  2. SSD1306 Library: Download

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
#include <Wire.h>
#include <SparkFun_APDS9960.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>
 
#define APDS9960_INT    2 // Needs to be an interrupt pin
 
 
#define SCREEN_WIDTH 128    // OLED display width, in pixels
#define SCREEN_HEIGHT 64    // OLED display height, in pixels
#define OLED_RESET 4        // Reset pin # (or -1 if sharing Arduino reset pin)
Adafruit_SSD1306 display(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, OLED_RESET);
 
#define LOGO_HEIGHT   64
#define LOGO_WIDTH    64
static const unsigned char PROGMEM myleft[] =
{
  0x45, 0x45, 0x45, 0xff,   /*Color of index 0*/
  0xe9, 0xea, 0xe9, 0xff,   /*Color of index 1*/
 
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xdf, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xef, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xe7, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xe3, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xe1, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xe0, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xd0, 0x7f,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xe0, 0x7f,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf0, 0x3f,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf0, 0x3f,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf8, 0x1f,
  0xff, 0xff, 0xff, 0xe7, 0xff, 0xff, 0xf8, 0x1f,
  0xff, 0xff, 0xff, 0xc7, 0xff, 0xff, 0xfc, 0x0f,
  0xff, 0xff, 0xff, 0x87, 0xff, 0xff, 0xfc, 0x0f,
  0xff, 0xff, 0xff, 0x07, 0xff, 0xff, 0xfe, 0x0f,
  0xff, 0xff, 0xfe, 0x07, 0xff, 0xff, 0xfe, 0x07,
  0xff, 0xff, 0xf8, 0x00, 0x00, 0x00, 0xfe, 0x07,
  0xff, 0xff, 0xf0, 0x00, 0x00, 0x00, 0xfe, 0x07,
  0xff, 0xff, 0xe0, 0x00, 0x00, 0x00, 0xfe, 0x07,
  0xff, 0xff, 0xc0, 0x00, 0x00, 0x00, 0xff, 0x03,
  0xff, 0xff, 0x80, 0x00, 0x00, 0x00, 0xff, 0x03,
  0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0xff, 0x03,
  0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0xff, 0x03,
  0xff, 0xff, 0x80, 0x00, 0x00, 0x00, 0xff, 0x03,
  0xff, 0xff, 0xc0, 0x00, 0x00, 0x00, 0xff, 0x03,
  0xff, 0xff, 0xe0, 0x00, 0x00, 0x00, 0xfe, 0x03,
  0xff, 0xff, 0xf0, 0x00, 0x00, 0x00, 0xfe, 0x03,
  0xff, 0xff, 0xf8, 0x00, 0x00, 0x00, 0xfe, 0x07,
  0xff, 0xff, 0xfc, 0x07, 0xff, 0xff, 0xfe, 0x07,
  0xff, 0xff, 0xfe, 0x07, 0xff, 0xff, 0xfc, 0x07,
  0xff, 0xff, 0xff, 0x87, 0xff, 0xff, 0xfc, 0x07,
  0xff, 0xff, 0xff, 0xc7, 0xff, 0xff, 0xfc, 0x07,
  0xff, 0xff, 0xff, 0xe7, 0xff, 0xff, 0xf8, 0x0f,
  0xff, 0xff, 0xff, 0xf7, 0xff, 0xff, 0xf8, 0x0f,
  0xff, 0xef, 0xff, 0xff, 0xff, 0xff, 0xf0, 0x1f,
  0xff, 0xef, 0xff, 0xff, 0xff, 0xff, 0xe0, 0x1f,
  0xff, 0xf7, 0xff, 0xff, 0xff, 0xff, 0xe0, 0x1f,
  0xff, 0xf3, 0xff, 0xff, 0xff, 0xff, 0xc0, 0x3f,
  0xff, 0xf9, 0xff, 0xff, 0xff, 0xff, 0x80, 0x7f,
  0xff, 0xfc, 0xff, 0xff, 0xff, 0xff, 0x00, 0x7f,
  0xff, 0x7c, 0x7f, 0xff, 0xff, 0xfe, 0x00, 0xff,
  0xff, 0xbe, 0x1f, 0xff, 0xff, 0xf8, 0x01, 0xff,
  0xff, 0xdf, 0x0f, 0xff, 0xff, 0xf0, 0x01, 0xff,
  0xff, 0xe0, 0x03, 0xff, 0xff, 0xc0, 0x03, 0xff,
  0xff, 0xf0, 0x00, 0x7f, 0xfe, 0x00, 0x07, 0xff,
  0xff, 0xf8, 0x00, 0x03, 0xc0, 0x00, 0x0f, 0xff,
  0xff, 0xfc, 0x00, 0x00, 0x00, 0x00, 0x3f, 0xff,
  0xff, 0xfe, 0x00, 0x00, 0x00, 0x00, 0x7f, 0xff,
  0xff, 0xff, 0x80, 0x00, 0x00, 0x01, 0xff, 0xff,
  0xff, 0xff, 0xc0, 0x00, 0x00, 0x03, 0xff, 0xff,
  0xff, 0xff, 0xf8, 0x00, 0x00, 0x0f, 0xff, 0xff,
  0xff, 0xff, 0xfe, 0x00, 0x00, 0x7f, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
};
 
static const unsigned char PROGMEM myright[] =
{ 0x33, 0x34, 0x33, 0xff,   /*Color of index 0*/
  0xec, 0xed, 0xec, 0xff,   /*Color of index 1*/
 
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf0, 0x07, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0x00, 0x00, 0x7f, 0xff, 0xff,
  0xff, 0xff, 0xf8, 0x00, 0x00, 0x0f, 0xff, 0xff,
  0xff, 0xff, 0xe0, 0x00, 0x00, 0x03, 0xff, 0xff,
  0xff, 0xff, 0x80, 0x00, 0x00, 0x00, 0xff, 0xff,
  0xff, 0xfe, 0x00, 0x0f, 0xf0, 0x00, 0x7f, 0xff,
  0xff, 0xfc, 0x00, 0xff, 0xff, 0x00, 0x1f, 0xff,
  0xff, 0xf8, 0x03, 0xff, 0xff, 0xc6, 0x0f, 0xff,
  0xff, 0xf0, 0x0f, 0xff, 0xff, 0xf0, 0x07, 0xff,
  0xff, 0xe0, 0x1f, 0xff, 0xff, 0xfc, 0x03, 0xff,
  0xff, 0xc0, 0x3f, 0xff, 0xff, 0xfe, 0x01, 0xff,
  0xff, 0x80, 0xff, 0xff, 0xff, 0xff, 0x00, 0xff,
  0xff, 0x01, 0xff, 0xff, 0xff, 0xff, 0x80, 0x7f,
  0xff, 0x03, 0xff, 0xff, 0xff, 0xff, 0xc0, 0x7f,
  0xfe, 0x03, 0xff, 0xff, 0xff, 0xff, 0xe0, 0x3f,
  0xfc, 0x07, 0xff, 0xff, 0xff, 0xff, 0xf0, 0x3f,
  0xfc, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xf0, 0x1f,
  0xf8, 0x0f, 0xff, 0xff, 0xef, 0xff, 0xf8, 0x1f,
  0xf8, 0x1f, 0xff, 0xff, 0xe7, 0xff, 0xf8, 0x0f,
  0xf0, 0x3f, 0xff, 0xff, 0xe3, 0xff, 0xfc, 0x0f,
  0xf0, 0x3f, 0xff, 0xff, 0xe1, 0xff, 0xfc, 0x07,
  0xf0, 0x3f, 0xff, 0xff, 0xe0, 0xff, 0xfc, 0x07,
  0xf0, 0x7f, 0xff, 0xff, 0xe0, 0x3f, 0xfe, 0x07,
  0xe0, 0x7f, 0x00, 0x00, 0x00, 0x1f, 0xfe, 0x07,
  0xe0, 0x7f, 0x00, 0x00, 0x00, 0x0f, 0xfe, 0x03,
  0xe0, 0x7f, 0x00, 0x00, 0x00, 0x07, 0xfe, 0x03,
  0xe0, 0xff, 0x00, 0x00, 0x00, 0x03, 0xfe, 0x03,
  0xe0, 0xff, 0x00, 0x00, 0x00, 0x01, 0xff, 0x03,
  0xe0, 0xff, 0x00, 0x00, 0x00, 0x00, 0xff, 0x03,
  0xe0, 0xff, 0x00, 0x00, 0x00, 0x00, 0xff, 0x03,
  0xe0, 0xff, 0x00, 0x00, 0x00, 0x01, 0xff, 0x03,
  0xe0, 0xff, 0x00, 0x00, 0x00, 0x03, 0xfe, 0x03,
  0xe0, 0x7f, 0x00, 0x00, 0x00, 0x07, 0xfe, 0x03,
  0xe0, 0x7f, 0x00, 0x00, 0x00, 0x0f, 0xfe, 0x03,
  0xe0, 0x7f, 0x00, 0x00, 0x00, 0x1f, 0xfe, 0x03,
  0xe0, 0x7f, 0xff, 0xff, 0xe0, 0x7f, 0xfe, 0x03,
  0xe0, 0x3f, 0xff, 0xff, 0xe0, 0xff, 0xfc, 0x07,
  0xe0, 0x3f, 0xff, 0xff, 0xe1, 0xff, 0xfc, 0x07,
  0xf0, 0x1f, 0xff, 0xff, 0xe3, 0xff, 0xf8, 0x07,
  0xf0, 0x1f, 0xff, 0xff, 0xe7, 0xff, 0xf8, 0x07,
  0xf0, 0x0f, 0xff, 0xff, 0xef, 0xff, 0xf0, 0x0f,
  0xf8, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xf0, 0x0f,
  0xf8, 0x07, 0xff, 0xff, 0xff, 0xff, 0xe0, 0x1f,
  0xfc, 0x83, 0xff, 0xff, 0xff, 0xff, 0xc0, 0x1f,
  0xfc, 0x41, 0xff, 0xff, 0xff, 0xff, 0xc0, 0x3f,
  0xfe, 0x80, 0xff, 0xff, 0xff, 0xff, 0x80, 0x3f,
  0xfe, 0x00, 0x7f, 0xff, 0xff, 0xff, 0x00, 0x7f,
  0xff, 0x00, 0x3f, 0xff, 0xff, 0xfc, 0x00, 0xff,
  0xff, 0x80, 0x1f, 0xff, 0xff, 0xf8, 0x00, 0xff,
  0xff, 0xc0, 0x07, 0xff, 0xff, 0xe0, 0x01, 0xff,
  0xff, 0xe0, 0x01, 0xff, 0xff, 0x80, 0x03, 0xff,
  0xff, 0xf0, 0x00, 0x3f, 0xfc, 0x00, 0x07, 0xff,
  0xff, 0xf8, 0x00, 0x00, 0x00, 0x00, 0x0f, 0xff,
  0xff, 0xfc, 0x00, 0x00, 0x00, 0x00, 0x1f, 0xff,
  0xff, 0xfe, 0x00, 0x00, 0x00, 0x00, 0x3f, 0xff,
  0xff, 0xff, 0x80, 0x00, 0x00, 0x00, 0xff, 0xff,
  0xff, 0xff, 0xe0, 0x00, 0x00, 0x03, 0xff, 0xff,
  0xff, 0xff, 0xf8, 0x00, 0x00, 0x0f, 0xff, 0xff,
  0xff, 0xff, 0xfe, 0x00, 0x00, 0x3f, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf0, 0x07, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
};
 
 
static const unsigned char PROGMEM myup[] =
{ 0x2d, 0x2d, 0x2d, 0xff,   /*Color of index 0*/
  0xf5, 0xf6, 0xf5, 0xff,   /*Color of index 1*/
 
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf0, 0x3f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xfe, 0x00, 0x01, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xf0, 0x00, 0x00, 0x3f, 0xff, 0xff,
  0xff, 0xff, 0xc0, 0x00, 0x00, 0x0f, 0xff, 0xff,
  0xff, 0xff, 0x00, 0x00, 0x00, 0x03, 0xff, 0xff,
  0xff, 0xfc, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff,
  0xff, 0xf8, 0x00, 0x7f, 0xf8, 0x00, 0x7f, 0xff,
  0xff, 0xf0, 0x03, 0xff, 0xff, 0x00, 0x3f, 0xff,
  0xff, 0xc0, 0x0f, 0xff, 0xff, 0xc0, 0x1f, 0xff,
  0xff, 0x80, 0x3f, 0xff, 0xff, 0xf0, 0x07, 0xff,
  0xff, 0x80, 0x7f, 0xff, 0xff, 0xf8, 0x03, 0xff,
  0xff, 0x00, 0xff, 0xff, 0xff, 0xfc, 0x03, 0xff,
  0xfe, 0x01, 0xff, 0xff, 0xff, 0xfe, 0x01, 0xff,
  0xfc, 0x03, 0xff, 0xfc, 0xff, 0xff, 0x00, 0xff,
  0xfc, 0x07, 0xff, 0xf8, 0x7f, 0xff, 0x80, 0xff,
  0xf8, 0x0f, 0xff, 0xf0, 0x3f, 0xff, 0xc0, 0x7f,
  0xf0, 0x1f, 0xff, 0xf0, 0x3f, 0xff, 0xe0, 0x3f,
  0xf0, 0x1f, 0xff, 0xe0, 0x1f, 0xff, 0xe0, 0x3f,
  0xe0, 0x3f, 0xff, 0xc0, 0x0f, 0xff, 0xf0, 0x1f,
  0xe0, 0x3f, 0xff, 0x80, 0x07, 0xff, 0xf0, 0x1f,
  0xe0, 0x7f, 0xff, 0x00, 0x03, 0xff, 0xf8, 0x1f,
  0xc0, 0x7f, 0xfe, 0x00, 0x01, 0xff, 0xf8, 0x0f,
  0xc0, 0x7f, 0xfc, 0x00, 0x00, 0xff, 0xf8, 0x0f,
  0xc0, 0xff, 0xf8, 0x00, 0x00, 0x7f, 0xfc, 0x0f,
  0xc0, 0xff, 0xf0, 0x00, 0x00, 0x3f, 0xfc, 0x0f,
  0x80, 0xff, 0xe0, 0x00, 0x00, 0x1f, 0xfc, 0x07,
  0x80, 0xff, 0xff, 0x80, 0x07, 0xff, 0xfc, 0x07,
  0x80, 0xff, 0xff, 0x80, 0x07, 0xff, 0xfc, 0x07,
  0x80, 0xff, 0xff, 0x80, 0x07, 0xff, 0xfc, 0x07,
  0x80, 0xff, 0xff, 0x80, 0x07, 0xff, 0xfc, 0x07,
  0x80, 0xff, 0xff, 0x80, 0x07, 0xff, 0xfc, 0x07,
  0x80, 0xff, 0xff, 0x80, 0x07, 0xff, 0xfc, 0x07,
  0x80, 0xff, 0xff, 0x80, 0x07, 0xff, 0xfc, 0x07,
  0x80, 0xff, 0xff, 0x80, 0x07, 0xff, 0xfc, 0x07,
  0x80, 0xff, 0xff, 0x80, 0x07, 0xff, 0xfc, 0x07,
  0xc0, 0xff, 0xff, 0x80, 0x07, 0xff, 0xfc, 0x07,
  0xc0, 0x7f, 0xff, 0x80, 0x07, 0xff, 0xf8, 0x0f,
  0xc0, 0x7f, 0xff, 0x80, 0x07, 0xff, 0xf8, 0x0f,
  0xc0, 0x7f, 0xff, 0x80, 0x07, 0xff, 0xf8, 0x0f,
  0xe0, 0x3f, 0xff, 0x80, 0x07, 0xff, 0xf0, 0x1f,
  0xe0, 0x3f, 0xff, 0x80, 0x07, 0xff, 0xf0, 0x1f,
  0xe0, 0x1f, 0xff, 0x80, 0x07, 0xff, 0xe0, 0x1f,
  0xf0, 0x0f, 0xff, 0x80, 0x07, 0xff, 0xc0, 0x3f,
  0xf0, 0x0f, 0xff, 0x80, 0x07, 0xff, 0xc0, 0x3f,
  0xf8, 0x07, 0xff, 0x80, 0x07, 0xff, 0x80, 0x7f,
  0xf8, 0x03, 0xff, 0x80, 0x07, 0xff, 0x00, 0x7f,
  0xfc, 0x01, 0xff, 0xff, 0xff, 0xfe, 0x00, 0xff,
  0xfe, 0x00, 0xff, 0xff, 0xff, 0xfc, 0x01, 0xff,
  0xfe, 0x00, 0x3f, 0xff, 0xff, 0xf0, 0x01, 0xff,
  0xff, 0x00, 0x1f, 0xff, 0xff, 0xe0, 0x03, 0xff,
  0xff, 0x80, 0x07, 0xff, 0xff, 0x80, 0x07, 0xff,
  0xff, 0xc0, 0x00, 0xff, 0xfc, 0x00, 0x0f, 0xff,
  0xff, 0xe0, 0x00, 0x0f, 0xc0, 0x00, 0x1f, 0xff,
  0xff, 0xf0, 0x00, 0x00, 0x00, 0x00, 0x3f, 0xff,
  0xff, 0xf8, 0x00, 0x00, 0x00, 0x00, 0x7f, 0xff,
  0xff, 0xfe, 0x00, 0x00, 0x00, 0x01, 0xff, 0xff,
  0xff, 0xff, 0x80, 0x00, 0x00, 0x07, 0xff, 0xff,
  0xff, 0xff, 0xe0, 0x00, 0x00, 0x1f, 0xff, 0xff,
  0xff, 0xff, 0xf8, 0x00, 0x00, 0x7f, 0xff, 0xff,
  0xff, 0xff, 0xff, 0x00, 0x03, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
};
 
 
static const unsigned char PROGMEM mydown[] =
{ 0x3f, 0x3f, 0x3f, 0xff,   /*Color of index 0*/
  0xea, 0xeb, 0xea, 0xff,   /*Color of index 1*/
 
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0x9f, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xe7, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xf1, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xf0, 0x7f, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xb8, 0x1f, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xe4, 0x0f, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xfa, 0x07, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xfc, 0x03, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xfe, 0x01, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x80, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xc0, 0x7f,
  0xff, 0xff, 0xff, 0xe0, 0x01, 0xff, 0xc0, 0x7f,
  0xff, 0xff, 0xff, 0xc0, 0x01, 0xff, 0xe0, 0x3f,
  0xff, 0xff, 0xff, 0xc0, 0x01, 0xff, 0xf0, 0x1f,
  0xff, 0xff, 0xff, 0xc0, 0x01, 0xff, 0xf8, 0x1f,
  0xff, 0xff, 0xff, 0xc0, 0x01, 0xff, 0xf8, 0x0f,
  0xff, 0xff, 0xff, 0xc0, 0x01, 0xff, 0xfc, 0x0f,
  0xff, 0xff, 0xff, 0xc0, 0x01, 0xff, 0xfc, 0x0f,
  0xff, 0xff, 0xff, 0xc0, 0x01, 0xff, 0xfe, 0x07,
  0xff, 0xff, 0xff, 0xc0, 0x01, 0xff, 0xfe, 0x07,
  0xff, 0xff, 0xff, 0xc0, 0x01, 0xff, 0xfe, 0x03,
  0xff, 0xff, 0xff, 0xc0, 0x01, 0xff, 0xff, 0x03,
  0xff, 0xff, 0xff, 0xc0, 0x01, 0xff, 0xff, 0x03,
  0xff, 0xff, 0xff, 0xc0, 0x01, 0xff, 0xff, 0x03,
  0xff, 0xff, 0xff, 0xc0, 0x01, 0xff, 0xff, 0x03,
  0xff, 0xff, 0xff, 0xc0, 0x01, 0xff, 0xff, 0x03,
  0xff, 0xff, 0xff, 0xc0, 0x01, 0xff, 0xff, 0x03,
  0xff, 0xff, 0xff, 0xc0, 0x01, 0xff, 0xff, 0x01,
  0xff, 0xff, 0xff, 0xc0, 0x01, 0xff, 0xff, 0x01,
  0xff, 0xff, 0xff, 0xc0, 0x01, 0xff, 0xff, 0x01,
  0xff, 0xff, 0xf8, 0x00, 0x00, 0x0f, 0xff, 0x03,
  0xff, 0xff, 0xfc, 0x00, 0x00, 0x0f, 0xff, 0x03,
  0xff, 0xff, 0xfc, 0x00, 0x00, 0x1f, 0xff, 0x03,
  0xff, 0xff, 0xfe, 0x00, 0x00, 0x3f, 0xfe, 0x03,
  0xff, 0xff, 0xff, 0x00, 0x00, 0x7f, 0xfe, 0x03,
  0xf7, 0xff, 0xff, 0x80, 0x00, 0xff, 0xfe, 0x03,
  0xff, 0xdf, 0xff, 0xc0, 0x01, 0xff, 0xfc, 0x07,
  0xff, 0xdf, 0xff, 0xe0, 0x03, 0xff, 0xfc, 0x07,
  0xfb, 0xef, 0xff, 0xf0, 0x07, 0xff, 0xf8, 0x07,
  0xf9, 0xef, 0xff, 0xf8, 0x07, 0xff, 0xf8, 0x0f,
  0xfd, 0xe7, 0xff, 0xfc, 0x0f, 0xff, 0xf0, 0x0f,
  0xfc, 0x13, 0xff, 0xfc, 0x1f, 0xff, 0xe0, 0x1f,
  0xfe, 0x01, 0xff, 0xfe, 0x3f, 0xff, 0xc0, 0x1f,
  0xfe, 0x00, 0xff, 0xff, 0xff, 0xff, 0x80, 0x3f,
  0xff, 0x00, 0x7f, 0xff, 0xff, 0xff, 0x00, 0x3f,
  0xff, 0x80, 0x3f, 0xff, 0xff, 0xfe, 0x00, 0x7f,
  0xff, 0x80, 0x1f, 0xff, 0xff, 0xfc, 0x00, 0xff,
  0xff, 0xc0, 0x07, 0xff, 0xff, 0xf0, 0x01, 0xff,
  0xff, 0xe0, 0x01, 0xff, 0xff, 0xc0, 0x01, 0xff,
  0xff, 0xf0, 0x00, 0x7f, 0xff, 0x00, 0x03, 0xff,
  0xff, 0xf8, 0x00, 0x03, 0xe0, 0x00, 0x07, 0xff,
  0xff, 0xfc, 0x00, 0x00, 0x00, 0x00, 0x1f, 0xff,
  0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x3f, 0xff,
  0xff, 0xff, 0x80, 0x00, 0x00, 0x00, 0x7f, 0xff,
  0xff, 0xff, 0xe0, 0x00, 0x00, 0x01, 0xff, 0xff,
  0xff, 0xff, 0xf8, 0x00, 0x00, 0x07, 0xff, 0xff,
  0xff, 0xff, 0xfe, 0x00, 0x00, 0x3f, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x03, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
};
 
static const unsigned char PROGMEM mynear[] =
{ 0x59, 0x59, 0x59, 0xff,   /*Color of index 0*/
  0xf8, 0xf9, 0xf8, 0xff,   /*Color of index 1*/
 
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe7, 0xef, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe3, 0xcf, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe1, 0x8f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x07, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0x00, 0x00, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0x00, 0x01, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0x80, 0x03, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xc0, 0x07, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf0, 0x1f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf8, 0x3f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xfe, 0x7f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xfe, 0x7f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf8, 0x1f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x03, 0xff, 0xff, 0xff,
  0xff, 0xf7, 0xff, 0x80, 0x01, 0xff, 0xef, 0xff,
  0xff, 0xf3, 0xff, 0x00, 0x00, 0xff, 0xcf, 0xff,
  0xff, 0xf1, 0xfe, 0x00, 0x00, 0x7f, 0x8f, 0xff,
  0xff, 0xf0, 0xfe, 0x00, 0x00, 0x3f, 0x0f, 0xff,
  0xc0, 0x00, 0x7c, 0x00, 0x00, 0x3e, 0x00, 0x03,
  0xc0, 0x00, 0x3c, 0x00, 0x00, 0x1c, 0x00, 0x03,
  0xe0, 0x00, 0x18, 0x00, 0x00, 0x18, 0x00, 0x0f,
  0xf0, 0x00, 0x08, 0x00, 0x00, 0x10, 0x00, 0x1f,
  0xf8, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1f,
  0xf8, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x1f,
  0xf0, 0x00, 0x18, 0x00, 0x00, 0x10, 0x00, 0x0f,
  0xe0, 0x00, 0x38, 0x00, 0x00, 0x18, 0x00, 0x07,
  0xc0, 0x00, 0x7c, 0x00, 0x00, 0x1c, 0x00, 0x03,
  0xff, 0xf0, 0xfc, 0x00, 0x00, 0x3e, 0x0f, 0xff,
  0xff, 0xf1, 0xfc, 0x00, 0x00, 0x3f, 0x0f, 0xff,
  0xff, 0xf3, 0xfe, 0x00, 0x00, 0x7f, 0x8f, 0xff,
  0xff, 0xf7, 0xff, 0x00, 0x00, 0xff, 0xcf, 0xff,
  0xff, 0xff, 0xff, 0x80, 0x01, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xc0, 0x03, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xfe, 0x7f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xfe, 0x7f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xfc, 0x3f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf8, 0x1f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x07, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xc0, 0x03, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0x80, 0x01, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0x00, 0x00, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x07, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe1, 0x8f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe3, 0xcf, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe7, 0xef, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
};
 
 
static const unsigned char PROGMEM myfar[] =
{ 0x63, 0x64, 0x63, 0xff,   /*Color of index 0*/
  0xf8, 0xfa, 0xf8, 0xff,   /*Color of index 1*/
 
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xfe, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xfc, 0x7f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf8, 0x3f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf0, 0x1f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xc0, 0x07, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0x80, 0x03, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0x00, 0x01, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xfe, 0x00, 0x00, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe1, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe3, 0x8f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe7, 0xcf, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xef, 0xef, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xc0, 0x03, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0x80, 0x01, 0xff, 0xff, 0xff,
  0xff, 0xbf, 0xff, 0x00, 0x00, 0xff, 0xfd, 0xff,
  0xff, 0x3f, 0xfe, 0x00, 0x00, 0x7f, 0xfc, 0xff,
  0xfe, 0x3f, 0xfc, 0x00, 0x00, 0x3f, 0xfc, 0x7f,
  0xfc, 0x3f, 0xfc, 0x00, 0x00, 0x3f, 0xfc, 0x3f,
  0xf8, 0x00, 0x00, 0x00, 0x00, 0x10, 0x00, 0x1f,
  0xf0, 0x00, 0x08, 0x00, 0x00, 0x10, 0x00, 0x0f,
  0xe0, 0x00, 0x18, 0x00, 0x00, 0x18, 0x00, 0x07,
  0xc0, 0x00, 0x38, 0x00, 0x00, 0x1c, 0x00, 0x03,
  0x80, 0x00, 0x78, 0x00, 0x00, 0x1e, 0x00, 0x01,
  0xc0, 0x00, 0x38, 0x00, 0x00, 0x1c, 0x00, 0x03,
  0xe0, 0x00, 0x18, 0x00, 0x00, 0x18, 0x00, 0x07,
  0xf0, 0x00, 0x08, 0x00, 0x00, 0x10, 0x00, 0x0f,
  0xf8, 0x00, 0x0c, 0x00, 0x00, 0x30, 0x00, 0x1f,
  0xfc, 0x3f, 0xfc, 0x00, 0x00, 0x3f, 0xfc, 0x3f,
  0xfe, 0x3f, 0xfe, 0x00, 0x00, 0x7f, 0xfc, 0x7f,
  0xff, 0x3f, 0xff, 0x00, 0x00, 0x7f, 0xfc, 0xff,
  0xff, 0xbf, 0xff, 0x00, 0x00, 0xff, 0xfd, 0xff,
  0xff, 0xff, 0xff, 0xc0, 0x03, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf0, 0x07, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf7, 0xe7, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf3, 0xc7, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf1, 0x87, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf0, 0x07, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf0, 0x07, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf0, 0x07, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf0, 0x07, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf0, 0x07, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf0, 0x07, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x07, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0x00, 0x00, 0x7f, 0xff, 0xff,
  0xff, 0xff, 0xff, 0x00, 0x00, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0x80, 0x01, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xc0, 0x03, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xe0, 0x07, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf0, 0x0f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xf8, 0x1f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xfc, 0x3f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xfe, 0x7f, 0xff, 0xff, 0xff,
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
};
 
 
 
 
 
// Global Variables
SparkFun_APDS9960 apds = SparkFun_APDS9960();
int isr_flag = 0;
 
void setup() {
 
  // Initialize Serial port
  Serial.begin(9600);
  Serial.println();
  Serial.println(F("--------------------------------"));
  Serial.println(F("APDS-9960 - GestureTest"));
  Serial.println(F("--------------------------------"));
 
    display.begin(SSD1306_SWITCHCAPVCC, 0x3C); //initialize with the I2C addr 0x3C (128x64)
    
 
  // Initialize interrupt service routine
  attachInterrupt(0, interruptRoutine, FALLING);
 
  // Initialize APDS-9960 (configure I2C and initial values)
  if ( apds.init() ) {
    Serial.println(F("APDS-9960 initialization complete"));
    display.clearDisplay();
    display.setCursor(0,0);  
    display.setTextSize(1);
    display.setTextColor(WHITE);
    display.println("ADPS Initialization");
    display.println("");
    display.setTextSize(2);
    display.println("Success! ");
    display.display();
  } else {
    Serial.println(F("Something went wrong during APDS-9960 init!"));
    display.clearDisplay();
    display.setCursor(0,0);  
    display.setTextSize(1);
    display.setTextColor(WHITE);
    display.println("ADPS Initialization");
    display.println("");
    display.setTextSize(2);
    display.println("Failed! ");
    display.display();
  }
 
  // Start running the APDS-9960 gesture sensor engine
  if ( apds.enableGestureSensor(true) ) {
    Serial.println(F("Gesture sensor is now running"));
    display.clearDisplay();
    display.setCursor(0,0);  
    display.setTextSize(1);
    display.setTextColor(WHITE);
    display.println("ADPS Initialization");
    display.println("");
    display.setTextSize(2);
    display.println("Success! ");
    display.display();
  } else {
    Serial.println(F("Something went wrong during gesture sensor init!"));
    display.clearDisplay();
    display.setCursor(0,0);  
    display.setTextSize(1);
    display.setTextColor(WHITE);
    display.println("ADPS Initialization");
    display.println("");
    display.setTextSize(2);
    display.println("Failed! ");
    display.display();
  }
}
 
void loop() {
  if( isr_flag == 1 ) {
    detachInterrupt(0);
    handleGesture();
    isr_flag = 0;
    attachInterrupt(0, interruptRoutine, FALLING);
  }
}
 
void interruptRoutine() {
  isr_flag = 1;
}
 
void handleGesture() {
    if ( apds.isGestureAvailable() ) {
    switch ( apds.readGesture() ) {
      case DIR_UP:
        Serial.println("UP");
        display.clearDisplay();
        display.drawBitmap(31, 0, myup, LOGO_WIDTH, LOGO_HEIGHT, 1);
        display.display();
        break;
      case DIR_DOWN:
        Serial.println("DOWN");
        display.clearDisplay();
        display.drawBitmap(31, 0, mydown, LOGO_WIDTH, LOGO_HEIGHT, 1);
        display.display();
        break;
      case DIR_LEFT:
        Serial.println("LEFT");
        display.clearDisplay();
        display.drawBitmap(31, 0, myleft, LOGO_WIDTH, LOGO_HEIGHT, 1);
        display.display();
        break;
      case DIR_RIGHT:
        Serial.println("RIGHT");
        display.clearDisplay();
        display.drawBitmap(31, 0, myright, LOGO_WIDTH, LOGO_HEIGHT, 1);
        display.display();
        break;
      case DIR_NEAR:
        Serial.println("NEAR");
        display.clearDisplay();
        display.drawBitmap(31, 0, mynear, LOGO_WIDTH, LOGO_HEIGHT, 1);
        display.display();
        break;
      case DIR_FAR:
        Serial.println("FAR");
        display.clearDisplay();
        display.drawBitmap(31, 0, myfar, LOGO_WIDTH, LOGO_HEIGHT, 1);
        display.display();
        break;
      default:
        Serial.println("NONE");
    }
  }
}


After uploading the code the OLED will display the following message on OLED Screen.

Now try moving your hands in left, right, up, down, far, near directions. The OLED display will indicate the directions by some arrow sign in OLED Screen. For example for the Left gesture, it shows the left arrow.


Video Tutorial & Guide

APDS9960 Gesture, Proximity, Light & RGB Sensor Tutorial with Arduino
Watch this video on YouTube.

Share. Facebook Twitter Pinterest LinkedIn Tumblr Email Reddit Telegram WhatsApp
Previous ArticleDIY Turbidity Meter using Turbidity Sensor & Arduino
Next Article How to interface Panasonic PIR Motion Sensor with Arduino

Related Posts

DC Energy Meter using Arduino

Build a DC Energy Meter using Arduino – 32V/5A

Updated:August 26, 20252K
Interfacing ADXL375 Accelerometer with Arduino

Interfacing ADXL375 Accelerometer with Arduino (±200g)

Updated:June 28, 2025
PZEM-004T Arduino Energy Meter

DIY AC Energy Meter using PZEM-004T & Arduino

Updated:March 6, 20258K
Interfacing BMI160 Accelerometer & Gyroscope with Arduino

Interfacing BMI160 Accelerometer & Gyroscope with Arduino

Updated:February 2, 20259K
Password Based Door Lock Security System Using Arduino & Keypad

Password Based Door Lock Security System Using Arduino & Keypad

Updated:February 2, 20252436K
Earthquake Detector Alarm with with Accelerometer & Arduino

Earthquake Detector Alarm with Accelerometer & Arduino

Updated:February 2, 2025661K
View 2 Comments

2 Comments

  1. Alexandra Molnar on November 16, 2022 7:02 PM

    Hello, I’ve been following your work, and I made the connections exactly like you did, and on the OLED it’s showing me the message “APDS initialization Success!” but for some reason my sensor does not want to read my hand gesture. Also, I have followed other tutorials without the OLED and my sensor still is not working. Could you please give me some advice on how should I proceed? Or maybe you have any idea why is not working for me?

    Reply
  2. dhus on February 27, 2023 3:54 PM

    Hi, perfect blog, how can I use all sensors color, proximity and guester at same time?

    Reply

CommentsCancel reply

Latest Posts
ESP32 Fingerprint Attendance System with Live Web Dashboard

ESP32 Fingerprint Attendance System with Live Web Dashboard

June 21, 2026
IoT Based PM & Air Quality Monitoring System using ESP32

IoT Based PM & Air Quality Monitoring System using ESP32

June 14, 2026
DIY ESP32 MLX90640 IR Thermal Camera with Live Web Display

DIY ESP32 MLX90640 IR Thermal Camera with Live Web Display

May 10, 2026
IoT Activity Tracker with ESP32 & Accelerometer Gyroscope

IoT Activity Tracker with ESP32 & Accelerometer/Gyroscope

May 2, 2026
A Guide to Sourcing Obsolete ICs for Vintage Projects

Beyond AliExpress: A Guide to Sourcing Obsolete ICs for Vintage Projects

April 21, 2026

ESP32 IoT Vehicle Motion Analyzer with MPU6050 & LIS3MDL

April 27, 2026
Building a Smart Sensor Node with a BLE Microcontroller

Building a Smart Sensor Node with a BLE Microcontroller

February 26, 2026
High-Accuracy Pitch, Roll, Yaw with ESP32 & BNO08x IMU

High-Accuracy Pitch, Roll, Yaw with ESP32 & BNO08x IMU

April 27, 2026
Top Posts & Pages
  • ESP32 Fingerprint Attendance System with Live Web Dashboard
    ESP32 Fingerprint Attendance System with Live Web Dashboard
  • IoT AC Energy Meter with PZEM-004T & ESP32 WebServer
    IoT AC Energy Meter with PZEM-004T & ESP32 WebServer
  • 12V DC to 220V AC Inverter Circuit & PCB
    12V DC to 220V AC Inverter Circuit & PCB
  • Buck Converter: Basics, Working, Design & Application
    Buck Converter: Basics, Working, Design & Application
  • How to use INA226 DC Current Sensor with Arduino
    How to use INA226 DC Current Sensor with Arduino
  • LD2410 Sensor with ESP32 - Human Presence Detection
    LD2410 Sensor with ESP32 - Human Presence Detection
  • ECG Graph Monitoring with AD8232 ECG Sensor & Arduino
    ECG Graph Monitoring with AD8232 ECG Sensor & Arduino
  • Designing of MPPT Solar Charge Controller using Arduino
    Designing of MPPT Solar Charge Controller using Arduino
Categories
  • Arduino Projects (197)
  • Articles (60)
    • Learn Electronics (19)
    • Product Review (15)
    • Tech Articles (28)
  • Electronics Circuits (46)
    • 555 Timer Projects (21)
    • Op-Amp Circuits (7)
    • Power Electronics (13)
  • IoT Projects (205)
    • ESP32 MicroPython (7)
    • ESP32 Projects (82)
    • ESP32-CAM Projects (15)
    • ESP8266 Projects (76)
    • LoRa/LoRaWAN Projects (22)
  • Microcontrollers (38)
    • AMB82-Mini IoT AI Camera (4)
    • BLE Projects (18)
    • STM32 Projects (19)
  • Raspberry Pi (93)
    • Raspberry Pi Pico Projects (57)
    • Raspberry Pi Pico W Projects (12)
    • Raspberry Pi Projects (24)
Follow Us
  • Facebook
  • Twitter
  • Pinterest
  • Instagram
  • YouTube
About Us

“‘How to Electronics’ is a vibrant community for electronics enthusiasts and professionals. We deliver latest insights in areas such as Embedded Systems, Power Electronics, AI, IoT, and Robotics. Our goal is to stimulate innovation and provide practical solutions for students, organizations, and industries. Join us to transform learning into a joyful journey of discovery and innovation.

Copyright © How To Electronics. All rights reserved.
  • About Us
  • Disclaimer
  • Privacy Policy
  • Contact Us
  • Advertise With Us

Type above and press Enter to search. Press Esc to cancel.

Ad Blocker Enabled!
Ad Blocker Enabled!
Looks like you're using an ad blocker. Please allow ads on our site. We rely on advertising to help fund our site.