APDS9960传感器在Hi3861上的移植和使用 原创 精华

发布于 2022-5-18 09:32
浏览
3收藏

1、APDS9960简介

APDS9960是一款多功能传感器。它可以在光线下检测手势、环境光和RGB值。该传感器还可用作接近传感器,主要用于智能手机,以便在通话时禁用触摸屏。该传感器由四个光电二极管组成。这些光电二极管检测由板载LED传输的反射IR能量。因此,无论何时执行任何手势,该IR能量都被阻挡并反射回传感器,现在传感器检测到关于手势的信息(方向、速度)并将其转换为数字信息。该传感器可用于通过检测反射的IR光来测量障碍物的距离。它具有用于检测RGB颜色的UV和IR阻挡滤光器,并为每种颜色生成16位数据。
官方介绍资料:https://www.sparkfun.com/products/12787

2、代码移植

官方提供了Arduino版本的源代码:https://github.com/sparkfun/APDS-9960_RGB_and_Gesture_Sensor
代码移植的核心为两部分:1)Arduino代码的转成标准C语言。2)修改I2C的驱动,适配openharmony。
这里介绍一下I2C的部分代码。其他代码,会放在附件中。

/*******************************************************************************
 * Raw I2C Reads and Writes
 ******************************************************************************/

/**
 * @brief Writes a single byte to the I2C device (no register)
 *
 * @param[in] val the 1-byte value to write to the I2C device
 * @return True if successful write operation. False otherwise.
 */
bool APDS9960_wireWriteByte(uint8_t val)
{
	uint8_t write_data[2] = {val};
    hi_i2c_data i2c_data = {0};
    i2c_data.send_buf = write_data;
    i2c_data.send_len = 1;
 
    uint32_t result = hi_i2c_write(apds_i2c_channel, (APDS9960_I2C_ADDR<<1), &i2c_data);
    if(result == 0){
        return true;
    }
	return false;
}

/**
 * @brief Writes a single byte to the I2C device and specified register
 *
 * @param[in] reg the register in the I2C device to write to
 * @param[in] val the 1-byte value to write to the I2C device
 * @return True if successful write operation. False otherwise.
 */
bool APDS9960_wireWriteDataByte(uint8_t reg, uint8_t val)
{
	uint8_t write_data[3] = {reg,val};
    hi_i2c_data i2c_data = {0};
    i2c_data.send_buf = write_data;
    i2c_data.send_len = 2;
 
    uint32_t result = hi_i2c_write(apds_i2c_channel, (APDS9960_I2C_ADDR<<1), &i2c_data);
    if(result == 0){
        return true;
    }
	return false;
}

/**
 * @brief Writes a block (array) of bytes to the I2C device and register
 *
 * @param[in] reg the register in the I2C device to write to
 * @param[in] val pointer to the beginning of the data byte array
 * @param[in] len the length (in bytes) of the data to write
 * @return True if successful write operation. False otherwise.
 */
bool APDS9960_wireWriteDataBlock(  uint8_t reg,
                                        uint8_t *val,
                                        unsigned int len)
{
    return true;
}

/**
 * @brief Reads a single byte from the I2C device and specified register
 *
 * @param[in] reg the register to read from
 * @param[out] the value returned from the register
 * @return True if successful read operation. False otherwise.
 */
bool APDS9960_wireReadDataByte(uint8_t reg, uint8_t *val)
{
    hi_i2c_data i2c_data = {0};
    uint8_t  buffer[1] = {0x00};
    buffer[0] = reg;
    i2c_data.send_buf = buffer;
    i2c_data.send_len = 1;
    i2c_data.receive_buf = val;
    i2c_data.receive_len = 1;
    int res = hi_i2c_writeread(apds_i2c_channel, (APDS9960_I2C_ADDR<<1), &i2c_data);
    if(res == 0)//成功
    {
        return true;
    }
    else
    {
        return false;
    }
}

/**
 * @brief Reads a block (array) of bytes from the I2C device and register
 *
 * @param[in] reg the register to read from
 * @param[out] val pointer to the beginning of the data
 * @param[in] len number of bytes to read
 * @return Number of bytes read. -1 on read error.
 */
int APDS9960_wireReadDataBlock(uint8_t reg,uint8_t *val,unsigned int len)
{
    hi_i2c_data i2c_data = {0};
    uint8_t  buffer[1] = {0x00};
    buffer[0] = reg;
    i2c_data.send_buf = buffer;
    i2c_data.send_len = 1;
    i2c_data.receive_buf = val;
    i2c_data.receive_len = len;
    int res = hi_i2c_writeread(apds_i2c_channel, (APDS9960_I2C_ADDR<<1), &i2c_data);
    if(res == 0)//成功
    {
        return len;
    }
    else
    {
        return -1;
    }
}

3、功能使用

实际的使用,也比较简单。官方也有其使用方法。这里介绍手势识别的使用方法。

1)I2C初始化

这里不做介绍,就是使用openharmony标准的方法即可。

2)手势检测模式初始化

// Start running the APDS-9960 gesture sensor engine
if (APDS9960_enableGestureSensor(true))
{
    DEBUG_printf("Gesture sensor is now running\r\n");
}
else
{
    DEBUG_printf("Something went wrong during gesture sensor init!\r\n");
}

3)测试使用

STATIC mp_obj_t machine_gesture_read(size_t n_args, const mp_obj_t *pos_args, mp_map_t *kw_args)
{
    int gesture = 0;
    if (APDS9960_isGestureAvailable())
    {
        switch (APDS9960_readGesture())
        {
        case DIR_UP:
            DEBUG_printf("UP\r\n");
            gesture = DIR_UP;
            break;
        case DIR_DOWN:
            DEBUG_printf("DOWN\r\n");
            gesture = DIR_DOWN;
            break;
        case DIR_LEFT:
            DEBUG_printf("LEFT\r\n");
            gesture = DIR_LEFT;
            break;
        case DIR_RIGHT:
            DEBUG_printf("RIGHT\r\n");
            gesture = DIR_RIGHT;
            break;
        case DIR_NEAR:
            DEBUG_printf("NEAR\r\n");
            gesture = DIR_NEAR;
            break;
        case DIR_FAR:
            DEBUG_printf("FAR\r\n");
            gesture = DIR_FAR;
            break;
        default:
            DEBUG_printf("NONE\r\n");
            gesture = 0;
            break;
        }
    }

    //return mp_obj_new_int(gesture);
    return mp_const_none;
}

根据手势的不同方向,可以检测不同的状态,比如,向上挥手,向做挥手等等。

©著作权归作者所有,如需转载,请注明出处,否则将追究法律责任
apds资料.zip 719.23K 2次下载
APDS-9960_RGB_and_Gesture_Sensor-master.zip 3.98M 4次下载
APDS-9960四合一传感器.pdf 957.1K 5次下载
3
收藏 3
回复
举报
回复
添加资源
添加资源将有机会获得更多曝光,你也可以直接关联已上传资源 去关联
    相关推荐