Autorun

Обсуждение только плагинов и утилит для Total Commander.

Модераторы: Avada, CaptainFlint, Nik, d-view, Моторокер

Аватара пользователя
Orion9
Сообщения: 1283
Зарегистрирован: Пн янв 01, 2024 17:18

Сообщение Orion9 »

FallenAngel писал(а):Понаблюдаю.
Если ТС сам закрывается (на что может указывать запись в логе), это плохо. С чего бы ему самому закрываться? Если только скрипт какой-то чудит ... А monkey business от маестро хорошо известен: клик по невидимой кнопке (окну) триала приводит к описанному вами явлению.
FallenAngel писал(а):Нужно понять, это глобальный баг или что-то частное.
Больше похоже на первое, чем на второе. Судя из описания, скрипт меняет %Path% на уровне пользователя

Код: Выделить всё

pathman.ps1. Добавляет \ удаляет каталог в пользовательскую переменную %PATH%. Поддерживает пакетный режим.
А это приводит к отправке сообщения WM_SETTINGCHANGE
Когда вы нажимаете «ОК» в системном диалоговом окне переменных сред, Windows отправляет специальное широковещательное сообщение WM_SETTINGCHANGE всем открытым окнам [1]. Некоторые среды разработки (IDE), продвинутые эмуляторы терминалов (например, VS Code, Fleet, или некоторые плагины для Windows Terminal) перехватывают это сообщение [1]. Вместо того чтобы просто проигнорировать его, они пытаются «помочь» пользователю: динамически перечитывают актуальные переменные из реестра и полностью перезаписывают ими текущий %PATH% вашего процесса.В результате все временные пути, которые вы добавляли локально внутри процесса (например, через скрипты или код), бесследно стираются.
Судя по всему, тотал перехватывает сообщение WM_SETTINGCHANGE и заново перечитывает переменные окружения, что приводит к сбросу изменений, сделанных через Autorun.

Проверить можно

Код: Выделить всё

# WM_WININICHANGE
SetMessageAction /P 0x001A "WinIniCallback"	

Func WinIniCallback(hWnd, uMsg, wParam, lParam)
    MsgBox(GetEnv("path"), "WM_WININICHANGE", 48+4096)
    If lParam <> 0 Then SendMessage(AUTORUN_TCHANDLE, 0x001A, 0, 0)
EndFunc
Сначала приходит системное сообщение (пути еще не успели измениться тоталом). Второе сообщение отсылает сам Autorun — пути сброшены.

Не знаю, что вам с этим делать. Наверное, можно отказаться пока от скрипта, это самый простой вариант. Добавлять нужные пути только через Autorun :)
Аватара пользователя
Orion9
Сообщения: 1283
Зарегистрирован: Пн янв 01, 2024 17:18

Сообщение Orion9 »

FallenAngel
Проверил на таких командах в PowerShell

Код: Выделить всё

# Получаем текущий ПОЛЬЗОВАТЕЛЬСКИЙ Path из реестра
$oldUserPath = [Environment]::GetEnvironmentVariable("PATH", "User")

# Формируем новую строку, добавив ваш путь через точку с запятой
$newUserPath = "$oldUserPath;C:\MyFolder"

# Записываем обновленный список обратно в профиль пользователя
[Environment]::SetEnvironmentVariable("PATH", $newUserPath, "User")
Да, теперь точно можно сказать, что SetEnvironmentVariable служит триггером для WM_SETTINGCHANGE, на которое реагирует тотал. Можно, конечно, следить за этим из Autorun, но стоит ли. По-моему, проще совсем отказаться от SetEnv /A PATH и менять переменные окружения из ps1 скрипта.
FallenAngel
Сообщения: 47
Зарегистрирован: Вт дек 30, 2025 20:01

Сообщение FallenAngel »

Orion9
Да, тут понимание пришло. Пока не знаю что "лучше", а что нет.
Надо обдумать.
Аватара пользователя
Orion9
Сообщения: 1283
Зарегистрирован: Пн янв 01, 2024 17:18

Сообщение Orion9 »

FallenAngel
Как-то сразу в голову не пришло, но оказывается, как говорил Вицин, все уже [s]украдено[/s] придумано за нас )

[cut][Configuration]
UpdateEnv=3

Wincmd.ini Version: 7.02

Определяет, должен ли TC в текущем сеансе работы автоматически обновлять свои переменные при обнаружении изменённых и/или новых системных переменных . Можно суммировать следующие значения:

1: Следить за изменением системных переменных с автообновлением своих переменных.

2: Учитывать не только изменённые, но и новые системные переменные.

По умолчанию: 3 (1+2, автоматически обновляются все указанные переменные). При значении 0 функция слежения за системными переменными отключена: TC не реагирует на их изменение и/или добавление.

ПРИМЕЧАНИЯ:

По умолчанию Total Commander при получении системного уведомления WM_SETTINGCHANGE сравнивает свои переменные окружения с глобальными, после чего считывает изменённые и новые системные переменные. Эта информация может быть использована и в запущенных из TC дочерних процессах.

Установка значения ключа в 0 может оказаться полезна, например, при тестировании программ с разными настройками переменных (в т.ч. с помощью пакетных файлов).

Следует учесть, что если какие-либо переменные окружения удалены в системе, они всё равно сохраняются в работающем TC. (Это вынужденное поведение, в противном случае были бы потеряны также собственные переменные TC и его плагинов.)

Управлять переменными из TC в ручном режиме с возможностью избирательного изменения, добавления или удаления позволяет FS-плагин Environment Variables Ex.

Используйте клавиши CTRL+B, чтобы просуммировать нужные вам значения.[/cut]
Не знаю, какую из этого можно извлечь пользу, но хоть что-то.
Аватара пользователя
Orion9
Сообщения: 1283
Зарегистрирован: Пн янв 01, 2024 17:18

Сообщение Orion9 »

AkulaBig
Кажется, теперь стало понятно, что за неприятные косяки у вас творились с переменными окружения. Причину вы нашли сами, инструкции Pragma Include действительно была ни при чем. Я проверил у себя. Консольная команда SetX тоже запускает WM_SETTINGCHANGE, как и команда PowerShell SetEnvironmentVariable. В результате строка в Autorun

Код: Выделить всё

ShellExec /SW_HIDE /WAIT %COMSPEC% '/c setx OIT_DATA_PATH "%COMMANDER_PATH%"'
приводит к сбросу переменных окружения.

В общем, это не баг. Фича, которой можно пользоваться.
AkulaBig
Сообщения: 638
Зарегистрирован: Ср дек 03, 2008 11:48

Сообщение AkulaBig »

Orion9 писал(а):В общем, это не баг. Фича, которой можно пользоваться.
Понятно. Будем знать.
Я тут для swf сделал скрипт через ExifTool, чтобы еще от одного плагина уйти. В планах и другие расширения обработать. Дак вот. Я решил, что временные файлы должны иметь другое название, чтобы с документами не засекаться. А оказывается должны использовать для всех скриптом одни и те-же файлы. Иначе -stay_open не работает.
Сейчас думаю как еще одну проблему решить. И там и там использую дату создания, модификации файлов. И непонятно, как использовать дату в двух разных скриптах. Получается надо писать скрипт для общих данных что ли.
Аватара пользователя
Orion9
Сообщения: 1283
Зарегистрирован: Пн янв 01, 2024 17:18

Сообщение Orion9 »

AkulaBig писал(а):Понятно. Будем знать.
Да, можно просто переставить строчку с SetX в самое начало, чтобы она не рушила уже объявленные переменные, и вроде так должно работать. Правда надо еще посмотреть, что при перезапуске ТС будет происходить, но это уже другое дело.

Добавлено спустя 12 минут:
AkulaBig писал(а): Получается надо писать скрипт для общих данных что ли.
Я бы и рад что-то по делу написать, но откуда мне это знать? :lol:

Юзайте ИИ, он ведь реально вывозит!
AkulaBig
Сообщения: 638
Зарегистрирован: Ср дек 03, 2008 11:48

Сообщение AkulaBig »

Orion9 писал(а):Я бы и рад что-то по делу написать, но откуда мне это знать?
Сделал уже. Отдельный скрипт для общих данных решил проблему. Собственно почему я здесь это пишу. Для Ауторан сами алгоритмы будут точно такими-же.
Аватара пользователя
Orion9
Сообщения: 1283
Зарегистрирован: Пн янв 01, 2024 17:18

Сообщение Orion9 »

AkulaBig писал(а):Для Ауторан сами алгоритмы будут точно такими-же.
Разумеется. Autorun это практически тот же Autohotkey или AutoIt, конечно алгоритмы будут такими же. При этом Autohotkey намного ближе по синтаксису, поэтому с него проще переводить код, полученный от ИИ.

Недели 2-3 назад я спрашивал у болвана за DllCall в Autorun, тогда он мне ответил, что Autorun его не поддерживает, но сейчас спросил и... :shock:

[cut="плагин Autorun для Total Commander поддерживает DllCall?"]Да, плагин Autorun для Total Commander поддерживает функцию DllCall. [1]
Возможность прямого вызова функций из динамических библиотек (DLL) была официально добавлена автором плагина в одном из крупных обновлений. Это нововведение позволило пользователям отказаться от создания сторонних утилит или сложных костылей ради одного-двумя вызовов WinAPI. [1]

## Особенности работы с DllCall в Autorun

* Прямой вызов WinAPI: С помощью этой функции можно напрямую обращаться к системным библиотекам Windows (например, user32.dll, kernel32.dll).

* Пример использования: Теперь в скриптах конфигурации autorun.cfg можно проверять состояние клавиш (например, нажата ли клавиша CapsLock или Shift) напрямую через системные функции, не прибегая к блокировкам или сторонним хукам. [2]

* Область видимости: Внедрение DllCall совпало с улучшением логики работы переменных окружения. Локальные и глобальные переменные плагина корректно изолируются, что упрощает передачу параметров в DLL и обработку возвращаемых значений. [1]

Если вы хотите детально настроить вызовы под конкретную задачу, дайте знать:

* Какую конкретную функцию WinAPI или сторонней DLL вы планируете вызвать?
* Какое действие (сворачивание, проверка системных параметров, управление окнами) должен выполнять скрипт?

Я смогу подсказать корректный синтаксис для вашего файла конфигурации autorun.cfg.[/cut]
Т.ч. двери открыты, дамы и господа! :mrgreen: Но не всё так просто. На предложение перевести вот этот код с Autohotkey, он выкинул какой-то мусор:

Код: Выделить всё

 WriteLine(text) {
        rawString := text "`r`n"
        bufLen := StrPut(rawString, "UTF-8")
        buf := Buffer(bufLen, 0)
        StrPut(rawString, buf, "UTF-8")
        
        ; Отправляем байты напрямую в канал процесса через WinAPI WriteFile
        DllCall("WriteFile", "Ptr", this.hPipe, "Ptr", buf, "UInt", bufLen - 1, "UInt*", &bytesWritten := 0, "Ptr", 0)
    }
[cut]

Код: Выделить всё

В скриптах плагина Autorun для Total Commander перевод этого AHK-кода будет выглядеть значительно проще. Плагин автоматически умеет выделять буферы и конвертировать строки в UTF-8, что избавляет вас от необходимости вручную вызывать аналоги StrPut и создавать структуры Buffer(). [1] 
Ниже представлен готовый перевод логики вашей функции в формат файла конфигурации autorun.cfg:
## Готовый код для autorun.cfg

# Предполагается, что переменная hPipe уже содержит хэндл вашего канала (Pipe)

# 1. Формируем строку с переносом каретки и переводом строки
SetEnv text_raw "%text%%CRLF%"

# 2. Вызываем WriteFile напрямую
# Autorun сам сконвертирует текстовую переменную в UTF-8 при использовании типа "utf8"
DllCall("WriteFile", "handle", %hPipe%, "utf8", %text_raw%, "dword", -1, "dword*", bytesWritten, "ptr", 0)

## Разбор ключевых изменений и упрощений:

   1. Автоматический подсчет длины: В типе параметра "utf8" плагина Autorun можно передать -1 в качестве размера данных (dword), если строка оканчивается нулевым байтом. Функция сама определит длину строки.
   2. Тип данных "utf8": Вместо ручного выделения памяти через Buffer и кодирования с помощью StrPut, в Autorun встроен тип параметра "utf8" (или "string" для ANSI/Unicode в зависимости от версии, но "utf8" строго указывает на нужную вам кодировку). Он берет строку, налету создает под неё байтовый буфер, отправляет в функцию WinAPI и сам же очищает память.
   3. Регистронезависимые типы: В Autorun используются стандартные типы данных для DllCall, аналогичные системным: "handle" вместо "Ptr" для дескрипторов, "dword" вместо "UInt", и "dword*" для получения количества записанных байт в переменную bytesWritten. [1] 
   4. Константа %CRLF%: Для добавления переноса строки (r`n из AHK) в Autorun используется встроенная системная переменная окружения %CRLF%.

Если вам необходимо собирать этот код внутри локальной секции (функции) или требуется инициализировать хэндл самого пайпа (hPipe) через CreateFile / CallNamedPipe — напишите, я помогу составить полную цепочку вызовов!
[/cut]
Т.ч. увы — пока только на собственный драйвер руки.sys придётся расчитывать.
AkulaBig
Сообщения: 638
Зарегистрирован: Ср дек 03, 2008 11:48

Сообщение AkulaBig »

Orion9
А у меня очередная проблема. Если после использования вид просмотра не переключить (то-есть, например из Документы в Краткий) и попытаться просмотреть другие пользовательские колонки, то они не показываются. Но общие колонки (у меня даты) показываются. Думал надо попробовать завершить процесс. Не помогло. Опять не знаю, что делать.
AkulaBig
Сообщения: 638
Зарегистрирован: Ср дек 03, 2008 11:48

Сообщение AkulaBig »

Уф, решил проблему. Решение к этой теме не относится.
Аватара пользователя
Orion9
Сообщения: 1283
Зарегистрирован: Пн янв 01, 2024 17:18

Сообщение Orion9 »

AkulaBig
Погодите. Лето на носу, какая может быть разработка? Время отдыхать и расправлять морщины. Autorun подождет :D
FallenAngel
Сообщения: 47
Зарегистрирован: Вт дек 30, 2025 20:01

Сообщение FallenAngel »

Мда, тихо тут совсем. Уже и лето пролететь успело...
Аватара пользователя
Orion9
Сообщения: 1283
Зарегистрирован: Пн янв 01, 2024 17:18

Сообщение Orion9 »

FallenAngel писал(а):Мда, тихо тут совсем. Уже и лето пролететь успело...
А что должно было случиться? :lol:
AkulaBig
Сообщения: 638
Зарегистрирован: Ср дек 03, 2008 11:48

Сообщение AkulaBig »

Orion9
Есть интересные тестирования. Если вы не против, завтра начнем переписку. Исключительно по Авторан.
Ответить