Forum: Mikrocontroller und Digitale Elektronik BMP von SDCard


von Harald (Gast)


Lesenswert?

Ich nutze ein STM32F429 Board mit 800x480Pixel TFT.

Mit der Funktion read_pic kann ich ein Bild von der SD Card auf dem TFT 
Darstellen aber relativ langsam.

Es gibt ja noch die Möglichkeit mit DMA2D, nur ich tue mich damit schwer 
das einzubinden, könnte mir einer von ihnen helfen.
Oder wie könnte mann das schneller machen.
mfg

1
//###################################################################################
2
void read_pic(u16 point_x , u16 point_y ,char *name)
3
//###################################################################################
4
{
5
 res = f_open(&fsrc, name, FA_READ);    
6
 if ( res == FR_OK )
7
 { //WriteString(0,0,"bmp found",WHITE,RED);
8
  f_read(&fsrc, (u8 *)&bmp, sizeof(bmp), &br);   
9
10
11
  if( (bmp.pic_head[0]=='B') && (bmp.pic_head[1]=='M') )  
12
   {
13
    res = f_lseek(&fsrc, ((bmp.pic_data_address_h<<16)|bmp.pic_data_address_l));
14
15
      ty=bmp.pic_h_l;
16
      while(ty) {
17
      
18
          ty--;
19
20
           f_read(&fsrc, &bmp_buffer, (bmp.pic_w_l)*3, &br);
21
            
22
       for(tx=0;tx<bmp.pic_w_l;tx++) 
23
             {
24
               point.x = ty;//ty;
25
               point.y = tx;//tx;
26
               point.r = *(tx*3 +2+bmp_buffer);
27
               point.g = *(tx*3 +1+bmp_buffer);
28
               point.b = *(tx*3 +0+bmp_buffer);                                 
29
                       
30
               LCD_SetPixel_16bpp(point.y + point_x  ,point.x + point_y  ,RGB888CONVERT565(point.r,point.g,point.b));  
31
             }
32
   
33
       if(ty==0) continue;
34
         }
35
36
37
       f_close(&fsrc);  
38
   }       
39
 }
40
}
41
42
43
void LCD_SetPixel_16bpp (int Xpos, int Ypos, unsigned short color)
44
{
45
  volatile unsigned short *pLCDbuf = (unsigned short *)CurrentFrameBuffer;  /* LCD buffer start address */
46
47
  pLCDbuf[ Ypos * LCD_X_SIZE + Xpos ] = color;  
48
}

von grundschüler (Gast)


Lesenswert?

Harald schrieb:
> void LCD_SetPixel_16bpp (int Xpos, int Ypos, unsigned short color)

Das füllen des Bildschirms geht mit streamwrite, d.h. du brauchst nicht 
für jedes Px die position eingeben.

von Harald (Gast)


Lesenswert?

grundschüler schrieb:
> Harald schrieb:
> void LCD_SetPixel_16bpp (int Xpos, int Ypos, unsigned short color)
>
> Das füllen des Bildschirms geht mit streamwrite, d.h. du brauchst nicht
> für jedes Px die position eingeben.

gibt es für streamwrite ein Beispiel wie das gemacht wird.
mfg

von Jim M. (turboj)


Lesenswert?

grundschüler schrieb:
>> void LCD_SetPixel_16bpp (int Xpos, int Ypos, unsigned short color)
>
> Das füllen des Bildschirms geht mit streamwrite, d.h. du brauchst nicht
> für jedes Px die position eingeben.

Problem: Er muss trotzdem jeden Pixel einzeln von RGB888 nach RGB565 
wandeln.

Ich würde die Wandlung der Bitmap auf dem PC machen, AFAIK kennt BMP 
auch RGB565 als Datenformat. Dann wäre das ein memcpy() und auch DMA 
möglich.

von grundschüler (Gast)


Lesenswert?

Harald schrieb:
> Beispiel
1
void kk_ILI9341_Fill_y(uint32_t xpxcam, uint32_t ypxcam) {//5
2
u32 tmp,n,i;
3
  u16 *zg = (uint32_t)0xd0000000;
4
  u32 faktor=(xpxcam+319)/320;
5
  u32 xlcd=xpxcam/faktor;
6
  u32 xrest=xpxcam%faktor;
7
  u32 ylcd=ypxcam/faktor;
8
  TM_ILI9341_SetCursorPosition(0, 0, xlcd - 1, ylcd - 1);
9
//  TM_ILI9341_SetCursorPosition(0, 0, ILI9341_Opts.width - 1, ILI9341_Opts.height - 1);
10
  TM_ILI9341_SendCommand(ILI9341_GRAM);
11
for (n = 0; n < ylcd; n++){
12
  for(i=0;i<xlcd;i++){
13
    px=zg + n*xpxcam*faktor + i*faktor;//2byte/px,jedes 2.px
14
    tmp = *(__IO uint16_t*)px;
15
   TM_ILI9341_SendData(tmp>>8);
16
   TM_ILI9341_SendData(tmp&0xff);
17
  }//i
18
tmp=px;
19
}//n
20
}

von grundschüler (Gast)


Lesenswert?

Beispiel für ili9230:
1
//==================================================
2
void lcd_streamwrite_start(void){
3
    lcd_setcursor(0,0);
4
     lcd_write_index(0x0022);
5
      lcd_cs_low;
6
     LCD_Write_Data_Start();
7
}
8
9
void lcd_streamwrite_px(uint8_t* ort,u32 anz){
10
u32 i,j;
11
  for (i=0;i<anz;i++){
12
    lcd_serialDataReg=ort[i];
13
      while(lcd_serialReadyFlag);
14
      }
15
}
16
17
void lcd_streamwrite_stop(void){
18
      lcd_cs_high;
19
}

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.