Display functions optimization

Libraries, utilities, bootloaders...

Re: Display functions optimization

Postby jonnection » Thu Jan 15, 2015 7:47 am

Myndale wrote:82ns :D


Under 100 ns. Fantastic, I knew you could do it !

Image
User avatar
jonnection
 
Posts: 317
Joined: Sun May 04, 2014 8:21 pm

Re: Display functions optimization

Postby rodot » Thu Jan 15, 2015 8:11 am

Myndale wrote:82ns :D


Wow, that's awesome, there are so many possibilities...

I'm filled with emotion.gif
I'm filled with emotion.gif (499.9 KiB) Viewed 8461 times
User avatar
rodot
Site Admin
 
Posts: 1290
Joined: Mon Nov 19, 2012 11:54 pm
Location: France

Re: Display functions optimization

Postby Myndale » Thu Jan 15, 2015 9:46 am

Lol, thx guys :) I did have a quick play with pre-compiled sprites just to see what kind of results I'd get, first-pass got down to around 40ms unaligned for that particular sprite. Pity they're not much use in a generic library.

I do plan to revisit this thread once the basic tracker is up and running.
Myndale
 
Posts: 507
Joined: Sat Mar 01, 2014 1:25 am

Re: Display functions optimization

Postby Drakker » Thu Jan 15, 2015 12:00 pm

Now aim for 20ns! You can do it!
User avatar
Drakker
 
Posts: 297
Joined: Sun Mar 30, 2014 2:54 am
Location: Québec, Canada

Re: Display functions optimization

Postby DFX2KX » Thu Jan 15, 2015 7:48 pm

82ms.... Alright, let's put that in perspective.... MILLISECONDS.... with that sort of drawing time, you could mimic the four-shade effect of a Gameboy screen....
DFX2KX
 
Posts: 250
Joined: Mon Apr 14, 2014 3:48 am

Re: Display functions optimization

Postby Skyrunner65 » Fri Jan 16, 2015 12:49 pm

I'm pretty sure that's NANOSECONDS (Say, for example, 80 ns would be 80/1,000,000,000 of a second, or 80 billionths of a second).
But still, great job guys. :mrgreen:
User avatar
Skyrunner65
 
Posts: 371
Joined: Thu Mar 20, 2014 5:37 pm
Location: NC,USA

Re: Display functions optimization

Postby rodot » Fri Jan 16, 2015 6:07 pm

I think he meant that 82ns (even if he mispelled is "ms") is pretty small compared to the milliseconds a frame lasts (50ms when the game runs at 20 frames per second). The high update rate of the screen would then allow 4 shades of gray (by alternating between black and white frames at high speed at different duty cycle to get different shades), just like the original Game Boy.
User avatar
rodot
Site Admin
 
Posts: 1290
Joined: Mon Nov 19, 2012 11:54 pm
Location: France

Re: Display functions optimization

Postby erico » Fri Jan 16, 2015 7:00 pm

I guess there will have to be some asm for shades to pop up?
Also a better understatement of the screen hardware itself?

Heck, this is beautiful, if 82 is possible in C/C++ then asm could make it 1 or less?
Nice thread here!
User avatar
erico
 
Posts: 671
Joined: Thu Mar 27, 2014 9:29 pm
Location: Brazil

Re: Display functions optimization

Postby Myndale » Fri Jan 16, 2015 9:00 pm

Doesn't matter how fast you draw, it won't improve grey scale capability beyond what we've already achieved. When you send data to the LCD it doesn't change the pixels instantaneously, it instead stores the values in its internal DDRAM while a separate multiplex driver continually streams this memory to the actual display:

pcd8544.png
pcd8544.png (26.21 KiB) Viewed 8406 times


As far as I'm aware the only way to change the mux rate of the driver is to feed it an external clock, which in the case of Gamebuino isn't possible as that pin is tied high:

lcd.png
lcd.png (11.88 KiB) Viewed 8406 times
Myndale
 
Posts: 507
Joined: Sat Mar 01, 2014 1:25 am

Re: Display functions optimization

Postby rodot » Sun Jan 18, 2015 7:00 pm

With all these posts about drawBitmap optimization, I was thinking that as there is going to be big changes, we could re-think the way bitmaps are stored. I suggest the following changes, don't hesitate if you have any critics. If you agree that it would be a valuable update, I'll implement all that soon.

Now, bitmaps are stored in a mono dimensional array of byte in PROGMEM. Instead, we could use a Bitmap class that would store a pointer to the bitmaps data. We could use indexed color index to embed all the colors in one bitmap. We could also store several frames in one bitmaps (for animated bitmaps or tilemaps).
Here is a quick snippet to explain the idea :

Code: Select all
class Bitmap{
public :
  uint8_t width;
  uint8_t height;
  uint8_t numColors; //number of indexed colors
  static uint8_t colorIndex[] = [WHITE, BLACK, GRAY, TRANSPARENT, INVERT];
                       //the colors are constants respectively equal to 0 1 2 3 4
                       //gray will be automatically filled by an alternating checkers pattern by gb.display.drawBitmap()
  uint8_t frames; //number of frames stored. Can be used for animated bitmaps or tilemaps
  uint8_t compression; //0 for raw bitmap, 1 for RLE, 2 for nokia swizzled...
  uint8_t location; //either 0 for PROGMEM or 1 for RAM (why not SD card support later on)
  const uint8_t *bitmap; //a pointer to the bitmap data array.
                        //Contains all the different colors, and one or several frames one after the other
                        //the duration of each frame is store right before the pixels data

  void loadPROGMEM(const uint8_t *bmp){
    location = 0; //bitmap located in progmem
    width = pgm_read_byte(bmp);
    height = pgm_read_byte(bmp + 1);
    colors = pgm_read_byte(bmp + 2);
    frames = pgm_read_byte(bmp + 3);
    compression = pgm_read_byte(bmp + 4);
    bitmap = bmp + 5;
  }

  void loadRAM(const uint8_t *bmp){
    location = 1; //bitmap located in RAM
    width = bmp[0];
    height = bmp[1];
    colors = bmp[2];
    frames = bmp[3];
    compression = bmp[4];
    bitmap = bmp + 5;
  }
};


The library function gb.display.drawBitmap() would then select the right algorithm to display the bitmap depending on the encoding, number of colors, etc.

It might also be interesting to add the continuous rotation (as in taxi fou) and scaling (as in the isle of maniax) of bitmaps to the library.
Instead of passing many arguments to gb.display.drawBitmap each times for the rotation, flipping, etc I could add the function gb.dislay.setBitmapRoation, gb.display.setBitmapScaling, etc. This will make the code more readable.

Another class that would be interesting to add to the library is an AnimatedBitmap class, for animated bitmaps to be played automatically and individually each time drawBitmap is called.

Code: Select all
class AnimatedBitmap{
  Bitmap *bitmap;
  int8_t currentFrame; //-1 when not playing
  uint8_t looping; //0 no looping, 1 normal looping, 2 back and forth loopming, 3 stay on the last frame, etc.
}


I think it's better to separate the AnimatedBitmap class for the Bitmap class to limit the RAM footprint. For example, if you have 10 monsters, you will store only 1 Bitmap object (containing width, height and all), and 10 AnimatedBitmap objects (only containing the current state of the animation and a pointer to the Bitmap object).

These changes will break compatibility, but I will use preprocessor instructions to be able to compile games made using previous versions in "compatibility mode". This will be a setting available in libraries/Gamebuino/settings.c

That's some pretty big changes but I think it's worth it. What do you think ?
User avatar
rodot
Site Admin
 
Posts: 1290
Joined: Mon Nov 19, 2012 11:54 pm
Location: France

PreviousNext

Return to Software Development

Who is online

Users browsing this forum: No registered users and 4 guests

cron