Board index » delphi » Shutting down with Delphi program active ?

Shutting down with Delphi program active ?

Have anybody experienced this weird problem:
when tring to shutdown windows with delphi program active, it refuses to
do it.

It looks like the program respondes with FALSE to WM_QUERYENDSESSION
message, no matter what form's CanClose returns. as suggested here, I
tried to intercept QueryEndSession, and call Application.Terminate. That
appears to work only when the window is not minimized, and I don't like
the idea of doing it for all windows, not knowing which  one will
receive the message first.

any ideas ?

thanks in advance,

------------------------------
Vadim        va...@melig.co.il
[ Remove  -NOSPAM to mail me ]

 

Re:Shutting down with Delphi program active ?


Quote
Vadim wrote:
> Have anybody experienced this weird problem:
> when tring to shutdown windows with delphi program active, it refuses to
> do it.

You haven't published your code, so it's hard to help. However, this
code works fine for me...

type
  TMainTrayForm = class(TForm)
                    procedure WMQueryEndSession(var WMsg:
TWMQueryEndSession);
                                                      message
WM_QUERYENDSESSION;
                    procedure WMEndSession(var WMsg: TWMEndSession);
                                                      message
WM_ENDSESSION;
                  end;

procedure TMainTrayForm.WMQueryEndSession(var WMsg: TWMQueryEndSession);
begin
{
  Query the user's intentions ...

Quote
}

  if MessageBox(0,'Killing Windows: Are you sure?',
                  PChar(Application.Title),
                  MB_YESNO or MB_ICONQUESTION) = ID_YES then
    inherited   // Default handling continues ShutDown request
end;

{
  Intentions confirmed: prepare for ShutDown ...

Quote
}

procedure TMainTrayForm.WMEndSession(var WMsg: TWMEndSession);
var
  EndMsg: string;
begin
  with WMsg do
    if EndSession then
      begin
        if BOOL(Unused) then   // Win95 LogOff parameter ...
          EndMsg := 'Logging out of Win95.'
        else
          EndMsg := 'Shutting down.';
        MessageBox(0,PChar(EndMsg),
                     PChar(Application.Title),
                     MB_OK or MB_ICONEXCLAMATION)
      end;
  inherited  // Continue ShutDown request
end;

Chris.

Re:Shutting down with Delphi program active ?


Quote
Vadim wrote:

> Have anybody experienced this weird problem:
> when tring to shutdown windows with delphi program active, it refuses
> to do it.

  ExitWindowsEx(0,EWX_FORCE);  will do it for you....

--
Jason
E...@DarkElf.reno.nv.us

Re:Shutting down with Delphi program active ?


Quote
>I need to be able to shut down the windows (given the
>program a chance to save it's data, of course). What I get now, is
>when I select 'shutdown the computer', or 'close all program ..'the
>computer begins the shutdown, closes a few progams, and then just
>stops, as if my program just cancels the operation.
>procedure TMainForm.WMQueryEndSession(var Message:
>TWMQueryEndSession);
>begin
>  // Message.Result := LongInt(true);
>  Application.Terminate;
>  Halt;
>end;

Maybe you *ARE* cancelling the operation... Windows passes the
WM_QUERYENDSESSION message to all open applications; if you
can terminate conveniently, then an app returns TRUE to this
message. If an app. returns FALSE then the shutdown is halted.
The default value is TRUE, so your form doesn't need to catch
WM_QUERYENDSESSION.

Once every app has agreed to the shutdown, Windows passes a
WM_ENDSESSION message to them all: THIS is where you perform
your cleanup.

procedure TMainForm.WMEndSession(var Msg: TWMEndSession);
begin
  { Cleanup code }
  Msg.Result := 0
end;

I see that you are using Application.Terminate and Halt. I'm
not sure that this is a good idea within the message-dispatch
mechanism... As an experiment: set a breakpoint on the Halt
command: does the de{*word*81} ever reach it?

It might be better to just call a routine to save your data (etc)
at this point.

Chris.

Re:Shutting down with Delphi program active ?


well, this doesn't appears to solve the problem.

a little more info: my program can be in one of two states: normal,
when the main window is visible, and hidden, when application can be
accessed via tray icon.
the code used to do the minimize/restore is like this:

procedure TMainForm.AppMinimize(Sender: TObject);
begin
  ShowWindow(Application.Handle, SW_HIDE);
end;

procedure TMainForm.TrayIcon1DblClick(Sender: TObject);
begin   {if minimized - unhide}
if IsIconic(Application.Handle) then begin
   ShowWindow(Application.Handle, SW_SHOW);
   Application.Restore;
   end
else    { else - just make active }
   SetForegroundWindow(MainForm.Handle);
end;

In both states I need to be able to shut down the windows (given the
program a chance to save it's data, of course). What I get now, is
when I select 'shutdown the computer', or 'close all program ..'the
computer begins the shutdown, closes a few porgams, and then just
stops, as if my program just cancels the operation.

I've tried to insert the following code in the main form:

procedure TMainForm.WMQueryEndSession(var Message:
TWMQueryEndSession);
begin
  // Message.Result := LongInt(true);
  Application.Terminate;
  Halt;
end;

It works only when the form is in 'normal' state, but has no effect
when the application is minimized.

There is no CanClose routines in any of the forms.

This whole issue is very strange, for I've never seen a program
interfering with a shutdown in this way. Any ideas ??

thanks for your help

Vadim           va...@melig.co.il

Quote
Chris Rankin <RankinC{no.sp...@Logica.com> wrote:
>Vadim wrote:
>> Have anybody experienced this weird problem:
>> when tring to shutdown windows with delphi program active, it refuses to
>> do it.

>You haven't published your code, so it's hard to help. However, this
>code works fine for me...

>type
>  TMainTrayForm = class(TForm)
>                    procedure WMQueryEndSession(var WMsg:
>TWMQueryEndSession);
>                                                      message
>WM_QUERYENDSESSION;
>                    procedure WMEndSession(var WMsg: TWMEndSession);
>                                                      message
>WM_ENDSESSION;
>                  end;

>procedure TMainTrayForm.WMQueryEndSession(var WMsg: TWMQueryEndSession);
>begin
>{
>  Query the user's intentions ...
>}
>  if MessageBox(0,'Killing Windows: Are you sure?',
>                  PChar(Application.Title),
>                  MB_YESNO or MB_ICONQUESTION) = ID_YES then
>    inherited   // Default handling continues ShutDown request
>end;

>{
>  Intentions confirmed: prepare for ShutDown ...
>}
>procedure TMainTrayForm.WMEndSession(var WMsg: TWMEndSession);
>var
>  EndMsg: string;
>begin
>  with WMsg do
>    if EndSession then
>      begin
>        if BOOL(Unused) then   // Win95 LogOff parameter ...
>          EndMsg := 'Logging out of Win95.'
>        else
>          EndMsg := 'Shutting down.';
>        MessageBox(0,PChar(EndMsg),
>                     PChar(Application.Title),
>                     MB_OK or MB_ICONEXCLAMATION)
>      end;
>  inherited  // Continue ShutDown request
>end;

>Chris.

Re:Shutting down with Delphi program active ?


I've found the problem, and it wasn't even in my code. A number of
components in my app used a hidden window created with AllocateHwnd,
but failed to process messsages correcly, returning false on
WM_QUERYENDSESSION.I fixed components with source, removed the ones
without, and everithing works as it should.

Thanks to everyone who replyed

Va...@melig.co.il

Quote

>>Vadim wrote:
>>> Have anybody experienced this weird problem:
>>> when tring to shutdown windows with delphi program active, it refuses to
>>> do it.

Other Threads