Страница 1 из 2

Кнопка вызова "Свойства - Безопасность" объекта под курсором

Добавлено: Пн авг 09, 2010 05:55
HA3APET
Здравствуйте, хотелось бы кнопочку по вызову диалога "Свойства" объекта под курсором и что бы сразу открывалась закладка "Безопасность".

Затем я совмещу эту кнопку с командой cm_EditPersmissionInfo\cm_EditPermissionInfo, что бы на Win2000\XP у нас выполнялась эта команда, а на Win выше открывалась вкладка "Безопасность"

Есть идеи как сделать эту кнопку?

Исправлена опечатка - безопастность.
Моторокер.

Добавлено: Пн авг 09, 2010 10:04
Avada
HA3APET
Идея одна — просить Гислера, чтобы на ОС выше XP по нужной NTFS-команде сразу выполнялось открытие именно того, что позволяет система. Чтобы соответствующая группа cm-команд начиная с Висты опять какую-то пользу приносила. Альтернативы, ИМХО, слишком громоздки и, по большому счёту, могут быть интересны только для сборок.

Добавлено: Пн авг 09, 2010 10:51
MVV
Мысль хорошая. Собственно, вот.

Добавлено: Пн авг 09, 2010 11:12
Avada
MVV
OK. Только лучше было дать предложение по всем трём командам этой группы: cm_EditPermissionInfo, cm_EditAuditInfo и cm_EditOwnerInfo.

Добавлено: Пн авг 09, 2010 13:25
MVV
Добавил.

Добавлено: Пн авг 09, 2010 19:48
HA3APET
ghisler(Author) писал(а):To my knowledge, there is no function to activate the correct tab automatically.
Видимо я захотел невозможного.
Может наши гуру по скриптам смогут это осуществить...

Есть reg-файл добавляющий в контекстное меню объектов команду, которая делает Владельцем текущего пользователя.

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

Windows Registry Editor Version 5.00

[HKEY_CLASSES_ROOT\*\shell\runas]
@="Take Ownership"
"NoWorkingDirectory"=""

[HKEY_CLASSES_ROOT\*\shell\runas\command]
@="cmd.exe /c takeown /f "%1" && icacls "%1" /grant administrators:F"
"IsolatedCommand"="cmd.exe /c takeown /f "%1" && icacls "%1" /grant administrators:F"

[HKEY_CLASSES_ROOT\Directory\shell\runas]
@="Take Ownership"
"NoWorkingDirectory"=""

[HKEY_CLASSES_ROOT\Directory\shell\runas\command]
@="cmd.exe /c takeown /f "%1" /r /d y && icacls "%1" /grant administrators:F /t"
"IsolatedCommand"="cmd.exe /c takeown /f "%1" /r /d y && icacls "%1" /grant administrators:F /t"
Возможно ли сделать кнопку с такой же функцией для выделенного под курсором объекта? Это и будет наша замена для cm_EditOwnerInfo

Добавлено: Пн авг 09, 2010 20:29
Avada
Кстати, Гислер не вполне прав. Точнее, прав он, например, в том смысле, что для разных объектов вкладка "Безопасность" может занимать разное место в общем ряду, а при определённых системных настройках — вовсе отсутствовать. Однако же при запуске в Висте/7 одной из трёх NTFS-команд лучше, если даже она просто откроет системное окно свойств на основной вкладке, чем не будет делать ничего.

Добавлено: Пн авг 09, 2010 20:58
MVV
HA3APET, позаменяй "%1" на %P%N - и будет работать.

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

cmd.exe /c takeown /f %P%N && icacls %P%N /grant administrators:F

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

cmd.exe /c takeown /f %P%N /r /d y && icacls %P%N /grant administrators:F /t
Разумеется, если у тебя есть утилиты/команды takeown и icacls.

Уточню, эти команды делают владельцем не текущего пользователя, а группу администраторов.

Добавлено: Вт авг 10, 2010 13:36
Loopback
HA3APET
В принципе Гислер прав, нет никакой возможности однозначно определить расположение нужной вкладки на разных языках.
Однако, если остановиться на каком-нибудь одном языке, можно пройти по всем вкладкам, получить их заголовки и перейти на нужную.

Скрипт ниже (разумеется, Autoit) это и делает для русского языка. Довольно развесистый, что связано со сложностью получения заголовка таба в другом процессе. Требует модуль Memory.au3, который входит в стандартный дистрибутив Autoit.

При запуске в Vista/7 открывает диалог свойств и переходит на нужную закладку, в других ОС - вызывает стандарную функцию тотала.

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

#include <Memory.au3>

Global $hWnd = _TCHGetActiveInstance()

Global Const $cm_Properties=1003
Global Const $cm_EditPermissionInfo=2200
Global Const $TC_SENDMESSAGE = 0x400 + 51
Global Const $TCM_FIRST = 0x1300
Global Const $TCM_GETITEMW = ($TCM_FIRST + 60)
Global Const $TCM_GETITEMCOUNT = ($TCM_FIRST + 4)
Global Const $TCIF_TEXT = 0x1

If Not ((@OSVersion = "WIN_7") Or (@OSVersion = "WIN_VISTA")) Then
    __TCHSendMessage($hWnd, $TC_SENDMESSAGE, $cm_EditPermissionInfo)
    Exit
EndIf

__TCHSendMessage($hWnd, $TC_SENDMESSAGE, $cm_Properties)

$WinWnd = WinWait("Свойства:", "", 5)
$TabWnd = ControlGetHandle($WinWnd, "", "SysTabControl321")

$nCount = __TCHSendMessage($TabWnd, $TCM_GETITEMCOUNT, 0, 0)
For $i = 0 To $nCount-1
    $sText = _TabGetItemText($TabWnd, $i)
    If $sText = "Безопасность" Then
        For $j =  0 To $i - 1
            ControlCommand($WinWnd, "", $TabWnd, "TabRight", "")
        Next
        Exit
    EndIf
Next

; Вспомогательные функции

Func __TCHSendMessage($hWnd, $nMsg, $wParam = 0, $lParam = 0)
    Local $aResult = DllCall("user32.dll", "int", "SendMessage", "hwnd", $hWnd, "int", $nMsg, "wparam", $wParam, "lparam", $lParam)
	If @error Then Return SetError(@error, @extended, "")
	Return $aResult[0]
EndFunc
 
Func _TCHGetActiveInstance()
    Local $aList = WinList("[CLASS:TTOTAL_CMD]")
    For $i = 1 To $aList[0][0]
        If WinActive($aList[$i][1]) Then Return $aList[$i][1]
    Next
    Return 0
EndFunc

Func _TabGetItemText($hWnd, $iIndex)
    Local $iBuffer = 1024, $iMaxPtrSize = 8
    Local $tItem = DllStructCreate("uint Mask;dword State;dword StateMask;ptr Text;int TextMax;int Image;lparam Param")
    Local $pItem = DllStructGetPtr($tItem)
    Local $iItem = DllStructGetSize($tItem)

    DllStructSetData($tItem, "Mask", $TCIF_TEXT)
    DllStructSetData($tItem, "TextMax", $iBuffer)

    Local $tBuffer = DllStructCreate("wchar Text[" & $iBuffer & "]")
    Local $pBuffer = DllStructGetPtr($tBuffer)

    Local $tMemMap
    Local $pMemory = _MemInit($hWnd, $iItem + $iBuffer * 2 + $iMaxPtrSize, $tMemMap)
    Local $pText = $pMemory + $iItem + $iMaxPtrSize

    DllStructSetData($tItem, "Text", $pText)
    
    _MemWrite($tMemMap, $pItem, $pMemory, $iItem)
    
    Local $iRet = __TCHSendMessage($hWnd, $TCM_GETITEMW, $iIndex, $pMemory)

    _MemRead($tMemMap, $pText, $pBuffer, $iBuffer)
    _MemFree($tMemMap)
    Return DllStructGetData($tBuffer, "Text")
EndFunc

Добавлено: Ср авг 11, 2010 21:56
HA3APET
Loopback
Ещё проблема в том, что некоторые программы вносят свою вкладку в свойства.
Спасибо за скрипт, буду пробовать.

Добавлено: Чт авг 12, 2010 11:03
Loopback
HA3APET писал(а):Ещё проблема в том, что некоторые программы вносят свою вкладку в свойства.
Скрипт это учитывает, поскольку определяет закладку по заголовку.

Добавлено: Чт авг 12, 2010 14:27
HA3APET
Loopback
Спасибо, всё работает. Не понял фразу - "Требует модуль Memory.au3"
Я переконвертировал ваш скрипт в exe, жаль только очень большой по размеру получился 600Kb в несжатом виде.

Добавлено: Чт авг 12, 2010 14:31
Flasher
HA3APET писал(а):Не понял фразу - "Требует модуль Memory.au3"
Этот файл должен быть в папке include для правильной работы скрипта. >>
Loopback писал(а):

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

#include <Memory.au3>

Добавлено: Чт авг 12, 2010 14:55
HA3APET
Flasher
А папка где должна быть тогда?
У меня всё чётко работает... просто сделал из приведённого выше скрипта exe-файл.

Добавлено: Чт авг 12, 2010 15:04
Flasher
HA3APET писал(а):А папка где должна быть тогда?
<PATH>\Autoit\Include\Memory.au3
HA3APET писал(а):просто сделал из приведённого выше скрипта exe-файл
Ну да, и пожаловался на размер. :wink: Любая конвертация в exe-шник(хоть из vbs, хоть из cmd/bat, и из au3 в данном случае) получает размер конечного файла в десятки и сотни раз больший в сравнении с исходным.