1 | #define DATA_PORT PORTA
|
2 | #define LCD_RS IOPORT_CREATE_PIN(PORTB,2)
|
3 | #define LCD_E IOPORT_CREATE_PIN(PORTB,0)
|
4 | #define LCD_RW IOPORT_CREATE_PIN(PORTB,1)
|
5 | #define P_DB0 IOPORT_CREATE_PIN(PORTA,0)
|
6 | #define P_DB1 IOPORT_CREATE_PIN(PORTA,1)
|
7 | #define P_DB2 IOPORT_CREATE_PIN(PORTA,2)
|
8 | #define P_DB3 IOPORT_CREATE_PIN(PORTA,3)
|
9 | #define P_DB4 IOPORT_CREATE_PIN(PORTA,4)
|
10 | #define P_DB5 IOPORT_CREATE_PIN(PORTA,5)
|
11 | #define P_DB6 IOPORT_CREATE_PIN(PORTA,6)
|
12 | #define P_DB7 IOPORT_CREATE_PIN(PORTA,7)
|
13 |
|
14 | void lcd_set_write_instruction();
|
15 | void lcd_set_write_data();
|
16 | void lcd_write_byte (char c);
|
17 | void lcd_clear_and_home();
|
18 | void lcd_home();
|
19 | void lcd_goto(uint8_t line, uint8_t pos);
|
20 | void lcd_line_one();
|
21 | void lcd_line_two();
|
22 | void lcd_write_data(char c);
|
23 | void lcd_write_string(char *x, uint8_t len );
|
24 | void lcd_write_string_0(char *x);
|
25 | void lcd_write_string_p(const char *s);
|
26 | void lcd_init();
|
27 | void lcd_set_on_off(uint8_t state);
|
28 | void lcd_write_inst(uint8_t cmd);
|
29 |
|
30 |
|
31 |
|
32 |
|
33 |
|
34 | //this function is directly called from main
|
35 | //it init the display and trys to print some test chars. The result is only a blinking cursor that moves
|
36 | void lcd_init()
|
37 | {
|
38 |
|
39 | ioport_configure_pin(LCD_E, IOPORT_INIT_LOW | IOPORT_DIR_OUTPUT);
|
40 | ioport_configure_pin(LCD_RS, IOPORT_INIT_LOW | IOPORT_DIR_OUTPUT);
|
41 | ioport_configure_pin(LCD_RW, IOPORT_INIT_LOW | IOPORT_DIR_OUTPUT);
|
42 |
|
43 | ioport_configure_pin(P_DB0, IOPORT_INIT_LOW | IOPORT_DIR_OUTPUT);
|
44 | ioport_configure_pin(P_DB1, IOPORT_INIT_LOW | IOPORT_DIR_OUTPUT);
|
45 | ioport_configure_pin(P_DB2, IOPORT_INIT_LOW | IOPORT_DIR_OUTPUT);
|
46 | ioport_configure_pin(P_DB3, IOPORT_INIT_LOW | IOPORT_DIR_OUTPUT);
|
47 | ioport_configure_pin(P_DB4, IOPORT_INIT_LOW | IOPORT_DIR_OUTPUT);
|
48 | ioport_configure_pin(P_DB5, IOPORT_INIT_LOW | IOPORT_DIR_OUTPUT);
|
49 | ioport_configure_pin(P_DB6, IOPORT_INIT_LOW | IOPORT_DIR_OUTPUT);
|
50 | ioport_configure_pin(P_DB7, IOPORT_INIT_LOW | IOPORT_DIR_OUTPUT);
|
51 |
|
52 | _delay_ms(250);
|
53 |
|
54 | // LCD display initialisation by instruction magic sequence
|
55 | lcd_set_write_instruction();
|
56 | lcd_write_inst(0x38); // function set
|
57 | _delay_ms(100);
|
58 | lcd_write_inst(0x08); // display on/off control
|
59 | _delay_ms(100);
|
60 | lcd_write_inst(0x01); // display clear
|
61 | _delay_ms(100);
|
62 | lcd_write_inst(0x06); // entry mode set
|
63 | _delay_ms(100);
|
64 | lcd_write_inst(0x02);
|
65 | _delay_ms(100);
|
66 | lcd_write_inst(0x0F);
|
67 | _delay_ms(100);
|
68 | lcd_write_inst(0x0F);
|
69 | _delay_ms(100);
|
70 | lcd_write_inst(0x39);
|
71 | _delay_ms(100);
|
72 |
|
73 | lcd_write_inst(0x80);
|
74 |
|
75 | lcd_write_data('A');
|
76 | lcd_write_data('B');
|
77 | lcd_write_data('C');
|
78 | lcd_write_data('D');
|
79 | lcd_write_data('E');
|
80 |
|
81 |
|
82 | _delay_ms(100);
|
83 |
|
84 |
|
85 | }
|
86 |
|
87 |
|
88 |
|
89 | void lcd_set_on_off(uint8_t state)
|
90 | {
|
91 | lcd_set_write_instruction();
|
92 | if(state==1)
|
93 | {
|
94 | lcd_write_byte(0x0F);
|
95 | }
|
96 | if(state==0)
|
97 | {
|
98 | lcd_write_byte(0x08);
|
99 | }
|
100 |
|
101 | }
|
102 |
|
103 | // This function clears the RS line to write a command
|
104 | void lcd_set_write_instruction()
|
105 | {
|
106 | ioport_set_pin_low(LCD_RS); // set RS line low
|
107 | _delay_ms(1);
|
108 | }
|
109 |
|
110 |
|
111 | // This function sets the RS line to write data
|
112 | void lcd_set_write_data()
|
113 | {
|
114 | ioport_set_pin_high(LCD_RS); // set RS line high
|
115 | _delay_ms(1);
|
116 |
|
117 | }
|
118 |
|
119 |
|
120 |
|
121 |
|
122 | // This function writes a byte to the LCD
|
123 | void lcd_write_byte (char c)
|
124 | {
|
125 | ioport_set_pin_low(LCD_RW);
|
126 | int output[CHAR_BIT];
|
127 | int i;
|
128 | for (i = 0; i < CHAR_BIT; ++i)
|
129 | {
|
130 | output[i] = (c >> i) & 1;
|
131 | }
|
132 | //manual approach
|
133 | if(output[0]==1)
|
134 | {
|
135 | ioport_set_pin_high(P_DB0);
|
136 | }
|
137 | else
|
138 | {
|
139 | ioport_set_pin_low(P_DB0);
|
140 | }
|
141 | if(output[1]==1)
|
142 | {
|
143 | ioport_set_pin_high(P_DB1);
|
144 | }
|
145 | else
|
146 | {
|
147 | ioport_set_pin_low(P_DB1);
|
148 | }
|
149 | if(output[2]==1)
|
150 | {
|
151 | ioport_set_pin_high(P_DB2);
|
152 | }
|
153 | else
|
154 | {
|
155 | ioport_set_pin_low(P_DB2);
|
156 | }
|
157 | if(output[3]==1)
|
158 | {
|
159 | ioport_set_pin_high(P_DB3);
|
160 | }
|
161 | else
|
162 | {
|
163 | ioport_set_pin_low(P_DB3);
|
164 | }
|
165 | if(output[4]==1)
|
166 | {
|
167 | ioport_set_pin_high(P_DB4);
|
168 | }
|
169 | else
|
170 | {
|
171 | ioport_set_pin_low(P_DB4);
|
172 | }
|
173 | if(output[5]==1)
|
174 | {
|
175 | ioport_set_pin_high(P_DB5);
|
176 | }
|
177 | else
|
178 | {
|
179 | ioport_set_pin_low(P_DB5);
|
180 | }
|
181 | if(output[6]==1)
|
182 | {
|
183 | ioport_set_pin_high(P_DB6);
|
184 | }
|
185 | else
|
186 | {
|
187 | ioport_set_pin_low(P_DB6);
|
188 | }
|
189 | if(output[7]==1)
|
190 | {
|
191 | ioport_set_pin_high(P_DB7);
|
192 | }
|
193 | else
|
194 | {
|
195 | ioport_set_pin_low(P_DB7);
|
196 | }
|
197 | _delay_us(100);
|
198 |
|
199 | //DATA_PORT.OUT = c; // Place data on Data Port
|
200 | ioport_set_pin_high(LCD_E); // set E line high
|
201 | _delay_us(100);
|
202 | ioport_set_pin_low(LCD_E); // set E line low to latch data into LCD
|
203 | _delay_ms(1);
|
204 | }
|
205 |
|
206 |
|
207 | // This function clears LCD and sets address to beginning of first line
|
208 | void lcd_clear_and_home()
|
209 | {
|
210 | lcd_set_write_instruction();
|
211 | lcd_write_byte(0x01);
|
212 | _delay_ms(2);
|
213 | lcd_write_byte(0x02);
|
214 | _delay_ms(1);
|
215 | }
|
216 |
|
217 | // This function sets address to beginning of first line
|
218 | void lcd_home()
|
219 | {
|
220 | lcd_set_write_instruction();
|
221 | lcd_write_byte(0x02);
|
222 | _delay_ms(1);
|
223 | }
|
224 |
|
225 |
|
226 | // This function moves cursor to a given line and position
|
227 | // line is either 0 (first line) or 1 (second line)
|
228 | // pos is the character position from 0 to 15.
|
229 | void lcd_goto(uint8_t line, uint8_t pos)
|
230 | {
|
231 | uint8_t position = 0;
|
232 |
|
233 | lcd_set_write_instruction();
|
234 | switch(line)
|
235 | {
|
236 | case 0: position = 0;
|
237 | break;
|
238 | case 1: position = 0x40;
|
239 | break;
|
240 | }
|
241 | lcd_write_byte(0x80 | (position + pos));
|
242 | }
|
243 |
|
244 |
|
245 | // This function moves the cursor to 1st character of 1st line
|
246 | void lcd_line_one() { lcd_goto(0, 0); }
|
247 |
|
248 |
|
249 | // This function moves the cursor to 1st character if 2nd line
|
250 | void lcd_line_two() { lcd_goto(1, 0); }
|
251 |
|
252 |
|
253 | // This function writes a character to the LCD
|
254 | void lcd_write_data(char c)
|
255 | {
|
256 | //ioport_set_pin_high(P_LED2);
|
257 | lcd_set_write_data();
|
258 | lcd_write_byte(c);
|
259 | // lcd_write_inst(0x14);
|
260 | //ioport_set_pin_low(P_LED2);
|
261 | }
|
262 |
|
263 | void lcd_write_inst(uint8_t cmd)
|
264 | {
|
265 | lcd_set_write_instruction();
|
266 | lcd_write_byte(cmd);
|
267 | }
|
268 |
|
269 | // This function writes a string (in SRAM) of given length to the LCD
|
270 | void lcd_write_string(char *x, uint8_t len )
|
271 | {
|
272 | while (--len > 0)
|
273 | lcd_write_data(*x++);
|
274 | }
|
275 |
|
276 |
|
277 | // This function writes a null-terminated string (in SRAM) to the LCD
|
278 | void lcd_write_string_0(char *x)
|
279 | {
|
280 | while (*x)
|
281 | lcd_write_data(*x++);
|
282 | }
|
283 |
|
284 |
|
285 | // Same as above, but the string is located in program memory,
|
286 | // so "lpm" instructions are needed to fetch it, and a \0
|
287 | // must be defined at the end of the string to terminate it.
|
288 | void lcd_write_string_p(const char *s)
|
289 | {
|
290 | char c;
|
291 |
|
292 | for (c = pgm_read_byte(s); c; ++s, c = pgm_read_byte(s))
|
293 | lcd_write_data(c);
|
294 | }
|