We help IT Professionals succeed at work.

keyframes not support in IE

Simon Leung
Simon Leung asked
on
I find that the following code doesn't work in IE. It works perfect in chrome or firebox. Any idea ?

div.map {
   margin: 20px auto;
   animation-name:rollmap;
   animation-duration: 3s;
   animation-iteration-count:infinite;
}

@keyframes rollmap {
      0% {background:url("../images/Map.png") no-repeat; }
      50% {background:url("../images/Maphover.png") no-repeat; }
      100% {background:url("../images/Map.png") no-repeat; }
}
Comment
Watch Question

Michel PlungjanIT Expert
Top Expert 2009

Commented:

Hi


Took a lot of investigation, I mad a few fiddles, played around with code from docs.microsoft.com and then finally found "Background-image is not animatable in IE"


https://developer.mozilla.org/en-US/docs/Web/CSS/background-image

Author

Commented:
Do u mean there is no solution on IE ? Thx
IT Expert
Top Expert 2009
Commented:

But because I am persistent, I found a workaround


https://jsfiddle.net/mplungjan/5e9szpcv/


div.map { 
  background-image: 
    url(https://www.iamexpat.nl/sites/default/files/sitefiles_2017-07/map-netherlands-provinces-municipalities.png), 
    url(https://www.iamexpat.nl/sites/default/files/sitefiles_2017-07/topographic-map-netherlands.png); 
  background-size: 100% 100%; 
  /* each image will be 800px x 800px */ 
  background-repeat: no-repeat; 
  background-position: 0px 0px, 800px 0px; 
  height: 800px; 
  width: 800px; 
  margin: 10px; 
  border: 1px solid; 
  animation: rollmap 3s infinite; 
} 
@keyframes rollmap { 
  0%, 50%{ 
    background-position: 0px 0px, 800px 0px; /* initially 1st image will be shown as it it as 0px 0px */ 
  } 
  50.1%, 100% { 
    background-position: -800px 0px, 0px 0px; /* at 50.1% 2nd image will be shown as it it as 0px 0px */ 
  } 
}

Thanks to hari_shanx for the example I found

Author

Commented:
Is it possible to change the animation effect such that it will change to gradually to next background, rather than change sharply ?

Thx
Michel PlungjanIT Expert
Top Expert 2009

Commented:

If I have to be honest, the above already exceeded my CSS3 knowledge :)

You could work around it with a :before element and play with the opacity instead:

        div.map { margin: 20px auto; position: relative; background-image: url("../Images/Map.png"); background-repeat: no-repeat; }
            div.map:before { content:""; position: absolute; top: 0px; left: 0px; width: 100%; height: 100%; background-image: url("../Images/MapHover.png"); background-repeat: no-repeat; opacity: 0; animation-name: rollmapIE; animation-duration: 3s; animation-iteration-count: infinite; }

        
        @keyframes rollmapIE {
            0% { opacity: 0; }
            50% { opacity: 1; }
            100% { opacity: 0; }
        }

Open in new window


That puts the static map.png in the background of the actual element, and adds a pseudo element with mapHover on it, with 0 opacity.
And then animates the opacity of the :before instead of the main one.

if your images have transparency, this will  NOT hide the original, just overlaying the top one, so you'd have to add another :after to get it to work properly and animate both.
Obviously this also won't work if you're already using :before for something else.

Author

Commented:
What's the usage of "div.map:before { content:"";

THx
:before and :after are called "pseudo-elements".  They're basically virtual / fake / new html elements that are inserted into the DOM before or after the content of the element you're targeting.

So if you had:
<p>asdf</p>

and added
p:before { content:"123 "; }

That would add "123" inside the p tag, before the "asdf".

You have to specify the content property in order for them to render, but it doesn't have to be anything meaningful.
So basically we put a virtual, empty element inside the <div> tag, before the content, and with the hover background image applied to it.
Then the animation is just toggling the opacity of that virtual element.

Not sure that was the best explanation, but did that make sense?