文档章节

PHP+jQuery寥寥几行代码轻松实现百度搜索那样的无刷新PJAX的分页列表和导航链接

eechen
 eechen
发布于 2016/12/08 17:15
字数 787
阅读 1328
收藏 10


PHP寥寥几行代码轻松实现百度搜索那样的分页列表和导航链接,某些语言的拥趸哭晕在厕所.

<?php

$app = array(
	'db_prefix' => 'phpbest_',
	'db_sqlite' => '/dev/shm/phpbest/phpbest.db3',
);

//数据库连接单例
function db() {
	global $app;
	static $db;
	if($db) {
		return $db;
	} else {
		try {
			$db = new PDO('sqlite:'.$app['db_sqlite']);
		} catch(PDOException $e) {
			echo $e->getMessage();
			exit();
		}
		return $db;
	}
}

//分页导航链接
function page_nav($page, $page_size = 10, $before = 5, $after = 4) {
	$page = intval($page);
	$page_size = intval($page_size);
	global $app;
	$db = db();
	$table = $app['db_prefix'].'post';
	$arr = $db->query("SELECT count(id) FROM $table")->fetchAll(PDO::FETCH_NUM);
	$records = $arr[0][0]; //记录数
	$pages = ceil($records/$page_size); //页数
	if($pages == 0) return;
	if($page <= 0 || $page > $pages) return;
	
	$html = '<p>当前页:前输出5页,后输出4页</p>';
	$html .= '<a href="?page=1">最前</a>';
	if($page != 1) { $html .= '<a href="?page='.($page - 1).'">上一页</a>'; }
	if($page <= $before) { for($i = 1; $i < $page; $i++) { $html .= '<a href="?page='.$i.'">第'.$i.'页</a>'; } }
	else { for($i = $page - $before; $i < $page; $i++) { $html .= '<a href="?page='.$i.'">第'.$i.'页</a>'; } }
	$html .= '<a href="?page='.$page.'">第'.$page.'页(当前页)</a>';
	if($pages >= $page + $after) { for($i = $page + 1; $i <= $page + $after; $i++) { $html .= '<a href="?page='.$i.'">第'.$i.'页</a>'; } }
	else { for($i = $page + 1; $i <= $pages; $i++) { $html .= '<a href="?page='.$i.'">第'.$i.'页</a>'; } }
	if($page != $pages) { $html .= '<a href="?page='.($page + 1).'">下一页</a>'; }
	$html .= '<a href="?page='.$pages.'">最后</a>';
	return $html;
}

//分页列表内容
function page_list($page, $page_size = 10) {
	$page = intval($page);
	$page_size = intval($page_size);
	global $app;
	$db = db();
	$table = $app['db_prefix'].'post';
	$offset = ($page - 1) * $page_size;
	return $db->query("SELECT * FROM $table ORDER BY id DESC LIMIT $page_size OFFSET $offset")->fetchAll(PDO::FETCH_ASSOC);
}

?>

<div class="content pjax">
	<?php echo page_nav($_GET['page'], 2); ?>
	<ul>
	<?php
		foreach(page_list($_GET['page'], 2) as $v) {
			echo '<li>'.$v['id'].'</li>';
			echo '<li>'.$v['title'].'</li>';
			echo '<li>'.$v['content'].'</li>';
			echo '<li>'.date('Y-m-d H:i:s', strtotime($v['date'])).'</li><br>';
		}
	?>
	</ul>
</div>
<script type="text/javascript" src="jquery.pjax.js"></script>
<script>
(function($){
	$(function(){
		//调用插件,用户点击链接后局部刷新class为pjax(要求唯一)的块并写入历史记录
		$(document).pjax("a:not([target='_blank'])", ".pjax");
	});
})(jQuery);
</script>

jquery.pjax.js是我写的一个插件,代码简单到差不多每个人都看得懂:

/* jquery.pjax.js */
(function($){
	$.fn.pjax = function(selector, container) {
		
		//IE8之流不支持HTML5 onpopstate,自然不会执行插件
		if("onpopstate" in window) {
			
			//AJAX加载函数
			var load = function(href) {
				var time = 600;
				$(document).trigger("pjax:start", [time]); //执行开发者的自定义事件(如:显示加载进度条)
				var start = new Date().getTime();
				$.ajax({
					type: "GET",
					url: href,
					data: {_pjax_: new Date().getTime()}
				}).done(function(data){
					//在回调函数中解析出head中的title和body中的指定块并更新(这样服务器端就不需要改变输出格式)
					var dom = $("<div>").html(data);
					document.title = dom.find("title").first().text();
					$(container).first().html(dom.find(container).first().html());
					var spend = new Date().getTime() - start;
					setTimeout(function(){
						$(document).trigger("pjax:done"); //执行开发者的自定义事件(如:隐藏加载进度条)
					}, spend >= time ? 0 : time - spend);
				});
			};
			
			history.replaceState({href:location.href}, "", location.href);
			
			window.onpopstate = function() {
				//用户点击后退和前进按钮时触发该事件
				if(history.state != null) {
					load(history.state.href);
				}
			}
			
			$(container).on("click", selector, function(e){
				//用户点击页面链接时改变地址栏(URL)并写入历史记录以及AJAX加载页面
				e.preventDefault();
				var href = $(this).attr("href");
				if(href != "javascript:void(0)") {
					history.pushState({href:href}, "", href);
					load(href);
				}
			});
		}
	};
})(jQuery);

不支持PJAX的浏览器如IE8会自动退化成原始的链接打开的方式,所以采用PJAX的站点也是可以兼容IE8的.

© 著作权归作者所有

共有 人打赏支持
eechen

eechen

粉丝 980
博文 107
码字总数 55962
作品 1
深圳
加载中

评论(9)

xiaose1205
xiaose1205
哎,还在自我陶醉。估计是刚毕业的
eechen
eechen
@notreami @DevYang
JS在服务器的运行环境(Node)跟浏览器差别很大.
在服务器Node是以一个独立的守护进程运行,
代码稍有不慎就可能导致进程崩溃退出,
而且修改代码需要重启Node进程才能生效(那些自动化工具nodemon/pm2本质也是重启服务).
服务器的PHP跟浏览器的JS反而更像,都是提供一个比较稳定的容器来执行脚本.
比如你很难写出让PHP容器(如PHP-FPM和Apache)发生崩溃的PHP代码.
浏览器也会尽量避免因为网站JS的问题导致的崩溃.
比如浏览器Chrome跟PHP-FPM用的都是多进程架构,
子进程崩溃并不会影响主进程,主进程可以重新启动一个子进程提供服务.

PHP的热部署特性大大方便了开发和运维,这点是Java等其他语言(包括Python/RoR/Node.JS)所不能媲美的.
基于HTML/CSS/JS的界面编程之所以流行,很大程度也是因为它们的"热部署"特性,修改代码刷新页面就生效了.
DevYang
DevYang
Node + CoffeeScript 笑而不语:relieved:
notreami
notreami
web上直接js就够了,php用处太小,扔了吧。。
西南茂
西南茂
厉害了我的天pjax。。。
踏雪无痕丶
踏雪无痕丶
自黑?
eechen
eechen

引用来自“蜗牛君”的评论

几行代码。。。。。
关键就2行:
分页导航链接: echo page_nav($_GET['page']);
PJAX无刷新加载: $(document).pjax("a:not([target='_blank'])", ".pjax");
狂暴的蜗牛君
狂暴的蜗牛君
几行代码。。。。。
php整合pjax(pushstate+ajax)实现无刷新页面

PJAX效果 通过url可以跟踪ajax的动态加载内容。这种技术尤其在two step view布局的视图中有很大的好处。无刷新加载页面,意味着响应速度和用户体验得到了极大的提升,在静态脚本和通用模块比...

_EKC
2012/10/01
0
2
PHP+jQuery实现Ajax分页效果:jPaginate插件的应用

jPaginate是基于jQuery的动感滚动分页插件,它的表现形式是像分页的按钮一样,非常有意思的是这些按钮却可以滚动,可以通过单击或鼠标滑向点两侧的小箭头来控制按钮的前后滚动。 调用jPagina...

mickelfeng
2013/12/28
0
2
习习风/pjaxpage

Download the compressed, production pjaxPage 1.1 Download the uncompressed, development pjaxPage 1.1 1. Quick Start 1.1 HTML Code Here is the minimal HTML code to get pages work......

习习风
2017/09/12
0
0
Pjax是什么以及为什么推荐大家用

什么是pjax? 现在很多网站( facebook, twitter)都支持这样的一种浏览方式, 当你点击一个站内的链接的时候, 不是做页面跳转, 而是只是站内页面刷新。 这样的用户体验, 比起整个页面都闪一...

Sub
2013/04/17
0
33
关于pjax方式无刷新加载网页?

pjax使用不成功啊,已经成功发出了pjax请求了,但是瞬间请求就abort,然后又采用刷新的方式加载,什么问题? 我的做法: 1.加入jquery、pjax的js包 2.前台对a标签作pjax处理,主要是a标签选择...

小薇
2013/04/23
3.5K
5

没有更多内容

加载失败,请刷新页面

加载更多

下一页

(一)软件测试专题——之Linux常用命令篇01

本文永久更新地址:https://my.oschina.net/bysu/blog/1931063 【若要到岸,请摇船:开源中国 不最醉不龟归】 Linux的历史之类的很多书籍都习惯把它的今生来世,祖宗十八代都扒出来,美其名曰...

不最醉不龟归
20分钟前
3
0
蚂蚁金服Java开发三面

8月20号晚上8点进行了蚂蚁金服Java开发岗的第三面,下面开始: 自我介绍(要求从实践过程以及技术背景角度着重介绍) 实习经历,说说你在公司实习所做的事情,学到了什么 关于你们的交易平台...

edwardGe
26分钟前
7
0
TypeScript基础入门 - 函数 - this(三)

转载 TypeScript基础入门 - 函数 - this(三) 项目实践仓库 https://github.com/durban89/typescript_demo.gittag: 1.2.4 为了保证后面的学习演示需要安装下ts-node,这样后面的每个操作都能...

durban
36分钟前
0
0
Spark core基础

Spark RDD的五大特性 RDD是由一系列的Partition组成的,如果Spark计算的数据是在HDFS上那么partition个数是与block数一致(大多数情况) RDD是有一系列的依赖关系,有利于Spark计算的容错 RDD中每...

张泽立
44分钟前
0
0
如何搭建Keepalived+Nginx+Tomcat高可用负载均衡架构

一.概述 初期的互联网企业由于业务量较小,所以一般单机部署,实现单点访问即可满足业务的需求,这也是最简单的部署方式,但是随着业务的不断扩大,系统的访问量逐渐的上升,单机部署的模式已...

Java大蜗牛
58分钟前
0
0

没有更多内容

加载失败,请刷新页面

加载更多

下一页

返回顶部
顶部