Skip to content

Commit

Permalink
samples: sensor: Add VCNL4040 sample
Browse files Browse the repository at this point in the history
Add sample to show usage of VCNL4040 sensor driver

Signed-off-by: Richard Osterloh <[email protected]>
  • Loading branch information
rosterloh authored and MaureenHelm committed Sep 4, 2020
1 parent 0a0026a commit e917c6c
Show file tree
Hide file tree
Showing 6 changed files with 248 additions and 0 deletions.
7 changes: 7 additions & 0 deletions samples/sensor/vcnl4040/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
# SPDX-License-Identifier: Apache-2.0

cmake_minimum_required(VERSION 3.13.1)
find_package(Zephyr HINTS $ENV{ZEPHYR_BASE})
project(vcnl4040)

target_sources(app PRIVATE src/main.c)
57 changes: 57 additions & 0 deletions samples/sensor/vcnl4040/README.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
.. _vcnl4040_sample:

VCNL4040: proximity and ambient light sensor
############################################

Overview
********
This sample periodically measures proximity and light for
5 sec in the interval of 300msec in polling mode. Then threshold trigger mode
is enabled with the high threshold value of 127 and data is fetched based
on interrupt. The result is displayed on the console.

Requirements
************

This sample uses the VCNL4040 sensor controlled using the I2C interface.
Connect sensor INT for interrupt to Feather D5 pin on the Adafruit STM32F405 Feather.

References
**********

- VCNL4040: https://www.vishay.com/docs/84274/vcnl4040.pdf

Building and Running
********************

This project outputs sensor data to the console. It requires a VCNL4040
sensor to be connected to the desired board.

.. zephyr-app-commands::
:app: samples/sensor/vcnl4040/
:goals: build flash


Sample Output
=============

.. code-block:: console
get device vcnl4040
Testing the polling mode.
Proximity: 31
Light (lux): 288
<repeats for 5sec every 300ms>
Polling mode test finished.
Testing the trigger mode.
Testing proximity trigger.
...
Triggered.
Proximity: 122
<repeats whenever triggered for 5sec>
Threshold trigger test finished.
Trigger mode test finished.
19 changes: 19 additions & 0 deletions samples/sensor/vcnl4040/boards/adafruit_feather_stm32f405.overlay
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
/*
* Copyright (c) 2020, Richard Osterloh
*
* SPDX-License-Identifier: Apache-2.0
*/

&feather_i2c {
vcnl4040@60 {
compatible = "vishay,vcnl4040";
reg = <0x60>;
label = "VCNL4040";
int-gpios = <&feather_header 14 (GPIO_ACTIVE_LOW | GPIO_PULL_UP)>;
led-current = <200>;
led-duty-cycle = <320>;
proximity-it = "8";
proximity-trigger = "close";
als-it = <640>;
};
};
7 changes: 7 additions & 0 deletions samples/sensor/vcnl4040/prj.conf
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
CONFIG_PRINTK=y
CONFIG_GPIO=y
CONFIG_I2C=y
CONFIG_SENSOR=y
CONFIG_VCNL4040=y
CONFIG_VCNL4040_TRIGGER_GLOBAL_THREAD=y
CONFIG_VCNL4040_ENABLE_ALS=y
9 changes: 9 additions & 0 deletions samples/sensor/vcnl4040/sample.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
sample:
name: VCNL4040 Sensor Sample
tests:
sample.sensor.vcnl4040:
harness: sensor
platform_allow: adafruit_feather_stm32f405
tags: sensors
depends_on: i2c gpio
filter: dt_compat_enabled("vishay,vcnl4040")
149 changes: 149 additions & 0 deletions samples/sensor/vcnl4040/src/main.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,149 @@
/*
* Copyright (c) 2020 Richard Osterloh
*
* SPDX-License-Identifier: Apache-2.0
*/

#include <zephyr.h>

#include <sys/printk.h>
#include <sys_clock.h>
#include <stdio.h>

#include <device.h>
#include <drivers/sensor.h>
#include <drivers/i2c.h>

#define MAX_TEST_TIME 5000
#define SLEEPTIME 300

static void print_proxy_data(const struct device *dev)
{
struct sensor_value pdata;

if (sensor_channel_get(dev, SENSOR_CHAN_PROX, &pdata) < 0) {
printf("Cannot read proximity data.\n");
return;
}

printf("Proximity: %d\n", (uint16_t) pdata.val1);
}
#if defined(CONFIG_VCNL4040_ENABLE_ALS)
static void print_als_data(const struct device *dev)
{
struct sensor_value val;

if (sensor_channel_get(dev, SENSOR_CHAN_LIGHT, &val) < 0) {
printf("ALS read error.\n");
return;
}

printf("Light (lux): %d\n", (uint16_t) val.val1);
}
#endif
static void test_polling_mode(const struct device *dev)
{
int32_t remaining_test_time = MAX_TEST_TIME;

do {
if (sensor_sample_fetch(dev) < 0) {
printf("sample update error.\n");
} else {
print_proxy_data(dev);
#if defined(CONFIG_VCNL4040_ENABLE_ALS)
print_als_data(dev);
#endif
}

/* wait a while */
k_sleep(K_MSEC(SLEEPTIME));

remaining_test_time -= SLEEPTIME;
} while (remaining_test_time > 0);
}

#if defined(CONFIG_VCNL4040_TRIGGER)
static void trigger_handler(const struct device *dev,
struct sensor_trigger *trig)
{
switch (trig->type) {
case SENSOR_TRIG_THRESHOLD:
printf("Triggered.\n");
if (sensor_sample_fetch(dev) < 0) {
printf("sample update error.\n");
} else {
print_proxy_data(dev);
}
return;

default:
printf("trigger handler: unknown trigger type.\n");
return;
}
}
#endif

static void test_trigger_mode(const struct device *dev)
{
#if defined(CONFIG_VCNL4040_TRIGGER)
struct sensor_trigger trig;
struct sensor_value attr;

printf("Testing proximity trigger.\n");

attr.val1 = 127;
attr.val2 = 0;

if (sensor_attr_set(dev, SENSOR_CHAN_PROX,
SENSOR_ATTR_UPPER_THRESH, &attr) < 0) {
printf("cannot set proximity high threshold.\n");
return;
}

attr.val1 = 122;

if (sensor_attr_set(dev, SENSOR_CHAN_PROX,
SENSOR_ATTR_LOWER_THRESH, &attr) < 0) {
printf("cannot set proximity low threshold.\n");
return;
}

trig.type = SENSOR_TRIG_THRESHOLD;
trig.chan = SENSOR_CHAN_PROX;

if (sensor_trigger_set(dev, &trig, trigger_handler) < 0) {
printf("cannot set trigger.\n");
return;
}

k_sleep(K_MSEC(MAX_TEST_TIME));

if (sensor_trigger_set(dev, &trig, NULL) < 0) {
printf("cannot clear trigger.\n");
return;
}

printf("Threshold trigger test finished.\n");
#endif

}

void main(void)
{
const struct device *vcnl;

printf("get device vcnl4040\n");
vcnl = device_get_binding(DT_LABEL(DT_INST(0, vishay_vcnl4040)));
if (!vcnl) {
printf("Device not found.\n");
return;
}

printf("Testing the polling mode.\n");
test_polling_mode(vcnl);
printf("Polling mode test finished.\n");

printf("Testing the trigger mode.\n");
test_trigger_mode(vcnl);
printf("Trigger mode test finished.\n");
}

0 comments on commit e917c6c

Please sign in to comment.