Уже не первый год я вставляю сюда фрагменты кода. Для того, чтобы сгенерировать код с подсветкой, я использую команду :TOhtml вима, которая генерирует html-код с подсветкой текущего файла или выделенного фрагмента. Код html появляется в отдельном окне, содержит теги head и body, содержит теги br, которые здесь в блоггере не нужны, содержит кучу лишних переносов строк.
Поэтому создание кода с подсветкой занимало у меня некоторое время: сгенерировать, выполнить команду для удаления тегов br, удалить ненужные переносы строк, выделить фрагмент html-кода без тегов head, body, скопировать, закрыть окно, и, наконец, вставить html в нужное место.
Сегодня мне это окончательно надоело, и я автоматизировал этот процесс, сведя всё к одной кнопке.
Собственно, писать особо не о чем, приведу фрагменты кода, которые я разместил в свой _vimrc файл:
fun! Code(line1, line2)
" Исполняем встроенную команду TOhtml
" Она создаст в отдельном окне код html-странички
exec a:line1.','.a:line2.'TOhtml'
" Удаляет всё, что находится выше строки, которая содержит <body
%g/<body/normal k$dgg
" Хитрое выражение с регуляркой
" Оно обрабатывает содержимое открывающего тега body, извлекает
" значения параметров bgcolor и text, и заменяет этот тег body
" на открывающий тег font, в котором в качестве цвета указывается
" параметр, который находился в параметре text тега body
%s/<body\s*\(bgcolor="\#[a-f0-9]\{6\}"\)\s*text=\("\#[a-f0-9]\{6\}"\)\s*>/<font color=\2>/i
" Заменяет всё, что находится между закрывающим тегом body
" и закрывающим тегом html, на закрывающий тег font
%s#</body>\(.\|\n\)*</html>#</font>#i
" Удаляет все теги br
%s#<br>##i
" Удаляет лишний перенос строки после самой первой строки
normal ggJ
" Удаляет лишний перенос строки перед самой последней строкой
normal GkJ
" Компируем в буфер всё содержимое TODO: копировать в именованный
" буфер
normal ggVGy
" Выходим из окна, не сохраняя ничего
q!
" Вставляем вместо выделенного фрагмента получившийся код
normal gvp
endf
(Подсветка этого кода сгенерирована им самим же.)
Добавляем возможность вызова команды для выделенного промежутка строк:
command -range=% Code :call Code(<line1>,<line2>)
Наконец, вешаем всё это на клавишу F4:
vmap <F4> :Code<CR>
Как этим пользоваться: выделяем фрагмент кода, подсветку которого хотим сделать, жмём F4, и вуаля! Вместо фрагмента кода появляется html-код с подсветкой.
Чтобы проще было разобраться как работают команды внутри функции Code, опишу как можно выполнить эту функцию вручную и пошагово. Пусть у нас есть код, подсветку которого хочется сделать:
:a CreateWindowExA DWORD LPCTSTR LPCTSTR DWORD LONG LONG
LONG LONG HWND HMENU HINST LPVOID HWND user32;
:a DefWindowProcA HWND UINT WPARAM LPARAM LRESULT user32;
:a DestroyWindow HWND BOOL user32;
:a DispatchMessageA LPMSG LONG user32;
Выделяем его при помощи shift+v (в терминах вима S-V), выполняем
:'<,'>TOhtml
У нас открывается новое окно со следующим содержимым:
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<title>D:\proj\DForth\trunk\release\units\windows.de.html</title>
<meta name="Generator" content="Vim/7.3">
<meta http-equiv="content-type" content="text/html; charset=windows-1251">
</head>
<body bgcolor="#000000" text="#a8a8a8"><font face="monospace">
<font color="#8700d7">:a CreateWindowExA</font> DWORD LPCTSTR LPCTSTR DWORD LONG LONG <br>
LONG LONG HWND HMENU HINST LPVOID HWND <font color="#8700d7">user32;</font><br>
<font color="#8700d7">:a DefWindowProcA</font> HWND UINT WPARAM LPARAM LRESULT <font color="#8700d7">user32;</font><br>
<font color="#8700d7">:a DestroyWindow</font> HWND BOOL <font color="#8700d7">user32;</font><br>
<font color="#8700d7">:a DispatchMessageA</font> LPMSG LONG <font color="#8700d7">user32;</font><br></font>
</body>
</html>
Выполняем
:%g/<body/normal k$dgg
, удаляется всё, что выше body:
<body bgcolor="#000000" text="#a8a8a8"><font face="monospace">
<font color="#8700d7">:a CreateWindowExA</font> DWORD LPCTSTR LPCTSTR DWORD LONG LONG <br>
LONG LONG HWND HMENU HINST LPVOID HWND <font color="#8700d7">user32;</font><br>
<font color="#8700d7">:a DefWindowProcA</font> HWND UINT WPARAM LPARAM LRESULT <font color="#8700d7">user32;</font><br>
<font color="#8700d7">:a DestroyWindow</font> HWND BOOL <font color="#8700d7">user32;</font><br>
<font color="#8700d7">:a DispatchMessageA</font> LPMSG LONG <font color="#8700d7">user32;</font><br></font>
</body>
</html>
Теперь выполним сперва
:%s/<body\s*\(bgcolor="\#[a-f0-9]\{6\}"\)\s*text=\("\#[a-f0-9]\{6\}"\)\s*>/<font color=\2>/i
затем
:%s#</body>\(.\|\n\)*</html>#</font>#i
Первая команда затронет строку, в которой открывается body, вторая -- строки, в которой закрываются body и html:
<font color="#a8a8a8"><font face="monospace">
<font color="#8700d7">:a CreateWindowExA</font> DWORD LPCTSTR LPCTSTR DWORD LONG LONG <br>
LONG LONG HWND HMENU HINST LPVOID HWND <font color="#8700d7">user32;</font><br>
<font color="#8700d7">:a DefWindowProcA</font> HWND UINT WPARAM LPARAM LRESULT <font color="#8700d7">user32;</font><br>
<font color="#8700d7">:a DestroyWindow</font> HWND BOOL <font color="#8700d7">user32;</font><br>
<font color="#8700d7">:a DispatchMessageA</font> LPMSG LONG <font color="#8700d7">user32;</font><br></font>
</font>
Удаляем все теги br:
:%s#<br>##i
Получаем:
<font color="#a8a8a8"><font face="monospace">
<font color="#8700d7">:a CreateWindowExA</font> DWORD LPCTSTR LPCTSTR DWORD LONG LONG
LONG LONG HWND HMENU HINST LPVOID HWND <font color="#8700d7">user32;</font>
<font color="#8700d7">:a DefWindowProcA</font> HWND UINT WPARAM LPARAM LRESULT <font color="#8700d7">user32;</font>
<font color="#8700d7">:a DestroyWindow</font> HWND BOOL <font color="#8700d7">user32;</font>
<font color="#8700d7">:a DispatchMessageA</font> LPMSG LONG <font color="#8700d7">user32;</font></font>
</font>
Наконец, удаляем первый перенос строки и последний:
ggJ
GkJ
Получаем:
<font color="#a8a8a8"><font face="monospace"> <font color="#8700d7">:a CreateWindowExA</font> DWORD LPCTSTR LPCTSTR DWORD LONG LONG
LONG LONG HWND HMENU HINST LPVOID HWND <font color="#8700d7">user32;</font>
<font color="#8700d7">:a DefWindowProcA</font> HWND UINT WPARAM LPARAM LRESULT <font color="#8700d7">user32;</font>
<font color="#8700d7">:a DestroyWindow</font> HWND BOOL <font color="#8700d7">user32;</font>
<font color="#8700d7">:a DispatchMessageA</font> LPMSG LONG <font color="#8700d7">user32;</font></font> </font>
Всё, код полностью готов для вставки в блог.
Комментариев нет:
Отправить комментарий