diff --git a/bsp/stm32/libraries/HAL_Drivers/SConscript b/bsp/stm32/libraries/HAL_Drivers/SConscript index 8c54e6327690055535299e2e1f4d04aaeb965e2b..356b5431d0c523ec19996123782e14eed3bda3fc 100644 --- a/bsp/stm32/libraries/HAL_Drivers/SConscript +++ b/bsp/stm32/libraries/HAL_Drivers/SConscript @@ -49,6 +49,9 @@ if GetDepend('BSP_USING_SDRAM'): if GetDepend('BSP_USING_LCD'): src += ['drv_lcd.c'] +if GetDepend('BSP_USING_LCD_MIPI'): + src += ['drv_lcd_mipi.c'] + if GetDepend('BSP_USING_ONCHIP_RTC'): src += ['drv_rtc.c'] diff --git a/bsp/stm32/libraries/HAL_Drivers/drv_lcd_mipi.c b/bsp/stm32/libraries/HAL_Drivers/drv_lcd_mipi.c new file mode 100644 index 0000000000000000000000000000000000000000..9a76ee7507eaaacbdd1932fb5e5b70511e7d248b --- /dev/null +++ b/bsp/stm32/libraries/HAL_Drivers/drv_lcd_mipi.c @@ -0,0 +1,257 @@ +/* + * Copyright (c) 2006-2018, RT-Thread Development Team + * + * SPDX-License-Identifier: Apache-2.0 + * + * Change Logs: + * Date Author Notes + * 2019-05-23 WillianChan first version + */ + +#include + +#ifdef BSP_USING_LCD_MIPI +#include +#include + +DSI_HandleTypeDef hdsi; +DSI_VidCfgTypeDef hdsi_video; +LTDC_HandleTypeDef hltdc; + +struct stm32_lcd +{ + struct rt_device parent; + struct rt_device_graphic_info info; +}; +static struct stm32_lcd lcd; + +extern void stm32_mipi_lcd_init(void); +extern void stm32_mipi_lcd_config(rt_uint32_t pixel_format); +extern void stm32_mipi_display_on(void); +extern void stm32_mipi_display_off(void); + +rt_err_t ltdc_init(void) +{ + uint32_t lcd_clock = 27429; + uint32_t lanebyte_clock = 62500; + + uint32_t HSA = LCD_HSYNC, HFP = LCD_HFP, HBP = LCD_HBP, HACT = LCD_WIDTH; + uint32_t VSA = LCD_VSYNC, VFP = LCD_VFP, VBP = LCD_VBP, VACT = LCD_HEIGHT; + + stm32_mipi_lcd_init(); + + /* ��ʼ��STM32��ʾ��ʱ�� */ + __HAL_RCC_LTDC_CLK_ENABLE(); + __HAL_RCC_LTDC_FORCE_RESET(); + __HAL_RCC_LTDC_RELEASE_RESET(); + + __HAL_RCC_DSI_CLK_ENABLE(); + __HAL_RCC_DSI_FORCE_RESET(); + __HAL_RCC_DSI_RELEASE_RESET(); + + RCC_PeriphCLKInitTypeDef PeriphClkInitStruct; + + PeriphClkInitStruct.PeriphClockSelection = RCC_PERIPHCLK_LTDC; + PeriphClkInitStruct.PLLSAI.PLLSAIN = 384; + PeriphClkInitStruct.PLLSAI.PLLSAIR = 7; + PeriphClkInitStruct.PLLSAIDivR = RCC_PLLSAIDIVR_2; + HAL_RCCEx_PeriphCLKConfig(&PeriphClkInitStruct); + + /* ����NVIC */ + HAL_NVIC_SetPriority(LTDC_IRQn, 3, 0); + HAL_NVIC_SetPriority(DSI_IRQn, 3, 0); + + HAL_NVIC_EnableIRQ(LTDC_IRQn); + HAL_NVIC_EnableIRQ(DSI_IRQn); + + /* ����DSI */ + DSI_PLLInitTypeDef dsi_pll; + + hdsi.Instance = DSI; + hdsi.Init.NumberOfLanes = DSI_TWO_DATA_LANES; + hdsi.Init.TXEscapeCkdiv = lanebyte_clock / 15620; + + dsi_pll.PLLNDIV = 125; + dsi_pll.PLLIDF = DSI_PLL_IN_DIV2; + dsi_pll.PLLODF = DSI_PLL_OUT_DIV1; + + HAL_DSI_DeInit(&hdsi); + HAL_DSI_Init(&hdsi, &dsi_pll); + + hdsi_video.VirtualChannelID = 0; + hdsi_video.ColorCoding = DSI_RGB888; + hdsi_video.VSPolarity = DSI_VSYNC_ACTIVE_HIGH; + hdsi_video.HSPolarity = DSI_HSYNC_ACTIVE_HIGH; + hdsi_video.DEPolarity = DSI_DATA_ENABLE_ACTIVE_HIGH; + hdsi_video.Mode = DSI_VID_MODE_BURST; + hdsi_video.NullPacketSize = 0xFFF; + hdsi_video.NumberOfChunks = 0; + hdsi_video.PacketSize = HACT; + hdsi_video.HorizontalSyncActive = (HSA * lanebyte_clock) / lcd_clock; + hdsi_video.HorizontalBackPorch = (HBP * lanebyte_clock) / lcd_clock; + hdsi_video.HorizontalLine = ((HACT + HSA + HBP + HFP) * lanebyte_clock) / lcd_clock; + hdsi_video.VerticalSyncActive = VSA; + hdsi_video.VerticalBackPorch = VBP; + hdsi_video.VerticalFrontPorch = VFP; + hdsi_video.VerticalActive = VACT; + hdsi_video.LPCommandEnable = DSI_LP_COMMAND_ENABLE; + hdsi_video.LPLargestPacketSize = 16; + hdsi_video.LPVACTLargestPacketSize = 0; + hdsi_video.LPHorizontalFrontPorchEnable = DSI_LP_HFP_ENABLE; + hdsi_video.LPHorizontalBackPorchEnable = DSI_LP_HBP_ENABLE; + hdsi_video.LPVerticalActiveEnable = DSI_LP_VACT_ENABLE; + hdsi_video.LPVerticalFrontPorchEnable = DSI_LP_VFP_ENABLE; + hdsi_video.LPVerticalBackPorchEnable = DSI_LP_VBP_ENABLE; + hdsi_video.LPVerticalSyncActiveEnable = DSI_LP_VSYNC_ENABLE; + HAL_DSI_ConfigVideoMode(&hdsi, &hdsi_video); + + DSI_PHY_TimerTypeDef dsi_phy; + + dsi_phy.ClockLaneHS2LPTime = 35; + dsi_phy.ClockLaneLP2HSTime = 35; + dsi_phy.DataLaneHS2LPTime = 35; + dsi_phy.DataLaneLP2HSTime = 35; + dsi_phy.DataLaneMaxReadTime = 0; + dsi_phy.StopWaitTime = 10; + HAL_DSI_ConfigPhyTimer(&hdsi, &dsi_phy); + + hltdc.Instance = LTDC; + + hltdc.Init.PCPolarity = LTDC_PCPOLARITY_IPC; + hltdc.Init.HorizontalSync = (HSA - 1); + hltdc.Init.AccumulatedHBP = (HSA + HBP - 1); + hltdc.Init.AccumulatedActiveW = (LCD_WIDTH + HSA + HBP - 1); + hltdc.Init.TotalWidth = (LCD_WIDTH + HSA + HBP + HFP - 1); + + hltdc.LayerCfg->ImageWidth = LCD_WIDTH; + hltdc.LayerCfg->ImageHeight = LCD_HEIGHT; + hltdc.Init.Backcolor.Blue = 0x00; + hltdc.Init.Backcolor.Green = 0x00; + hltdc.Init.Backcolor.Red = 0x00; + HAL_LTDCEx_StructInitFromVideoConfig(&hltdc, &(hdsi_video)); + HAL_LTDC_Init(&(hltdc)); + + HAL_DSI_Start(&(hdsi)); + + stm32_mipi_lcd_config(RTGRAPHIC_PIXEL_FORMAT_ARGB888); + + return RT_EOK; +} + +void ltdc_layer_init(uint16_t index, uint32_t framebuffer) +{ + LTDC_LayerCfgTypeDef layer_cfg; + + layer_cfg.WindowX0 = 0; + layer_cfg.WindowX1 = LCD_WIDTH; + layer_cfg.WindowY0 = 0; + layer_cfg.WindowY1 = LCD_HEIGHT; + layer_cfg.PixelFormat = LTDC_PIXEL_FORMAT_ARGB8888; + layer_cfg.BlendingFactor1 = LTDC_BLENDING_FACTOR1_PAxCA; + layer_cfg.BlendingFactor2 = LTDC_BLENDING_FACTOR2_PAxCA; + layer_cfg.Alpha = 255; + layer_cfg.Alpha0 = 0; + layer_cfg.ImageWidth = LCD_WIDTH; + layer_cfg.ImageHeight = LCD_HEIGHT; + layer_cfg.Backcolor.Blue = 0; + layer_cfg.Backcolor.Green = 0; + layer_cfg.Backcolor.Red = 0; + layer_cfg.FBStartAdress = framebuffer; + + HAL_LTDC_ConfigLayer(&hltdc, &layer_cfg, index); +} + +void LTDC_IRQHandler(void) +{ + rt_interrupt_enter(); + HAL_LTDC_IRQHandler(&hltdc); + rt_interrupt_leave(); +} + +static rt_err_t stm32_lcd_init(rt_device_t device) +{ + lcd.info.width = LCD_WIDTH; + lcd.info.height = LCD_HEIGHT; + lcd.info.pixel_format = RTGRAPHIC_PIXEL_FORMAT_ARGB888; + lcd.info.bits_per_pixel = 32; + lcd.info.framebuffer = (void *)rt_malloc_align(LCD_WIDTH * LCD_HEIGHT * (lcd.info.bits_per_pixel / 8), 32); + memset(lcd.info.framebuffer, 0, LCD_WIDTH * LCD_HEIGHT * (lcd.info.bits_per_pixel / 8)); + ltdc_init(); + ltdc_layer_init(0, (uint32_t)lcd.info.framebuffer); + + return RT_EOK; +} + +static rt_err_t stm32_lcd_control(rt_device_t device, int cmd, void *args) +{ + switch(cmd) + { + case RTGRAPHIC_CTRL_RECT_UPDATE: + break; + + case RTGRAPHIC_CTRL_POWERON: + stm32_mipi_display_on(); + break; + + case RTGRAPHIC_CTRL_POWEROFF: + stm32_mipi_display_off(); + break; + + case RTGRAPHIC_CTRL_GET_INFO: + rt_memcpy(args, &lcd.info, sizeof(lcd.info)); + break; + + case RTGRAPHIC_CTRL_SET_MODE: + break; + + case RTGRAPHIC_CTRL_GET_EXT: + break; + } + + return RT_EOK; +} + +int rt_hw_lcd_init(void) +{ + rt_err_t ret; + + rt_memset(&lcd, 0x00, sizeof(lcd)); + + lcd.parent.type = RT_Device_Class_Graphic; + lcd.parent.init = stm32_lcd_init; + lcd.parent.open = RT_NULL; + lcd.parent.close = RT_NULL; + lcd.parent.read = RT_NULL; + lcd.parent.write = RT_NULL; + lcd.parent.control = stm32_lcd_control; + + lcd.parent.user_data = (void *)&lcd.info; + + ret = rt_device_register(&lcd.parent, "lcd", RT_DEVICE_FLAG_RDWR); + + return ret; +} +INIT_DEVICE_EXPORT(rt_hw_lcd_init); + + +RT_WEAK void stm32_mipi_lcd_init(void) +{ + rt_kprintf("please Implementation function %s\n", __func__); +} + +RT_WEAK void stm32_mipi_lcd_config(rt_uint32_t pixel_format) +{ + rt_kprintf("please Implementation function %s\n", __func__); +} + +RT_WEAK void stm32_mipi_display_on(void) +{ + rt_kprintf("please Implementation function %s\n", __func__); +} + +RT_WEAK void stm32_mipi_display_off(void) +{ + rt_kprintf("please Implementation function %s\n", __func__); +} + +#endif /* BSP_USING_LCD_MIPI */ diff --git a/bsp/stm32/stm32f469-st-disco/board/Kconfig b/bsp/stm32/stm32f469-st-disco/board/Kconfig index 3627b742eb98cc08763cc402b55a634e8956ca17..8eb5ac1bf3c1aca9a34887f539c3c671e4f10db2 100644 --- a/bsp/stm32/stm32f469-st-disco/board/Kconfig +++ b/bsp/stm32/stm32f469-st-disco/board/Kconfig @@ -10,11 +10,16 @@ menu "Onboard Peripheral Drivers" bool "Enable SDRAM" select BSP_USING_FMC default n + + config BSP_USING_LCD_MIPI + bool + default n config BSP_USING_LCD_OTM8009A bool "Enable LCD OTM8009A" select BSP_USING_SDRAM select BSP_USING_LTDC + select BSP_USING_LCD_MIPI default n config BSP_USING_QSPI_FLASH diff --git a/bsp/stm32/stm32f469-st-disco/board/SConscript b/bsp/stm32/stm32f469-st-disco/board/SConscript index 0d843da0b971db39721a8a0001746321180a53c1..3c07ee8dbce7cee76826163b6fc406d5e66d8ab5 100644 --- a/bsp/stm32/stm32f469-st-disco/board/SConscript +++ b/bsp/stm32/stm32f469-st-disco/board/SConscript @@ -13,22 +13,22 @@ CubeMX_Config/Src/stm32f4xx_hal_msp.c ''') if GetDepend(['BSP_USING_QSPI_FLASH']): - src += Glob('ports/drv_qspi_flash.c') + src += ['ports/drv_qspi_flash.c'] if GetDepend(['PKG_USING_FAL']): - src += Glob('ports/qspi_mnt.c') + src += ['ports/qspi_mnt.c'] if GetDepend(['BSP_USING_LCD_OTM8009A']): - src += Glob('ports/drv_lcd_otm8009a.c') + src += ['ports/drv_otm8009a.c'] if GetDepend(['BSP_USING_TOUCH']): src += Glob('ports/touch/*.c') if GetDepend(['BSP_USING_SDCARD']): - src += Glob('ports/drv_sdcard.c') + src += ['ports/drv_sdcard.c'] if GetDepend(['BSP_USING_QSPI']): - src += Glob('ports/drv_qspi_flash.c') + src += ['ports/drv_qspi_flash.c'] path = [cwd] path += [cwd + '/CubeMX_Config/Inc'] diff --git a/bsp/stm32/stm32f469-st-disco/board/ports/drv_lcd_otm8009a.c b/bsp/stm32/stm32f469-st-disco/board/ports/drv_otm8009a.c similarity index 51% rename from bsp/stm32/stm32f469-st-disco/board/ports/drv_lcd_otm8009a.c rename to bsp/stm32/stm32f469-st-disco/board/ports/drv_otm8009a.c index 661042796f6e8fd019c4d31b896c5889a24139d0..84202f84c82c7fd6f47546c31954f4933afd02cc 100644 --- a/bsp/stm32/stm32f469-st-disco/board/ports/drv_lcd_otm8009a.c +++ b/bsp/stm32/stm32f469-st-disco/board/ports/drv_otm8009a.c @@ -5,37 +5,13 @@ * * Change Logs: * Date Author Notes - * 2018-07-28 liu2guang the first version for STM32F469NI-Discovery. - * 2019-04-19 WillianChan porting STM32F469NI-Discovery lcd driver to - * the new STM32 BSP framework. + * 2019-05-23 WillianChan first version */ #include - #ifdef BSP_USING_LCD_OTM8009A -#include - -struct stm32_lcd -{ - struct rt_device device; - struct rt_device_graphic_info info; - - LTDC_HandleTypeDef ltdc; - DSI_HandleTypeDef dsi; - DSI_VidCfgTypeDef dsi_video; - DMA2D_HandleTypeDef dma2d; -}; -static struct stm32_lcd lcd; - -#define LCD_WIDTH ((uint16_t)800) -#define LCD_HEIGHT ((uint16_t)480) - -#define LCD_HSYNC ((uint16_t)1) -#define LCD_HBP ((uint16_t)15) -#define LCD_HFP ((uint16_t)16) -#define LCD_VSYNC ((uint16_t)2) -#define LCD_VBP ((uint16_t)34) -#define LCD_VFP ((uint16_t)34) +extern DSI_HandleTypeDef hdsi; +extern DSI_VidCfgTypeDef hdsi_video; const rt_uint8_t RDL01[] = {0x80, 0x09, 0x01, 0xFF}; const rt_uint8_t RDL02[] = {0x80, 0x09, 0xFF}; @@ -117,7 +93,7 @@ const rt_uint8_t RDS49[] = {0xF5, 0x06}; const rt_uint8_t RDS50[] = {0x00, 0xB1}; const rt_uint8_t RDS51[] = {0xC6, 0x06}; -static void otm8009a_reset(void) +void otm8009a_reset(void) { rt_pin_mode (GET_PIN(H, 7), PIN_MODE_OUTPUT); rt_pin_write(GET_PIN(H, 7), PIN_LOW); @@ -126,19 +102,19 @@ static void otm8009a_reset(void) rt_thread_delay(rt_tick_from_millisecond(20)); } -void otm8009a_write_cmd(uint8_t *p, uint32_t num) +static void otm8009a_write_cmd(uint8_t *p, uint32_t num) { if (num <= 1) { - HAL_DSI_ShortWrite(&(lcd.dsi), lcd.dsi_video.VirtualChannelID, DSI_DCS_SHORT_PKT_WRITE_P1, p[0], p[1]); + HAL_DSI_ShortWrite(&hdsi, hdsi_video.VirtualChannelID, DSI_DCS_SHORT_PKT_WRITE_P1, p[0], p[1]); } else { - HAL_DSI_LongWrite(&(lcd.dsi), lcd.dsi_video.VirtualChannelID, DSI_DCS_LONG_PKT_WRITE, num, p[num], p); + HAL_DSI_LongWrite(&hdsi, hdsi_video.VirtualChannelID, DSI_DCS_LONG_PKT_WRITE, num, p[num], p); } } -void otm8009a_delay(uint32_t d) +static void otm8009a_delay(uint32_t d) { rt_thread_delay(rt_tick_from_millisecond(d)); } @@ -264,262 +240,24 @@ static void otm8009a_config(rt_uint32_t pixel_format) otm8009a_write_cmd((rt_uint8_t *)RDS45, 0); } -rt_err_t otm8009a_init(void) -{ - uint32_t lcd_clock = 27429; - uint32_t lanebyte_clock = 62500; - - uint32_t HSA = LCD_HSYNC, HFP = LCD_HFP, HBP = LCD_HBP, HACT = LCD_WIDTH; - uint32_t VSA = LCD_VSYNC, VFP = LCD_VFP, VBP = LCD_VBP, VACT = LCD_HEIGHT; - - /* ��λOTM8009A��ʾ�� */ - otm8009a_reset(); - - /* ��ʼ��STM32��ʾ��ʱ�� */ - __HAL_RCC_LTDC_CLK_ENABLE(); - __HAL_RCC_LTDC_FORCE_RESET(); - __HAL_RCC_LTDC_RELEASE_RESET(); - - __HAL_RCC_DMA2D_CLK_ENABLE(); - __HAL_RCC_DMA2D_FORCE_RESET(); - __HAL_RCC_DMA2D_RELEASE_RESET(); - - __HAL_RCC_DSI_CLK_ENABLE(); - __HAL_RCC_DSI_FORCE_RESET(); - __HAL_RCC_DSI_RELEASE_RESET(); - - RCC_PeriphCLKInitTypeDef PeriphClkInitStruct; - - PeriphClkInitStruct.PeriphClockSelection = RCC_PERIPHCLK_LTDC; - PeriphClkInitStruct.PLLSAI.PLLSAIN = 384; - PeriphClkInitStruct.PLLSAI.PLLSAIR = 7; - PeriphClkInitStruct.PLLSAIDivR = RCC_PLLSAIDIVR_2; - HAL_RCCEx_PeriphCLKConfig(&PeriphClkInitStruct); - - /* ����NVIC */ - HAL_NVIC_SetPriority(LTDC_IRQn, 3, 0); - HAL_NVIC_SetPriority(DMA2D_IRQn, 3, 0); - HAL_NVIC_SetPriority(DSI_IRQn, 3, 0); - - HAL_NVIC_EnableIRQ(LTDC_IRQn); - HAL_NVIC_EnableIRQ(DMA2D_IRQn); - HAL_NVIC_EnableIRQ(DSI_IRQn); - - /* ����DSI */ - DSI_PLLInitTypeDef dsi_pll; - - lcd.dsi.Instance = DSI; - lcd.dsi.Init.NumberOfLanes = DSI_TWO_DATA_LANES; - lcd.dsi.Init.TXEscapeCkdiv = lanebyte_clock / 15620; - - dsi_pll.PLLNDIV = 125; - dsi_pll.PLLIDF = DSI_PLL_IN_DIV2; - dsi_pll.PLLODF = DSI_PLL_OUT_DIV1; - - HAL_DSI_DeInit(&(lcd.dsi)); - HAL_DSI_Init(&(lcd.dsi), &(dsi_pll)); - - /* ����DSI Video */ - lcd.dsi_video.VirtualChannelID = 0; - lcd.dsi_video.ColorCoding = DSI_RGB888; - lcd.dsi_video.VSPolarity = DSI_VSYNC_ACTIVE_HIGH; - lcd.dsi_video.HSPolarity = DSI_HSYNC_ACTIVE_HIGH; - lcd.dsi_video.DEPolarity = DSI_DATA_ENABLE_ACTIVE_HIGH; - lcd.dsi_video.Mode = DSI_VID_MODE_BURST; - lcd.dsi_video.NullPacketSize = 0xFFF; - lcd.dsi_video.NumberOfChunks = 0; - lcd.dsi_video.PacketSize = HACT; - lcd.dsi_video.HorizontalSyncActive = (HSA * lanebyte_clock) / lcd_clock; - lcd.dsi_video.HorizontalBackPorch = (HBP * lanebyte_clock) / lcd_clock; - lcd.dsi_video.HorizontalLine = ((HACT + HSA + HBP + HFP) * lanebyte_clock) / lcd_clock; - lcd.dsi_video.VerticalSyncActive = VSA; - lcd.dsi_video.VerticalBackPorch = VBP; - lcd.dsi_video.VerticalFrontPorch = VFP; - lcd.dsi_video.VerticalActive = VACT; - lcd.dsi_video.LPCommandEnable = DSI_LP_COMMAND_ENABLE; - lcd.dsi_video.LPLargestPacketSize = 16; - lcd.dsi_video.LPVACTLargestPacketSize = 0; - lcd.dsi_video.LPHorizontalFrontPorchEnable = DSI_LP_HFP_ENABLE; - lcd.dsi_video.LPHorizontalBackPorchEnable = DSI_LP_HBP_ENABLE; - lcd.dsi_video.LPVerticalActiveEnable = DSI_LP_VACT_ENABLE; - lcd.dsi_video.LPVerticalFrontPorchEnable = DSI_LP_VFP_ENABLE; - lcd.dsi_video.LPVerticalBackPorchEnable = DSI_LP_VBP_ENABLE; - lcd.dsi_video.LPVerticalSyncActiveEnable = DSI_LP_VSYNC_ENABLE; - HAL_DSI_ConfigVideoMode(&(lcd.dsi), &(lcd.dsi_video)); - - /* ����DSI PHY */ - DSI_PHY_TimerTypeDef dsi_phy; - - dsi_phy.ClockLaneHS2LPTime = 35; - dsi_phy.ClockLaneLP2HSTime = 35; - dsi_phy.DataLaneHS2LPTime = 35; - dsi_phy.DataLaneLP2HSTime = 35; - dsi_phy.DataLaneMaxReadTime = 0; - dsi_phy.StopWaitTime = 10; - HAL_DSI_ConfigPhyTimer(&(lcd.dsi), &dsi_phy); - - /* ����LTDC */ - lcd.ltdc.Instance = LTDC; - - lcd.ltdc.Init.PCPolarity = LTDC_PCPOLARITY_IPC; - lcd.ltdc.Init.HorizontalSync = (HSA - 1); - lcd.ltdc.Init.AccumulatedHBP = (HSA + HBP - 1); - lcd.ltdc.Init.AccumulatedActiveW = (LCD_WIDTH + HSA + HBP - 1); - lcd.ltdc.Init.TotalWidth = (LCD_WIDTH + HSA + HBP + HFP - 1); - - lcd.ltdc.LayerCfg->ImageWidth = LCD_WIDTH; - lcd.ltdc.LayerCfg->ImageHeight = LCD_HEIGHT; - lcd.ltdc.Init.Backcolor.Blue = 0x00; - lcd.ltdc.Init.Backcolor.Green = 0x00; - lcd.ltdc.Init.Backcolor.Red = 0x00; - HAL_LTDCEx_StructInitFromVideoConfig(&(lcd.ltdc), &(lcd.dsi_video)); - HAL_LTDC_Init(&(lcd.ltdc)); - - HAL_DSI_Start(&(lcd.dsi)); - - otm8009a_config(RTGRAPHIC_PIXEL_FORMAT_ARGB888); - - return RT_EOK; -} -void otm8009a_layer_init(uint16_t index, uint32_t framebuffer) +void stm32_mipi_lcd_init(void) { - LTDC_LayerCfgTypeDef layer_cfg; - - layer_cfg.WindowX0 = 0; - layer_cfg.WindowX1 = LCD_WIDTH; - layer_cfg.WindowY0 = 0; - layer_cfg.WindowY1 = LCD_HEIGHT; - layer_cfg.PixelFormat = LTDC_PIXEL_FORMAT_ARGB8888; - layer_cfg.BlendingFactor1 = LTDC_BLENDING_FACTOR1_PAxCA; - layer_cfg.BlendingFactor2 = LTDC_BLENDING_FACTOR2_PAxCA; - layer_cfg.Alpha = 255; - layer_cfg.Alpha0 = 0; - layer_cfg.ImageWidth = LCD_WIDTH; - layer_cfg.ImageHeight = LCD_HEIGHT; - layer_cfg.Backcolor.Blue = 0; - layer_cfg.Backcolor.Green = 0; - layer_cfg.Backcolor.Red = 0; - layer_cfg.FBStartAdress = framebuffer; - - HAL_LTDC_ConfigLayer(&(lcd.ltdc), &layer_cfg, index); + otm8009a_reset(); } -static void otm8009a_display_on(void) +void stm32_mipi_lcd_config(rt_uint32_t pixel_format) { - HAL_DSI_ShortWrite(&(lcd.dsi), lcd.dsi_video.VirtualChannelID, DSI_DCS_SHORT_PKT_WRITE_P1, 0x29, 0x00); + otm8009a_config(pixel_format); } -static void otm8009a_display_off(void) +void stm32_mipi_display_on(void) { - HAL_DSI_ShortWrite(&(lcd.dsi), lcd.dsi_video.VirtualChannelID, DSI_DCS_SHORT_PKT_WRITE_P1, 0x28, 0x00); + HAL_DSI_ShortWrite(&hdsi, hdsi_video.VirtualChannelID, DSI_DCS_SHORT_PKT_WRITE_P1, 0x29, 0x00); } -void LTDC_IRQHandler(void) +void stm32_mipi_display_off(void) { - rt_interrupt_enter(); - HAL_LTDC_IRQHandler(&(lcd.ltdc)); - rt_interrupt_leave(); + HAL_DSI_ShortWrite(&hdsi, hdsi_video.VirtualChannelID, DSI_DCS_SHORT_PKT_WRITE_P1, 0x28, 0x00); } - -/* ���Դ���: ---------------------------------------- */ -static void lcd_fill_buffer(void *addr, uint32_t x_size, uint32_t y_size, uint32_t offset, uint32_t color) -{ - lcd.dma2d.Instance = DMA2D; - - lcd.dma2d.Init.Mode = DMA2D_R2M; - lcd.dma2d.Init.ColorMode = DMA2D_ARGB8888; - lcd.dma2d.Init.OutputOffset = offset; - - if (HAL_DMA2D_Init(&lcd.dma2d) == HAL_OK) - { - if (HAL_DMA2D_ConfigLayer(&lcd.dma2d, 0) == HAL_OK) - { - if (HAL_DMA2D_Start(&lcd.dma2d, color, (uint32_t)addr, x_size, y_size) == HAL_OK) - { - HAL_DMA2D_PollForTransfer(&lcd.dma2d, 10); - } - } - } -} - -void lcd_clear(uint32_t color) -{ - /* Clear the LCD */ - lcd_fill_buffer((uint32_t *)(lcd.ltdc.LayerCfg[0].FBStartAdress), LCD_WIDTH, LCD_HEIGHT, 0, color); -} - -void lcd_fill_rect(uint16_t x_pos, uint16_t y_pos, uint16_t width, uint16_t height) -{ - uint32_t Xaddress = (lcd.ltdc.LayerCfg[0].FBStartAdress) + 4 * (LCD_WIDTH * x_pos + y_pos); - lcd_fill_buffer((uint32_t *)Xaddress, width, height, (LCD_WIDTH - width), 0xFF00FF00); -} - -/* ���Դ��� ----------------------------------------- */ - -static rt_err_t stm32_lcd_init(rt_device_t device) -{ - lcd.info.width = LCD_WIDTH; - lcd.info.height = LCD_HEIGHT; - lcd.info.pixel_format = RTGRAPHIC_PIXEL_FORMAT_ARGB888; - lcd.info.bits_per_pixel = 32; - lcd.info.framebuffer = (void *)rt_malloc_align(LCD_WIDTH * LCD_HEIGHT * (lcd.info.bits_per_pixel / 8), 32); - otm8009a_init(); - otm8009a_layer_init(0, (uint32_t)lcd.info.framebuffer); - lcd_clear(0xFF000000); - - return RT_EOK; -} - -static rt_err_t stm32_lcd_control(rt_device_t device, int cmd, void *args) -{ - switch(cmd) - { - case RTGRAPHIC_CTRL_RECT_UPDATE: - break; - - case RTGRAPHIC_CTRL_POWERON: - otm8009a_display_on(); - break; - - case RTGRAPHIC_CTRL_POWEROFF: - otm8009a_display_off(); - break; - - case RTGRAPHIC_CTRL_GET_INFO: - rt_memcpy(args, &lcd.info, sizeof(lcd.info)); - break; - - case RTGRAPHIC_CTRL_SET_MODE: - break; - - case RTGRAPHIC_CTRL_GET_EXT: - break; - } - - return RT_EOK; -} - -int rt_hw_lcd_init(void) -{ - rt_err_t ret; - - rt_memset(&lcd, 0x00, sizeof(lcd)); - - lcd.device.type = RT_Device_Class_Graphic; - lcd.device.init = stm32_lcd_init; - lcd.device.open = RT_NULL; - lcd.device.close = RT_NULL; - lcd.device.read = RT_NULL; - lcd.device.write = RT_NULL; - lcd.device.control = stm32_lcd_control; - - lcd.device.user_data = (void *)&lcd.info; - - ret = rt_device_register(&lcd.device, "lcd", RT_DEVICE_FLAG_RDWR); - - return ret; -} -INIT_DEVICE_EXPORT(rt_hw_lcd_init); - -#endif /* BSP_USING_LCD_OTM8009A */ +#endif diff --git a/bsp/stm32/stm32f469-st-disco/board/ports/lcd_port.h b/bsp/stm32/stm32f469-st-disco/board/ports/lcd_port.h index 76df5528dcd51f6a8dcc49badbc93c6d01e8f2e7..d5ee2b13b49b1a3e4201b83836d48127ece79b75 100644 --- a/bsp/stm32/stm32f469-st-disco/board/ports/lcd_port.h +++ b/bsp/stm32/stm32f469-st-disco/board/ports/lcd_port.h @@ -15,9 +15,14 @@ #include #include -rt_err_t otm8009a_init(void); -void otm8009a_layer_init(uint16_t index, uint32_t framebuffer); -void lcd_clear(uint32_t color); -void lcd_fill_rect(uint16_t x_pos, uint16_t y_pos, uint16_t width, uint16_t height); +#define LCD_WIDTH (800U) +#define LCD_HEIGHT (480U) + +#define LCD_HSYNC (1U) +#define LCD_HBP (15U) +#define LCD_HFP (16U) +#define LCD_VSYNC (2U) +#define LCD_VBP (34U) +#define LCD_VFP (34U) #endif