Имя пользователя:
Пароль:  
Помощь | Регистрация | Забыли пароль?  | Правила  

Компьютерный форум OSzone.net » Программирование, базы данных и автоматизация действий » AutoIt » [решено] Внутренняя связь между двумя "файлами" написанных на AutoIT

Ответить
Настройки темы
[решено] Внутренняя связь между двумя "файлами" написанных на AutoIT

Аватара для FlatX007

Ветеран


Сообщения: 553
Благодарности: 87

Профиль | Отправить PM | Цитировать


Допустим есть 2 утилиты выполняющие некоторые функции ... как можно сделать связь между ними , то есть одна программа получает данные а другая отображает. Через чтение и запись INI файла очень неустраивает!!
Нужна "связь" неоставляющая видимых следов

Мона как нито ? ...

Отправлено: 21:10, 15-05-2009

 

Аватара для beve

Старожил


Сообщения: 307
Благодарности: 137

Профиль | Отправить PM | Цитировать


Как один из вариантов (если обе утилитки написанны на Autoit), можно сделать невидимый контрол в одной из утилиток (или у двоих), например Edit, и потом просто отсылать в него сообщения, и соответственно Через соответствующую функцию отслеживать "приходящие сообщения".

-------
Не в кількості знань полягає освіта, а в повному розумінні і вмілому використанні того, що знаєш.

Это сообщение посчитали полезным следующие участники:

Отправлено: 21:38, 15-05-2009 | #2



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

Если же вы забыли свой пароль на форуме, то воспользуйтесь данной ссылкой для восстановления пароля.


Аватара для Yashied

Старожил


Сообщения: 206
Благодарности: 88

Профиль | Отправить PM | Цитировать


Цитата FlatX007:
Допустим есть 2 утилиты выполняющие некоторые функции ... как можно сделать связь между ними , то есть одна программа получает данные а другая отображает. Через чтение и запись INI файла очень неустраивает!!
Нужна "связь" неоставляющая видимых следов »
Например с помощью WM_COPYDATA. Подойдет?

Вот тебе пример. Откомпилируй его и запусти EXE-файл два раза.

Код: Выделить весь код
#Include <GUIConstantsEx.au3>

Opt('WinTitleMatchMode', 3)

global const $TITLE_SENDER = '#Sender'
global const $TITLE_RECEIVER = '#Reseiver'
global const $WM_COPYDATA = 0x004A

global $sMsg, $Dummy, $Flag = 0

if WinExists($TITLE_RECEIVER) then
    if WinExists($TITLE_SENDER) then
        exit
    endif
    _Sender()
else
    _Receiver()
endif

func _Sender()

    local $Input, $Button, $ID

    GUICreate($TITLE_SENDER, 400, 100)
    $Input = GUICtrlCreateinput('', 20, 20, 360, 20)
    $Button = GUICtrlCreateButton('Send', 165, 60, 70, 23)
    $Dummy = GUICtrlCreateDummy()
    GUIRegisterMsg($WM_COPYDATA, '_WM_COPYDATA')
    GUISetState()

    while 1
        $ID = GUIGetMsg()
        switch $ID
            case 0
                continueloop
            case $GUI_EVENT_CLOSE
                _SendData(WinGetHandle($TITLE_RECEIVER), '@exit')
                exitloop
            case $Button
                $sMsg = GUICtrlRead($Input)
                $hWnd = WinGetHandle($TITLE_RECEIVER)
                if (not @error) and ($sMsg > '') then
                    if _SendData($hWnd, $sMsg) then
                        GUICtrlSetState($Button, $GUI_DISABLE)
                    endif
                endif
            case $Dummy
                GUICtrlSetState($Button, $GUI_ENABLE)
        endswitch
    wend

    GUIDelete()
endfunc

func _Receiver()
    GUICreate($TITLE_RECEIVER)
    GUIRegisterMsg($WM_COPYDATA, '_WM_COPYDATA')

    while 1
        Sleep(10)
        if $Flag then
            if $sMsg = '@exit' then
                exitloop
            endif
            $Flag = 0
            _DoSomething($sMsg)
            _SendData(WinGetHandle($TITLE_SENDER), '')
        endif
    wend

    GUIDelete()
endfunc; _Receiver

func _DoSomething($sData)
    MsgBox(0, 'Message', $sData)
endfunc; _DoSomething

func _SendData($hWnd, $sData)

    local $tCOPYDATA, $tMsg

    $tMsg = DllStructCreate('char[' & StringLen($sData) + 1 & ']')
    DllStructSetData($tMsg, 1, $sData)
    $tCOPYDATA = DllStructCreate('dword;dword;ptr')
    DllStructSetData($tCOPYDATA, 2, StringLen($sData) + 1)
    DllStructSetData($tCOPYDATA, 3, DllStructGetPtr($tMsg))
    $Ret = DllCall('user32.dll', 'lparam', 'SendMessage', 'hwnd', $hWnd, 'int', $WM_COPYDATA, 'wparam', 0, 'lparam', DllStructGetPtr($tCOPYDATA))
    if (@error) or ($Ret[0] = -1) then
        return 0
    endif
    return 1
endfunc; _SendData

func _WM_COPYDATA($hWnd, $msgID, $wParam, $lParam)

    local $tCOPYDATA = DllStructCreate('dword;dword;ptr', $lParam)
    local $tMsg = DllStructCreate('char[' & DllStructGetData($tCOPYDATA, 2) & ']', DllStructGetData($tCOPYDATA, 3))

    $sMsg = DllStructGetData($tMsg, 1)

; For Sender
    GUICtrlSendToDummy($Dummy)

; For Receiver
    $Flag = 1

    return 0
endfunc; _WM_COPYDATA

Последний раз редактировалось Yashied, 15-05-2009 в 21:50.

Это сообщение посчитали полезным следующие участники:

Отправлено: 21:39, 15-05-2009 | #3


Аватара для proxy

Старожил


Сообщения: 460
Благодарности: 152

Профиль | Отправить PM | Цитировать


Или попробуйте эту udf - можно создать внешний ассоциируемый массив, который может использовать оба скрипта.
К примеру, если скрипт1 запускает скрипт2 то он может передовать указатель "этого" массива, и все будет ок.

Либо как сказал beve.
Скрытые элемнты, и каждые 10-20 vctr считывать из них данные. По анализу данных выполнять необходимые действия.

-------
Мысли-читатель сломался, может подробней расскажите?
А где исходный код? Или мы стихи обсуждаем?! )) Настройки темы > Решено ?

Это сообщение посчитали полезным следующие участники:

Отправлено: 23:41, 15-05-2009 | #4


Аватара для Yashied

Старожил


Сообщения: 206
Благодарности: 88

Профиль | Отправить PM | Цитировать


Цитата proxy:
Или попробуйте эту udf - можно создать внешний ассоциируемый массив, который может использовать оба скрипта.
К примеру, если скрипт1 запускает скрипт2 то он может передовать указатель "этого" массива, и все будет ок. »
Ну это уже совсем экзотика, к тому же написан на COM. Проще тогда уж использовать STDIN и STDOUT. А чем WM_COPYDATA не устраивает, большинство програм так общаются.
Это сообщение посчитали полезным следующие участники:

Отправлено: 23:58, 15-05-2009 | #5


Аватара для Yashied

Старожил


Сообщения: 206
Благодарности: 88

Профиль | Отправить PM | Цитировать


Вот еще один пример. Messages.au3 можешь скачать здесь.

Код: Выделить весь код
#Include <EditConstants.au3>
#Include <GUIConstantsEx.au3>
#Include <GUIEdit.au3>
#Include <GUISlider.au3>
#Include <StaticConstants.au3>
#Include <WindowsConstants.au3>

#Include <Messages.au3>

#NoTrayIcon

if StringLower(StringRight(@ScriptFullPath, 3)) = 'au3' then
    MsgBox(64, 'Messages UDF Library Demonstration', 'To run this script, you must first compile it and then run the (.exe) file.')
    exit
endif

Opt('MustDeclareVars', 1)

if $CmdLine[0] = 0 then
    ShellExecute(@ScriptFullPath, '1')
    ShellExecute(@ScriptFullPath, '2')
    ShellExecute(@ScriptFullPath, '3')
    exit
endif

local $Form, $Input1, $Input2, $Radio1, $Radio2, $Radio3, $ButtonSend, $Edit, $Slider, $Check

switch $CmdLine[1]
    case '1', '2', '3'
        _Main(Int($CmdLine[1]))
    case else

endswitch

func _Main($Index)

    local $GUIMsg, $nScript, $Data, $Timer = _MsgTimerInterval(0)

    $Form = GUICreate('Script' & $Index, 324, 384, (@DesktopWidth - 1018) / 2 + ($Index - 1) * 344, (@DesktopHeight - 440) / 2, BitOR($WS_CAPTION, $WS_SYSMENU), $WS_EX_TOPMOST)

    GUISetFont(8.5, 400, 0, 'Tahoma', $Form)

    GUICtrlCreateLabel('Message:', 14, 22, 48, 14)
    $Input1 = GUICtrlCreateInput('', 64, 19, 246, 20)
    GUICtrlCreateLabel('Send to:', 14, 56, 48, 14)

    GUIStartGroup()

    $Radio1 = GUICtrlCreateRadio('Script1', 64, 56, 56, 14)
    GUICtrlSetState(-1, $GUI_CHECKED)
    $Radio2 = GUICtrlCreateRadio('Script2', 130, 56, 56, 14)
    $Radio3 = GUICtrlCreateRadio('Script3', 196, 56, 56, 14)

    $ButtonSend = GUICtrlCreateButton('Send', 236, 88, 75, 23)
    GUICtrlSetState(-1, $GUI_DEFBUTTON)
    GUICtrlCreateLabel('', 14, 128, 299, 2, $SS_ETCHEDHORZ)
    GUICtrlCreateLabel('Received message:', 14, 142, 98, 14)
    $Edit = GUICtrlCreateEdit('', 14, 160, 296, 129, BitOR($ES_READONLY, $WS_VSCROLL, $WS_HSCROLL))
    GUICtrlSetBkColor(-1, 0xFFFFFF)
    GUICtrlCreateLabel('Timer interval (ms):', 14, 316, 98, 14)
    $Slider = GUICtrlCreateSlider(110, 312, 162, 26, BitOR($TBS_AUTOTICKS, $WS_TABSTOP))
    GUICtrlSetLimit(-1, 20, 1)
    GUICtrlSetData(-1, $Timer / 50)
    _GUICtrlSlider_SetTicFreq(-1, 1)
    $Input2 = GUICtrlCreateInput($Timer, 274, 313, 36, 20, $ES_READONLY)
    GUICtrlSetBkColor(-1, 0xFFFFFF)
    $Check = GUICtrlCreateCheckBox('Enable receiver', 14, 354, 96, 19)
    GUICtrlSetState(-1, $GUI_CHECKED)

    Opt('GUICloseOnESC', 0)

    GUISetState()

    _MsgRegister('Script' & $Index, '_Receiver')

    while 1
        $GUIMsg = GUIGetMsg()
        select
            case $GUIMsg = $GUI_EVENT_CLOSE
                exit
            case $GUIMsg = $ButtonSend
                for $i = $Radio1 to $Radio3
                    if GUICtrlRead($i) = $GUI_CHECKED then
                        $nScript = 1 + $i - $Radio1
                        exitloop
                    endif
                next
                $Data = GUICtrlRead($Input1)
                if StringStripWS($Data, 3) = '' then
                    $Data = '(empty)'
                endif
                if _IsReceiver('Script' & $nScript) then
                    _MsgSend('Script' & $nScript, 'From Script' & $Index & ':  ' & $Data)
                endif
            case $GUIMsg = $Slider
                _MsgTimerInterval($Timer)
            case $GUIMsg = $Check
                if GUICtrlRead($Check) = $GUI_CHECKED then
                    GUICtrlSetState($Edit, $GUI_ENABLE)
                    GUICtrlSetBkColor($Edit, 0xFFFFFF)
                    GUICtrlSetState($Slider, $GUI_ENABLE)
                    GUICtrlSetState($Input2, $GUI_ENABLE)
                    _MsgRegister('Script' & $Index, '_Receiver')
                else
                    GUICtrlSetState($Edit, $GUI_DISABLE)
                    GUICtrlSetBkColor($Edit, $GUI_BKCOLOR_TRANSPARENT)
                    GUICtrlSetState($Slider, $GUI_DISABLE)
                    GUICtrlSetState($Input2, $GUI_DISABLE)
                    _MsgRegister('Script' & $Index, '')
                endif
        endselect
        $Data = GUICtrlRead($Slider) * 50
        if BitXOR($Data, $Timer) then
            $Timer = $Data
            GUICtrlSetData($Input2, $Timer)
        endif
    wend
endfunc; _Main

func _Receiver($sMessage)
    _GUICtrlEdit_AppendText($Edit, $sMessage & @CRLF)
    return 0
endfunc; _Receiver
Это сообщение посчитали полезным следующие участники:

Отправлено: 00:16, 16-05-2009 | #6


Аватара для FlatX007

Ветеран


Сообщения: 553
Благодарности: 87

Профиль | Отправить PM | Цитировать


Цитата Yashied:
Например с помощью WM_COPYDATA. Подойдет?
Вот тебе пример. Откомпилируй его и запусти EXE-файл два раза. »
Типа в одно GUI вводим текст а другой "GUI" его отображает ?
А как в краце это работает для чего какая функция ?

Отправлено: 00:31, 16-05-2009 | #7


Аватара для Yashied

Старожил


Сообщения: 206
Благодарности: 88

Профиль | Отправить PM | Цитировать


Одно окно посылает сообщение WM_COPYDATA другому. В параметрах сообщения передаешь свои данные. Окно-приемник получает это сообщение через зарегистрированную функцию GUIRegisterMsg(). Обратно прердача идет анологичным образом.

Отправлено: 00:55, 16-05-2009 | #8


Аватара для Yashied

Старожил


Сообщения: 206
Благодарности: 88

Профиль | Отправить PM | Цитировать


FlatX007, постараюсь объяснить на примере моего UDF. Вот простой пример программы-приемника:

Код: Выделить весь код
#Include <Messages.au3>

Global $MyMessage = ''

_MsgRegister('Receiver', '_Receiver')

While 1
    Sleep(10)
; Проверяем наличие сообщения
    If $MyMessage > '' Then
; Здесь выполняем произвольный код, сообщение находится в переменной $MyMessage
        MsgBox(0, '', $MyMessage)
; Очищаем сообщение
        $MyMessage = ''
    EndIf
WEnd

Func _Receiver($sData)
    $MyMessage = $sData
    Return 0
EndFunc; _Receiver
Первым делом регистрируешь функцию для приема сообщений, здесь я ее назвал _Receiver(). Первый параметр - это произвольное (уникальное) имя, на твое усмотрение.

Код: Выделить весь код
_MsgRegister('Receiver', '_Receiver')
Далее в цикле проверяешь наличие нового сообщения. Как только сообщение будет получено ($MyMessage > ''), выполняешь необходимые действия и очищаешь сообщение ($MyMessage = ''). Надеюсь понимаешь для чего это нужно. Функция-приемник (_Receiver()) выполняется, когда приходят сообщения. Она просто передает переменной $MyMessage данные, которые ей были переданы. Для передачи сообщения из другого скрипта просто пишешь следующее:

Код: Выделить весь код
_MsgSend('Receiver', 'Текст сообщения')
Здесь первый параметр должен в точности соответствовать первому параметру у функции _MsgRegister(). Это идентификатор твоего приемника. Вот и все. Конечно, правильнее будет организовать передачу в дуплексном режиме. Например: приемник получает очередное сообщение обрабатывает его и в ответ посылает ответное сообщение, мол все OK, давай дальше. И только после этого ты посылаешь следующее сообщение, и т.д. Описание других функций из этого UDF можешь прочесть в самом файле. Все, пойду спать, устал.


Последний раз редактировалось Yashied, 16-05-2009 в 02:24.

Это сообщение посчитали полезным следующие участники:

Отправлено: 02:06, 16-05-2009 | #9


Аватара для Creat0R

Must AutoIt


Moderator


Сообщения: 3047
Благодарности: 1005

Профиль | Сайт | Отправить PM | Цитировать


Ох этих методов море развелось, вот ещё пару:

* AddControls_Interaction.zip - Добавление новых элементов с внешнего скрипта.
* UDF - «AU3_INTERACT.au3» (второй пример) - Удобная интеракция между скриптами через сообщения (SendMessage).

-------
“Сделай так просто, как возможно, но не проще этого.”... “Ты никогда не решишь проблему, если будешь думать так же, как те, кто её создал.”

Альберт Эйнштейн

P.S «Не оказываю техподдержку через ПМ/ICQ, и по email - для этого есть форум. ©»

Русское сообщество AutoIt | CreatoR's Lab | Opera AC Community

Это сообщение посчитали полезным следующие участники:

Отправлено: 11:10, 16-05-2009 | #10



Компьютерный форум OSzone.net » Программирование, базы данных и автоматизация действий » AutoIt » [решено] Внутренняя связь между двумя "файлами" написанных на AutoIT

Участник сейчас на форуме Участник сейчас на форуме Участник вне форума Участник вне форума Автор темы Автор темы Шапка темы Сообщение прикреплено

Похожие темы
Название темы Автор Информация о форуме Ответов Последнее сообщение
Интерфейс - [решено] Как удалить папку "Моя музыка","Мои Картинки", "Мое видео"? verdix Microsoft Windows 2000/XP 3 03-10-2009 23:46
Debian/Ubuntu - [решено] Пропали кнопки "свернуть","закрыть","во весь екран" в папках Alex.sys Общий по Linux 5 02-04-2009 11:13
Wireless - Связь между двумя точками доступа Asus и Linksys sol-minor Сетевое оборудование 0 05-02-2009 12:48
[решено] Какая разница между "Сигнатурный анализ" и "Эвристический анализ"? verdix Хочу все знать 3 10-11-2008 23:50
Запретить/удалить пункт "Programs" ("Программы") из меню кнопки "Start" ("Пуск") submaster Microsoft Windows NT/2000/2003 5 13-09-2006 12:29




 
Переход