
технарь
Профессионал
Сообщений: 1830
Регистрация: 12.2011

|
ВступлениеНачиная с SMF версии 2.0 для добавления пользовательских функций не требуется каких-либо изменений в "основной" код.
Теперь для этого достаточно просто создать несколько отдельных файлов и написать соответствующий интеграционный обработчик.
Для понимания, как это работает в SMF, давайте взглянем, что обычно происходит при выполнении кода. Запуск корневого файла index.php приводит в частности к созданию массива $actionArray, где определены все стандартные функции SMF (например календарь, почта и т.д.).
Структура элементов этого массива следующая:
code:'myaction' => array('myaction_file.php', 'myaction_function'), где:
myaction - это название функции, для использования в URL (например http://www.yourdomain.tld/forum/index.php?action=myaction),
myaction_function - это функция, которую SMF должен будет вызвать,
myaction_file.php - это файл, который содержит функцию myaction_function.
Таким образом, что бы добавить на форум нужную функцию нам нужно подготовить файлы и прописать их интеграцию в массив $actionArray. Первое, что в данном случае нужно решить, это определиться с названием действия, которое мы хотим получить, именем функции для этого действия и именем файла, который будет эту функцию содержать.
Допустим для данного примера решили, что:
действие - youraction
функция - YourActionMain
файл - YourAction.php
Для удобства восприятия в дальнейшем мы эти параметры выделим красным цветом.
Создаём интеграционный файл
Назначением интеграционного файла по сути является внесение нужных изменений в базу данных. Этот файл запускается однократно, после чего его лучше с форума удалить. Для упрощения процедуры в SMF существует функция add_integration_function . Создадим чистый PHP файл с произвольным именем, например add_action_hook.php. В этот файл необходимо внести примерно такой код:
PHP:<?php
// Если SSI.php находится в том же месте, что и файл, а переменная SMF не определена, то подключаем файл.
if (file_exists(dirname(__FILE__) . '/SSI.php') && !defined('SMF'))
require_once(dirname(__FILE__) . '/SSI.php');
// Хмм... нет SSI.php и не определена переменная SMF?
elseif (!defined('SMF'))
die('<b>Ошибка:</b> Интеграция не удалась! Пожалуйста убедитесь, что вы поместили этот файл рядом с корневым index.php.');
add_integration_function('integrate_pre_include', '$sourcedir/Subs-YourAction.php');
add_integration_function('integrate_actions', 'youraction_add_hook');
?>
Как можно увидеть в коде присутствуют два интеграционных вызова:
integrate_pre_include - определяет файл, который содержит функцию youraction_add_hook
integrate_actions - определяет функцию, которая будет добавлена в массив $actionArray.
Создаем файлы с кодом
./Sources/Subs-YourAction.php
Этот файл должен содержать функцию youraction_add_hook. Он будет подгружаться каждый раз при вызове SMF, чтобы добавить наше действие в общий список. Этот файл должен быть помещен в каталог /Sources/.
Код данного файла должен быть примерно таким:
PHP:<?php
if (!defined('SMF')) die('Hacking attempt...');
function youraction_add_hook(&$actionArray)
{
$actionArray['youraction'] = array('YourAction.php', 'YourActionMain');
}
?>
./Sources/YourAction.php
Этот файл должен содержать функцию YourActionMain, срабатывающую при вызове youraction. Он так же должен быть помещен в каталог /Sources/.
Содержимое файла должно содержать по крайней мере одну функцию:
PHP:<?php
if (!defined('SMF')) die('Hacking attempt...');
function YourActionMain()
{
}
?>
Эта функция может включать в себя загрузку шаблона YourAction.template.php например так:
code:loadTemplate('YourAction');
При этом в этой функции будет необходимо определить такие параметры, как заголовок шаблона и древо ссылок.
В результате окончательный YourAction.php должен выглядеть примерно следующим образом:
PHP:<?php
if (!defined('SMF')) die('Hack Attempt...');
function YourActionMain()
{
// Прежде всего необходимо дать доступ ко всем нужным глобальным переменным
global $context, $scripturl, $txt, $smcFunc;
// Затем загрузить нужный для этого действия шаблон
loadTemplate('YourAction');
//Потом определить заголовок для главной страницы
$context['page_title'] = $txt['youraction_PageTitle'];
$context['page_title_html_safe'] = $smcFunc['htmlspecialchars'](un_htmlspecialchars($context['page_title']));
//Затем определить древо ссылок
$context['linktree'][] = array(
'url' => $scripturl. '?action=youraction',
'name' => $txt['your_action'],
);
//И наконец начать делать действия по выводу нужной информации
//Результаты этого вывода хранятся в массиве $context.
$context['youraction_Head'] = $txt['youraction'];
$context['youraction_Body'] = 'Hello World';
}
?>
Создаем шаблон
./Themes/default/YourAction.template.php
Как уже объяснялось ранее, файл YourAction.template.php должен содержать функцию шаблона, в данном случае template_main:
PHP:<?php
function template_main()
{
}
?>
Эта функция используется для отображения выходных данных при вызове действия youraction, и предназначена для создания выходных HTML данных посредством оператора echo.
Если предполагается создать заголовок и раздел с содержимым, нужно будет использовать примерно следующий код:
PHP:<?php
function template_main()
{
// Объявляем нужные глобальные переменные
global $context;
// Определяем заголовок класса "catbg"
echo '<div class="cat_bar">
<h3 class="catbg">', $context['youraction_Head'], '</h3>
</div>';
//Определяем содержимое классом "windowbg2"
echo '<div class="windowbg2">
<span class="topslice"><span></span></span>
<div class="content">', $context['youraction_Body'], '</div>
<span class="botslice"><span></span></span>
</div><br />';
}
?>
Файл YourAction.template.php должен быть помещен в каталог /Themes/default/.
Языковые файлы
./Themes/default/languages/Modifications.russian.php
Файлы вида Modifications.languages.php обычно используются для того, чтобы добавить новые строки в массив $txt. Таким образом можно легко перевести любой мод SMF на другие языки. Все эти файлы необходимо помещать в /Themes/default/languages/.
Чтобы добавить новую строку в массив $txt, достаточно добавить этот код:
PHP:// Ваши языковые переменные
$txt['youraction'] = 'Новая функция';
$txt['youraction_PageTitle'] = 'Заголовок страницы новой функции';
в файл Modification.russian.php или Modification.russian-utf8.php (в зависимости от нужной кодировки) и сохранить его.
./Themes/default/languages/Who.russian.php
Присутствующие в Modification.russian.php строки будут доступны повсюду в коде SMF. В некоторых случаях может быть полезно, чтобы некоторые строки были доступны только при определённых вызовах. Такие строки можно добавить в другие языковые файлы. Рассмотрим к примеру файл Who.russian.php - это файл подключается только тогда, когда кто-то обращается к странице через действие ?action=who .
После открытия файла нужно добавить в конец файла примерно такой код:
PHP:// Моя функция на странице "Кто онлайн"
$txt['whoall_youraction'] = 'Использует <a href="' . $scripturl . '?action=youraction">Новая функция</a>.';
Наконец, необходимо очистить кэш файлов для того, чтобы языковые переменные вступили в силу. Это можно сделать в Админка > Обслуживание > Обслуживание форума > Очистить файл кэша.
Осуществляем интеграцию
Загрузите ранее подготовленный файл add_action_hook.php в корневой каталог вашего форума (тот же каталог, который содержит SSI.php), а затем перейдите вашим браузером по ссылке httр://yourdomain.tld/forum/add_action_hook.php.
Если вы не получили каких-либо сообщений об ошибках, и вы видите пустую страницу - все прошло успешно, и вы можете удалить add_action_hook.php с сервера.
Смотрим результат
Перейдите в браузере по ссылке httр://yourdomain.tld/forum/index.php?action=youraction и вы должны увидеть на экране результат вашего действия!
Удаление интеграции
Чтобы удалить интеграцию, нужно выполнить два следующих действия:
1. Удалить все связанные файлы.
2. Удалить обработчики интеграции.
Для удаления обработчиков интеграции можно использовать файл, аналогичный add_action_hook.php, он может называться called remove_action_hook.php и должен содержать этот код:
PHP:<?php
// Если SSI.php находится в том же месте, что и файл, а переменная SMF не определена, то подключаем файл.
if (file_exists(dirname(__FILE__) . '/SSI.php') && !defined('SMF'))
require_once(dirname(__FILE__) . '/SSI.php');
// Хмм... нет SSI.php и не определена переменная SMF?
elseif (!defined('SMF'))
die('<b>Ошибка:</b> Удаление не удалось! Пожалуйста убедитесь, что вы поместили этот файл рядом с корневым index.php.');
remove_integration_function('integrate_pre_include', '$sourcedir/Subs-YourAction.php');
remove_integration_function('integrate_actions', 'youraction_add_hook');
?>
Файл должен быть загружен в корневой каталог форума, после чего вызван браузером по ссылке http://yourdomain.tld/forum/remove_action_hook.php, а затем удалён с сервера так же, как и add_action_hook.php.
Оригинал статьи расположен здесь. |