Разделы

Прямой эфир

Весь эфир | RSS

Snippet prevnextPage



Вероятно у всех рано или поздно возникает необходимость создать ссылки на предыдущую и следующую страницы в папке.

Собственно для этого мною и был написан сниппет prevnextPage

Он делает простую вещь, устанавливает плейсхолдеры [+pnp_prev+] и [+pnp_next+]. Шаблон плейсхолдера можно задать как в коде так и в чанке. Можно установить префикс для плейсхолдеров, для множественного вызова на странице.

Сниппет проверит, если он вызван в документе, который не расположен в интересующей нас папке, то он благоразумно оставит плейсхолдеры пустыми.

В общем не вижу преград для его использования =)

<?php
/**
 * @name prevnextPage
 * @author Gorbarov Iliya at gorbarov.ru
 * @version 1.1
 * @desc Создает ссылки на предыдущую и следующую страницы
 *
 * Сниппет устанавливает плейсхолдеры [+pnp_prev+] [+pnp_next+]
 *
 * В плейсхолдерах находятся ссылки на предыдущую и следующую страницы, в зависимости от настроек сниппета
 * Плейсхолдеры устанавливаются только для документов в папке c &folderId
 *
 * &folderId - id папки
 * &sortBy - поле в базе данных для сортировки, например pub_date
 * &sortDir - Порядок сортировки ASC или DESC
 * &showHidden - Показывать скрытые пункты в меню, по умолчанию - 0
 * &letsCycle - Зациклить ссылки, по умолчанию - нет.
 * &prevTpl - Чанк для предыдущей ссылки
 * &nextTpl - Чанк для следующей ссылки
 * &id - Префикс плейсхолдеров для мультивызовов. По умолчанию 'pnp_'
 * &nextClass - CSS класс
 * &prevClass - CSS класс
 * &directOutput - Выводить результат напрямую, по умолчанию - использовать плейсхолдеры
 * &directOutputTpl - Шаблоны прямого вывода, строка, по умолчанию, [+prev+] | [+next+]
 *
 * Пример самого "обычного вызова": [[prevnextPage? &directOutput=`1`]]
 *
 */

if (!isset($folderId)) $folderId = 'parent';
if (!isset($sortBy)) $sortBy = 'menuindex';
if (!isset($sortDir)) $sortDir = 'ASC';
if (!isset($showHidden)) $showHidden = 0;
if (!isset($letsCycle)) $letsCycle = 0;
if (!isset($nextTpl) || !isset($prevTpl)) $useBuildInTpl = true;
if (!isset($nextClass)) $nextClass = '';
if (!isset($prevClass)) $prevClass = '';
if (!isset($directOutput)) $directOutput = 0;
if (!isset($directOutputTpl)) $directOutputTpl = '[+prev+] | [+next+]';
if (!isset($prevTpl)) $prevTpl = '<a href="[~[+id+]~]" class="'.$prevClass.'" title="[+pagetitle+]">[+pagetitle+]</a>';
if (!isset($nextTpl)) $nextTpl = '<a href="[~[+id+]~]" class="'.$nextClass.'" title="[+pagetitle+]">[+pagetitle+]</a>';
if (!isset($id)) $id = 'pnp_';

if (!function_exists('parseString')) {
    function parseString($tpl,$data,$prefix = '[+',$suffix = '+]') {
        foreach($data as $k => $v) {
            $tpl = str_replace($prefix.(string)$k.$suffix, (string)$v, $tpl);
        }
        return $tpl;
    };
}

$curId = $modx->documentIdentifier;
if ($folderId == 'parent') $folderId = array_pop($modx->getParentIds($curId,1));

$docs = $modx->getDocumentChildren ($folderId, 1, 0, 'id, pagetitle, parent', 'hidemenu = '.$showHidden, $sortBy, $sortDir, '');

foreach ($docs as $key=>$doc) {
    if ($doc['id'] == $curId) $curKey = $key;
}

$curDoc = $docs[$curKey];
$next = $docs[$curKey + 1];
$prev = $docs[$curKey - 1];

if (!isset($next) && $letsCycle) {
    $next = $docs[0];
}

if (!isset($prev) && $letsCycle) {
    $prev = $docs[count($docs) - 1];
}

if ($useBuildInTpl) {
    $rNext = parseString($nextTpl,array('id'=>$next['id'],'pagetitle'=>$next['pagetitle']));
    $rPrev = parseString($prevTpl,array('id'=>$prev['id'],'pagetitle'=>$prev['pagetitle']));
} else {
    $rNext = $modx->parseChunk($nextTpl,array('id'=>$next['id'],'pagetitle'=>$next['pagetitle']),'[+','+]');
    $rPrev = $modx->parseChunk($prevTpl,array('id'=>$prev['id'],'pagetitle'=>$prev['pagetitle']),'[+','+]');
}

if ($curDoc['parent'] == $folderId) {
    if ($directOutput) {
        echo parseString($directOutputTpl,array('next' => $rNext, 'prev' => $rPrev));
    } else {
        if (isset($next)) $modx->setPlaceholder($id.'next',$rNext);
        if (isset($prev)) $modx->setPlaceholder($id.'prev',$rPrev);
    }
}
?>


Как использовать?

А очень просто, достаточно вызвать сниппет в коде страницы и в нужном месте вставить плейсхолдеры [+pnp_prev+] и [+pnpNext+].

Или указать параметр &directOutput и тогда сниппет вернет результат выполнения и не будет устанавливать плейсхолдеры.

Также важно задать для сниппета порядок и поле по которому будет производится сортировка документов.

Пример:

[[prevnextPage?directOutput=`1`]]


Кажется все, пользуйтесь! =)

UPD: Теперь версия 1.1:
— Учитывать или не учитывать скрытые в меню пункты
— Теперь можно «зацикливать» ссылки
— Использовать или не использовать плейсхолдеры
— Ну и упростил код, чтобы его было удобней модифицировать под свои нужды
  • +9
  • 27 апреля 2010, 12:27
  • pitbull

Комментарии (40)

RSS свернуть / развернуть
0
Спасибо, Илья! :)
avatar

style-nes

  • 27 апреля 2010, 12:41
+1
почему бы по-умолчанию не делать folderId равной [*parent*]?
ведь это наверное 99% случаев применения?
avatar

antonkuzmin

  • 27 апреля 2010, 12:56
0
а ведь и правда! =)
avatar

pitbull

  • 27 апреля 2010, 13:07
+1
и еще было бы удобно, если б можно было класс ссылке задавать параметром, например &class=`sidenav` и он подставлялся бы в тег
<a class="sidenav">...</a>


а сниппет нужный :)
avatar

antonkuzmin

  • 27 апреля 2010, 13:11
0
Ну для этого шаблоны prevTpl-nextTpl и сделаны в принципе-то =)
avatar

pitbull

  • 27 апреля 2010, 13:15
0
это лишний чанк создавать. гораздо быстрее вписывается класс :)
avatar

antonkuzmin

  • 27 апреля 2010, 13:22
0
Тогда сниппет подправить проще, не? =)

Вон Breadcrumbs вообще шаблон в сниппете и без вариантов =)

Кстати, обновил код, чтобы по умолчанию был parent.
avatar

pitbull

  • 27 апреля 2010, 13:24
0
Сейчас прикрутил на готовый сайт и первым делом пришлось прописать css класс!

Посему, добавились два параметра ;)
avatar

pitbull

  • 27 апреля 2010, 14:04
+1
avatar

Andchir

  • 27 апреля 2010, 21:05
+1
Спасибо, но когда искал я не нашел решения, поэтому сделал.

К тому же изобретение велосипедов развивает скилл разработчика =)
avatar

pitbull

  • 27 апреля 2010, 22:37
0
Это да. Выбор тоже хорошо :)
avatar

Andchir

  • 27 апреля 2010, 23:12
0
выбор безусловно это хорошо, но субъективно какое лучше решение?
pitbull +1 безусловно… при любом раскладе :)
avatar

skmskm

  • 8 мая 2010, 20:29
0
Не знаю =)

Я свое использовал, мне было достаточно ;)
avatar

pitbull

  • 10 мая 2010, 21:25
0
Случайно нашел еще одно изделие на эту тему: habrahabr.ru/blogs/modx/71722/
avatar

pitbull

  • 14 мая 2010, 09:31
0
Это дело конечно хорошее, и впринцепе все эти переключалки страниц похожи одна на одну. Но вот у меня возникла другая задача, чтобы страницы выбирались из одной папки, но переключать можно было по-тематике (tv-параметру), что-то вроде filter в функции ditto. К сожалению колдуя над ditto 100% решения так и не нашел. :(
avatar

z211

  • 15 мая 2010, 13:32
+1
В тексте «Как использовать?» и примере опечатка [+pnpNext+] --> [+pnp_next+]

Поставил, все работает.
Спасибо за сниппет.
avatar

sdp

  • 22 мая 2010, 17:27
0
Спасибо, исправил, наслаждайтесь ;)
avatar

pitbull

  • 24 мая 2010, 14:35
комментарий был удален

0
Хороший сниппет, но неплохо было бы добавить параметр «не показывать документы не показываемы в меню», удобно если хочешь что-бы не перескакивало на некоторые доки из папки.

И ещё хорошо зациклить это дело, чтобы последний документ в папке ссылался на первый, можно тоже как параметр сделать да / нет.

P.S. Вначале поставил его, но пришлось отказаться к сожалению из-за того что показывает скрытые для других доки, которые не видны в меню. Но автору респект, просто и со вкусом…
avatar

SDee

  • 15 сентября 2010, 20:31
0
Вот действительно такие бы возможности реализовать.
А может есть в каком-нить из подобных?
avatar

Akool

  • 1 октября 2010, 13:12
0
Сделать это несложно, вот только некогда, но если надо очень, то можно ;)
avatar

pitbull

  • 1 октября 2010, 13:21
0
Жду с нетерпением :)
avatar

SDee

  • 6 октября 2010, 14:14
0
А версия для Revo будет?)
avatar

Pahom-ka

  • 20 сентября 2010, 19:36
0
Ну как начну Revo использовать и потребуется такая возможность =)
avatar

pitbull

  • 1 октября 2010, 13:21
0
Когда же уже будет новая версия, руки чешутся на сайт прикрутить сей девайс :)
avatar

SDee

  • 9 октября 2010, 16:34
0
Пардноьте, но не раньше чем через неделю =)
avatar

pitbull

  • 9 октября 2010, 16:39
0
Ну как там время не появилось? :)
avatar

SDee

  • 21 октября 2010, 14:34
0
Ну как, руки не дошли? :)
avatar

SDee

  • 2 ноября 2010, 17:03
0
Дошли, спасибо за насточивость!
avatar

pitbull

  • 25 ноября 2010, 14:01
+1
Теперь версия 1.1:
— Учитывать или не учитывать скрытые в меню пункты
— Теперь можно «зацикливать» ссылки
— Использовать или не использовать плейсхолдеры
— Ну и упростил код, чтобы его было удобней модифицировать под свои нужды
avatar

pitbull

  • 25 ноября 2010, 14:11
0
Шикарно! Спасибо, сегодня попробую поставить.
avatar

SDee

  • 25 ноября 2010, 16:48
0
А я правильно понял, что если не указывать id, то он просто будет листать в текущей папке? А то у меня для 5 папок шаблон одинаковый, сниппет внутри папки каждой тогда будет листать или сразу все папки?
avatar

SDee

  • 26 ноября 2010, 19:30
0
По умолчанию внутри папки листает.
avatar

pitbull

  • 26 ноября 2010, 20:14
0
Спасибо за ответ
avatar

SDee

  • 26 ноября 2010, 22:16
0
Просто не хотелось бы ради листалки делать пять шаблонов :( и в каждом указывать ид папки.
avatar

SDee

  • 26 ноября 2010, 19:31
0
Теперь бы ещё у кого-нибудь руки дошли до реализации этого вопроса :) community.modx-cms.ru/blog/questions/1145.html вещь для сео весьма полезная!
avatar

SDee

  • 27 ноября 2010, 00:19
0
Отличный сниппет, часто использую его, еще раз спасибо автору!
Возникла необходимость прицепить тв-параметр документа к ссылкам вперед-назад, как это можно реализовать? Просто есть необходимость подцеплять к конопочкам маленькие превьюшки в статьях.

Спасибо!
avatar

SDee

  • 21 марта 2011, 15:04
0
Большое спасибо!

Особенно порадовала гибкость настроек
avatar

Anysidor

  • 23 марта 2011, 20:05
0
Так и не ответили по поводу «тв-параметр документа к ссылкам вперед-назад» (
avatar

SDee

  • 14 июля 2011, 16:02
0
В отчете просмотр событий пишется ошибка на снипете
«Only variables should be passed by reference»
В чем может быть дело, что не так?
Evo 1.0.5
avatar

w3d

  • 16 января 2012, 16:52

Только зарегистрированные и авторизованные пользователи могут оставлять комментарии.