forked from Traumflug/Teacup_Firmware
-
Notifications
You must be signed in to change notification settings - Fork 0
/
display_hd44780.c
133 lines (103 loc) · 3.05 KB
/
display_hd44780.c
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
/** \file
\brief Code specific to the HD44780 display.
*/
#include "display.h"
#if defined TEACUP_C_INCLUDE && defined DISPLAY_TYPE_HD44780
#include "displaybus.h"
#include "delay.h"
#include "sendf.h"
#include "dda.h"
#include "temp.h"
/**
* Initializes the display's controller configuring the way of
* displaying data.
*/
void display_init(void) {
// Minimum initialisation time after power up.
delay_ms(15);
displaybus_init(0);
// Write left to right, no display shifting.
displaybus_write(0x06, parallel_4bit_instruction);
// Display ON, cursor not blinking.
displaybus_write(0x0C, parallel_4bit_instruction);
}
/**
Show a nice greeting. Pure eye candy.
*/
void display_greeting(void) {
display_clear();
// We have only 16 characters at our disposal ...
display_writestr_P(PSTR("Welcome @ Teacup"));
// Forward this to the display immediately.
while (buf_canread(display)) {
display_tick();
}
// Allow the user to worship our work for a moment :-)
delay_ms(5000);
}
/**
Regular update of the display. Typically called once a second from clock.c.
*/
void display_clock(void) {
uint16_t temperature;
display_clear();
update_current_position();
sendf_P(display_writechar, PSTR("X:%lq Y:%lq"),
current_position.axis[X], current_position.axis[Y]);
#ifdef HEATER_EXTRUDER
display_set_cursor(1, 0);
temperature = temp_get(TEMP_SENSOR_extruder);
sendf_P(display_writechar, PSTR("%u.%su"),
temperature >> 2, (uint8_t)(temperature & 3) * 25);
#endif
#ifdef HEATER_BED
display_set_cursor(1, DISPLAY_SYMBOLS_PER_LINE / 2);
temperature = temp_get(TEMP_SENSOR_bed);
sendf_P(display_writechar, PSTR("%u.%su"),
temperature >> 2, (uint8_t)(temperature & 3) * 25);
#endif
}
/**
Forwards a character or a control command from the display queue to display
bus. As this is a character based display it's easy.
*/
void display_tick() {
uint8_t data, command;
if (displaybus_busy()) {
return;
}
if (buf_canread(display)) {
buf_pop(display, data);
switch (data) {
case low_code_clear:
displaybus_write(0x01, parallel_4bit_instruction);
break;
case low_code_set_cursor:
/**
Set the cursor to the given position.
This is a three-byte control command, so we fetch additional bytes
from the queue and cross fingers they're actually there.
*/
command = 0x80; // "Set DDRAM Address" base command.
/**
Add address of line.
As we have two lines only, this can be "calculated" without
a multiplication.
*/
buf_pop(display, data);
if (data) {
command += 0x40;
}
// Add column address.
buf_pop(display, data);
command += data;
displaybus_write(command, parallel_4bit_instruction);
break;
default:
// Should be a printable character.
displaybus_write(data, parallel_4bit_data);
break;
}
}
}
#endif /* TEACUP_C_INCLUDE && DISPLAY_TYPE_HD44780 */