38

I've read 3 pages of Google Results on how to load a JS file for all pages and still am not able to do it.

I've got a few doubts, hope somebody can clear them out.

  1. Do I need to create a module inside app/code with the requirejs-config.js ? Or I can put a requirejs-config.js inside my theme instead?

  2. What should I put inside requirejs-config.js ?

  3. What should the code look like inside my .js file? I saw that you can't use jQuery's document.ready and you must have a define([

  4. What should I put inside define([ ?

  5. If I've got third party jQuery modules, do I have to edit them to make them work?

  6. Do I need to put xml somewhere to tell magento that my.js file exists?

  7. If I create a module inside app/code with all the js code there, would it include all the stuff in all pages? How can I achieve that?

65

To load a custom main.js file on all pages (in the RequireJS-way) this is a good way:

1) Create main.js

Create main.js within the theme folder

<theme_dir>/web/js/main.js

with this content:

define([
  "jquery"
], 
function($) {
  "use strict";

  // Here your custom code...
  console.log('Hola');

});

In short: we declare dependencies at the start, e.g. "jquery". We define as function's parameter the variable name for using the dependency within the function, e.g. "jquery" --> $. We put all our custom code within function($) { ... }.

2) Declare main.js with a requirejs-config.js file

Create a requirejs-config.js file within the theme folder:

<theme_dir>/requirejs-config.js

with this content:

var config = {

  // When load 'requirejs' always load the following files also
  deps: [
    "js/main"
  ]

};

"js/main" is the path to our custom main.js. The ".js" extension is not required.

Our requirejs-config.js will be merged with other requirejs-config.js defined in Magento.

RequireJS will load our main.js file, on each page, resolving dependencies and loading files in an async way.


Optional: Including third-party library

This is the way to include third-party libraries.

1) Add the library in web/js:

<theme_dir>/web/js/vendor/jquery/slick.min.js

2) Open requirejs-config.js and add this content:

var config = {

  deps: [
    "js/main"
  ],

  // Paths defines associations from library name (used to include the library,
  // for example when using "define") and the library file path.
  paths: {
    'slick': 'js/vendor/jquery/slick.min',
  },

  // Shim: when you're loading your dependencies, requirejs loads them all
  // concurrently. You need to set up a shim to tell requirejs that the library
  // (e.g. a jQuery plugin) depends on another already being loaded (e.g. depends
  // on jQuery).
  // Exports: if the library is not AMD aware, you need to tell requirejs what 
  // to look for so it knows the script has loaded correctly. You can do this with an 
  // "exports" entry in your shim. The value must be a variable defined within
  // the library.
  shim: {
    'slick': {
      deps: ['jquery'],
      exports: 'jQuery.fn.slick',
    }
  }

};

It looks more complicated than what it actually is.

3) Add the dependency within main.js:

define([
  'jquery',
  'slick'
], 
function($) {

  // ...

});
  • Hi , Can you tell if I have to include bootstrap.js here. How can I add it so that bootstrap works well in my theme. Thanks! – anujeet Feb 27 '17 at 14:06
  • 1
    @anujeet You can include bootstrap.js in the same way I included slick.js in the above example. For the shim value you can try to use this: 'bootstrap': { deps: ["jquery"], exports: '$.fn.popover' }, as explained here: stackoverflow.com/a/13556882/3763649 – Andrea Feb 27 '17 at 17:59
  • See my require-config.js var config = { deps: [ "js/animate", "js/incase", "js/confetti" ], paths: { "jquery.bootstrap":"js/bootstrap.min" }, shim:{ 'jquery.bootstrap':{ 'deps':['jquery'] } } }; require(["jquery",'jquery.bootstrap', 'jquery/ui', 'jquery/validate', 'mage/validation/validation', 'domReady!']); My minicart stops working with this – anujeet Feb 28 '17 at 6:57
  • @anujeet Better you open another question with this issue, reporting your require-config.js and if you have some errors in the javascript console. If you link your question here I will be glad to help you :) – Andrea Feb 28 '17 at 8:58
  • when include more js I have errors "js/ScrollMagic.min", "js/debug.addIndicators.min" – yavonz15 Sep 14 '17 at 10:38
6

You can add JS files using xml as below. This will add js in all the pages.

With custom module:

Create default.xml file in your module.

app/code/vendor_name/module_name/view/frontend/layout/default.xml

<?xml version="1.0"?>
<page xsi:noNamespaceSchemaLocation="urn:magento:framework:View/Layout/etc/page_configuration.xsd" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
    <head>
        <!-- Add js using link tag-->
        <link src="js/script.js"/>

        <!-- Add js-->
        <script src="Vendor_Module::js/script.js"/>

        <!-- Add external js -->
        <script src="https://apis.google.com/js/platform.js" src_type="url" />
   </head>
</page>
6

Duplicate the file:

app/code/Magento/Theme/view/frontend/layout/default_head_blocks.xml

To

app/code/your_vendor/your_theme/Magento_Theme/layout/default_head_blocks.xml

<page xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:View/Layout/etc/page_configuration.xsd">
    <head>
        <!-- Add local resources -->
        <css src="css/my-styles.css"/>

        <!-- The following two ways to add local JavaScript files are equal -->
        <script src="Magento_Catalog::js/sample1.js"/>
        <link src="js/sample.js"/>

        <!-- Add external resources -->
        <css src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.4/css/bootstrap-theme.min.css" src_type="url" />
        <script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.4/js/bootstrap.min.js" src_type="url" />
        <link src="http://fonts.googleapis.com/css?family=Montserrat" src_type="url" /> 
    </head>
</page>

For more information:

http://devdocs.magento.com/guides/v2.0/frontend-dev-guide/layouts/xml-manage.html

Good luck!

BTW read the frontend devdocs official from magento to get the basic :)

  • Because Bootstrap's script requires JQuery to be initialized, including it in the head won't work. Read this official doc. for more info. :) – V.S Jan 26 '17 at 18:23
2

The method of adding js using the default_head_blocks.xml file will not work for 3rd party JQuery plugins. So, if you want to add custom JQuery plugins and use them, you will need to use requirejs-config.js file.

To answer your questions one by one:

1) & 2) You don't need to create a module to add the requirejs-config.js file. You can just add it in this location:

app/design/frontend/<Vendor>/<theme>/requirejs-config.js

Refer to this answer to creating a proper requirejs-config.js file.

3) You will need to list the dependencies of your js file before you write your scripts.

require([
  'jquery',
  'jquery/ui'
], function($){
   // ... Your code here
}); 

The above code says that you will need jquery and jquery ui for your scripts.

4) You don't need to use the define([ unless you are creating a javascript plugin.

5) No, you don't need to edit them but you will need to specify their dependency using the requirejs-config.js file. If you have owl.carousel.min.js in <vendor>/<theme>/web/js/owl.carousel.min.js, your requirejs-config.js file will look like this:

var config = {
    map: {
        '*': {
            owlCarouselTheme: 'js/owl.carousel.min'
        }
    },
    shim: {
        owlCarouselTheme: ['jquery']
    }
};

In the above code, please remember that there is no .js for the file. And now to use it in your js

require(['jquery', 'owlCarouselTheme'],function($){
    $(document).ready(function() {
        $(".footer.links").addClass("owl-carousel").owlCarousel({items: 1});
    });
})

If everything works well, you should have your footer links in a slider.

6) & 7) Just use the method suggested by @Goldy to add your js. It will add your js file to all the pages.

For further reading, you can look at this post

Hope this helps.

1

This is how I add dotdotdot library in my magento2 custom theme.

1. Download and add Js Library in your theme following the path:

// app/design/frontend/Namespace/themename/web/js/jquery.dotdotdot.min.js

2. Create a theme's requirejs file as follow and let the requirejs know newly added library.

// app/design/frontend/Namespace/themename/requirejs-config.js
var config = {
   map: {
       '*': {
           dotdotdot: 'js/jquery.dotdotdot.min',
       }
   }
};

3. Use the added library in your theme's main js file as follow:

// app/design/frontend/Namespace/themename/web/js/main.js
require([ 'jquery' , 'dotdotdot' , 'domReady!'],function($){
    $(window).load(function() {
        //custom js code
        /* $(".product-item-name").each(function(){
            $(this).dotdotdot(); 
        }); */
    });
});

4. and include your theme's js file in your site's head as follow:

// app/design/frontend/Namespace/themename/Magento_Theme/layout/default_head_blocks.xml
<?xml version="1.0"?>
<page xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:View/Layout/etc/page_configuration.xsd">
    <head>
        <link src="js/main.js"/> 
    </head>
</page>

You can add any external JS library and custom file on every page in magento2.

  • I have tried this is admin side, js is coming correctly but expected result is not coming – Naveenbos Sep 18 '17 at 12:44
  • Nice answer. Gonna try it. Is there a way to specify a certain page where the js file is needed.? – Mohammed Joraid Mar 14 at 12:53
  • For a specific page, move the "default_head_blocks.xml" content in above example to your specific layout file. For example in case of product detail page, add that xml in app/design/frontend/Namespace/themename/Magento_Catalog/layout/catalog_product_view.xml – saiid Mar 15 at 2:58

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.