最近用到了TM1650,折騰一下,寫驅動時嚴格按著時序要求。
- #include "gd32f10x.h"
- #include "Header.h"
- #include "systick.h"
- //產生IIC總線起始信號
- static void TM1650_IIC_start(void)
- {
- TM1650_IIC_SCL_HIGH; //SCL=1
- TM1650_IIC_SDA_HIGH; //SDA=1
- DelayUs(100);
- TM1650_IIC_SDA_LOW; //SDA=0
- DelayUs(100);
- TM1650_IIC_SCL_LOW; //SCL=0
- }
-
- //產生IIC總線結束信號
- static void TM1650_IIC_stop(void)
- {
- TM1650_IIC_SDA_LOW; //SDA=0
- DelayUs(100);
- TM1650_IIC_SCL_HIGH;
- DelayUs(100);
- TM1650_IIC_SDA_HIGH; //SDA=1
- DelayUs(100);
- TM1650_IIC_SCL_LOW; //SCL=0
- TM1650_IIC_SDA_LOW; //SDA=0
- }
-
- //通過IIC總線發送一個字節
- static void TM1650_IIC_write_byte(uint8_t dat)
- {
- uint8_t i;
-
- TM1650_IIC_SCL_LOW;
- for(i=0;i<8;i++)
- {
- TM1650_IIC_SDA_WR(dat&0x80);
- DelayUs(100);
- TM1650_IIC_SCL_HIGH;
- DelayUs(100);
- TM1650_IIC_SCL_LOW;
- DelayUs(100);
- dat<<=1;
- }
- }
-
- //通過IIC總線接收從機響應的ACK信號
- void TM1650_IIC_wait_ack(void)
- {
-
- TM1650_IIC_SDA_HIGH; //SDA=1
- DelayUs(100);
- DelayUs(100);
- TM1650_IIC_SCL_HIGH;
-
- //TM1650_IIC_SDA_MODE_IF; //控制引腳為浮空輸入
- DelayUs(100);
- //while(TM1650_IIC_SDA_RD()) //ack_signal = 1; //如果讀取到的是NACK信號
- //TM1650_IIC_SDA_MODE_OD; // 控制引腳為開漏輸出
- DelayUs(100);
- TM1650_IIC_SCL_LOW;
- DelayUs(100);
- }
-
-
- //TM1650初始化
- void TM1650_init(void)
- {
- rcu_periph_clock_enable(RCU_AF);
- rcu_periph_clock_enable(RCU_GPIOA); // 開時基
- rcu_periph_clock_enable(RCU_GPIOC);
-
- gpio_pin_remap_config(GPIO_SWJ_SWDPENABLE_REMAP, ENABLE); // 將PA15定義成普通IO
- TM1650_IIC_SCL_MODE_OD; //SCL開漏輸出
- TM1650_IIC_SDA_MODE_OD; //SDA開漏輸出
-
- TM1650_IIC_SDA_HIGH; //釋放SDA線
- TM1650_IIC_SCL_HIGH; //釋放SCL線
-
- TM1650_cfg_display(TM1650_BRIGHT5); //初始化為5級亮度,打開顯示
- TM1650_clear(); //將顯存內容清0
- delay_1ms(20);
- }
-
-
- //作用:設置顯示參數
- //備注:這個操作不影響顯存中的數據
- //用例:
- // 設置亮度并打開顯示:TM1650_cfg_display(TM1650_BRIGHTx)
- // 關閉顯示:TM1650_cfg_display(TM1650_DSP_OFF)
- void TM1650_cfg_display(uint8_t param)
- {
- TM1650_IIC_start();
- TM1650_IIC_write_byte(0x48); TM1650_IIC_wait_ack(); //固定命令
- TM1650_IIC_write_byte(param); TM1650_IIC_wait_ack(); //參數值
- TM1650_IIC_stop();
- }
-
-
- //將顯存數據全部刷為0,清空顯示
- void TM1650_clear(void)
- {
- uint8_t dig;
- for(dig = TM1650_DIG1 ; dig<= TM1650_DIG4 ;dig++)
- {
- TM1650_print(dig,0); //將顯存數據刷為0
- }
- }
-
- //往一個指定的數碼管位寫入指定的顯示數據
- //共陰數碼管段碼表:
- //const uint8_t TUBE_TABLE_0[10] = {0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f}; //共陰,0~9的數字
- //const uint8_t TUBE_TABLE_0[16] = {0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f,0x77,0x7c,0x39,0x5e,0x79,0x71}; //共陰,0~9~A~F
- //用例:
- // 在DIG1位上顯示數字3: TM1650_print(TM1650_DIG1,TUBE_TABLE_0[3]);
- void TM1650_print(uint8_t dig,uint8_t seg_data)
- {
- TM1650_IIC_start();
- TM1650_IIC_write_byte(dig*2+0x68); TM1650_IIC_wait_ack(); //顯存起始地址為0x68
- TM1650_IIC_write_byte(seg_data); TM1650_IIC_wait_ack(); //發送段碼
- TM1650_IIC_stop();
- }
復制代碼
TM1650.h
- #ifndef TM1650_H_
- #define TM1650_H_
- #include "header.h"
- #include "gd32f10x.h"
- #define GPIO_SCL GPIOC
- #define GPIO_Pin_SCL GPIO_PIN_12
- #define GPIO_SDA GPIOA
- #define GPIO_Pin_SDA GPIO_PIN_15
- //==========【配置IIC驅動引腳】========
-
- //配置驅動SCL的gpio為開漏輸出模式
- #define TM1650_IIC_SCL_MODE_OD gpio_init(GPIO_SCL, GPIO_MODE_OUT_PP, GPIO_OSPEED_50MHZ, GPIO_Pin_SCL)
-
- //配置驅動SDA的gpio為開漏輸出模式
- #define TM1650_IIC_SDA_MODE_OD gpio_init(GPIO_SDA, GPIO_MODE_OUT_PP , GPIO_OSPEED_50MHZ, GPIO_Pin_SDA)
- #define TM1650_IIC_SDA_MODE_IF gpio_init(GPIO_SDA, GPIO_MODE_IN_FLOATING , GPIO_OSPEED_50MHZ, GPIO_Pin_SDA)
-
- //=====================================
-
-
- //========【配置IIC總線的信號讀寫和時序】=======
- //主機拉高SCL
- #define TM1650_IIC_SCL_HIGH gpio_bit_set(GPIO_SCL,GPIO_Pin_SCL)
-
- //主機拉低SCL
- #define TM1650_IIC_SCL_LOW gpio_bit_reset(GPIO_SCL,GPIO_Pin_SCL)
-
-
- //主機拉高SDA
- #define TM1650_IIC_SDA_HIGH gpio_bit_set(GPIO_SDA,GPIO_Pin_SDA)
-
- //主機拉低SDA
- #define TM1650_IIC_SDA_LOW gpio_bit_reset(GPIO_SDA,GPIO_Pin_SDA)
-
- //參數b為0時主機拉低SDA,非0則拉高SDA
- #define TM1650_IIC_SDA_WR(b) do{ \
- if(b) gpio_bit_set(GPIO_SDA,GPIO_Pin_SDA); \
- else gpio_bit_reset(GPIO_SDA,GPIO_Pin_SDA); \
- }while(0)
-
-
- //主機讀取SDA線電平狀態,返回值為0為低電平,非0則為高電平
- #define TM1650_IIC_SDA_RD() gpio_input_bit_get(GPIO_SDA,GPIO_Pin_SDA)
-
- //軟件延時2us
- //#define TM1650_IIC_DELAY_2US do{for(int ii_=0;ii_<22;ii_++);}while(0)
-
- //軟件延時4us
- //#define TM1650_IIC_DELAY_4US do{for(int ii_=0;ii_<40;ii_++);}while(0)
- //================================
-
- //顯示參數
- #define TM1650_BRIGHT1 0x11 /*一級亮度,打開LED顯示*/
- #define TM1650_BRIGHT2 0x21 /*二級亮度,打開LED顯示*/
- #define TM1650_BRIGHT3 0x31 /*三級亮度,打開LED顯示*/
- #define TM1650_BRIGHT4 0x41 /*四級亮度,打開LED顯示*/
- #define TM1650_BRIGHT5 0x51 /*五級亮度,打開LED顯示*/
- #define TM1650_BRIGHT6 0x61 /*六級亮度,打開LED顯示*/
- #define TM1650_BRIGHT7 0x71 /*七級亮度,打開LED顯示*/
- #define TM1650_BRIGHT8 0x01 /*八級亮度,打開LED顯示*/
- #define TM1650_DSP_OFF 0x00 /*關閉LED顯示*/
-
- //數碼管位選
- #define TM1650_DIG1 0
- #define TM1650_DIG2 1
- #define TM1650_DIG3 2
- #define TM1650_DIG4 3
-
- void TM1650_init(void);
- void TM1650_cfg_display(uint8_t param);
- void TM1650_clear(void);
- void TM1650_print(uint8_t dig,uint8_t seg_data);
-
- #endif //TM1650_H_
復制代碼
|