📄 mcs51-项目开发经典.lst
字号:
194 1 PS=1; //串口中断优先级设为高,因为要通过串口干预程序流程,为保证可靠接收所以有此设置
195 1 SCON=0x50;//串口工作于方式1,启动串口接收
196 1
197 1 EA=1;//CPU中断开放
198 1
199 1 //以下是程序中软件逻辑需要的变量初值设置和硬件初始状态设置
200 1 key_value_main=0xff;
201 1
202 1 }
203 //=================================================================================================
204 // 以下是HD7279驱动程序
205 // 操作HD7279的关键是如何保证手册中给定的T1到T8这8个时间间隔
206 // 并且只有当HD7279的27脚外接R=1。5K、C=15P时,T1到T8才是手册中给的数值,建议不要随意改变R、C的值
207 // 弄清楚这个问题,则你对器件时序图的理解将上升到一个新的高度。任何器件的驱动程序只要看懂时序图就OK!
208 //=================================================================================================
209 // 函数功能:长延时,保证延时时间在50~250uS之间
210 void HD7279_LongDelay(void)
211 { uchar i;
212 1 for (i=0;i<30;i++);
213 1 }
214 //-------------------------------------------------------------------------------------------------
215 // 函数功能:短延时,保证延时时间在8~250uS之间
216 void HD7279_ShortDelay(void)
217 { uchar i;
218 1 for (i=0;i<8;i++);
219 1 }
220 //-------------------------------------------------------------------------------------------------
221 //函数功能:向HD7279写字节
222 void HD7279_SendByte(uchar out_byte)
223 { uchar i;
224 1 CLK_7279=0;//准备CLK脚状态
225 1 CS_7279=0; //准备CS脚状态,置0允许操作7279
226 1 HD7279_LongDelay();//延时T1,在带数据的命令中此延时相当于送数据之前的T4延时
227 1 for(i=0;i<8;i++)
228 1 {if(out_byte&0x80) DATA_7279=1;//准备数据,高位MSB先入
229 2 else DATA_7279=0;
230 2 CLK_7279=1;//CLK_7279下降沿时DATA_7279数据写入
231 2 HD7279_ShortDelay();//延时T2
232 2 CLK_7279=0;
233 2 HD7279_ShortDelay();//延时T3
234 2 out_byte<<=1;//准备要写入数据的次高位
235 2 }
236 1 }
237 //-------------------------------------------------------------------------------------------------
238 //函数功能:从HD7279读字节,只在读键值时用到
239 uchar HD7279_ReceiveByte(void)
240 { uchar i;
241 1 uchar in_byte;
C51 COMPILER V7.06 MCS51__钅靠猒_____ 12/10/2008 19:58:27 PAGE 5
242 1 DATA_7279=1;//置单片机DATA_7279端为输入状态
243 1 HD7279_LongDelay();//延时T5
244 1 for(i=0;i<8;i++)
245 1 {CLK_7279=1;
246 2 HD7279_ShortDelay();//延时T7(因为T7=T6),此延时结束后HD7279_DATA数据才有效,
247 2 in_byte=in_byte<<1;//键值的高位MSB先出,因为最低位LSB取出后不需要左移,所以有此操作
248 2 if(DATA_7279) in_byte=in_byte|0x01;//取HD7279_DATA的数据状态,放入in_byte最低位LSB
249 2 CLK_7279=0;
250 2 HD7279_ShortDelay();//延时T3,这个延时手册中没有标出(因为T3>T8,所以最后1位取出后此T3相当于T8)
251 2 }
252 1 return (in_byte);
253 1 }
254 //----------------------------------------------------------------------------------------------
255 //函数功能:获得按键代码
256 uchar HD7279_GetKey(void)
257 { uchar key;
258 1 HD7279_SendByte(HD7279_READ_KEY);
259 1 key=HD7279_ReceiveByte();
260 1 return(key);
261 1 }
262 //-------------------------------------------------------------------------------------------------
263 // 函数功能:按方式0译码,在指定的1到8位置显示数据
264 // 通常情况下我们都使用方式0译码,方式1译码与之大同小异
265 // 形参:Position 显示位置(1-8),ShowData 数据(0-15),Have_DP 是否显示小数点(1显示,0不显示)
266 void HD7279_ShowData(uchar Position,uchar ShowData,bit Have_DP)
267 { uchar Decode0_data;
268 1 if(Have_DP) ShowData = ShowData|0x80;//处理小数点的显示与否
269 1 Decode0_data=(Position-1)|HD7279_DECODE0;//将译码方式0和要显示的位置合并
270 1 HD7279_SendByte(Decode0_data);//送命令
271 1 HD7279_SendByte(ShowData);//送数据
272 1 CS_7279=1;
273 1 }
274 //-------------------------------------------------------------------------------------------------
275 // 函数功能:按方式0译码,在指定的1到8位置闪烁数据
276 // 通常情况下我们都使用方式0译码,方式1译码与之大同小异
277 // 形参:Position_flash 显示位置(1-8)
278 void HD7279_Showflash(uchar Position_flash)
279 { uchar FlashDate=0xff;
280 1 FlashDate=FlashDate&(~(0x01<<(Position_flash-1)));
281 1 HD7279_SendByte(HD7279_FLASH);//送命令
282 1 HD7279_SendByte(FlashDate);//送数据
283 1 CS_7279=1;
284 1 }
285 //-------------------------------------------------------------------------------------------------
286 //函数功能:HD7279初始化,建议在工业现场干扰严重情况下,刷新显示时先执行此命令
287 void HD7279_Initial(void)
288 {
289 1 HD7279_SendByte( HD7279_RESET );//复位
290 1 }
291 //=================================================================================================
292 // 串口UART操作相关程序
293 //=================================================================================================
294 //函数功能:串口发射1个字节
295 void uart_byte_out(uchar uart_data_out)
296 { SBUF = uart_data_out;
297 1 while(TI==0);
298 1 TI=0;
299 1 }
300 //-------------------------------------------------------------------------------------------------
301 //函数功能:串口发射字符数组。通常将要发送的字符数组定义在CODE代码区。
302 void uart_string_out(char * char_array)
303 { uchar i;
C51 COMPILER V7.06 MCS51__钅靠猒_____ 12/10/2008 19:58:27 PAGE 6
304 1 for(i=0; i<strlen(char_array) ;i++)
305 1 {
306 2 uart_byte_out(char_array[i]);
307 2 }
308 1 }
309 //-------------------------------------------------------------------------------------------------
310 //函数功能:串口输出数据十进制到PC机屏幕上
311 //形参:范围 0-65535 ;例如:data_to_out=12345(或0x3039),则计算机屏幕就显示12345
312 void uart_data_decimalist_out(uint data_to_out)
313 { bit entrance;
314 1 uchar ge,shi,bai,qian,wan;
315 1 wan = (data_to_out/10000) ;//拆分万位,并转化为ASKII码
316 1 qian = (data_to_out%10000)/1000;//拆分千位,并转化为ASKII码
317 1 bai = (data_to_out%1000)/100 ;//拆分百位,并转化为ASKII码
318 1 shi = (data_to_out%100)/10 ;//拆分十位,并转化为ASKII码
319 1 ge = (data_to_out%10) ;//拆分个位,并转化为ASKII码
320 1 entrance=1;//开放个、十、百、千、万的判断传输入口
321 1 if(wan && entrance)
322 1 {uart_byte_out(change_hex_to_askii(wan));
323 2 uart_byte_out(change_hex_to_askii(qian));
324 2 uart_byte_out(change_hex_to_askii(bai));
325 2 uart_byte_out(change_hex_to_askii(shi));
326 2 uart_byte_out(change_hex_to_askii(ge));
327 2 entrance=0;//如果万位不为0,则不再判断其它位
328 2 }
329 1 else if(qian && entrance)
330 1 {uart_byte_out(change_hex_to_askii(qian));
331 2 uart_byte_out(change_hex_to_askii(bai));
332 2 uart_byte_out(change_hex_to_askii(shi));
333 2 uart_byte_out(change_hex_to_askii(ge));
334 2 entrance=0;//如果千位不为0,则不再判断其它位
335 2 }
336 1 else if(bai && entrance)
337 1 {uart_byte_out(change_hex_to_askii(bai));
338 2 uart_byte_out(change_hex_to_askii(shi));
339 2 uart_byte_out(change_hex_to_askii(ge));
340 2 entrance=0;//如果百位不为0,则不再判断其它位
341 2 }
342 1 else if(shi && entrance)
343 1 {uart_byte_out(change_hex_to_askii(shi));
344 2 uart_byte_out(change_hex_to_askii(ge));
345 2 entrance=0;//如果十位不为0,则不再判断其它位
346 2 }
347 1 else
348 1 {uart_byte_out(change_hex_to_askii(ge));
349 2 }
350 1 }
351 //-------------------------------------------------------------------------------------------------
352 // 函数功能:串口显示的回车换行
353 // 形参:newline_number 表示一共换几行
354 void uart_newline(uchar newline_number)
355 { uchar i;
356 1 for(i=0;i<newline_number;i++)
357 1 {
358 2 uart_byte_out(0x0d);
359 2 uart_byte_out(0x0a);
360 2 }
361 1 }
362 //-------------------------------------------------------------------------------------------------
363 // 函数功能:串口显示的空格
364 // 形参:space_number 表示空几个格
365 void uart_space(uchar space_number)
C51 COMPILER V7.06 MCS51__钅靠猒_____ 12/10/2008 19:58:27 PAGE 7
366 { uchar i;
367 1 for(i=0;i<space_number;i++)
368 1 {
369 2 uart_byte_out(0x20);
370 2 }
371 1 }
372 //=================================================================================================
373 // 数制转换相关程序
374 //=================================================================================================
375 uchar change_bcd_to_hex(uchar shu)//转换BCD码成十进制数
376 { uchar shu_h;
377 1 uchar shu_l;
378 1 shu_l=shu&0x0f;
379 1 shu_h=shu&0xf0;
380 1 shu_h=shu_h>>4;
381 1 return (shu_h*10+shu_l);
382 1 }
383 //-------------------------------------------------------------------------------------------------
384 uchar change_hex_to_bcd(uchar shu)//转换十进制数成BCD码
385 { uchar shu_h;
386 1 uchar shu_l;
387 1 shu_l=shu%10;
388 1 shu_h=shu/10;
389 1 return ((shu_h<<4)|shu_l);
390 1 }
391 //-------------------------------------------------------------------------------------------------
392 uchar change_askii_to_hex(uchar askii)//转换ASKII码成HEX,实参范围:30-39、41-46
393 { if(askii<=0x39) return(askii-0x30);
394 1 else return(askii-0x37);
395 1 }
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -