如何在一个真实的例子中使用javascript模块模式?

Pat*_*cow 12 javascript jquery design-patterns module-pattern

我想了解JavaScript模块模式.我已经看到它应该是什么样子的例子,但我不明白如何使用它.

例如,这里发生了一些事情:

$('input#share').on("click", function() {

    $('.loading').html('<img class="remove_loading" src="/graphics/loading.gif" />');

    var message = $(".wallmessage").val();

    if (message == ""){
        $("#messageempty").jmNotify();
        $('.remove_loading').remove();
    } else {
        addMessage(message);
    }

    return false;
});


function addMessage(message)
{
    $.ajax({
        url: '/test',
        type: 'POST',
        dataType: "json",
        data: {'message' : message},
        success: function(data) {
                ...
        },
        error: function() {
            ...
        }
    });
}
Run Code Online (Sandbox Code Playgroud)

我如何使用上面的例子:

var myTest = function() {
    var selectId;
    function addMessage () {
        // ...
    }
    return { // public interface
        publicMethod1: function () {
            // all private members are accesible here
        }
    };
};
var start = myTest();
Run Code Online (Sandbox Code Playgroud)

我在哪里添加click事件,声明我的vars,addMessage使用ajax调用添加该函数.并调用该addMessage函数?我必须把所有东西都包起来$(document).ready(function()吗?

任何人都可以为我阐明这一点吗?

谢谢

Jac*_*lin 21

这是一个相当自以为是的主题,但我会这样做(不完全知道你的完整应用程序及其功能),有点像这样:

var myApp = (function() {

  var someElement = $("#foo"); //some element I know I'll use lots

  var addMessage = function(message) {
    $.ajax({
      url: '/test',
      type: 'POST',
      dataType: "json",
      data: {'message' : message},
      success: function(data) {
              ...
      },
      error: function() {
          ...
      }
    });
  };

  var inputClick = function(event) {
    event.preventDefault();
    //depending on if you'll reuse these selectors throughout the app I might have these as variables
    $('.loading').html('<img class="remove_loading" src="/graphics/loading.gif" />');

    var message = $(".wallmessage").val();

    if (message == ""){
      $("#messageempty").jmNotify();
      $('.remove_loading').remove();
    } else {
      addMessage(message);
    }
  };

  var bindFunctions = function() {
    $("input#share").on("click", inputClick)
  };

  var init = function() {
    bindFunctions();
  };

  return {
    // EDIT: 27/12/16 - need to return init for 'usage' example to work
    init: init,
    addMessage: addMessage
    //anything else you want available
    //through myApp.function()
    //or expose variables here too
  };


})();

//usage

myApp.init();
Run Code Online (Sandbox Code Playgroud)

你的模式的原始代码是错误的,函数必须()在最后,使它成为一个立即被调用的函数,然后执行,通过它暴露任何东西return statement.

你可能希望与我所做的略有不同,这只是一个基本的想法,但我希望它可以让你开始.

有一段时间回来问了一个与这个模式有关的问题,我回答了它解释了我们使用的原因(function() {})();以及return声明在这种情况下是如何工作的,如果你对它有点混淆可能也值得一读.


jba*_*bey 13

显示模块模式使用如下:

var moduleName = (function () {
    var privateVariable = 'private';

    var privateMethod = function () {
        alert('this is private');
    };

    // this is the "revealed" part of the module
    return { 
        publicVariable: 'public',
        publicMethod: function () {
            alert('this is public');
        }
    };
}());
Run Code Online (Sandbox Code Playgroud)

您还可以将公共变量/方法定义为私有,然后公开对它们的引用,使它们公开.这是一个偏好的问题.

在您的示例中,如果您想addMessage成为模块的一部分,您可以这样做:

var moduleName = (function () {
    // this becomes public due to the reference exposure in the return below
    var addMessage = function () {
        // do whatever
    };

    // this is the "revealed" part of the module
    return { 
        addMessage: addMessage
    };
}());

moduleName.addMessage();
Run Code Online (Sandbox Code Playgroud)