سؤال

I have an app that can optionally open PDF's after it creates them. If two reports are generated in succession with the same name, the second attempt fails if the first copy of acrobat still has the PDF open, so before I write the PDF I check (with FindWindow) for a window with the document name. If one is found I issue a SendMessage WM_Close.

This works OK, but I was doing some other tests and was using Word to "edit" the PDF, to hold it open so I could test the app's behaviour when it can't write the PDF file. Now, when my app tries to close the window, Word pops up a "do you want to save" dialog. If I click cancel, Word remains open, my app carries on and I can test that it behaves sensibly when it encounters a file that it can't write to.

All good, but it has alerted me to the fact that using SendMessage WM_CLOSE to close another app will snag my app if the other app pops up a modal dialog. Is there any way around this - i.e a more forceful (but not too forceful) way of closing the other app? Or a "Close and click on cancel if necessary". Or should I use asynchronous messages?

هل كانت مفيدة؟

المحلول

Do not force any application to close, there may be other documents open the user is viewing etc... You can use SendMessageTimeout to wait the return of WM_CLOSE a sensible amount of time, and then proceed with either failure or success..

var
  Word: HWND;
  msgResult: DWORD;
begin
  ...

  SendMessageTimeout(Word, WM_CLOSE, 0, 0, SMTO_NORMAL, 5000, msgResult);
  if IsWindow(Word) then begin
    // bummer! Application is open...
 

نصائح أخرى

I would not close the other application at all. I think it's better to delete the current file before generating the report. If it fails (DeleteFile), show a message to the user that the file cannot be overwritten (because it is opened by another program) and do not generate the report at all. This is much safer, because you leave the option to the user. Also this saves you from major headaches, what if the program is opened by another program that does not show the title in the window caption?

If you want to go one step further than WM_CLOSE you can only terminate the application. Everything else would be like lottery.

That said I am against both. What if your PDF opens in a MDI application already showing other documents? Forcing the application to close would make the user lose all changes to the other open documents. And sending a close message to this application would be annoying since the user still needs the other documents opened.

You cannot predict the behavior of every application. And you certainly don't know every application. If the report has the same name then you can tell the user to close the other one with the same name. Otherwise he won't get a new report. Think what would happen if Windows started closing your applications as soon as you try to overwrite a file which is currently in use.

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top