MoistureSoftware/Source/max6675.c

126 lines
3.5 KiB
C
Raw Permalink Normal View History

2025-09-28 09:17:22 +00:00
#include "BSP.H"
#define MAX6675_SCK_GPIO GPIOB
#define MAX6675_SCK_PIN GPIO_Pin_5
#define MAX6675_CS_GPIO GPIOB
#define MAX6675_CS_PIN GPIO_Pin_4
#define MAX6675_SO_GPIO GPIOB
#define MAX6675_SO_PIN GPIO_Pin_3
uint16_t MAX6675_ReadData(void)
{
uint16_t data = 0;
int8_t i = 0;
// ѡ<>д<EFBFBD><D0B4><EFBFBD><EFBFBD><EFBFBD>
GPIO_ResetBits(MAX6675_CS_GPIO, MAX6675_CS_PIN);
// <20><>SO<53><4F><EFBFBD>Ŷ<EFBFBD>ȡ<EFBFBD><C8A1><EFBFBD><EFBFBD>
for (i = 15; i >= 0; i--) {
// <20><>SCK<43><4B><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
GPIO_ResetBits(MAX6675_SCK_GPIO, MAX6675_SCK_PIN);
// <20><>ʱһ<CAB1><D2BB>ʱ<EFBFBD><CAB1>
delay_us(1);
// <20><>ȡSO<53><4F><EFBFBD><EFBFBD>״̬
if (GPIO_ReadInputDataBit(MAX6675_SO_GPIO, MAX6675_SO_PIN)) {
data |= (1 << i); // <20><><EFBFBD>ö<EFBFBD>ӦλΪ1
}
// <20><>SCK<43><4B><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
GPIO_SetBits(MAX6675_SCK_GPIO, MAX6675_SCK_PIN);
// <20><>ʱһ<CAB1><D2BB>ʱ<EFBFBD><CAB1>
delay_us(1);
}
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ѡ<EFBFBD><D1A1>״̬
GPIO_SetBits(MAX6675_CS_GPIO, MAX6675_CS_PIN);
return data;
}
float Temperature;
// <20><><EFBFBD><EFBFBD><E5BFA8><EFBFBD><EFBFBD><EFBFBD>˲<EFBFBD><CBB2><EFBFBD><EFBFBD>IJ<EFBFBD><C4B2><EFBFBD><EFBFBD><EFBFBD><E1B9B9>
typedef struct {
float x; // ״̬<D7B4><CCAC><EFBFBD><EFBFBD>ֵ
float P; // ״̬Э<CCAC><D0AD><EFBFBD><EFBFBD>
float Q; // <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Э<EFBFBD><D0AD><EFBFBD><EFBFBD>
float R; // <20>۲<EFBFBD><DBB2><EFBFBD><EFBFBD><EFBFBD>Э<EFBFBD><D0AD><EFBFBD><EFBFBD>
float K; // <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
} KalmanFilter;
KalmanFilter kf;
// <20><>ʼ<EFBFBD><CABC><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>˲<EFBFBD><CBB2><EFBFBD>
void kalman_filter_init(KalmanFilter *kf, float initial_x, float initial_P, float process_noise, float measurement_noise)
{
kf->x = initial_x;
kf->P = initial_P;
kf->Q = process_noise;
kf->R = measurement_noise;
}
// <20><><EFBFBD>¿<EFBFBD><C2BF><EFBFBD><EFBFBD><EFBFBD><EFBFBD>˲<EFBFBD><CBB2><EFBFBD>״̬
void kalman_filter_update(KalmanFilter *kf, float measurement)
{
// Ԥ<><EFBFBD><E2B2BD>
float x_pred = kf->x; // Ԥ<><D4A4><EFBFBD><EFBFBD>״ֵ̬
float P_pred = kf->P + kf->Q; // Ԥ<><D4A4><EFBFBD><EFBFBD>״̬Э<CCAC><D0AD><EFBFBD><EFBFBD>
// <20><><EFBFBD>²<EFBFBD><C2B2><EFBFBD>
kf->K = P_pred / (P_pred + kf->R); // <20><><EFBFBD><EFBFBD><E3BFA8><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
kf->x = x_pred + kf->K * (measurement - x_pred); // <20><><EFBFBD><EFBFBD>״̬<D7B4><CCAC><EFBFBD><EFBFBD>ֵ
kf->P = (1 - kf->K) * P_pred; // <20><><EFBFBD><EFBFBD>״̬Э<CCAC><D0AD><EFBFBD><EFBFBD>
}
#include "APPDEF.H"
void MAX6675_ConvertTemperature(const void *P_arg)
{
kalman_filter_init(&kf, 0.0, 1.0, 0.01, 0.3);
for (;;) {
osDelay(250);
uint16_t data = MAX6675_ReadData();
// <20><>ȡ<EFBFBD><EFBFBD><C2B6><EFBFBD><EFBFBD>ݲ<EFBFBD><DDB2>֣<EFBFBD><D6A3><EFBFBD>λ14λ<34><CEBB>
uint16_t temperatureData = data >> 3;
// <20>ж<EFBFBD><D0B6><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>λ
uint8_t sign = (data & 0x04) >> 2;
// <20><EFBFBD>ת<EFBFBD><D7AA>Ϊ<EFBFBD><CEAA><EFBFBD>϶<EFBFBD>
float temperature = (float)temperatureData * 0.25f;
// <20><><EFBFBD><EFBFBD>Ϊ<EFBFBD><CEAA><EFBFBD>ȣ<C2B6>ȡ<EFBFBD><C8A1><EFBFBD><EFBFBD><EBB2A2><EFBFBD>Ӹ<EFBFBD><D3B8><EFBFBD>
if (sign == 1) {
temperature = -((~temperatureData + 1) * 0.25f);
}
kalman_filter_update(&kf, temperature); // <20><><EFBFBD>²<EFBFBD><C2B2><EFBFBD>
Temperature = kf.x + Set.TempDelta;
/* code */
}
}
osThreadDef(MAX6675_ConvertTemperature, osPriorityNormal, 1, 0);
void MAX6675_Init(void)
{
// <20><>ʼ<EFBFBD><CABC>CS<43><53><EFBFBD><EFBFBD>Ϊ<EFBFBD>ߵ<EFBFBD>ƽ<EFBFBD><C6BD><EFBFBD><EFBFBD>ѡ<EFBFBD>д<EFBFBD><D0B4><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
GPIO_SetBits(MAX6675_CS_GPIO, MAX6675_CS_PIN);
// <20><>ʼ<EFBFBD><CABC>GPIO<49><4F><EFBFBD>ź<EFBFBD><C5BA><EFBFBD>ʱ<EFBFBD><CAB1><EFBFBD><EFBFBD>
GPIO_InitTypeDef GPIO_InitStruct;
GPIO_InitStruct.GPIO_Pin = MAX6675_SCK_PIN;
GPIO_InitStruct.GPIO_Mode = GPIO_Mode_Out_PP;
GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(MAX6675_SCK_GPIO, &GPIO_InitStruct);
GPIO_InitStruct.GPIO_Pin = MAX6675_CS_PIN;
GPIO_InitStruct.GPIO_Mode = GPIO_Mode_Out_PP;
GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(MAX6675_CS_GPIO, &GPIO_InitStruct);
GPIO_InitStruct.GPIO_Pin = MAX6675_SO_PIN;
GPIO_InitStruct.GPIO_Mode = GPIO_Mode_IN_FLOATING;
GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(MAX6675_SO_GPIO, &GPIO_InitStruct);
osThreadCreate(osThread(MAX6675_ConvertTemperature), NULL);
}