【资料图】
NTC任敏电阻采集,查表+中值滤波算法void app_adc_init(void)
{
/* pins and clock are already in the pin_init.c and clock_init.c. */
/* setup the converter. */
ADC_Init_Type adc_init;
adc_init.Resolution = ADC_Resolution_12b;
adc_init.ClockDiv = ADC_ClockDiv_16;
adc_init.ConvMode = ADC_ConvMode_SingleSlot;
adc_init.Align = ADC_Align_Right;
ADC_Init(BOARD_ADC_PORT, &adc_init);
ADC_Enable(BOARD_ADC_PORT, true); /* power on the converter. */
ADC_EnableTempSensor(BOARD_ADC_PORT, true); /* enable the temperature sensor. */
/* setup the sequence, a regular conversion with only one channel. */
ADC_RegSeqConf_Type adc_regseq_conf;
adc_regseq_conf.SeqSlots = 1u << BOARD_ADC_CHN_NUM;
adc_regseq_conf.SeqDirection = ADC_RegSeqDirection_LowFirst;
ADC_EnableRegSeq(BOARD_ADC_PORT, &adc_regseq_conf);
/* set channel sample time. */
ADC_SetChnSampleTime(BOARD_ADC_PORT, BOARD_ADC_CHN_NUM, ADC_SampleTime_Alt7);
}
/* software tirgger the adc converter and start the sequence conversion. */
uint32_t app_adc_run_conv(void)
{
uint32_t data;
uint32_t flags;
uint32_t adc_channel; /* keep the actual hardware conversion channel number. */
/* software tirgger the conversion. */
ADC_DoSwTrigger(BOARD_ADC_PORT, true);
/* wait while the conversion is ongoing. */
while( 0u == (ADC_GetStatus(BOARD_ADC_PORT) & ADC_STATUS_CONV_SEQ_DONE) )
{}
ADC_ClearStatus(BOARD_ADC_PORT, ADC_STATUS_CONV_SEQ_DONE);
data = ADC_GetConvResult(BOARD_ADC_PORT, &adc_channel, &flags);
if (0u == (flags & ADC_CONV_RESULT_FLAG_VALID) )
{
data = 0u; /* the data is unavailable when the VALID flag is not on. */
}
return data;
}
PID温控算法:const u32 g_rvTable[TABLE_SIZE] = {
1034600, 959006, 889452, 825419, 766434, //-55~-51
712066, 661926, 615656, 572934, 533466, 496983, 463240, 432015, 403104, 376320, //-50~-41
351495, 328472, 307110, 287279, 268859, 251741, 235826, 221021, 207242, 194412, //-40~-31
182460, 171320, 160932, 151241, 142196, 133750, 125859, 118485, 111589, 105139, //-30~-21
99102, 93450, 88156, 83195, 78544, 74183, 70091, 66250, 66643, 59255, //-20~-11
56071, 53078, 50263, 47614, 45121, 42774, 40563, 38480, 36517, 34665, //-10~-1
32919, //0
31270, 29715, 28246, 26858, 25547, 24307, 23135, 22026, 20977, 19987, //1~10
19044, 18154, 17310, 16510, 15752, 15034, 14352, 13705, 13090, 12507, //11~20
11953, 11427, 10927, 10452, 10000, 9570, 9161, 8771, 8401, 8048, //21~30
7712, 7391, 7086, 6795, 6518, 6254, 6001, 5761, 5531, 5311, //31~40
5102, 4902, 4710, 4528, 4353, 4186, 4026, 3874, 3728, 3588, //41~50
3454, 3326, 3203, 3085, 2973, 2865, 2761, 2662, 2567, 2476, //51~60
2388, 2304, 2223, 2146, 2072, 2000, 1932, 1866, 1803, 1742, //61~70
1684, 1627, 1573, 1521, 1471, 1423, 1377, 1332, 1289, 1248, //71~80
1208, 1170, 1133, 1097, 1063, 1030, 998, 968, 938, 909, //81~90
882, 855, 829, 805, 781, 758, 735, 714, 693, 673, //91~100
653, 635, 616, 599, 582, 565, 550, 534, 519, 505, //101~110
491, 478, 465, 452, 440, 428, 416, 405, 395, 384, //111~120
374, 364, 355, 345, 337 //121~125
};
u16 mid_filter(u16 *collection, u16 size)
{
u16 e;
u16 i, j;
u8 sorted;
i = 0;
while(i < size - 1){//冒泡的趟数
sorted = 1;
j = 0;
while(j < size - 1 - i){//一趟冒的次数
if(collection[j] > collection[j + 1]){
e = collection[j];
collection[j] = collection[j + 1];
collection[j + 1] = e;
sorted = 0;
}
j++;
}
if(sorted) break;
i++;
}
return collection[size / 2];
}
s8 ntc_get_temp(void)
{
s16 i;
u32 adcValue;
float rValue;
s8 temperature;
u16 adc_buffer[ADC1_CONVDATA_SIZE];
for(i = 0; i < ADC1_CONVDATA_SIZE; i++)
{
//adc_buffer[i] = GetAdcAverage(5);
adc_buffer[i] =app_adc_run_conv() ;
delay_ms(1);
}
adcValue = mid_filter(adc_buffer, ADC1_CONVDATA_SIZE);
rValue = 4095000.0;
rValue = rValue / adcValue - 1000;
adcValue = 10000000.0 / rValue;
for(i = 0; i < TABLE_SIZE; i++) {
if(adcValue > g_rvTable[i]) {
temperature = i - 55;
break;
}
}
return temperature;
}
#define D_SCALE 10 //结果放大倍数, 放大10倍就是保留一位小数
int get_temperature(uint adc)
{
uint code *p;
uint i;
uchar j,k;
uchar min,max; //查表序号, 0对应-40度, 160对应120度
// adc = 4096 - adc; //Rt接地
p = temp_table;
if(adc < p[0]) return (0xfffe);
if(adc > p[160]) return (0xffff);
min = 0; //-40度
max = 160; //120度
for(j=0; j<5; j++) //对分查表
{
k = min / 2 + max / 2;
if(adc <= p[k]) max = k;
else min = k;
}
if(adc == p[min]) i = (uint)min * D_SCALE;
else if(adc == p[max]) i = (uint)max * D_SCALE;
else // min < temp < max
{
while(min <= max)
{
min++;
if(adc == p[min]) {i = (uint)min * D_SCALE; break;}
else if(adc < p[min]) //线性插补
{
min--;
i = p[min]; //min
j = (adc - i) * D_SCALE / (p[min+1] - i);
i = min;
i *= D_SCALE;
i += j;
break;
}
}
}
return (i-400);
}
void temp_control()//控制温度上下限函数
{
if(limit_choise==0)//选择按键
{
delay_ms(1);
if(limit_choise==0)
{
while(!limit_choise);
limit_choise_num++;
if(limit_choise_num>=2)
{
limit_choise_num=0;
}
}
}
if(limit_choise_num==0)//正常显示
{
Display_GB2312_String(0,90,3, "水箱设定温度",WHITE); //32x32汉字
}
if(limit_choise_num==1)//调节上限温度
{
Display_GB2312_String(0,90,3, "水箱温度调节",RED); //32x32汉字
if(increase_temperature==0)//增加温度
{
delay_ms(1);
if(increase_temperature==0)
{
// while(!increase_temperature);
up_limit_temp+=0.5;
if(up_limit_temp>=100)
{
up_limit_temp=0;
}
sprintf(fs,"%.2f",up_limit_temp);
Display_Asc_String(200,90,5, fs,WHITE); //ASC 7X8点阵
}
}
if(reduce_temperature==0)//减少温度
{
delay_ms(1);
if(reduce_temperature==0)
{
// while(!reduce_temperature);
up_limit_temp-=0.5;
if(up_limit_temp<0)
{
up_limit_temp=99;
}
sprintf(fs,"%.2f",up_limit_temp);
Display_Asc_String(200,90,5, fs,WHITE); //ASC 7X8点阵
}
}
}
}
系统可以物联网通信:NB IOT BC26 AT 指令通过HTTP连接onenet平台发送温度实现远程控制;
一路接NB模组,一路接433M 无线通讯。实现断网情况下跟电脑无线通信,不依赖运行商。
基于C++的上位机设计:AT+NSOSD=1,307,504F5354202F646576696365732F33393939343933312F64617461706F696E747320485454502F312E310D0A6170692D6B65793A59414A34626B6C64796F6671657558767871473D6C54416661796B3D0D0A486F73743A6170692E6865636C6F7564732E636F6D0D0A436F6E74656E742D4C656E6774683A3137360D0A0D0A7B226461746173747265616D73223A5B7B226964223A2254656D70222C2264617461706F696E7473223A5B7B2276616C7565223A32387D5D7D2C7B226964223A2268756D69222C2264617461706F696E7473223A5B7B2276616C7565223A31317D5D7D2C7B226964223A22475053222C2264617461706F696E7473223A5B7B2276616C7565223A7B226C6174223A32322E3439393933332C226C6F6E223A3130382E3131323434317D7D5D7D5D7D0D0A0D0A0D0A
OK
+NSONMI:1,203//这是服务器返回来的数据。
AT+NSORF=1,203//查询接收内容的指令203是需要查询的长度。可以多,
1,183.230.40.33,80,203,485454502F312E31203230302
04F4B0D0A446174653A205475652C2030342053657020323031382030393A323
53A353120474D540D0A436F6E74656E742D547970653A206170706C696361746
96F6E2F6A736F6E0D0A436F6E74656E7
42D4C656E6774683A2032360D0A436F6E6E656374696F6E3A206B6565702D616
C6976650D0A5365727665723A204170616368652D436F796F74652F312E310D0
A507261676D613A206E6F2D63616368650D0A0D0A7B226572726E6F223A302C2
26572726F72223A2273756363227D,0
OK
AT+NSOCL=1 //关闭连接
OK
作者:abner_ma, 来源:面包板社区
链接:https://mbb.eet-china.com/forum/topic/124296_1_1.html
版权声明:本文为博主原创,未经本人允许,禁止转载!
END评测中心 免费申请☝长按图片,扫码申请☝