GeSHi (Generic Syntax Highlighter) позволяет подсвечивать синтаксис кода, написанного любом из более 80 языков. GeSHi использует подключаемые файлы с описанием синтаксиса языков, что обеспечивает простоту добавления новых описаний. GeSHi написан на PHP. В настоящей статье мы рассмотрим использование GeSHi для автоматической подсветки синтаксиса в тексте статей или сообщений на сайте.
Cкачаем GeSHi 1.0.7.21 с SourceForge. Мы напишем функцию, обеспечивающую подсветку кода, расположенного внутри специального BBCode-тега [syntax]. Например, код внутри [syntax=php] [/syntax] будет подсвечен с использованием синтаксиса PHP. Кроме того, в названии языка можно использовать специальные символы: # - в подсвеченном коде строки будут пронумерованы, * - код будет подсвечен в режиме inline (span вместо div). Например, [syntax=*mysql]SHOW PROCESSLIST[/syntax] будет выглядеть как
SHOW PROCESSLIST
А
[syntax=#php]
<?php
function hellow() {
echo "Hello, world!";
}
?>
[/syntax]
будет выглядеть так:
<?php
function hellow() {
echo "Hello, world!";
}
?>
Среди подсвечиваемых по-умолчанию языков - bash, c, c++, css, delphi, diff, fortran, html, java, javascript, latex, matlab, mysql, oracle, perl, php, python, rails, ruby, smarty, sql, tcl, xml и другие. Языковые файлы находятся в каталоге geshi дистрибутива. Мы будем выполнять подсветку с использованием CSS, для этого потребуется требуется сгенерировать css, используя contib/cssgen.php, входящий в дистрибутив. cssgen.php попросит выбрать языки для включения в стилевой файл и цвета для подсветки различных элементов. Не забудьте включить ссылку на сгенерированный css-файл в заголовок страниц сайта.
Приведенный ниже код определяет функцию syntax_filter(), подсвечивающую код, внутри тегов [syntax]. Данную функцию следует включить в цепочку функций, обрабатыващих материалы сайта при формировании HTML-страницы. Обратите внимание, что в случае подсветки HTML, код внутри тегов [syntax] [/syntax] должен быть написан в чистом виде, GeSHi самостоятельно преобразует его в HTML-сущности.
<?php
require_once("geshi/geshi.php");
function syntax_filter($text) {
$search = '/\[syntax=(.*?)\]\r?\n?(.*?)\r?\n?\[\/syntax\]/is';
return preg_replace_callback($search, 'syntax_filter_callback', $text);
}
function syntax_filter_callback($data) {
$linenumbers = false;
$urls = false;
$inline = false;
$indentsize = 4;
if (isset($data[2])) {
$syntax = $data[1];
$code = $data[2];
if(strstr($syntax, '*')) {
$inline = true;
$syntax=str_replace('*','',$syntax);
}
if(strstr($syntax, '#')) {
$linenumbers = true;
$syntax=str_replace('#','',$syntax);
}
if ($syntax=='html') {
$syntax = 'html4strict';
}
if ($syntax=='js') {
$syntax = 'javascript';
}
$geshi =& new GeSHi($code, $syntax);
$geshi->set_header_type(GESHI_HEADER_DIV);
$geshi->enable_classes(true);
$geshi->set_overall_style('font-family: monospace;');
if($linenumbers) {
$geshi->enable_line_numbers(GESHI_FANCY_LINE_NUMBERS, 5);
$geshi->set_line_style('color:#222;', 'color:#888;');
$geshi->set_overall_style('font-size: 14px;font-family: monospace;', true);
}
if (!$urls) {
for ($i = 0; $i < 5; $i++) {
$geshi->set_url_for_keyword_group($i, '');
}
}
if ($indentsize) {
$geshi->set_tab_width($indentsize);
}
$parsed = $geshi->parse_code();
if($inline) {
$parsed = preg_replace('/^<div/','<span', $parsed);
$parsed = preg_replace('/<\/div>$/','</span>', $parsed);
}
}
return $parsed;
}
?>
|