Справочник функций

Ваш аккаунт

Войти через: 
Забыли пароль?
Регистрация
Информацию о новых материалах можно получать и без регистрации:

Почтовая рассылка

Подписчиков: -1
Последний выпуск: 19.06.2015

Запуск и управление другими приложениями

8.9K
18 декабря 2004 года
Alaudo
6 / / 18.12.2004
Привет всем!
Меня тут попросили помочь немного, такая задача.

Дано: одна брокерская фирма, в которой брокер приходит утречком и включает комп,
1) запускает первую программу (работает с локальными базами данных), которая выдает модальное окно, не нажав в котором "Ок" дальше ничего не работает.

2) запускает вторую программу, которая связывается с сервером биржи и считывает котировки акций. В то время, как идет соединение, программа показывает песочные часы.

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

Задача: автоматизировать этот процесс, чтобы пользователь получил все три запущенные программы.

Проблемы:
1) Как запустить приложение отдельным процессом? Команда С++ system("application") останавливает выполнение базового приложения до завершение работы дочернего.
2) как нажать "Ок" в модальном окне.
3) как определить, занято ли еще приложение чтением данных (показывает ли песочные часы), или уже нет.

Какие идеи?
368
18 декабря 2004 года
rostyslav
629 / / 13.07.2004
1) Как запустить приложение отдельным процессом?

Запускается C:\prog.exe и устанавливется для него текущим каталог C:\
[COLOR=darkblue]
STARTUPINFO si;
ZeroMemory(&si, sizeof(STARTUPINFO));
si.cb = sizeof(STARTUPINFO);
PROCESS_INFORMATION pi;
BOOL fCreated = CreateProcess(_T("C:\\prog.exe"),
NULL,NULL,NULL,FALSE, CREATE_NEW_CONSOLE, NULL, _T("C:\\"), &si, &pi);[/COLOR]

2) как нажать "Ок" в модальном окне.

Если внутри модального окна, то вызвать OnOK();

А если нужно закрыть со стороны, то если заголовок диалоговое окна напр. "Dialog1", тогда
[COLOR=darkblue]
CWnd *pWnd = FindWindow(NULL, "Dialog1");
if(pWnd!=NULL)pWnd->SendMessage(WM_COMMAND, IDOK, 0);
[/COLOR]
3) как определить, занято ли еще приложение чтением данных (показывает ли песочные часы), или уже нет.

Можно сделать это через события(Event), но для этого нужно изменить код второй программы, чтоб она сгенерировала событие.

Если вторая прога, после считывания сама завершает работу, то верхний код из 1) +сразу же
[COLOR=darkblue]
HANDLE hProcess = pi.hProcess;
WaitForSingleObject(hProcess, INFINITE);
[/COLOR]
и программа будет ждать до тех пор, пока prog.exe не завершит свою работу.
8.9K
18 декабря 2004 года
Alaudo
6 / / 18.12.2004
Спасибо огромное!!!
Перевел все это нашим программистам (на немецкий). У меня осталось еще 2 вопроса:

Цитата:
А если нужно закрыть со стороны, то если заголовок диалоговое окна напр. "Dialog1", тогда
[COLOR=darkblue]


А как узнать имя окна?

Цитата:
Можно сделать это через события(Event), но для этого нужно изменить код второй программы, чтоб она сгенерировала событие.


Это понятно. Проблема в том, что модифицировать другую программу нельзя. И работу она не завершает, а продолжает дальше.
Другими словами: как определить, показывает ли курсор над ней еще песочные часы или нет?

Если так сделать нельзя, то как можно сделать, чтобы программа просто ждала 30-40 секунд?

Спасибо за ответы!!!

368
18 декабря 2004 года
rostyslav
629 / / 13.07.2004
//А как узнать имя окна?

Заголовок окна. Это то что пишется в синей полосе в самом верху. Или на соответствующей кнопке на taskbar. Если это не диалоговое окно, тогда возможно для закрытия нужна будет команда
pWnd->SendMessage(WM_SYSCOMMAND, SC_CLOSE, 0);

//как можно сделать, чтобы программа просто ждала 30-40 секунд?

Sleep(30000);

Если вторая прога открывает файл, в которую записывает данные, с аттрибутом OF_SHARE_EXCLUSIVE или хотя бы OF_SHARE_DENY_WRITE, то можно попытаться в try/catch блоке открыть этот файл для записи через каждые 10 сек.
8.9K
19 декабря 2004 года
Alaudo
6 / / 18.12.2004
Спасибо еще раз за ответы.
Вот ответ наших программистов:

>> CWnd *pWnd = FindWindow(NULL, "Dialog1");
>> if(pWnd!=NULL)pWnd->SendMessage(WM_COMMAND,IDOK, 0);

>ich habe es etwa in der Art programmiert, aber
> es gelingt mir nicht, ein
> ENTER oder IDOK o.д. zu senden. Das einzige,
> was immer klappt, ist, die
> Anwendung per WM_CLOSE zu schliessen.
> An dieser Stelle komme ich einfach nicht mehr weiter.

Перевод:
"Я попытался сделать что-то в этом роде, но мне не удалось послать сообщение ENTER или IDOK. Единственное, что работает, это закрытие окна при помощи команды WM_CLOSE.
С этой точки я не могу сдвинуться.

Цитата:
Заголовок окна. Это то что пишется в синей полосе в самом верху. Или на соответствующей кнопке на taskbar. Если это не диалоговое окно, тогда возможно для закрытия нужна будет команда
pWnd->SendMessage(WM_SYSCOMMAND, SC_CLOSE, 0);


Да, я и имел в виду заголовок, извините.
Я сам работаю не под С++, а в основном под Delphi (что касатеся Windows API, хотя вообще такого рода программированием редко занимаюсь) -- и я помню, что там можно было получать заголовок окна опрашивая массив открытых окон. Можно ли что-то такое сделать и в С++?

Это модальное окно, то есть содержание выбор "Ок" "Отмена". Как его закрыть с кодом завершение IDOK???

Цитата:
Если вторая прога открывает файл, в которую записывает данные, с аттрибутом OF_SHARE_EXCLUSIVE или хотя бы OF_SHARE_DENY_WRITE, то можно попытаться в try/catch блоке открыть этот файл для записи через каждые 10 сек.


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

Спасибо за Вашу помощь, особенно вы выходной день!! Срок сдачи нашей программы -- понедельник, поэтому это так важно :)

368
19 декабря 2004 года
rostyslav
629 / / 13.07.2004
Цитата:
Originally posted by Alaudo
>> CWnd *pWnd = FindWindow(NULL, "Dialog1");
>> if(pWnd!=NULL)pWnd->SendMessage(WM_COMMAND,IDOK, 0);

"Я попытался сделать что-то в этом роде, но мне не удалось послать сообщение ENTER или IDOK. Единственное, что работает, это закрытие окна при помощи команды WM_CLOSE.

Странно. Можно еще запустить Spy. Найти это окно и посмотреть чему равен Control ID кнопки Ok. Напр. если= 0x3E8, то теоретически[COLOR=darkblue]
CWnd *pWnd = FindWindow(NULL, "Dialog1");
if(pWnd!=NULL)pWnd->PostMessage(WM_COMMAND,0x3E8, 0);[/COLOR]
равнозначна нажатию на эту кнопку. В данном случае большой разницы нет, но наверно лучше использовать PostMessage. Это я ошибся.

Цитата:
я помню, что там можно было получать заголовок окна опрашивая массив открытых окон. Можно ли что-то такое сделать и в С++?


EnumWindows перебирает все верхние окна активных приложений.EnumChildWindows находит дочерные окна для заданного окна.

Цитата:
Это модальное окно, то есть содержание выбор "Ок" "Отмена". Как его закрыть с кодом завершение IDOK???


Нужно нажать на ту кнопку. WM_CLOSE закрывает окно с кодом 2(IDCANCEL).

Цитата:
Спасибо за Вашу помощь, особенно вы выходной день!!

Незачто. Дело в том, что я тоже работаю, хочу иметь бОльшой выходной в конце/начала года. :)

8.9K
19 декабря 2004 года
Alaudo
6 / / 18.12.2004
Я передал Ваш ответ, спасибо большое. Вот что пришло в ответ:

Цитата:
Es ist mir inzwischen gelungen, den Befehl

SendMessage(DialogFensterHandle, WM_KEYDOWN, VK_RETURN, 0);

abzusenden und er sendet tatsachlich ein RETURN an die Schaltflache!

Das Problem ist nur, er macht es nur manchmal - das sind die schlimmsten
Fehler. Wenn ich zum Beispiel Windows herunterfahre, es wieder neustarte
und
dann das Programm neustarte - geht es immer. Aber danach geht es manchmal
und manchmal nicht. Ich wei? nicht woran das liegt.


Перевод:
Мне уже удалось послать комманду

SendMessage(DialogFensterHandle, WM_KEYDOWN, VK_RETURN, 0);

и она действительно посылает команду нажатия клавиши "Enter" на клавиатуре.
Проблема сейчас состоит в том, что это получается не всегда -- в этом самое ужасное. Например, когда я выхожу из Виндоуз и снова ее запускаю, затем запускаю мою программу -- это всегда получается. Однако потом иногда получается, а иногда нет. И я не знаю, от чего это зависит.

Можете помочь? Заранее спасибо...

(Если честно, эти немецкие программисты как дети прямо :) )

368
19 декабря 2004 года
rostyslav
629 / / 13.07.2004
Цитата:
Originally posted by Alaudo
Однако потом иногда получается, а иногда нет. И я не знаю, от чего это зависит.


Если кнопка OK не имеет стандартный ID, то у меня как раз этот метод неработает. Окно закрывается, но код который привязан к кнопке не вызывается.

[COLOR=darkred]Им нужно бы запустить Spy и смотреть какие сообщения получает окно.[/COLOR] Тогда может смогут определить, почему иногда не закрывается.

Они узнавали через Spy ControlID Ok кнопки, и отправляли pWnd->PostMessage(WM_COMMAND, ControlID, 0); ???
Я думаю это лучший вариант закрытия диал.окна.

Описание Spy++ есть в MSDN.

8.9K
19 декабря 2004 года
Alaudo
6 / / 18.12.2004
Спасибо, все перевел...
Тем времене пришел еще один вопрос:

----
Meine Frage reduziert sich jetzt nur noch auf die Frage:

Wie finde ich heraus, was SendMessage zurückgegeben hat, ich möchte den Wert
abtesten.

Die restlichen Probleme habe ich alle gelöst.
----
Перевод:
Моя проблема теперь сводится только к одному вопросу:

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

Все остальные проблемы уже решены.

Мне также прислали исходный код, но я думаю, он очень длинный, чтобы его публиковать здесь...
368
19 декабря 2004 года
rostyslav
629 / / 13.07.2004
Цитата:
Originally posted by Alaudo
Как я могу определить, что вернула функция SendMessage, я бы хотел протестировать это значение.


 
Код:
LRESULT lR = pWnd->SendMessage(WM_COMMAND,1002, 0);
char c[12];
itoa(lR, c, 10);
AfxMessageBox(c);

Теоретически LRESULT может быть равен 0(FALSE) или 1(TRUE) если команда была обработана
Реклама на сайте | Обмен ссылками | Ссылки | Экспорт (RSS) | Контакты
Добавить статью | Добавить исходник | Добавить хостинг-провайдера | Добавить сайт в каталог