1.遮罩层使用JS写入,DOM渲染完毕后初始化插件;

2.为实现同一页面多次调用,每次呼出时为遮罩层分配一个ID,模态框内容采用动态写入的方式,关闭模态框时将遮罩层初始化;

3.模态框主要分为三种类型,类alert、类confirm、类prompt(按钮:确定/取消);

4.在此思路基础上可继续根据模态框内容继续分类,完全格式化模态框;

5.其他参数,例如窗体大小,是否可改变,点击遮罩层是否可以隐藏,是否可拖拽,触发事件,回调函数等。

基本思路有了,接下来就是着手实现了。

首先,声明一个构造函数:

var myMask = function (element, options) {
        this.caller = $(element);
        this.options = options;
        this.isShown = false;
        this.init();
}

这样就获得了一个拥有三个属性的myMask对象并将其初始化了。
首先为对象设置一些默认的选项:

myMask.Defaults = {
    dialog_type: 'alert',
    dialog_title: '提示信息',
    content_type: 'msg',
    dialog_content: '提交成功!',
    dialog_width: 600,
    Mask_click_close: true,
    is_draggable: false,
    show_Mask_Events: ['click'],
    close_Mask_Events: ['click'],
    selector: this.selector,
    before_show_callback: null, 
    shown_callback: null,
    after_close_callback: null
}

只有默认选项显然是不够用的,因此需要扩展它:

myMask.Options = $.extend(myMask.Defaults, this.options);

而在构造函数中用以初始化对象而调用的init方法是什么呢?还没有定义。因此,下一步就是要先为这个对象定义它的第一个方法:

myMask.prototype.init=function(){
    if (!$(".Mask").length) {
         $("body script").first().before('<div class="Mask"></div>');
         document.getElementsByClassName('Mask')[0].innerHTML += '<div class="dialog"></div>';
         this.dialog = document.getElementsByClassName('dialog')[0];
         this.dialog.innerHTML += '<div class="dialog-header"><a class="close" id="close">×</a><h4></h4></div>';
         this.dialog.innerHTML += '<div class="dialog-body"></div>';
         this.dialog.innerHTML += '<div class="dialog-footer"></div>';
    }
    if (this.options.show_Mask_Events.length) {
        var s_events = this.options.show_Mask_Events.join(" ");
        this.caller.on(s_events, $.proxy(this.show, this));
    }
    else {
        this.show();
    }
}

这样在函数被调用的时候,就完成了页面上遮罩层及模态框的写入,并为myMask的触发器caller绑定了弹出事件。而myMask对象又得到了一个新的属性定义:dialog。

接下来,顺理成章地,定义show方法。为了实现特性2,我的页面上只允许存在一个Mask层,因此我需要首先为它分配一个ID,此后所有的操作都是以此为基础的:

myMask.prototype.show = function () {
    var count = 3000;
    var oArray = [];
    for (var i = 1000; i < count; i++) {
        oArray.push(i);
    }
    oArray.sort(function () {
        return 0.3 - Math.random();
    });

    var maskId = 'mask' + oArray[1];

    ('.Mask').attr('id', maskId);
    this.mask = $('#' + maskId);
    this.dialog = $(this.dialog);
    this.dialogTitle = this.dialog.find('dialog-header').find('h4');
    this.contentContainer = this.dialog.find('.dialog-body');
    this.dialogFooter = this.dialog.find('.dialog-footer');
    this.dialogTitle = this.dialog.find('h4');

    var isConfm = false;
    var h_events = this.options.close_Mask_Events.join(" ");
    var background_height = $("body").height();
    var background_width = $("body").width();
    this.mask.css({
        "height": background_height,
        "width": background_width,
        "position": "fixed",
        "opacity": "1"
    });
    if (!this.isShown) {
    if (this.options.before_show_callback == null || (this.options.before_show_callback != null && this.options.before_show_callback())) {
        this.mask.fadeIn();
        this.dialogTitle.html(this.options.dialog_title);
        this.dialog.css({
            "width": this.options.dialog_width + "px",
            "margin-left": "-" + this.options.dialog_width / 2 + "px"
        });
        this.typeSet();
        this.dialog.show();
        this.dialog.animate({
            top: "60px",
            opacity: "1"
        });
        this.toClose.on(h_events, $.proxy(this.close, this));
        if (this.options.shown_callback != null) {
            this.options.shown_callback();
        }
        this.isShown = true;
    }
}

定义typeSet方法:

myMask.prototype.typeSet = function () {
    switch (this.options.content_type) {
        //根据需要添加case
    }
    switch (this.options.dialog_type){
        case 'alert':
            this.dialogFooter.append('<button type="button" id="confm">' + this.options.dialog_confm + '</button>');
            break;
        case 'confirm':
        case 'prompt':
            this.dialogFooter.append('<button type="button" id="cncel">' + this.options.dialog_cncl + '</button> <button type="button" id="confm">' + this.options.dialog_confm + '</button>');
            break;
        default:
            break;
    }
}

close方法:

myMask.prototype.close = function (e) {
    e.stopPropagation();
    if (this.isShown) {
        for (var i = 0; i < this.toClose.length; i++) {
            if (this.toClose[i] == e.target) {
                isConfm = ($(e.target).attr("id") == "confm") ? true : false;
                if (isConfm && this.options.after_close_callback) {
                    this.options.after_close_callback();
                }
                this.toClose.off(e);
                this.dialog.animate({
                    top: "0",
                    opacity: "0"
                });
                this.mask.fadeOut(1000, function () {
                    $(this).find('.dialog').removeAttr('style');
                    $(this).find('h4').html('');
                    $(this).find('.dialog-body').html('');
                    $(this).find('.dialog-footer').html('');
                    $(this).removeAttr('style');
                    $(this).removeAttr('id');
                });
                this.isShown = false;
                break;
            }
        }
    }
}

扩展jQuery:

function Plugin(option) {
    return this.each(function () {
        var $this = $(this);
        var data = $this.data('maskFI');
        var options = $.extend({}, MaskFI.Defaults, typeof option == 'object' && option);
        if (!data) {
            $this.data('maskFI', (data = new MaskFI(this, options)));
        }
        if (typeof option == 'string') {
            data[option]();
        }
    });
}

var old = $.fn.mymask;
$.fn.mymask= Plugin;
$.fn.mymask.Constructor = myMask;
$.fn.mymask.noConflict = function () {
    $.fn.mymask= old;
    return this;
}

最后进行闭包:

(function($){
    //上面写好的所有代码
})(jQuery);

感谢阅读。