显示浮点数的小程序(AVR)
2013-01-10
标签: 浮点数

如果自己编写程序来处理浮点数,那是很头疼的事。还好,各种C语言开发平台都有现成的浮点数处理函数,而且CodeVisionAVR还提供了浮点数转换成字符串形式的函数,让像我这样的“小白菜”爽死了:)!本文就是用CodeVisionAVR写的一个显示浮点数的小程序,还涉及到了MAX7219及AVR单片机的SPI串行口的运用,供广大“小白菜”参考。

MAX7219是SPI串行接口的数码管驱动芯片,内部集成了段驱动器、位驱动器、数据保存器(实现静态显示)、BCD译码器、多路扫描器(单独修改某位数字)等,可驱动8位LED数码管或可以驱动64只发光二极管,节省大量的IO引脚。其特点如下:

  • 采用SPI串行接口;
  • 内部集成8字节显示RAM和6个控制寄存器,能单独修改某一位,且不需要动态扫描;
  • 译码与不译码两种显示模式,可单独设置某一位或多位的显示模式;
  • 可通过外部电阻或编程方式调节LED高度;
  • 可编程设置成“低功耗模式”,关闭LED显示。
  • MAX7219还支持级联,N个MAX7219芯片DOUT相联,驱动N个8位LED或64N个发光二极管

附:Proteus仿真结果


/*****************************************************
Author: Benny
Chip type: ATmega16L
Clock frequency: 8.000000 MHz
知识点:浮点数显示、max7219、SPI
*****************************************************/
#include <avr/io.h>
#define uint unsigned int
#define uchar unsigned char
#define ulong unsigned long
#define LOAD_PORT PORTB
void send(uchar addr, uchar data)
{
    //PB3接Max7219的load引脚
    LOAD_PORT &= ~(1 << 3); //拉低load
    spi(addr);
    spi(data);
    LOAD_PORT |= (1 << 3); //拉高load
}

#define DECODE_MODE 0X09
#define INTENSITY0X0A
#define SCAN_LIMIT0X0B
#define SHUTDOWN0X0C
#define DISPLAYTEST 0X0F

void max7219_init(uchar decode_bits)
{
// decode_bits如:0b01001111中 1:decode0:nodecode
    send(SHUTDOWN, 0x01); //从Shutdown模式进入Normal
    send(DECODE_MODE, decode_bits); //设置需要转换成BCD码的位
    send(SCAN_LIMIT, 0x07); //共有8只LED(或8位一体)
    send(INTENSITY, 0x09); //亮度
    send(DISPLAYTEST, 0x00); //测试
}

void display_float(float data, uchar bits)
{
    /*bits:小数位数,必须是1,2,3,4,5*/
    uchar i, dot_position;
    uchar arr[16];
    for (i = 0; i < 16; i++) {
        arr[i] = 0;
    }
    ftoa(data, bits, arr); //将浮点数转换成字符串
    for (i = 0; i < 9; i++) {
        if (arr[i] == ''.'') {
            dot_position = i;
        }
    }
    for (i = 0; i < 8; i++) {
        if (i == dot_position - 1) {
            send(i + 1, arr[i] | 0x80); //个位数+小数点
        }
        else if (i >= dot_position) {
            if (i {
            send(i + 1, arr[i + 1]); //小数点后bits个数字
            }
            else {
                send(i + 1, 0x7f); //无效位关闭显示
            }
        }
        else {
            send(i + 1, arr[i]); //十位以上的数字
        }
    }
}
void spi_init(void)
{
    PORTB = 0x00;
    DDRB = 0xB8;
    ACSR = 0x80;
    SFIOR = 0x00;
// SPI initialization
// SPI Type: Master
// SPI Clock Rate: 2000.000 kHz
// SPI Clock Phase: Cycle Half
// SPI Clock Polarity: Low
// SPI Data Order: MSB First
    SPCR = 0x50;
    SPSR = 0x00;
}

void main(void)
{
    spi_init();//初始化SPI串行口
    max7219_init(0b11111111);//8位都初始化为max7219内部译成七段码模式
    display_float(123.4567891, 5); //显示结果为123.45678
    while (1);
}


可能会用到的工具/仪表
本站简介 | 意见建议 | 免责声明 | 版权声明 | 联系我们
CopyRight@2024-2039 嵌入式资源网
蜀ICP备2021025729号