こんにちは。 システムインテグレーション部の白川と申します。
以前、入力補助機能を拡充するためにjQueryを利用することになったのですが
jQueryとprototype.jsのコンフリクト(競合)でハマってしまいました。
簡単なことですが、回避策を覚えておくと便利なので例を上げて紹介いたします
以下のhtmlをブラウザで開くと、通常は次のようなカレンダーが入力補助として表示されます。
<link rel="stylesheet" href="http://ajax.googleapis.com/ajax/libs/jqueryui/1.10.1/themes/base/jquery.ui.all.css" /> <script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jquery/1/jquery.min.js"></script> <script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jqueryui/1/jquery-ui.min.js"></script> <script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jqueryui/1/i18n/jquery.ui.datepicker-ja.min.js"></script> <script type="text/javascript"> <!-- $(function() { $.datepicker.setDefaults($.extend($.datepicker.regional['ja'])); $("#datepicker").datepicker({ changeMonth: true, changeYear: true, dateFormat: 'yy/mm/dd', yearRange: '2010:2030', }); }); --> </script> <p>日付: <input type="text" name="calendar" id="datepicker"></p>
以下のように入力補助カレンダーが表示されます。
エラーとなる事象を発生させるために prototype.jsのロードを以下のように追加します。
jQueryとコンフリクト(競合)し、カレンダーが表示されなくなります。
<link rel="stylesheet" href="http://ajax.googleapis.com/ajax/libs/jqueryui/1.10.1/themes/base/jquery.ui.all.css" /> <script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jquery/1/jquery.min.js"></script> <script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jqueryui/1/jquery-ui.min.js"></script> <script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jqueryui/1/i18n/jquery.ui.datepicker-ja.min.js"></script> <script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/prototype/1.7.0.0/prototype.js"></script> <script type="text/javascript"> <!-- $(function() { $.datepicker.setDefaults($.extend($.datepicker.regional['ja'])); $("#datepicker").datepicker({ changeMonth: true, changeYear: true, dateFormat: 'yy/mm/dd', yearRange: '2010:2030', }); }); --> </script> <p>日付: <input type="text" name="calendar" id="datepicker"></p>
prototype.jsでは、$は”document.getElementById”として扱われます。
jQueryでは、$はjQueryオブジェクトを指します。
取得できる要素が全く異なるものなのでエラーとなります。
このコンフリクト(競合)の回避方法について
本ブログでは以下2のパターンを紹介します。
1.prototype.js を先頭でロードするように移動し「$」⇒「jQuery」に変更する
2.jQuery.noConflict()を使う
1について
以下のように、prototype.jsを先頭でロードさせ、jQueryオブジェクトとして用いる箇所は
全てjQueryと書き換えます。
<link rel="stylesheet" href="http://ajax.googleapis.com/ajax/libs/jqueryui/1.10.1/themes/base/jquery.ui.all.css" /> <script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/prototype/1.7.0.0/prototype.js"></script> <script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jquery/1/jquery.min.js"></script> <script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jqueryui/1/jquery-ui.min.js"></script> <script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jqueryui/1/i18n/jquery.ui.datepicker-ja.min.js"></script> <script type="text/javascript"> <!-- jQuery(function() { jQuery.datepicker.setDefaults(jQuery.extend(jQuery.datepicker.regional['ja'])); jQuery("#datepicker").datepicker({ changeMonth: true, changeYear: true, dateFormat: 'yy/mm/dd', yearRange: '2010:2030', }); }); --> </script> <p>日付: <input type="text" name="calendar" id="datepicker"></p>
2について
多くの場合は、このnoConflictを使う事が多いかと思います。
以下のように記述することで、競合を防ぎ、prototype.jsと共存させることができます。
<link rel="stylesheet" href="http://ajax.googleapis.com/ajax/libs/jqueryui/1.10.1/themes/base/jquery.ui.all.css" /> <script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jquery/1/jquery.min.js"></script> <script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jqueryui/1/jquery-ui.min.js"></script> <script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jqueryui/1/i18n/jquery.ui.datepicker-ja.min.js"></script> <script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/prototype/1.7.0.0/prototype.js"></script> <script type="text/javascript"> <!-- jQuery.noConflict(); (function($) { $(function() { $.datepicker.setDefaults($.extend($.datepicker.regional['ja'])); $("#datepicker").datepicker({ changeMonth: true, changeYear: true, dateFormat: 'yy/mm/dd', yearRange: '2010:2030', }); }); })(jQuery) --> </script> <p>日付: <input type="text" name="calendar" id="datepicker"></p>
上記の方法で、$の衝突を回避することができます。
あくまで$の衝突回避となりますが、多くの場合は、上記の方法でprototype.jsとjQueryの競合を回避できると思います。
最後まで読んでいただき、ありがとうございました。