วิธีสร้างปลั๊กอิน jQuery ที่โหลดได้ด้วย requirejs


88

ฉันทำงานกับ requirejs + jquery และฉันสงสัยว่ามีวิธีที่ชาญฉลาดในการทำให้ปลั๊กอิน jQuery ทำงานได้ดีกับความต้องการหรือไม่

ตัวอย่างเช่นฉันใช้ jQuery-cookie ถ้าฉันเข้าใจถูกต้องฉันสามารถสร้างไฟล์ชื่อ jquery-cookie.js และภายใน do

define(["jquery"], // Require jquery
       function($){
// Put here the plugin code. 
// No need to return anything as we are augmenting the jQuery object
});
requirejs.config( {
    "shim": {
        "jquery-cookie"  : ["jquery"]
    }
} );

ฉันสงสัยว่าฉันสามารถทำสิ่งต่างๆเช่น jQuery ได้หรือไม่ซึ่งเป็นเช่นนี้:

if ( typeof define === "function" && define.amd && define.amd.jQuery ) {
    define( "jquery", [], function () { return jQuery; } );
}

หรือถ้านี่เป็นวิธีเดียวที่จะทำให้ปลั๊กอิน jQuery เข้ากันได้กับ requirejs หรือ amd ใด ๆ

คำตอบ:


67

คุณต้องทำอย่างใดอย่างหนึ่งเท่านั้น

define(["jquery"], // Require jquery
       function($){
// Put here the plugin code. 
// No need to return anything as we are augmenting the jQuery object
});

ในตอนท้ายของ jquery-cookie.js หรือ

requirejs.config( {
    "shim": {
        "jquery-cookie"  : ["jquery"]
    }
} );

ที่ใดก็ได้ก่อนที่คุณจะรวม jquery-cookie (เช่นที่ใดก็ตามที่จุดข้อมูลหลักไป)

บล็อกโค้ดสุดท้ายที่คุณโพสต์นั้นดีสำหรับสิ่งต่างๆเช่น jQuery ซึ่งได้รับการแจกจ่ายซ้ำและอาจหรือไม่อยู่ในสภาพแวดล้อมของ AMD ตามหลักการแล้วปลั๊กอิน jQuery ทุกตัวจะมีการตั้งค่าไว้แล้ว

ฉันชอบที่จะให้ห้องสมุดรวมเป็นบริสุทธิ์ที่เป็นไปได้เพื่อให้สามารถกำหนดค่าพารามิเตอร์ชิมทั่วโลกครั้งเดียวต่อหน้าดูเหมือนว่าทางออกที่สะอาดให้ฉัน ด้วยวิธีนี้การอัพเกรดจะปลอดภัยกว่าและ CDN กลายเป็นไปได้


1
ถ้าฉันไม่ทำทั้งสิ่งที่กำหนดและชิมไม่ได้ผลฉันจะได้รับ $ .cookie ไม่ใช่ข้อความแสดงข้อผิดพลาดของฟังก์ชัน
Nicola Peluchetti

จากประสบการณ์ของฉันการไม่ส่งคืนสิ่งใดจากฟังก์ชันการกำหนดไม่เพียงพอ requirejs จะไม่รับรู้ว่าโมดูลโหลด สิ่งนี้สามารถวนเวียนได้โดย shim: {plugins: {depend: ['jquery'], export: 'plugins'}
honzajde

คุณควรทราบว่าสคริปต์ปลั๊กอิน jQuery จำเป็นต้องทำงานจริง ฉันไม่ใช่ผู้เชี่ยวชาญ แต่ฉันพบวิธีแก้ปัญหาที่ตรงไปตรงมาโดยที่คุณมีตัวเดียวrequire(['plugin1', 'plugin2']);และอื่น ๆ ไม่มีการส่งการเรียกกลับดังนั้นจะไม่มีอะไรทำงานยกเว้นสคริปต์ปลั๊กอินเอง ซึ่งหมายความว่าจากนั้นพวกเขาจะเพิ่มตัวเองเข้าไปในjQuery.fnทุกที่คุณสามารถระบุ 'jquery' เป็นการอ้างอิงและจะรวมเข้าด้วยกัน อย่างที่ฉันพูดฉันค่อนข้างใหม่สำหรับสิ่งนี้และอาจมีแนวทางที่ดีกว่า (เช่นแค่ใช้scriptแท็ก) แต่ก็ใช้ได้ผล
Joshua Bambrick

3
Josh: คุณกำลังพนันว่าทุกอย่างจะโหลดในลำดับที่ถูกต้อง ผู้ใช้บางรายในไซต์ของคุณอาจเห็นของเสีย ปัญหาไม่ได้อยู่ที่ปลั๊กอินโหลดมากเท่าตอนที่ปลั๊กอินโหลดและสิ่งอื่นที่กำลังดำเนินการในเวลานั้น เหตุผลหลักที่ต้องใช้คือเพื่อให้แน่ใจว่าลำดับการดำเนินการที่เหมาะสมโดยอาศัยการอ้างอิงมากกว่าการคาดเดา
Hans

104

มีบางประการเกี่ยวกับการใช้การกำหนดค่าชิมใน RequireJS จะชี้ให้เห็นในhttp://requirejs.org/docs/api.html#config-shim กล่าวคือ "อย่าผสมการโหลด CDN กับ shim config ในบิลด์" เมื่อคุณใช้เครื่องมือเพิ่มประสิทธิภาพ

ฉันกำลังมองหาวิธีใช้โค้ดปลั๊กอิน jQuery เดียวกันบนไซต์ทั้งที่มีและไม่มี RequireJS ผมพบว่าข้อมูลโค้ดนี้ปลั๊กอิน jQuery ที่https://github.com/umdjs/umd/blob/master/jqueryPlugin.js คุณรวมปลั๊กอินของคุณไว้ในโค้ดนี้และจะทำงานได้อย่างถูกต้องไม่ว่าจะด้วยวิธีใดก็ตาม

(function (factory) {
if (typeof define === 'function' && define.amd) {
    // AMD. Register as an anonymous module depending on jQuery.
    define(['jquery'], factory);
} else {
    // No AMD. Register plugin with global jQuery object.
    factory(jQuery);
}
}(function ($) {

    $.fn.yourjQueryPlugin = function () {
        // Put your plugin code here
    };  

}));

เครดิตไปที่ jrburke; เช่นเดียวกับจาวาสคริปต์มากฟังก์ชันภายในฟังก์ชันที่ทำหน้าที่ในฟังก์ชันอื่น ๆ แต่ฉันคิดว่าฉันได้แกะกล่องแล้วว่ามันทำอะไร

อาร์กิวเมนต์ของฟังก์ชันfactoryในบรรทัดแรกเป็นฟังก์ชันที่เรียกใช้เพื่อกำหนดปลั๊กอินบน$อาร์กิวเมนต์ เมื่อไม่มีตัวโหลดที่เข้ากันได้กับ AMD จะเรียกใช้โดยตรงเพื่อกำหนดปลั๊กอินบนjQueryวัตถุส่วนกลาง นั่นเหมือนกับสำนวนนิยามปลั๊กอินทั่วไป:

function($)
{
  $.fn.yourjQueryPlugin = function() {
    // Plugin code here
  };
}(jQuery);

หากมีตัวโหลดโมดูลfactoryจะถูกลงทะเบียนเป็นการเรียกกลับเพื่อให้ตัวโหลดเรียกใช้หลังจากโหลด jQuery สำเนาที่โหลดของ jQuery คืออาร์กิวเมนต์ เทียบเท่ากับ

define(['jquery'], function($) {
  $.fn.yourjQueryPlugin = function() {
     // Plugin code here
  };
})

3
ฉันชอบคำตอบนี้เพราะแม้ว่าคำถามจะเกี่ยวกับปลั๊กอิน jQuery แต่ก็ใช้ได้กับโมดูลหรือไลบรารีทุกประเภทไม่ใช่แค่ jQuery ฉันใช้เวลาหนึ่งนาทีในการคาดเดารหัสของคุณ แต่เมื่อฉันทำแล้วมันก็สมเหตุสมผลดี
Adam Tuttle

1
เป็นจาวาสคริปต์ที่ไม่สามารถยอมรับได้อย่างแน่นอน ฉันได้เพิ่มคำอธิบายเกี่ยวกับวิธีการทำงาน
Carl Raymond

มีเคล็ดลับในการทำสิ่งนี้และสร้างปลั๊กอินที่ทำงานร่วมกับ jQuery หรือ Zepto ได้อย่างไร คุณสามารถแทนที่โค้ดที่ไม่ใช่ AMD ได้อย่างง่ายดายfactory(jQuery || Zepto);แต่ฉันไม่รู้ว่าคุณจะทำส่วน AMD อย่างไร ฉันคิดว่าคุณจะต้องกำหนด jQuery "path" เป็น zepto ?? paths: { jquery: 'vendor/zepto/zepto.min' }
Ryan Wheale

ว้าวฉันอยากจะเข้าใจข้อมูลโค้ดนี้มานานแล้ว ขอบคุณมากจริงๆแล้วการshimทำแบบนั้นไม่ใช่เหรอ? ฉันเดาว่าไม่ .. เพราะคุณบอกว่าคุณกำลังเขียนโค้ดด้วยตนเองเหมือนข้างบน
eugene

Protip for idiots like me: ที่มันบอก$.fn.jqueryPluginใน snippet เปลี่ยนjqueryPluginเป็น plugin name !!
Matt Lacey

2

เช่นเดียวกับ FYI สำหรับปลั๊กอิน jquery บางตัวใช้ amd / ต้องใช้อยู่แล้วดังนั้นคุณไม่จำเป็นต้องประกาศอะไรใน shim ในความเป็นจริงการทำเช่นนั้นอาจทำให้เกิดปัญหากับคุณในบางกรณี

หากคุณดูใน jquery คุกกี้ JS คุณจะเห็นกำหนดการเรียกและต้องการ (["jquery"])

และใน jquery.js คุณจะเห็นการเรียกเพื่อกำหนด ("jquery", [], function () ...

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.