+7 919 711 99 12
metail@list.ru
  • Шрифт

  • 14

  • 16

  • 18

  • 20

  • 22

16 Ноября 2020

Постраничная навигация на PHP и MySQL


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

Начнём установку постраничной навигации на PHP и MySQL.

Есть база данных mysite с таблицей articles, в которой находится 20 статей. (Если базы данных нет совсем, то в статье ниже есть информация, как создать базу данных с необходимыми таблицами.)



Создание таблицы

В базе данных mysite создаём таблицу options вручную, через SQL запрос или через Импорт.


Вручную

1. Создаём таблицу options с двумя столбцами id и str.


2. Свойства столбца id: тип int, длина 2, A_I (auto increment) включен. Свойства столбца str: тип int, длина 10.


Вставляем в созданную таблицу одну строку. id = 1, str = 2. Цифра 2 означает количество статей на одной странице. В любое время её можно изменить.


Через SQL запрос

В базе данных mysite на вкладке SQL вставляем нижеприведённый код.


СветлаяТёмнаяПеренос 
--
-- Структура таблицы `options`
--
CREATE TABLE `options` (
  `id` int(2) NOT NULL,
  `str` int(10) NOT NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

--
-- Дамп данных таблицы `options`
--
INSERT INTO `options` (`id`, `str`) VALUES
(1, 2);

--
-- Индексы таблицы `options`
--
ALTER TABLE `options`
  ADD PRIMARY KEY (`id`);

--
-- AUTO_INCREMENT для таблицы `options`
--
ALTER TABLE `options`
  MODIFY `id` int(2) NOT NULL AUTO_INCREMENT, AUTO_INCREMENT=2;
COMMIT;

Через импорт

Скачиваем файл options.zip и добавляем его в базу данных mysite через Импорт.


Если базы данных нет совсем, то сначала создаём в MySQL пустую базу данных с именем mysite и импортируем туда таблицы articles.zip и options.zip.

Или ещё проще. Импортируем всю базу данных (обе таблицы) с автоматическим созданием базы данных: mysite.zip.

Теперь в базе данных mysite есть две таблицы: articles и options.


Подключение сайта к базе данных

Если сайт не подключен к базе данных, то нужно его подключить. Создаём файл connection.php, вставляем нижеприведённый код, и в коде меняем на свои имя пользователя, пароль пользователя и имя базы данных.

СветлаяТёмнаяПеренос 
<?php
$host = 'localhost'; // имя хоста
$user = 'root'; // имя пользователя
$pass = 'root'; // пароль пользователя
$database = 'mysite'; // имя базы данных
$connect = mysqli_connect( $host, $user, $pass, $database )or die( 'Нет связи с базой данных' );
$connect->query( "SET NAMES 'utf8' " );
$connect->query( "SET lc_time_names = 'ru_RU'" );
?>


Сейчас в начале страницы до тега <!doctype html> подключен файл подключения к базе данных и запрос к таблице articles. База данных возвращает массив с данными из всех полей таблицы articles.

СветлаяТёмнаяПеренос 
<?php
include( "connection.php" ); /*Соединяемся с базой данных*/
$query = mysqli_query( $connect, "SELECT * FROM articles ORDER BY id DESC", $db );
$myrow = mysqli_fetch_array( $query );
?>

Немного дополняем запрос к таблице articles и добавляем дополнительно ещё код. Код до тега <!doctype html> должен получится таким.

СветлаяТёмнаяПеренос 
<?php
include( "connection.php" ); /*Соединяемся с базой данных*/
/* Page navigation */
$result2 = mysqli_query( $connect, "SELECT str FROM options", $db );
$myrow2 = mysqli_fetch_array( $result2 );
$num = $myrow2[ "str" ];
// Извлекаем из URL текущую страницу
@$page = $_GET[ 'page' ];
// Определяем общее число сообщений в базе данных
$result3 = mysqli_query( $connect, "SELECT COUNT(*) FROM articles" );
$temp = mysqli_fetch_array( $result3 );
$posts = $temp[ 0 ];
// Находим общее число страниц
$total = ( ( $posts - 1 ) / $num ) + 1;
$total = intval( $total );
// Определяем начало сообщений для текущей страницы
$page = intval( $page );
// Если значение $page меньше единицы или отрицательно
// переходим на первую страницу
// А если слишком большое, то переходим на последнюю
if ( empty( $page )or $page < 0 )$page = 1;
if ( $page > $total )$page = $total;
// Вычисляем начиная с какого номера
// следует выводить сообщения
$start = $page * $num - $num;
// Выбираем $num сообщений начиная с номера $start
$query = mysqli_query( $connect, "SELECT * FROM articles ORDER BY id DESC, id LIMIT $start, $num", $db );
$myrow = mysqli_fetch_array( $query );
/* End page navigation */
?>

Сейчас на странице между тегами <body> </body> в цикле выводятся статьи.

СветлаяТёмнаяПеренос 
<?php
  do {
    printf(
      "<div class='article'>
        %s
      </div>",
      $myrow[ "article_text" ]
    );
  }
  while ( $myrow = mysqli_fetch_array( $query ) );
?>

Вставляем кнопки

Сразу после вывода статей вставляем кнопки постраничной навигации.

СветлаяТёмнаяПеренос 
<?php
  if ( $page - 5 > 0 )$page5left = '<a href=index.php?page=' . ( $page - 5 ) . '>' . ( $page - 5 ) . '</a>';
  if ( $page - 4 > 0 )$page4left = '<a href=index.php?page=' . ( $page - 4 ) . '>' . ( $page - 4 ) . '</a>';
  if ( $page - 3 > 0 )$page3left = '<a href=index.php?page=' . ( $page - 3 ) . '>' . ( $page - 3 ) . '</a>';
  if ( $page - 2 > 0 )$page2left = '<a href=index.php?page=' . ( $page - 2 ) . '>' . ( $page - 2 ) . '</a>';
  if ( $page - 1 > 0 )$page1left = '<a href=index.php?page=' . ( $page - 1 ) . '>' . ( $page - 1 ) . '</a>';

  if ( $page + 5 <= $total )$page5right = '<a href=index.php?page=' . ( $page + 5 ) . '>' . ( $page + 5 ) . '</a>';
  if ( $page + 4 <= $total )$page4right = '<a href=index.php?page=' . ( $page + 4 ) . '>' . ( $page + 4 ) . '</a>';
  if ( $page + 3 <= $total )$page3right = '<a href=index.php?page=' . ( $page + 3 ) . '>' . ( $page + 3 ) . '</a>';
  if ( $page + 2 <= $total )$page2right = '<a href=index.php?page=' . ( $page + 2 ) . '>' . ( $page + 2 ) . '</a>';
  if ( $page + 1 <= $total )$page1right = '<a href=index.php?page=' . ( $page + 1 ) . '>' . ( $page + 1 ) . '</a>';
  // Проверяем нужны ли стрелки назад
  if ( $page != 1 )$pervpage = '<a href=index.php?page=1><i class="fa fa-angle-double-left"></i></a><a href=index.php?page=' . ( $page - 1 ) . '><i class="fa fa-angle-left"></i></a>';
  // Проверяем нужны ли стрелки вперед
  if ( $page != $total )$nextpage = '<a href=index.php?page=' . ( $page + 1 ) . '><i class="fa fa-angle-right"></i></a><a href=index.php?page=' . $total . '><i class="fa fa-angle-double-right"></i></a>';
  // Находим две ближайшие станицы с обоих краев, если они есть
  // Вывод меню если страниц больше одной
  if ( $total > 1 ) {
    echo "<div id='pstrnav'>";
    echo $pervpage . $page5left . $page4left . $page3left . $page2left . $page1left . '<p id="pstrnav_activ">' . $page . '</p>' . $page1right . $page2right . $page3right . $page4right . $page5right . $nextpage;
    echo "</div>";
  }
?>

В файле style.css кнопкам пропишем стили.

СветлаяТёмнаяПеренос 
#pstrnav {
  text-align: center;
}
#pstrnav_activ {
  text-decoration: none;
  display: inline-block;
  font-weight: bold;
  background: #FF2727;
  border: 1px solid #fff;
  box-shadow: 0 0 0 1px #FF2727;
  color: #fff;
  padding: 6px 14px;
  margin: 1px 3px;
}
#pstrnav a {
  text-decoration: none;
  background: #2727FF;
  color: #fff;
  padding: 6px 12px;
  margin: 2px 3px;
  -webkit-transition: all 0.4s ease-in-out;
  -moz-transition: all 0.4s ease-in-out;
  -ms-transition: all 0.4s ease-in-out;
  -o-transition: all 0.4s ease-in-out;
  transition: all 0.4s ease-in-out;
}
#pstrnav a:hover {
  background: #FF2727;
  color: #fff;
  -webkit-transition: all 0.1s ease-in-out;
  -moz-transition: all 0.1s ease-in-out;
  -ms-transition: all 0.1s ease-in-out;
  -o-transition: all 0.1s ease-in-out;
  transition: all 0.1s ease-in-out;
}

Не обязательно, но для красоты можно добавить в файл .htaccess несколько строк, которые на всех страницах удаляют из адресной строки index.php и на первой странице постраничной навигации удаляют GET-параметр ?page=1. У меня сработал такой код, но не на всех серверах он будет работать.

СветлаяТёмнаяПеренос 
RewriteEngine on

RewriteRule ^(.*)$ https://%{HTTP_HOST}%{REQUEST_URI} [L,R=301]
RewriteRule ^index.php / [R]

RewriteCond %{QUERY_STRING} ^page=1$
RewriteRule ^(.*)$ /? [R=301,L]

Если страница с постраничной навигацией находится в папке, то нужно создать файл .htaccess в этой папке и добавить нижеприведённые строки. Не забудьте исправить пути к папке на свои.

СветлаяТёмнаяПеренос 
RewriteEngine on

RewriteRule ^(.*)$ https://%{HTTP_HOST}%{REQUEST_URI} [L,R=301]
RewriteRule ^index.php https://metail.ru/demo/pagenavigation/ [R]

RewriteCond %{QUERY_STRING} ^page=1$
RewriteRule ^(.*)$ https://metail.ru/demo/pagenavigation/? [R=301,L]

Готово.