There are currently three ways of adding JavaScript in Magento 2 using RequireJS, which are presented by the three JS module types: plain module, jQuery widget and UIComponent.
Each type will require you to have set up a basic Magento module structure, including a requirejs-config.js
file. For example, let’s assume that a custom.js
file is to be included.
// app/code/Vendor/Module/view/frontend/requirejs-config.js
var config = {
map: {
'*': {
custom: '<Vendor>_<Module>/js/custom'
}
}
};
To add JavaScript via a plain module, you can define your JS file like the following:
// app/code/Vendor/Module/view/frontend/web/js/custom.js
define([
"jquery"
], function($, custom) {
"use strict";
return function (config, element) {
$(element).click(function (event) {
alert('Hey, the element was clicked!');
});
};
});
The code consists of two major parts. The define statement, which declares all dependencies and the return statement. Because of the way in which Magento 2 executes the JavaScript, the return statement takes two parameters: element
and config
.
The jQuery widget has the same define statement as a plain module, but the return part is slightly different. It uses config and element parameters, but now they are hidden inside of its structure.
// app/code/Vendor/Module/view/frontend/web/js/custom.js
define([
"jquery"
], function($, custom) {
"use strict";
// Create the widget
$.widget('custom.js', {
_create: function() {
// Access to the config
var config = this.config;
// Access to the JS element
var element = this.element;
element.on('click', function(e){
alert('Hey, the element was clicked!');
});
}
});
return $.custom.js;
});
So what is element
and this.element
? This is where you need to load and use the JavaScript in a .phtml
file.
You can use the data-mage-init
attribute.
// somefile.phtml
<div class="some-class" data-mage-init='{ "custom": {...} }'></div>
Notice within this attribute resides a JSON object that lists the custom
module and config for the module.
You could also use the text/x-magento-init
attribute. This approach allows the execution of a JS module without connecting it to a specific DOM-node or multiple nodes.
// somefile.phtml
<script type="text/x-magento-init">
{
// Components initialised on the element defined by selector
"<element_selector>": {
"<js_component1>": ...,
"<js_component2>": ...
},
// Components initialised without binding to an element
"*": {
"<js_component3>": ...
}
}
</script>
You can extend an existing UIComponent’s JavaScript in Magento 2 by tweaking your requirejs-config.js
and adding a require.js mixin
.
// app/code/Vendor/Module/view/frontend/requirejs-config.js
var config = {
'config': {
'mixins': {
'Magento_Ui/js/form/form': {
'<Vendor>_<Module>/js/custom': true
}
}
}
};
Then within your custom.js
file:
// app/code/Vendor/Module/view/base/web/custom.js
define([
], function () {
'use strict';
return function (Form) {
return Form.extend({
initialize: function () {
this._super();
alert('Successfully extended the UIComponent!');
}
});
}
});
Note: This article is based on Magento CE version 2.1.