【问题标题】:Require.js not loading Three.jsRequire.js 没有加载 Three.js
【发布时间】:2026-01-04 18:50:01
【问题描述】:

所以我有一些生成的 JavaScript(来自 TypeScript):

define(["require", "exports", "three", "jquery", "./test"], function (require, exports, THREE, jQuery, Test) {
var Main = (function () {
    function Main() {
        this.container = jQuery('#test');
        this.scene = new THREE.Scene();
...

这最终导致浏览器出现错误(在上面的最后一行):

Uncaught TypeError: Cannot read property 'Scene' of undefined

有趣的是 jQuery 没有问题;就好像 Three.js 根本没有被加载一样。

需要配置:

requirejs.config({
    baseUrl: "src",
    paths: {
        "main": "../main",
        "test": "../test",
        "three": "../three/three",
        "sizzle": "/src/sizzle/dist/sizzle"
    }
});

jQuery 位于 'js/src' 文件夹中,而 Three.js 位于 'js/three/three.js' (正在使用 Express,因此 js 文件夹对浏览器是隐藏的,它似乎没有如果我将 three.js 移动到 src 文件夹,会有什么不同)。 Sizzle 是独立存在的,因为它在 src 的子文件夹中导致错误。

我是否遗漏了什么明显的东西?我没有线索

【问题讨论】:

    标签: javascript three.js requirejs


    【解决方案1】:

    从 r72 开始

    从 r72 开始,三个确实调用 define。所以你不应该设置shim。如果您没有有依赖于THREE 在全局空间中可用的代码,那么您就完成了。

    但是,如果有代码依赖于全局空间中的 THREE,这是一个问题,因为作为一个表现良好的 AMD 模块,THREE 不再只是泄漏到全球空间。对于在全局空间中需要 THREE 的代码,您可以创建一个像这样的模块,您可以在调用 requirejs.config 之前放置它:

    define("three-glue", ["three"], function (three) {
        window.THREE = three;
        return three;
    });
    

    您的 RequireJS 配置应包含此映射:

    map: {
      '*': {
        three: 'three-glue'
      },
      'three-glue': {
        three: 'three'
      }
    }
    

    这告诉 RequireJS “在需要 three 的地方,加载 three-glue,但是当 three-glue 需要 three 时,加载 three。”

    大家一起:

    define("three-glue", ["three"], function (three) {
        window.THREE = three;
        return three;
    });
    
    requirejs.config({
        baseUrl: "src",
        paths: {
            "main": "../main",
            "test": "../test",
            "three": "../three/three",
            "sizzle": "/src/sizzle/dist/sizzle"
        },
        map: {
            '*': {
                three: 'three-glue'
            },
            'three-glue': {
                three: 'three'
            }
        }
    });
    

    (技术说明:r72 实际上仍然执行对全局空间的泄漏,以及之后的一些版本。编辑此答案时的最新发布版本 (r83) 确实 not 泄漏到全局空间本身。我没有检查 r72 和 r83 之间的每个版本以检查何时进行更改。将上面的代码与旧的 AMD 兼容版本一起使用是安全的。它只会导致不必要的代码。 )

    对于 r71 及更早版本

    如果this file是任何向导,三不调用define。因此,如果您希望它在需要它作为模块时具有值,那么您需要一个shim。像这样的:

    shim: {
        three: {
            exports: 'THREE'
        }
    }
    

    根据您在问题中的配置:

    requirejs.config({
        baseUrl: "src",
        paths: {
            "main": "../main",
            "test": "../test",
            "three": "../three/three",
            "sizzle": "/src/sizzle/dist/sizzle"
        },
        shim: {
            three: {
                exports: 'THREE'
            }
        }
    });
    

    【讨论】:

    • 感谢您的回复!如果您不介意问,我将如何实施?我对垫片不太熟悉
    • 对不起,我明白你的意思了,我试试看!
    • 在您撰写第二条评论时,我正在编辑我的答案。 :)
    • 漂亮,解决了! :D 标记为答案,非常感谢!
    • 如果我想使用 OrbitControls 应该怎么做?
    最近更新 更多