11/*
22 * Copyright (C) 2018 Koen Zandberg
33 * 2021 Francisco Molina
4+ * 2023 Gunar Schorcht
45 *
56 * This file is subject to the terms and conditions of the GNU Lesser
67 * General Public License v2.1. See the file LICENSE in the top level
1314 *
1415 * @brief Driver for the LCD display
1516 *
16- * The LCD is a generic display driver for small RGB displays. The driver
17- * implemented here operates over SPI to communicate with the device.
17+ * The LCD is a generic display driver for small RGB displays. It communicates
18+ * with the device either via an
19+ *
20+ * - SPI serial interface (if module `lcd_spi` enabled) or an
21+ * - MCU 8080 8-/16-bit parallel interface (if module `lcd_parallel` or
22+ * module `lcd_parallel_16` is enabled).
23+ *
24+ * Usually the device driver is used either for a single display with SPI serial
25+ * interface or for a display with parallel MCU 8080 8-/16-bit parallel
26+ * interface. However, the device driver can also be used simultaneously for
27+ * multiple displays with different interfaces if several of the `lcd_spi`,
28+ * `lcd_parallel` and `lcd_parallel_16bit` modules are enabled at the same time.
29+ * In this case, please refer to the notes in @ref lcd_params_t.
30+ *
31+ * @warning MCU 8080 16-bit parallel interface (module `lcd_parallel_16bit`) is
32+ * not supported yet.
1833 *
1934 * The device requires colors to be send in big endian RGB-565 format. The
2035 * @ref CONFIG_LCD_LE_MODE compile time option can switch this, but only use this
2843 *
2944 * @author Koen Zandberg <[email protected] > 3045 * @author Francisco Molina <[email protected] > 46+ * @author Gunar Schorcht <[email protected] > 3147 *
3248 */
3349
3450#ifndef LCD_H
3551#define LCD_H
3652
3753#include "board.h"
54+ #include "mutex.h"
3855#include "periph/spi.h"
3956#include "periph/gpio.h"
4057
@@ -70,18 +87,58 @@ extern "C" {
7087
7188/**
7289 * @brief Device initialization parameters
90+ *
91+ * @note The device driver can be used simultaneously for displays with
92+ * SPI serial interface and parallel MCU 8080 8-/16-bit interfaces
93+ * if the modules `lcd_spi` and `lcd_parallel` or `lcd_parallel_16bit`
94+ * are enabled at the same time. In this case the interface parameters
95+ * for the SPI serial interface and the MCU 8080 parallel 8-/16-bit
96+ * interfaces are defined. @ref lcd_params_t::spi must then be set to
97+ * @ref SPI_UNDEF for displays that use the MCU-8080-parallel-8-/16-bit
98+ * interface, i.e. @ref lcd_params_t::spi is then used to detect the
99+ * interface mode.
73100 */
74101typedef struct {
102+ #if MODULE_LCD_SPI || DOXYGEN
103+ /* Interface parameters used for serial interface */
75104 spi_t spi ; /**< SPI device that the display is connected to */
76105 spi_clk_t spi_clk ; /**< SPI clock speed to use */
77106 spi_mode_t spi_mode ; /**< SPI mode */
107+ #endif
108+ #if MODULE_LCD_PARALLEL || DOXYGEN
109+ /* Interface parameters used for MCU 8080 8-bit parallel interface */
110+ gpio_t wrx_pin ; /**< pin connected to the WRITE ENABLE line */
111+ gpio_t rdx_pin ; /**< pin connected to the READ ENABLE line */
112+ gpio_t d0_pin ; /**< pin connected to the D0 line */
113+ gpio_t d1_pin ; /**< pin connected to the D1 line */
114+ gpio_t d2_pin ; /**< pin connected to the D2 line */
115+ gpio_t d3_pin ; /**< pin connected to the D3 line */
116+ gpio_t d4_pin ; /**< pin connected to the D4 line */
117+ gpio_t d5_pin ; /**< pin connected to the D5 line */
118+ gpio_t d6_pin ; /**< pin connected to the D6 line */
119+ gpio_t d7_pin ; /**< pin connected to the D7 line */
120+ #if MODULE_LCD_PARALLEL_16BIT || DOXYGEN
121+ /* Interface parameters used for MCU 8080 16-bit parallel interface */
122+ gpio_t d8_pin ; /**< pin connected to the D8 line */
123+ gpio_t d9_pin ; /**< pin connected to the D9 line */
124+ gpio_t d10_pin ; /**< pin connected to the D10 line */
125+ gpio_t d11_pin ; /**< pin connected to the D11 line */
126+ gpio_t d12_pin ; /**< pin connected to the D12 line */
127+ gpio_t d13_pin ; /**< pin connected to the D13 line */
128+ gpio_t d14_pin ; /**< pin connected to the D14 line */
129+ gpio_t d15_pin ; /**< pin connected to the D15 line */
130+ #endif /* MODULE_LCD_PARALLEL_16BIT */
131+ #endif /* MODULE_LCD_PARALLEL */
132+ /* Common interface parameters */
78133 gpio_t cs_pin ; /**< pin connected to the CHIP SELECT line */
79134 gpio_t dcx_pin ; /**< pin connected to the DC line */
80- gpio_t rst_pin ; /**< pin connected to the reset line */
81- bool rgb ; /**< True when display is connected in RGB mode
82- * False when display is connected in BGR mode */
135+ gpio_t rst_pin ; /**< pin connected to the RESET line */
136+ bool rgb ; /**< True when display is connected in RGB mode\n
137+ False when display is connected in BGR mode */
83138 bool inverted ; /**< Display works in inverted color mode */
84- uint16_t lines ; /**< Number of lines, from 16 to 320 in 8 line steps */
139+ uint16_t lines ; /**< Number of lines, from 16 to the number of
140+ lines supported by the driver IC in 8 line
141+ steps */
85142 uint16_t rgb_channels ; /**< Display rgb channels */
86143 uint8_t rotation ; /**< Display rotation mode */
87144 uint8_t offset_x ; /**< LCD offset to apply on x axis. */
@@ -104,11 +161,15 @@ typedef struct lcd_driver lcd_driver_t;
104161 * @brief Device descriptor for a lcd
105162 */
106163typedef struct {
107- #ifdef MODULE_DISP_DEV
164+ #if MODULE_DISP_DEV || DOXYGEN
108165 disp_dev_t * dev ; /**< Pointer to the generic display device */
109166#endif
110167 const lcd_driver_t * driver ; /**< LCD driver */
111168 const lcd_params_t * params ; /**< Device initialization parameters */
169+ #if MODULE_LCD_PARALLEL || DOXYGEN
170+ mutex_t lock ; /**< Mutex used to lock the device in
171+ MCU 8080 parallel interface mode */
172+ #endif
112173} lcd_t ;
113174
114175/**
@@ -142,7 +203,7 @@ struct lcd_driver {
142203 * @param[in] y2 y coordinate of the opposite corner
143204 *
144205 */
145- void (* set_area )(const lcd_t * dev , uint16_t x1 , uint16_t x2 , uint16_t y1 ,
206+ void (* set_area )(lcd_t * dev , uint16_t x1 , uint16_t x2 , uint16_t y1 ,
146207 uint16_t y2 );
147208};
148209
@@ -162,14 +223,14 @@ struct lcd_driver {
162223 *
163224 * @param[out] dev device descriptor
164225 */
165- void lcd_ll_acquire (const lcd_t * dev );
226+ void lcd_ll_acquire (lcd_t * dev );
166227
167228/**
168229 * @brief Low-level function to release the device
169230 *
170231 * @param[out] dev device descriptor
171232 */
172- void lcd_ll_release (const lcd_t * dev );
233+ void lcd_ll_release (lcd_t * dev );
173234
174235/**
175236 * @brief Low-level function to write a command
@@ -182,7 +243,7 @@ void lcd_ll_release(const lcd_t *dev);
182243 * @param[in] data command data to the device
183244 * @param[in] len length of the command data
184245 */
185- void lcd_ll_write_cmd (const lcd_t * dev , uint8_t cmd , const uint8_t * data ,
246+ void lcd_ll_write_cmd (lcd_t * dev , uint8_t cmd , const uint8_t * data ,
186247 size_t len );
187248
188249/**
@@ -201,7 +262,7 @@ void lcd_ll_write_cmd(const lcd_t *dev, uint8_t cmd, const uint8_t *data,
201262 * @param[out] data data from the device
202263 * @param[in] len length of the returned data
203264 */
204- void lcd_ll_read_cmd (const lcd_t * dev , uint8_t cmd , uint8_t * data , size_t len );
265+ void lcd_ll_read_cmd (lcd_t * dev , uint8_t cmd , uint8_t * data , size_t len );
205266/** @} */
206267
207268/**
@@ -234,7 +295,7 @@ int lcd_init(lcd_t *dev, const lcd_params_t *params);
234295 * @param[in] y2 y coordinate of the opposite corner
235296 * @param[in] color single color to fill the area with
236297 */
237- void lcd_fill (const lcd_t * dev , uint16_t x1 , uint16_t x2 ,
298+ void lcd_fill (lcd_t * dev , uint16_t x1 , uint16_t x2 ,
238299 uint16_t y1 , uint16_t y2 , uint16_t color );
239300
240301/**
@@ -253,7 +314,7 @@ void lcd_fill(const lcd_t *dev, uint16_t x1, uint16_t x2,
253314 * @param[in] y2 y coordinate of the opposite corner
254315 * @param[in] color array of colors to fill the area with
255316 */
256- void lcd_pixmap (const lcd_t * dev , uint16_t x1 , uint16_t x2 , uint16_t y1 ,
317+ void lcd_pixmap (lcd_t * dev , uint16_t x1 , uint16_t x2 , uint16_t y1 ,
257318 uint16_t y2 , const uint16_t * color );
258319
259320/**
@@ -264,34 +325,38 @@ void lcd_pixmap(const lcd_t *dev, uint16_t x1, uint16_t x2, uint16_t y1,
264325 * @param[in] data command data to the device
265326 * @param[in] len length of the command data
266327 */
267- void lcd_write_cmd (const lcd_t * dev , uint8_t cmd , const uint8_t * data ,
328+ void lcd_write_cmd (lcd_t * dev , uint8_t cmd , const uint8_t * data ,
268329 size_t len );
269330
270331/**
271332 * @brief Raw read command
272333 *
334+ * @note Very often the SPI MISO signal of the serial interface or the RDX
335+ * signal of the MCU 8080 parallel interface are not connected to the
336+ * display. In this case the read command does not provide valid data.
337+ *
273338 * @pre len > 0
274339 *
275340 * @param[in] dev device descriptor
276341 * @param[in] cmd command
277342 * @param[out] data data from the device
278343 * @param[in] len length of the returned data
279344 */
280- void lcd_read_cmd (const lcd_t * dev , uint8_t cmd , uint8_t * data , size_t len );
345+ void lcd_read_cmd (lcd_t * dev , uint8_t cmd , uint8_t * data , size_t len );
281346
282347/**
283348 * @brief Invert the display colors
284349 *
285350 * @param[in] dev device descriptor
286351 */
287- void lcd_invert_on (const lcd_t * dev );
352+ void lcd_invert_on (lcd_t * dev );
288353
289354/**
290355 * @brief Disable color inversion
291356 *
292357 * @param[in] dev device descriptor
293358 */
294- void lcd_invert_off (const lcd_t * dev );
359+ void lcd_invert_off (lcd_t * dev );
295360/** @} */
296361
297362#ifdef __cplusplus
0 commit comments