val-off-little/screen/screen.c

954 lines
23 KiB
C
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

#include "cmd_queue.h"
#include <stdlib.h>
char *pEnd;
char ipaddr[32] = ""; //存储字符串IP
char gw_ipaddr[32] = ""; //存储字符串IP
char ipmask[32] = ""; //存储字符串IP
uint8_t cmd_buffer[CMD_MAX_SIZE]; //指令缓存
static uint16_t current_screen_id = 0; //当前画面ID
uint8_t years,months,weeks,days,hours,minutes,sec;
uint8_t power_state = 5,power_flag = 0;
int angular_travel_flag = 1;//是否启用角行程
int straight_travel_flag = 1;//是否启用直行程
int current_calib[4]; //电流校准值
int pressure_calib[4]; //气压校准值
float ao_out;
int unit_pulse = 100; //编码器单位脉冲数
float gear_ratio = 60; //角行程阀轴直径
int power_cnt = 0;
bool change_flag = false;
extern bool cal_change_flag;
extern void get_power_state(void);
/*!
* \brief 消息处理流程
* \param msg 待处理消息
* \param size 消息长度
*/
void ProcessMessage( PCTRL_MSG msg, uint16_t size )
{
uint8 cmd_type = msg->cmd_type; //指令类型
uint8 ctrl_msg = msg->ctrl_msg; //消息的类型
uint8 control_type = msg->control_type; //控件类型
uint16 screen_id = PTR2U16(&msg->screen_id); //画面ID
uint16 control_id = PTR2U16(&msg->control_id); //控件ID
uint32 value = PTR2U32(msg->param); //数值
switch(cmd_type)
{
case NOTIFY_TOUCH_PRESS: //触摸屏按下
case NOTIFY_TOUCH_RELEASE: //触摸屏松开
NotifyTouchXY(cmd_buffer[1],PTR2U16(cmd_buffer+2),PTR2U16(cmd_buffer+4));
break;
case NOTIFY_WRITE_FLASH_OK: //写FLASH成功
NotifyWriteFlash(1);
break;
case NOTIFY_WRITE_FLASH_FAILD: //写FLASH失败
NotifyWriteFlash(0);
break;
case NOTIFY_READ_FLASH_OK: //读取FLASH成功
NotifyReadFlash(1,cmd_buffer+2,size-6); //去除帧头帧尾
break;
case NOTIFY_READ_FLASH_FAILD: //读取FLASH失败
NotifyReadFlash(0,0,0);
break;
case NOTIFY_READ_RTC: //读取RTC时间
NotifyReadRTC(cmd_buffer[2],cmd_buffer[3],cmd_buffer[4],cmd_buffer[5],cmd_buffer[6],cmd_buffer[7],cmd_buffer[8]);
break;
case NOTIFY_CONTROL:
{
if(ctrl_msg==MSG_GET_CURRENT_SCREEN) //画面ID变化通知
{
NotifyScreen(screen_id); //画面切换调动的函数
}
else
{
switch(control_type)
{
case kCtrlButton: //按钮控件
NotifyButton(screen_id,control_id,msg->param[1]);
break;
case kCtrlText: //文本控件
NotifyText(screen_id,control_id,msg->param);
break;
case kCtrlProgress: //进度条控件
NotifyProgress(screen_id,control_id,value);
break;
case kCtrlSlider: //滑动条控件
NotifySlider(screen_id,control_id,value);
break;
case kCtrlMeter: //仪表控件
NotifyMeter(screen_id,control_id,value);
break;
case kCtrlMenu: //菜单控件
NotifyMenu(screen_id,control_id,msg->param[0],msg->param[1]);
break;
case kCtrlSelector: //选择控件
NotifySelector(screen_id,control_id,msg->param[0]);
break;
case kCtrlRTC: //倒计时控件
NotifyTimer(screen_id,control_id);
break;
default:
break;
}
}
break;
}
default:
break;
}
}
/*!
* \brief 画面切换通知
* \details 当前画面改变时(或调用GetScreen),执行此函数
* \param screen_id 当前画面ID
*/
void NotifyScreen(uint16_t screen_id)
{
//TODO: 添加用户代码
current_screen_id = screen_id; //在工程配置中开启画面切换通知记录当前画面ID
change_flag = true;
if(screen_id == 0)
{
AnimationPlayFrame(0,99,power_state - 1); //电量
}
if(screen_id == 1)
{
AnimationPlayFrame(1,99,power_state - 1); //电量
}
if(screen_id == 2)
{
AnimationPlayFrame(2,99,power_state - 1); //电量
}
if(screen_id == 3)
{
AnimationPlayFrame(3,99,power_state - 1); //电量
}
if(screen_id == 4)
{
AnimationPlayFrame(4,99,power_state - 1); //电量
}
}
/*!
* \brief 触摸坐标事件响应
* \param press 1按下触摸屏3松开触摸屏
* \param x x坐标
* \param y y坐标
*/
void NotifyTouchXY(uint8_t press,uint16_t x,uint16_t y)
{
//TODO: 添加用户代码
}
int pow_grade = 1;
/*!
* \brief 更新数据
*/
void UpdateUI(void)
{
//文本设置和显示 定时20ms刷新一次
if(current_screen_id == 0)
{
if(DisState[0] & 0x20)
{
power_cnt++;
if(power_cnt < 5)
AnimationPlayFrame(0,98,1);
else
AnimationPlayFrame(0,98,0);
if(power_cnt > 10)
{
power_cnt = 0;
power_state--;
}
if(power_state < 1)
power_state = 3;
}
else
{
get_power_state();
AnimationPlayFrame(0,98,3);
}
AnimationPlayFrame(0,99,power_state - 1); //电量
}
if(current_screen_id == 1)
{
if(DisState[0] & 0x20)
{
power_cnt++;
if(power_cnt < 5)
AnimationPlayFrame(1,98,1);
else
AnimationPlayFrame(1,98,0);
if(power_cnt > 10)
{
power_cnt = 0;
power_state--;
}
if(power_state < 1)
power_state = 3;
}
else
{
get_power_state();
AnimationPlayFrame(1,98,2);
}
AnimationPlayFrame(1,99,power_state - 1); //电量
SetTextInt32(1,9,HoldReg[0],0,0);
SetTextInt32(1,15,HoldReg[1],0,0);
if(InputReg[1] > 1000)
{
SetTextInt32(1,24,InputReg[1],0,0);
}
else
{
SetTextInt32(1,24,0,0,0);
}
if(InputReg[2] > 1000)
{
SetTextInt32(1,25,InputReg[2],0,0);
}
else
{
SetTextInt32(1,25,0,0,0);
}
SetTextFloat(1,10,ao1_offsets,0,0);
SetTextFloat(1,16,ao2_offsets,0,0);
if(HoldReg[0] > 4000)
SetSliderValue(1,1,HoldReg[0]-4000);
else
SetSliderValue(1,1,0);
if(HoldReg[1] > 4000)
SetSliderValue(1,14,HoldReg[1]-4000);
else
SetSliderValue(1,14,0);
}
if(current_screen_id == 2)
{
if(DisState[0] & 0x20)
{
power_cnt++;
if(power_cnt < 5)
AnimationPlayFrame(2,98,1);
else
AnimationPlayFrame(2,98,0);
if(power_cnt > 10)
{
power_cnt = 0;
power_state--;
}
if(power_state < 1)
power_state = 3;
}
else
{
get_power_state();
AnimationPlayFrame(2,98,2);
}
AnimationPlayFrame(2,99,power_state - 1); //电量
if(InputReg[12] > 500)
{
SetTextFloat(2,3,InputReg[12] / 1000.0,3,0);//输入电流
}
else
{
SetTextFloat(2,3,0,0,0);//输入电流
}
SetTextFloat(2,6,((float)InputReg[8] / 10),1,1);//环境压力
SetTextFloat(2,7,((float)(InputReg[5] - InputReg[8]) / 10),1,1); // A口压力
SetTextFloat(2,8,((float)(InputReg[6] - InputReg[8]) / 10),1,1); // B口压力
SetTextFloat(2,9,((float)(InputReg[7] - InputReg[8]) / 10),1,1); //气源压力
if(straight_travel_flag)
{
SetTextFloat(2,4,(((float)((long)(InputReg[10]*65536) + InputReg[11]) - 10000000) / HoldReg[2]),2,1);//编码器(直行程)
}
else
{
SetTextFloat(2,4,0,2,1);//编码器(直行程)
}
if(angular_travel_flag)
{
SetTextFloat(2,5,((((float)((long)(InputReg[10]*65536) + InputReg[11]) - 10000000) / HoldReg[2]) * (60 / (HoldReg[13]/100.0))),2,1);//编码器 (角行程)
}
else
{
SetTextFloat(2,5,0,2,1);//编码器 (角行程)
}
if(CoilState[0] & 0x20)
SetButtonValue(2,2,1);
else
SetButtonValue(2,2,0);
if(DisState[0] & 0x80)
AnimationPlayFrame(2,12,1);
else
AnimationPlayFrame(2,12,0);
if(DisState[0] & 0x40)
AnimationPlayFrame(2,13,1);
else
AnimationPlayFrame(2,13,0);
}
if(current_screen_id == 3)
{
if(DisState[0] & 0x20)
{
power_cnt++;
if(power_cnt < 5)
AnimationPlayFrame(3,98,1);
else
AnimationPlayFrame(3,98,0);
if(power_cnt > 10)
{
power_cnt = 0;
power_state--;
}
if(power_state < 1)
power_state = 3;
}
else
{
get_power_state();
AnimationPlayFrame(3,98,2);
}
AnimationPlayFrame(3,99,power_state - 1); //电量
if(CoilState[0] & 0x80)
SetButtonValue(3,4,1);
else
SetButtonValue(3,4,0);
}
if(current_screen_id == 4)
{
if(DisState[0] & 0x20)
{
power_cnt++;
if(power_cnt < 5)
AnimationPlayFrame(4,98,1);
else
AnimationPlayFrame(4,98,0);
if(power_cnt > 10)
{
power_cnt = 0;
power_state--;
}
if(power_state < 1)
power_state = 3;
}
else
{
get_power_state();
AnimationPlayFrame(4,98,2);
}
AnimationPlayFrame(4,99,power_state - 1); //电量
if(InputReg[12] > 500)
{
SetTextInt32(4,2,InputReg[12],0,0);//输入电流
}
else
{
SetTextInt32(4,2,0,0,0);//输入电流
}
SetTextFloat(4,3,((float)InputReg[8] / 10),1,1);//环境压力
SetTextFloat(4,4,((float)(InputReg[5] - InputReg[8]) / 10),1,1); // A口压力
SetTextFloat(4,5,((float)(InputReg[6] - InputReg[8]) / 10),1,1); // B口压力
SetTextFloat(4,6,((float)(InputReg[7] - InputReg[8]) / 10),1,1); //气源压力
SetTextInt32(4,12,HoldReg[2],0,0);//单位脉冲
SetTextInt32(4,13,HoldReg[13]/100,0,0);//阀杆直径
}
if(current_screen_id == 5)
{
if(DisState[0] & 0x20)
{
power_cnt++;
if(power_cnt < 5)
AnimationPlayFrame(5,98,1);
else
AnimationPlayFrame(5,98,0);
if(power_cnt > 10)
{
power_cnt = 0;
power_state--;
}
if(power_state < 1)
power_state = 3;
}
else
{
get_power_state();
AnimationPlayFrame(5,98,2);
}
AnimationPlayFrame(5,99,power_state - 1); //电量
}
if(current_screen_id == 6)
{
if(change_flag)
{
//整形转字符串
sprintf(ipaddr,"%d.%d.%d.%d", HoldReg[40], HoldReg[41], HoldReg[42], HoldReg[43]);
sprintf(gw_ipaddr,"%d.%d.%d.%d", HoldReg[44], HoldReg[45], HoldReg[46], HoldReg[47]);
sprintf(ipmask,"%d.%d.%d.%d", HoldReg[48], HoldReg[49], HoldReg[50], HoldReg[51]);
SetTextValue(6,9,(uchar *)ipaddr);
SetTextValue(6,10,(uchar *)gw_ipaddr);
SetTextValue(6,11,(uchar *)ipmask);
SetTextInt32(6,12,HoldReg[52],0,0);
SetTextInt32(6,13,HoldReg[53],0,0);
change_flag = false;
}
}
}
/*!
* \brief 按钮控件通知
* \details 当按钮状态改变(或调用GetControlValue)时,执行此函数
* \param screen_id 画面ID
* \param control_id 控件ID
* \param state 按钮状态0弹起1按下
*/
void NotifyButton(uint16_t screen_id, uint16_t control_id, uint8_t state)
{
if(screen_id == 1)//开关量输出
{
switch(control_id)
{
case 3:
{
HoldReg[0] = 4000;
}
break;
case 4:
{
HoldReg[0] = 8000;
}
break;
case 5:
{
HoldReg[0] = 12000;
}
break;
case 6:
{
HoldReg[0] = 16000;
}
break;
case 7:
{
HoldReg[0] = 20000;
}
break;
case 11:
{
if(state)
{
ao1_offsets += 1;
cal_change_flag = true;
}
}
break;
case 12:
{
if(state)
{
ao1_offsets -= 1;
cal_change_flag = true;
}
}
break;
case 17:
{
if(state)
{
ao2_offsets += 1;
cal_change_flag = true;
}
}
break;
case 18:
{
if(state)
{
ao2_offsets -= 1;
cal_change_flag = true;
}
}
break;
case 19:
{
HoldReg[1] = 4000;
}
break;
case 20:
{
HoldReg[1] = 8000;
}
break;
case 21:
{
HoldReg[1] = 12000;
}
break;
case 22:
{
HoldReg[1] = 16000;
}
break;
case 23:
{
HoldReg[1] = 20000;
}
break;
}
}
if(screen_id == 2)
{
if(control_id == 11)
{
__HAL_TIM_SetCounter(&htim1, 0x9718); //初始化计数值
cnt_update = 152;
}
if(control_id == 2)
{
if(state)
CoilState[0] = CoilState[0] | 0x20;
else
CoilState[0] = CoilState[0] & 0xDF;
}
}
if(screen_id == 3)
{
if(control_id == 4)
{
if(state)
CoilState[0] = CoilState[0] | 0x80;
else
CoilState[0] = CoilState[0] & 0x7F;
}
}
if(screen_id == 4)//开关量输出
{
switch(control_id)
{
case 16:
{
InputReg[12] = InputReg[12] - current_offsets[0];
current_offsets[0] = current_calib[0] - InputReg[12];
if(current_offsets[0] >= 0)
{
HoldReg[5] = current_offsets[0];
}
else
{
int coff_num = -current_offsets[0];
HoldReg[5] = (uint16_t)((0xFFFF - coff_num) + 1);
}
}
break;
case 17:
{
InputReg[8] = InputReg[8] - pressure_offsets[0];
pressure_offsets[0] = pressure_calib[0] - InputReg[8];
if(pressure_offsets[0] >= 0)
{
HoldReg[9] = pressure_offsets[0];
}
else
{
int poff_num = -pressure_offsets[0];
HoldReg[9] = (uint16_t)((0xFFFF - poff_num) + 1);
}
}
break;
case 18:
{
InputReg[5] = InputReg[5] - pressure_offsets[1];
pressure_offsets[1] = pressure_calib[1] + InputReg[8] - InputReg[5];
if(pressure_offsets[1] >= 0)
{
HoldReg[10] = pressure_offsets[1];
}
else
{
int poff_num = -pressure_offsets[1];
HoldReg[10] = (uint16_t)((0xFFFF - poff_num) + 1);
}
}
break;
case 19:
{
InputReg[6] = InputReg[6] - pressure_offsets[2];
pressure_offsets[2] = pressure_calib[2] + InputReg[8] - InputReg[6];
if(pressure_offsets[2] >= 0)
{
HoldReg[11] = pressure_offsets[2];
}
else
{
int poff_num = -pressure_offsets[2];
HoldReg[11] = (uint16_t)((0xFFFF - poff_num) + 1);
}
}
break;
case 20:
{
InputReg[7] = InputReg[7] - pressure_offsets[3];
pressure_offsets[3] = pressure_calib[3] + InputReg[8] - InputReg[7];
if(pressure_offsets[3] >= 0)
{
HoldReg[12] = pressure_offsets[3];
}
else
{
int poff_num = -pressure_offsets[3];
HoldReg[12] = (uint16_t)((0xFFFF - poff_num) + 1);
}
}
break;
case 21:
{
for(int n = 5;n < 13;n++)
{
HoldReg[n] = 0;
}
}
break;
}
}
if(screen_id == 5)
{
if(control_id == 2)
{
net_status = state;//网络开启状态 0-未开启 1-初始化 2-已开启
}
}
if(screen_id == 6)//网络配置
{
HoldReg[54] = 1;//初始为0赋值1让改动数据存入本地之后数值变为2
}
}
int net_data[4] = {0};
/*!
* \brief 文本控件通知
* \details 当文本通过键盘更新(或调用GetControlValue)时,执行此函数
* \details 文本控件的内容以字符串形式下发到MCU如果文本控件内容是浮点值
* \details 则需要在此函数中将下发字符串重新转回浮点值。
* \param screen_id 画面ID
* \param control_id 控件ID
* \param str 文本控件内容
*/
void NotifyText(uint16_t screen_id, uint16_t control_id, uint8_t *str)
{
if(screen_id == 1)
{
ao_out = strtof((const char *)str,&pEnd);
if(control_id == 9)
{
HoldReg[0] = ao_out;//AO1电流输出
}
if(control_id == 10)
{
ao1_offsets = ao_out;//AO1电流输出
if(ao1_offsets >= 0)
{
HoldReg[3] = ao1_offsets;//AO1输出补偿
}
else
{
int aoff_num = -ao1_offsets;
HoldReg[3] = (uint16_t)((0xFFFF - aoff_num) + 1);//AO1输出补偿
}
}
if(control_id == 15)
{
HoldReg[1] = ao_out;//AO1电流输出
}
if(control_id == 16)
{
ao2_offsets = ao_out;//AO1电流输出
if(ao2_offsets >= 0)
{
HoldReg[4] = ao2_offsets;//AO2输出补偿
}
else
{
int aoff_num = -ao2_offsets;
HoldReg[4] = (uint16_t)((0xFFFF - aoff_num) + 1);//AO2输出补偿
}
}
}
if(screen_id == 4)
{
if(control_id == 7)
{
current_calib[0] = strtof((const char *)str,&pEnd);
}
if(control_id == 8)
{
pressure_calib[0] = strtof((const char *)str,&pEnd) * 10;
}
if(control_id == 9)
{
pressure_calib[1] = strtof((const char *)str,&pEnd) * 10;
}
if(control_id == 10)
{
pressure_calib[2] = strtof((const char *)str,&pEnd) * 10;
}
if(control_id == 11)
{
pressure_calib[3] = strtof((const char *)str,&pEnd) * 10;
}
if(control_id == 12)
{
unit_pulse = strtof((const char *)str,&pEnd);
HoldReg[2] = unit_pulse;//单位脉冲
}
if(control_id == 13)
{
gear_ratio = strtof((const char *)str,&pEnd);;
HoldReg[13] = gear_ratio * 100;//阀杆直径
}
}
if(screen_id == 6)//网络配置
{
if(control_id == 9)//IP
{
sscanf((const char *)str,"%d.%d.%d.%d",&net_data[0],&net_data[1],&net_data[2],&net_data[3]);
for(int n = 0;n < 4;n++)
{
HoldReg[40 + n] = net_data[n];
}
}
if(control_id == 10)//GWIP
{
sscanf((const char *)str,"%d.%d.%d.%d",&net_data[0],&net_data[1],&net_data[2],&net_data[3]);
for(int n = 0;n < 4;n++)
{
HoldReg[44 + n] = net_data[n];
}
}
if(control_id == 11)//IPMASK
{
sscanf((const char *)str,"%d.%d.%d.%d",&net_data[0],&net_data[1],&net_data[2],&net_data[3]);
for(int n = 0;n < 4;n++)
{
HoldReg[48 + n] = net_data[n];
}
}
if(control_id == 12)//端口1
{
HoldReg[52] = strtof((const char *)str,&pEnd);
}
if(control_id == 13)//端口2
{
HoldReg[53] = strtof((const char *)str,&pEnd);
}
}
}
/*!
* \brief 进度条控件通知
* \details 调用GetControlValue时执行此函数
* \param screen_id 画面ID
* \param control_id 控件ID
* \param value 值
*/
void NotifyProgress(uint16_t screen_id, uint16_t control_id, uint32_t value)
{
//TODO: 添加用户代码
}
/*!
* \brief 滑动条控件通知
* \details 当滑动条改变(或调用GetControlValue)时,执行此函数
* \param screen_id 画面ID
* \param control_id 控件ID
* \param value 值
*/
void NotifySlider(uint16_t screen_id, uint16_t control_id, uint32_t value)
{
if(screen_id == 1)
{
if(control_id == 1)
{
HoldReg[0] = 4000 + value;
}
if(control_id == 14)
{
HoldReg[1] = 4000 + value;
}
}
if(screen_id == 5)
{
if(control_id == 1)
SetBackLight(255 - value*2);
}
}
/*!
* \brief 仪表控件通知
* \details 调用GetControlValue时执行此函数
* \param screen_id 画面ID
* \param control_id 控件ID
* \param value 值
*/
void NotifyMeter(uint16_t screen_id, uint16_t control_id, uint32_t value)
{
//TODO: 添加用户代码
}
/*!
* \brief 菜单控件通知
* \details 当菜单项按下或松开时,执行此函数
* \param screen_id 画面ID
* \param control_id 控件ID
* \param item 菜单项索引
* \param state 按钮状态0松开1按下
*/
void NotifyMenu(uint16_t screen_id, uint16_t control_id, uint8_t item, uint8_t state)
{
if(screen_id == 4)
{
if(item)
{
angular_travel_flag = 1;
straight_travel_flag = 0;
}
else
{
angular_travel_flag = 0;
straight_travel_flag = 1;
}
}
}
/*!
* \brief 选择控件通知
* \details 当选择控件变化时,执行此函数
* \param screen_id 画面ID
* \param control_id 控件ID
* \param item 当前选项
*/
void NotifySelector(uint16_t screen_id, uint16_t control_id, uint8_t item)
{
}
/*!
* \brief 定时器超时通知处理
* \param screen_id 画面ID
* \param control_id 控件ID
*/
void NotifyTimer(uint16_t screen_id, uint16_t control_id)
{
}
/*!
* \brief 读取用户FLASH状态返回
* \param status 0失败1成功
* \param _data 返回数据
* \param length 数据长度
*/
void NotifyReadFlash(uint8_t status,uint8_t *_data,uint16_t length)
{
//TODO: 添加用户代码
}
/*!
* \brief 写用户FLASH状态返回
* \param status 0失败1成功
*/
void NotifyWriteFlash(uint8_t status)
{
//TODO: 添加用户代码
}
/*!
* \brief 读取RTC时间注意返回的是BCD码
* \param year 年BCD
* \param month 月BCD
* \param week 星期BCD
* \param day 日BCD
* \param hour 时BCD
* \param minute 分BCD
* \param second 秒BCD
*/
void NotifyReadRTC(uint8_t year,uint8_t month,uint8_t week,uint8_t day,uint8_t hour,uint8_t minute,uint8_t second)
{
sec =(0xff & (second>>4))*10 +(0xf & second); //BCD码转十进制
years =(0xff & (year>>4))*10 +(0xf & year);
months =(0xff & (month>>4))*10 +(0xf & month);
weeks =(0xff & (week>>4))*10 +(0xf & week);
days =(0xff & (day>>4))*10 +(0xf & day);
hours =(0xff & (hour>>4))*10 +(0xf & hour);
minutes =(0xff & (minute>>4))*10 +(0xf & minute);
}
void get_power_state(void)
{
if(!power_flag)
{
power_flag = 1;
if(InputReg[0] > 3000)
power_state = 1;
else if(InputReg[0] > 2750)
power_state = 2;
else if(InputReg[0] > 2500)
power_state = 3;
else if(InputReg[0] > 2250)
power_state = 4;
else if(InputReg[0] > 2000)
power_state = 5;
}
else
{
if(InputReg[0] > 2960)
power_state = 1;
else if(InputReg[0] > 2710 && InputReg[0] < 2940)
power_state = 2;
else if(InputReg[0] > 2460 && InputReg[0] < 2690)
power_state = 3;
else if(InputReg[0] > 2210 && InputReg[0] < 2440)
power_state = 4;
else if(InputReg[0] > 2000 && InputReg[0] < 2190)
power_state = 5;
}
}