घर
Top.Mail.Ru Yandeks.Metrika
मंच: "शुरुआती";
वर्तमान संग्रह: 2018.11.04;
डाउनलोड करें: [xml.tar.bz2];

नीचे

CreateProcess का उपयोग करना। बाद में वांछित आकार कैसे दिखाएं इसी तरह की शाखाएँ खोजें


Abcdef123   (2016-09-09 07:36) [0]

नमस्कार स्वामी।
Ситуация такая: Проект1 из главной формы запускается новый проект2 (без синкронизации) и из главной формы вызывается третий проект3 (с синкронизацией - т.е. пока проект3 работает проект2 не должен быть закрыт). После закрытия проекта3 мне надо чтобы на экране была форма проекта2, но почему то всегда активируется форма первого проекта.
Подскажите в каком направлении двигаться? На данный момент я не знаю, то ли параметры CreateProcess не правильные устанавливаю (к примеру, пробовала параметр bInheritHandles ставить True- не помогло), или проблема вообще не в этой функции?
Для информации, я пробовала использовать ShellExecute, в этом случае работает правильно, так как там передается Application.Handle как параметр. Но ShellExecute мне не подходит по другой причине.
Прокомментируйте, пожалуйста.
अग्रिम धन्यवाद
आशा



Игорь Шевченко ©   (2016-09-09 10:31) [1]

कुछ प्रक्रिया के पूरा होने के बाद, सिस्टम किसी भी प्रक्रिया की विंडो को सक्रिय कर सकता है, सबसे अधिक संभावना है कि अंतिम एक जो पूर्ण होने से पहले सक्रिय था। इस तंत्र का CreateProcess पैरामीटर से कोई संबंध नहीं है।



Abcdef123   (2016-09-09 11:47) [2]

To [1] Большое спасибо за ответ. По крайней мере я теперь буду знать, что дело не в CreateProcess.
Насчет активизиции последнего окна, то что вы написали - логически я так и думала, но почему то в моей ситуации это не работает. Я даже пыталась
कोशिश
CreateProcess(....)
आखिरकार
Application.Mainform.Setfocus;  //не помогло
समाप्त
А можно как-то форсировать активацию нужного окна если известен Handle этой формы или по Application.Handle? Если да, то как?



Игорь Шевченко ©   (2016-09-09 13:04) [3]


> Если да, то как?


SetForegroundWindow, но в вашем случае, нужно, чтобы окно появлясь на переднем плане по завершении процесса, а не после его создания. Кроме всего прочего, SetForegroundWindow не обязательно приводит к появлению окна на переднем плане, возможно, будет мигать кнопкой в таскбаре вместо появления.


> Проект1 из главной формы запускается новый проект2 (без
> синкронизации) и из главной формы вызывается третий проект3
> (с синкронизацией - т.е. пока проект3 работает проект2 не
> должен быть закрыт).


У вас оба процесса проект2 и проект3 запускаются из одного Проект1 ? А то непонятно.



sniknik ©   (2016-09-09 13:23) [4]

> Я даже пыталась
> Application.Mainform.Setfocus;  //не помогло
эээ... а выше вроде про другой процесс было, а тут фокус форме из своего процесса-приложения.

> Если да, то как?
я делал свое событие которое посылал из одной проги в другую, а там уж ловил и "подымал" нужную форму.
иначе, (SetForegroundWindow), все как то неправильно работало, в разных "осях", на XP как задумывалось. в висте игнорировало, в семерке "мигало в таскбаре"...
в итоге эта неопределенность и привела к собственному "велосипеду" с событием.
+
с событием тоже есть "заморочки", их нужно разрешать... типа (as is)
VistaMessagesEnable([WM_SELFRESTORE, WM_SYSCOMMAND]); //разрешим "подьем" формы извне, в висте и выше. + команды системы для Aero Shake и т.д.

procedure VistaMessagesEnable(const Values: array of Cardinal);
var
 DLLHandle: THandle;
 ChangeWindowMessageFilter: function(msg: Cardinal; dwFlag : Word): BOOL; stdcall;
 i: integer;
begin
 DLLHandle:=  LoadLibrary("user32.dll");
 if DLLHandle > 0 then
   try
     //иначе как говорят не будет проходить сообщение в программу, в висте/вин7 из-за UAC (будет виста проверим)
     @ChangeWindowMessageFilter:= GetProcAddress(DLLHandle, "ChangeWindowMessageFilter");
     if @ChangeWindowMessageFilter <> nil then //в XP функции нет, поэтому статически подключить не получится, только динамически
       for i:= 0 to High(Values) do
         ChangeWindowMessageFilter(Values[i], 1);
   finally
     FreeLibrary(DLLHandle);
   end;
end;



Abcdef123   (2016-09-12 04:58) [5]

[3]
> У вас оба процесса проект2 и проект3 запускаются из одного
> Проект1 ? А то непонятно.

Я прошу прощения, что написала не понятно насчет трех проектов. Идет линейно - из главной формы первого проекта вызывается второй проект, а потом из главной формы второго проекта вызывается проект 3. Связь между первым и вторым проектом необязательна (без синхронизации), то есть после открытия второго проекта можно закрыть первый проект. А вот связь между вторым и третьим должна быть синхронизирована, то есть пока открыт третий проект второй проект не должен закрываться. То есть третий проект работает "модально" в каком то смысле.
Для вызова третьего проекта во втором проекте я пишу так
   try
     Application.MainForm.Enabled := False;
     <здесь вызывается экзешник третьего проекта с помощью  СreateProcess >
   finally
     Application.MainForm.Enabled := True;  //это имеется в виду главная форма второго проекта, после того как третий проект закрыли
     Application.MainForm.SetFocus;
    //здесь попробовала применить виша советы про SetForegroundWindow - не помогло, еще пробовала применить здесь совет [5] вызвать VistaMessagesEnable - не помогло тоже.
   end;




Abcdef123   (2016-09-12 05:04) [6]

To [4] Насчет вашего совета, я пробовала применить, пожалуйста, посмотрите мое сообщение выше. Возможно я не там примерила вызов вашей процедуры VistaMessagesEnable?
Кстати, я работаю в D2007 и у меня не находит флаг WM_SELFRESTORE, я заменила на WM_MDIRESTORE (это все что я нашла по смыслу интуитивно). Может поэтому не сработало?



sniknik ©   (2016-09-12 08:55) [7]

> еще пробовала применить здесь совет [5] вызвать VistaMessagesEnable - не помогло тоже.
разрешение покататься на машине <> езда на машине... где у меня вообще про замену вызова SetForegroundWindow на VistaMessagesEnable? логика меняется, в принципе.
> событие которое посылал из одной проги в другую, а там уж ловил и "подымал" нужную форму.
где у тебя обработчик события?

> Возможно я не там примерила вызов вашей процедуры VistaMessagesEnable?
впечатление, что вообще не читал "совета".

> не находит флаг WM_SELFRESTORE
это мое событие "самовостановления", юзерское, про которое в [5] словами.

> пока открыт третий проект второй проект не должен закрываться.
в этом случае все можно сделать проще, у программ есть код возврата, и ожидания завершение. помню еще бат файлы писали, с реакцией по коду возврата т.е. ожиданием завершения вызываемой программы... дельфя не быт файл, возможностей больше, значит также можно сделать. ищи по куду завершения программы.



Игорь Шевченко ©   (2016-09-12 11:28) [8]


> А вот связь между вторым и третьим должна быть синхронизирована,
>  то есть пока открыт третий проект второй проект не должен
> закрываться. То есть третий проект работает "модально" в
> каком то смысле.


Хотелось бы увидеть как вы вызываете и обеспечиваете "модальность" одного процесса по отношению к другому. Тот код, который приведен в [5] этого не показывает.

Но дело еще в том, что в Windows процессы друг от друга независимы, поэтому сдается мне, что ваше требование о "модальности" несколько искусственно и идет вразрез с той самой идеологией.
О задаче подробнее расскажите, может, есть более гуманные способы ?



Leonid Troyanovsky ©   (2016-09-12 19:03) [9]


> Abcdef123   (12.09.16 04:58) [5]

> закрыть первый проект. А вот связь между вторым и третьим
> должна быть синхронизирована, то есть пока открыт третий
> проект второй проект не должен закрываться. То есть третий
> проект работает "модально" в каком то смысле.

Для того, чтобы понять что можно, а что нельзя читаем msdn.

Соберем воедино restrictions для SetForegroundWindow & AllowSetForegroundWindow :

A process can set the foreground window only if one of the following conditions is true:

The process is the foreground process.
The process was started by the foreground process.
The process received the last input event.
There is no foreground process.
The foreground process is being debugged.
The foreground is not locked (see LockSetForegroundWindow).
The foreground lock time-out has expired (see SPI_GETFOREGROUNDLOCKTIMEOUT in SystemParametersInfo).
The foreground process is not a Modern Application or the Start Screen (from SWF restriction)
No menus are active.

Что, IMHO, читать надо так:
"Нет активных меню, а одно из следующих условий истинно: .."

Используя оную таблицу легко разобрать любые цепочки
взаимодействий приложений.

Ну, а для того, чтобы сделать результат гарантированным следует
поискать более "гуманные способы". Например, объединить три
проекта в один, и разворачивать его в требуемой последовательности.

--
सादर, LVT



Abcdef123   (2016-09-13 12:28) [10]

[8]
> Хотелось бы увидеть как вы вызываете и обеспечиваете "модальность"
> одного процесса по отношению к другому.

मैं इसे इस तरह से कॉल करता हूं:
ExecuteProcess(AExeFile + " "+AExtraParams,SW_SHOWNORMAL,0,true);где сама фунция ExecuteProcess вот:
function ExecuteProcess(FileName: string; Visibility: Integer; BitMask: Integer; Synch: Boolean): Longword;
var
 zAppName: array[0..512] of Char;
 zCurDir: array[0..255] of Char;
 WorkDir: string;
 StartupInfo: TStartupInfo;
 ProcessInfo: TProcessInformation;
 Closed: Boolean;
begin
 Closed := True;
 StrPCopy(zAppName, FileName);
 GetDir(0, WorkDir);
 StrPCopy(zCurDir, WorkDir);
 FillChar(StartupInfo, SizeOf(StartupInfo), #0);
 StartupInfo.cb := SizeOf(StartupInfo);
 StartupInfo.dwFlags := STARTF_USESHOWWINDOW;
 StartupInfo.wShowWindow := Visibility;
 if not CreateProcess(nil,
   zAppName,
   nil,
   nil,
   False,
   CREATE_NEW_CONSOLE or
   NORMAL_PRIORITY_CLASS,
   nil,
   nil,
   StartupInfo,
   ProcessInfo)
   then Result := WAIT_FAILED
 else
 begin
   if (Synch = True) then
     begin
       Closed:= False;
       repeat
         case WaitForSingleObject(
           ProcessInfo.hProcess, 100) of
             WAIT_OBJECT_0 : Closed:= True;
             WAIT_FAILED : RaiseLastWin32Error;
         end;
         Application.ProcessMessages;
       until (Closed);
       GetExitCodeProcess(ProcessInfo.hProcess, Result);
       CloseHandle(ProcessInfo.hProcess);
       CloseHandle(ProcessInfo.hThread);
     end
   else
     begin
       Result := 0;
     end;
 end;
end;


और के बारे में
> "модальности" несколько искусственно

я согласна с вами.
> О задаче подробнее расскажите, может, есть более гуманные
> способы
Если коротко о причине, то в зависимости от клиента нам надо "собирать" отдельные фукциональности (проекты) в один проект, в то же время, некоторые пользователи хотят всё. Вот в данном примере, нам нужна возможность запускать третий проект как чать второго проекта. В что же время, чтоб оставалась возможность предоставить третий проект кому то как отдельную единичную задачу.



Игорь Шевченко ©   (2016-09-13 17:02) [11]


> Если коротко о причине


Коротко не надо, расскажите длинно. Может, вам проще проекты в виде DLL/BPL оформить и управлять сущностями в одном приложении.

Когда вы запускаете программу из-под отладчика в среде, то вы ожидаете, что по завершении программы фокус вернется к среде. Однако и это не всегда происходит, так что, мне кажется, с мечтой о модальности и управлением фокусом между процессами лучше проститься сразу.



sniknik ©   (2016-09-14 07:58) [12]

repeat
 case WaitForSingleObject(ProcessInfo.hProcess, 100) of
   WAIT_OBJECT_0 : Closed:= True;
   WAIT_FAILED : RaiseLastWin32Error;
 end;
 Application.ProcessMessages; //вот причина почему твоя "псевдомодальность" не работает, убери это
until (Closed);

ну и в конце этой процедуры, ставь фокус, если он еще будет нужен.

ты как то определись с логикой, и пиши либо линейно либо событийно... во втором случае ProcessMessages = ошибка, т.к. это попытка совместить несовместимое.



Abcdef123   (2016-09-15 05:04) [13]

[11]
> Коротко не надо, расскажите длинно. Может, вам проще проекты
> в виде DLL/BPL оформить и управлять сущностями в одном приложении.
>

Честно признаться, про это направление "DLL/BPL" имею только теоретическое представление. Так что даже не знаю, в этом случае подходит ли. Конечно, очень бы хотелось узнать ваше мнение по этому направлению, даже если это не мой случай. (в будущем пригодится тогда). Если у вас будет возможность написать, буду очень признательна.
Итак, если подробнее, то схема такая:
Первый проект по смыслу никак не связан со вторым и третьим. Просто из главного меню по клику запускается второй проект
Проект второй и третий имеют смысловую связь и работают с одними и теми же данными (таблицами).
Второй проект это всего лишь главная форма с главным меню, из которого вызываются проекты третьего типа, а также всякого рода отчеты.
Проекты третьего типа все типичны, созданы по одному макету (даже названия файлов одинаковое) - это форма ввода данных, из этой формы можно запустить листинг отчет (по кнопке) и дата модуль. Не знаю, важно или нет, для информации- этот же отчет (я имею в виду файл -форму ввода) используется и во втором проекте.
यहाँ, शायद, यह सब है।



Abcdef123   (2016-09-15 05:46) [14]

To [12] Спасибо, большое. Это действительно помогло. Правда поведение "псевдомодальности" изменилось (раньше форма проекта 2 была не доступна, в смысле никакой реакции, если кликнуть, а сейчас если кликнуть, то форма становится "серой" и в заголовке формы добаваляетс (Not Responding). В принципе, всё правильно, просто пользователей может это "напугать" с непривычки.
Поскольку проектом уже пользуются, я остановлюсь на этом варианте!
А если поступит ответ на [11]->[13], то, возможно в следующей версии перепишу всё.
Преогромное всем спасибо за отзывы, комментарии и советы!!! И за большое терпение отдельное огромное спасибо sniknik и Игорь Шевченко!



पन्ने: 1 पूरी शाखा

मंच: "शुरुआती";
वर्तमान संग्रह: 2018.11.04;
डाउनलोड करें: [xml.tar.bz2];

ऊपर









मेमोरी: 0.65 एमबी
समय: 0.034 c
2-1473404951
Valya
2016-09-09 10:09
2018.11.04
संकेत


2-1474184193
एलेक्स सेरोव
2016-09-18 10:36
2018.11.04
पासवर्ड के तहत एक्सेल टेबल कैसे खोलें?


2-1473395811
Abcdef123
2016-09-09 07:36
2018.11.04
CreateProcess का उपयोग करना। बाद में वांछित आकार कैसे दिखाएं


2-1474009068
उपयोगकर्ता
2016-09-16 09:57
2018.11.04
HTML फॉर्म भरना


2-1474206922
KropotkinGosha
2016-09-18 16:55
2018.11.04
फ़ंक्शन में कोड निष्पादित नहीं किया गया है





अफ्रीकी अल्बानियन अरबी भाषा अर्मेनियाई आज़रबाइजानी बस्क बेलारूसी बल्गेरियाई कैटलन सरलीकृत चीनी) चीनी पारंपरिक) क्रोएशियाई चेक डेनिश डच अंग्रेज़ी एस्तोनियावासी फिलिपिनो फिनिश फ्रेंच
गैलिशियन् जॉर्जियाई जर्मन यूनानी हाईटियन यहूदी हिंदी हंगरी आइसलैंड का इन्डोनेशियाई आयरिश इतालवी जापानी कोरियाई लात्वीयावासी लिथुआनियाई मेसीडोनियन मलायी मोलतिज़ नार्वेजियन
फ़ारसी पोलिश पुर्तगाली रोमानियाई रूसी सर्बियाई स्लोवाक स्लोवेनियाई स्पेनिश स्वाहिली स्वीडिश थाई तुर्की यूक्रेनी उर्दू वियतनामी वेल्श यहूदी बंगाली बोस्नियाई
सिबुआनो एस्पेरांतो गुजराती हौसा हमोंग ईग्बो जावानीस कन्नड़ खमेर लाओ लैटिन माओरी मराठी मंगोलियन नेपाली पंजाबी सोमाली तामिल तेलुगु योरूबा
ज़ुलु
Английский Французский Немецкий Итальянский Португальский Русский Испанский