4

I'm trying to make an animated splashscreen while my app loads his database. I already created a splashscreen but I want to make the image "move" from left to right while the db is getting converted. Been searching for a while now but all I could find is about progress bars...

Here's my code:

SplashScreen := TSplashScreen.Create(Application) ;
SplashScreen.Show;
Application.Initialize;
SplashScreen.Update;
SplashScreen.lblStatus.Caption:='Loading...';
SplashScreen.Update;
SplashScreen.lblStatus.Caption:='Updating database...';
SplashScreen.Update;
Application.Initialize;
Application.CreateForm(TfmMain, fmMain);
Sleep(1000);

Application.CreateForm(TfmPrefs, fmPrefs);
Application.CreateForm(TfmCode, fmCode);
Application.CreateForm(TfmEmps, fmEmps);
Application.CreateForm(TfmRest, fmRest);
Application.ShowMainForm:=FALSE;

SplashScreen.Hide;
SplashScreen.Free;
Application.Run;

On my splashscrren form, I created 5 duplicates of the same image and while the Main Form is created, I want the image to be Visible and not visible in alternance... ex:

while my db loads... begin
Splashscreen.Image1.Visible:=FALSE;
SplashScreen.Update;
Sleep(25);
SplashScreen.Image1.Visible:=FALSE;
SplashScreen.Update;
SplashScreen.Image2.Visible:=TRUE;....

and so on!

Any thoughts?

Gab
  • 681
  • 4
  • 14
  • 27
  • What exactly is your question? The `Sleep` in both your code snippets, since you're executing everything in the main thread, will pause your entire application (including the `while my db loads` code) for at least the duration of the call to `Sleep`. IOW, you're stopping your application by putting the thread in pause while you're expecting it to work updating the image display. – Ken White Nov 18 '11 at 21:26
  • Original post, as Ken suggested :) - Hm, why don't you try using a GIF image instead? For displaying animated GIFs on your form, you may consider using TGifImage, accessible from here: http://www.tolderlund.eu/delphi/ – Pateman Nov 18 '11 at 21:29
  • The SLeep(1000) in the top snippets is only to show my splashscreen and will be removed when the app is complete... it is there to let me actually see the splashscreen. The second one is there so that the images stay at least 25 milliseconds so that they don't appear as a tray. – Gab Nov 18 '11 at 22:19
  • @Pateman, thanks but I don't want it to be animated I just want it the 1st image to be visible and then not, then the one on its right will be and so on... sorry I f i'm not clear! – Gab Nov 18 '11 at 22:22
  • You are probably looking for a threaded splash screen. This one by Peter Below is highly used : [Threaded Splashscreen for Delphi](http://cc.embarcadero.com/Item/20139) – LU RD Nov 18 '11 at 22:51
  • @LURD, you should expand on your comment slightly (to explain why you need a threaded splash screen instead of using `Sleep`) and post it as an answer. (I thought of Peter's threaded splash screen as well, but you posted the link first. ) – Ken White Nov 19 '11 at 00:46
  • @KenWhite, ok I expanded the comment into an answer. – LU RD Nov 19 '11 at 12:07

1 Answers1

4

Doing heavy work in the main thread during startup (like initializing database and many forms) does not work well with splash screens. The main thread is too occupied to do anything with the GUI. Putting Sleep into the code will not work, since this will stop the main thread to do any work at all.

This leaves you with two options :

  1. Do your database initializations in another thread. Sometimes also only initializing the main form is a good option. The database thread can send progress messages to the splash form via PostMessage calls.

  2. Start the splash screen in a separate thread. This is kind of tricky, because you may not use the VCL from another thread. And also you must avoid blocking the message queue. Luckily, Peter Below has made a good example how to do a threaded splash screen using only windows api calls.

There are some more information in this SO thread : displaying-splash-screen-in-delphi-when-main-thread-is-busy.

Community
  • 1
  • 1
LU RD
  • 34,438
  • 5
  • 88
  • 296
  • @KenWhite, thanks. And perhaps I should have mentioned that option 1 is a generic solution while option 2 may depend on windows version. – LU RD Nov 19 '11 at 17:19
  • @TOndrej, #1 might be a problem. Database connections (for every DB I've ever used, anyway) are per-thread, so initializing in a separate thread means that the main thread won't have access to that connection once the initialization is complete (unless, of course, you set up a means of communicating between the secondary and main thread, which is a whole different topic ). – Ken White Nov 19 '11 at 17:46