Mon application fonctionne de la manière que vous décrivez. Voici l'approche que j'ai prise. J'aurais aimé trouver une approche plus simple mais je ne l'ai jamais fait.
J'ai commencé par lire ces articles. Cette première est une grande écriture par Peter Ci-dessous:
http://groups-beta.google.com/group/borland.public.delphi.winapi/msg/e9f75ff48ce960eb?hl=en
Autres informations a également été trouvé ici, mais cela ne prouve pas être une solution valable: pour mon utilisation: http://blogs.teamb.com/DeepakShenoy/archive/2005/04/26/4050.aspx
Finalement, voici ce que j'ai fini avec.
Mon écran de démarrage sert également de formulaire principal d'application. Le formulaire principal a un lien spécial avec l'objet Application.Utiliser toutes les formes secondaires m'apporte le comportement que je cherchais.
Dans chaque formulaire que je veux dans la barre des tâches je substitue CreateParams. Je le fais sur mes formes d'édition et ce que les utilisateurs considère comme la « forme principale »
procedure TUaarSalesMain.CreateParams(var Params: TCreateParams);
begin
inherited CreateParams(Params);
Params.ExStyle := Params.ExStyle or WS_EX_APPWINDOW;
Params.WndParent := GetDesktopWindow;
end;
Ma forme « Main » dans la mesure où Delphi est la forme des charges concernées vraie principale dans sa fonction Activitate. J'utilise une variable membre pour suivre la première activation. Puis, à la fin de la fonction, je masque la forme splash, mais ne la ferme pas. C'était important pour moi car si l'utilisateur éditait un document et fermait le formulaire principal, je ne voulais pas que les écrans d'édition soient forcés de fermer en même temps. De cette façon, toutes les formes visibles sont traitées de la même manière.
if FFirstActivate = false then
exit;
FFristActivate := false;
/*
Main Load code here
Update Splash label, repaint
Application.CreateForm
etc.
*/
// I can't change visible here but I can change the size of the window
Self.Height := 0;
Self.Width := 0;
Self.Enabled := false;
// It is tempting to set Self.Visible := false here but that is not
// possible because you can't change the Visible status inside this
// function. So we need to send a message instead.
ShowWindow(Self.Handle, SW_HIDE);
end;
Mais il y a toujours un problème. Vous devez fermer la fenêtre principale/splash lorsque tous les autres formulaires sont fermés. J'ai une vérification supplémentaire dans mes routines de fermeture pour Parent <> nil parce que j'utilise des formes comme plugins (forme mes objectifs ils fonctionnent mieux que les cadres).
Je n'aimais pas vraiment utiliser l'événement Idle, mais je ne remarque pas que ce soit un frein sur le processeur.
{
TApplicationManager.ApplicationEventsIdle
---------------------------------------------------------------------------
}
procedure TApplicationManager.ApplicationEventsIdle(Sender: TObject;
var Done: Boolean);
begin
if Screen.FormCount < 2 then
Close;
end;
{
TApplicationManager.FormCloseQuery
---------------------------------------------------------------------------
}
procedure TApplicationManager.FormCloseQuery(Sender: TObject;
var CanClose: Boolean);
var
i: integer;
begin
for i := 0 to Screen.FormCount - 1 do
begin
if Screen.Forms[i] <> self then
begin
// Forms that have a parent will be cleaned up by that parent so
// ignore them here and only attempt to close the parent forms
if Screen.Forms[i].Parent = nil then
begin
if Screen.Forms[i].CloseQuery = false then
begin
CanClose := false;
break;
end;
end;
end;
end;
end;
{
TApplicationManager.FormClose
---------------------------------------------------------------------------
}
procedure TApplicationManager.FormClose(Sender: TObject;
var Action: TCloseAction);
var
i: integer;
begin
for i := Screen.FormCount - 1 downto 0 do
begin
if Screen.Forms[i] <> self then
begin
// Forms that have a parent will be cleaned up by that parent so
// ignore them here and only attempt to close the parent forms
if Screen.Forms[i].Parent = nil then
begin
Screen.Forms[i].Close;
end;
end;
end;
end;
Cela m'a bien servi jusqu'ici. J'ai fait un petit changement pour Vista parce que l'icône de mon écran "Main/Splash" était toujours visible. Je ne me souviens pas de ce que c'était. Je n'ai probablement pas besoin de définir la largeur, la hauteur, activé et envoyer le message masquer sur l'écran de démarrage. Je voulais juste m'assurer que ça ne se voit pas :-).
La gestion des événements de proximité était nécessaire. Si je me souviens bien, c'était nécessaire quand Windows a envoyé un message d'arrêt. Je pense que seule la forme principale reçoit ce message.
Le splash caché semble horrible, mais il pourrait aussi résoudre un autre problème. Cela pourrait être ce que je vais avec si rien d'idéal n'apparaît. Merci! – mj2008
J'ai également adopté une approche similaire avec l'une de mes applications et cela a bien fonctionné. J'ai ajouté un peu de code pour appeler l'application de minimiser quand le "formulaire principal" a été réduit, et ajouté un événement à l'application.onrestore pour restaurer le "formulaire principal". – skamradt
Je suis d'accord le splash caché est horrible. Si quelque chose de mieux apparaît, je vais aussi changer mon code :-). C'est dommage que stackoverflow n'était pas là quand j'ai écrit ça pour la première fois. –