Добавление модификаторов Fenom
Задался вопросом добавления своих модификатором в парсер Fenom для modx.
Из этого вышел простой модификатор |days, который правильно склоняет «дней», «дня», «день».
вызывать так:
Для всего этого перво-наперво создаем файлик в дириктории /core/model/modx/pdotools/pdotoolscustom.class.php с содержимым:
gist.github.com/soulcreate/bf202b14173f5d41717f
Да да, нам придется редактировать папку /core/model/modx/ — святая светых ядра modx. Но так делает и сам pdoTools, тем более мы ничего не удаляем\перезаписываем, а просто расширяем класс pdoTools своей функцией вызова fenom. При обновлении modx/pdoTools ничего не должно затереться.
Затем идем в системные настройки pdoTools и меняем pdoTools.class на
pdotools.pdotoolscustom:
Собственно все!
Таким образом, можно задействовать всю мощь fenom и в modx, не создавая кучу маленьких сниппетов-модификаторов.
Что-то мне подсказывает, это ключ для использования composer в modx. К примеру, можно вызывать там autoload.php и применять как модификаторы для переменных.
Из этого вышел простой модификатор |days, который правильно склоняет «дней», «дня», «день».
вызывать так:
{$dayscount|days}
Для всего этого перво-наперво создаем файлик в дириктории /core/model/modx/pdotools/pdotoolscustom.class.php с содержимым:
gist.github.com/soulcreate/bf202b14173f5d41717f
Да да, нам придется редактировать папку /core/model/modx/ — святая светых ядра modx. Но так делает и сам pdoTools, тем более мы ничего не удаляем\перезаписываем, а просто расширяем класс pdoTools своей функцией вызова fenom. При обновлении modx/pdoTools ничего не должно затереться.
Затем идем в системные настройки pdoTools и меняем pdoTools.class на
pdotools.pdotoolscustom:
Собственно все!
Таким образом, можно задействовать всю мощь fenom и в modx, не создавая кучу маленьких сниппетов-модификаторов.
Что-то мне подсказывает, это ключ для использования composer в modx. К примеру, можно вызывать там autoload.php и применять как модификаторы для переменных.
Комментарии: 15
Прикольно! Только советую переписать код вот так:
Надо будет придумать какой-то более удобный способ добавления модификаторов в следующей версии.
public function getFenom() {
$add = empty($this->fenom);
$fenom = parent::getFenom();
if ($add) {
$this->fenom->addModifier('days', function ($day) {
$a=substr($day,strlen($day)-1,1);
if($a==1) $str="день";
if($a==2 || $a==3 || $a==4) $str="дня";
if($a==5 || $a==6 || $a==7 || $a==8 || $a==9 || $a==0) $str="дней";
return $str;
});
}
return $fenom;
}
Надо будет придумать какой-то более удобный способ добавления модификаторов в следующей версии.
только почему-то в inline чанках не работает. пишет:
Modifier pricess not found in inline/0fd73cb4e653affba9947feef38d9944 line 1, near '{$price_jackpot|pricess' <- there
выяснил что pdofetch тоже надо расширять, т.к. он расширяет pdoTools напрямую, не смотря на системную настройку modx «pdoTools.class»
class pdoFetch extends pdoTools {...
PHP не умеет динамически расширять классы.
Нужно расширить еще и pdoFetch вот так:
В общем, советую переписать заметку и код по нашему обсуждению.
Нужно расширить еще и pdoFetch вот так:
<?php
if (!class_exists('pdoToolsCustom')) {
require 'pdotoolscustom.class.php';
}
class pdoFetchCustom extends pdoToolsCustom {
}
И указать его там же, в настройке pdoFetch.class — pdotools.pdofetchcustom.В общем, советую переписать заметку и код по нашему обсуждению.
тогда класс pdoFetchCustom не будет ничего знать о методах класса pdoFetch и будет вылезать ошибка:
Call to undefined method pdofetchcustom::run()
С чего это?
pdoFetchCustom extends pdoToolsCustom, а pdoToolsCustom extends pdoTools. Всё должно работать.
pdoFetchCustom extends pdoToolsCustom, а pdoToolsCustom extends pdoTools. Всё должно работать.
потому что в классе pdoTools нету функции run(), она в классе pdoFetch.
А, ясно.
Ну тогда можно подключить нужный класс без наследования, и вызывать из него публичные методы.
Ну тогда можно подключить нужный класс без наследования, и вызывать из него публичные методы.
да похоже на то. Пока не понял до конца этот механизм.
получилось с трейтами (на другом сайте была подобная задача, решил разобраться по-новой). Но только не для mfilter2, для pdoResources работает. Чуть позже скину решение.
в общем какой-то замкнутый круг получается. так и не удалось расширить класс pdoFetch с кустомерными модификаторами для безболезненного обновления pdoTools.
вот тут кстати советуют использовать композитный паттерн, либо eval:
вот тут кстати советуют использовать композитный паттерн, либо eval:
<?php
function dynamic_class_name() {
if(time() % 60)
return "Class_A";
if(time() % 60 == 0)
return "Class_B";
}
eval(
"class MyRealClass extends " . dynamic_class_name() . " {" .
# some code string here, possibly read from a file
. "}"
);
?>
более удобный способ -задать в системных настройках параметр «ID группы сниппетов для модификаторов» и все сниппеты из этой группы инициализировать как модификаторы fenom
Заслал Pull-request. Только там ошибка, вот так правильно:
if($opt = $this->modx->getOption('pdotools_fenom_category_snippet_modiffer', null, null, true)){
$snippets = $this->modx->getCollection('modSnippet',['category' => $opt]);
foreach($snippets as $snippet){
$nameSnippet = $snippet->name;
$modx = &$this->modx;
$this->fenom->addModifier($snippet->name, function ($input, $settings = []) use ($nameSnippet,&$modx){
if(is_array($settings)){
$settings = array_merge($settings,['input'=>$input]);
return $modx->runSnippet($nameSnippet,$settings);
}
else return $modx->runSnippet($nameSnippet,['input'=>$input]);
});
//echo $snippet->name."\r\n";
}
}
Иначе warning возникает на замыкание
Спасибо за PR, но:
1. если есть ошибка, нужно исправлять её в присланном коммите. Если не получается — удалить и прислать заново.
2. Комментарии типа
3. Очень странно вызывать modX::getCollection() в дополнении, которое его изо всех сил старается не использовать и даже пытается заменить своей версией.
Ну и сама идея тупо загружать все сниппеты из указанной категории элементов мне не нравится. Гораздо лучше было бы просто указать список сниппетов-фильтров через запятую в системной настройке.
В общем, за идею спасибо. Как будет время, попробую применить.
1. если есть ошибка, нужно исправлять её в присланном коммите. Если не получается — удалить и прислать заново.
2. Комментарии типа
//echo $snippet->name."\r\n";
нужно удалять3. Очень странно вызывать modX::getCollection() в дополнении, которое его изо всех сил старается не использовать и даже пытается заменить своей версией.
Ну и сама идея тупо загружать все сниппеты из указанной категории элементов мне не нравится. Гораздо лучше было бы просто указать список сниппетов-фильтров через запятую в системной настройке.
В общем, за идею спасибо. Как будет время, попробую применить.
Авторизуйтесь или зарегистрируйтесь, чтобы оставлять комментарии.