gzrm 发表于 2013-6-26 23:53:01

请教利用树莓派连接DHT11上传YEELINK的方法

我是个新手,已按网上的教程,将DTH11连接树莓派并显示湿度和温度数据了,现在不知该怎样连接yeelink的传感器,之前按教程连接摄像头成功,但网上找不到如何连接YEELINK的程序。
我是参考这教程http://hugozhu.myalert.info/2013 ... h-raspberry-pi.html操作的,但教程是教连接coms.com;请热心人指导

钱学森℡ 发表于 2015-1-25 20:07:47

代码写的不好,请见谅
DHT11引脚连接:GND---GND   VCC---3.3V   DATA---GPIO1
注:需要安装wiringpi和smbus
在树莓派的/home/pi里:
新建文本yeelink.py
内容:#!/usr/bin/python
import os
import commands
import requests
import json
from time import strftime, sleep
#apikey换成你自己的,设备ID也是
headers = {"U-ApiKey": "ffd6293ec3a7b1025ae9b3a262xxxxxx"}
DEVICE_ID = "17618"
RH_ID = "30658"
TMP_ID = "30651"

def upload_temp(sensor_type, temp):

    if sensor_type == "RH":
      sensor_id = RH_ID
      print "RH:", temp
      url = r"http://api.yeelink.net/v1.1/device/%s/sensor/%s/datapoints" % (DEVICE_ID, sensor_id)
      #print url
      data = {"timestamp": strftime("%Y-%m-%dT%H:%M:%S"), "value": temp}
      #print data
      r = requests.post(url, data=json.dumps(data), headers=headers)
    else:
      sensor_id = TMP_ID
      print "TEMP:", temp
      url = r"http://api.yeelink.net/v1.1/device/%s/sensor/%s/datapoints" % (DEVICE_ID, sensor_id)
      #print url
      data = {"timestamp": strftime("%Y-%m-%dT%H:%M:%S"), "value": temp}
      #print data
      r = requests.post(url, data=json.dumps(data), headers=headers)
while True:
    p = os.popen('sudo ./sensor1')
    rh = p.readline();
    q = os.popen('sudo ./sensor')
    tmp = q.readline();
    upload_temp("RH", rh)
    upload_temp("TEMP",tmp)
    sleep(20)
新建文本sensor.c
内容:#include <wiringPi.h>
#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#define MAX_TIME 85
#define GpioPort 1

//存储读取的数据
int dht11_val = { 0, 0, 0, 0, 0 };
//此函数读取温度值
int dht11_read_val(){
    uint8_t lststate = HIGH;//HIGH在wiringPi.h定义为1
    uint8_t counter = 0;//计数器
    uint8_t j = 0, i;
    //初始化数组为0
    for (i = 0; i < 5; i++)
      dht11_val = 0;
    //发送开始信号
    pinMode(GpioPort, OUTPUT);//设置GPIO为输出
    digitalWrite(GpioPort, LOW);//保持低电平至少18ms
    delay(18);
    digitalWrite(GpioPort, HIGH);//保持高电平20-40us
    delayMicroseconds(40);
    //开始接受dht响应信号
    pinMode(GpioPort, INPUT);//设置GPIO为输入
    //开始等待温度传感器回应(根据数据手册温度传感器回应时会拉低数据线)
    for (i = 0; i < MAX_TIME; i++)
    {
      counter = 0;
      while (digitalRead(GpioPort) == lststate){//如果此时的电平和当前电平相等说明电平没有发生变化,所以继续等下一次循环
            counter++;
            delayMicroseconds(1);
            if (counter == 255)//如果在循环了255+1次之后温度传感器还未变换数据线则退出此次循环
                break;
      }
      lststate = digitalRead(GpioPort);//读取数据线最新的状态值
      if (counter == 255)//如果在循环了255+1次之后温度传感器还未变换数据线则退出此次循环
            break;
      //前三次被忽略可能是在等温度传感器响应(这玩意不是数据手册上说的反应那么快的....)
      if ((i >= 4) && (i % 2 == 0)){//对2取余是因为偶数电平是用来传输数据的(从数据手册可以看出)
            dht11_val <<= 1;//左移一位(此时最后一位为0)
            if (counter > 16) //此处时间很长代表此处为1
                dht11_val |= 1; //将数据1写入
            j++;
      }
    }
    /*
    开始处理数据

    1.因为一次完整的数据输出为40位,所以j应大于40
    2.dht11_val为校验和,此处判断校验和是否正确
    3.只打印dht11_val, dht11_val是因为dht11_val, dht11_val?切∈糠郑菔菔植嵝∈贾瘴?
    */
    if ((j >= 40) && (dht11_val == ((dht11_val + dht11_val + dht11_val + dht11_val) & 0xFF))){
      //printf("RH:%d,TEMP:%d\n", dht11_val, dht11_val);
      printf("%d",dht11_val);
      return 1;
    }
    else
      return 0;
}
int main(void){
    //重复5次进行尝试
    int attempts = 5;
    //初始化GPIO
    if (wiringPiSetup() == -1)
      exit(1);
    //进行5次尝试
    while (attempts){
      //获取温度值
      int success = dht11_read_val();
      //获取成功后退出
      if (success)
            break;
      attempts--;
      delay(2500);
    }
    return 0;
}新建文本sensor1.c
内容:#include <wiringPi.h>
#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#define MAX_TIME 85
#define GpioPort 1

//存储读取的数据
int dht11_val = { 0, 0, 0, 0, 0 };
//此函数读取温度值
int dht11_read_val(){
    uint8_t lststate = HIGH;//HIGH在wiringPi.h定义为1
    uint8_t counter = 0;//计数器
    uint8_t j = 0, i;
    //初始化数组为0
    for (i = 0; i < 5; i++)
      dht11_val = 0;
    //发送开始信号
    pinMode(GpioPort, OUTPUT);//设置GPIO为输出
    digitalWrite(GpioPort, LOW);//保持低电平至少18ms
    delay(18);
    digitalWrite(GpioPort, HIGH);//保持高电平20-40us
    delayMicroseconds(40);
    //开始接受dht响应信号
    pinMode(GpioPort, INPUT);//设置GPIO为输入
    //开始等待温度传感器回应(根据数据手册温度传感器回应时会拉低数据线)
    for (i = 0; i < MAX_TIME; i++)
    {
      counter = 0;
      while (digitalRead(GpioPort) == lststate){//如果此时的电平和当前电平相等说明电平没有发生变化,所以继续等下一次循环
            counter++;
            delayMicroseconds(1);
            if (counter == 255)//如果在循环了255+1次之后温度传感器还未变换数据线则退出此次循环
                break;
      }
      lststate = digitalRead(GpioPort);//读取数据线最新的状态值
      if (counter == 255)//如果在循环了255+1次之后温度传感器还未变换数据线则退出此次循环
            break;
      //前三次被忽略可能是在等温度传感器响应(这玩意不是数据手册上说的反应那么快的....)
      if ((i >= 4) && (i % 2 == 0)){//对2取余是因为偶数电平是用来传输数据的(从数据手册可以看出)
            dht11_val <<= 1;//左移一位(此时最后一位为0)
            if (counter > 16) //此处时间很长代表此处为1
                dht11_val |= 1; //将数据1写入
            j++;
      }
    }
    /*
    开始处理数据

    1.因为一次完整的数据输出为40位,所以j应大于40
    2.dht11_val为校验和,此处判断校验和是否正确
    3.只打印dht11_val, dht11_val是因为dht11_val, dht11_val?切∈糠郑菔菔植嵝∈贾瘴?
    */
    if ((j >= 40) && (dht11_val == ((dht11_val + dht11_val + dht11_val + dht11_val) & 0xFF))){
      //printf("RH:%d,TEMP:%d\n", dht11_val, dht11_val);
      printf("%d",dht11_val);
      return 1;
    }
    else
      return 0;
}
int main(void){
    //重复5次进行尝试
    int attempts = 5;
    //初始化GPIO
    if (wiringPiSetup() == -1)
      exit(1);
    //进行5次尝试
    while (attempts){
      //获取温度值
      int success = dht11_read_val();
      //获取成功后退出
      if (success)
            break;
      attempts--;
      delay(2500);
    }
    return 0;
}执行命令:

sudo gcc -o sensor sensor.c -L/usr/local/lib -lwiringPi
sudo gcc -o sensor1 sensor1.c -L/usr/local/lib -lwiringPi

sudo python yeelink.py
即可

钱学森℡ 发表于 2015-1-25 20:08:27

本帖最后由 钱学森℡ 于 2015-1-30 17:27 编辑

不懂再问我。。。。。
页: [1]
查看完整版本: 请教利用树莓派连接DHT11上传YEELINK的方法