Skip to content

Fix rgb565 / bgr565 interchange issue in Zephyr display #79996

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 6 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion boards/shields/rk043fn02h_ct/rk043fn02h_ct.overlay
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@
vsync-active = <0>;
clock-frequency = <9210240>;
};
pixel-format = <PANEL_PIXEL_FORMAT_BGR_565>;
pixel-format = <PANEL_PIXEL_FORMAT_RGB_565>;
data-bus-width = "16-bit";
backlight-gpios = <&nxp_parallel_lcd_connector 0 GPIO_ACTIVE_HIGH>;
};
2 changes: 1 addition & 1 deletion boards/shields/rk043fn66hs_ctg/rk043fn66hs_ctg.overlay
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,7 @@
vsync-active = <0>;
clock-frequency = <9210240>;
};
pixel-format = <PANEL_PIXEL_FORMAT_BGR_565>;
pixel-format = <PANEL_PIXEL_FORMAT_RGB_565>;
data-bus-width = "16-bit";
backlight-gpios = <&nxp_parallel_lcd_connector 0 GPIO_ACTIVE_HIGH>;
};
2 changes: 1 addition & 1 deletion boards/shields/rk055hdmipi4m/rk055hdmipi4m.overlay
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,7 @@
*/
clock-frequency = <62346240>;
};
pixel-format = <PANEL_PIXEL_FORMAT_BGR_565>;
pixel-format = <PANEL_PIXEL_FORMAT_RGB_565>;
data-bus-width = "24-bit";
backlight-gpios = <&nxp_mipi_connector 0 GPIO_ACTIVE_HIGH>;
};
Expand Down
2 changes: 1 addition & 1 deletion boards/shields/rk055hdmipi4ma0/rk055hdmipi4ma0.overlay
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,7 @@
*/
clock-frequency = <62346240>;
};
pixel-format = <PANEL_PIXEL_FORMAT_BGR_565>;
pixel-format = <PANEL_PIXEL_FORMAT_RGB_565>;
data-bus-width = "24-bit";
backlight-gpios = <&nxp_mipi_connector 0 GPIO_ACTIVE_HIGH>;
};
Expand Down
5 changes: 5 additions & 0 deletions doc/releases/migration-guide-4.2.rst
Original file line number Diff line number Diff line change
Expand Up @@ -631,6 +631,11 @@ Audio
* The binding file for :dtcompatible:`cirrus,cs43l22` has been renamed to have a name
matching the compatible string.

Display
=======

* The RGB565 and BGR565 interchange issue has been fixed in the display sample.

Other subsystems
****************

Expand Down
15 changes: 3 additions & 12 deletions drivers/display/display_mcux_dcnano_lcdif.c
Original file line number Diff line number Diff line change
Expand Up @@ -133,16 +133,11 @@ static void mcux_dcnano_lcdif_get_capabilities(const struct device *dev,

capabilities->y_resolution = config->dpi_config.panelHeight;
capabilities->x_resolution = config->dpi_config.panelWidth;
capabilities->supported_pixel_formats =
(PIXEL_FORMAT_BGR_565 | PIXEL_FORMAT_ARGB_8888);
capabilities->supported_pixel_formats = (PIXEL_FORMAT_RGB_565 | PIXEL_FORMAT_ARGB_8888);
capabilities->current_orientation = DISPLAY_ORIENTATION_NORMAL;
switch (data->fb_config.format) {
case kLCDIF_PixelFormatRGB565:
/* Zephyr stores RGB565 as big endian, and LCDIF
* expects little endian. Use BGR565 format to resolve
* this.
*/
capabilities->current_pixel_format = PIXEL_FORMAT_BGR_565;
capabilities->current_pixel_format = PIXEL_FORMAT_RGB_565;
break;
#if DT_ENUM_IDX_OR(DT_NODELABEL(lcdif), version, 0) == 1
case kLCDIF_PixelFormatARGB8888:
Expand Down Expand Up @@ -185,11 +180,7 @@ static int mcux_dcnano_lcdif_set_pixel_format(const struct device *dev,
struct mcux_dcnano_lcdif_data *data = dev->data;

switch (pixel_format) {
case PIXEL_FORMAT_BGR_565:
/* Zephyr stores RGB565 as big endian, and LCDIF
* expects little endian. Use BGR565 format to resolve
* this.
*/
case PIXEL_FORMAT_RGB_565:
data->fb_config.format = kLCDIF_PixelFormatRGB565;
data->pixel_bytes = 2;
break;
Expand Down
6 changes: 3 additions & 3 deletions drivers/display/display_mcux_elcdif.c
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@ LOG_MODULE_REGISTER(display_mcux_elcdif, CONFIG_DISPLAY_LOG_LEVEL);
K_HEAP_DEFINE(display_heap, CONFIG_MCUX_ELCDIF_FB_NUM * CONFIG_MCUX_ELCDIF_FB_SIZE + 512);

static const uint32_t supported_fmts =
PIXEL_FORMAT_BGR_565 | PIXEL_FORMAT_ARGB_8888 | PIXEL_FORMAT_RGB_888;
PIXEL_FORMAT_RGB_565 | PIXEL_FORMAT_ARGB_8888 | PIXEL_FORMAT_RGB_888;

struct mcux_elcdif_config {
LCDIF_Type *base;
Expand Down Expand Up @@ -152,7 +152,7 @@ static int mcux_elcdif_write(const struct device *dev, const uint16_t x, const u
pxp_block.block_size = desc->buf_size;

/* DMA slot sets pixel format and rotation angle */
if (dev_data->pixel_format == PIXEL_FORMAT_BGR_565) {
if (dev_data->pixel_format == PIXEL_FORMAT_RGB_565) {
pxp_dma.dma_slot = DMA_MCUX_PXP_FMT(DMA_MCUX_PXP_FMT_RGB565);
} else if (dev_data->pixel_format == PIXEL_FORMAT_RGB_888) {
pxp_dma.dma_slot = DMA_MCUX_PXP_FMT(DMA_MCUX_PXP_FMT_RGB888);
Expand Down Expand Up @@ -274,7 +274,7 @@ static int mcux_elcdif_set_pixel_format(const struct device *dev,
}

dev_data->rgb_mode = config->rgb_mode;
if (pixel_format == PIXEL_FORMAT_BGR_565) {
if (pixel_format == PIXEL_FORMAT_RGB_565) {
dev_data->rgb_mode.pixelFormat = kELCDIF_PixelFormatRGB565;
} else if (pixel_format == PIXEL_FORMAT_RGB_888) {
dev_data->rgb_mode.pixelFormat = kELCDIF_PixelFormatRGB888;
Expand Down
4 changes: 2 additions & 2 deletions samples/drivers/display/src/main.c
Original file line number Diff line number Diff line change
Expand Up @@ -119,7 +119,7 @@ static uint16_t get_rgb565_color(enum corner corner, uint8_t grey)
return color;
}

static void fill_buffer_rgb565(enum corner corner, uint8_t grey, uint8_t *buf,
static void fill_buffer_bgr565(enum corner corner, uint8_t grey, uint8_t *buf,
size_t buf_size)
{
uint16_t color = get_rgb565_color(corner, grey);
Expand All @@ -130,7 +130,7 @@ static void fill_buffer_rgb565(enum corner corner, uint8_t grey, uint8_t *buf,
}
}

static void fill_buffer_bgr565(enum corner corner, uint8_t grey, uint8_t *buf,
static void fill_buffer_rgb565(enum corner corner, uint8_t grey, uint8_t *buf,
size_t buf_size)
{
uint16_t color = get_rgb565_color(corner, grey);
Expand Down
4 changes: 2 additions & 2 deletions samples/drivers/video/capture/src/main.c
Original file line number Diff line number Diff line change
Expand Up @@ -42,8 +42,8 @@ static inline int display_setup(const struct device *const display_dev, const ui
/* Set display pixel format to match the one in use by the camera */
switch (pixfmt) {
case VIDEO_PIX_FMT_RGB565:
if (capabilities.current_pixel_format != PIXEL_FORMAT_BGR_565) {
ret = display_set_pixel_format(display_dev, PIXEL_FORMAT_BGR_565);
if (capabilities.current_pixel_format != PIXEL_FORMAT_RGB_565) {
ret = display_set_pixel_format(display_dev, PIXEL_FORMAT_RGB_565);
}
break;
case VIDEO_PIX_FMT_XRGB32:
Expand Down
Loading