2015-02-10 93 views
2

我主要的應用程序基於JavaScript的「頁」上的文件加載訪問:調用JavaScript函數從動態加載的內部函數

var AdminConsole = (function() { 
    function openPage(folder, template) { 
     $.getScript('viewmodels/' + template + '.js') 
      .done(function() { 
       console.log(template + " script loaded."); 
      }); 
    } 
    function test() { 
     // do something ... 
    } 
})(); 

的JavaScript在$.getScript()加載看起來是這樣的:

var UserPermissions = (function() { 
    // try to call test() 
})(); 

我問題是,如何從UserPermissions()內撥打AdminConsole.test()

當我嘗試AdminConsole.test()它說AdminConsole是未定義的。當我嘗試test()時,測試是未定義的。

+0

定義AdminConsole gloablly。 – void 2015-02-10 20:29:07

回答

4

分配給AdminConsole的值是該匿名函數返回的值。既然你什麼都不回來,那就是undefined

相反,你應該導出的公共方法/屬性:

var AdminConsole = (function() { 
    // ... (private data) 
    return { // Export public data to the outside 
     test: test, 
     openPage: openPage 
    }; 
})(); 

如果你不需要的私人數據,你也可以考慮簡單

var AdminConsole = { 
    test: function(){ /*...*/ }, 
    openPage: function(){ /*...*/ } 
}; 
1

AdminConsole似乎是調用函數的結果。如果該功能沒有return,則AdminConsole將不確定。 也許你想這樣的:

AdminConsole = { 
    openPage: ... 
    test: ... 
} 

但你可能想要的是使用的模塊,如Browserify或​​提供。

1

在你的代碼片段中,AdminConsole是一個自動執行的匿名函數。換句話說,它等於(function() {/* your code*/})()返回的結果。在你上面的例子中,你不會返回任何東西(你只是在匿名函數中有函數),所以AdminConsole == undefined。這些功能是私人的。例如,

function myPrivateData() { 
    this.data = "public"; 
    var nobodyCanSee = "private"; 
} 
var test = new myPrivateData(); 
// test.data => "public" 
// test.nobodyCanSee => undefined 

這與您的情況相同。您的內部函數都不會附加到匿名函數,因此它們在該函數的範圍之外是不可見的。

如果你想內AdminConsole訪問的功能,你可以把它的對象:

var adminConsole = { 
    openPage: function() { 
     // etc 
    }, 
    test: function() { 
     // etc 
    } 
} 

採用這種結構,可以調用testadminConsole.test()

+0

我沒有看到關閉與此有什麼關係。看起來事情只是沒有被定義爲OP的預期。 – 2015-02-10 20:32:59

+0

這裏涉及「a」閉包,但它不是問題或問題的焦點。 – 2015-02-10 20:36:25

+0

@JonSurrell我的意思是,它與範圍有關,但我可以刪除第一句。 – royhowie 2015-02-10 20:38:56