4

Update:

The problem occurred again and gave me a chance to check a few more things. The script is loaded and the contents can be viewed in Chrome's developer tools under the "Sources" panel.

This means that it is being loaded, but it is not being executed.

jQuery is available on that page publicly and I was trying to pass it through as a dependency into the call back as jQuery

Since the function is anonymous - there should be no conflict here - no?

My proof is that this works and logs the response from the ajax query. Is requireJs refusing to use it with that name since the global variable already exists for that parameter? jQuery.ajax('/', function(jQuery) { console.log(jQuery); });


Original Post:

It is very important that I understand why this is happening and how to get around it.

I am avoiding the use of the $ sign for jQuery everywhere in my scripts and loading all of them through requirejs.

There are many buttons that have event listeners attached to them that work nearly all of the time - however sometimes when the page loads the events do not fire or may never be binded to the elements.

I don't know if it's a requirejs problem or jquery conflict. Has anyone else dealt with this yet?

Config:

var config = {
    map: {
        '*': {
            footerContact: 'Module_Contact/js/contact',
        }
    }
};

Script (contact.js)

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

    jquery('.element').on('click', function(event) {
    });
});

phtml include:

<script type="text/javascript">
  require(['footerContact']);
</script>

Edit:

I am not convinced it is a requirejs shim issue, reading the documentation it states the criteria for using shim config:

Ideally the scripts you load will be modules that are defined by calling define(). However, you may need to use some traditional/legacy "browser globals" scripts that do not express their dependencies via define(). For those, you can use the shim config. To properly express their dependencies.

Yet my script uses define to include its dependencies...

  • 2
    please add your js code to more debug – Rakesh Jesadiya Nov 24 '16 at 9:57
  • I have updated answer you can check at last. Remove var folder and clear cache. check your changes – Rakesh Jesadiya Nov 24 '16 at 10:39
  • Yes, thank you. Testing now, how do you know when to use shim? – LM_Fielding Nov 24 '16 at 10:41
  • I have occur same type of issue in past so many times so i have debug requirejs, using shim of requirejs and after that used of shim, No more issue are available of some time load or some times not load. – Rakesh Jesadiya Nov 24 '16 at 10:46
  • 1
    Please let me know if you have problem are still occur – Rakesh Jesadiya Nov 24 '16 at 10:51
2
+25

You have to set jQuery dependency for your custom script. You have occurance of problem because of dependency issue.

  1. For Module/Extension Level

You can set at module/extension level dependency like below,

app/code/Packagename/Modulename/view/frontend/requirejs-config.js

var config = {
    paths: {            
            'slider': "Packagename_Modulename/js/slider"
        },   
    shim: {
        'slider': {
            deps: ['jquery']
        }
    }
};

Add slider.js inside path, app/code/Packagename/Modulename/view/frontend/web/js/slider.js

You can use in any template file like this,

<script>
    require(["jquery","slider"],function($)(){
        $(document).ready(function() {
            $(element).slider({
                   //option
            });
        });
    });
</script>
  1. Theme Level

If you want to apply require js changes at theme level, Go to theme module,

app/design/frontend/{Packagename}/{themename}/Packagename_Modulename/requirejs-config.js

Set your theme required js file in requirejs-config.js

var config = {
    paths: {            
            'slider': "Packagename_Modulename/js/slider",
            'customjsfile': "Packagename_Modulename/js/customjsfile",
        },   
    shim: {
        'slider': {
            deps: ['jquery']
        },
        'customjsfile':{
            deps: ['jquery']
        }
    }
};

Add your js file inside web folder of theme,

app/design/frontend/{Packagename}/{themename}/Packagename_Modulename/web/js/slider.js
app/design/frontend/{Packagename}/{themename}/Packagename_Modulename/web/js/customjsfile.js

In your template file,

<script>
    require(["jquery","slider","customjsfile"],function($)(){
        $(document).ready(function() {
            $(element).slider({
                   //option
            });
        });
    });
</script>

For your case,

Keep below config in requirejs-config.js file,

var config = {
    paths: {            
            'footerContact': 'Module_Contact/js/contact'
        },   
    shim: {
        'footerContact': {
            deps: ['jquery']
        }
    }
};

Inside phtml file,

<script>
  require(["jquery","footerContact"],function($)(){
    jquery('.element').on('click', function(event) {
        console.log('logging');
    });
  });
</script>
  • I'm sorry but I don't understand how this relates to event listeners not firing? – LM_Fielding Nov 24 '16 at 10:16
  • So if you don't set the dependency it works sometimes but not always...? – LM_Fielding Nov 24 '16 at 10:17
  • 1
    yes because of requirejs used AMD. so some time other js are loaded before our main js and dependancy are not ordered so we have to set dependancy for our js to prevent those type of changes. – Rakesh Jesadiya Nov 24 '16 at 10:22
  • Is this because jquery isn't a real requirejs module? – LM_Fielding Nov 24 '16 at 10:25
  • you have to load jquery in requirejs parameter under your template. – Rakesh Jesadiya Nov 24 '16 at 10:28
1

Try including your scripts the declarative way instead.

If you are targeting a specific element, apply the data-mage-init attribute:

<button data-mage-init='{"footerContact":{}}'>Click Me</button>

If you are binding to a group of elements, use the text/x-magento-init script tag:

<script type="text/x-magento-init">
{
    ".someCssSelector": {
        "footerContact": {}
    }
}
</script>

in the corresponding js file:

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

    return function (config, element) {
        $(element).click(function (e) {
            // do something
        });
    };
});
  • Sounds good. What if I'm not binding to an element? Do you have an option for that - or is that what could be causng my problems? – LM_Fielding Nov 24 '16 at 12:00
  • 1
    You would use "*" as the selector. – Aaron Allen Nov 24 '16 at 12:36
  • The two solutions I've had will take a while to test, bear with me. Thank you for your input. – LM_Fielding Nov 24 '16 at 14:18

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.