This repository has been archived on 2024-12-31. You can view files and clone it, but cannot push or open issues or pull requests.
mfps/App/Src/oled2.c

701 lines
14 KiB
C
Raw Blame History

This file contains invisible Unicode characters

This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

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 "oled2.h"
#include "app.h"
/*******************************************模拟I2C***********************************************************/
static void i2c_Delay(void)
{
uint8_t i;
/* 
下面的时间是通过逻辑分析仪测试得到的。
工作条件CPU主频72MHz MDK编译环境1级优化
循环次数为10时SCL频率 = 205KHz
循环次数为7时SCL频率 = 347KHz SCL高电平时间1.5usSCL低电平时间2.87us
循环次数为5时SCL频率 = 421KHz SCL高电平时间1.25usSCL低电平时间2.375us
*/
for (i = 0; i < 10; i++)
;
}
void i2c_Start(void)
{
/* 当SCL高电平时SDA出现一个下跳沿表示I2C总线启动信号 */
BSP_I2C_SDA_1();
BSP_I2C_SCL_1();
i2c_Delay();
BSP_I2C_SDA_0();
i2c_Delay();
BSP_I2C_SCL_0();
i2c_Delay();
}
void i2c_Stop(void)
{
/* 当SCL高电平时SDA出现一个上跳沿表示I2C总线停止信号 */
BSP_I2C_SDA_0();
BSP_I2C_SCL_1();
i2c_Delay();
BSP_I2C_SDA_1();
}
void i2c_SendByte(uint8_t _ucByte)
{
uint8_t i;
/* 先发送字节的高位bit7 */
for (i = 0; i < 8; i++)
{
if (_ucByte & 0x80)
{
BSP_I2C_SDA_1();
}
else
{
BSP_I2C_SDA_0();
}
i2c_Delay();
BSP_I2C_SCL_1();
i2c_Delay();
BSP_I2C_SCL_0();
if (i == 7)
{
BSP_I2C_SDA_1(); // 释放总线
}
_ucByte <<= 1; /* 左移一个bit */
i2c_Delay();
}
}
uint8_t i2c_ReadByte(void)
{
uint8_t i;
uint8_t value;
/* 读到第1个bit为数据的bit7 */
value = 0;
for (i = 0; i < 8; i++)
{
value <<= 1;
BSP_I2C_SCL_1();
i2c_Delay();
if (BSP_I2C_SDA_READ())
{
value++;
}
BSP_I2C_SCL_0();
i2c_Delay();
}
return value;
}
uint8_t i2c_WaitAck(void)
{
uint8_t re;
BSP_I2C_SDA_1(); /* CPU释放SDA总线 */
i2c_Delay();
BSP_I2C_SCL_1(); /* CPU驱动SCL = 1, 此时器件会返回ACK应答 */
i2c_Delay();
if (BSP_I2C_SDA_READ()) /* CPU读取SDA口线状态 */
{
re = 1;
}
else
{
re = 0;
}
BSP_I2C_SCL_0();
i2c_Delay();
return re;
}
void i2c_Ack(void)
{
BSP_I2C_SDA_0(); /* CPU驱动SDA = 0 */
i2c_Delay();
BSP_I2C_SCL_1(); /* CPU产生1个时钟 */
i2c_Delay();
BSP_I2C_SCL_0();
i2c_Delay();
BSP_I2C_SDA_1(); /* CPU释放SDA总线 */
}
void i2c_NAck(void)
{
BSP_I2C_SDA_1(); /* CPU驱动SDA = 1 */
i2c_Delay();
BSP_I2C_SCL_1(); /* CPU产生1个时钟 */
i2c_Delay();
BSP_I2C_SCL_0();
i2c_Delay();
}
void i2c_CfgGpio(void)
{
GPIO_InitTypeDef GPIO_InitStruct = {0};
I2Cx_SCL_GPIO_CLK_ENABLE();
I2Cx_SDA_GPIO_CLK_ENABLE();
/**I2C2 GPIO Configuration
PB10 ------> I2C2_SCL
PB9 ------> I2C2_SDA
*/
GPIO_InitStruct.Pin = BSP_I2C_SCL_PIN | BSP_I2C_SDA_PIN;
;
GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_OD;
GPIO_InitStruct.Pull = GPIO_NOPULL;
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_HIGH;
HAL_GPIO_Init(BSP_GPIO_PORT_I2C, &GPIO_InitStruct);
/* 给一个停止信号, 复位I2C总线上的所有设备到待机模式 */
i2c_Stop();
}
/*******************************************模拟I2C***********************************************************/
//static uint8_t sendBuffer[2] = {0};
//void OLED2_Send(uint8_t *data, uint8_t len)//发送数据 8bit * len
//{
// //HAL_I2C_Master_Transmit(&hi2c1, SSD1306_I2C_ADDR| 0x00, data, len,10);//1000
//}
//void SSD1306_WriteCmd(uint8_t cmd)//发送命令 [0x00;cmd]
//{
// sendBuffer[0] = 0x00;
// sendBuffer[1] = cmd;
// OLED2_Send(sendBuffer, 2);
// delay_us(50);
//}
void SSD1306_WriteCmd(uint8_t cmd)
{
// sendBuffer[0] = 0x00;
// sendBuffer[1] = cmd;
// HAL_I2C_Master_Transmit(&hi2c1,SSD1306_I2C_ADDR,sendBuffer, 2,20);
i2c_Start();
i2c_SendByte(SSD1306_I2C_ADDR | 0x00);
i2c_Ack();
i2c_SendByte(0x00); //cmd
i2c_Ack();
i2c_SendByte(cmd);
i2c_Ack();
i2c_Stop();
}
void SSD1306_WriteData(uint8_t data)
{
// sendBuffer[0] = 0x40;
// sendBuffer[1] = data;
// OLED2_Send(sendBuffer, 2);
i2c_Start();
i2c_SendByte(SSD1306_I2C_ADDR | 0x00);
i2c_Ack();
i2c_SendByte(0x40); //data
i2c_Ack();
i2c_SendByte(data);
i2c_Ack();
i2c_Stop();
}
//SSD1306???
void OLED2_Init(void)
{
// delay_us(500000);
//SSD1306????,?????????
SSD1306_WriteCmd(0xAE);//--display off
SSD1306_WriteCmd(0x00);//--set low column address
SSD1306_WriteCmd(0x10);//--set high column address
SSD1306_WriteCmd(0x40);//--set start line address
SSD1306_WriteCmd(0xB0);//--set page address
SSD1306_WriteCmd(0x81);// contract control
SSD1306_WriteCmd(0xFF);//--128
// SSD1306_WriteCmd(0xA1);//set segment re-map 0 to 127
SSD1306_WriteCmd(0xA0);//左右翻转
SSD1306_WriteCmd(0xA6);//set normal display
SSD1306_WriteCmd(0xA8);//set multiplex ratio(1 to 64)
SSD1306_WriteCmd(0x3F);//--1/32 duty
// SSD1306_WriteCmd(0xC8);//Com scan direction
SSD1306_WriteCmd(0xC0);//上下翻转
SSD1306_WriteCmd(0xD3);//set display offset
SSD1306_WriteCmd(0x00);//no offset
SSD1306_WriteCmd(0xD5);//set display clock divide ratio/oscillator frequency
SSD1306_WriteCmd(0x80);//
SSD1306_WriteCmd(0xD8);//set area color mode off
SSD1306_WriteCmd(0x05);//
SSD1306_WriteCmd(0xD9);//Set Pre-Charge Period
SSD1306_WriteCmd(0xF1);//
SSD1306_WriteCmd(0xDA);//set com pin hardware configuartion
SSD1306_WriteCmd(0x12);//
SSD1306_WriteCmd(0xDB);//set Vcomh
SSD1306_WriteCmd(0x30);//0x20,0.77xVcc
SSD1306_WriteCmd(0x8D);//set charge pump enable
SSD1306_WriteCmd(0x14);//
SSD1306_WriteCmd(0xAF);//--turn on oled panel
OLED_Clear();
}
//????:????????
void OLED_SetPos(uint8_t x, uint8_t y)
{
//??3???????????????
SSD1306_WriteCmd(0xb0+y); //????? 0xb0~0xb7
SSD1306_WriteCmd(((x&0xf0)>>4)|0x10); //???????
SSD1306_WriteCmd((x&0x0f)); //???????
}
//??OLED??
void OLED_DisplayOn(void)
{
SSD1306_WriteCmd(0X8D); //SET DCDC??
SSD1306_WriteCmd(0X14); //DCDC ON
SSD1306_WriteCmd(0XAF); //DISPLAY ON
}
//??OLED??
void OLED_DisplayOff(void)
{
SSD1306_WriteCmd(0X8D); //SET DCDC??
SSD1306_WriteCmd(0X10); //DCDC OFF
SSD1306_WriteCmd(0XAE); //DISPLAY OFF
}
//????,???,????????!??????
//int clr_i = 0;
//uint8_t clr_n = 0;
void OLED_Clear(void)
{
// clr_i *= (clr_i<8);
int i;
uint8_t n;
for(i=0;i<8;i++)
{
SSD1306_WriteCmd (0xb0+i); //?????(0~7)
SSD1306_WriteCmd (0x00); //??????<3F>????
SSD1306_WriteCmd (0x10); //??????<3F>????
for(n = 0;n < 128;n++)
SSD1306_WriteData(0);
} //????
// clr_i++;
}
//???????????,??????
//x:0~127,y:0~7
//Char_Size:???? 16/12
//uint8_t sc_i = 0;
void OLED_ShowChar(uint8_t x,uint8_t y,uint8_t chr,uint8_t Char_Size,uint8_t color)
{
uint8_t c=0,i=0;
// uint8_t c = 0;
c=chr-' ';//???????
if(x>MAX_COLUMN-1)
{
x=0;
y=y+2;
}
if(Char_Size ==16)
{
if(color == 0)
{
OLED_SetPos(x,y);
for(i=0;i<8;i++)
{
SSD1306_WriteData(F8X16[c*16+i]);//??????
}
OLED_SetPos(x,y+1);
for(i=0;i<8;i++)
{
SSD1306_WriteData(F8X16[c*16+i+8]);//??????
}
}
if(color == 1)
{
OLED_SetPos(x,y);
for(i=0;i<8;i++)
{
SSD1306_WriteData(~F8X16[c*16+i]);//??????
}
OLED_SetPos(x,y+1);
for(i=0;i<8;i++)
{
SSD1306_WriteData(~F8X16[c*16+i+8]);//??????
}
}
}
else
{
OLED_SetPos(x,y);
for(i=0;i<6;i++)
{
SSD1306_WriteData(F6x8[c][i]);
}
// sc_i *= (sc_i<6);
// OLED_SetPos(x,y);
// SSD1306_WriteData(F6x8[c][sc_i]);
// sc_i++;
}
}
//???????
void OLED_ShowString(uint8_t x,uint8_t y,char *str,uint8_t Char_Size,uint8_t color)
{
unsigned char j=0;
while (str[j]!='\0')
{
OLED_ShowChar(x,y,str[j],Char_Size,color);
x+=8;
if(x>120)
{
x=0;
y+=2;
}
j++;//????????page,??0-7
}
}
//????
//?????16*16???,??????4???
//index:?????????
void OLED_ShowCN(uint8_t x,uint8_t y,uint8_t index)
{
uint8_t t;
OLED_SetPos(x,y);
for(t=0;t<16;t++)
{
SSD1306_WriteData(Hzk[index][t]);
}
OLED_SetPos(x,y+1);
for(t=0;t<16;t++)
{
SSD1306_WriteData(Hzk[index][t+16]);
}
}
char str_print2[16] = {0};
float Xads_temp2[2] = {0},T_temp2[2] = {0},OC1_temp[2] = {0},OC2_temp[2] = {0};
char disp_step2 = 0;
void OLED_DisplayTest(void)
{
switch(disp_step2)
{
case 0 :// 初始化
{
OLED2_Init();
disp_step2++;
}
break;
case 1 :// 显示不动
{
disp_step2++;
OLED_ShowString(0,0,(char *)("Pos"),16,0); //(x,y,char,size,color), color{0正常1反显},x{0-128},y{}
OLED_ShowString(0,4,(char *)("Temp"),16,0);
OLED_ShowString(48,2,(char *)("%"),16,0);
}
break;
case 2 :// 显示动的部分
{
//位置
Xads_temp2[0] = X_ads1220_prc;
if(Xads_temp2[1] != Xads_temp2[0] )
{
OLED_ShowString(40,2," ",16,0);
sprintf(str_print2, "%.2f",Xads_temp2[0]*100 ); // 电阻尺
OLED_ShowString(0,2,str_print2,16,0);
Xads_temp2[1] = Xads_temp2[0];
}
//温度
T_temp2[0] = TEMP_M1820;
if(T_temp2[1] != T_temp2[0])
{
sprintf(str_print2, "%.2f",T_temp2[1] ); //温度
OLED_ShowString(40,6," ",16,0);
OLED_ShowString(0,6,str_print2,16,0);
T_temp2[1] = T_temp2[0];
}
}
break;
default ://
{
disp_step2 = 0;
}
break;
}
}
char oled_p = 0,oled_s[2] = {1,1},oled_en = 0,para_flag = 0,motor_flag1 = 0,motor_flag2 = 0;
unsigned int step_temp[2] = {0};;
void OLED_MenuTest(void)
{
switch(oled_p)
{
case 0: //初始化
{
OLED2_Init();
oled_p++;
}
break;
case 1: //显示不动的内容
{
OLED_Clear();
OLED_ShowString(0,0,"Menu",16,0);
OLED_ShowString(0,2,"Parameter ",16,0);
OLED_ShowString(0,4,"Motor Control",16,0);
oled_p++;
}
break;
case 2: //菜单选择
{
if(oled_s[1] == 1)
{
OLED_ShowString(0,2,"Parameter ",16,1);
if(oled_s[0] == 2) OLED_ShowString(0,4,"Motor Control",16,0);
oled_s[0] = oled_s[1];
}
if(oled_s[1] == 2)
{
OLED_ShowString(0,4,"Motor Control",16,1);
if(oled_s[0] == 1) OLED_ShowString(0,2,"Parameter ",16,0);
oled_s[0] = oled_s[1];
}
if( (oled_s[1] == 1) && (oled_en == 1) ) //进入参数观测
{
oled_en = 0;
oled_p = 3;
}
if( (oled_s[1] == 2) && (oled_en == 1) ) //进入电机控制
{
oled_en = 0;
oled_p = 4;
}
}
break;
case 3:
{
if(para_flag == 0)
{
para_flag = 1;
OLED_Clear();
OLED_ShowString(0,0,(char *)("Pos"),16,0); //(x,y,char,size,color), color{0正常1反显},x{0-128},y{}
OLED_ShowString(72,0,(char *)("OC1"),16,0);
OLED_ShowString(0,4,(char *)("Temp"),16,0);
OLED_ShowString(72,4,(char *)("OC2"),16,0);
OLED_ShowString(48,2,(char *)("%"),16,0);
if(ocin1 == 1)
{
OLED_ShowString(72,2," OK ",16,0);
}else
{
OLED_ShowString(72,2,"ERROR",16,0);
}
if(ocin2 == 1)
{
OLED_ShowString(72,6," OK ",16,0);
}else
{
OLED_ShowString(72,6,"ERROR",16,0);
}
}else
{
//位置
Xads_temp2[0] = X_ads1220_prc;
if(Xads_temp2[1] != Xads_temp2[0] )
{
OLED_ShowString(40,2," ",16,0);
sprintf(str_print2, "%.2f",Xads_temp2[0]*100 ); // 电阻尺
OLED_ShowString(0,2,str_print2,16,0);
Xads_temp2[1] = Xads_temp2[0];
}
//温度
T_temp2[0] = TEMP_M1820;
if(T_temp2[1] != T_temp2[0])
{
sprintf(str_print2, "%.2f",T_temp2[1] ); //温度
OLED_ShowString(40,6," ",16,0);
OLED_ShowString(0,6,str_print2,16,0);
T_temp2[1] = T_temp2[0];
}
//位置开关1
OC1_temp[0] = ocin1;
if( OC1_temp[1] != OC1_temp[0] )
{
if(OC1_temp[0] == 1)
{
OLED_ShowString(72,2," OK ",16,0);
}else
{
OLED_ShowString(72,2,"ERROR",16,0);
}
OC1_temp[1] = OC1_temp[0];
}
//位置开关2
OC2_temp[0] = ocin2;
if( OC2_temp[1] != OC2_temp[0] )
{
if(OC2_temp[0] == 1)
{
OLED_ShowString(72,6," OK ",16,0);
}else
{
OLED_ShowString(72,6,"ERROR",16,0);
}
OC2_temp[1] = OC2_temp[0];
}
}
if(oled_en == 1)
{
oled_en = 0;
oled_p = 1;
}
}
break;
case 4:
{
if(motor_flag1 == 0)
{
motor_flag1 = 1;
OLED_Clear();
OLED_ShowString(0,0,"Motor Control",16,0);
OLED_ShowString(0,2,"Run Mode: STEP",16,0);
OLED_ShowString(0,4,"Run Step:",16,0);
sprintf(str_print2, "%d",Run_mm );
OLED_ShowString(80,4,str_print2,16,1);
OLED_ShowString(100,4,"mm",16,0);
}else
{
step_temp[0] = Run_mm;
if(step_temp[0] != step_temp[1])
{
sprintf(str_print2, "%d",step_temp[0] );
OLED_ShowString(80,4,str_print2,16,1);
}
step_temp[1] = step_temp[0];
}
if(oled_en == 1)
{
oled_en = 0;
OLED_ShowString(80,4,str_print2,16,0);
Motor_Run = 1;
oled_p = 5;
}
}
break;
case 5:
{
if(motor_flag2 == 0)
{
motor_flag2 = 1;
OLED_Clear();
OLED_ShowString(0,0,"Running...",16,0);
OLED_ShowString(0,2,"Pos:",16,0);
OLED_ShowString(90,2,"%",16,0);
OLED_ShowString(0,4,"OC1:",16,0);
OLED_ShowString(64,4,"OC2:",16,0);
if(ocin1 == 1)
{
OLED_ShowString(8,6," OK ",16,0);
}else
{
OLED_ShowString(8,6,"ERROR",16,0);
}
if(ocin2 == 1)
{
OLED_ShowString(72,6," OK ",16,0);
}else
{
OLED_ShowString(72,6,"ERROR",16,0);
}
}else
{
//位置
Xads_temp2[0] = X_ads1220_prc;
if(Xads_temp2[1] != Xads_temp2[0] )
{
OLED_ShowString(80,2," ",16,0);
sprintf(str_print2, "%.2f",Xads_temp2[0]*100 ); // 电阻尺
OLED_ShowString(40,2,str_print2,16,0);
Xads_temp2[1] = Xads_temp2[0];
}
//位置开关1
OC1_temp[0] = ocin1;
if( OC1_temp[1] != OC1_temp[0] )
{
if(OC1_temp[0] == 1)
{
OLED_ShowString(8,6," OK ",16,0);
}else
{
OLED_ShowString(8,6,"ERROR",16,0);
}
OC1_temp[1] = OC1_temp[0];
}
//位置开关2
OC2_temp[0] = ocin2;
if( OC2_temp[1] != OC2_temp[0] )
{
if(OC2_temp[0] == 1)
{
OLED_ShowString(72,6," OK ",16,0);
}else
{
OLED_ShowString(72,6,"ERROR",16,0);
}
OC2_temp[1] = OC2_temp[0];
}
}
if(oled_en == 1)
{
Motor_Run = 0;
oled_en = 0;
oled_p = 1;
}
}
}
}