新聞中心

        EEPW首頁 > 嵌入式系統 > 設計應用 > 自制51單片機常用頭文件(LCD1602)

        自制51單片機常用頭文件(LCD1602)

        作者: 時間:2016-11-10 來源:網絡 收藏
        /*--------------------------------------------------------------------------

        LCD1602.H

        本文引用地址:http://www.104case.com/article/201611/317353.htm

        The user function is C51.
        Copyright (c) 1988-2004 Keil Elektronik GmbH sum zhaojun
        All rights reserved.
        --------------------------------------------------------------------------*/

        #ifndef __LCD1602_H__
        #define __LCD1602_H__

        /*連接線圖:
        ---------------------------------------------------
        | LCM-----51  | LCM-----51  | LCM------51 |
        | ----------------------------------------------- |
        | DB0-----P0.0 | DB4-----P0.4 | RS-------P2.0 |
        | DB1-----P0.1 | DB5-----P0.5 | RW-------P2.1 |
        | DB2-----P0.2 | DB6-----P0.6 | E--------P2.2 |
        | DB3-----P0.3 | DB7-----P0.7 | VLCD接1K電阻到GND |
        ---------------------------------------------------*/

        /****************** LCD1602指令 ***********************************/
        //輸入方式設置
        #define LCD_AC_AUTO_INCREMENT 0x06 // 數據讀、寫操作后,AC自動增一
        #define LCD_AC_AUTO_DECREASE 0x04 // 數據讀、寫操作后,AC自動減一
        #define LCD_MOVE_ENABLE 0x05 // 數據讀、寫操作,畫面平移
        #define LCD_MOVE_DISENABLE 0x04 // 數據讀、寫操作,畫面不動
        #define LCD_GO_HOME 0x02 // AC=0,光標、畫面回HOME位
        //設置顯示、光標及閃爍開、關
        #define LCD_DISPLAY_ON 0x0C // 顯示開
        #define LCD_DISPLAY_OFF 0x08 // 顯示關
        #define LCD_CURSOR_ON 0x0A // 光標顯示
        #define LCD_CURSOR_OFF 0x08 // 光標不顯示
        #define LCD_CURSOR_BLINK_ON 0x09 // 光標閃爍
        #define LCD_CURSOR_BLINK_OFF 0x08 // 光標不閃爍
        //光標、畫面移動,不影響DDRAM
        #define LCD_LEFT_MOVE 0x18 // LCD顯示左移一位
        #define LCD_RIGHT_MOVE 0x1C // LCD顯示右移一位
        #define LCD_CURSOR_LEFT_MOVE 0x10 // 光標左移一位
        #define LCD_CURSOR_RIGHT_MOVE 0x14 // 光標右移一位
        //工作方式設置
        #define LCD_DISPLAY_DOUBLE_LINE 0x38 // 兩行顯示
        #define LCD_DISPLAY_SINGLE_LINE 0x30 // 單行顯示
        #define LCD_CLEAR_SCREEN 0x01 // 清屏

        /***********************LCD1602地址相關******************************/
        #define LINE1_HEAD 0x80 // 第一行DDRAM起始地址
        #define LINE2_HEAD 0xc0 // 第二行DDRAM起始地址
        #define LINE1 0 // 第一行
        #define LINE2 1 // 第二行
        #define LINE_LENGTH 8 // 每行的最大字符長度

        /***********************LCD1602接線引腳定義**************************/

        #define LCM_RS P2_0 // 數據/命令選擇信號
        #define LCM_RW P2_1 // 讀/寫選擇信號
        #define LCM_E P2_2 // 使能信號
        #define LCM_Data P0 // 顯示數據端口
        #define Busy 0x80 // 用于檢測LCM狀態字中的Busy標識

        #define uchar unsigned char
        #define uint unsigned int

        //================================ LCM1602控制部分 =========================================================

        /*****************************************************
        函 數 名:void Delay_LCD(void)
        功 能:5ms延時
        說 明:LCD顯示延時
        入口參數:無
        返 回 值:無
        *****************************************************/
        void Delay_LCD(void)
        {
        uint TempCyc = 5552; // 放入延時數據

        while(TempCyc--)
        {
        ;
        }
        }

        /*****************************************************
        函 數 名:uchar ReadStatusLCM()
        功 能:讀忙狀態
        說 明:判斷LCM的工作狀態;也可以不用此函數,用一段延時程序代替
        入口參數:無
        返 回 值:LCM_Data
        *****************************************************/
        //讀狀態
        uchar ReadStatusLCM(void)
        {
        LCM_Data = 0xFF; // LCM數據口先置1

        LCM_RS = 0;
        LCM_RW = 1;
        LCM_E = 0;
        LCM_E = 0;
        LCM_E = 1;

        while (LCM_Data & Busy) // 檢測忙信號.如果忙,則不執行
        {
        ;
        }

        return (LCM_Data); // 不忙返回讀取數據
        }

        /*****************************************************
        函 數 名:void WriteDataLCM()
        功 能:向LCM1602中寫入數據
        說 明:將形參WDLCM中的數據寫入LCM中
        入口參數:WDLCM
        返 回 值:無
        *****************************************************/
        //寫數據
        void WriteDataLCM(uchar WDLCM)
        {
        ReadStatusLCM(); // 檢測忙

        LCM_Data = WDLCM; // 寫入數據到LCM

        LCM_RS = 1;
        LCM_RW = 0;
        LCM_E = 0; // 若晶振速度太高可以在這后加小的延時
        LCM_E = 0; // 延時
        LCM_E = 1;
        }

        /*****************************************************
        函 數 名:void WriteCommandLCM()
        功 能:向LCM1602中寫入指令
        說 明:向LCM中寫入指令;如果BuysC=0時,忽略忙檢測,如果BuysC=1時,不忽略忙檢測
        入口參數:WCLCM,BuysC
        返 回 值:無
        *****************************************************/
        //寫指令
        void WriteCommandLCM(uchar WCLCM,BuysC) // BuysC為0時忽略忙檢測
        {
        if (BuysC)
        {
        ReadStatusLCM(); // 根據需要檢測忙
        }

        LCM_Data = WCLCM; // 寫入指令

        LCM_RS = 0;
        LCM_RW = 0;
        LCM_E = 0;
        LCM_E = 0;
        LCM_E = 1;
        }

        /*****************************************************
        函 數 名:void LCMInit()
        功 能:初始化LCM1602
        說 明:LCM在工作前先要對顯示屏初始化,否則模塊無法正常工作
        入口參數:無
        返 回 值:無
        *****************************************************/
        //LCM初始化
        void LCMInit(void)
        {
        LCM_Data = 0;
        WriteCommandLCM(LCD_DISPLAY_DOUBLE_LINE,0); // 三次顯示模式設置,不檢測忙信號
        Delay_LCD();
        WriteCommandLCM(LCD_DISPLAY_DOUBLE_LINE,0); // 0x38指令表示:8位數據顯示模式,倆行多顯示
        Delay_LCD();
        WriteCommandLCM(LCD_DISPLAY_DOUBLE_LINE,0);
        Delay_LCD();

        WriteCommandLCM(LCD_DISPLAY_DOUBLE_LINE,1); // 顯示模式設置,開始要求每次檢測忙信號
        WriteCommandLCM(LCD_DISPLAY_OFF,1); // 關閉顯示
        WriteCommandLCM(LCD_CLEAR_SCREEN,1); // 顯示清屏
        WriteCommandLCM(LCD_AC_AUTO_INCREMENT,1); // 顯示光標移動設置
        WriteCommandLCM(LCD_DISPLAY_ON,1); // 顯示開及光標設置
        }

        /*****************************************************
        函 數 名:void DisplayOneChar()
        功 能:按指定坐標中寫入數據
        說 明:X-橫坐標,Y-縱坐標,DData為ASCII值
        入口參數:X,Y,DData
        返 回 值:無
        *****************************************************/
        //按指定位置顯示一個字符
        void DisplayOneChar(uchar X, uchar Y, uchar DData)
        {
        Y &= 0x01;
        X &= 0x0F; // 限制X不能大于15,Y不能大于1

        if (Y)
        {
        X |= LINE2_HEAD; // 當要顯示第二行時地址碼:0xc0
        }

        X |= LINE1_HEAD; // 第一行的地址碼:0x80
        WriteCommandLCM(X, 0); // 這里不檢測忙信號,發送地址碼
        WriteDataLCM(DData);
        }
        /*在LCD1602中使用此函數,在DIPS082中使用下面的函數
        /*****************************************************
        函 數 名:void DisplayListChar(uchar x,uchar y,uchar *DData)
        功 能:向指定坐標中寫入字符串(在LCD1602中使用此函數)
        說 明:X-橫坐標,Y-縱坐標
        入口參數:X,Y,*DData
        返 回 值:無
        *****************************************************
        //按指定位置顯示字符串
        void DisplayListChar(uchar x,uchar y,uchar *DData)
        {
        if (y == LINE1) // 判斷是否寫入第1行
        {
        if (x < LINE_LENGTH) // 寫入位數
        {
        WriteCommandLCM(LINE1_HEAD+x,0); // 寫入第1行地址

        for (;x

        主站蜘蛛池模板: 察雅县| 长宁县| 南平市| 舒城县| 英吉沙县| 资溪县| 呼图壁县| 洛阳市| 新河县| 宁陵县| 温宿县| 曲阳县| 莆田市| 宝清县| 常宁市| 通城县| 浏阳市| 福安市| 日照市| 乌拉特后旗| 应城市| 鹤岗市| 甘德县| 乐陵市| 和林格尔县| 永定县| 西安市| 甘孜县| 巨野县| 华亭县| 眉山市| 积石山| 灌云县| 揭阳市| 环江| 抚顺县| 雷州市| 文山县| 南溪县| 海南省| 合江县|