Heya,
A couple of weeks ago, I posted:
>> Hi Folks,
>>
>> As it says in the subject line, I would like to create an DirectFB
>> application with the following capabilities:
>>
>> 1. The ability to use the Draw functions in an area outside the viewable
>> area (ie invisible to the user).
>> 2. Pan the data in the area outside the viewable area into (and out of)
>> the viewable area.
>> 3. Copy data from one part of the surface to another, to provide
>> temporary saving (I realize that I could use the "Dump" API for this,
>> create a png and when I want to restore it, load it back in but this
>> seems somewhat inefficient) as well as a provide a very fast (or fade in)
>> transition between images.
>>
>> Can anybody point me to any references or example code explaining how
>> this could be done? I'm using the basic DirectFB package (ie no
>> QT/Qtopia) to try and keep the code footprint as small as possible.
>>
>> Thanx - I really appreciate any suggestions that people would have for
>> me.
>>
>> myke
I wanted to follow up and say that I believe that I have solved all my
problems.
What I was missing was an understanding of how “surfaces” work in DirectFB;
they provide the ability of drawing off screen, bring data into the viewable
area and provide the ability to temporarily save data off screen.
To demonstrate this operation, I created the application below so hopefully
somebody else new to working with DirectFB and wanting similar capabilities
will have a place to start. I would also appreciate any of the old hands at
DirectFB reviewing the code below and commenting/suggesting on where I have
done things wrong/could be done better or more efficiently.
My application runs on a Freescale i.MX233, which is an ARM without video
hardware acceleration running Linux 2.6.31. The display is 480x272 and for
the “bckgnd#.png” images, I clipped some basic pictures to this size.
Similarly, the font used is an open-source Open Text font which should be
easy to find.
This is a resend because the original seemed to lose formatting (hopefully this
one won’t).
Please reply back with any questions or comments,
myke
/*
* dfb_image6.c
*
*
* Save and Later Redisplay Surface on the display
*
* Written for fsl i.MX233 EVK running Linux 2.6.31
*
*
* Created on: 29-Dec-2011
* Author: myke
*/
#include <stdio.h>
#include <unistd.h>
#include <directfb.h>
static IDirectFB* dfb = NULL;
static IDirectFBSurface* primary = NULL;
DFBSurfaceDescription primary_dsc;
static IDirectFBSurface* image1;
DFBSurfaceDescription image1_dsc;
static IDirectFBSurface* image2;
DFBSurfaceDescription image2_dsc;
static IDirectFBSurface* image3;
DFBSurfaceDescription image3_dsc;
IDirectFBFont* font = NULL;
DFBFontDescription font_dsc;
static int screen_width = 0;
static int screen_height = 0;
#define DFBCHECK(x...) \
{ \
DFBResult err = x; \
\
if (err != DFB_OK) \
{ \
fprintf( stderr, "%s <%d>:\n\t", __FILE__, __LINE__ ); \
DirectFBErrorFatal( #x, err ); \
} \
}
int main (int argc, char **argv)
{
int i;
IDirectFBImageProvider* provider;
// Create Super Interface
DFBCHECK(DirectFBInit (&argc, &argv));
DFBCHECK(DirectFBCreate (&dfb));
// Create Primary Surface
DFBCHECK(dfb->SetCooperativeLevel(dfb, DFSCL_FULLSCREEN));
primary_dsc.flags = DSDESC_CAPS;
primary_dsc.caps = DSCAPS_PRIMARY | DSCAPS_DOUBLE;
DFBCHECK(dfb->CreateSurface(dfb, &primary_dsc, &primary));
// Get the size of the primary Display
DFBCHECK(primary->GetSize(primary, &screen_width, &screen_height));
// printf("\r#### - \"primary\" screen_width = %i, screen_height = %i\r\n",
screen_width, screen_height);
// Create (1) - JUST a background image
DFBCHECK(dfb->CreateImageProvider(dfb, "/home/images/bckgnd1.png",
&provider)); // Gears Background
DFBCHECK(provider->GetSurfaceDescription(provider, &image1_dsc));
DFBCHECK(dfb->CreateSurface(dfb, &image1_dsc, &image1));
DFBCHECK(provider->RenderTo(provider, image1, NULL));
DFBCHECK(provider->Release(provider));
// Create (2) - NO background image
image2_dsc.flags = DSDESC_WIDTH | DSDESC_HEIGHT;
image2_dsc.width = screen_width; image2_dsc.height = screen_height;
DFBCHECK(dfb->CreateSurface(dfb, &image2_dsc, &image2));
font_dsc.flags = DFDESC_HEIGHT | DFDESC_ROTATION;
font_dsc.height = 24;
font_dsc.rotation = DFB_DEGREES(0);
DFBCHECK(dfb->CreateFont(dfb, "/home/fonts/NotCourierSans-Bold.otf",
&font_dsc, &font));
DFBCHECK(image2->SetFont(image2, font));
DFBCHECK(image2->SetColor(image2, 0x00, 0x00, 0xff, 0xff));
DFBCHECK(image2->FillRectangle(image2, 0, 0, screen_width, screen_height));
DFBCHECK(image2->SetColor(image2, 0xff, 0xff, 0xff, 0xff));
DFBCHECK(image2->DrawString(image2, "Image (2)", -1, 25, screen_height / 2,
DSTF_LEFT | DSTF_TOP));
// Create (3) - Background image & Box
DFBCHECK(dfb->CreateImageProvider(dfb, "/home/images/bckgnd2.png",
&provider)); // Gears Background
DFBCHECK(provider->GetSurfaceDescription(provider, &image3_dsc));
DFBCHECK(dfb->CreateSurface(dfb, &image3_dsc, &image3));
DFBCHECK(provider->RenderTo(provider, image3, NULL));
DFBCHECK(provider->Release(provider));
DFBCHECK(image3->SetColor(image3, 0xff, 0xff, 0xff, 0xff));
DFBCHECK(image3->FillRectangle(image3, screen_width / 4, screen_height / 4,
screen_width / 2, screen_height / 2));
// Display the First Image
DFBCHECK(primary->SetBlittingFlags(primary, DSBLIT_NOFX));
DFBCHECK(primary->Blit(primary, image1, NULL, 0, 0));
DFBCHECK(primary->Flip(primary, NULL, DSFLIP_ONSYNC));
sleep(1);
// Display the Second Image
DFBCHECK(primary->SetBlittingFlags(primary, DSBLIT_NOFX));
DFBCHECK(primary->Blit(primary, image2, NULL, 0, 0));
DFBCHECK(primary->Flip(primary, NULL, DSFLIP_ONSYNC));
sleep(1);
// Display the Third Image - From Right
for (i = screen_width; 0 <= i; i -= 4) {
// printf("\ri = %i\r\n", i);
DFBCHECK(primary->SetBlittingFlags(primary, DSBLIT_NOFX));
DFBCHECK(primary->Blit(primary, image3, NULL, i, 0));
DFBCHECK(primary->Flip(primary, NULL, DSFLIP_ONSYNC));
}
sleep(1);
// Redisplay the Second Image - From Bottom
for (i = screen_height; 0 <= i; i -= 4) {
// printf("\ri = %i\r\n", i);
DFBCHECK(primary->SetBlittingFlags(primary, DSBLIT_NOFX));
DFBCHECK(primary->Blit(primary, image2, NULL, 0, i));
DFBCHECK(primary->Flip(primary, NULL, DSFLIP_ONSYNC));
}
sleep(1);
// Redisplay the First Image - From Left
for (i = -screen_width; 0 >= i; i += 4) {
// printf("\ri = %i\r\n", i);
DFBCHECK(primary->SetBlittingFlags(primary, DSBLIT_NOFX));
DFBCHECK(primary->Blit(primary, image1, NULL, i, 0));
DFBCHECK(primary->Flip(primary, NULL, DSFLIP_ONSYNC));
}
sleep(1);
// Before redisplaying Third Image, make white rectangle outlined black box
DFBCHECK(image3->SetColor(image3, 0x00, 0x00, 0x00, 0xff));
DFBCHECK(image3->FillRectangle(image3, (screen_width / 4) + 3,
(screen_height / 4) + 3, (screen_width / 2) - 6, screen_height / 2) - 6));
// Redisplay the Third Image - From Top
for (i = -screen_height; 0 >= i; i += 4) {
// printf("\ri = %i\r\n", i);
DFBCHECK(primary->SetBlittingFlags(primary, DSBLIT_NOFX));
DFBCHECK(primary->Blit(primary, image3, NULL, 0, i));
DFBCHECK(primary->Flip(primary, NULL, DSFLIP_ONSYNC));
}
sleep(1);
// Update the currently shown image
DFBCHECK(primary->SetColor(primary, 0xff, 0xff, 0xff, 0xff));
DFBCHECK(primary->DrawLine(primary, screen_width / 8, screen_height / 8,
(screen_width * 7 ) / 8, screen_height / 8));
DFBCHECK(primary->DrawLine(primary, screen_width / 8, (screen_height * 7) /
8, (screen_width * 7 ) / 8, (screen_height * 7) / 8));
DFBCHECK(primary->SetFont(primary, font));
DFBCHECK(primary->DrawString(primary, "That's all!", -1, (screen_width / 4)
+ 6, (screen_height / 4) + 6, DSTF_LEFT | DSTF_TOP));
DFBCHECK(primary->Flip(primary, NULL, DSFLIP_ONSYNC));
sleep(1);
// Copy primary into image2
DFBCHECK(image2->SetBlittingFlags(image2, DSBLIT_NOFX));
DFBCHECK(image2->Blit(image2, primary, NULL, 0, i));
// Clear the "That's all!" message on displayed image
DFBCHECK(primary->SetColor(primary, 0x00, 0x00, 0x00, 0xff));
DFBCHECK(primary->FillRectangle(primary, (screen_width / 4) + 3,
(screen_height / 4) + 3, (screen_width / 2) - 6, (screen_height / 2) - 6));
DFBCHECK(primary->Flip(primary, NULL, DSFLIP_ONSYNC)); // Remember the Flip
after updating the display
sleep(1);
// Display the First Image
DFBCHECK(primary->SetBlittingFlags(primary, DSBLIT_NOFX));
DFBCHECK(primary->Blit(primary, image1, NULL, 0, 0));
DFBCHECK(primary->Flip(primary, NULL, DSFLIP_ONSYNC));
sleep(1);
// Display the saved Image
DFBCHECK(primary->SetBlittingFlags(primary, DSBLIT_NOFX));
DFBCHECK(primary->Blit(primary, image2, NULL, 0, 0));
DFBCHECK(primary->Flip(primary, NULL, DSFLIP_ONSYNC));
sleep(5);
// Release the DirectFB components
DFBCHECK(font->Release(font));
DFBCHECK(image1->Release(image1));
DFBCHECK(image2->Release(image2));
DFBCHECK(image3->Release(image3));
DFBCHECK(primary->Release(primary));
DFBCHECK(dfb->Release(dfb));
return 6;
}
_______________________________________________
directfb-users mailing list
[email protected]
http://mail.directfb.org/cgi-bin/mailman/listinfo/directfb-users