Шаблон новостей

Приведем пример шаблона новостей, с четырьмя представлениями, которые охватывают практически все задачи, которые могут возникнуть в связи с отображением новостей (кроме рассылки). В зависимости от различных условий, шаблон будет отображаться в одном из четырех видов.

  • "Новости" (по умолчанию)
    По умолчанию в новостном блоке должны быть показано 5 последних новостей. Каждая новость должна состоять из даты, заголовка новости, урезанного текста новости и уменьшенной фотографии (миниатюры).
  • "Архив новостей"
    При щелчке по ссылке "Архив новостей" должен отображаться список новостей, состоящий только из даты и заголова. На одной странице архива должно показываться не более 50 новостей.
  • "Одна новость"
    Из обоих представленией ("Архив новостей" и "Новости"), щелкнув по заголовоку новости, можно перейти на подробное отображение только одной новости (с датой, заголовком новости, полным текстом и большой фотографией). Должны быть ссылки на предыдущую и следующую новость, а также ссылка "Список новостей" для возврата на представление "Новости" или "Архив новостей" (в зависимости от того, с какого списка зашел пользователь).
  • "Новости коротко"
    Новости желательно также отображать не только на новостной странце (основной), но и на некоторых других страницах сайта (чужих). В этом представлении также, как в представлении "Новости" будем показывать 5 новостей, но в усеченном виде (только дату и заголовок новости).

На странице, отведенной для новостей, основному содержательному блоку нужно назначить шаблон news. В этом блоке будут работать первые три из перечисленных представлений. На остальных страницах сайта этот новостной блок нужно просто делегировать. При этом автоматически будет работать четвертое представление "Новости коротко"

В представлениях "Новости", "Архив новостей" и "Новости коротко" показывается ограниченное число новостей, поэтому в этих представлениях должны присутсвовать ссылки для показа других частей. Для этих целей специально формируется переменная $partsNav.

Остальные разъяснения смотрите в комментариях к коду.

Дескриптор news.tdd
<?php

    $titles = [
        1 => 'Дата',
        2 => 'Заголовок новости',
        3 => 'Текст новости',
        4 => 'Фото шириной 480px',
        5 => 'Фото шириной 220px (получается автоматически)',
    ];

    $types = [
        1 => 'date',
        2 => 'varchar(255)',
        3 => 'text',
        4 => 'file maxWidth(480)',
        5 => 'file maxWidth(220) maxHeight(165) sourceField(4)',
        // Если маленькое фото не закачивается, то используется большое фото.
    ];

    $params['multi-record'] = true;
    $params['backward'] = true; // Новости принято показывать в обратном порядке.
    $params['part']['limit'] = 5; // За один раз показывается только 5 новостей.

?>

Шаблон news.tpl
<?php

    if (empty($tab)) 
        return; // Если данных нет, то выйти
    $request = Request::get($block);
    
    # Лимит записей на странице "Архив новостей", отличный от лимита по умолчанию (5)
    $archLimit = 50;

    # В переменной $partsNav сохраним код для навигации по частям (для всех представлений).
    $partsNav = "<br>";
    # Ссылка на предыдущую часть
    if (empty($request['part']['prev'])) $partsNav .= "предыдущая ";
    else $partsNav .= "<a href='?page=$page&block=$block&part={$request['part']['prev']}'>предыдущая</a> ";
    # Ссылка на следующую часть
    if (empty($request['part']['next'])) $partsNav .= "следующая";
    else $partsNav .= "<a href='?page=$page&block=$block&part=$request['part']['next']'>следующая</a>";
    $partsNav .= "<br>";
    # Ссылки на страницы с разными номерами частей
    if ($request['part']['parts'])
    {
        foreach ($request['part']['parts'] as $p)
        {
            if ($p == $request['part']['current']) $partsNav .= "$p ";
            else $partsNav .= "<a href='?page=$page&block=$block&part=$p'>$p</a> ";
        }
    }


    # Представления на основной новостной странице.
    # Идентификатор регулярного блока совпадает и
    # идентификатором блока с данными, т.е. блок не делегирован.
    if ($block == $blockInfo['src-block-id'])
    {
        #################### "Одна новость" (подробно) ####################
        if ($_GET['single'])
        {
            # Ссылка для возврата на список "Новости" или "Архив новостей",
            # в зависимости от предыдущего состояния.
            echo "<a href='?page=$page'>Список новостей</a><br>";

            # Ссылка на предыдущую новость
            if ($tab['prev']['rec']) echo "
                <a href='?page=$page&block=$block&single={$tab['prev']['rec']}'>
                    предыдущая
                </a> 
            ";
            else echo "предыдущая ";
            # Ссылка на следующую новость
            if ($tab['next']['rec']) echo "
                <a href='?page=$page&block=$block&single={$tab['next']['rec']}'>
                    следующая
                </a>
            ";
            else echo "следующая";

            echo "
            <h1>$dat[2]</h1>
            {$dat['edit']}
            $dat[1]<br>
            $dat[3]<br>
            ";
            if ($dat[4]) echo "<img src='datafiles/$dat[4]'><br>";
        }

        #################### "Архив новостей" ####################
        elseif ($request['part']['limit'])
        {
            echo "
            <a href='?page=$page'>Последние новости</a>
            <h1>Архив новостей</h1>
            ";
            foreach ($tab as $dat)
            echo "
                {$dat['edit']}
                $dat[1]
                <a href='?page=$page&block=$block&single={$dat['rec']}'>$dat[2]</a><br>
            ";
            echo $partsNav;
        }

        ################# "Новости" (по умолчанию) #################
        # Для показа только начального фрагмента текста новости,
        # встроена функция strip_tags, удаляющая html-теги,
        # и функция substr, усекающая текст до 150 знаков.
        else
        {
            echo "
            <a href='?page=$page&block=$block&limit=$archLimit'>Архив новостей</a>
            <h1>Новости</h1>
            ";
            foreach ($tab as $dat)
            {
                echo "
                {$dat['edit']}
                $dat[1]<br>
                <a href='?page=$page&block=$block&single={$dat['rec']}'>
                    $dat[2]
                </a>
                <br>".substr(strip_tags($dat[3]), 0, 150)."...<br>
                <img src='datafiles/$dat[5]'><br><br>
                ";
            }
            echo $partsNav;
        }
    }
    
    ############### "Новости коротко" (на чужой странице) ##############
    # В этом коде есть редко используемые переменные шаблона $blockInfo['src-block-id'] и Blox::getBlockPageId($blockInfo['src-block-id'])
    # На чужой странице идентификатор блока отличается
    # от идентификатора блока на основной странице ($block != $blockInfo['src-block-id']).
    # Для просмотра одной записи нужно перейти на основную страницу (page=Blox::getBlockPageId($blockInfo['src-block-id'])).
    # Соответственно запросы должны относиться к основному блоку ($block==$blockInfo['src-block-id']).
    # После переходе на основную страницу, номер части нужно сделать такой же,
    # какая была на чужой странице (part=$request['part']['current']), чтобы при выходе из одиночной
    # записи на список (уже на основной странице), мы попали на такую же часть.
    else // $block != $blockInfo['src-block-id']
    {
        echo "<h2>Новости коротко</h2>";
        foreach ($tab as $dat)
        echo "
        {$dat['edit']}
        $dat[1]<br>
        <a href='?page=".Blox::getBlockPageId($blockInfo['src-block-id'])."&block={$blockInfo['src-block-id']}&single={$dat['rec']}'>
            $dat[2]
        </a><br>
        ";
        echo $partsNav;  // Навигацию по частям здесь можно и не помещать
    }

?>

См. также