Reputation:
This works well for browsers that support background-size
. Otherwise the 2x image is zoomed.
.a {
background-image: url(img2x.jpg); /* 1000x1000 */
background-size: 100%;
height: 500px;
width: 500px;
}
This should be used for browsers without background-size
support.
.a {
background-image: url(img1x.jpg); /* 500x500 */
height: 500px;
width: 500px;
}
Is it possible to trick the browser to fallback when background-size
is not supported? I know I can use @supports
but it's much less supported than background-size
so quite pointless in this case. I don't want to use JavaScript either.
Basically like so, except work!
.a {
background-image: url(img1x.jpg); /* 500x500 */
height: 500px;
width: 500px;
/* stop parsing this rule when background-size is not supported */
/* otherwise continue parsing and set different background-image */
background-size: 100%;
background-image: url(img2x.jpg); /* 1000x1000 */
}
This doesn't work obviously, but is there a trick which could make it work? Thanks.
Upvotes: 7
Views: 4699
Reputation: 168655
A CSS-only fallback for background-size
is tricky, but yes it can be done.
The trick is to use the short-form background
style to set the various background properties, rather than using the individual styles like background-size
, background-image
, etc.
So in your case, you would have something like this:
background: url(img2x.jpg) 0% 0%/100%;
(The 0% 0%
is for background-position
(0% 0% is default) which is required before the background-size
value when using the short-form style).
So far, all I've done is condense your existing code into a single short-form CSS line, but the clever bit is that now we've done this, a browser that doesn't recognise background-size
will throw away the whole line, rather than just throwing away the background-size
on its own.
This means that we can specify an entirely different set of background values for older browsers.
background: url(ie8bg.jpg); /* Shown by IE8 and other old browsers */
background: url(img2x.jpg) 0% 0%/100%; /* shown by new browsers with background-size support*/
You can see a demonstration of this in action here. Modern browsers will get the one background image, stretched by a 100% background-size
setting, and older browsers (like IE8) will get the an entirely different image, without any stretching.
Since you get to define an entirely separate background for old browsers, you can even do things like have a solid background colour for IE8 rather than an image while still providing an image for other browsers.
So yes, a fully CSS solution that gives you a fallback for browsers that don't support background-size
.
Hope that helps.
[EDIT]
Browser compatibility may be a minor issue here. Some browsers may support background-size
but not support it as part of the background
short syntax. For the most part this applies only to older browsers (eg Firefox 7), but it is still a problem in current versions of Safari. What this means is that with this technique, Safari will see the fall-back background, even though it does actually support background-size
.
This obviously isn't ideal, but it is mitigated by the fact that it will at least get the fallback image, which means the page ought to at least look okay, if not quite as good as in other browsers. Hopefully this issue in Safari will be fixed in a future version.
In the meanwhile, this point doesn't detract from the fact that this answer is a valid solution to the question - it does indeed provide a fallback option in pure CSS.
In light of this question I've written a blog post on the subject, which hopefully covers it in more detail and provides other options if this CSS fall-back solution isn't sufficient.
Upvotes: 15
Reputation: 3642
I might not completely understand what exactly the problem is with the lack of support of the 'background-size' property, but here is my thinking:
If you want to use a double sized background image, probably that is for high density (retina) displays. If so, I'd try to define my basic style with the single background image and the 'background-size', which will be ignored by older IE versions. However, browsers handling the pixel-density media query will try to render the double density background image.
.a {
background-image: url(img1x.jpg); /* 500x500 */
background-size: 500px 500px;
height: 500px;
width: 500px;
}
@media only screen and (-webkit-min-device-pixel-ratio: 1.5),
only screen and (-o-min-device-pixel-ratio: 3/2),
only screen and (min--moz-device-pixel-ratio: 1.5),
only screen and (min-device-pixel-ratio: 1.5) {
.a {
background-image: url(img2x.jpg); /* 1000x1000 */
}
}
I hope it makes sense and that's what you've been looking for.
Here are some more nice ideas about CSS/JS retina background sizing: http://coding.smashingmagazine.com/2012/08/20/towards-retina-web/
Upvotes: 0
Reputation: 6908
You already mentioned @supports
. You could define imgx1.jpg
as default and if background-size
is supported, you set it to img2x.jpg
For browsers like Chrome you could parse your CSS file with PHP and decide according to the User-Agent if the browser supports this or not.
You get the User-Agent in PHP with $_SERVER['HTTP_USER_AGENT']
Upvotes: 1