![]() |
| ||
|
|
Новости |
Поиск |
FAQ |
Статьи |
Книги |
Новости VCL
| | Форумы ЧАТ |
Орешник |
|
| |||
| |||
« предыдущая ветвь | форум | следующая ветвь »
Как из второго экземпляра программы послать первому сообщение?... [D6, Win2k]
Dinara © (2002-07-31 23:29:00)... просто о том, что второй экземпляр запущен?
nick_sniper (2002-08-01 02:43:00) [1]Извини за большой код, но:
Unit1:
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,
StdCtrls, Buttons, VCLutils;
type
TMyMainForm = class(TForm)
BitBtn1: TBitBtn;
Label1: TLabel;
Label2: TLabel;
procedure BitBtn1Click(Sender: TObject);
procedure FormClose(Sender: TObject; var Action: TCloseAction);
private
{ Private declarations }
public
{ Public declarations }
procedure DefaultHandler(var Message); override;
end;
var
MyMainForm: TMyMainForm;
var
FirstProgram : Boolean;
ActivePrograms : Integer;
WM_ProgActivate : Cardinal;
WM_ProgDeactivate : Cardinal;
procedure CheckActive;
implementation
{$R *.DFM}
procedure CheckActive;
const
MessText1 : PChar = "WM_ProgActivate";
MessText2 : PChar = "WM_ProgDeactivate";
begin
ActivePrograms := 0;
WM_ProgActivate := RegisterWindowMessage(MessText1);
WM_ProgDeactivate := RegisterWindowMessage(MessText2);
if (FindPrevInstance(TMyMainForm.ClassName,"MyMainForm") <> 0) then begin
FirstProgram := False;
SendMessage(HWND_BROADCAST,WM_ProgActivate,0,0); //
DenKop (2002-08-01 01:26:00) [2]Упустил самое главное, в твоём случае вместо строк
begin Result:=True;Exit;end;вставляешь PostMessage(Wnd,Своё_сообщение);
DenKop (2002-08-01 01:24:00) [3]Я делал это примерно так:
function VerCopyProg:Boolean;
VAR
Wnd : hWnd;
buff: ARRAY [0..127] OF Char;
begin
Result:=False;
Wnd := 1;
WHILE Wnd <> 0 DO
BEGIN
IF (Wnd <> Application.Handle) AND
(IsWindowVisible(Wnd)or False) AND
((GetWindow(Wnd, gw_Owner) = 0)or False) AND
(GetWindowText(Wnd, buff, sizeof(buff)) <> 0)
THEN
BEGIN
GetWindowText(Wnd, buff, sizeof(buff));
if StrPas(buff)="Здесь Caption гдавной формы" then
begin Result:=True;Exit;end;
END;
Wnd := GetWindow(Wnd, gw_hWndNext);
END;
end;
Если программа уже запущена функция вернёт True.
Dinara (2002-08-01 00:25:00) [4]nick_sniper, можно поподробнее - куда что пихать?
Суть в чем - запускается первая копия, работает. Потом вторую запускают с параметром. Она кое-что делает, потом обнаруживает мьютекс и завершается. И надо как-нибудь сделать так, чтобы первый экземпляр узнал о том, что второй кое-что сделал.
Какой час уже с этим мучаюсь :(((
nick_sniper (2002-08-01 00:05:00) [5]Можно использовать модуль VCLutils из RxLib. Там есть такие прекрасные функции, как:
function FindPrevInstance(const MainFormClass, ATitle: string): HWnd;
function ActivatePrevInstance(const MainFormClass, ATitle: string): Boolean;
И сделать что-то типа:
wnd := FindPrevInstance(...);
if wnd <> 0 then begin
PostMessage(wnd,...);
Application.Terminate; // Если нужен только один экземпляр программы
end;
VID (2002-07-31 23:54:00) [6]Зато "Примитивный вариант" позволяет посылать разные сообщения от одной копии другой, что расширяет сферу приминения этого метода...
:)
VID (2002-07-31 23:52:00) [7]Кстати, после прочтения файла Message.txt и выполнения указанных действия, программа, выполнившая действия, должна ОЧИСТИТЬ ФАЙЛ Message.txt, т.е. удалить обе строки.
Этим достигается большая стабильность работы программы, т.к. если содержимое файла не будут очищено, а пользователь вручную откорректирует этот файл, и отменив свои корректировки, сохранит этот файл, то одна из программ, снова выполнит действия, связанные с сообщеним второй строки.
Это конечно всё маловероятно, но возможно.
Странный Прохожий (2002-07-31 23:47:00) [8]Mutex лучше :o)
VID (2002-07-31 23:45:00) [9]Примитивный вариант:
Т.к. речь идёт фактически об одной и той же программе, то можно сделать так:
в папке расположения проги создать подпапку и файл:
.../MSG/Message.TXT
Программа отслеживает изменения (запись) файлов в папке MSG
Как только поступил сигнал об изменения какого-нибудь файла в папке MSG, программа читает первые две строки файла Message.txt
А теперь реализация сабжа:
В необходимый момент вторая копия проги записывает в файл, message.txt две строки:
1 - Application.Handle
2 - Строку сообщения
Сразу же , ОБЕ проги обнаружив изменение файла, прочтут его первые две строки. Пусть S1 - первая строка, а S2 - вторая.
И сделают проверку:
IF StrTOInt(S1)<>Application.Handle then
begin
//необходимые действия, связанные с сообщением S2
end;
В результате, одна прога (копия), ничего не сделает (т.к. Application.Handle = S1), а первая - выполнит необх. действия.
Всё.
Странный Прохожий (2002-07-31 23:41:00) [10]Можно создать именованый Mutex.
Второй экземпляр при запуске может проверять его наличие/отсутствие.