Re: Delphi prevent Windows shutdown until files saved

Posted by webmaster Guido on September 29, 2008

In Reply to Prevent Windows shutdown until files saved posted by Felice P16730 on September 28, 2008

: How can I stop Windows from shutting down if my Delphi application is still running and there are still some of my data to be saved? Because some people forget to save the files and shut down my program before they shut down Windows.

When Windows is about to shut down, it sends the message WM_QueryEndSession to all open applications. To detect this message from your Delphi application and take appropriate action, you write a message handler. Put the definition of that message handler in the private section of the unit for your application's main form (see below).

You also need a Boolean (logical) variable, say DataToBeSaved, indicating if your data should be saved or not. Set this variable to False at the beginning of the program and each time that you save the data; set it to True whenever your data is changed. Let's also declare that variable in the private section:

private
  { Private declarations }
  DataToBeSaved: Boolean;
  procedure WMQueryEndSession(var Msg: TWMQueryEndSession);
    message WM_QueryEndSession; // detect Windows shutdown message
  procedure SaveData; // routine to save data to disk
  // ...and so on

In the implementation section of the unit, add the following code:

// If necessary (if DataToBeSaved is True), delay the closing of Windows until
// your data are saved 
procedure TForm1.WMQueryEndSession(var Msg: TWMQueryEndSession); 
begin 
  if DataToBeSaved then
    if MessageDlg('Windows is shutting down! First save data changes?',
         mtConfirmation, [mbYes, mbNo], 0) = mrYes then begin
      Msg.Result := 0; // disallow Windows from shutting down
      SaveData; 
    end;
  Msg.Result := 1;     // allow Windows shutdown
end; 

// Set DataToBeSaved to False after saving data 
procedure TForm1.SaveData;
begin
  // Save data to disk files
  // ...
  DataToBeSaved := False;
end;  

// At the start of the program, DataToBeSaved must be False 
procedure TForm1.FormCreate(Sender: TObject);
begin
  DataToBeSaved := False;
end; 

Notes:

1. Don't forget to set DataToBeSaved to True, each time that your data are changed.

2. If you want your data to be saved automatically when Windows is closed while your application is still running, then omit the message dialog with the question 'Windows is shutting down! First save data changes?' The code for the message handler becomes:

procedure TForm1.WMQueryEndSession(var Msg: TWMQueryEndSession); 
begin 
  if DataToBeSaved then begin
    Msg.Result := 0; // stop Windows from shutting down
    SaveData; 
  end;
  Msg.Result := 1; // allow Windows shutdown
end; 

Related articles