We're using SVGs for the first time for our mobile HTML5 based app sprites file (they make dealing with retina an other screen size differences easy).
I know generated SVGs can be manipulated directly (as they are text files) but can one modify an SVG asset (in this case, a background image loaded via the CSS) via CSS or scripting?
For instance, can we load an all-black SVG object, and then change it to white?
You can't access the DOM of the SVG file if it's loaded as an image (either through img or background-image). You can't style it via CSS either.
If you intend to do these kind of manipulations you should append the SVG to a div. You should still be able to perform sprite-like manipulations to that div. You will be able to style it via CSS or javascript.
The SVG should be inlined. You can copy and paste the SVG into the div that used to contain background-image or load it there through an ajax request.
Instead of animating background-position you can animate with left or -webkit-transform: translate(...).
Related
I want to use animated GIF in my Gtk3 application. I know this can be done by assigning GdkPixbufAnimation to the Gtk.Image component, but this approach requires the animation file name to be referenced directly from the source code.
Is it possible to specify the animation file in CSS, like "normal" background image? I tried to set the animated GIF as background-image property of Gtk.Image and Gtk.Label components, but the image is displayed statically.
TL;DR: Is it possible to load other images based on media-query from svg included via img tag?
I generate a bunch of svg files with have tables with text and icons inside. A PDF would be semantically a better container, but I need to keep such "documents" as images for seamless embed/preview and it probably won't solve my problem. So the story is about icons.
I wrote inline styles with media queries picking icons corresponding to user's screen DPI. Icons are already bundled into sprites, so I use pattern/image[xlink:href] + fill:url(#id). Everything works as needed when I embed svg directly into HTML (DOM islands). But if I embed svg via img tag (i.e. <img src="foo.svg">), it doesn't load icons at all, let alone showing them.
I understand, that I can embed icons via data-URL, but embedding icons for all supported screen dpis seems too much. The irony is that icons are raster ones, hardly vectorizable pixel-art, so I cannot have one set of icons for all DPIs.
Is there a way to have proper icons picked by media query w/o embedding them all?
You can't load external files from an SVG used in an <img> tag (or used in other "image" contexts, like CSS background images). For security and performance reasons, SVG used as image has to behave like any other image -- a single file, no secondary resources and no scripts.
If you don't want to use inline SVG, you might consider embedding an SVG file with an <object> tag or <iframe>. However, I recommend that you actually test carefully to see whether browsers are downloading the image files even if they aren't using them because of CSS.
So since it's not possible to load conditionally: either embed or not, I should do some clever detection about raster sets. Technically not a direct answer, but in case someone needs.
I decided to go with cookies. People visit normally the same site that hosts those SVG.
I'd set a cookie for their DPI and then all SVGs served would pick proper DPI images.
For people who haven't visited the site yet, I'd go with UA sniffing: mobiles and macs get 2x, others 1x. Or just 1x for everyone.
Ok, obviously if you have a lot if icons you generally load them in via a background image so you can utilise sprites; however, I was just wondering if there is any advantage to loading them in via the background versus loading them via a img tag when it is just a single image?
Does the one in the CSS still make a http request for the image?
Sounds like you're mostly interested in how this affects performance. But since the question is open-ended here are other reasons, for completeness:
If you need to calculate the image's height based on its width (a common responsive design method is width: [something > 0]; height: 0; padding-bottom: [some]% )
If you need to use CSS to swap out the image (basic icon example: if the image changes on :hover and you aren't using a sprite, for any number of reasons)
If you need to be able to use CSS background options like background-size or background-position (IE > 8)
If you need to have HTML on top of your image without adding an additional element
If you need to use pseudoelements like :before and :after, which are not supported for <img> (not required to be supported, anyway)
Yes, it still makes a request, unless you URL encode the image, but this you can also do inline and is not necessarily more performant.
I am placing a large, non-repeating background image on my website using the CSS background property. Since the image is so large, it takes a long time for some connections to render the image.
Here is my CSS:
#wrapper {
background: url('large-image.jpg) no-repeat center center;
}
I have already done the following to optimize the image for the web:
Reduced it to the lowest possible resolution that does not compromise quality
Changed the image type from a PNG to a JPEG
Styled the page so that the content is readable even without the background image
My question: To further optimize the image loading time, would it make a difference if I put the background tag at the bottom of my style sheet? Or would the effect of this be negligible?
I tend to order my CSS by the hierarchy of my HTML, so the #wrapper styles are at the top of my style sheet. Does the order of properties in a style sheet make a noticeable impact on load time when the user has a slower connection?
Location in the stylesheet will not affect the load time.
What you can do though is prevent it loading in some cases, such as on a cellphone.
For reference:
http://css-tricks.com/snippets/css/media-queries-for-standard-devices/
Those media queries aren't fail-proof, but they'll catch alot of the slower cases, which would generally be mobile devices. On the other hand, if somebody is on a 56k modem with their desktop, I just don't know what to do about it (maybe they're used to it).
You can use Jquery and waitforimages to ensure it loads after all other images, if you wish.
What could affect perceived loading time is initial #wrapper availability - i.e. if at the time of the initial load it is not part of the page and is added with JS, the background image will not begin loading - but I doubt this would be a common scenario.
Background image loading does not affect domready handlers, however if you want to speed up background availability you could try the following:
#wrapper {
background: url(large-image.png) no-repeat center center,
url(small-image.png) no-repeat center center;
}
From mdn:
With CSS3, you can apply multiple backgrounds to elements. These are
layered atop one another with the first background you provide on top
and the last background listed in the back. Only the last background
can include a background color.
What this does is effectively allows you to load a lower-res image as the bottom layer of the background, while the expensive hi-res image is still loading. Remember the good old times of lowsrc? That's the behaviour we're simulating. Note that both the low- and the hi-res image downloads begin simultaneously, so use this only if the large image is truly unbearably large.
Also: you're saying you've optimized the image; I still suggest you try Yahoo SmushIt, you'd be surprised how muich redundant data can be stripped from a PNG witout loss of quality (I currently have intermittent problems using their service, but it works after a few attempts, alternatively you could use OptiPNG but imo it would be too much effort to set it up and configure for a single image)
Update:
It has been suggested you wait for domready to fire and add your style using $("#wrapper").css(...);. What that does is add inline styling to an element, which would 1) interfere with selector specificity 2) only apply to this particular instance of #wrapper (bad if, say, it is part of ajax content coming from the server).
You could alternatively add a new css rule at runtime:
$('head').append('<style type="text/css">#wrapper {background: url(large-image.jpg) no-repeat center center;}</style>');
This would be organically added to document stylesheets and apply to all future instances of #wrapper, as well as not interfere with selector specificity. You still end up with a brief flash of unstyled content (before the handler is fired and the style is applied) so I don't advocate this approach.
See this previous question. The CSS stylesheet will be fully loaded and evaluated before the page is shown, so the location of your background-image CSS does not matter in the stylesheet.
If you want the image to only load once the rest of the content is displayed you could use jQuery:
$(window).load(function(){
$("#wrapper").css({'background-image':'url("large-image.jpg")', 'background-repeat':'no-repeat', 'background-position':'center center'});
});
I have created the layout of the website (template). I used Photoshop to design the picture and sliced it to create the divs. It gave me an HTML file including the HTML and CSS code. I separated these in two files HTML and CSS. The background images were being called inside the <div id="idName"> tags as <img src=... tags. I changed this. I loaded the images in the CSS file as
idName { background-image: url(URL); }
All the images in the site are loaded like this creating the background as a whole.
Now my question is: Is this a bad practice? because if I leave the images inside the <div> tags I wont be able to put my content on top of the image. With the background-image attribute in the css file I can put my content anywhere, not having to worry about the background.
No, this is perfectly fine, and actually may be a best practice for background images. Moving the image declarations into the style sheet means the images may be downloaded a little bit later, but most browsers should have enough other resources to load in the meantime, and you'll want prioritize HTML and stylesheets before background images anyways.
Just don't use CSS backgrounds for actual images: If the fallback background color would significantly change the meaning (i.e. the image is content), you should use <img> elements with an alt= attribute. If you're not sure whether this is a good idea, consider this question.
To increase performance (by reducing the number of HTTP requests), you may want to consider using CSS sprites.