[作品] 【樹莓派Pico測評】-制作紅外體溫計( I2C接口測試+MLX90614)

fxyc87 樓主
2021-2-7 16:40
本帖最后由 fxyc87 于 2021-2-7 16:46 編輯

我上個貼子發布了如何利用USB進行串口通信,

【樹莓派Pico測評】- USB CDC串口通信(BSP編譯,非MicroPython)

這次發布一個I2C的例子,剛好我手頭上有MLX90614,市場上的手持紅外測溫的清一色的都是用的它

這個芯片我買了大概5-6年了,一直吃灰,剛好最近玩PICO時又從寶箱里翻出了它,剛好在這個疫情后時代用得上

程序基于我上次的程序進行修改,這里我只發出主程序

#include <stdio.h>
#include "pico/stdlib.h"
#include "pico/stdio_usb.h"
#include "hardware/i2c.h"

// I2C 聲明
#define I2C_PORT i2c0
#define I2C_SDA 0
#define I2C_SCL 1
//MLX90614 聲明
#define MLX90614_ADDR 0x5a        //地址

#define CMD_RAM(n)  (0|n)
#define CMD_EEPROM(n) (32|n)                 //001x xxxx* EEPROM Access
#define CMD_FLAG(n) (0xf0)            //1111_0000** Read Flags
#define CMD_SLEEP(n) (0xff)                      //1111_1111 Enter SLEEP mode


//led 聲明
#define LED 25
//usb 聲明

//函數申明
int ReadData(uint8_t reg_addr);       //
//變量申明
uint16_t MLX90614_value;            //讀取的16位原始結果

int main()
{
    //USB初始化
    stdio_usb_init();
    //LED初始化
    gpio_init(LED);
    gpio_set_dir(LED,GPIO_OUT);
    gpio_put(LED,1);
    //LED閃爍提示
    sleep_ms(5000);
    for(int i=0;i<10;i++){
        sleep_ms(100);
        gpio_put(LED,0);
        sleep_ms(100);
        gpio_put(LED,1);
    }

    //MLX90614切換到I2C模式,SCL至少低電平 1.44ms
    gpio_set_function(I2C_SCL, GPIO_FUNC_SIO);
    gpio_set_dir(I2C_SCL, GPIO_OUT);
    gpio_put(I2C_SCL, 0);
    sleep_ms(5);
    gpio_put(I2C_SCL, 1);
    sleep_ms(30);

    // I2C 50Khz.
    i2c_init(I2C_PORT, 50*1000);
    
    gpio_set_function(I2C_SDA, GPIO_FUNC_I2C);
    gpio_set_function(I2C_SCL, GPIO_FUNC_I2C);
    gpio_pull_up(I2C_SDA);
    gpio_pull_up(I2C_SCL);

    /*  MLX90614 RAM地址
ta本體溫度,      6
溫度1              7
溫度2              8
    */

    /*  MLX90614 EEPROM地址
Tomax           0x00 Yes
Tomin           0x01 Yes
PWMCTRL     0x02 Yes
Ta range        0x03 Yes
Emissivity      0x04 Yes
Config Register1 0x05 Yes
SMBus address (LSByte only) 0x0E Yes
    */
    //讀取EEPROM配置數據
    float max, min;

    int r= ReadData(CMD_EEPROM(0));
    if (r < 3) {
        printf("讀取配置失敗\n");
        while (1);
    }
    printf("dat:%d\n", MLX90614_value);
    max = MLX90614_value / 100.0f - 273.15f;
    printf("Tomax:%f\n", max);
    r = ReadData(CMD_EEPROM(1));
    if (r < 3) {
        printf("讀取RAM失敗\n");
        while (1);
    }
    printf("dat:%d\n", MLX90614_value);
    min = MLX90614_value / 100.0f - 273.15f;
    printf("Tomax:%f\n", min);

    while(1){
        //本體溫度
        float temp1,temp2;
        int r;

        r = ReadData(CMD_RAM(6));
        if (r < 3) {
            printf("讀取溫度6失敗\n");
            while (1);
        } 
        temp1 = MLX90614_value * 0.02f-273.15;

        r = ReadData(CMD_RAM(7));
        if (r < 3) {
            printf("讀取溫度7失敗\n");
            while (1);
        }
        temp2 = MLX90614_value * 0.02f - 273.15;
        printf("temp:%3.2f,%3.2f  \t@eeworld.fxyc87\n", temp1,temp2);

       //打印出讀的數據
        
        gpio_put(LED, 1);
        sleep_ms(500);
        gpio_put(LED, 0);
        sleep_ms(500);
    }

    return 0;
}
/*
讀取MLX90614寄存器數據   
reg_addr 地址有 CMD_RAM(a),CMD_EEPROM(a),CMD_FLAG(a),CMD_SLEEP(a)
讀取成功,返回數據長度
失敗:-1
*/
int ReadData(uint8_t reg_addr) {       //
    uint8_t bf[3];
    int r = 0;
        //先寫站號及命令碼 nostop=false 寫入后不發送i2c停止指令
        //PICO_ERROR_TIMEOUT
    r = i2c_write_timeout_us(I2C_PORT, MLX90614_ADDR, &reg_addr, 1, true, 2000);    //超時2ms
    if (r < 1) {
        return -1;
    }
    //再讀數據      lsb,msb,pec
    r = i2c_read_timeout_us(I2C_PORT, MLX90614_ADDR, &bf[0], 3, false, 2000);
    if (r < 1) {
        return -1;
    }
    MLX90614_value = bf[0] + (bf[1] << 8);
    return r;
}

以主是主程序,程序比較簡單,輸出當前溫度及芯片本體溫度,參數及地址參照MLX90614手冊進行就好了

企業微信截圖_20210207153809.png

 

編譯主程序,并且復制程序

企業微信截圖_20210207162257.png

硬件鏈接圖:

微信圖片_20210207163023.jpg

運行效果展示

企業微信截圖_20210207162234.png

從上圖中可以看出,室溫/芯片溫度約16度左右,基本正常,手摸一下溫度會慢慢升高

目標物體溫度,無物體時約15.61度,差不多室溫,手腕放主去,2秒后升到33度左右,

和公司的每天早上量體溫的機器基本一致,至于為什么不是36,37度我也不知道,應該是出廠就校準過的啊,不應該差這么多吧?可能是一些參數還需要配置,比如測量溫度上下限等,有空了再試試。

等節后了加工一個PCB,再找個漂亮的盒子,再搞個小屏,這樣就是一個成品模塊了。

這芯片買的時候180,現在估計賣300也能賣出去,哈,增值啊。

不該2019年底的時候把 MLX90640,如果這個沒賣玩起來更爽。32*24像素的紅外相機啊!

 

再列個網址 https://raspberrypi.github.io/pico-sdk-doxygen/group__hardware__i2c.html

這個網址是關于I2C的SDK API說明,當然其它API這里也有看到介紹

https://raspberrypi.github.io/pico-sdk-doxygen/group__hardware.html

 

游客,如果您要查看本帖隱藏內容請回復

回復評論 (6)

沙發 fxyc87

2021-2-7 17:22

mlx90614 接線圖.png

硬件鏈接

SDA接P00,

SCL接P01

板凳 annysky2012

2021-2-8 09:30
贊贊贊贊,期待成品。這個靈敏度怎么樣

4樓 fxyc87

2021-2-8 09:44
引用: annysky2012 發表于 2021-2-8 09:30 贊贊贊贊,期待成品。這個靈敏度怎么樣

MLX90614有好幾個子系列,

5V的,3V的,還有角度

有90度視野的,有30度,有10度的,

還有溫度有+-1度,+-0.5度的,+-0.1度的,好幾個級別呢,

我這個是最普通的,

5樓 kangkls

2021-2-9 08:22

國產的測溫計很多賣20塊錢,不知道用的 那個測溫芯片,速度快,但是不準

http://www.jslaser.com高性價比激光測距傳感器

6樓 joeymm

2021-2-9 10:57

1.用614測溫應該使用醫療級別的型號,而不是工業級別的型號

2.測體表溫度與實際值偏差大,是因為你缺少一個值換算的經驗公式~

7樓 fxyc87

2021-2-9 11:13
引用: joeymm 發表于 2021-2-9 10:57 1.用614測溫應該使用醫療級別的型號,而不是工業級別的型號 2.測體表溫度與實際值偏差大,是因為你缺少 ...

對,實際上就是校準

電子工程世界版權所有 京B2-20211791 京ICP備10001474號-1 京公網安備 11010802033920號
    我也要說兩句
    發送
    評論
    萝卜大香蕉