Qt+Raspberry pi 3B+ 讀取ds18b20溫度傳感器的值

因爲項目需要,要在上位機界面實時顯示室內溫度,上位機採用QT5.5編寫,採用DS18B20採集數據,顯示在控件lcdNumber上。DS18B20是一個比較常用的溫度傳感器,採用單總線控制,在linux中,一切都是文件,所以數據採集也是文件的讀取。

一、修改配置文件
在/boot/config.txt文件後面添加下面這一句

sudo vi /boot/config.txt

dtoverlay=w1-gpio

這一句就是樹莓派添加Device Tree設備,dtoverlay=w1-gpio表示添加單總線設備,也可以寫成dtoverlay=w1-gpio,gpioin=4默認管腳爲BCM編號4,如果DS18B20接到其他管腳則需要修改這個值,在微雪電子的樹莓派擴展板上Pioneer 600擴展板DS18B20默認接到4,故不用修改。

二、查看模塊是否啓動

重啓樹莓派使設置生效,運行lsmod命令,如果發現紅色方框的兩個模塊說明模塊已啓動。
出現空曠中
如果沒有發現,也可以運行如下命令加載模塊

sudo modprobe w1_gpio
sudo modprobe w1_therm

三、 讀取溫度

如果沒有問題,在/sys/bus/w1/devices中發現一個28-XXXX開頭的文件夾,這個就是DS18B20的ROM,每個DS18B20都一樣,連接多個18B20就會有多個這樣的文件,在這個文件夾中再讀取w1_slave文件則會返回當前溫度值。

這裏我們先進去打印一下,看看有哪些數值:

	sudo modprobe w1-gpio
	sudo modprobe w1-therm
	cd  /sys/bus/w1/devices
	cd 28-00000xxx
	cat w1_slave

在這裏插入圖片描述
在返回數據中,第一行最後的YRS表示CRC校驗成功,數據有效。第二行最後t=30500表示當前溫度爲30.5攝氏度。
按照此邏輯,只要反覆讀取這個文件中的t值即可顯示溫度。

四:QT界面顯示溫度

在QT中ui界面拖選一個lcdNumber,然後使用定時器定時去讀取數值,顯示在這個控件上即可;參照一個大佬的程序:QT+樹莓派讀取溫度,在實際使用中有一點問題,一是顯示在lcdNumber上,必須是個字符串,而我想要的是帶小數點的溫度值。二是涉及到一些數值類型裝換,如讀到的值是30500,實際要顯示爲30.5。三是樹莓派直接接DS18B20是找不到上面所說的文件的,必須要在DS18B20的VCC和數據引腳之間接一個4.7K的上拉電阻纔可以。

五:源程序

.h文件
只是添加一些要用到的包,再聲明一個信號函數private slots:void cj();

#ifndef MAINWINDOW_H
#define MAINWINDOW_H

#include <QMainWindow>
#include <QString>
#include <QDir>
#include <QStringList>
#include <QMessageBox>
#include <QTextStream>
#include <QDebug>
#include <QTimer>
#include <QTime>
#inclede <QTextCodec>

namespace Ui {
class MainWindow;
}

class MainWindow : public QMainWindow
{
    Q_OBJECT

public:
    explicit MainWindow(QWidget *parent = 0);
    ~MainWindow();


private slots:

    void cj();

private:
    Ui::MainWindow *ui;
    QDebug *Debug;
};

#endif // MAINWINDOW_H

.cpp文件


MainWindow::~MainWindow()
{
    delete ui;
}

void MainWindow::cj()
{


        system("sudo modprobe w1-gpio");
        system("sudo modprobe w1-therm");

        QString tempFile="/sys/bus/w1/devices/";
        qDebug() << tempFile;
        QString tempData;

        //設置ds18b20的文件所在位置
        QDir tempPath("/sys/bus/w1/devices/");

        //得到所有的文件列表
        QStringList fileList=tempPath.entryList();
        //遍歷所有文件,找到關於ds18b20的文件
        int i=0;
        while(i<fileList.size())
        {
            if(fileList.at(i).contains("28-"))
            {
                tempFile.append(fileList.at(i));  //已經找到了文件
                break;
            }
            i++;
        }
        tempFile.append("/w1_slave");
        qDebug() << tempFile;
        QFile file(tempFile);
        if(!file.open(QIODevice::ReadOnly|QFile::Text))
        {
            QMessageBox::information(this,tr("fgbdfgds"),tr("hjggnfghn"));
            return;
        }
        QTextStream in(&file);

        //根據存儲的文件找到需要的數據
        QString str=in.readAll(); //讀出所有內容
//        qDebug() << str;
        tempData=str.mid(str.indexOf('t')+2,3); //定位數據的位置,找到所需要的數據,精度可以達到小數點後三位,本程序只    需一位

        float temp = tempData.toFloat();       // 將字符類型轉換爲float
        float temp2 = temp/10;                    // 將float進行運算得到小數點
        QString temp3 = QString::number(temp2,'f',2);   // 再將float轉換爲字符型,2代表小數點後幾位
        ui->lcdNumber->display(temp3);
        file.close();

}

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章