请选择 进入手机版 | 继续访问电脑版

『瀚思彼岸』» 智能家居技术论坛

 找回密码
 立即注册
查看: 195|回复: 7

[求助] 求大佬教下16进制温湿度怎么解析

[复制链接]

7

主题

369

帖子

1711

积分

金牌会员

Rank: 6Rank: 6

积分
1711
金钱
1342
HASS币
0
发表于 2021-4-28 00:55:06 | 显示全部楼层 |阅读模式
户外温湿度探测器通讯协议
一、 协议格式
1.1、描述
  每条协议指令都已固定的长度传输,以十六进制方式发送。
1.2、格式
设备类别 数据长度 数据类型 数据段
1.3、格式详解
设备类别:用于识别设备类型,占用 1 字节。 软件版本和硬件版本:高四位为软件版本,低四位为硬件版本。 数据长度:数据类型与数据段的长度。 数据类型:表明数据段中的消息类型。 数据段:实际数据,长度具体由协议中数据长度字节规定。
          软件版本和 硬件版本
                    0xNN
0xNN
0xNN
0xNN
数据字节 1
数据字节 2
数据字节...
数据字节 n
        3/5
户外温湿度探测器通讯协议
二、 指令详解
  详细解释每条指令的功能与格式。
2.1、传感器数据(设备上行)
按照设置时间周期上传
         字节索引
段
描述
            0
0XNN
设备类别
            1
0XNN
软件版本和硬件版本
            2
0XNN
                                                                     例:3D 22 07 00 0915 0526 0E30 户外温湿度检测终端:3D(HEX)→61(DEC)
软件版本 V2.0,硬件版本 V2.0:(22) 数据长度:07(HEX)→07(DEC),有效数据长度 7 字节 数据类型:01,此设备固定类型为 01
温 度:0915(HEX)→2325(DEC)→23.25°C(DEC/100) 湿 度:0526(HEX)→1318(DEC)→13.18%(DEC/100) 电池电压:0E18(HEX)→3608(DEC)→3.608V(DEC/1000)

这个是厂家给的协议,正常用没问题,但是我把他放冰箱冷冻室 报上来的数据是:


{"payload":[4,17,7,1,249,239,24,96,14,212],"qos":0,"retain":false,"_msgid":"18392dfe.c7a6a2","rssi":-55,"Temperature":639.83,"Humidity":62.4,"Voltage":3.796}
我解析出来了是几百度。




回复

使用道具 举报

13

主题

284

帖子

1919

积分

论坛技术达人

积分
1919
金钱
1625
HASS币
0

教程狂人

QQ
发表于 2021-4-28 08:22:25 | 显示全部楼层
63983转换为16进制是F9EF,F9EF转换为有符号数是-1553,实际温度是-15.53℃。去了解一下有符号和无符号数的区别,还有原码,反码和补码

评分

参与人数 2金钱 +30 收起 理由
qjiang + 10 膜拜大神!
27hh + 20 大神666!

查看全部评分

回复

使用道具 举报

7

主题

369

帖子

1711

积分

金牌会员

Rank: 6Rank: 6

积分
1711
金钱
1342
HASS币
0
 楼主| 发表于 2021-4-28 09:09:33 来自手机 | 显示全部楼层
谢谢大佬
回复

使用道具 举报

7

主题

369

帖子

1711

积分

金牌会员

Rank: 6Rank: 6

积分
1711
金钱
1342
HASS币
0
 楼主| 发表于 2021-4-28 12:58:39 | 显示全部楼层
alei643 发表于 2021-4-28 08:22
63983转换为16进制是F9EF,F9EF转换为有符号数是-1553,实际温度是-15.53℃。去了解一下有符号和无符号数的 ...

大佬,这个在nodered里面应该怎么写?
回复

使用道具 举报

13

主题

284

帖子

1919

积分

论坛技术达人

积分
1919
金钱
1625
HASS币
0

教程狂人

QQ
发表于 2021-4-28 15:14:13 | 显示全部楼层
qjiang 发表于 2021-4-28 12:58
大佬,这个在nodered里面应该怎么写?
var hex = "0xF9EF";
hex= parseInt(hex, 16);
hex= hex| 0xFFFF0000; 
msg.payload=hex
return msg;
回复

使用道具 举报

7

主题

369

帖子

1711

积分

金牌会员

Rank: 6Rank: 6

积分
1711
金钱
1342
HASS币
0
 楼主| 发表于 2021-4-28 23:51:12 | 显示全部楼层
谢谢大佬回复,这个太难了,在零下2位数温度的时候得数还对,零下9度开始就变成 负几百摄氏度了,恢复到0以上数据就更离谱了。
回复

使用道具 举报

13

主题

284

帖子

1919

积分

论坛技术达人

积分
1919
金钱
1625
HASS币
0

教程狂人

QQ
发表于 2021-4-29 08:39:38 | 显示全部楼层
qjiang 发表于 2021-4-28 23:51
谢谢大佬回复,这个太难了,在零下2位数温度的时候得数还对,零下9度开始就变成 负几百摄氏度了,恢复到0以 ...

上面那段代码只是用于处理负数,没有考虑正数,所以0上的数据会出错。其实加段代码判断一下最高位是0还是1就知道需不需要进行补码运算,下面这段代码可以将16进制转换为有符号数
var i="F9EF"
 let n = parseInt(i, 16).toString(2);
  let bitNum=i.length*4;
  if (n.length < bitNum) {
    while (n.length < bitNum) {
      n = "0" + n;
    }
  }
 
  if (n.substring(0, 1) == "0") {
    n = parseInt(n, 2);
 msg.payload=n
    return msg;
  } else {
    let n_unsign = "";
    n = parseInt(n, 2) - 1;
    n = n.toString(2);
    n_unsign = n.substring(1, bitNum);
    n_unsign = n_unsign.replace(/0/g, "z");
    n_unsign = n_unsign.replace(/1/g, "0");
    n_unsign = n_unsign.replace(/z/g, "1");
    n = parseInt(-n_unsign, 2);
    msg.payload=n
    return msg;
  }
回复

使用道具 举报

7

主题

369

帖子

1711

积分

金牌会员

Rank: 6Rank: 6

积分
1711
金钱
1342
HASS币
0
 楼主| 发表于 2021-4-29 22:08:36 | 显示全部楼层
膜拜大佬,参照大佬的帖子终于弄好了,代码贴出来

var a= msg.payload[4];
var b= msg.payload[5];
var aa= (a.toString(16));
var aaa = hexNum(aa)
var bb= (b.toString(16));
var bbb = hexNum(bb)

function hexNum(str){
    var newstr=str+''
    if(newstr.length>0 && newstr.length<2){
        newstr='0'+str
    }
    return newstr
}

var i= aaa+bbb;
let n = parseInt(i, 16).toString(2);
  let bitNum=i.length*4;
  if (n.length < bitNum) {
    while (n.length < bitNum) {
      n = "0" + n;
    }
  }
 
  if (n.substring(0, 1) == "0") {
    n = parseInt(n, 2);
 msg.payload=n/100
    return msg;
  } else {
    let n_unsign = "";
    n = parseInt(n, 2) - 1;
    n = n.toString(2);
    n_unsign = n.substring(1, bitNum);
    n_unsign = n_unsign.replace(/0/g, "z");
    n_unsign = n_unsign.replace(/1/g, "0");
    n_unsign = n_unsign.replace(/z/g, "1");
    n = parseInt(-n_unsign, 2);
    msg.payload=n/100
    return msg;
  }
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

Archiver|手机版|小黑屋|Hassbian

GMT+8, 2021-5-7 17:30 , Processed in 0.068810 second(s), 41 queries .

Powered by Discuz! X3.4

Copyright © 2001-2020, Tencent Cloud.

快速回复 返回顶部 返回列表