標(biāo)題:
stm8l152c6單片機(jī)adc1采集數(shù)據(jù)在1.0伏進(jìn)位跳躍變成1.99伏
[打印本頁]
作者:
lixianshen
時(shí)間:
2019-4-1 22:56
標(biāo)題:
stm8l152c6單片機(jī)adc1采集數(shù)據(jù)在1.0伏進(jìn)位跳躍變成1.99伏
用網(wǎng)上茗風(fēng)的adc測stm8l內(nèi)部參考電壓程序跑adc1,用的也是他下面的lcd顯示程序,配置如下
開發(fā)環(huán)境:IAR for stm8 v6.5.3
lixianshen 地板
2019-3-29 19:28
大師,我用你的lcd程序和你的adc程序調(diào)試stm8ldiscover套件時(shí)發(fā)現(xiàn),stm8l152c 6t6的adc測電壓時(shí),輸入電壓從0伏調(diào)到2.99伏,lcd輸出顯示也從0到2.99伏,輸入電壓從2.99到1伏時(shí),輸出顯示2.99到1伏。但是輸入電壓從1伏到0.99伏時(shí),顯示從1伏一下跳到1.99伏,輸入電壓從1伏調(diào)到0伏,顯示就從1伏跳到1.99,顯示跟著從1.99伏逐漸降到1.0,1.0伏就是對應(yīng)輸入電壓的0伏。就可以要多顯示1伏,如果現(xiàn)在輸入又從0伏調(diào)大到1伏,顯示就從1增大到1.99伏,然后進(jìn)位又變成1伏,顯示過了1伏后繼續(xù)增加輸入電壓到2.99伏,顯示也從1伏到2.99。而在電腦上的軟件調(diào)試程序窗口中顯示的電壓,與輸入電壓是同步增減的,幾乎相等。而單片機(jī)輸入電壓是用萬用表和示波器同步看的,輸入調(diào)壓是用精密繞線電位器調(diào)壓,輸入電壓沒有跳躍。接收adc高位數(shù)據(jù),從1到15增加沒有問題,從15降到1之后,又跳到19,而adc的低位數(shù)據(jù)從255的0,然后從255到0,基本都很有規(guī)律。如果用lcd顯示電壓比如說1.95伏不正確時(shí),按重啟鍵,然后lcd顯示就變?yōu)?.95伏,就正常顯示,此時(shí)調(diào)低輸入電壓,顯示也跟著正常變低,一旦調(diào)高電壓超過1伏,顯示就成0.99跳到1.99。adc程序從寄存器換成了庫函數(shù),毛病一樣。輸入從pc7換成pf0,毛病一樣。程序觸發(fā)等等都試過,情況沒有變化,不知道是那里的問題?請板主和各位大師解答一下。
*硬件平臺:STM8L-DISCOVERY
*功能說明:使用STM8L-DISCOVERY液晶屏顯示一串6位數(shù)字
*作 者:茗風(fēng)
#include"iostm8l152c6.h"
#include"stm8l15x.h”
#define a 0x01
#define b 0x02
#define c 0x04
#define d 0x08
#define e 0x10
#define f 0x20
#define g 0x40
#define m 0x80
const uint8_t LCD_Tab[10] = {
a + b + c + d + e + f, // Displays "0"
b + c, // Displays "1"
a + b + m + g + e + d, // Displays "2"
a + b + m + g + c + d, // Displays "3"
f + g + m + b + c, // Displays "4"
a + f + g + m + c +d, // Displays "5"
a + f + e + d + c + g + m , // Displays "6"
a + b + c, // Displays "7"
a + b + c + d + e + f + g + m, // Displays "8"
a + b + c + d + f + g + m // Displays "9"
};
/******************************************************************************************************
* 名 稱:void LCD_Config(void)
* 功 能:配置DAC,禁用DMA,不使用TIM4觸發(fā),也不用軟件觸發(fā),寫入DHR的數(shù)據(jù)被立即送入DOR寄存器,
* 立即輸出對應(yīng)電壓
* 入口參數(shù):無
* 出口參數(shù):無
* 說 明:STM8L152C6屬于中等容量MCU,只有一路DAC輸出,輸出引腳為PF0
* 范 例:無
******************************************************************************************************/
void LCD_Config(void)
{
//------打開LCD/RTC時(shí)鐘------
CLK_PCKENR2_PCKEN22=1;//打開RTC時(shí)鐘,LCD刷新頻率與此時(shí)鐘有關(guān)
CLK_PCKENR2_PCKEN23=1;//打開LCD時(shí)鐘,讀寫LCD寄存器用到此時(shí)鐘
//---選擇LSE作為RTC時(shí)鐘---
CLK_CRTCR_RTCSEL0=0;
CLK_CRTCR_RTCSEL1=0;
CLK_CRTCR_RTCSEL2=0;
CLK_CRTCR_RTCSEL3=1;
/* 0000: No clock selected
0001: HSI clock used as RTC clock source
0010: LSI clock used as RTC clock source
0100: HSE clock used as RTC clock source
1000: LSE clock used as RTC clock sourc*/
//----設(shè)置RTC時(shí)鐘分頻值----
CLK_CRTCR_RTCDIV0=0;
CLK_CRTCR_RTCDIV1=0;
CLK_CRTCR_RTCDIV2=0;
/*000: RTC clock source/1
001: RTC clock source /2
010: RTC clock source /4
011: RTC clock source /8
100: RTC clock source /16
101: RTC clock source /32
110: RTC clock source /64
111: RTC clock source /128*/
//----設(shè)置LCD預(yù)分頻值----
LCD_FRQ_PS0=0;// 2^PS[3:0]
LCD_FRQ_PS1=0;//分頻值為1
LCD_FRQ_PS2=0;
LCD_FRQ_PS3=0;
//----設(shè)置LCD分頻值----
LCD_FRQ_DIV0=1;//DIV[3:0]+16
LCD_FRQ_DIV1=1;//分頻值為15+16=31
LCD_FRQ_DIV2=1;
LCD_FRQ_DIV3=1;
//以上分頻值的設(shè)置,最為了得到適合的LCD的刷新頻率,如果增大分頻值,會導(dǎo)致
//LCD刷新頻率變低,會看到LCD顯示出現(xiàn)閃爍
//比如,我們將PS[3:0]設(shè)置為0011,會看到液晶閃爍
//----1/4 duty----
LCD_CR1_DUTY0=1;//1/4 duty
LCD_CR1_DUTY1=1;
/* Duty ratio selection
00: Static duty
01: 1/2 duty
10: 1/3 duty
11: 1/4 duty */
//----1/3 bias----
LCD_CR1_B2=0;//1/3 bias
/* 0: 1/3 bias
1: 1/2 bias */
//----內(nèi)部電壓源----
LCD_CR2_VSEL=0;
//----打開引腳的SEG功能----
// LCD_PM0=0xFF;//頭文件這個(gè)地方定義錯(cuò)誤,無法直接向LCD_PM0寫入數(shù)據(jù)
// LCD_PM1=0xFF;//PM0寄存器定義錯(cuò)誤,導(dǎo)致PM1也無法直接寫入
// LCD_PM2=0xFF;//PM0寄存器定義錯(cuò)誤,導(dǎo)致PM2也無法直接寫入
*((uint8_t *)0x5404)=0xFF;//直接向LCD_PM0寄存器的地址寫入數(shù)據(jù)
*((uint8_t *)0x5405)=0xFF;//直接向LCD_PM1寄存器的地址寫入數(shù)據(jù)
*((uint8_t *)0x5406)=0xFF;//直接向LCD_PM2寄存器的地址寫入數(shù)據(jù)
//----To set contrast to mean value----
LCD_CR2_CC0=0;//對比度
LCD_CR2_CC1=1;
LCD_CR2_CC2=0;
/* 000: VLCD0 2.6V
001: VLCD1 2.7V
010: VLCD2 2.8V
011: VLCD3 2.9V
100: VLCD4 3.0V
101: VLCD5 3.1V
110: VLCD6 3.2V
111: VLCD7 */
//----Dead time 0----
LCD_CR3_DEAD0=0;//no dead time
LCD_CR3_DEAD1=0;
LCD_CR3_DEAD2=0;
//----LCD_PulseOnDuration_1----
LCD_CR2_PON0=1;
LCD_CR2_PON1=0;
LCD_CR2_PON2=0;
/* 000: 0 CLKps pulses
001: 1 CLKps pulses
010: 2 CLKps pulses
011: 3 CLKps pulses
100: 4 CLKps pulses
101: 5 CLKps pulses
110: 6 CLKps pulses
111: 7 CLKps pulses */
//----Enable LCD peripheral----
LCD_CR3_LCDEN=1;
}
/******************************************************************************************************
* 名 稱:LCD_DisplayNum(uint8_t number)
* 功 能:控制段式液晶屏的數(shù)字顯示部分
* 入口參數(shù):number:要顯示的數(shù)字
* 出口參數(shù):無
* 說 明:根據(jù)數(shù)字的長度,判斷要顯示的長度,長度大于6位,只顯示后六位
* 范 例:無
******************************************************************************************************/
void LCD_DisplayNum(uint32_t number)
{
uint8_t cnts=0,tmp=0;
if(number<10)cnts=1;
else if(number<100)cnts=2;
else if(number<1000)cnts=3;
else if(number<10000)cnts=4;
else if(number<100000)cnts=5;
else if(number<(uint32_t) 1000000)cnts=6;
else cnts=6;
//判斷需要顯示數(shù)字的長度,確定在LCD屏上需要的位數(shù)
switch(cnts)
{
case 6:
tmp = LCD_Tab[number%1000000/100000];
((tmp&m)==0)?(LCD_RAM0&=~0x02):(LCD_RAM0 |=0x02) ;
((tmp&e)==0)?(LCD_RAM0&=~0x01):(LCD_RAM0 |=0x01) ;
((tmp&g)==0)?(LCD_RAM2&=~0x80):(LCD_RAM2 |=0x80) ;
((tmp&b)==0)?(LCD_RAM2&=~0x40):(LCD_RAM2 |=0x40) ;
((tmp&f)==0)?(LCD_RAM6&=~0x08):(LCD_RAM6 |=0x08) ;
((tmp&a)==0)?(LCD_RAM6&=~0x04):(LCD_RAM6 |=0x04) ;
((tmp&c)==0)?(LCD_RAM3&=~0x20):(LCD_RAM3 |=0x20) ;
((tmp&d)==0)?(LCD_RAM3&=~0x10):(LCD_RAM3 |=0x10) ;
case 5:
tmp = LCD_Tab[number%100000/10000];
((tmp&m)==0)?(LCD_RAM0&=~0x08):(LCD_RAM0 |=0x08) ;
((tmp&e)==0)?(LCD_RAM0&=~0x04):(LCD_RAM0 |=0x04) ;
((tmp&g)==0)?(LCD_RAM2&=~0x20):(LCD_RAM2 |=0x20) ;
((tmp&b)==0)?(LCD_RAM2&=~0x10):(LCD_RAM2 |=0x10) ;
((tmp&f)==0)?(LCD_RAM6&=~0x02):(LCD_RAM6 |=0x02) ;
((tmp&a)==0)?(LCD_RAM6&=~0x01):(LCD_RAM6 |=0x01) ;
((tmp&c)==0)?(LCD_RAM3&=~0x80):(LCD_RAM3 |=0x80) ;
((tmp&d)==0)?(LCD_RAM3&=~0x40):(LCD_RAM3 |=0x40) ;
case 4:
tmp = LCD_Tab[number%10000/1000];
((tmp&m)==0)?(LCD_RAM0&=~0x20):(LCD_RAM0 |=0x20) ;
((tmp&e)==0)?(LCD_RAM0&=~0x10):(LCD_RAM0 |=0x10) ;
((tmp&g)==0)?(LCD_RAM2&=~0x08):(LCD_RAM2 |=0x08) ;
((tmp&b)==0)?(LCD_RAM2&=~0x04):(LCD_RAM2 |=0x04) ;
((tmp&f)==0)?(LCD_RAM5&=~0x80):(LCD_RAM5 |=0x80) ;
((tmp&a)==0)?(LCD_RAM5&=~0x40):(LCD_RAM5 |=0x40) ;
((tmp&c)==0)?(LCD_RAM4&=~0x02):(LCD_RAM4 |=0x02) ;
((tmp&d)==0)?(LCD_RAM4&=~0x01):(LCD_RAM4 |=0x01) ;
case 3:
tmp = LCD_Tab[number%1000/100];
((tmp&m)==0)?(LCD_RAM0&=~0x80):(LCD_RAM0 |=0x80) ;
((tmp&e)==0)?(LCD_RAM0&=~0x40):(LCD_RAM0 |=0x40) ;
((tmp&g)==0)?(LCD_RAM2&=~0x02):(LCD_RAM2 |=0x02) ;
((tmp&b)==0)?(LCD_RAM2&=~0x01):(LCD_RAM2 |=0x01) ;
((tmp&f)==0)?(LCD_RAM5&=~0x20):(LCD_RAM5 |=0x20) ;
((tmp&a)==0)?(LCD_RAM5&=~0x10):(LCD_RAM5 |=0x10) ;
((tmp&c)==0)?(LCD_RAM4&=~0x08):(LCD_RAM4 |=0x08) ;
((tmp&d)==0)?(LCD_RAM4&=~0x04):(LCD_RAM4 |=0x04) ;
case 2:
tmp = LCD_Tab[number%100/10];
((tmp&m)==0)?(LCD_RAM1&=~0x02):(LCD_RAM1 |=0x02) ;
((tmp&e)==0)?(LCD_RAM1&=~0x01):(LCD_RAM1 |=0x01) ;
((tmp&g)==0)?(LCD_RAM1&=~0x80):(LCD_RAM1 |=0x80) ;
((tmp&b)==0)?(LCD_RAM1&=~0x40):(LCD_RAM1 |=0x40) ;
((tmp&f)==0)?(LCD_RAM5&=~0x08):(LCD_RAM5 |=0x08) ;
((tmp&a)==0)?(LCD_RAM5&=~0x04):(LCD_RAM5 |=0x04) ;
((tmp&c)==0)?(LCD_RAM4&=~0x20):(LCD_RAM4 |=0x20) ;
((tmp&d)==0)?(LCD_RAM4&=~0x10):(LCD_RAM4 |=0x10) ;
case 1:
tmp = LCD_Tab[number%10];
((tmp&m)==0)?(LCD_RAM1&=~0x08):(LCD_RAM1 |=0x08) ;
((tmp&e)==0)?(LCD_RAM1&=~0x04):(LCD_RAM1 |=0x04) ;
((tmp&g)==0)?(LCD_RAM1&=~0x20):(LCD_RAM1 |=0x20) ;
((tmp&b)==0)?(LCD_RAM1&=~0x10):(LCD_RAM1 |=0x10) ;
((tmp&f)==0)?(LCD_RAM5&=~0x02):(LCD_RAM5 |=0x02) ;
((tmp&a)==0)?(LCD_RAM5&=~0x01):(LCD_RAM5 |=0x01) ;
((tmp&c)==0)?(LCD_RAM4&=~0x80):(LCD_RAM4 |=0x80) ;
((tmp&d)==0)?(LCD_RAM4&=~0x40):(LCD_RAM4 |=0x40) ;
break;
default:break;
}
}
void main(void)
{
LCD_Config();
LCD_DisplayNum(201609);
// asm("rim"); //enable interrupts
while(1)
{
asm("wfi");
}
}
復(fù)制代碼
作者:
lixianshen
時(shí)間:
2019-4-2 10:02
今天早上看了一下,感覺是lcd顯示程序有問題,調(diào)用lcdconfig()在程序中放的位置不同,就會有退位后已經(jīng)是0伏,仍然還顯示1,另外兩位也會出現(xiàn)同樣問題。
作者:
lixianshen
時(shí)間:
2019-4-10 07:59
問題已經(jīng)解決了,主要是原程序中沒有清屏語句,在寫入數(shù)據(jù)到顯示緩存之前加上lcd_clear()函數(shù)就沒有問題了。
歡迎光臨 (http://www.torrancerestoration.com/bbs/)
Powered by Discuz! X3.1