(function ($) {
|
'use strict';
|
|
$.jqPaginator = function (el, options) {
|
if(!(this instanceof $.jqPaginator)){
|
return new $.jqPaginator(el, options);
|
}
|
|
var self = this;
|
|
self.$container = $(el);
|
|
self.$container.data('jqPaginator', self);
|
|
self.init = function () {
|
|
if (options.first || options.prev || options.next || options.last || options.page) {
|
options = $.extend({}, {
|
first: '',
|
prev: '',
|
next: '',
|
last: '',
|
page: ''
|
}, options);
|
}
|
|
self.options = $.extend({}, $.jqPaginator.defaultOptions, options);
|
|
self.verify();
|
|
self.extendJquery();
|
|
self.render();
|
|
self.fireEvent(this.options.currentPage, 'init');
|
};
|
|
self.verify = function () {
|
var opts = self.options;
|
|
if (!self.isNumber(opts.totalPages)) {
|
throw new Error('[jqPaginator] type error: totalPages');
|
}
|
|
if (!self.isNumber(opts.totalCounts)) {
|
throw new Error('[jqPaginator] type error: totalCounts');
|
}
|
|
if (!self.isNumber(opts.pageSize)) {
|
throw new Error('[jqPaginator] type error: pageSize');
|
}
|
|
if (!self.isNumber(opts.currentPage)) {
|
throw new Error('[jqPaginator] type error: currentPage');
|
}
|
|
if (!self.isNumber(opts.visiblePages)) {
|
throw new Error('[jqPaginator] type error: visiblePages');
|
}
|
|
if (!opts.totalPages && !opts.totalCounts) {
|
throw new Error('[jqPaginator] totalCounts or totalPages is required');
|
}
|
|
if (!opts.totalPages && opts.totalCounts && !opts.pageSize) {
|
throw new Error('[jqPaginator] pageSize is required');
|
}
|
|
if (opts.totalCounts && opts.pageSize) {
|
opts.totalPages = Math.ceil(opts.totalCounts / opts.pageSize);
|
}
|
|
if (opts.currentPage < 1 || opts.currentPage > opts.totalPages) {
|
throw new Error('[jqPaginator] currentPage is incorrect');
|
}
|
|
if (opts.totalPages < 1) {
|
throw new Error('[jqPaginator] totalPages cannot be less currentPage');
|
}
|
};
|
|
self.extendJquery = function () {
|
$.fn.jqPaginatorHTML = function (s) {
|
return s ? this.before(s).remove() : $('<p>').append(this.eq(0).clone()).html();
|
};
|
};
|
|
self.render = function () {
|
self.renderHtml();
|
self.setStatus();
|
self.bindEvents();
|
};
|
|
self.renderHtml = function () {
|
var html = [];
|
|
var pages = self.getPages();
|
for (var i = 0, j = pages.length; i < j; i++) {
|
html.push(self.buildItem('page', pages[i]));
|
}
|
|
self.isEnable('prev') && html.unshift(self.buildItem('prev', self.options.currentPage - 1));
|
self.isEnable('first') && html.unshift(self.buildItem('first', 1));
|
self.isEnable('statistics') && html.unshift(self.buildItem('statistics'));
|
self.isEnable('next') && html.push(self.buildItem('next', self.options.currentPage + 1));
|
self.isEnable('last') && html.push(self.buildItem('last', self.options.totalPages));
|
|
if (self.options.wrapper) {
|
self.$container.html($(self.options.wrapper).html(html.join('')).jqPaginatorHTML());
|
} else {
|
self.$container.html(html.join(''));
|
}
|
};
|
|
self.buildItem = function (type, pageData) {
|
var html = self.options[type]
|
.replace(/{{page}}/g, pageData)
|
.replace(/{{totalPages}}/g, self.options.totalPages)
|
.replace(/{{totalCounts}}/g, self.options.totalCounts);
|
|
return $(html).attr({
|
'jp-role': type,
|
'jp-data': pageData
|
}).jqPaginatorHTML();
|
};
|
|
self.setStatus = function () {
|
var options = self.options;
|
|
if (!self.isEnable('first') || options.currentPage === 1) {
|
$('[jp-role=first]', self.$container).addClass(options.disableClass);
|
}
|
if (!self.isEnable('prev') || options.currentPage === 1) {
|
$('[jp-role=prev]', self.$container).addClass(options.disableClass);
|
}
|
if (!self.isEnable('next') || options.currentPage >= options.totalPages) {
|
$('[jp-role=next]', self.$container).addClass(options.disableClass);
|
}
|
if (!self.isEnable('last') || options.currentPage >= options.totalPages) {
|
$('[jp-role=last]', self.$container).addClass(options.disableClass);
|
}
|
|
$('[jp-role=page]', self.$container).removeClass(options.activeClass);
|
$('[jp-role=page][jp-data=' + options.currentPage + ']', self.$container).addClass(options.activeClass);
|
};
|
|
self.getPages = function () {
|
var pages = [],
|
visiblePages = self.options.visiblePages,
|
currentPage = self.options.currentPage,
|
totalPages = self.options.totalPages;
|
|
if (visiblePages > totalPages) {
|
visiblePages = totalPages;
|
}
|
|
var half = Math.floor(visiblePages / 2);
|
var start = currentPage - half + 1 - visiblePages % 2;
|
var end = currentPage + half;
|
|
if (start < 1) {
|
start = 1;
|
end = visiblePages;
|
}
|
if (end > totalPages) {
|
end = totalPages;
|
start = 1 + totalPages - visiblePages;
|
}
|
|
var itPage = start;
|
while (itPage <= end) {
|
pages.push(itPage);
|
itPage++;
|
}
|
|
return pages;
|
};
|
|
self.isNumber = function (value) {
|
var type = typeof value;
|
return type === 'number' || type === 'undefined';
|
};
|
|
self.isEnable = function (type) {
|
return self.options[type] && typeof self.options[type] === 'string';
|
};
|
|
self.switchPage = function (pageIndex) {
|
self.options.currentPage = pageIndex;
|
self.render();
|
};
|
|
self.fireEvent = function (pageIndex, type) {
|
return (typeof self.options.onPageChange !== 'function') || (self.options.onPageChange(pageIndex, type) !== false);
|
};
|
|
self.callMethod = function (method, options) {
|
switch (method) {
|
case 'option':
|
self.options = $.extend({}, self.options, options);
|
self.verify();
|
self.render();
|
break;
|
case 'destroy':
|
self.$container.empty();
|
self.$container.removeData('jqPaginator');
|
break;
|
default :
|
throw new Error('[jqPaginator] method "' + method + '" does not exist');
|
}
|
|
return self.$container;
|
};
|
|
self.bindEvents = function () {
|
var opts = self.options;
|
|
self.$container.off();
|
self.$container.on('click', '[jp-role]', function () {
|
var $el = $(this);
|
if ($el.hasClass(opts.disableClass) || $el.hasClass(opts.activeClass)) {
|
return;
|
}
|
|
var pageIndex = +$el.attr('jp-data');
|
if (self.fireEvent(pageIndex, 'change')) {
|
self.switchPage(pageIndex);
|
}
|
});
|
};
|
|
self.init();
|
|
return self.$container;
|
};
|
|
$.jqPaginator.defaultOptions = {
|
wrapper: '',
|
first: '<li class="first"><a href="javascript:;">First</a></li>',
|
prev: '<li class="prev"><a href="javascript:;">Previous</a></li>',
|
next: '<li class="next"><a href="javascript:;">Next</a></li>',
|
last: '<li class="last"><a href="javascript:;">Last</a></li>',
|
page: '<li class="page"><a href="javascript:;">{{page}}</a></li>',
|
totalPages: 0,
|
totalCounts: 0,
|
pageSize: 0,
|
currentPage: 1,
|
visiblePages: 7,
|
disableClass: 'disabled',
|
activeClass: 'active',
|
onPageChange: null
|
};
|
|
$.fn.jqPaginator = function () {
|
var self = this,
|
args = Array.prototype.slice.call(arguments);
|
|
if (typeof args[0] === 'string') {
|
var $instance = $(self).data('jqPaginator');
|
if (!$instance) {
|
throw new Error('[jqPaginator] the element is not instantiated');
|
} else {
|
return $instance.callMethod(args[0], args[1]);
|
}
|
} else {
|
return new $.jqPaginator(this, args[0]);
|
}
|
};
|
|
})(jQuery);
|