Войти Регистрация

jQuery перелистывание - эффект перелистывания страниц на jquery


jquery перелистываниеЭффект перелистывания страницы, наиболее часто создается с помощью Flash анимации. В интернете этот эффект набирает популярности в онлайн журналах и презентациях. Это связано с реализацией этого эффекта в ebook и мобильных устройствах.

В этой статье мы будем использовать PHP и плагин turns.js, которые позволят реализовать эффект перелистывания страницы на чистом CSS3 и jQuery. Мы возьмем наиболее популярные картинки из Instagram.com и создадим красивый журнал.

Ссылку на ДЕМО смотрите в комментариях, в конце статьи. Также скачайте архив скрипта, и протестируйте на своем компютере.

HTML

Прежде всего нам нужно понять основы этого примера. Мы будем использовать простой дизайн странички, который совмещает HTML5 разметку и PHP в одном файле. Так будет проще понимать. Вы можете видеть результат выполнения ниже:

index.php

<!DOCTYPE html>
<html>
    <head>
        <meta charset="utf-8" />
        <title>jQuery эффект перелистывания | Sitear.ru</title>

        <!-- наши стили -->
        <link rel="stylesheet" href="assets/css/styles.css" />

        <!--[if lt IE 9]>
          <script src="http://html5shiv.googlecode.com/svn/trunk/html5.js"></script>
        <![endif]-->
    </head>

    <body>

		<div id="magazine" class="centerStart">

		<!-- PHP будет здесь -->

		</div>

        <!-- JavaScript подключения - jQuery, turn.js и наш написаный script.js -->
		<script src="http://code.jquery.com/jquery-1.7.1.min.js"></script>
		<script src="assets/js/turn.js"></script>
		<script src="assets/js/script.js"></script>

    </body>
</html>

Здесь мы подключаем style.css, в head, и javascript файлы внизу. Далее мы подключаем еще 3 js файла: библиотека jQuery, turn.js, script.js, в котором мы будем инициализировать плагин и принимать события клавиатуры. PHP код, который мы напишем немножечко позже, будет выполнятся в #magazine div блоке. PHP будет генерировать странички нашего журнала, которые будут нужны для turn.js.

Как пример, вы можете посмотреть на три первых страницы журнала, сгенерированных с помощью PHP:

<div id="page1" class="page">
	<div class="img1">

		<!-- pageNum span может быть как правой так и левой страницей -->

		<span class="pageNum right">1 // 32</span>
		<img src="assets/img/cover.jpg" alt="Cover" />
	</div>
</div>

<div id="page2" class="page">
	<div class="img2">
		<span class="pageNum left">2 // 32</span>
		<img src="http://distilleryimage7.instagram.com/..." alt="Little tulips" />
	</div>
</div>

<div id="page3" class="page">
	<div class="img3">
		<span class="pageNum right">3 // 32</span>
		<img src="http://distilleryimage2.instagram.com/..." alt="My style" />
	</div>
</div>

Код который вы видели, полностью лежит в блоке #magazine div. Это единственное, что нужно для turns.js. Вам не нужно создавать какие-то специальные классы или дата атрибуты для элементов, которые будут интерпретированы в странички. На этом мы готовы приступить к написанию PHP кода!

jquery эффект перелистывания страницы

PHP

PHP будет соединяться с Intagram API, кешировать результаты, и генерировать разметку, которую вы видели выше.

Первым шагом будет регистрация Instagram девелоперского сайта. После чего вы получите client_id ключ, который вставим как значение в переменную $instagramClientID, в файле index.php. Мы не нуждаемся в расширенной функциональности API, мы просто запросим наиболее популярные картинки. Это освободит нас от использования дополнительной OAuth аутентификации, которая только утруднит понимание кода.

Ниже пример JSON ответа текущих популярных картинок от Instagram. Я скрыл некоторые атрибуты, чтобы сделать код более понятным.

{    "meta": {
        "code": 200
    },
    "data": [{
        "tags": ["beautiful", "sky"],
        "location": "null",
        "comments": {
            "count": 31,
            "data": [...]
        },
        "filter": "Normal",
        "created_time": "1331910134",
        "link": "http:\/\/instagr.am\/p\/IPNNknqs84\/",
        "likes": {
            "count": 391,
            "data": [..]
        },
        "images": {
            "low_resolution": {
                "url": "http:\/\/distilleryimage8.instagram.com\/03c80dd86f7911e1a87612313804ec91_6.jpg",
                "width": 306,
                "height": 306
            },
            "thumbnail": {
                "url": "http:\/\/distilleryimage8.instagram.com\/03c80dd86f7911e1a87612313804ec91_5.jpg",
                "width": 150,
                "height": 150
            },
            "standard_resolution": {
                "url": "http:\/\/distilleryimage8.instagram.com\/03c80dd86f7911e1a87612313804ec91_7.jpg",
                "width": 612,
                "height": 612
            }
        },
        "caption": {
            "created_time": "1331910148",
            "text": "Goodnight.\ue056",
            "from": {
                "username": "jent99",
                "profile_picture": "http:\/\/images.instagram.com\/profiles\/profile_6227738_75sq_1319878922.jpg",
                "id": "6227738",
                "full_name": "jent99"
            },
            "id": "148395540733414783"
        },
        "type": "image",
        "id": "148395420004568888_6227738",
        "user": {
            "username": "jent99",
            "website": "",
            "bio": "Mostly nature pics.\ue32b\ue32b\ue32b Hope you like them.\ue056\ue32a     \ue334gi\ue334                    ",
            "profile_picture": "http:\/\/images.instagram.com\/profiles\/profile_6227738_75sq_1319878922.jpg",
            "full_name": "jent99",
            "id": "6227738"
        }
    }, {
		/* Здесь идет больше фотографий... */
	}]
}

API ограничивается 32 последними картинками, но этого вполне достаточно для нашего примера. Вы можете видеть, что каждое фото имеет три размера, но мы будем использовать только один. Также здесь присутствует дополнительная информация о тегах, комментариях, и так далее.

PHP будет кешировать результаты этого API запроса. Таким образом, мы будем получать последние картинки каждый час. Это сделает наше приложение более быстрым и ограничит количество обращений к API.

index.php

// Вы можете получить client ID из Instagram API страницы
$instagramClientID = '-- вставьте свой client id ключ здесь --';

$api = 'https://api.instagram.com/v1/media/popular?client_id='.$instagramClientID;
$cache = 'cache.txt';

if(file_exists($cache) && filemtime($cache) > time() - 60*60){
	// Если файл кэша существует и он
	// свежее нежели 1 час, будем использовать его
	$images = unserialize(file_get_contents($cache));
}
else{
	// Создаем API запрос и генерируем файл кэша

	// Получаем 32 популярные фотографии на Instagram
	$response = file_get_contents($api);

	$images = array();

	// Декодируем ответ и создаем массив
	foreach(json_decode($response)->data as $item){

		$title = '';

		if($item->caption){
			$title = mb_substr($item->caption->text,0,70,"utf8");
		}

		$src = $item->images->standard_resolution->url;

		$images[] = array(
			"title" => htmlspecialchars($title),
			"src" => htmlspecialchars($src)
		);
	}

	// Удаляем последнюю картинку, но мы будем иметь
	// 32 картинки, когда добавим обложку
	array_pop($images);

	// Добавляем обложку в начале массива
	array_unshift($images,array("title"=>"Cover", "src"=>"assets/img/cover.jpg"));

	// Обновляем файл кэша
	file_put_contents($cache,serialize($images));
}

// создаем разметку
$totalPages = count($images);
foreach($images as $i=>$image){

	?>

	<div id="page<?php echo $i+1?>" class="page">
		<div class="img<?php echo $i+1?>">
			<span class="pageNum <?php echo ($i+1)%2? 'right' : 'left'?>"><?php echo $i+1?> // <?php echo $totalPages?></span>
			<img src="<?php echo $image['src']?>" alt="<?php echo $image['title']?>" />
		</div>
	</div>

	<?php

}

Кеширование реализовано просто: мы используем временный файл – cache.txt – чтобы сохранить репрезентацию массива картинок. Если файл не существует или создан позже одного часа назад, мы создадим новый API запрос.

Обратите внимание на функции array_pop и array_unshift. Это необходимо для создания ячейки для картинки обложки, которая хранится в assets/img. Журнал работает лучше, если мы имеем равное количество страниц, иначе мы не сможем перелистывать последнюю страничку. Это будет выглядеть не естественно.

Теперь мы готовы к написанию плагина перелистывания страниц!

jQuery

Использование turns.js до нельзя простое. Если мы имеем готовую разметку журнала, нам нужно всего лишь вызвать turn() метод. Также мы будем воспринимать события нажатия стрелок на клавиатуре, которые будут запускать перелистывания страницы.

assets/js/script.js

$(function(){

	var mag = $('#magazine');

	// Инициализируем turn.js для #magazine div
	mag.turn();

	// turn.js определяет собственные события. Мы воспринимаем
	// события нажатия клавиш и центрируем
	mag.bind('turned', function(e, page, pageObj) {

		if(page == 1 && $(this).data('done')){
			mag.addClass('centerStart').removeClass('centerEnd');
		}
		else if (page == 32 && $(this).data('done')){
			mag.addClass('centerEnd').removeClass('centerStart');
		}
		else {
			mag.removeClass('centerStart centerEnd');
		}

	});

	setTimeout(function(){
		// Оставим немножко время для инициализации плагина
		// потом показываем журнал
		mag.fadeTo(500,1);
	},1000);

	$(window).bind('keydown', function(e){

		// Воспринимаем события нажатия клавиш

		if (e.keyCode == 37){
			mag.turn('previous');
		}
		else if (e.keyCode==39){
			mag.turn('next');
		}

	});

});

Вот такой простой jquery плагин перелистывания страниц. В принципе все понятно из комментариев кода. Теперь сделаем наш журнал привлекательным!

CSS

Нам нужно уточнить размеры журнала, стиль страничек и номеров. turns.js сделает все остальное.

assets/css/styles.css

#magazine{
	width:1040px;
	height:520px;
	margin:0 auto;
	position:relative;
	left:0;

	opacity:0;

	-moz-transition:0.3s left;
	-webkit-transition:0.3s left;
	transition:0.3s left;
}

#magazine .page{
	width:520px;
	height:520px;
	background-color:#ccc;
	overflow:hidden;
}

/* Центрируем журнал, когда показана обложка */
#magazine.centerStart{
	left:-260px;
}

/* Центрируем журнал, когда показана последняя страница */
#magazine.centerEnd{
	left:260px;
}

.page img{
	height:520px;
	width:520px;
	display:block;
}

/* Показываем темную тень */
.centerStart .turn-page-wrapper:first-child{
	box-shadow:0 0 10px #040404;
}

/* Номера страниц */

span.pageNum{
    background-color: rgba(0, 0, 0, 0.3);
    bottom: 25px;
    box-shadow: 0 0 3px rgba(0, 0, 0, 0.25);
    color: #FFFFFF;
    font-size: 11px;
    height: 24px;
    line-height: 22px;
    opacity: 0.9;
    position: absolute;
    text-align: center;
    width: 55px;
}

span.pageNum.left{
	left:0;
	right:auto;
}

span.pageNum.right{
	left:auto;
	right:0;
}

/* Скрываем номера страниц на обложке */
#page1 .pageNum{
	display:none;
}

На этом наш журнал с эффектом jquery перелистывания страниц готов!

Мы сделали!

Этот пример работает в последних версиях браузеров – Firefox, Chrome, Safari, Opera и даже IE. Этот эффект перелистывания также работает на iOS и Android. Вы можете использовать этот эффект как часть фотогалерей, как шаблон для онлайновых журналов. Хотя вам придется создать другую версию для старых браузеров, которые не поддерживают этого.

На этом все! Если имеете вопросы по поводу jquery перелистывания, пишите в комментарии.


Источник материала ...

Дальше: Семантическая верстка: понятие и примеры семантического кода


Дискуссия по теме    30 Комментариев
Добавить комментарий
Алмат 04.01.2016 в 18:18
Спасибо
Олег 07.04.2015 в 09:24
Недостаток turn.js в том, что страница дергается и "разфокусируется", когда мышь наводишь на уголок и он чуть сгибается. Это можно слегка поправить, если в turn.js в функции transform = function(tr, c, x, a) {... заключить операторы "that.css(cssA).transform" и "data.wrapper.transform(" в условие: if (a!=45 88 a!=-45 88 gradientSize>0){ that.css(cssA).transform(rotate(a) translate(tr.x aliasingFk, tr.y, ac), origin); data.wrapper.transform(translate(-tr.x mvW-aliasingFk, -tr.y mvH, ac) rotate(-a), origin);} (здесь 88-это два знака "амперсанд", иначе не удавалось написать комментарий.) Правда, теперь за этим уголком виден кусочек не следующей страницы, а этой же. Но это терпимо и исправляется при нажатии кнопки на мыши.
Дмитрий 19.05.2014 в 17:34
Разместил галерю на временном сайте http://kushiy.myjino.ru, но отображается очень коряво пока. В css изменял высоту и ширину галери. Не могу понять почему не видны страницы галереи? И напишите пожалуйста, можно на почту, как в instragram получить пробные картинки, ip подключил, но там совершенно непонятно. И Вы не написали куда внедрять код от instragram
Дмитрий 19.05.2014 в 12:25
А как происходит расчет высоты и ширины класса "turn-page-wrapper"? Мне нужно совершенно другие выставить размеры, а как непонятно?
ACIRIC 24.06.2013 в 03:01
Не плохо было бы костыль для IE
Тарас 24.06.2013 в 13:35
Вот, у Вас есть возможность реализовать это.
Андрей 27.05.2013 в 11:56
как сделать, чтобы угол отворачивался при наведении на страницу?
Алексей 20.05.2013 в 12:35
тоже себе искал информацию как сделать книги с эффектом листания... все какое-то кривое блин... нашел единственное решение - программу flippingbook publisher http://luxedition.ru вот только она платная, но зато листалки красивые, но прога платная :)
morten 16.05.2013 в 13:39
Скрипт интересный, но его работа малость кривая. Переход с одной страницы на две - рваный, перелистывание идёт по прямой без радиусов. Центральные точки плавают, нет теней и т.д. Для простого проекта пойдёт, но вот для презентаьельного имхо не катит
Алекс 04.05.2013 в 11:36
Интересует тоже как определить четные нечетные страницы, расскажите как сделать. Спасибо!
Тарас 04.05.2013 в 20:20
$('.page:even') - этот селектор вернет все четные элементы с классом .page $('.page:odd') - вернет нечетные элементы с классом .page должно быть так: $('.page:odd').click(function(){ $('#magazine').turn('previous'); }); $('.page:even').click(function(){ $('#magazine').turn('next'); });
Максим 30.04.2013 в 15:48
Как можно перелистывать страницу при клике на нее.
Тарас 30.04.2013 в 23:19
$('.page').click(function(){ $('#magazine').turn('next'); }); только будет перелистывать вперед. Можно еще определить четные и нечетные. Если кликать на четные то вперед, и соответственно нечетные назад.
Юлия 14.04.2013 в 15:42
Работает отлично, но привязка к instagram'у не делалась за ненадобностью. Вот есть вопрос только. Можно ли сделать так, чтобы id станицы книг отображалась в адресной строке ? На сайте плагина в примерах (напр. про Стива Джобса) именно так и происходит - на развороте в адресной строке id каждой четной. Просто надо будет выкладывать ссылки на определенные страницы журнала. Гиперссылками с якорями не выходит, конечно. Спасибо !
Тарас 20.04.2013 в 16:26
Если URL типа site.com/magazine/page/12 то можно сделать так: var pageUrl = document.URL; var arrUrl = pageUrl.split('/'); var pageNumber = arrUrl[3]; сначала получаем урл из адресной строки, потом разбиваем на массив [site.com magazine page 12]. Четвертым элементом массива будет страница журнала.
Silver Soft 28.05.2013 в 09:37
менять адресную строку можно так: window.history.replaceState({}, '', '/page/' currentPage);
Ирина 06.11.2012 в 20:46
Спасибо за jquery перелистывания. Возникла проблема: перестал работать, хотя сначала все было ок. Может подскажете что. Мой jquery перелистывания размещен http://www.spasbog.org.ua/health1.php
Тарас 07.11.2012 в 14:53
Раньше работало с этими же картинками или другими? Может быть размер не подходит? Что меняли, после чего перестало работать?
Валентин 18.09.2012 в 21:04
Только не понятно как сделать журнал из картинок, которые будут на хостинге, не инстаграмовские
Тарас 18.09.2012 в 22:46
Какая разница? В файле php, просто берем не инстаграмовские а свои с хостинга... помещаем информацию в массив, потом через foreach читаем этот массив и формируем разметку для каждой страницы. Пример разметки, второй пример кода в этой статье.
Олег 18.09.2012 в 17:29
А насколько сложно будет задать вертикальное перелистывание (блокнотное, снизу вверх)?
Тарас 18.09.2012 в 22:59
Незнаю как это сделать... Если честно, не очень то и нравиться этот плагин... браузер тупит постоянно, нет поддержки старых версий браузеров. Вообщем, красиво и интересно, но на практике мало применимо.
Asya 14.08.2012 в 11:36
А есть ли здесь возможность изменить ширину одной страницы, а остальные оставить по умолчанию?
Тарас 14.08.2012 в 12:59
В стилях CSS прописать для конкретной страницы. Например: #page2 .page { width:300px; }
Asya 11.08.2012 в 19:24
Тарас, спасибо огромное и за отличную статью и за быстрый ответ! Вы очень помогли!!!
Asya 11.08.2012 в 11:06
Здравствуйте! А Вы можете подсказать, как сделать так, чтобы при открытии сайта была не обложка журнала, а сразу разворот из двух страниц? Это нужно править в самом файле turn.js? или как-то проще можно сделать?
Тарас 11.08.2012 в 13:45
Можно при завершении загрузки страницы вызвать mag.turn('next'); что перевернет из обложки на развернутую сторону, будет в виде анимации. Или после mag.turn(); в фале script.js пишем ту же строку mag.turn('next'); это перевернет из обложки на следующую страницу еще до появления журнала на старнице.
Оксана 14.07.2012 в 10:41
Не работает в IE
Тарас 14.07.2012 в 15:28
Печально.
Тарас 24.03.2012 в 14:50
Вот обещанная ссылка на ДЕМО версию: http://demo.tutorialzine.com/2012/03/instagram-magazine-php-jquery/
Добавить комментарий
Просмотров: 37028