分享一个4位数码管的动态显示的模块,也可以用在其他的芯片上。
很简洁的实现了字符串的滚动显示,
源代码如下
#ifndef __DIGITRON_H__
#define __DIGITRON_H__
#include <stdio.h>
#include <string.h>
#include "me32f103.h"
#include "me32f103_sys.h"
#include "me32f103_gpio.h"
#include "me32f103_ioconfig.h"
#include "me32f103_iap.h"
#include "typedefs.h"
#define BITA BIT0
#define BITB BIT1
#define BITC BIT2
#define BITD BIT3
#define BITE BIT4
#define BITF BIT5
#define BITG BIT6
#define BITH BIT7
#define DIGIT_0 (BITA|BITB|BITC|BITD|BITE|BITF)
#define DIGIT_1 (BITB|BITC)
#define DIGIT_2 (BITA|BITB|BITG|BITD|BITE)
#define DIGIT_3 (BITA|BITB|BITC|BITD|BITG)
#define DIGIT_4 (BITB|BITC|BITF|BITG)
#define DIGIT_5 (BITA|BITF|BITG|BITC|BITD)
#define DIGIT_6 (BITA|BITG|BITC|BITD|BITE|BITF)
#define DIGIT_7 (BITA|BITB|BITC)
#define DIGIT_8 (BITA|BITB|BITC|BITD|BITE|BITF|BITG)
#define DIGIT_9 (BITA|BITB|BITC|BITD|BITF|BITG)
#define DIGIT_A (BITA|BITB|BITC|BITE|BITF|BITG)
#define DIGIT_B (BITC|BITD|BITE|BITF|BITG)
#define DIGIT_C (BITA|BITD|BITE|BITF)
#define DIGIT_D (BITB|BITC|BITD|BITE|BITG)
#define DIGIT_E (BITA|BITD|BITE|BITF|BITG)
#define DIGIT_F (BITA|BITE|BITF|BITG)
#define DIGIT_G (BITA|BITC|BITD|BITE|BITF)
#define DIGIT_H (BITB|BITC|BITE|BITF|BITG)
#define DIGIT_I (BITA|BITB|BITC|BITD)
#define DIGIT_J (BITB|BITC|BITD)
#define DIGIT_K (BITA|BITC|BITE|BITF|BITG)
#define DIGIT_L (BITD|BITE|BITF)
#define DIGIT_M (BITA|BITB|BITC|BITE|BITF)
#define DIGIT_N (BITC|BITE|BITG)
#define DIGIT_O (BITC|BITD|BITE|BITG)
#define DIGIT_P (BITA|BITB|BITE|BITF|BITG)
#define DIGIT_Q (BITA|BITB|BITC|BITF|BITG)
#define DIGIT_R (BITA|BITE|BITF)
#define DIGIT_S (BITA|BITD|BITG)
#define DIGIT_T (BITD|BITE|BITF|BITG)
#define DIGIT_U (BITB|BITC|BITD|BITE|BITF)
#define DIGIT_V (BITC|BITD|BITE)
#define DIGIT_W (BITB|BITC|BITD|BITE|BITF|BITG)
#define DIGIT_X (BITC|BITF|BITG)
#define DIGIT_Y (BITB|BITC|BITD|BITF|BITG)
#define DIGIT_Z (BITB|BITD|BITE|BITG)
#define DIGIT_OFF 0
#define DIGIT_ALL (BITA|BITB|BITC|BITD|BITE|BITF|BITG|BITH)
typedef struct
{
char * string; //ÐèÒªÏÔʾµÄ×Ö·û´®
uint8_t coms; //ÊýÂë¹ÜλÊý
uint8_t length; //ÏÔʾ×Ö·û´®³¤¶È
uint8_t current; //µ±Ç°²½Êý
uint8_t levels; //×ܲ½Êý
uint8_t rate; //ÏÔʾ¸üÐÂƵÂÊ
union //ÏÔʾË÷Òý»º´æ
{
uint8_t bytes[4];
uint32_t dat;
} buffers;
} digitron_object_t;
extern digitron_object_t digitron_object;
extern const uint8_t alphanumeric_array_size ;
extern char *convert_value2str(uint16_t val, uint8_t radix);
extern void digitron_gpio_init(void);
extern void digitron_strings_set(digitron_object_t *object, char *str);
extern void digitron_update(digitron_object_t *object);
extern void digitron_scan(digitron_object_t *object);
#endif
#include "digitron.h"
digitron_object_t digitron_object;
const uint8_t alphanumeric_array[] =
{
DIGIT_OFF ,
DIGIT_0 ,
DIGIT_1 ,
DIGIT_2 ,
DIGIT_3 ,
DIGIT_4 ,
DIGIT_5 ,
DIGIT_6 ,
DIGIT_7 ,
DIGIT_8 ,
DIGIT_9 ,
DIGIT_A ,
DIGIT_B ,
DIGIT_C ,
DIGIT_D ,
DIGIT_E ,
DIGIT_F ,
DIGIT_G ,
DIGIT_H ,
DIGIT_I ,
DIGIT_J ,
DIGIT_K ,
DIGIT_L ,
DIGIT_M ,
DIGIT_N ,
DIGIT_O ,
DIGIT_P ,
DIGIT_Q ,
DIGIT_R ,
DIGIT_S ,
DIGIT_T ,
DIGIT_U ,
DIGIT_V ,
DIGIT_W ,
DIGIT_X ,
DIGIT_Y ,
DIGIT_Z ,
DIGIT_ALL ,
};
const uint8_t alphanumeric_array_size = ARR_SIZE(alphanumeric_array);
/**
* @method digitron_gpio_init
* @brief ÊýÂë¹ÜGPIO³õʼ»¯
* @details 4λ¹²Òõ
* @param ;
* @retval ;
*/
void digitron_gpio_init(void)
{
//com0~com3
PA9_INIT(PA9_GPIO);
PA10_INIT(PA10_GPIO);
PA11_INIT(PA11_GPIO);
PA12_INIT(PA12_GPIO);
//seg1~8
PB3_INIT(PB3_GPIO);
PB4_INIT(PB4_GPIO);
PB5_INIT(PB5_GPIO);
PB6_INIT(PB6_GPIO);
PA4_INIT(PA4_GPIO);
PA5_INIT(PA5_GPIO);
PA6_INIT(PA6_GPIO);
PA7_INIT(PA7_GPIO);
PB_INIT_AS_OUTPUT(IO_PIN3);
PB_INIT_AS_OUTPUT(IO_PIN4);
PB_INIT_AS_OUTPUT(IO_PIN5);
PB_INIT_AS_OUTPUT(IO_PIN6);
PA_INIT_AS_OUTPUT(IO_PIN9);
PA_INIT_AS_OUTPUT(IO_PIN10);
PA_INIT_AS_OUTPUT(IO_PIN11);
PA_INIT_AS_OUTPUT(IO_PIN12);
PA_INIT_AS_OUTPUT(IO_PIN4);
PA_INIT_AS_OUTPUT(IO_PIN5);
PA_INIT_AS_OUTPUT(IO_PIN6);
PA_INIT_AS_OUTPUT(IO_PIN7);
}
/**
* @method convert_value2str
* @brief ½«Ò»¸öÎÞ·ûºÅÕûÐÍֵת»»Îª×Ö·û´®
* @details ;
* @param uint16_t val ÐèÒª±»×ª»»µÄÖµ
* @param uint8_t radix ת»»½øÖÆ 2£º¶þ½øÖÆ£¬8£º°Ë½øÖÆ£¬10£ºÊ®½øÖÆ£¬16£ºÊ®Áù½øÖÆ
* @retval ;
*/
char * convert_value2str(uint16_t val, uint8_t radix)
{
uint8_t i = 0, left = 0, right = 0;
static char str[17] = "";
if(radix == 2)
{
while(val != 0)
{
str = (val % radix) + '0' ;
val /= radix;
i++;
}
if(i > 0) right = i - 1;
while (left < right)
{
char temp = str[left];
str[left] = str[right];
str[right] = temp;
left++;
right--;
}
}
else if(radix == 8) sprintf(str, "%o", val);
else if(radix == 10) sprintf(str, "%u", val);
else if(radix == 16) sprintf(str, "%x", val);
return (char *)(&str);
}
/**
* @method digitron_drive
* @brief ;
* @details ;
* @param ;
* @retval ;
*/
static void digitron_drive(uint8_t dat)
{
ubit8_t temp;
temp.byte = dat;
(temp.bits.bit0 != 0) ? (PB->DOSET = IO_BIT_PIN3) : (PB->DOCLR = IO_BIT_PIN3);
(temp.bits.bit1 != 0) ? (PB->DOSET = IO_BIT_PIN4) : (PB->DOCLR = IO_BIT_PIN4);
(temp.bits.bit2 != 0) ? (PB->DOSET = IO_BIT_PIN5) : (PB->DOCLR = IO_BIT_PIN5);
(temp.bits.bit3 != 0) ? (PB->DOSET = IO_BIT_PIN6) : (PB->DOCLR = IO_BIT_PIN6);
(temp.bits.bit4 != 0) ? (PA->DOSET = IO_BIT_PIN4) : (PA->DOCLR = IO_BIT_PIN4);
(temp.bits.bit5 != 0) ? (PA->DOSET = IO_BIT_PIN5) : (PA->DOCLR = IO_BIT_PIN5);
(temp.bits.bit6 != 0) ? (PA->DOSET = IO_BIT_PIN6) : (PA->DOCLR = IO_BIT_PIN6);
(temp.bits.bit7 != 0) ? (PA->DOSET = IO_BIT_PIN7) : (PA->DOCLR = IO_BIT_PIN7);
}
/**
* @method digitron_scan
* @brief ÊýÂë¹ÜɨÃè
* @details ;
* @param ;
* @retval ;
*/
void digitron_scan(digitron_object_t *object)
{
static uint8_t steps = 0;
ubit8_t coms = {0xff};
PA->DOSET = IO_BIT_PIN9;
PA->DOSET = IO_BIT_PIN10;
PA->DOSET = IO_BIT_PIN11;
PA->DOSET = IO_BIT_PIN12;
coms.byte &= ~(0x01 << steps);
digitron_drive(alphanumeric_array[(object->buffers).bytes[steps]]);
(coms.bits.bit3 != 0) ? (PA->DOSET = IO_BIT_PIN9) : (PA->DOCLR = IO_BIT_PIN9);
(coms.bits.bit2 != 0) ? (PA->DOSET = IO_BIT_PIN10) : (PA->DOCLR = IO_BIT_PIN10);
(coms.bits.bit1 != 0) ? (PA->DOSET = IO_BIT_PIN11) : (PA->DOCLR = IO_BIT_PIN11);
(coms.bits.bit0 != 0) ? (PA->DOSET = IO_BIT_PIN12) : (PA->DOCLR = IO_BIT_PIN12);
if(++steps >= object->coms) steps = 0;
}
/**
* @method get_character_index
* @brief »ñÈ¡Ò»¸ö×Ö·ûµÄË÷ÒýÖµ
* @details »ñÈ¡×Ö·û´®ÖÐÆ«ÒÆnλµÄ×Ö·ûÔÚÊý×éalphanumeric_arrayÖеÄË÷ÒýÖµ
* @param char *chr ÐèÒª²éÕÒ×Ö·ûËùÔÚµÄ×Ö·û´®
* @param uint8_t n Æ«ÒÆλÊý
* @retval uint8_t ·µ»ØË÷ÒýÖµ ÈôÊÇÕÒ²»µ½Ëù²éÕÒ×Ö·û»òÆ«ÒÆλÊýn´óÓÚ×Ö·û´®³¤¶È·µ»Ø 0£»
*/
static uint8_t get_character_index(char *chr, uint8_t n)
{
uint8_t i, len;
const char * string = " 0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ";
if( n >= strlen(chr) ) return 0;
len = strlen(string);
chr += n;
if( (*chr) >= 'a' && (*chr) <= 'z') *chr = (*chr) - 32; //ÈôÊÇСд×ÖĸÔòת»»Îª´óд×Öĸ
for(i = 0; i < len ; i++)
{
if(*string == *chr)
{
return i;
}
string++;
}
return 0;
}
/**
* @method digitron_buffer_lshift
* @brief ÊýÂë¹Ü»º´æÊý¾Ý×óÒÆ
* @details ÓÃÓÚ×Ö·û´®´óÓÚÊýÂë¹ÜλÊýµÄÇé¿öÏÂÉèÖûº´æ£¬ÊµÏÖ¶¯Ì¬ÏÔʾ
* @param ;
* @retval ;
*/
static void digitron_buffer_lshift(digitron_object_t *object)
{
(object->buffers).dat <<= 8;
if(object->current < object->length)
{
(object->buffers).bytes[0] = get_character_index(object->string, object->current);
}
if((++(object->current)) >= object->levels)
{
object->current = 0;
}
}
/**
* @method digitron_buffer_set
* @brief ÊýÂë¹Ü»º´æÊý¾ÝÉèÖÃ
* @details ÓÃÓÚ×Ö·û´®Ð¡ÓÚ»òµÈÓÚÊýÂë¹ÜλÊýµÄÇé¿öÏÂÉèÖûº´æ£¬ÊµÏÖ¾²Ì¬ÏÔʾ
* @param ;
* @retval ;
*/
static void digitron_buffer_set(digitron_object_t *object)
{
uint8_t i;
for(i = 0; i < 4; i++)
{
(object->buffers).bytes = get_character_index(object->string, i);
}
}
/**
* @method ;
* @brief ;
* @details ;
* @param ;
* @retval ;
*/
void digitron_strings_set(digitron_object_t *object, char *str)
{
object->string = str;
object->length = strlen(object->string); //ÏÔʾ×Ö·û´®³¤¶È
object->coms = 4;
//×Ö·û´®³¤¶ÈСÓÚµÈÓÚÊýÂë¹ÜλÊýʱ£¬¹ö¶¯ÏÔʾ»ò¾²Ö¹ÏÔʾ
// object->levels = object->length + object->coms -1 ;
object->levels = (object->length > object->coms) ? (object->length + object->coms - 1 ) : (0);
(object->buffers).dat = 0;
object->current = 0;
object->rate = 0;
}
/**
* @method ;
* @brief ;
* @details ;
* @param ;
* @retval ;
*/
void digitron_update(digitron_object_t *object)
{
(object->levels > 0) ? (digitron_buffer_lshift(object)) : (digitron_buffer_set(object));
// (object->length > object->coms) ? (digitron_buffer_lshift(object)) : (digitron_buffer_set(object));
}
// main 文件
#include "me32f103.h"
#include "me32f103_sys.h"
#include "me32f103_gpio.h"
#include "me32f103_ioconfig.h"
#include "me32f103_iap.h"
#include "digitron.h"
uint16_t cnt = 0;
int main(void)
{
digitron_gpio_init();
digitron_strings_set(&digitron_object, "HELLO MIAN BAO BAN");
while(1)
{
digitron_scan(&digitron_object);
if(++cnt >= 4000)
{
digitron_update(&digitron_object);
cnt = 0;
}
}
}