Страница 2 из 4
Добавлено: Вт дек 02, 2014 23:54
Skif_off
MVV
Спасибо, буду пробовать, как доберусь до компа. Кстати, в примерах AutoHotkey после флагов нулевой символ не ставят, в функции на AutoIt тоже, кажется, не стал.
Вообще, производит впечатление своеобразного костыля для совместимости с неюникодными Win9x/Me: откуда я могу знать, какой путь попадётся? Проверять каждый раз, что символы строки не вылезли за диапазон 0-127 не очень удобно.
Добавлено: Ср дек 03, 2014 14:20
MVV
Если конкатенируешь строки, обычно в конце нулевой символ добавляется автоматически. Но однозначно будет не лишним его указать явно, тем более, его необходимо учитывать в длине строки, а завершающий нулевой обычно не включается в длины строк.
А где костыль? Посылай всегда в UTF-8. Функция эта в тотале появилась давно, юникодные пути тогда еще не были в моде, потом была добавлена поддержка юникода с сохранением совместимости.
Добавлено: Ср апр 22, 2015 02:42
LonerD
Подозреваю, что тут ответ можно получить быстрее и понятней, потому повторю свой вопрос.
Как
эту конструкцию использовать внутри своих скриптов?
Например, надо нам узнать Source Path (SP) и передать его какой-то переменной.
Что-то наподобие вот этого
MyVariable := Send_WM_COPYDATA(cmd:="SP")
И ещё - если тут кто-то из AHK-шников заглянет - каким образом команда CD работает? Потому как объяснения Balderstrom весьма туманны.
Добавлено: Ср апр 22, 2015 10:38
Flasher
Там уже вроде как что-то отписали, но больше невнятицы про errorlevel.
Вот
этот скрипт я попробовал на 1.1.05.02, gui возвращает данные. Теперь бы ещё по-отдельности отобразить, только с иероглифами первого значения получилось...
Добавлено: Ср апр 22, 2015 13:43
Skif_off
У меня с 1.1.21.03 ничего не показывает, активную панель скрипт показал только после изменения
Код: Выделить всё
inf:=Asc("G") + 256 * Asc("A")
;на
inf:=Asc("G") + 256 * Asc("W")
С 1.1.05.02 вообще ничего.
Добавлено: Ср апр 22, 2015 13:45
MVV
Skif_off,
Видимо, твоя версия AHK юникодная, поэтому и идентификатор сообщения нужно указывать юникодный.
Добавлено: Ср апр 22, 2015 14:47
Skif_off
MVV
Точно, проглядел
I used autohotkey_L ansi version 1.1.05.01
Юникод рулит, однако.
На AutoIt сразу делал с юникодом.
Добавлено: Ср апр 22, 2015 15:37
LonerD
Flasher писал(а):Там уже вроде как что-то отписали, но больше невнятицы про errorlevel.
Вроде как низзя без перехватчика OnMessage... а как его прервать после получения сообщения - вопрос.
По нажатию хоткея выполняется Send_WM_COPYDATA - формируется запрос Тоталу с заданным параметром.
Далее этот запрос обрабатывается, получается какая-то фигня - строка (иероглиф) CopyDataStruct и этот запрос отправляется Тоталу.
Тотал даёт некий ответ, и висящий в трее AHK отслеживает появление ответа через OnMessage, обрабатывает в Receive_WM_COPYDATA и высвечивает результат...
Как всё это упростить - непонятно.
Добавлено спустя 49 минут:
Ага. Индусский код начинает вырисовываться.
Убираем #Persistent чтобы скрипт не висел постоянно в памяти, убираем горячие клавиши.
Убираем MsgBox, %retVal% и в начале функции Receive_WM_COPYDATA пишем global retVal (назначаем переменную глобальной, то есть результат отправляется в глобальную переменную, которая будет доступна вне скрипта).
Тогда тело скрипта будет выглядет так
Код: Выделить всё
OnMessage(0x4a, "Receive_WM_COPYDATA")
Send_WM_COPYDATA(cmd:="A")
; в переменной retVal - желаемое значение, делаем что хотим с этим значением, и в конце концов завершаем скрипт обязательно через ExitApp
ExitApp
Можно ли ещё проще?
И зачем совет "must have a wait loop arround onMessage in order to receive data from TC"? Ведь если запустить OnMessage внутри цикла, он продолжает висеть в памяти даже после прерывания цикла...
Как прервать OnMessage? Можно ли и нужно ли это делать?
Добавлено: Ср апр 22, 2015 16:12
Flasher
LonerD писал(а):Тогда тело скрипта будет выглядет так
А какого скрипта не хочешь рассказать?
LonerD писал(а):Можно ли ещё проще?
Тут про функции нужно думать, там основной код.
LonerD писал(а):Можно ли и нужно ли это делать?
Думаю, нет необходимости.
Добавлено: Ср апр 22, 2015 16:20
LonerD
Flasher писал(а):LonerD писал(а):Тогда тело скрипта будет выглядет так
А какого скрипта не хочешь рассказать?

Я выше в теме
указал - вот этот
скрипт. Насколько я понимаю, он и есть финальный. Его всё время и пытаюсь "осмыслить" и адаптировать для своих потребностей.
Добавлено: Ср апр 22, 2015 16:30
Flasher
LonerD
Финальный? Это просто вариант. Предыдущый как-то покомпактней смотрится. А тут какие-то навороты отладочные, ну их. Нужно скомпоновать самый наипростейший и компактный вариант с записью в переменную и msgbox для одного значения. В данном случае SС больше всего интересует.
Добавлено: Ср апр 22, 2015 19:29
LonerD
Flasher писал(а):Предыдущый как-то покомпактней смотрится. А тут какие-то навороты отладочные, ну их. Нужно скомпоновать самый наипростейший и компактный вариант с записью в переменную и msgbox для одного значения. В данном случае SС больше всего интересует.
Предыдущий - это
вот этот имеешь в виду?
Не очень-то и компактно, если принять во внимание, что разные команды нужно отсылать - посмотри вначале скрипта конструкцию if A_IsUnicode ... else и доп. функцию StrPutVar
Flasher писал(а):А тут какие-то навороты отладочные, ну их.
Что ты подразумеваешь под отладочными наворотами? Защиту от дурака можно просто убрать (или переделать по-своему).
Для меня туманным остаётся смысл проверки if( A_IsUnicode ). На первый взгляд все AutoHotkey.exe-шники работает и без неё.
Добавлено спустя 48 минут:
В общем, получился вот такой примерчик. Переключение панелей - определяем активную панель, и переходим на другую.
Основная суть достигнута - получено значение retVal использовано дальше в скрипте.
Код: Выделить всё
; #Warn
#NoEnv
#NoTrayIcon
#SingleInstance, Force
;SetBatchLInes, -1
;SendMode, Input
If WinExist("ahk_class TTOTAL_CMD") && WinActive("ahk_class TTOTAL_CMD")
{
WinGet, TCHWND, ID, A
OnMessage(0x4a, "Receive_WM_COPYDATA") ; 0x4a is WM_COPYDATA
Send_WM_COPYDATA(cmd:="A")
if ( retVal = "R" )
SendMessage, 1075, 4001,,, % "ahk_id " TCHWND
else
SendMessage, 1075, 4002,,, % "ahk_id " TCHWND
}
ExitApp
Send_WM_COPYDATA(ByRef cmd, aWinID=0x0)
{
global TCHWND
Critical
if(!RegExMatch(cmd, "^(A|[LRST][PCIN]?)$"))
return
len:=StrLen(cmd) + 1
if( A_IsUnicode ) ; This needs to be done, as TC is expecting
{ ; "chars" for the cmd string.
cmdStr:=cmd
VarSetCapacity(cmd, StrPut(cmd, "cp0"))
Loop, % len
NumPut( Asc(SubStr(cmdStr, A_Index, 1)), cmd, A_Index - 1, "Char")
}
VarSetCapacity(CopyDataStruct, A_PtrSize * 3)
NumPut(Asc("G") + 256 * Asc(A_IsUnicode ? "W" : "A"), CopyDataStruct)
NumPut(len , CopyDataStruct, A_PtrSize)
NumPut(&cmd, CopyDataStruct, A_PtrSize * 2)
SendMessage, 0x4A, %A_ScriptHwnd%, &CopyDataStruct, , % "ahk_id " TCHWND
return ErrorLevel
}
Receive_WM_COPYDATA(wParam, lParam, msg, hwnd)
{
global retVal
retVal:=StrGet(NumGet(lParam + A_PtrSize * 2))
return 1
}
Добавлено: Чт апр 23, 2015 05:19
Flasher
LonerD писал(а):Предыдущий - это вот этот имеешь в виду?
Его.
LonerD писал(а):Не очень-то и компактно
У тебя получилось компактней? Что-то не заметил.
LonerD писал(а):Основная суть достигнута - получено значение retVal использовано дальше в скрипте.
А я как просил? Для SC, SI или SN (типа Send_WM_COPYDATA("SC") | msgbox retVal).
Добавлено: Чт апр 23, 2015 14:27
LonerD
Flasher писал(а):У тебя получилось компактней?
Да, примерно на 8 строк.
Чтобы ещё сократить - в моём варианте можно убрать безболезненно "защиту от дурака"
Код: Выделить всё
if(!RegExMatch(cmd, "^(A|[LRST][PCIN]?)$"))
return
Хотя сейчас посмотрел - почерпнул из того скрипта переменную A_ScriptHwnd, исправил свой скрипт.
Flasher писал(а):А я как просил? Для SC, SI или SN (типа Send_WM_COPYDATA("SC") | msgbox retVal).
Заменить
Send_WM_COPYDATA(cmd:="A")
на желаемое, например
Send_WM_COPYDATA(cmd:="SC").
Входные данные - ByRef, потому не ("SC"), а (cmd:="SC")
Также заменить
if ( retVal = "R" ) и три строки ниже на
msgbox, % retVal
Добавлено: Чт апр 23, 2015 16:18
Flasher
LonerD писал(а):if ( retVal = "R" ) и три строки ниже на
msgbox, % retVal
Хм. Сравнение без %, а вывод с? Как интересно.