[文章]【码上评选】HarmonyOS润和HiSpark智能物联灯产品实现初试

阅读量0
0
1
``

Harmony OS-Hi3861-HiSpark Wi-Fi智能家居套件-智能物联灯产品实现初试.
三种场景中的产品创意效果图

微信图片_20201225120048.png
微信图片_20201225104801.png
微信图片_20201225120802.png


一、创意

主要基于HiSpark Wi-Fi智能家居套件中Hi3861芯片、通用底板、炫彩灯板、环境监测板等在HarmonyOS的HUAWEI DevEco Device Tool中测试开发,得出的心得体验;结合一个实际的智能物联家居产品场景综合性的从创意、场景、底层功能初步尝试实现、整体效果样式设计、后续完善思路等的整套鸿蒙产品服务解决方案初试。


将传统开关的台灯、单片机感应台灯、手电筒或者小夜灯等,和人体感应、温度、湿度、可燃气体监测融合成全新的感应、温湿度监测、可燃气体预警联网的智能型灯产品系列。


二、场景

1. 安全智能灯放置在家庭客厅或者洗手间门口等,当家人晚上起床时自动感应人体,灯从暗到亮(考虑到人的暗适应过程)。当感应人体远离后,灯自动关闭。摆脱各种开关灯的烦恼。

2. 灯会监测环境中的温度、湿度、可燃气体情况,设置高低阈值,超过阈值时,灯会报警和触发手机里的应用提示等。

3. 搭载鸿蒙操作系统的手机、手表穿戴设备及里的应用服务,通过多种方式,可以近距离及远程控制灯的开关,获取室内的环境监测情况。比如晚上回家开门时就通过手机或者穿戴设备已经将室内灯打开。

4. 一些特殊环境下,比如矿井、洞内探索、野外夜晚探险等特殊产品形式使用。在实现照亮的同时,现场和远程都可以监测危险情况等。

5. 完全改变了传统灯的概念与使用方式;在不改变原有灯体系的基础上,家庭室内等可以先独立配置一个物联智能灯体验与感受物联智能灯时代的体贴、便捷、智能、安全保护等。物联智能灯先锋产品,从单品体验,带动全屋灯及全系列灯具物联智能改造升级。

三、产品配置

1. 芯片开发板及主要功能模块

HISpark Wi-Fi智能家居套件、通用底板、炫彩灯板、环境监测板。

2. 操作系统 HarmonyOS

3. 模组、其它配件与外设等,暂时只是一种创意设想,具体参见达成效果图所需要的相关配件。

四、HISpark Wi-Fi智能家居套件功能使用效果展现与HUAWEI DevEco Device Tool中代码实现

暂时只是通过HISpark Wi-Fi智能家居套件通用底板、炫彩灯板、环境监测板简单实现来自动感应人体,灯从暗到亮;当感应人体远离后,灯自动关闭;灯会监环境的温度、湿度、可燃气体情况来呈现整体产品概念;受制于各项条件,各项细节要求等,暂时还满足不了真实产品的实际需求。
感应人体灯亮
感应人体灯亮\n
感应人体灯亮


代码
#include<stdio.h>
#include<unistd.h>

#include "ohos_init.h"
#include "cmsis_os2.h"
#include "wifiiot_gpio.h"
#include "wifiiot_gpio_ex.h"
#include "wifiiot_pwm.h"
#include "wifiiot_adc.h"
#include "wifiiot_errno.h"

#define PWM_FREQ_DIVITION 64000
#define ADC_RESOLUTION 4996

static void jltfcloudcom(void *arg)
{
    (void)arg;
    //由于炫彩灯板中红色led灯的GIPO为10,这里初始化控制GPIO10的控制方式为PWM模式
    IoSetFunc(WIFI_IOT_IO_NAME_GPIO_10,WIFI_IOT_IO_FUNC_GPIO_10_PWM1_OUT);

    //调用函数初始化PWM模式
    PwmInit(WIFI_IOT_PWM_PORT_PWM1);
   
   while(1){
       unsigned short data = 0;
       unsigned short duty = 0;
       //使用AdcRead函数对3通道进行ADC信号读取,读取到的结果存储在data中
       if(AdcRead(WIFI_IOT_ADC_CHANNEL_3,&data,WIFI_IOT_ADC_EQU_MODEL_4,WIFI_IOT_ADC_CUR_BAIS_DEFAULT,0)==WIFI_IOT_SUCCESS)
       {
           printf("data:%d",data);
           duty = PWM_FREQ_DIVITION *(unsigned int)data / ADC_RESOLUTION;
           //128 1820
            //duty = PWM_FREQ_DIVITION * (1948-(unsigned int)data) / ADC_RESOLUTION;

       }
       //PWM模式开启对红色led灯的控制
       PwmStart(WIFI_IOT_PWM_PORT_PWM1,duty,PWM_FREQ_DIVITION);
       usleep(10000);
       //PWM模式关闭对红色led灯的控制
       PwmStop(WIFI_IOT_PWM_PORT_PWM1);

   }
}
static void jltfcloudcn(void)
{
    osThreadAttr_t attr;
    GpioInit();
    attr.name="jltfcloudcom";
    attr.attr_bits=0U;
    attr.cb_mem=NULL;
    attr.cb_size=0U;
    attr.stack_mem=NULL;
    attr.stack_size=4096;
    attr.priority=osPriorityNormal;

    if(osThreadNew(jltfcloudcom,NULL,&attr) == NULL){
        printf("[jltfcloudcn] Failed to create jltfcloudcom!
");
    }

}
APP_FEATURE_INIT(jltfcloudcn);
灯亮从弱到强
灯光弱\n
灯光弱


代码
#include<stdio.h>
#include<unistd.h>

#include "ohos_init.h"
#include "cmsis_os2.h"
#include "wifiiot_gpio.h"
#include "wifiiot_gpio_ex.h"
#include "wifiiot_pwm.h"
#include "wifiiot_adc.h"
#include "wifiiot_errno.h"

#define LED_DELAY_TIME_US 300000
#define LED_BRIGHT WIFI_IOT_GPIO_VALUE1
#define LED_DARK WIFI_IOT_GPIO_VALUE0

#define RED_LED_PIN_NAME WIFI_IOT_IO_NAME_GPIO_10
#define RED_LED_PIN_FUNCTION WIFI_IOT_IO_FUNC_GPIO_10_GPIO

#define GREEN_LED_PIN_NAME WIFI_IOT_IO_NAME_GPIO_11
#define GREEN_LED_PIN_FUNCTION WIFI_IOT_IO_FUNC_GPIO_11_GPIO

#define BLUE_LED_PIN_NAME WIFI_IOT_IO_NAME_GPIO_12
#define BLUE_LED_PIN_FUNCTION WIFI_IOT_IO_FUNC_GPIO_12_GPIO

//设置灯光的初始值
#define NUM_BLINKS 1

#define PWM_FREQ_DIVITION 64000

static void jltfcloudcom(void *arg)
{
    (void)arg;
    IoSetFunc(RED_LED_PIN_NAME,WIFI_IOT_IO_FUNC_GPIO_10_PWM1_OUT);
    IoSetFunc(GREEN_LED_PIN_NAME,WIFI_IOT_IO_FUNC_GPIO_11_PWM2_OUT);
    IoSetFunc(BLUE_LED_PIN_NAME,WIFI_IOT_IO_FUNC_GPIO_12_PWM3_OUT);
    PwmInit(WIFI_IOT_PWM_PORT_PWM1);
    PwmInit(WIFI_IOT_PWM_PORT_PWM2);
    PwmInit(WIFI_IOT_PWM_PORT_PWM3);

    static const WifiIotGpioIdx pins[] = {RED_LED_PIN_NAME,GREEN_LED_PIN_NAME,BLUE_LED_PIN_NAME};
    for(int i = 1 ; i <= NUM_BLINKS ; i++){
        for(int i = 1 ; i <= PWM_FREQ_DIVITION ; i *= 2){
           PwmStart(WIFI_IOT_PWM_PORT_PWM1,i,PWM_FREQ_DIVITION);
           usleep(250000);
       }
        for(int i = 1 ; i <= PWM_FREQ_DIVITION ; i *= 2 ){
           PwmStart(WIFI_IOT_PWM_PORT_PWM2,1,PWM_FREQ_DIVITION);
            // usleep(10);
            // PwmStop(WIFI_IOT_PWM_PORT_PWM2);
        }
        for(int i = 1 ; i <= PWM_FREQ_DIVITION ; i *= 2){
           PwmStart(WIFI_IOT_PWM_PORT_PWM3,1,PWM_FREQ_DIVITION);
        //    usleep(10);
        //    PwmStop(WIFI_IOT_PWM_PORT_PWM3);
       }
        for(unsigned j = 0 ; j < sizeof(pins)/sizeof(pins[0]);j++){
            GpioSetOutputVal(pins[j],LED_BRIGHT);
            usleep(LED_DELAY_TIME_US);
            GpioSetOutputVal(pins[j],LED_DARK);
            usleep(LED_DARK);
        }
    }
   
}
static void jltfcloudcn(void)
{
    osThreadAttr_t attr;
    GpioInit();
    attr.name="jltfcloudcom";
    attr.attr_bits=0U;
    attr.cb_mem=NULL;
    attr.cb_size=0U;
    attr.stack_mem=NULL;
    attr.stack_size=4096;
    attr.priority=osPriorityNormal;

    if(osThreadNew(jltfcloudcom,NULL,&attr) == NULL){
        printf("[jltfcloudcn] Failed to create jltfcloudcom!
");
    }

}
APP_FEATURE_INIT(jltfcloudcn);
温湿度监测
微信截图_20201225121116.png



代码
主代码:
/*
* Copyright (c) 2020, HiHope Community.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this
*    list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice,
*    this list of conditions and the following disclaimer in the documentation
*    and/or other materials provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its
*    contributors may be used to endorse or promote products derived from
*    this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/

#include "aht20.h"

#include <stdio.h>
#include <string.h>
#include <unistd.h>

#include "wifiiot_i2c.h"
#include "wifiiot_errno.h"

#define AHT20_I2C_IDX WIFI_IOT_I2C_IDX_0

#define AHT20_STARTUP_TIME     20*1000 // 上电启动时间
#define AHT20_CALIBRATION_TIME 40*1000 // 初始化(校准)时间
#define AHT20_MEASURE_TIME     75*1000 // 测量时间

#define AHT20_DEVICE_ADDR   0x38
#define AHT20_READ_ADDR     ((0x38<<1)|0x1)
#define AHT20_WRITE_ADDR    ((0x38<<1)|0x0)

#define AHT20_CMD_CALIBRATION       0xBE // 初始化(校准)命令
#define AHT20_CMD_CALIBRATION_ARG0  0x08
#define AHT20_CMD_CALIBRATION_ARG1  0x00

/**
* 传感器在采集时需要时间,主机发出测量指令(0xAC)后,延时75毫秒以上再读取转换后的数据并判断返回的状态位是否正常。
* 若状态比特位[Bit7]为0代表数据可正常读取,为1时传感器为忙状态,主机需要等待数据处理完成。
**/
#define AHT20_CMD_TRIGGER       0xAC // 触发测量命令
#define AHT20_CMD_TRIGGER_ARG0  0x33
#define AHT20_CMD_TRIGGER_ARG1  0x00

// 用于在无需关闭和再次打开电源的情况下,重新启动传感器系统,软复位所需时间不超过20 毫秒
#define AHT20_CMD_RESET      0xBA // 软复位命令

#define AHT20_CMD_STATUS     0x71 // 获取状态命令

/**
* STATUS 命令回复:
* 1. 初始化后触发测量之前,STATUS 只回复 1B 状态值;
* 2. 触发测量之后,STATUS 回复6B: 1B 状态值 + 2B 湿度 + 4b湿度 + 4b温度 + 2B 温度
*      RH = Srh / 2^20 * 100%
*      T  = St  / 2^20 * 200 - 50
**/
#define AHT20_STATUS_BUSY_SHIFT 7       // bit[7] Busy indication
#define AHT20_STATUS_BUSY_MASK  (0x1<<AHT20_STATUS_BUSY_SHIFT)
#define AHT20_STATUS_BUSY(status) ((status & AHT20_STATUS_BUSY_MASK) >> AHT20_STATUS_BUSY_SHIFT)

#define AHT20_STATUS_MODE_SHIFT 5       // bit[6:5] Mode Status
#define AHT20_STATUS_MODE_MASK  (0x3<<AHT20_STATUS_MODE_SHIFT)
#define AHT20_STATUS_MODE(status) ((status & AHT20_STATUS_MODE_MASK) >> AHT20_STATUS_MODE_SHIFT)

                                        // bit[4] Reserved
#define AHT20_STATUS_CALI_SHIFT 3       // bit[3] CAL Enable
#define AHT20_STATUS_CALI_MASK  (0x1<<AHT20_STATUS_CALI_SHIFT)
#define AHT20_STATUS_CALI(status) ((status & AHT20_STATUS_CALI_MASK) >> AHT20_STATUS_CALI_SHIFT)
                                        // bit[2:0] Reserved

#define AHT20_STATUS_RESPONSE_MAX 6

#define AHT20_RESOLUTION            (1<<20)  // 2^20

#define AHT20_MAX_RETRY 10

static uint32_t AHT20_Read(uint8_t* buffer, uint32_t buffLen)
{
    WifiIotI2cData data = { 0 };
    data.receiveBuf = buffer;
    data.receiveLen = buffLen;
    uint32_t retval = I2cRead(AHT20_I2C_IDX, AHT20_READ_ADDR, &data);
    if (retval != WIFI_IOT_SUCCESS) {
        printf("I2cRead() failed, %0X!
", retval);
        return retval;
    }
    return WIFI_IOT_SUCCESS;
}

static uint32_t AHT20_Write(uint8_t* buffer, uint32_t buffLen)
{
    WifiIotI2cData data = { 0 };
    data.sendBuf = buffer;
    data.sendLen = buffLen;
    uint32_t retval = I2cWrite(AHT20_I2C_IDX, AHT20_WRITE_ADDR, &data);
    if (retval != WIFI_IOT_SUCCESS) {
        printf("I2cWrite(%02X) failed, %0X!
", buffer[0], retval);
        return retval;
    }
    return WIFI_IOT_SUCCESS;
}

// 发送获取状态命令
static uint32_t AHT20_StatusCommand(void)
{
    uint8_t statusCmd[] = { AHT20_CMD_STATUS };
    return AHT20_Write(statusCmd, sizeof(statusCmd));
}

// 发送软复位命令
static uint32_t AHT20_ResetCommand(void)
{
    uint8_t resetCmd[] = {AHT20_CMD_RESET};
    return AHT20_Write(resetCmd, sizeof(resetCmd));
}

// 发送初始化校准命令
static uint32_t AHT20_CalibrateCommand(void)
{
    uint8_t clibrateCmd[] = {AHT20_CMD_CALIBRATION, AHT20_CMD_CALIBRATION_ARG0, AHT20_CMD_CALIBRATION_ARG1};
    return AHT20_Write(clibrateCmd, sizeof(clibrateCmd));
}

// 读取温湿度值之前, 首先要看状态字的校准使能位Bit[3]是否为 1(通过发送0x71可以获取一个字节的状态字),
// 如果不为1,要发送0xBE命令(初始化),此命令参数有两个字节, 第一个字节为0x08,第二个字节为0x00。
uint32_t jltfcloudcom_Calibrate(void)
{
    uint32_t retval = 0;
    uint8_t buffer[AHT20_STATUS_RESPONSE_MAX];
    memset(&buffer, 0x0, sizeof(buffer));

    retval = AHT20_StatusCommand();
    if (retval != WIFI_IOT_SUCCESS) {
        return retval;
    }

    retval = AHT20_Read(buffer, sizeof(buffer));
    if (retval != WIFI_IOT_SUCCESS) {
        return retval;
    }

    if (AHT20_STATUS_BUSY(buffer[0]) || !AHT20_STATUS_CALI(buffer[0])) {
        retval = AHT20_ResetCommand();
        if (retval != WIFI_IOT_SUCCESS) {
            return retval;
        }
        usleep(AHT20_STARTUP_TIME);
        retval = AHT20_CalibrateCommand();
        usleep(AHT20_CALIBRATION_TIME);
        return retval;
    }

    return WIFI_IOT_SUCCESS;
}

// 发送 触发测量 命令,开始测量
uint32_t jltfcloudcom_StartMeasure(void)
{
    uint8_t triggerCmd[] = {AHT20_CMD_TRIGGER, AHT20_CMD_TRIGGER_ARG0, AHT20_CMD_TRIGGER_ARG1};
    return AHT20_Write(triggerCmd, sizeof(triggerCmd));
}

// 接收测量结果,拼接转换为标准值
uint32_t jltfcloudcn_GetMeasureResult(float* oC, float* humidity)
{
    uint32_t retval = 0, i = 0;
    if (oC == NULL || humidity == NULL) {
        return WIFI_IOT_FAILURE;
    }

    uint8_t buffer[AHT20_STATUS_RESPONSE_MAX];
    memset(&buffer, 0x0, sizeof(buffer));
    retval = AHT20_Read(buffer, sizeof(buffer));  // recv status command result
    if (retval != WIFI_IOT_SUCCESS) {
        return retval;
    }

    for (i = 0; AHT20_STATUS_BUSY(buffer[0]) && i < AHT20_MAX_RETRY; i++) {
        // printf("AHT20 device busy, retry %d/%d!
", i, AHT20_MAX_RETRY);
        usleep(AHT20_MEASURE_TIME);
        retval = AHT20_Read(buffer, sizeof(buffer));  // recv status command result
        if (retval != WIFI_IOT_SUCCESS) {
            return retval;
        }
    }
    if (i >= AHT20_MAX_RETRY) {
        printf("AHT20 device always busy!
");
        return WIFI_IOT_FAILURE;
    }

    uint32_t humiRaw = buffer[1];
    humiRaw = (humiRaw << 8) | buffer[2];
    humiRaw = (humiRaw << 4) | ((buffer[3] & 0xF0) >> 4);
    *humidity = humiRaw / (float)AHT20_RESOLUTION * 100;

    uint32_t tempRaw = buffer[3] & 0x0F;
    tempRaw = (tempRaw << 8) | buffer[4];
    tempRaw = (tempRaw << 8) | buffer[5];
    *oC = tempRaw / (float)AHT20_RESOLUTION * 200 - 50;
    // printf("humidity = %05X, %f, oC= %05X, %f
", humiRaw, *humidity, tempRaw, *oC);
    return WIFI_IOT_SUCCESS;
}

引用文件:
#ifndef AHT20_H
#define AHT20_H

#include <stdint.h>

uint32_t jltfcloudcom_Calibrate(void);

uint32_t jltfcloudcom_StartMeasure(void);

uint32_t jltfcloudcn_GetMeasureResult(float* oC, float* humidity);

#endif  // AHT20_H
代码执行入口:
/*
* Copyright (c) 2020, HiHope Community.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this
*    list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice,
*    this list of conditions and the following disclaimer in the documentation
*    and/or other materials provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its
*    contributors may be used to endorse or promote products derived from
*    this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/

#include "aht20.h"

#include <stdio.h>
#include <unistd.h>

#include "ohos_init.h"
#include "cmsis_os2.h"
#include "wifiiot_gpio.h"
#include "wifiiot_gpio_ex.h"
#include "wifiiot_i2c.h"

void Aht20TestTask(void* arg)
{
    (void) arg;
    uint32_t retval = 0;

    IoSetFunc(WIFI_IOT_IO_NAME_GPIO_13, WIFI_IOT_IO_FUNC_GPIO_13_I2C0_SDA);
    IoSetFunc(WIFI_IOT_IO_NAME_GPIO_14, WIFI_IOT_IO_FUNC_GPIO_14_I2C0_SCL);

    I2cInit(WIFI_IOT_I2C_IDX_0, 400*1000);

    retval = jltfcloudcom_Calibrate();
    printf("jltfcloudcom_Calibrate: %d
", retval);

    while (1) {
        float oC = 0.0, humidity = 0.0;

        retval = jltfcloudcom_StartMeasure();
        printf("jltfcloudcom_StartMeasure: %d
", retval);

        retval = jltfcloudcn_GetMeasureResult(&oC, &humidity);
        printf("jltfcloudcn_GetMeasureResult: %d, oC = %.2f, humidity = %.2f
", retval, oC, humidity);

        sleep(1);
    }
}

void Aht20Test(void)
{
    osThreadAttr_t attr;

    attr.name = "Aht20Task";
    attr.attr_bits = 0U;
    attr.cb_mem = NULL;
    attr.cb_size = 0U;
    attr.stack_mem = NULL;
    attr.stack_size = 4096;
    attr.priority = osPriorityNormal;

    if (osThreadNew(Aht20TestTask, NULL, &attr) == NULL) {
        printf("[Aht20Test] Failed to create Aht20TestTask!
");
    }
}
APP_FEATURE_INIT(Aht20Test);
可然气体监测



代码
/*
* Copyright (c) 2020 Huawei Device Co., Ltd.
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
*     http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/

#include <stdio.h>

#include <unistd.h>

#include "ohos_init.h"
#include "cmsis_os2.h"
#include "wifiiot_gpio.h"
#include "wifiiot_gpio_ex.h"
#include "wifiiot_errno.h"

#include <hi_types_base.h>
#include <hi_io.h>
#include <hi_early_debug.h>
#include <hi_gpio.h>
#include <hi_task.h>

#include <hi_types_base.h>

#include <hi_adc.h>
#include <hi_pwm.h>
#include <hi_stdlib.h>
#include <hi_early_debug.h>
#include <hi_timer.h>

#define ADC_TEST_LENGTH  64
#define VLT_MIN 100

hi_u16 g_adc_buf[ADC_TEST_LENGTH] = { 0 };
float gas_detection_value = 0.0;

float jltfcloudcom(hi_u32 data_len)
{
    hi_u32 i;
    float vlt_max = 0;
    float vlt_min = VLT_MIN;
    float vlt_sum = 0;
    float vlt_val = 0;

    hi_u16 vlt;
    for (i = 0; i < data_len; i++) {
        vlt = g_adc_buf;
        float voltage = hi_adc_convert_to_voltage(vlt);
        vlt_max = (voltage > vlt_max) ? voltage : vlt_max;//三目运算   判断电压的大小
        vlt_min = (voltage < vlt_min) ? voltage : vlt_min;
        vlt_sum += voltage;
    }
    //printf("vlt_min:%.3f, vlt_max:%.3f
", vlt_min, vlt_max);

    vlt_val = (vlt_sum - vlt_min - vlt_max) / (data_len - 2.0);   

    return vlt_val;
}

void jltfcloudcn(void)
{
    hi_u32 ret, i;
    hi_u16 data;  /* 10 */

    memset_s(g_adc_buf, sizeof(g_adc_buf), 0x0, sizeof(g_adc_buf));

    for (i = 0; i < ADC_TEST_LENGTH; i++) {
        ret = hi_adc_read((hi_adc_channel_index)HI_ADC_CHANNEL_5, &data, HI_ADC_EQU_MODEL_1, HI_ADC_CUR_BAIS_DEFAULT, 0);
        if (ret != HI_ERR_SUCCESS) {
            printf("ADC Read Fail
");
            return;
        }
        g_adc_buf = data;
    }

    gas_detection_value = jltfcloudcom(ADC_TEST_LENGTH);
}

static void MQ2_demo(const char* arg)
{   
    (void)arg;
   
    printf("Enter the MQ2_demo ...
");

    while (1) {

        jltfcloudcn();

        if(gas_detection_value > 1.5)
        {
            hi_pwm_start(HI_PWM_PORT_PWM0, 30000 / 2, 30000);
            usleep(2 * 1000 * 1000);
            hi_pwm_stop(HI_PWM_PORT_PWM0);
        }
      
        printf("gas_detection_value = %f
" , gas_detection_value);

        usleep(100 * 1000);
    }

    return;
}

static void hmtimescn(void)
{
    unsigned int ret = 0;
    GpioInit();

    //蜂鸣器初始化
    hi_pwm_set_clock(PWM_CLK_XTAL); //设置时钟源为晶体时钟;
    IoSetFunc(WIFI_IOT_IO_NAME_GPIO_9, WIFI_IOT_IO_FUNC_GPIO_9_PWM0_OUT);//IO复用为PWM功能
    ret = GpioSetDir(WIFI_IOT_IO_NAME_GPIO_9, WIFI_IOT_GPIO_DIR_OUT);//设置为输出
    if (ret != WIFI_IOT_SUCCESS) {
        printf("===== ERROR ======gpio -> GpioSetDir ret:%d
", ret);
        return;
    }
    hi_pwm_init(HI_PWM_PORT_PWM0);//初始化PWM

    hi_io_set_func(HI_IO_NAME_GPIO_11, HI_IO_FUNC_GPIO_11_GPIO); /* GPIO11 ADC5 */

    ret = hi_gpio_set_dir(HI_GPIO_IDX_11, HI_GPIO_DIR_IN);
    if (ret != HI_ERR_SUCCESS) {
        printf("===== ERROR ======gpio -> hi_gpio_set_dir1 ret:%d
", ret);
        return;
    }
   
    osThreadAttr_t attr = {0};
   
    attr.name = "MQ2_demo";
    attr.attr_bits = 0U;
    attr.cb_mem = NULL;
    attr.cb_size = 0U;
    attr.stack_mem = NULL;
    attr.stack_size = 1024;
    attr.priority = osPriorityNormal;   

    if(osThreadNew((osThreadFunc_t)MQ2_demo,NULL,&attr) == NULL)
    {
        printf("Failed to create MQ2_demo !
");
    }   
}

SYS_RUN(hmtimescn);


五、关于产品完善

后续可以考虑将HI3861,鸿蒙操作系统软总线,基于鸿蒙操作系统的应用服务,将更多可融合功能比如音箱等进行植入,以灯为载体,打造一个全新的鸿蒙智能物联灯爆款系列产品。



原文链接:【码上评选】HarmonyOS润和HiSpark智能物联灯产品实现初试











``灯光强\n
灯光强
微信截图_20201225121414.png

回帖

声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容图片侵权或者其他问题,请联系本站作侵删。 侵权投诉
链接复制成功,分享给好友