Turning scripts off and on based on Media Queries?

1.3k views Asked by At

I am using a widget in my layout and I have it now so when a certain breakpoint is hit it will not display that larger widget and then goes to the smaller one. The larger widget does hide and the smaller one shows up but the text that is associated with both isn't right.

The text for the large widget displays and the smaller text for the small widget doesn't. I am pretty sure it has to do with the scripts each are using. The display none does hide the elements but the scripts seem to be still running.

I have absolutely no clue about JavaScript yet and would prefer a HTML or CSS answer if possible. If not then I will go with JS but will need some direction please. I have read numerous articles and even in the process of learning JS but still not sure how some of what I've read applies.

@media all and (max-width: 900px) {
  // styles
}

if (document.documentElement.clientWidth < 900) {
  // scripts
}

This is what I've found that seems like it is what I need but I'm not sure on the syntax of how to call the script I need. Do I just put the script itself in there without any other information? I have also read about using jquery to do this with something like this

$(window).resize(function() {
if ($(this).width() > 480) {
  // call supersize method
}
});

And I've even read about using Modernizer to do this but I still have to go through the documentation.

In the bin it doesn't show any of the text at all but the larger text is there and off to the side of the small widget. I just need to shut that large script off and turn the other on at a certain media query.

Any help is greatly appreciated.

HTML

  <aside class="smallScreen">
      <div class="smallWeather" style='width: 200px; height: 440px; background-image:
  url(http://vortex.accuweather.com/adcbin/netweather_v2/backgrounds/red_500x440_bg.jpg
  ); background-repeat: no-repeat; background-color: #993333;' ><div 
  id='NetweatherContainer' style='height: 420px;' ><script src='http://...'></script>  
  </div></div></aside>
  </div></div></div></aside>


  <aside class="largeScreen">
      <div class="largeWeather" style='width: 500px; height: 440px; background-image:
  url(http://vortex.accuweather.com/adcbin/netweather_v2/backgrounds/red_500x440_bg.jpg
  ); background-repeat: no-repeat; background-color: #993333;' ><div 
  id='NetweatherContainer' style='height: 420px;' ><script src='http://...'></script>  
  </div></div></aside> 

CSS

  @media screen and (min-width: 564px) and (max-width: 604px) {
  .largeScreen {
display: none;
}

  .smallScreen {
display: block; 
width: 55%;
min-width: 240px;
height: 100%;
font-size: 0;
margin-left: auto;
margin-right: auto;
margin-bottom: 1.2rem;
}

  .smallWeather {
position: relative;
display: block;
width: 240px;
height: 420px;  
background: white;
margin-left: auto;
margin-right: auto;
}

What is the best way to do this and why please? Is jQuery the best way from a mobile performance standpoint?

UPDATE: Going to use enquire.js because of it's straightforward approach (although I'm still a bit sketchy on it's use) and how small it is.

This is the basic code:

enquire.register("screen and (max-width: 605px)", {

// OPTIONAL
// If supplied, triggered when a media query matches.
match : function() {},      

// OPTIONAL
// If supplied, triggered when the media query transitions 
// *from a matched state to an unmatched state*.
unmatch : function() {},    

// OPTIONAL
// If supplied, triggered once, when the handler is registered.
setup : function() {},    

// OPTIONAL, defaults to false
// If set to true, defers execution of the setup function 
// until the first time the media query is matched
deferSetup : true,

// OPTIONAL
// If supplied, triggered when handler is unregistered. 
// Place cleanup code here
destroy : function() {}

});

Still not done and looking for more support with this. Now that I've chose this route, I see that there is quite a few articles and questions already about enquire.js. I will update my situation as I read up.

UPDATE: This is where I'm at but it's not working yet. I have the styles associated with each script still in the HTML and display none used accordingly. Will doing this work once I get the enquire.js correct?

Here is the new jsbin

Thanks again for everything!!

1

There are 1 answers

9
Mathijs Flietstra On

I think you are looking for something like enquire.js, which is a lightweight JavaScript library for responding to CSS media queries.

If you don't want to use a library, this post on reacting to media queries in JavaScript runs through a way of doing what you are after with vanilla JavaScript.

Here's a jsFiddle Demo with some working example code, and here's a Fullscreen jsFiddle Demo, which is handy when trying to test how it works. If you use the fullscreen version and make the browser window less than 600px wide, a javascript alert will tell you that you have done so. Because the alert comes up, the browser will jump back to its original size and tell you that it got bigger than 600px again. So you can see, it calls the match function when it matches (so at the time of loading and at the time of resizing to a larger width), and it calls the unmatch function when resizing to a smaller width, because then the media query doesn't match any more. That's how you call a certain function only for mobile or only for desktop based on their screen size.

JS

enquire.register("screen and (min-width:600px)", {
    match: function () {
        alert("Now the screen width is more than 600px");
    },
    unmatch: function () {
        alert("Now the screen width is less than 600px");
    }
});