jQuery
和别的库冲突怎么解决?本文就和大家一起来详细扒一扒这个问题,一起来看看吧,希望对大家
学习jquery有所帮助。
我的思路就是如果让我来设计,那我就用一个默认值$
,不传参数,那就用
$
,最后就挂载在
window.$
上,传参数就用传入名字,比如传入
jq
,那我就挂载在
window.jq
上。
var myControl="jq";
(
function(name){
var $=name ||"$"; //name
存在
$
的值就是
name
的值,不存在或为
null
,
$
的值为字符串
"$"
console.log($);
window[$]=
function(){
alert("123");
}
})(myControl)window[myControl]();
事实上这肯定不是jquery
解决冲突的办法了。那就看看
jQuery
怎么解决冲突吧。
jQuery
多个版本
或
和其他js库
冲突主要是常用的$
符号的冲突。
一、冲突的解决
1、同一页面jQuery多个版本冲突解决方法
<body>
<!--
引入
1.6.4
版的
jq -->
<script src="http://ajax.googleapis.com/ajax/libs/jquery/1.6.4/jquery.js"></script>
<script> var jq164 = jQuery.noConflict(true); </script>
<!--
引入
1.4.2
版的
jq -->
<script src="http://ajax.googleapis.com/ajax/libs/jquery/1.4.2/jquery.js"></script>
<script> var jq142 = jQuery.noConflict(true); </script>
<script>
(function($){
//
此时的
$
是
jQuery-1.6.4
$('#');
})(jq164);
</script>
<script>
jq142(function($){
//
此时的
$
是
jQuery-1.4.2
$('#');
});
</script>
</body>
2、jQuery库在其他库之后导入
jQuery noConflict()
方法会释放会
$
标识符的控制,这样其他脚本就可以使用它了。
1、可以通过jQuery全名替代简写的方式来使用 jQuery
在其他库和jQuery
库都加载完毕后,可以在任何时候调用
jQuery.noConflict()
函数来将变量
$
的控制权移交给其他
JavaSript
库。然后就可以在程序里将
jQuery()
函数作为
jQuery
对象的制造工厂。
<script src="prototype.js" type="text/javascript"></script>
<script src="jquery.js" type="text/javascript"></script>
<p id="pp">test---prototype</p>
<p>test---jQuery</p>
<script type="text/javascript">
jQuery.noConflict(); //
将变量
$
的控制权让渡给
prototype.js
,全名可以不调用。
jQuery(function(){ //
使用
jQuery
jQuery("p").click(function(){
alert( jQuery(this).text() );
});
});
//
此处不可以再写成
$,
此时的
$
代表
prototype.js
中定义的
$
符号。
$("pp").style.display = 'none'; //
使用
prototype
</script>
2、自定义一个快捷方式
noConflict()
可 返回对
jQuery
的引用 ,可以把它存入自定义名称,例如
jq,$J
变量,以供稍后使用。
这样可以确保jQuery
不会与其他库冲突,同时又使用自定义一个快捷方式。
<script type="text/javascript">
var $j = jQuery.noConflict(); //
自定义一个比较短快捷方式
$j(function(){ //
使用
jQuery
$j("p").click(function(){
alert( $j(this).text() );
});
});
$("pp").style.display = 'none'; //
使用
prototype
</script>
3、在不冲突的情况下仍然用$
如果想在jQuery
代码块使用
$
简写,不愿意改变这个快捷方式,可以把
$
符号作为变量传递给
ready
方法。这样就可以在函数内使用
$
符号了 , 而在函数外,依旧不得不使用
"jQuery"
。
<script type="text/javascript">
jQuery.noConflict(); //
将变量
$
的控制权让渡给
prototype.js
jQuery(document).ready(function($){
$("p").click(function(){ //
继续使用
$
方法
alert( $(this).text() );
});
});
//
或者如下
jQuery(function($){ //
使用
jQuery
$("p").click(function(){ //
继续使用
$
方法
alert( $(this).text() );
});
});
</script>
或者使用IEF
语句块,这应该是最理想的方式,因为可以通过改变最少的代码来实现全面的兼容性。
在我们自己写jquery
插件时
,
应该都使用这种写法,因为我们不知道具体工作过程中是如何顺序引入各种
js
库的
,
而这种语句块的写法却能屏蔽冲突。
<script type="text/javascript">
jQuery.noConflict(); //
将变量
$
的控制权让渡给
prototype.js
(function($){ //
定义匿名函数并设置形参为
$
$(function(){ //
匿名函数内部的
$
均为
jQuery
$("p").click(function(){ //
继续使用
$
方法
alert($(this).text());
});
});
})(jQuery); //
执行匿名函数且传递实参
jQuery
$("pp").style.display = 'none'; //
使用
prototype
</script>
3、jQuery库在其他库之前导入
jQuery
库在其他库之前导入,
$
的归属权默认归后面的
JavaScript
库所有。那么可以直接使用
"jQuery"
来做一些
jQuery
的工作。
同时,可以使用$()
方法作为其他库的快捷方式。这里无须调用
jQuery.noConflict()
函数。
<!--
引入
jQuery -->
<script src="../../scripts/jquery.js" type="text/javascript"></script>
<!--
引入
prototype -->
<script src="lib/prototype.js" type="text/javascript"></script>
<body>
<p id="pp">Test-prototype(
将被隐藏
)</p>
<p >Test-jQuery(
将被绑定单击事件
)</p>
<script type="text/javascript">
jQuery(function(){ //
直接使用
jQuery ,
没有必要调用
"jQuery.noConflict()"
函数。
jQuery("p").click(function(){
alert( jQuery(this).text() );
});
});
$("pp").style.display = 'none'; //
使用
prototype
</script>
</body>
二、原理
1、源码
源码:看一下源码里怎么做到的
var// Map over jQuery in case of overwrite
_jQuery = window.jQuery,
// Map over the $ in case of overwrite
_$ = window.$,
jQuery.extend({
noConflict:
function( deep ) {
if ( window.$ === jQuery ) {
window.$ = _$;
}
if ( deep && window.jQuery === jQuery ) {
window.jQuery = _jQuery;
}
return jQuery;
}
});
在jQuery
加载的时候,通过事先声明的
_jQuery
变量获取到当前
window.jQuery
,通过
_$
获取到当前
window.$
。
通过jQuery.extend()
把
noConflict
挂载到
jQuery
下面。所以我们在调用的时候都是
jQuery.noConflict()
这样调。
在调用noConflict()
时做了
2
个判断,
第一个if
,把
$
的控制权交出去。
第二个if
,在
noConflict()
传参的时候把,
jQuery
的控制权交出去。
最后noConflict()
返回
jQuery
对象,用哪个参数接收,哪个参数将拥有
jQuery
的控制权。
2、 验证
//
冲突
var $ = 123; //
假设其他库中
$
为
123
$(
function () {
console.log($); //
报错
Uncaught TypeError: $ is not a function
}
);
解决冲突
//
解决冲突
var jq = $.noConflict();
var $ = 123;
jq(
function () {
alert($); //123
});
释放$
控制权例子
<script>
var $ = 123; // window.$
是
123
,存储在私有的
_$
上。
</script>
<script src="https://code.jquery.com/jquery-2.2.4.js"></script>
<body>
<div>aaa</div>
<script>
var jq = $.noConflict();//
当
window.$===jQuery
的时候,把
_$
赋给了
window.$
。
jq(function () {
alert($); //123
});
</script>
释放jQuery
控制权例子
参数deep
的作用:
deep
用来放弃
jQuery
对外的接口。
如下,noConflict()
不写参数,弹出
jQuery
为构造函数。
<script>
var $ = 123;
var jQuery=456;
</script>
<script src="https://code.jquery.com/jquery-2.0.3.js"></script>
<body>
<div>aaa</div>
<script>
var jq = $.noConflict();
jq(function () {
alert(jQuery); //
构造函数
});
</script>
file:///C:\Users\ADMINI~1\AppData\Local\Temp\ksohtml\wps7521.tmp.jpg
如果写个参数true
,会弹出
456
。
<script>
var $ = 123;
var jQuery=456;
</script>
<script src="https://code.jquery.com/jquery-2.0.3.js"></script>
<body>
<div>aaa</div>
<script>
var jq = $.noConflict(true); //
写了
true
或者参数的时候,
deep
为真
window.jQuery===jQuery
为真,所以进入
if
条件。把
456
赋值给
window.jQuery
jq(function () {
alert(jQuery); //456
});
</script>
来源:
博客园