当在noconflict / noglobal状态下使用jQuery强制所有模块指示它们是否需要jQuery时,我试图使jQuery插件与RequireJS一起正常使用。但是,对于非AMD友好插件,shim
配置似乎不起作用。即,如果使用如下包装器定义了jQuery插件:
(function($) {
$.extend($.myPlugin, { myPlugin: { version:'0.0.1'} });
})(jQuery);
然后以下RequireJS配置不起作用:
requirejs.config({
paths: {
jquery: ['//ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min', 'jquery-min'],
},
map: {
'*': { 'jquery': 'jquery-noglobal' }, // Force all modules to use the non-global jQuery...
'jquery-noglobal': { 'jquery': 'jquery' } // ...except the wrapper module itself, which needs the real one.
},
shim: {
'sadPlugin': {
deps: ['jquery']
}
}
});
jquery-noglobal.js
:define(['jquery'], function(jq) {
return jq.noConflict( true );
});
插件代码运行时引发的错误是:“无法在
extend
上调用undefined
”,这意味着jQuery
从未在外部级别设置,因此$
在自执行函数中未定义。我在插件自我执行功能的外部放置了断点,并在内部进行了验证。我猜问题的一部分是大写;该模块写为期望
jQuery
(camelCase),而AMD模块名称为jquery
(小写)。 shim
配置中是否可以指定注入的需求的变量名应该是什么?我也尝试过在
sadPlugin: {'jquery':'jquery'}
哈希中添加一个map
条目,希望使shim
为该模块提供全局jQuery,而不是非全局jQuery,但当时尚未定义jQuery / $该函数被调用。编辑:找到了一个可以解决部分问题的混合器:根据发现的注释here,
deps
的shim
必须是要加载的脚本的完整文件路径,并且不能是paths
配置。因此,由于我的jQuery CDN后备文件为
jquery-min.js
,因此如果执行以下操作:shim: {
'sadPlugin': {
deps: ['jquery-min']
}
}
该插件有效!但是,由于现在使用的是“真正的” jQuery,因此会污染全局名称空间,然后
$
变量就可以使用,而无需require()
对其进行变量化,因此破坏了noglobal
包装器的全部用途... 最佳答案
只需使用
return jQuery.noConflict( true );
代替
return jq.noConflict( true );
因此,作为requirejs中的局部变量,您的插件可以将变量jQuery用于参数$
(function($) {$.extend($.myPlugin, { myPlugin: { version:'0.0.1'} });})(jQuery);
对我有用的配置是:
-main.js
-jquery-private.js
在main.js文件中:
require.config({
paths: {
},
map: {
'*': { 'jquery': 'jquery-private' },
'jquery-private': { 'jquery': '//ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js' }
},
shim: {
myplugins: ['jquery']
}
});
在jquery-private.js文件中:
define(['jquery'], function () {
jQuery = $.noConflict(true);
return jQuery;
});
关于javascript - RequireJS jQuery插件补片不起作用?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/25871403/