329 lines
10 KiB
JavaScript
329 lines
10 KiB
JavaScript
![]() |
/**
|
|||
|
* jQuery弹出层插件,简单精致,结构简单,样式简洁,接口丰富,满足轻量应用
|
|||
|
* email: tianshaojie@msn.com
|
|||
|
* date: 2013-01-15
|
|||
|
* version: 1.0.0
|
|||
|
*/
|
|||
|
(function($) {
|
|||
|
var
|
|||
|
$doc = $(document),
|
|||
|
$win = $(window),
|
|||
|
ie = /msie/.test(navigator.userAgent.toLowerCase()),
|
|||
|
ie6 = ('undefined' == typeof(document.body.style.maxHeight)),
|
|||
|
max = Math.max,
|
|||
|
min = Math.min,
|
|||
|
|
|||
|
purebox = function(options) {
|
|||
|
return purebox.list[options.id] ? purebox.list[options.id] : new purebox.fn._init(options);
|
|||
|
};
|
|||
|
purebox.fn = purebox.prototype = {
|
|||
|
constructor : purebox,
|
|||
|
_init : function(options) {
|
|||
|
var opts = $.extend({}, purebox.defaults, options || {}),
|
|||
|
template = ['<div id="',opts.id,'" class="pb"><div class="cboxContent">',
|
|||
|
opts.head ? ('<div class="pb-hd">' + (opts.xBtn ? '<a class="pb-x">\u2715</a>' : '') + '<span class="pb-title">'+opts.title+'</span></div>') : '',
|
|||
|
'<div class="pb-bd"><div class="pb-ct"></div>',
|
|||
|
opts.foot ? ('<div class="pb-ft">'+(opts.cBtn ? '<a class="pb-btn pb-ok">' + opts.ok_title + '</a>' : '') + (opts.cl_cBtn ? '<a class="pb-btn pb-cl">' + opts.cl_title + '</a>' : '') + '</div>') : '',
|
|||
|
'</div></div></div>'].join(''),
|
|||
|
$pb = $(template),
|
|||
|
$head = $pb.find('.pb-hd'),
|
|||
|
$foot = $pb.find('.pb-ft'),
|
|||
|
that = this;
|
|||
|
|
|||
|
that.$pb = $pb,
|
|||
|
that.$head = $head;
|
|||
|
that.$foot = $foot;
|
|||
|
that.$xBtn = $head.find('.pb-x');
|
|||
|
that.$cont = $pb.find('.pb-ct');
|
|||
|
that.$cBtn = $foot.find('.pb-cl');
|
|||
|
that.$oBtn = $foot.find('.pb-ok');
|
|||
|
that.$pb.appendTo(document.body);
|
|||
|
that.opts = opts;
|
|||
|
that.offsetHeight = $head.outerHeight()+$foot.outerHeight();
|
|||
|
|
|||
|
that._bindEvent();
|
|||
|
that._setPbZindex();
|
|||
|
that.resize(opts.width, opts.height);
|
|||
|
that.setContent(opts.content);
|
|||
|
opts.drag && that._setDrag();
|
|||
|
opts.mask && that._setMask();
|
|||
|
opts.resize && that.$pb.resizable({
|
|||
|
handles: "e, s, se",
|
|||
|
onResize:function() {
|
|||
|
that.$cont.height(that.$pb.innerHeight() - that.offsetHeight);
|
|||
|
},
|
|||
|
onStopResize:function() {
|
|||
|
that.$cont.height(that.$pb.innerHeight() - that.offsetHeight);
|
|||
|
}
|
|||
|
});
|
|||
|
!opts.fixed && that.$pb.css('position','absolute');
|
|||
|
that.setPos(opts.top, opts.left);
|
|||
|
purebox.list[opts.id] = that;
|
|||
|
that._focus();
|
|||
|
return that;
|
|||
|
},
|
|||
|
//定义全局变量window.zindex,每次Z值加一
|
|||
|
_zindex : function() {
|
|||
|
window.pb_zindex = window.pb_zindex || 100000;
|
|||
|
return ++window.pb_zindex;
|
|||
|
},
|
|||
|
//设置弹出层Z轴坐标
|
|||
|
_setPbZindex : function() {
|
|||
|
var that = this;
|
|||
|
return that.$pb.css('z-index', that._zindex());
|
|||
|
},
|
|||
|
//设置遮罩层Z轴坐标
|
|||
|
_setMaskZindex : function() {
|
|||
|
var that = this;
|
|||
|
return $('#pb-mask').css('z-index', that._zindex()).show();
|
|||
|
},
|
|||
|
//设置遮罩,遮罩的Z轴比最上面弹出层小,比已打开的弹出层大
|
|||
|
_setMask : function() {
|
|||
|
var that = this;
|
|||
|
if($('#pb-mask').length) {
|
|||
|
that._setMaskZindex();
|
|||
|
that._setPbZindex();
|
|||
|
} else {
|
|||
|
var css = 'position:fixed;width:100%;height:100%;top:0;left:0;filter: progid:DXImageTransform.Microsoft.Alpha(opacity=40);opacity:0.4;overflow:hidden;background-color:#fff;_position:absolute;left:expression(documentElement.scrollLeft+documentElement.clientWidth-this.offsetWidth);top:expression(documentElement.scrollTop+documentElement.clientHeight-this.offsetHeight);',
|
|||
|
iframe = ie6 ? '<iframe src="about:blank" style="width:100%;height:100%;position:absolute;top:0;left:0;z-index:-1;filter:alpha(opacity=0)"></iframe>' : '';
|
|||
|
$('<div id="pb-mask" style="'+css+'">' + iframe + '</div>').css('z-index', that._zindex()).appendTo(document.body);
|
|||
|
that._setPbZindex();
|
|||
|
}
|
|||
|
},
|
|||
|
//设置弹出层是否可以拖拽
|
|||
|
_setDrag : function() {
|
|||
|
return new purebox.dragable(this.$pb, this.$head);
|
|||
|
},
|
|||
|
//绑定触发事件
|
|||
|
_bindEvent : function(opts) {
|
|||
|
var that = this,
|
|||
|
opts = that.opts;
|
|||
|
that.$xBtn.length && that.$xBtn.click(function() {
|
|||
|
$.isFunction(opts.onClose) && opts.onClose();
|
|||
|
that.dispose();
|
|||
|
});
|
|||
|
that.$cBtn.length && that.$cBtn.click(function() {
|
|||
|
$.isFunction(opts.onCancel) && opts.onCancel();
|
|||
|
that.dispose();
|
|||
|
});
|
|||
|
that.$oBtn.length && that.$oBtn.click(function() {
|
|||
|
$.isFunction(opts.onOk) && opts.onOk();
|
|||
|
that.dispose();
|
|||
|
});
|
|||
|
//窗口调整大小事件
|
|||
|
var resizeTimer;
|
|||
|
$win.resize(function() {
|
|||
|
resizeTimer && clearTimeout(resizeTimer);
|
|||
|
resizeTimer = setTimeout(function () {
|
|||
|
that.setPos(opts.top, opts.left);
|
|||
|
}, 40);
|
|||
|
});
|
|||
|
},
|
|||
|
_focus : function() {
|
|||
|
var focus = purebox.focus;
|
|||
|
this.prev = focus;
|
|||
|
purebox.focus = this;
|
|||
|
},
|
|||
|
//设置尺寸
|
|||
|
resize : function(width, height) {
|
|||
|
var that = this;
|
|||
|
that.$pb.css('width', max.call(Math,150,width) + 'px');
|
|||
|
that.$cont.css('height', max.call(Math,50,height) + 'px');
|
|||
|
return that;
|
|||
|
},
|
|||
|
//设置位置
|
|||
|
setPos : function(top, left) {
|
|||
|
var that = this,
|
|||
|
dl = that.opts.fixed ? 0 : $doc.scrollLeft(),
|
|||
|
dt = that.opts.fixed ? 0 : $doc.scrollTop();
|
|||
|
if(top === 'c') {
|
|||
|
top = $win.height() - that.$pb.outerHeight();
|
|||
|
top = top > 0 ? dt + (top>>1)-(top>>3) : 0;
|
|||
|
}
|
|||
|
if(left === 'c') {
|
|||
|
left = $win.width() - that.$pb.outerWidth();
|
|||
|
left = left > 0 ? dl + (left>>1) : 0;
|
|||
|
}
|
|||
|
that.$pb.css({top:top,left:left});
|
|||
|
return that;
|
|||
|
},
|
|||
|
center : function() {
|
|||
|
return this.setPos('c', 'c');
|
|||
|
},
|
|||
|
//设置弹出要显示的内容,支持html和jQuery对象,暂不支持URL和Image
|
|||
|
setContent : function(c) {
|
|||
|
var that = this;
|
|||
|
if(typeof(c) === 'string') {
|
|||
|
that.$cont.html(c);
|
|||
|
} else if(c instanceof jQuery) {
|
|||
|
var display = c.css('display'),
|
|||
|
prev = c.prev(),
|
|||
|
next = c.next(),
|
|||
|
parent = c.parent();
|
|||
|
that._elemBack = function () {
|
|||
|
if (prev.length) {
|
|||
|
prev.after(c);
|
|||
|
} else if (next.length) {
|
|||
|
next.before(c);
|
|||
|
} else if (parent.length) {
|
|||
|
parent.append(c);
|
|||
|
};
|
|||
|
c.css('display',display);
|
|||
|
that._elemBack = null;
|
|||
|
};
|
|||
|
that.$cont.append(c);
|
|||
|
}
|
|||
|
return that;
|
|||
|
},
|
|||
|
//关闭按钮对应的操作
|
|||
|
dispose : function() {
|
|||
|
var that = this;
|
|||
|
that._elemBack && that._elemBack();
|
|||
|
that.$pb.remove();
|
|||
|
|
|||
|
delete purebox.list[that.opts.id];
|
|||
|
purebox.focus = purebox.focus.prev;
|
|||
|
|
|||
|
if(purebox.focus) {
|
|||
|
if(purebox.focus.opts.mask) {
|
|||
|
that._setMaskZindex();
|
|||
|
} else {
|
|||
|
$('#pb-mask').hide();
|
|||
|
}
|
|||
|
$('.pb').last().css('z-index', that._zindex());
|
|||
|
} else {
|
|||
|
$('#pb-mask').remove();
|
|||
|
}
|
|||
|
}
|
|||
|
};
|
|||
|
purebox.fn._init.prototype = purebox.fn;
|
|||
|
|
|||
|
purebox.defaults = {
|
|||
|
id : 'pb', //弹出层ID
|
|||
|
title : '\u6807\u9898', //弹出层标题,默认“标题”
|
|||
|
content : '', //弹出层内容,支持html和jQuery对象,暂不支持URL和Image
|
|||
|
width : 'auto', //弹出层宽度
|
|||
|
height : 'auto', //弹出层高度
|
|||
|
left : 'c', //X轴坐标,center默认居中显示
|
|||
|
top : 'c', //Y轴坐标,center默认居中显示
|
|||
|
fixed : true, //是否静止定位
|
|||
|
drag : true, //是否拖拽
|
|||
|
mask : true, //是否锁屏
|
|||
|
resize : false, //是否可以调节尺寸,需要引入jquery.resizable.js
|
|||
|
head : true, //是否显示标题栏
|
|||
|
foot : true, //是否显示按钮栏
|
|||
|
xBtn : true, //是否显示关闭按钮
|
|||
|
cBtn : true, //是否显示取消按钮
|
|||
|
cl_cBtn : true,
|
|||
|
onClose : null, //关闭回调事件
|
|||
|
onOk : null, //确定回调事件
|
|||
|
onCancel: null //取消回调事件
|
|||
|
};
|
|||
|
purebox.focus = null;
|
|||
|
purebox.list = {};
|
|||
|
//拖拽
|
|||
|
purebox.dragable = function() {
|
|||
|
return this.initialize.apply(this, arguments);
|
|||
|
};
|
|||
|
purebox.dragable.prototype = {
|
|||
|
//拖放对象
|
|||
|
initialize: function($drag, $handle) {
|
|||
|
this._drag = $drag;//拖放对象
|
|||
|
this._handle = $handle || this._drag;
|
|||
|
|
|||
|
//事件代理
|
|||
|
this.move = $.proxy(this.onMove,this);
|
|||
|
this.stop = $.proxy(this.onStop,this);
|
|||
|
|
|||
|
this._handle.bind("mousedown", $.proxy(this.onStart,this));
|
|||
|
},
|
|||
|
//准备拖动
|
|||
|
onStart: function(event) {
|
|||
|
//记录鼠标相对拖放对象的位置
|
|||
|
this._x = event.clientX - parseInt(this._drag.css('left'), 10);
|
|||
|
this._y = event.clientY - parseInt(this._drag.css('top'), 10);
|
|||
|
$doc.bind('mousemove',this.move).bind('mouseup', this.stop);
|
|||
|
if(ie){
|
|||
|
//焦点丢失
|
|||
|
this._handle.bind("losecapture", this.stop);
|
|||
|
//设置鼠标捕获
|
|||
|
this._handle.get(0).setCapture();
|
|||
|
}else{
|
|||
|
//焦点丢失
|
|||
|
$doc.bind("blur", this.stop);
|
|||
|
//阻止默认动作
|
|||
|
event.preventDefault();
|
|||
|
};
|
|||
|
},
|
|||
|
//拖动
|
|||
|
onMove: function(event) {
|
|||
|
//清除选择
|
|||
|
window.getSelection ? window.getSelection().removeAllRanges() : document.selection.empty();
|
|||
|
//设置移动参数、范围限制,动态的使用$win.width()和$drag.outerWidth()是为了避免窗口大小和弹出层大小改变是对拖动位置的影响
|
|||
|
var iLeft = event.clientX - this._x,
|
|||
|
iTop = event.clientY - this._y,
|
|||
|
fixed = this._drag.css('position') === 'fixed',
|
|||
|
dl = fixed ? 0 : $doc.scrollLeft(),
|
|||
|
dt = fixed ? 0 : $doc.scrollTop(),
|
|||
|
maxLeft = dl + $win.width() - this._drag.outerWidth(),
|
|||
|
maxTop = dt + $win.height() - this._drag.outerHeight();
|
|||
|
iLeft = max(min(iLeft, maxLeft), dl);
|
|||
|
iTop = max(min(iTop, maxTop), dt);
|
|||
|
this._drag.css({top:iTop, left:iLeft});
|
|||
|
},
|
|||
|
//停止拖动
|
|||
|
onStop: function() {
|
|||
|
//移除事件
|
|||
|
$doc.unbind("mousemove", this.move);
|
|||
|
$doc.unbind("mouseup", this.stop);
|
|||
|
if(ie){
|
|||
|
this.unbind("losecapture", this.stop);
|
|||
|
this._handle.get(0).releaseCapture();
|
|||
|
}else{
|
|||
|
$doc.unbind("blur", this.stop);
|
|||
|
};
|
|||
|
}
|
|||
|
};
|
|||
|
|
|||
|
//扩展到jQuery工具集
|
|||
|
window.pb = $.pb = $.purebox = purebox;
|
|||
|
|
|||
|
//扩展到jQuery包装集
|
|||
|
$.fn.pb = $.fn.purebox = function (options) {
|
|||
|
return this.bind('click', function() {
|
|||
|
$.pb(options);
|
|||
|
});
|
|||
|
};
|
|||
|
|
|||
|
//扩展alert
|
|||
|
$.pb.alert = function(content, callback) {
|
|||
|
return $.pb({
|
|||
|
id : 'pb-alert',
|
|||
|
title : '\u63d0\u793a',
|
|||
|
content : wrapCont(content),
|
|||
|
width : 300,
|
|||
|
height : 70,
|
|||
|
onOk : callback,
|
|||
|
cBtn : false,
|
|||
|
resize : false
|
|||
|
});
|
|||
|
};
|
|||
|
//扩展confirm
|
|||
|
$.pb.confirm = function(content, ok, cancel) {
|
|||
|
return $.pb({
|
|||
|
id : 'pb-confirm',
|
|||
|
title : '\u786e\u8ba4',
|
|||
|
content : wrapCont(content),
|
|||
|
width : 300,
|
|||
|
height : 70,
|
|||
|
onOk : ok,
|
|||
|
onCancel : cancel,
|
|||
|
resize : false
|
|||
|
});
|
|||
|
};
|
|||
|
|
|||
|
//居中显示文字Alert,Confirm
|
|||
|
function wrapCont(cont) {
|
|||
|
return '<div style="text-align:center;padding: 20px 10px 0;">' + cont + '</div>';
|
|||
|
}
|
|||
|
})(window.jQuery);
|