Дополнительная клавиатура c функциональными клавишами

При верстки сайтов и написании PHP и JS кода, много времени тратится на повторение конструкций – теги, стили, операторы и т.д. Emmet в несколько раз ускоряет процесс, но подходит только для верстки. Хочется большего, например обварачивание строк выделенного текста нужными тегами, вставка из буфера сразу в нужном виде и вставка готовых заготовок кода.

Прочитав статью на Хабре «Использование POS-клавиатуры для решения рутинных задач» пришла идея взять обычную клавиатуру т. к. POS-клавиатура крупногабаритная и не дешевая. И запрограммировать клавиши своими действиями для HTML, JS, CSS, MySQL, PHP, a раскладку клавиш распечатать на самоклейке.

И вот была куплена обычная USB- клавиатура:

Клавиатура OKLICK

Чтобы нарисовать все кнопки с сохранением пропорций при последующей печати, клавиатура была отсканирована обычным МФУ в два захода и соединена в одну картинку. Далее эта «фотка» использовалась как подложка.

В процессе составления списка команд выяснилось что клавиш не хватает и придется использовать дополнительные сочетания клавиш с Ctrl и Win. Клавиша Fn аппаратная и компьютер ее не считывает.

Так же было решено оставить клавиши Tab, Enter, Backspace и пробел чтобы иметь возможность исправить ошибку не возвращая руку на основную клавиатуру.

И вот результат:

Исходник keyboard-src.png в Adobe Fireworks CS5.

Далее все кнопки были вырезана и наклеены на клавиши клавиатуры, чтобы со временем тонер не стирался дополнительно был наклеен скотч:

С программами для назначения клавишам своих функций возникла проблема – все они «из коробки» не распознают с какой клавиатуры была нажата клавиша. Но решение было найдено – AutoHotkey с расширением AutoHotInterception.

AutoHotInterception (AHI) использует драйвер перехвата и позволяет выполнять код AutoHotkey в ответ на события от определенной клавиатуры или мыши.

Установка AutoHotkey и AutoHotInterception

1. Скачать и установить AutoHotkey.

2. Скачать драйвер Interception и распаковать архив (для удобства в корень диска C:\).

3. Для установки драйвера нужно запустить cmd.exe от имени администратора из директории C:\windows\system32. И выполнить команды:

cd: c\Interception\command line installer
install-interception.exe /install

Установка драйвера Interception

4. Скачать и распаковать архив AutoHotInterception.zip c AutoHotInterception, также в корень диска C:\.

5. Скопировать два dll файла из Interception в AutoHotInterception:

C:\Interception\library\x64\interception.dll в C:\AutoHotInterception\Lib\x64\interception.dll
C:\Interception\library\x86\interception.dll в C:\AutoHotInterception\Lib\x86\interception.dll

6. В директории C:\AutoHotInterception\Lib запустить файл Unblocker.ps1 от имени администратора (установка драйвера).

Индификация дополнительной клавиатуры

Нужно узнать VID/PID клавиатуры, для этого потребуется скомпилировать скрипт C:\AutoHotInterception\Monitor.ahk в AHK и запустить Monitor.exe.

Нажимая клавиши на клавиатурах можно определить ID новой клавиатуры.

Определение ID клавиатуры
В данном случаи новая клавиатура имеет ID: 2

Принцип работы AutoHotInterception

AutoHotInterception предлагает несколько вариантов перехвата клавиш на второй клавиатуре:

1. Context mode – работает не стабильно, примерно 1 раз из 10 перехват не срабатывает.

2. Subscription mode – все клавиши на выбранной клавиатуре перестают выполнять свои стандартные действия, работает только перехватчик – что и нужно.

Отслеживание нажатой клавиши в AHK-скрипте происходит следующим способом:

#include Lib\AutoHotInterception.ahk
AHI := new AutoHotInterception()
keyboardId := AHI.GetKeyboardId(0x1A2C, 0x4094, 1)
AHI.SubscribeKeyboard(keyboardId, true, Func("KeyEvent"))

KeyEvent(code, state){
	ToolTip % "Keyboard Key - Code: " code ", State: " state
}
AHK

Далее в скрипте keyboard.ahk всем клавишам по скан-коду были назначены необходимые команды.

; version 2.3

#NoEnv
#Warn
SendMode Input
#Persistent 

#include Lib\AutoHotInterception.ahk
AHI := new AutoHotInterception()
keyboardId := AHI.GetKeyboardId(0x1A2C, 0x4094, 1)
AHI.SubscribeKeyboard(keyboardId, true, Func("KeyEvent"))

EMAIL = mail@example.com

CTRL_KEY = 0
WIN_KEY = 0

; & to $amp;
EncodeHTML(String, Flags := 1)
{
    SetBatchLines, -1
    static TRANS_HTML_NAMED := 1
    static TRANS_HTML_NUMBERED := 2
    static ansi := ["euro", "#129", "sbquo", "fnof", "bdquo", "hellip", "dagger", "Dagger", "circ", "permil", "Scaron", "lsaquo", "OElig", "#141", "#381", "#143", "#144", "lsquo", "rsquo", "ldquo", "rdquo", "bull", "ndash", "mdash", "tilde", "trade", "scaron", "rsaquo", "oelig", "#157", "#382", "Yuml", "nbsp", "iexcl", "cent", "pound", "curren", "yen", "brvbar", "sect", "uml", "copy", "ordf", "laquo", "not", "shy", "reg", "macr", "deg", "plusmn", "sup2", "sup3", "acute", "micro", "para", "middot", "cedil", "sup1", "ordm", "raquo", "frac14", "frac12", "frac34", "iquest", "Agrave", "Aacute", "Acirc", "Atilde", "Auml", "Aring", "AElig", "Ccedil", "Egrave", "Eacute", "Ecirc", "Euml", "Igrave", "Iacute", "Icirc", "Iuml", "ETH", "Ntilde", "Ograve", "Oacute", "Ocirc", "Otilde", "Ouml", "times", "Oslash", "Ugrave", "Uacute", "Ucirc", "Uuml", "Yacute", "THORN", "szlig", "agrave", "aacute", "acirc", "atilde", "auml", "aring", "aelig", "ccedil", "egrave", "eacute", "ecirc", "euml", "igrave", "iacute", "icirc", "iuml", "eth", "ntilde", "ograve", "oacute", "ocirc", "otilde", "ouml", "divide", "oslash", "ugrave", "uacute", "ucirc", "uuml", "yacute", "thorn", "yuml"]
    static unicode := {0x20AC:1, 0x201A:3, 0x0192:4, 0x201E:5, 0x2026:6, 0x2020:7, 0x2021:8, 0x02C6:9, 0x2030:10, 0x0160:11, 0x2039:12, 0x0152:13, 0x2018:18, 0x2019:19, 0x201C:20, 0x201D:21, 0x2022:22, 0x2013:23, 0x2014:24, 0x02DC:25, 0x2122:26, 0x0161:27, 0x203A:28, 0x0153:29, 0x0178:32}

    if !A_IsUnicode && !(Flags & TRANS_HTML_NAMED)
        throw Exception("Parameter #2 must be omitted or 1 in the ANSI version.", -1)
    
    out  := ""
    for i, char in StrSplit(String)
    {
        code := Asc(char)
        switch code
        {
            case 10: out .= "<br>`n"
            case 34: out .= "&quot;"
            case 38: out .= "&amp;"
            case 60: out .= "&lt;"
            case 62: out .= "&gt;"
            default:
            if (code >= 160 && code <= 255)
            {
                if (Flags & TRANS_HTML_NAMED)
                    out .= "&" ansi[code-127] ";"
                else if (Flags & TRANS_HTML_NUMBERED)
                    out .= "&#" code ";"
                else
                    out .= char
            }
            else if (A_IsUnicode && code > 255)
            {
                if (Flags & TRANS_HTML_NAMED && unicode[code])
                    out .= "&" ansi[unicode[code]] ";"
                else if (Flags & TRANS_HTML_NUMBERED)
                    out .= "&#" code ";"
                else
                    out .= char
            }
            else
            {
                if (code >= 128 && code <= 159)
                    out .= "&" ansi[code-127] ";"
                else
                    out .= char
            }
        }
    }
    return out
}

; Количество табов в начале строк
get_tabs(text)
{
	tabs := 0
	Loop, parse, text, `n,`r 
	{
		StringReplace, _, A_LoopField, `t,, UseErrorLevel
		tabs := ErrorLevel
	}
	rows := ""
	Loop, %tabs%
	{
		rows .= "`t" 
	}
	return rows
}

; Получение выделенного текста
get_selected()
{
	global WIN_KEY
	if (WIN_KEY == 1) {
		return %Clipboard%
	}

	ClipSaved := ClipboardAll
    clipboard := ""
    Send, ^{sc02E}  ; ctrl+c
    ClipWait, 0.2
    clip_content := clipboard
    
	Clipboard := ClipSaved
    if DllCall("IsClipboardFormatAvailable", "uint", 1) {
		return clip_content
    } else if DllCall("IsClipboardFormatAvailable", "uint", 15) {
        MsgBox Clipboard contains files.	
		return ""
    } else {
		return clip_content
	}
}

; Вывод текста через буфер (так быстрее и проще отменить вставку)
send_text(text, back)
{
	clipboard_tmp := ClipboardAll
	Clipboard := text
	sleep 50
    Send, ^{sc02F}  ; ctrl+v
    sleep 50
	Clipboard := clipboard_tmp	
	if (back > 0) {
		Loop, %back%
		{
			SendInput {left}
		}
	}
}

send_selected(text1, text2)
{
	selected := get_selected()
	if (StrLen(selected)) {
		send_text(text1 . selected . text2, 0)
	} else {
		send_text(text1 . text2, StrLen(text2))
	}
}

send_wrap(before, after, before2, after2, rn = false)
{
	selected := get_selected()
	if (StrLen(selected)) {
		tabs := get_tabs(selected)
		rows := ""
		if (RegExMatch(selected, "[\r|\n]") || rn) {
			Loop, parse, selected, `n,`r 
			{
				if (A_Index = 1) {
					if RegExMatch(A_LoopField, "^[`t]") {
						rows := tabs . before . "`r`n"
						addtab = 0
					} else {
						rows := before . "`r`n"
						addtab = 1
					}
				}
				if (StrLen(A_LoopField)) {
					if (A_Index == 1 && addtab == 1) {
						space := tabs
					} else {
						space := RegExReplace(A_LoopField, "^(\s+)?.*", "$1")
					}
					rows .= space . before2 . trim(A_LoopField) . after2
				}
				rows .= "`r`n"
			}
			rows .= tabs . after
			send_text(rows, 0)	
		} else {
			text := tabs . before . Ltrim(selected) . after
			send_text(text, 0)
		}
	} else {
		send_text(before . after, StrLen(after))
	}
}

; Обворачивание текста тегами (многосрочный)
send_wrap_multiline(before, after)
{
	selected := get_selected()
	if (StrLen(selected)) {
		tabs := get_tabs(selected)
		if RegExMatch(selected, "[\r|\n]") {
			rows := ""
			Loop, parse, selected, `n,`r 
			{
				if (A_Index = 1) {
					if RegExMatch(A_LoopField, "^[`t]") {
						rows .= tabs
					} 
					rows .= before . trim(A_LoopField) . after . "`r`n"
				} else {
					if (StrLen(A_LoopField)) {
						rows .= tabs . before . trim(A_LoopField) . after . "`r`n"
					}
				}
			}
			send_text(rows, 0)	
		} else {
			text := tabs . before . Ltrim(selected) . after
			send_text(text, 0)
		}
	} else {
		send_text(before . after, StrLen(after))
	}
}

KeyEvent(code, state){
	global EMAIL
	global CTRL_KEY
	global WIN_KEY

	if (code == 29 && state == 1) {
		CTRL_KEY := 1
	}
	if (code == 29 && state == 0) {
		CTRL_KEY := 0
	}
	if (code == 347 && state == 1) {
		WIN_KEY := 1
	}
	if (code == 347 && state == 0) {
		WIN_KEY := 0
	}
	if (state == 0) {
		return
	}

	; Ctrl+Z
	if (code == 1 && CTRL_KEY == 0) {
		send ^z
		return	
	}	

	; id=""
	if (code == 59 && CTRL_KEY == 0) {
		send_selected("id=""", """")
		return	
	}
    
	; class=""
	if (code == 60 && CTRL_KEY == 0) {
		send_selected("class=""", """")
		return	
	}

	; <div class="">...</div>
	if (code == 61 && CTRL_KEY == 0) {
		send_wrap("<div class="""">", "</div>", "`t", "", true)
		return
	}
   
	; <div class="">...</div> (многосрочный) 
	if (code == 61 && CTRL_KEY == 1) {
		send_wrap_multiline("<div class="""">", "</div>")
		return
	}
    
	; <a href=""></a> 
	if (code == 62 && CTRL_KEY == 0) {
		send_wrap("<a href="""">", "</a>", "`t", "")
		return
	}
    
	; <a href="">...</a> (многострочный) 
	if (code == 62 && CTRL_KEY == 1) {
		send_wrap_multiline("<a href="""">", "</a>")
		return	
	}	
	
	; <?php echo get_url(''); ?>	
	if (code == 63 && CTRL_KEY == 0) {
		send_selected("<?php echo get_url('", "'); ?>")
		return
	}	

	; get_url('')	
	if (code == 63 && CTRL_KEY == 1) {
		send_selected("get_url('", "')")
		
		return	
	}	
	
	; target="_blank" 
	if (code == 64 && CTRL_KEY == 0) {
		send_text("target=""_blank""", 0)
		return
	}
    
	; target="_parent"
	if (code == 64 && CTRL_KEY == 1) {
		send_text("target=""_parent""", 0)
		return		
	}		
	
	; rel="nofollow"
	if (code == 65 && CTRL_KEY == 0) {
		send_text("rel=""nofollow""", 0)
		return
	}	
	
	; <noindex>...<noindex>
	if (code == 65 && CTRL_KEY == 1) {
		send_wrap("<noindex>", "</noindex>", "`t", "")
		return		
	}	
	
	; onclick="..."
	if (code == 66 && CTRL_KEY == 0) {
		send_selected("onclick=""", """")
		return	
	}	
	
	; onchange="..."
	if (code == 66 && CTRL_KEY == 1) {
		send_selected("onchange=""", """")
		return	
	}	

	; <ol>...</ol>
	if (code == 67 && CTRL_KEY == 0) {
		send_wrap("<ol>", "</ol>", "`t", "", true)
		return	
	}
	
	; <ol><li>...</li></ol>
	if (code == 67 && CTRL_KEY == 1) {
		send_wrap("<ol>", "</ol>", "`t<li>", "</li>")
		return	
	}
    
	; <ul>...</ul>
	if (code == 68 && CTRL_KEY == 0) {
		send_wrap("<ul>", "</ul>", "`t", "", true)
		return	
	}
	
	; <ul><li>...</li></ul>
	if (code == 68 && CTRL_KEY == 1) {
		send_wrap("<ul>", "</ul>", "`t<li>", "</li>")
		return	
	}

	; <li>...</li>
	if (code == 87 && CTRL_KEY == 0) {
		send_wrap("<li>", "</li>", "`t", "")
		return	
	}
	
	; <li>...</li> (многострочный)
	if (code == 87 && CTRL_KEY == 1) {
		send_wrap_multiline("<li>", "</li>")
		return	
	}

	
	; <li class="">...</li>
	if (code == 88 && CTRL_KEY == 0) {
		send_wrap("<li class="">", "</li>", "`t", "")
		return	
	}
	
	; <li class="">...</li> (многострочный)
	if (code == 88 && CTRL_KEY == 1) {
		send_wrap_multiline("<li class="""">", "</li>")
		return	
	}

	; <!-- ... -->
	if (code == 41 && CTRL_KEY == 0) {
		send_wrap("<!-- ", " -->", "", "")
		return
	}	

	; <pre>...</pre>
	if (code == 41 && CTRL_KEY == 1) {
		send_wrap("<pre>", "</pre>", "`t", "")
		return
	}	
	
	; <h1>...</h1>
	if (code == 2 && CTRL_KEY == 0) {
		send_wrap("<h1>", "</h1>", "`t", "")
		return	
	}
	
	; <h4>...</h4>
	if (code == 2 && CTRL_KEY == 1) {
		send_wrap("<h4>", "</h4>", "`t", "")
		return
	}
    
	; <h2>...</h2>
	if (code == 3 && CTRL_KEY == 0) {
		send_wrap("<h2>", "</h2>", "`t", "")
		return	
	}
	
	; <h5>...</h5>
	if (code == 3 && CTRL_KEY == 1) {
		send_wrap("<h5>", "</h5>", "`t", "")
		return	
	}
    
	; <h3>...</h3>
	if (code == 4 && CTRL_KEY == 0) {
		send_wrap("<h3>", "</h3>", "`t", "")
		return	
	}
    
	; <h6>...</h6>
	if (code == 4 && CTRL_KEY == 1) {
		send_wrap("<h6>", "</h6>", "`t", "")
		return	
	}
    
	; <p>...</p>
	if (code == 5 && CTRL_KEY == 0) {
		send_wrap("<p>", "</p>", "`t", "")
		return
	}

	; <p>...</p> (многострочный)
	if (code == 5 && CTRL_KEY == 1) {
		send_wrap_multiline("<p>", "</p>")
		return	
	}
    
	; <br>
	if (code == 6 && CTRL_KEY == 0) {
		send_text("<br>", 0)
		return	
	}
	
	; \r\n
	if (code == 6 && CTRL_KEY == 1) {
		send_text("\r\n", 0)
		return	
	}
	
	; <img>
	if (code == 7 && CTRL_KEY == 0) {
		send_wrap_multiline("<img src=""", """ alt="""">")
		return
	}
	
	; <a href="..."><img src="..."></a>
	if (code == 7 && CTRL_KEY == 1) {
		selected := get_selected()
		if (StrLen(selected)) {
			rows := ""
			Loop, parse, selected, `n,`r 
			{
				text := Trim(A_LoopField)
				if (StrLen(text)) {
					rows .= "<a href=""" . text . """><img src=""" . text . """ alt=""""></a>"
				}
				rows .= "`r`n"
			}
			send_text(rows, 0)		
		} 
		return
	}
	
	; <span>...</span>
	if (code == 8 && CTRL_KEY == 0) {
		send_wrap("<span>", "</span>", "`t", "")
		return
	}
    
	; <span>...</span> (многосрочный) 
	if (code == 8 && CTRL_KEY == 1) {
		send_wrap_multiline("<span>", "</span>")
		return
	}

	; <strong>...</strong>
	if (code == 9 && CTRL_KEY == 0) {
		send_wrap("<strong>", "</strong>", "`t", "")
		return	
	}
	
	; <i>...</i>
	if (code == 9 && CTRL_KEY == 1) {
		send_wrap("<i>", "</i>", "`t", "")
		return	
	}
	
	; <table>...</table>
	if (code == 10 && CTRL_KEY == 0) {
		send_wrap("<table>", "</table>", "`t", "", true)
		return	
	}
	
	; <table>...</table> полностью
	if (code == 10 && CTRL_KEY == 1) {
		selected := get_selected()
		send_text("<table class="""">`r`n`t<colgroup>`r`n`t`t<col width="""">`r`n`t</colgroup>`r`n`t<thead>`r`n`t`t<tr>`r`n`t`t`t<th></th>`r`n`t`t</tr>`r`n`t</thead>`r`n`t<tbody>`r`n`t`t<tr>`r`n`t`t`t<td>" . selected . "</td>`r`n`t`t</tr>`r`n`t</tbody>`r`n</table>", 0)
		return
	}
	
	; <tr>...</tr>
	if (code == 11 && CTRL_KEY == 0) {
		send_wrap("<tr>", "</tr>", "`t", "", true)
		return	
	}
	
	; thead tbody
	if (code == 11 && CTRL_KEY == 1) {
		selected := get_selected()
		send_text("<colgroup>`r`n`t`t<col width="""">`r`n`t</colgroup>`r`n`t<thead>`r`n`t`t<tr>`r`n`t`t`t<th></th>`r`n`t`t</tr>`r`n`t</thead>`r`n`t<tbody>`r`n`t`t<tr>`r`n`t`t`t<td>" . selected . "</td>`r`n`t`t</tr>`r`n`t</tbody>", 0)
		return	
	}
	
	; <th>...</th>
	if (code == 12 && CTRL_KEY == 0) {
		send_wrap("<th>", "</th>", "`t", "")
		return
	}	

	; <th>...</th> (многосрочный)
	if (code == 12 && CTRL_KEY == 1) {
		send_wrap_multiline("<th>", "</th>")
		return
	}	
	
	; <td>...</td>
	if (code == 13 && CTRL_KEY == 0) {
		send_wrap("<td>", "</td>", "`t", "")
		return
	}
	
	; <td>...</td> (многострочный)
	if (code == 13 && CTRL_KEY == 1) {
		send_wrap_multiline("<td>", "</td>")
		return
	}
	
	; BACKSPACE
	if (code == 14 && CTRL_KEY == 0) {
		Send {BackSpace}
		return
	}
	
	; Удалить html теги
	if (code == 14 && CTRL_KEY == 1) {
		selected := get_selected()
		if (StrLen(selected)) {
			selected := RegExReplace(selected, "(<[\w]+>)(.+?)(</[\w]+>)", "$2")
			selected := RegExReplace(selected, "<[\w]+>", " ")
			selected := RegExReplace(selected, "(</[\w]+>)", "")
			send_text(selected, 0)
		} 
		return
	}	
    
	; TAB
	if (code == 15 && CTRL_KEY == 0) {
		Send {Tab}
		return
	}
    
	; Выпавнивание по горизантали
	if (code == 15 && CTRL_KEY == 1) {
		selected := get_selected()
		if (StrLen(selected)) {
			text := ""
    
			; =>
			max_len := 0
			max_count := 0
			Loop, parse, selected, `n,`r 
			{
				if (StrLen(trim(A_LoopField))) {
					word_array := StrSplit(A_LoopField, "=>")
					if (StrLen(trim(word_array[1])) > max_len) {
						max_len := StrLen(trim(word_array[1]))
					}
					c_count := word_array.MaxIndex() 
					if (c_count > max_count) {
						max_count += c_count
					}
				}
			}
			if (max_count > 1) {
				Loop, parse, selected, `n,`r 
				{
					if (StrLen(trim(A_LoopField))) {
						word_array := StrSplit(A_LoopField, "=>")
						len := StrLen(trim(word_array[1]))
						text .= rtrim(word_array[1])
						t_len := max_len - len
						Loop % t_len
						{
							text .= " "
						}
						text .= " => " . trim(word_array[2]) . "`r`n"
					}
				}
				send_text(rtrim(text), 0)
				return
			}
    
			; =
			max_len := 0
			max_count := 0
			Loop, parse, selected, `n,`r 
			{
				if (StrLen(trim(A_LoopField))) {
					word_array := StrSplit(A_LoopField, "=")
					if (StrLen(trim(word_array[1])) > max_len) {
						max_len := StrLen(trim(word_array[1]))
					}
					c_count := word_array.MaxIndex() 
					if (c_count > max_count) {
						max_count += c_count
					}
				}
			}
			if (max_count > 1) {
				Loop, parse, selected, `n,`r 
				{
					if (StrLen(trim(A_LoopField))) {
						word_array := StrSplit(A_LoopField, "=")
						len := StrLen(trim(word_array[1]))
						text .= rtrim(word_array[1])
						t_len := max_len - len
						Loop % t_len
						{
							text .= " "
						}
						text .= " = " . trim(word_array[2]) . "`r`n"
					}
				}
				send_text(rtrim(text), 0)
				return
			}
			
			; :
			max_len := 0
			max_count := 0
			Loop, parse, selected, `n,`r 
			{
				if (StrLen(trim(A_LoopField))) {
					word_array := StrSplit(A_LoopField, ":")
					if (StrLen(trim(word_array[1])) > max_len) {
						max_len := StrLen(trim(word_array[1]))
					}
					c_count := word_array.MaxIndex() 
					if (c_count > max_count) {
						max_count += c_count
					}
				}
			}
			if (max_count > 1) {
				Loop, parse, selected, `n,`r 
				{
					if (StrLen(trim(A_LoopField))) {
						word_array := StrSplit(A_LoopField, ":")
						len := StrLen(trim(word_array[1]))
						text .= rtrim(word_array[1]) . ":"
						t_len := max_len - len
						Loop % t_len
						{
							text .= " "
						}
						text .= " " . trim(word_array[2]) . "`r`n"
					}
				}
				send_text(rtrim(text), 0)
				return
			}	
			; =
			max_len := 0
			max_count := 0
			Loop, parse, selected, `n,`r 
			{
				if (StrLen(trim(A_LoopField))) {
					word_array := StrSplit(A_LoopField, "=")
					if (StrLen(trim(word_array[1])) > max_len) {
						max_len := StrLen(trim(word_array[1]))
					}
					c_count := word_array.MaxIndex() 
					if (c_count > max_count) {
						max_count += c_count
					}
				}
			}
			if (max_count > 1) {
				Loop, parse, selected, `n,`r 
				{
					if (StrLen(trim(A_LoopField))) {
						word_array := StrSplit(A_LoopField, "=")
						len := StrLen(trim(word_array[1]))
						text .= rtrim(word_array[1]) . "="
						t_len := max_len - len
						Loop % t_len
						{
							text .= " "
						}
						text .= " " . trim(word_array[2]) . "`r`n"
					}
				}
				send_text(rtrim(text), 0)
				return
			}
		} 
    
		return
	}
    
	; <form>...</form>
	if (code == 16 && CTRL_KEY == 0) {
		send_wrap("<form action="""" method=""post"">", "</form>", "`t", "", true)
		return
	}	
	
	; width=""
	if (code == 16 && CTRL_KEY == 1) {
		send_selected("width=""", """")
		return
	}		
	
	; <label for="">...</label>
	if (code == 17 && CTRL_KEY == 0) {
		send_wrap("<label for="""">", "</label>", "`t", "")
		return
	}	
	
	; height=""
	if (code == 17 && CTRL_KEY == 1) {
		send_selected("height=""", """")
		return
	}		
    
	; name="..."
	if (code == 18 && CTRL_KEY == 0) {
		send_selected("name=""", """")
		return	
	}	
	
	; placeholder="..."
	if (code == 18 && CTRL_KEY == 1) {
		send_selected("placeholder=""", """")
		return	
	}
	
	; value="..."
	if (code == 19 && CTRL_KEY == 0) {
		send_selected("value=""", """")
		return	
	}
	
	; required
	if (code == 19 && CTRL_KEY == 1) {
		send_text("required", 0)
		return	
	}
    
	; <input type="text" name="" value="" placeholder="">
	if (code == 20 && CTRL_KEY == 0) {
		send_text("<input type=""text"" name="""" value="""" placeholder="""">", 0)
		return
	}
    
	; <input type="email" name="" value="" placeholder="">
	if (code == 20 && CTRL_KEY == 1) {
		send_text("<input type=""email"" name=""email"" value="""" placeholder=""E-mail"">", 0)
		return
	}	
    
	; <textarea name="">...</label>
	if (code == 21 && CTRL_KEY == 0) {
		send_wrap("<textarea name="""" placeholder="""">", "</textarea>", "`t", "")
		return
	}
    
	; rows=""
	if (code == 21 && CTRL_KEY == 1) {
		send_selected("rows=""", """")
		return
	}
	
	; <input type="hidden" name="" value="">
	if (code == 22 && CTRL_KEY == 0) {
		send_text("<input type=""hidden"" name="""" value="""">", 0)
		return
	}
	
	; <input type="password" name="" value="">
	if (code == 22 && CTRL_KEY == 1) {
		send_text("<input type=""password"" name="""" value="""">", 0)
		return
	}	
    
	; <select>
	if (code == 23 && CTRL_KEY == 0) {
		send_wrap("<select name="""">", "</select>", "`t<option value="""">", "</option>", true)
		return
	}
    
	; multiple
	if (code == 23 && CTRL_KEY == 1) {
		send_text("multiple", 0)
		return
	}	

	; <option>
	if (code == 24 && CTRL_KEY == 0) {
		send_wrap_multiline("<option value="""">", "</option>")
		return
	}
    
	; selected
	if (code == 24 && CTRL_KEY == 1) {
		send_text("selected", 0)
		return
	}
	
	; <input type="checkbox" name="" value="">
	if (code == 25 && CTRL_KEY == 0) {
		send_text("<input type=""checkbox"" name="""" value="""">", 0)
		return
	}
    
	; checked
	if (code == 25 && CTRL_KEY == 1) {
		send_text("checked", 0)
		return
	}	
    
	; <input type="radio" name="" value="">
	if (code == 26 && CTRL_KEY == 0) {
		send_text("<input type=""radio"" name="""" value="""">", 0)
		return
	}
    
	; disabled
	if (code == 26 && CTRL_KEY == 1) {
		send_text("disabled", 0)
		return
	}	
    
	; <input type="submit" name="" value="">
	if (code == 27 && CTRL_KEY == 0) {
		send_text("<input type=""submit"" name=""send"" value=""Отправить"">", 0)
		return
	}
	
	; <button>...</button>
	if (code == 27 && CTRL_KEY == 1) {
		send_wrap("<button type=""submit"" name=""send"" value=""1"">", "</button>", "", "")
		return
	}	
    
	; <input type="file">
	if (code == 43 && CTRL_KEY == 0) {
		send_text("<input type=""file"" name=""file"">", 0)
		return
	}
    
	; multipart
	if (code == 43 && CTRL_KEY == 1) {
		send_text("enctype=""multipart/form-data""", 0)
		return
	}	
    
	; /*...*/
	if (code == 58 && CTRL_KEY == 0) {
		send_wrap("/* ", " */", "", "")
		return
	}
    
	; /** ... */
	if (code == 58 && CTRL_KEY == 1) {
		send_wrap("/**", " */", " * ", "")
		return
	}	
	
	; <script>...<script>
	if (code == 30 && CTRL_KEY == 0) {
		send_wrap("<script>", "</script>", "", "", true)
		return
	}
	
	; <script src="..."></script>
	if (code == 30 && CTRL_KEY == 0) {
		send_selected("<script src=""", """></script>")
		return
	}
    
	; if
	if (code == 31 && CTRL_KEY == 0) {
		send_wrap("if(){", "}", "`t", "")
		return
	}

	; if else
	if (code == 31 && CTRL_KEY == 1) {
		send_wrap("else{", "}", "`t", "")
		return
	}	
	
	; return
	if (code == 32 && CTRL_KEY == 0) {
		send_text("return", 0)
		return
	}	
	
	; $("...")
	if (code == 33 && CTRL_KEY == 0) {
		send_selected("$(""", """)")
		return
	}
    
	; $(document).ready(function(){...}
	if (code == 33 && CTRL_KEY == 1) {
		send_wrap("$(document).ready(function(){", "}", "`t", "")
		return
	}

	; function name(){...}
	if (code == 34 && CTRL_KEY == 0) {
		send_wrap("function name(){", "}", "`t", "")
		return
	}
	
	; 
	;if (code == 34 && CTRL_KEY == 1) {
	;
	;}	

	; console.log(...);
	if (code == 35 && CTRL_KEY == 0) {
		send_selected("console.log(", ");")
		return
	}
    
	; console.dir(...);
	if (code == 35 && CTRL_KEY == 1) {
		send_selected("console.dir(", ");")
		return
	}
    
	; SELECT
	if (code == 36 && CTRL_KEY == 0) {
		send_text("SELECT * FROM ``#__`` WHERE ``approve`` = 1 ORDER BY ``name``", 0)
		return
	}
    
	; LEFT JOIN
	if (code == 36 && CTRL_KEY == 1) {
		send_text("LEFT JOIN ``#__`` AS `b` ON ``b``.``id`` = ``a``.``id``", 0)
		return
	}	
	
	; INSERT
	if (code == 37 && CTRL_KEY == 0) {
		send_text("INSERT INTO ``#__`` SET ``name`` = ?", 0)
		return
	}
    
	; GROUP BY
	if (code == 37 && CTRL_KEY == 1) {
		send_text("GROUP BY ``id``", 0)
		return
	}
	
	; UPDATE
	if (code == 38 && CTRL_KEY == 0) {
		send_text("UPDATE ``#__`` SET ``name`` = ? WHERE ``id`` = ?", 0)
		return
	}
    
	; LIKE
	if (code == 38 && CTRL_KEY == 1) {
		send_selected("LIKE '%", "%'")
		return
	}	
    
	; DELETE
	if (code == 39 && CTRL_KEY == 0) {
		send_text("DELETE FROM ``#__`` WHERE `id` = ?", 0)
		return
	}
    
	; FIND_IN_SET
	if (code == 39 && CTRL_KEY == 1) {
		send_selected("FIND_IN_SET(", ")")
		return
	}
    
	; `...`
	if (code == 40 && CTRL_KEY == 0) {
		send_selected("``", "``")
		return
	}
	
	; UNIX_TIMESTAMP()
	if (code == 40 && CTRL_KEY == 1) {
		send_text("UNIX_TIMESTAMP()", 0)
		return
	}	
	
	; Enter
	if (code == 28 && CTRL_KEY == 0) {
		Send {Enter}
		return
	}	
	
	; <?php
	if (code == 42 && CTRL_KEY == 0) {
		send_wrap("<?php ", " ?>", "", "")
		return
	}
    
	; ?><?php
	if (code == 42 && CTRL_KEY == 1) {
		send_wrap("?>", "<?php", "", "")
		return
	}
    
	; echo ...;
	if (code == 44 && CTRL_KEY == 0) {
		send_selected("echo ", ";")
		return
	}
	
	; <?php echo ...; ?>
	if (code == 44 && CTRL_KEY == 1) {
		selected := get_selected()
		send_selected("<?php echo ", "; ?>")
		return
	}
	
	; ' .  . '
	if (code == 45 && CTRL_KEY == 0) {
		send_selected("' . ", " . '")		
		return
	}
	
	; " .  . "	
	if (code == 45 && CTRL_KEY == 1) {
		send_selected(""" . ", " . """)
		return
	}
	
	; if () {...}
	if (code == 46 && CTRL_KEY == 0) {
		send_wrap("if () {", "}", "`t", "", true)
		return
	}	
    
	; <?php if (): ?>...<?php endif; ?>
	if (code == 46 && CTRL_KEY == 1) {
		send_wrap("<?php if (): ?>", "<?php endif; ?>", "`t", "", true)
		return
	}
	
	; empty(...)
	if (code == 47 && CTRL_KEY == 0) {
		send_wrap("empty(", ")", "`t", "")
		return
	}	
   
	; isset(...)
	if (code == 47 && CTRL_KEY == 1) {
		send_wrap("isset(", ")", "`t", "")
		return
	}	
	
	; else {...}
	if (code == 48 && CTRL_KEY == 0) {
		send_wrap("else {", "}", "`t", "", true)
		return
	}	
    
	; <?php else: ?>...
	if (code == 48 && CTRL_KEY == 1) {
		send_wrap("<?php else: ?>", "", "", "", true)
		return
	}
	
	; foreach () {...}
	if (code == 49 && CTRL_KEY == 0) {
		send_wrap("foreach ( as $i => $row) {", "}", "`t", "", true)				
		return
	}	
    
	; <?php foreach (): ?>...<?php foreach; ?>
	if (code == 49 && CTRL_KEY == 1) {
		send_wrap("<?php foreach ( as $i => $row): ?>", "<?php endforeach; ?>", "", "", true)
		return
	}	
	
	; for () {...}
	if (code == 50 && CTRL_KEY == 0) {
		send_wrap("for ($n = 10; $n <= 10; $n++) {", "}", "`t", "", true)					
		return
	}	
    
	; <?php for (): ?>...<?php endif; ?>
	if (code == 50 && CTRL_KEY == 1) {
		send_wrap("<?php for ($n = 10; $n <= 10; $n++): ?>", "<?php endfor; ?>", "", "", true)		
		return
	}
	
	; switch () {...}
	if (code == 51 && CTRL_KEY == 0) {
		send_selected("switch ($i) {`r`n`tcase 1:`r`n`r`n", "`t`tbreak;`r`n`tdefault:`r`n`r`n`t`tbreak;`r`n}")		
		return
	}	
    
	; <?php switch (): ?>...<?php endswitch; ?>
	if (code == 51 && CTRL_KEY == 1) {
		return
	}
    
	; array(...)
	if (code == 52 && CTRL_KEY == 0) {
		send_wrap("array(", ")", "`t", "")
		return
	}
	
	; $array = array(...)
	if (code == 52 && CTRL_KEY == 1) {
		send_wrap("$array = array(", ");", "`t", "")
		return
	}
	
	; ['...']
	if (code == 53 && CTRL_KEY == 0) {
		send_wrap_multiline("['", "']")
		return
	}
	
	; =>
	if (code == 53 && CTRL_KEY == 1) {
		send_text(" => ", 0)
		return
	}
    
	; '...',
	; '...',
	if (code == 310 && CTRL_KEY == 0) {
		selected := get_selected()
		rows := ""
		Loop, parse, selected, `n,`r 
		{
			if (A_Index == 1 && (SubStr(A_LoopField, 1, 1) != "`t")) {
				rows .=  "'" . trim(A_LoopField) . "',`r`n"
			} else {
				rows .=  get_tabs(selected) . "'" . trim(A_LoopField) . "',`r`n"
			}
		}
		send_text(rows, 0)
		return
	}	
	
	; 1 => '...',
	; 2 => '...',
	if (code == 310 && CTRL_KEY == 1) {
		selected := get_selected()
		rows := ""
		Loop, parse, selected, `n,`r 
		{
			if (A_Index == 1 && (SubStr(A_LoopField, 1, 1) != "`t")) {
				rows .= A_Index . " => '" . trim(A_LoopField) . "',`r`n"
			} else {
				rows .=  get_tabs(selected) . A_Index . " => '" . trim(A_LoopField) . "',`r`n"
			}
		}
    
		; Выравнивание по ключу
		max_len := 0
		max_count := 0
		Loop, parse, rows, `n,`r 
		{
			if (StrLen(trim(A_LoopField))) {
				word_array := StrSplit(A_LoopField, "=>")
				if (StrLen(trim(word_array[1])) > max_len) {
					max_len := StrLen(trim(word_array[1]))
				}
				c_count := word_array.MaxIndex() 
				if (c_count > max_count) {
					max_count += c_count
				}
			}
		}
		if (max_count > 1) {
			text := ""
			Loop, parse, rows, `n,`r 
			{
				if (StrLen(trim(A_LoopField))) {
					word_array := StrSplit(A_LoopField, "=>")
					len := StrLen(trim(word_array[1]))
					text .= rtrim(word_array[1])
					t_len := max_len - len
					Loop % t_len
					{
						text .= " "
					}
					text .= " => " . trim(word_array[2]) . "`r`n"
				}
			}
			send_text(text, 0)
		} else {
			send_text(rows, 0)	
		}
	}
    
	; Яндекс
	if (code == 56 && CTRL_KEY == 0) {
		selected := get_selected()
		if (StrLen(selected)) {
			if InStr(selected, "http") {
				Run, %selected%
			} else if (InStr(selected, ".ru") || InStr(selected, ".su") || InStr(selected, ".com") || InStr(selected, ".net")) {
				Run, https://%selected%
			} else {
				Run, https://yandex.ru/search/?text=%selected%
			}
		} else {
			Run, https://yandex.ru/
		}
		return
	}

	; Google
	if (code == 56 && CTRL_KEY == 1) {
		selected := get_selected()
		if (StrLen(selected)) {
			if InStr(selected, "http") {
				Run, %selected%
			} else if (InStr(selected, ".ru") || InStr(selected, ".su") || InStr(selected, ".com") || InStr(selected, ".net")) {
				Run, https://%selected%
			} else {
				Run, https://www.google.ru/search?ie=UTF-8&q=%selected%
			}
		} else {
			Run, https://www.google.ru/
		}
		return
	}
    
	; Пробел
	if (code == 57 && CTRL_KEY == 0) {
		Send {Space}
		return
	}	
    
	; $this->
	if (code == 312 && CTRL_KEY == 0) {
		send_selected("$this->", "")
		return
	}	
	
	; self::
	if (code == 312 && CTRL_KEY == 1) {
		send_selected("self::", "")
		return
	}	
	
	; E-mail
	if (code == 311 && CTRL_KEY == 0) {
		send_text(EMAIL, 0)
		return
	}
    
	; Генерация пароля
	if (code == 311 && CTRL_KEY == 1) {
		length := 8
		password := ""
		possible := "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ1234567890"
		StringLen, max, possible
		Loop {
			Random, rand, 1, max
			StringMid, char, possible, rand, 1
			if !InStr(password, char) 
				password .= char
			if StrLen(password) >= length 
				break
		}
		send_text(password, 0)
		Clipboard := password
		return
	}

	; Удаление кроме цифр
	if (code == 70 && CTRL_KEY == 0) {
		selected := get_selected()
		if (StrLen(selected)) {
			text := RegExReplace(selected, "[^\d]", "")
			send_text(text, 0)
		}
		return
	}
	
	; trim
	if (code == 70 && CTRL_KEY == 1) {
		selected := get_selected()
		send_text(trim(selected), 0)
		return
	}

	; Транслит для URL
	if (code == 326 && CTRL_KEY == 1) {
		selected := get_selected()
		if (StrLen(selected)) {
			StringLower, selected, selected
			translit := ""
			arrRuEn := {a:"a",b:"b",c:"c",d:"d",e:"e",f:"f",g:"g",h:"h",i:"i",j:"j",k:"k",l:"l",m:"m",n:"n",o:"o",p:"p",q:"q",r:"r",s:"s",t:"t",u:"u",v:"v",w:"w",x:"x",y:"y",z:"z",а:"a",б:"b",в:"v",г:"g",д:"d",е:"e",ё:"yo",ж:"zh",з:"z",и:"i",й:"j",к:"k",л:"l",м:"m",н:"n",о:"o",п:"p",р:"r",с:"s",т:"t",у:"u",ф:"f",х:"h",ц:"c",ч:"ch",ш:"sh",щ:"shh",ъ:"",ы:"y",ь:"",э:"e",ю:"yu",я:"ya"," ":" ",".":".",",":","}
			arrStr := StrSplit(selected, "")
			for indexArrStr, valueArrStr in arrStr {
				for indexArrRuEn, valuearrRuEn in arrRuEn {
					if ( indexarrRuEn = valueArrStr ) {
						translit .= valuearrRuEn
					} 
				}
			}
			translit := RegExReplace(translit, "[^-0-9a-z]", "-")
			translit := RegExReplace(translit, "[-]+", "-")
			translit := trim(translit, "-")
			send_text(translit, 0)
		}
		return
	}
	
	; Первая заглавная буква
	if (code == 338 && CTRL_KEY == 0) {
		selected := get_selected()
		text := ""
		if InStr(selected, " ") {
			Loop, parse, selected, " "
			{
				if(A_Index = 1) {
					row := A_LoopField
					StringUpper, row, row, T
					text .= row . " "
				} else {
					tt := A_LoopField
					StringLower, tt, tt
					text .= tt  . " "
				}
			}
			text := trim(text)
		} else {
			StringUpper, text, selected, T
		}
		send_text(text, 0)
		return
	}	
	
	; В нижний регистр
	if (code == 327 && CTRL_KEY == 0) {
		selected := get_selected()
		if (StrLen(selected)) {
			StringLower, selected, selected
			send_text(selected, 0)
		}
		return
	}	
	
	; В верхний регистр
	if (code == 327 && CTRL_KEY == 1) {
		selected := get_selected()
		if (StrLen(selected)) {
			StringUpper, selected, selected
			send_text(selected, 0)
		}
		return
	}

	; htmlspecialchars 
	if (code == 329 && CTRL_KEY == 0) {
		selected := get_selected()
		if (StrLen(selected)) {
			send_text(EncodeHTML(selected), 0)
		}
		return
	}	

	; Удаление экранирования символов
	if (code == 329 && CTRL_KEY == 1) {
		selected := get_selected()
		if (StrLen(selected)) {
			selected := StrReplace(selected, "\""", """")
			selected := StrReplace(selected, "\'", "'")
			selected := StrReplace(selected, "\\", "\")
			send_text(selected, 0)
		}
		return
	}

	; '...'
	if (code == 339 && CTRL_KEY == 0) {
		send_selected("'", "'")
		return
	}
	
	; '...' мультистрочный
	if (code == 339 && CTRL_KEY == 1) {
		send_wrap_multiline("'", "'")
		return
	}
	
	; "..."
	if (code == 335 && CTRL_KEY == 0) {
		send_selected("""", """")
		return
	}
	
	; "..." мультистрочный
	if (code == 335 && CTRL_KEY == 1) {
		send_wrap_multiline("""", """")
		return
	}
    
	; «...»
	if (code == 337 && CTRL_KEY == 0) {
		send_selected("«", "»")
		return
	}
    
	; Длинное тире
	if (code == 337 && CTRL_KEY == 1) {
		send_text("–", 1)
		return
	}
	
	; <...>
	if (code == 328 && CTRL_KEY == 0) {
		send_selected("<", ">")
		return
	}
    
	; <...> мультистрочный
	if (code == 328 && CTRL_KEY == 1) {
		send_wrap_multiline("<", ">")
		return
	}
    
	; [...]
	if (code == 331 && CTRL_KEY == 0) {
		send_selected("[", "]")
		return
	}
	
	; [...] мультистрочный
	if (code == 331 && CTRL_KEY == 1) {
		send_wrap_multiline("[", "]")
		return
	}	
	
	; {...}
	if (code == 336 && CTRL_KEY == 0) {
		send_selected("{", "}")
		return
	}
	
	; {...} мультистрочный
	if (code == 336 && CTRL_KEY == 1) {
		send_wrap_multiline("{", "}")
		return
	}
	
	; (...)
	if (code == 333 && CTRL_KEY == 0) {
		send_selected("(", ")")
		return
	}
	
	; (...) мультистрочный
	if (code == 333 && CTRL_KEY == 1) {
		send_wrap_multiline("(", ")")
		return
	}
    
	; <style>...</style>
	if (code == 325 && CTRL_KEY == 0) {
		send_wrap("<style>", "</style>", "", "", true)
		return
	}
    
	; <link href="">
	if (code == 325 && CTRL_KEY == 1) {
		send_wrap_multiline("<link rel=""stylesheet"" href=""", """ type=""text/css"">")
		return
	}
    
	; style=""
	if (code == 309 && CTRL_KEY == 0) {
		send_selected("style=""", """")
		return	
	}
    
	; Remove style
	if (code == 309 && CTRL_KEY == 1) {
		selected := get_selected()
		if (StrLen(selected)) {
			text := RegExReplace(selected, "(\s?style=[""][^""]*""\s?)", " ")
			send_text(text, 0)
		}
		return
	}
	
	; Format CSS
	if (code == 55 && CTRL_KEY == 0) {
		selected := get_selected()
		if (StrLen(selected)) {
			if !InStr(selected, "{") {
				text := ""
				Loop, parse, selected, `n,`r 
				{
					row := Trim(A_LoopField)
					if (StrLen(row)) {
						text .= "`t" . Trim(A_LoopField) . "`r`n"
					}
				}
				
				text := StrReplace(text, ": ", ":")
				text := StrReplace(text, ":", ": ")
				send_text(text, 0)
			} else {
				minify := ""
				Loop, parse, selected, `n,`r 
				{
					minify .= Trim(A_LoopField)
				}
				minify := StrReplace(minify, ": ", ":")
				minify := StrReplace(minify, "( ", "(")
				minify := StrReplace(minify, " )", ")")
				minify := StrReplace(minify, ", ", ",")
				minify := StrReplace(minify, "{", "{`r`n")
				minify := StrReplace(minify, ";", ";`r`n")
		
				text := ""
				Loop, parse, minify, `n,`r 
				{
					if InStr(A_LoopField, ":") {
						text .= "`t" . trim(A_LoopField)
						if !InStr(A_LoopField, ";") {
							text .= ";"
						}
						text .= "`r`n"
					} else {
						text .= trim(A_LoopField) . "`r`n"
					}
				}
				
				selected := text
				selected := StrReplace(selected, ":", ": ")
				selected := StrReplace(selected, "  ", " ")
				selected := StrReplace(selected, "`r`n`r`n", "`r`n")
				selected := rtrim(selected)
				send_text(selected, 0)			
			}
		} 
		return
	}
    
	; Minify CSS
	if (code == 55 && CTRL_KEY == 1) {
		selected := get_selected()
		if (StrLen(selected)) {
			minify := ""
			Loop, parse, selected, `n,`r 
			{
				minify .= Trim(A_LoopField)
			}
			minify := StrReplace(minify, ": ", ":")
			minify := StrReplace(minify, "( ", "(")
			minify := StrReplace(minify, " )", ")")
			minify := StrReplace(minify, ", ", ",")
			minify := StrReplace(minify, ";}", "}")
			minify := StrReplace(minify, "}", "}`r`n")
			send_text(minify, 0)
		} 
		return
	}
	
	; border
	if (code == 74 && CTRL_KEY == 0) {
		selected := get_selected()
		if (StrLen(selected)) {
			if !InStr(selected, "#") {
				send_text("border: 1px solid #" . RTrim(selected, "; ") . ";", 0)
			} else {
				send_text("border: 1px solid " . RTrim(selected, "; ") . ";", 0)
			}
		} else {
			send_text("border: 1px solid #ddd;", 0)
		}
		return
	}
  
	; border-radius
	if (code == 74 && CTRL_KEY == 1) {
		send_text("border-radius: 0 0;", 0)
		return
	}
	
	; ....{} 
	if (code == 71 && CTRL_KEY == 0) {
		send_selected(".", " {`r`n`t`r`n}")
		return		
	}
    
	; .class{...}
	if (code == 71 && CTRL_KEY == 1) {
		selected := get_selected()
		if (StrLen(selected)) {
			rows := ".class {`r`n"
			Loop, parse, selected, `n,`r 
			{
				text := Trim(A_LoopField)
				if (StrLen(text)) {
					rows .= "`t" . Trim(text) . "`r`n"
				}
			}
			rows .= "}"
			send_text(rows, 0)
		} else {
			send_text(".class {`r`n`t`r`n}", 2)
		}
		return		
	}
	
	; #...{}
	if (code == 72 && CTRL_KEY == 0) {
		send_wrap("# {", "}", "`t", "", true)
		return	
	}
    
	; #id{...}
	if (code == 72 && CTRL_KEY == 1) {
		selected := get_selected()
		if (StrLen(selected)) {
			rows := "#id {`r`n"
			Loop, parse, selected, `n,`r 
			{
				text := Trim(A_LoopField)
				if (StrLen(text)) {
					rows .= "`t" . Trim(text) . "`r`n"
				}
			}
			rows .= "}"
			send_text(rows, 0)
		} else {
			send_text("#id {`r`n`t`r`n}", 2)
		}
		return
	}

	; @mobile
	if (code == 73 && CTRL_KEY == 0) {
		send_wrap("@media only screen and (min-device-width: 480px) {", "}", "`t", "")
		return
	}
	
	; @desktop
	if (code == 73 && CTRL_KEY == 1) {
		send_wrap("@media only screen and (min-device-width: 768px) {", "}", "`t", "")
		return
	}
	
	; :before
	if (code == 75 && CTRL_KEY == 0) {
		send_selected("", ":before {`r`n`tcontent: '';`r`n`tdisplay: inline-block;`r`n`tbackground: url(../img/image.png) 0px 0px no-repeat;`r`n`twidth: 16px;`r`n`theight: 16px;`r`n}")
		return
	}
	
	; :first-child
	if (code == 75 && CTRL_KEY == 1) {
		send_wrap(":first-child {", "}", "`t", "", true)
		return
	}
	
	; :after
	if (code == 76 && CTRL_KEY == 0) {
		send_selected("", ":after {`r`n`tcontent: '';`r`n`tdisplay: inline-block;`r`n`tbackground: url(../img/image.png) 0px 0px no-repeat;`r`n`twidth: 16px;`r`n`theight: 16px;`r`n}")
		return
	}
	
	; :last-child
	if (code == 76 && CTRL_KEY == 1) {
		send_wrap(":last-child {", "}", "`t", "", true)
		return
	}
	
	; :hover
	if (code == 77 && CTRL_KEY == 0) {
		send_wrap(":hover {", "}", "`t", "", true)
		return
	}
	
	; :nth-child
	if (code == 77 && CTRL_KEY == 1) {
		selected := get_selected()
		if (StrLen(selected)) {
			send_text(selected . ":nth-child() {`r`n`t`r`n}", 2)
		} else {
			send_text(":nth-child() {`r`n`t`r`n}", 2)
		}
		ToolTip % "odd - нечетные элементы `neven - четные элементы `n3n+2 - 2, 5, 8, 11, 14 `n-n+3 - 1, 2, 3 `n5n-2 - 3, 8, 13, 18, 23"
		Sleep, 5000
		ToolTip
		return
	}
    
	; margin
	if (code == 79 && CTRL_KEY == 0) {
		send_text("margin: 0px;", 0)
		return
	}
	
	; width
	if (code == 79 && CTRL_KEY == 1) {
		send_text("width: 0px;", 0)
		return
	}
	
	; padding
	if (code == 80 && CTRL_KEY == 0) {
		send_text("padding: 0px;", 0)
		return
	}
	
	; height
	if (code == 80 && CTRL_KEY == 1) {
		send_text("height: 0px;", 0)
		return
	}
	
	; display: block
	if (code == 81 && CTRL_KEY == 0) {
		send_text("display: block;", 0)
		return
	}
	
	; box-sizing: border-box
	if (code == 81 && CTRL_KEY == 1) {
		send_text("box-sizing: border-box;", 0)
		return
	}
	
	; !important
	if (code == 82 && CTRL_KEY == 0) {
		send_text(" !important", 0)
		return
	}
	
	; poa
	if (code == 83 && CTRL_KEY == 0) {
		send_text("position: absolute;`r`n`ttop: 0px;`r`n`tleft: 0px;", 0)
		return
	}
	
	; por
	if (code == 83 && CTRL_KEY == 1) {
		send_text("position: relative;", 0)
		return
	}
	
	; background color
	if (code == 78 && CTRL_KEY == 0) {
		selected := get_selected()
		if (StrLen(selected)) {
			if InStr(selected, "#") {
				send_text("background: " . selected . ";", 0)
				return
			} else {
				send_text("background: #" . selected . ";", 0)
				return
			} 
		} 
		send_text("background: #;", 1)
		return
	}
	
	; background
	if (code == 78 && CTRL_KEY == 1) {
		selected := get_selected()
		if (StrLen(selected)) {
			send_text("background: url(../img/" . selected . ") 0px 0px no-repeat;", 24)
			return
		}
		send_text("background: url(../img/.png) 0px 0px no-repeat;", 24)
		return
	}

	; font
	if (code == 284 && CTRL_KEY == 0) {
		send_text("font-size: 18px;`r`n`tline-height: 18px;`r`n`tcolor: rgb(0, 0, 0);", 0)
		return
	}
	
	; font-face
	if (code == 284 && CTRL_KEY == 1) {
		send_text("@font-face {`r`n`tfont-family: 'FONTNAME';`r`n`tsrc: url('../fonts/FONTNAME.eot');`r`n`tsrc: local('FONTNAME'),`r`n`turl('../fonts/FONTNAME.eot?#iefix') format('embedded-opentype'),`r`n`turl('../fonts/FONTNAME.woff2') format('woff2'),`r`n`turl('../fonts/FONTNAME.woff') format('woff'),`r`n`turl('../fonts/FONTNAME.ttf') format('truetype');`r`n`tfont-weight: normal;`r`n`tfont-style: normal;`r`n}", 0)
		return
	}

	; PASTE
	if (code == 347 && CTRL_KEY == 0) {
		return
	}

	; PHP Functions
	if (code == 285) {
		GLOBAL SELECT_TEXT
		SELECT_TEXT := get_selected()

		Gui Add, GroupBox, x7 y5 w133 h185, Vars
		Gui Add, Button, gget x17 y24 w113 h23, $_GET
		Gui Add, Button, gpost x17 y52 w113 h23, $_POST
		Gui Add, Button, grequest x17 y80 w113 h23, $_REQUEST
		Gui Add, Button, gcookie x17 y108 w113 h23, $_COOKIE
		Gui Add, Button, gsession x17 y135 w113 h23, $_SESSION
		Gui Add, Button, gserver x17 y161 w113 h23, $_SERVER
		Gui Add, GroupBox, x7 y199 w133 h158, Int
		Gui Add, Button, gmt_rand x17 y217 w113 h23, mt_rand()
		Gui Add, Button, ground x17 y245 w113 h23, round()
		Gui Add, Button, gfloor x17 y272 w113 h23, floor()
		Gui Add, Button, gceil x17 y298 w113 h23, ceil()
		Gui Add, Button, gnumber_format x17 y324 w113 h23, number_format()
		Gui Add, GroupBox, x7 y359 w133 h132, Debug		
		Gui Add, Button, gvar_dump x17 y378 w113 h23, var_dump()	
		Gui Add, Button, gprint_r x17 y405 w113 h23, print_r()	
		Gui Add, Button, gphpinfo x17 y432 w113 h23, phpinfo()
		Gui Add, Button, gexit x17 y459 w113 h23, exit()
		Gui Add, GroupBox, x151 y5 w178 h275, String
		Gui Add, Button, gimplode x163 y24 w155 h23, implode()		
		Gui Add, Button, gtrim x163 y52 w155 h23, trim()		
		Gui Add, Button, gstr_replace x163 y80 w155 h23, str_replace()		
		Gui Add, Button, gmb_strpos x163 y108 w155 h23, mb_strpos()	
		Gui Add, Button, gmb_strlen x163 y135 w155 h23, mb_strlen()		
		Gui Add, Button, gmb_sudstr x163 y161 w155 h23, mb_sudstr()		
		Gui Add, Button, gstripslashes x163 y189 w155 h23, stripslashes()		
		Gui Add, Button, ghtmlspecialchars_decode x163 y217 w155 h23, htmlspecialchars_decode()
		Gui Add, Button, giconv x163 y245 w155 h23, iconv()
		Gui Add, GroupBox, x151 y283 w178 h130, RegExp
		Gui Add, Button, gpreg_replace x163 y299 w155 h23, preg_replace()	
		Gui Add, Button, gpreg_match x163 y351 w155 h23, preg_match()		
		Gui Add, Button, gpreg_match_all x163 y378 w155 h23, preg_match_all()
		Gui Add, Button, gpreg_split x163 y325 w155 h23, preg_split()
		Gui Add, GroupBox, x152 y415 w178 h77, Output		
		Gui Add, Button, gob_start x164 y432 w155 h23, ob_start()
		Gui Add, Button, gob_get_clean x164 y459 w155 h23, ob_get_clean()		
		Gui Add, GroupBox, x341 y6 w133 h406, Array	
		Gui Add, Button, gexplode x351 y24 w113 h23, explode()		
		Gui Add, Button, gcount x351 y52 w113 h23, count()	
		Gui Add, Button, gin_array x351 y80 w113 h23, in_array()			
		Gui Add, Button, garray_key_exists x351 y108 w113 h23, array_key_exists()		
		Gui Add, Button, gis_array x351 y135 w113 h23, is_array()
		Gui Add, Button, garray_shift x351 y161 w113 h23, array_shift()		
		Gui Add, Button, garray_pop x351 y189 w113 h23, array_pop()		
		Gui Add, Button, garray_chunk x351 y217 w113 h23, array_chunk()
		Gui Add, Button, garray_diff x351 y245 w113 h23, array_diff()		
		Gui Add, Button, garray_unique x351 y272 w113 h23, array_unique()		
		Gui Add, Button, garray_merge x351 y299 w113 h23, array_merge()		
		Gui Add, Button, garray_map x351 y325 w113 h23, array_map()		
		Gui Add, Button, gunset x351 y351 w113 h23, unset()	
		Gui Add, Button, ghttp_build_query x351 y380 w113 h23, http_build_query()		
		Gui Add, GroupBox, x341 y416 w132 h76, JSON
		Gui Add, Button, gjson_encode x350 y432 w113 h23, json_encode()
		Gui Add, Button, gjson_decode x350 y459 w113 h23, json_decode()
		Gui Add, GroupBox, x485 y6 w133 h105, Date
		Gui Add, Button, gdate_1 x497 y24 w113 h23, date('d.m.Y H:i')
		Gui Add, Button, gdate_2 x497 y51 w113 h23, date('d.m.Y')
		Gui Add, Button, gstrtotime x497 y80 w113 h23, strtotime()
		Gui Add, GroupBox, x486 y115 w132 h377, Files
		Gui Add, Button, gis_dir x497 y135 w113 h23, is_dir()
		Gui Add, Button, gis_file x497 y161 w113 h23, is_file()
		Gui Add, Button, gfile_exists x497 y189 w113 h23, file_exists()
		Gui Add, Button, gdirname x497 y217 w113 h23, dirname()		
		Gui Add, Button, gbasename x497 y245 w113 h23, basename()		
		Gui Add, Button, g__FILE__ x497 y272 w113 h23, __FILE__
		Gui Add, Button, g__DIR__ x497 y298 w113 h23, __DIR__
		Gui Add, Button, grequire_once x497 y324 w113 h23, require_once()
		Gui Add, Button, gfile_get_contents x497 y351 w113 h23, file_get_contents()
		Gui Add, Button, gfile_put_contents x497 y378 w113 h23, file_put_contents()
		Gui Add, Button, grename x497 y405 w113 h23, rename()
		Gui Add, Button, gcopy x497 y432 w113 h23, copy()
		Gui Add, Button, gunlink x497 y459 w113 h23, unlink()

		Gui Show, w625 h498, PHP функции
		return

		get:
		GUI, Cancel
		send_text("$_GET['" . SELECT_TEXT . "']", 2)
		return

		post:
		GUI, Cancel
		send_text("$_POST['" . SELECT_TEXT . "']", 2)
		return	
		
		request:
		GUI, Cancel
		send_text("$_REQUEST['" . SELECT_TEXT . "']", 2)
		return
		
		cookie:
		GUI, Cancel
		send_text("$_COOKIE['" . SELECT_TEXT . "']", 2)
		return		
		
		session:
		GUI, Cancel
		send_text("$_SESSION['" . SELECT_TEXT . "']", 2)
		return
		
		server:
		GUI, Cancel
		send_text("$_SERVER['" . SELECT_TEXT . "']", 2)
		return	
        
		mt_rand:
		GUI, Cancel
		send_text("mt_rand(1, 1000)", 0)
		return	
        
		round:
		GUI, Cancel
		send_text("round(" . SELECT_TEXT . ", 2)", 4)
		return	
        
		floor:
		GUI, Cancel
		send_text("floor(" . SELECT_TEXT . ")", 1)
		return	
		
		ceil:
		GUI, Cancel
		send_text("floor(" . SELECT_TEXT . ")", 1)
		return		
		
		number_format:
		GUI, Cancel
		send_text("number_format(" . SELECT_TEXT . ", 2, ',', ' ')", 0)
		return		
		
		var_dump:
		GUI, Cancel
		send_text("var_dump(" . SELECT_TEXT . ")", 1)
		return	
		
		print_r:
		GUI, Cancel
		send_text("print_r(" . SELECT_TEXT . ")", 1)
		return	
		
		phpinfo:
		GUI, Cancel
		send_text("phpinfo()", 0)
		return	
		
		exit:
		GUI, Cancel
		send_text("exit(" . SELECT_TEXT . ")", 0)
		return	
		
		implode:
		GUI, Cancel
		send_text("implode('', " . SELECT_TEXT . ")", 1)
		return	
		
		trim:
		GUI, Cancel
		send_text("trim(" . SELECT_TEXT . ")", 1)
		return		
		
		str_replace:
		GUI, Cancel
		send_text("str_replace('', '', " . SELECT_TEXT . ")", 1)
		return	
		
		mb_strpos:
		GUI, Cancel
		send_text("mb_strpos(" . SELECT_TEXT . ", 'text')", 0)
		return	
		
		mb_strlen:
		GUI, Cancel
		send_text("mb_strlen(" . SELECT_TEXT . ")", 1)
		return			
		
		mb_sudstr:
		GUI, Cancel
		send_text("mb_sudstr(" . SELECT_TEXT . ", 0, 3)", 0)
		return		
		
		stripslashes:
		GUI, Cancel
		send_text("stripslashes(" . SELECT_TEXT . ")", 0)
		return	
		
		htmlspecialchars_decode:
		GUI, Cancel
		send_text("htmlspecialchars_decode(" . SELECT_TEXT . ", ENT_QUOTES)", 0)
		return	
			
		iconv:
		GUI, Cancel
		send_text("iconv('windows-1251//IGNORE', 'UTF-8//IGNORE', " . SELECT_TEXT . ")", 0)
		return	
		
		preg_replace:
		GUI, Cancel
		send_text("preg_replace('//', '$1', $text)", 0)
		return	
        
		preg_match:
		GUI, Cancel
		send_text("preg_match('//', $text)", 0)
		return		
		
		preg_match_all:
		GUI, Cancel
		send_text("preg_match('//', $text)", 0)
		return	
		
		preg_split:
		GUI, Cancel
		send_text("preg_match_all('//', $text)", 0)
		return	

		ob_start:
		GUI, Cancel
		send_text("ob_start()", 0)
		return	
		
		ob_get_clean:
		GUI, Cancel
		send_text("ob_get_clean()", 0)
		return	

		explode:
		GUI, Cancel
		send_text("explode(',', $text)", 0)
		return	
        
		count:
		GUI, Cancel
		send_text("count($array)", 0)
		return	
		
		in_array:
		GUI, Cancel
		send_text("in_array($array)", 0)
		return		
		
		array_key_exists:
		GUI, Cancel
		send_text("array_key_exists('key', $array)", 0)
		return	
		
		is_array:
		GUI, Cancel
		send_text("is_array($array)", 0)
		return	
		
		array_shift:
		GUI, Cancel
		send_text("array_shift($array)", 0)
		return		
				
		array_pop:
		GUI, Cancel
		send_text("array_pop($array)", 0)
		return		
        
		array_chunk:
		GUI, Cancel
		send_text("array_chunk($array, ceil(count($array) / 3))", 0)
		return		
        
		array_diff:
		GUI, Cancel
		send_text("array_diff($array, array(''))", 0)
		return		
        
		array_unique:
		GUI, Cancel
		send_text("array_unique($array)", 0)
		return	
		
		array_merge:
		GUI, Cancel
		send_text("array_merge($array, $array2)", 0)
		return	
		
		array_map:
		GUI, Cancel
		send_text("array_map('func', $array)", 0)
		return	
	    
		unset:
		GUI, Cancel
		send_text("unset($array[''])", 0)
		return	
		
		http_build_query:
		GUI, Cancel
		send_text("http_build_query($array)", 0)
		return		
		
		json_encode:
		GUI, Cancel
		send_text("json_encode($array, JSON_UNESCAPED_UNICODE)", 0)
		return		
		
		json_decode:
		GUI, Cancel
		send_text("json_decode($json, true)", 0)
		return			
		
		date_1:
		GUI, Cancel
		send_text("date('d.m.Y H:i')", 0)
		return	
		
		date_2:
		GUI, Cancel
		send_text("date('d.m.Y')", 0)
		return		
		
		strtotime:
		GUI, Cancel
		send_text("strtotime()", 0)
		return	
		
		is_dir:
		GUI, Cancel
		send_text("is_dir($path)", 0)
		return	
		
		is_file:
		GUI, Cancel
		send_text("is_file($filename)", 0)
		return	
		
		file_exists:
		GUI, Cancel
		send_text("file_exists($filename)", 0)
		return		
		
		dirname:
		GUI, Cancel
		send_text("dirname($path)", 0)
		return		
		
		basename:
		GUI, Cancel
		send_text("basename($filename)", 0)
		return		
		
		__FILE__:
		GUI, Cancel
		send_text("__FILE__", 0)
		return	
		
		__DIR__:
		GUI, Cancel
		send_text("__DIR__", 0)
		return		
		
		require_once:
		GUI, Cancel
		send_text("require_once('')", 0)
		return		
		
		file_get_contents:
		GUI, Cancel
		send_text("file_get_contents($filename)", 0)
		return	
		
		file_put_contents:
		GUI, Cancel
		send_text("file_put_contents($filename, $text)", 0)
		return		
		
		rename:
		GUI, Cancel
		send_text("rename($src, $filename)", 0)
		return		
		
		copy:
		GUI, Cancel
		send_text("copy($src, $filename)", 0)
		return		
		
		unlink:
		GUI, Cancel
		send_text("unlink($filename)", 0)
		return	
	}

	; Вывод кода нажатой клавиши
	;ToolTip % "Keyboard Key - Code: " code ", State: `r`n" state ",Ctrl: " CTRL_KEY ",Win: " WIN_KEY
}
AHK

Файл скрипта должен находится в C:\AutoHotInterception. Далее он компилируется, запускается и помещается в автозагрузку Windows.

В общей сложности получилось 190 команд – вставка HTML тегов и атрибутов, CSS свойства, SQL-запроссы, JS и PHP операторы, изминение регистра, вставка символов и т.д.

Обварачивание строк текста HTML-тегами:

Обварачивание строк текста HTML-тегами

Выравнивение списков:

Выравнивение списков

Форматирование CSS:

Форматирование CSS

Быстрая вставка PHP-функций:

Быстрая вставка PHP-функций
23.12.2021
388

Комментарии

, чтобы добавить комментарий.

Другие публикации

Замена раскладки на PHP
PHP функции для исправление неправильной раскладки клавиатуры в тексте и использование их в поиске по сайту.
6350
+6
Как отследить нажатие клавиш JQuery?
В событиях – keydown(), keyup(), keypress() можно получить нажатые клавиши в шести свойствах. Получить их можно из...
9612
+1
Горячие клавиши Google Chrome
Список сочетаний клавиш, которые можно использовать в Google Chrome для Windows и MacOS.
3727
+1
Javascript коды клавиш клавиатуры
Список кодов клавиш стандартной клавиатуры на Windows и MacOS...
33099
+1
Как ограничить ввод данных в текстовое поле
Примеры, приведенные ниже позволят ограничить ввод символов в текстовые поле. Например, можно ограничить количество...
16560
+2
Contenteditable – текстовый редактор
Если добавить атрибут contenteditable к элементу, его содержимое становится доступно для редактирования пользователю, а...
23488
+29