![]() |
| ||
|
|
Новости |
Поиск |
FAQ |
Статьи |
Книги |
Новости VCL
| | Форумы ЧАТ |
Орешник |
|
| |||
| |||
« предыдущая ветвь | форум | следующая ветвь »
Не могу разобраться ... [D5]
Solod © (2002-03-14 03:58:00)Функция
WinExec(запуск архиватора ARJ с созданием архива, содержащего 2 файла),SW_HIDE)
архивирует только один первый файл если далее стоит
if MessageDlg()
помогите позжайлуста.
Solod (2002-03-19 14:04:00) [1]Ура, спосибо!!!
Solod (2002-03-19 14:04:00) [2]Ура, спасибо!!!
Song (2002-03-19 13:22:00) [3]Uses ShellApi не помогает?
Solod (2002-03-19 11:10:00) [4]Ладно, я плюнул на свои эксперименты и пробую полностью вставить Ваш код. Компилятор не знакет TShellExecuteInfo. В чем дело?
Song (2002-03-19 08:26:00) [5]Что описать?
Просто вставьте процедурку и всё будет работать. Ok, если не работает, то что именно?
Solod (2002-03-19 04:37:00) [6]Song>
Если можешь, опиши при помощи CreateProcess.
Я пробовал вклеить, что-то не получается.
Solod (2002-03-14 11:44:00) [7]Еще не проверил, но ,все равно, большое СПАСИБО за полный и ясный ответ!
Song (2002-03-14 11:14:00) [8]:))
А почему WinExec должен что-то ждать?
У Вас инструкции следуют одна за другой и они все выполняются одна за другой. Когда Вы запускаете WinExec она в свою очередь запускает ShellExecute, которая запускает ваше приложение в отдельномпроцессе. А выполнение же Вашей основной программы продолжается как прежде (почитайте статью о потоках и процессах на этом сайте).
Вы бы могли убедиться в этом, просто заменив SW_HIDE на SW_SHOWNORMAL и увидите, что процесс архиватора работает, а сообещение, предусмотренное в MessageDlg уже вывелось.
Поэтому проблема в следующем: так процесс arj.exe был для Вас скрыт, то Вы видя сообщение в MessageDlg и решив, что архиватор типа уже закончил работу, преспокойно заершали работу своего приложения, однако arj.exe выполняемый в отдельном потоке не успевал ещё сархивировать второй файл и обрывался. Поэтому второй файл не был добавлен. Однако если MessageDlg не выводилось то выполнение текущей процедуры заканчивалось, и управление основным процессом отдавалось снова главной форме. Вот здесь почему всё работало ok, я не уверен.
Чтобы написать процедуру, которая будет ждать выполнения процесса arj.exe поместите следующий текст:
Procedure TForm5.CrProcess(S:String);
Var SeInfo:TShellExecuteInfo;
ExecuteFile:String;
ExitCode:DWord;
Begin
ExecuteFile:="arj.exe;
FillChar(SEInfo,SizeOf(SEInfo),0);
With SEInfo Do
Begin
cbSize:=SizeOf(TShellExecuteInfo);
fmask:=SEE_MASK_NOCLOSEPROCESS;
Wnd:=Application.Handle;
lpFile:=PChar(ExecuteFile);
lpParameters:=PChar(S);
lpDirectory:=PChar(TempPath);
nShow:=SW_HIDE;
End;
IF ShellExecuteEx(@SEInfo) then
Repeat
Application.ProcessMessages;
GetExitCodeProcess(SEInfo.hProcess,ExitCode);
Until(ExitCode<>STILL_ACTIVE) or (Application.Terminated) else MessageDlg("Ошибка создания внешнего процесса.",mtError,[mbAbort],0);
End;
И программа будет ждать пока вызываемый процесс не закончит свою работу или не прервётся по ошибке.
Всё бы Ok, но недавно писав такую задачу и именно для arj.exeу меня не получилось это сделать. Вот почему: по какой-то причине arj.exe по завершению работы не выходит по коду ExitCode=STILL_ACTIVE и прога висит, думая, что процесс всё ещё выполняется. У меня работало всё, но только не arj.exe. Поэтому, если у Вас будет такая же ситуация замените концовку кода на следующий отрывок:
....
IF ShellExecuteEx(@SEInfo) then
Repeat
Application.ProcessMessages;
GetExitCodeProcess(SEInfo.hProcess,ExitCode);
IF FindWindow(nil,"(Сеанс завершен) - Arj")<>0 then
Begin
SendMessage(FindWindow(nil,"(Сеанс завершен) - Arj"),WM_CLOSE,0,0);
Application.ProcessMessages;
Break;
End;
Until False else MessageDlg("Ошибка создания внешнего процесса.",mtError,[mbAbort],0);
И тогда всё будет Ok. Уф, наконец-то. :))
Solod (2002-03-14 10:45:00) [9]Интересно, а почему MessageDlg не ждет WinExec.
Объясните поподробнее.
Вод код:
if MessageDlg(текст, [mbYes, mbNo], 0)=mrYes thenтексттекст
begin
if CopyFile(PStr1, PStr2, False) then MessageDlg(, )текст
else MessageDlg(();
end
Спасибо за отклик.
Song (2002-03-14 10:08:00) [10]MessageDlg в твоём случае не будет ждать до тех пор пока WinExec завершит свою работу, поэтому процесс архивации блокируется чем-то, стоящим после MessageDlg. Приведи больший кусок кода.
Solod (2002-03-14 09:32:00) [11]Дело в том, что строка "arj a -e C:\ARJ\arh.arj C:\FILES\file1.DBF C:\FILES\file2\DBF" обрабатывается нормально,
если я убираю далее стоящее if MessageDlg()=mrYes then ...
Иначе - оба файла архивируются в первый раз, после запуска приложения, а далее в архив попадает только первый файл.
Короче происходит что-то не понятное.
Song (2002-03-14 08:39:00) [12]приведи кокнкретную строку стоящую в WinExec только не ту, которую ты приводил раньше с нагромождением всяких функций, а транслируй её в текст при трассировке и напиши здесь. Кстати, может после этого сам найдёшь свою ошибку.