You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

147 lines
5.4 KiB

!function ($) {
"use strict";
function ninjaSelect(element, options) {
this.$element = $(element);
this.options = $.extend({}, $.fn.ninjaSelect.defaults, options);
this.page = 1;
this.init();
}
ninjaSelect.prototype = {
constructor: ninjaSelect,
init: function() {
var self = this, allow = true;
self.$div = $('<div>', {'id': 'ninja_' + this.$element.attr('id'), 'class': 'ninjaSelect'}),
self.$input = $('<input>'),
self.$list = $('<div>', {'class': 'ninjaSelect_wrapper'}).hide();
self.$selected = $('<div>', {'class': 'ninjaSelect_selected'});
self.$ul = $('<ul>', {'class': 'ninjaSelect_list'});
self.$element.hide().after(
self.$div.append(
self.$input, self.$selected, self.$list.append(
self.$ul
)
)
);
self.$input.on('keyup', function(e) {
self.loadData($(this).val());
});
self.$ul.delegate('li', 'click', function(e) {
var id = $(this).data().id, allow = true;
self.$selected.show().find('.ninjaSelect_item').each(function() {
if ($(this).data().id == id) {
allow = false;
}
});
if (!self.options.multiple && $('.ninjaSelect_item').length == 1) {
allow = false;
}
if (allow) {
$(this).addClass('active');
self.$selected.append(
$('<div>', {'class': 'ninjaSelect_item'}).data({'id': id, 'index': $(this).index()}).text($(this).text()).click(function() {
self.$ul.find('li').eq($(this).data().index).removeClass('active');
$(this).next().remove().end().remove();
if (!self.$selected.find('.ninjaSelect_item').length) {
self.$selected.hide()
}
}),
$('<input>', {'type': 'hidden', 'name': $(this).text() + '_' + id}).val($(this).text())
)
}
});
self.$list.mousewheel(function(e, delta) {
if (delta < 0) {
if ($(this).scrollTop() + $(this).innerHeight() >= self.$ul.innerHeight() && allow) {
allow = false;
self.loadData(self.$input.val(), function() {
allow = true;
})
}
}
});
$(document).delegate('body', 'click', function(e) {
if ($(e.target).closest('.ninjaSelect_list').length == 0) {
self.$list.hide();
self.$ul.empty();
}
})
},
loadData: function(val, callback) {
var self = this, len = val.length;
if (len >= self.options.minLength) {
$.get(self.options.url, {offset: self.page, count: self.options.itemsPerPage, value: val, data: self.options.data}, function(json) {
if (json.length) {
if (json.length >= self.options.itemsPerPage) {
self.page++;
}
self.$list.show();
json.forEach(function(item, i, arr) {
self.$ul.append(
$('<li>').text(item.text).data('id', item.id)
)
})
if (self.page == 1) {
self.$list.animate({scrollTop: 0}, 0);
} else {
self.$list.css({scrollTop: self.$list.scrollTop()}, 0);
}
if (callback) {
callback();
}
} else {
self.$list.hide();
self.$ul.empty();
}
}, 'json');
} else {
self.$list.hide();
self.$ul.empty();
}
}
}
$.fn.ninjaSelect = function(options) {
return this.each(function() {
var $this = $(this), data = $this.data('ninjaSelect');
if (!data) {
$this.data('ninjaSelect', (data = new ninjaSelect(this, options)))
}
})
}
$.fn.ninjaSelect.defaults = {
url: '/ajax.php',
data: {},
minLength: 2,
itemsPerPage: 3,
multiple: true
}
}(jQuery);