Compass: generate Sprites, plus width / height on each images in the sprite - css

I'm using Compass (a CSS Framework) to generate sprite images.
It work, but compass generate only a background-position for each image.
Is it possible to get also the width and the height for each image in the sprite?
This is my code:
#import "ico/*.png";
#include all-ico-sprites;
The generated code:
.ico-sprite, .ico-bag-blue, .ico-bag-black {
background: url('../images/ico-s78b1a1919b.png') no-repeat;
}
.ico-bag-blue {
background-position: 0 0;
}
.ico-bag-black {
background-position: 0 -24px;
}
And the code i would like to have:
.ico-sprite, .ico-bag-blue, .ico-bag-black {
background: url('../images/ico-s78b1a1919b.png') no-repeat;
}
.ico-bag-blue {
background-position: 0 0;
width:40px;
height:24px;
}
.ico-bag-black {
background-position: 0 -24px;
width:44px;
height:30px;
}
Can anyone explain to me how I can do that?
Thanks.

This works:
#include all-<map>-sprites(true);
But you may want to consider the documented way of using configuration variables:
http://compass-style.org/help/tutorials/spriting/
You just specify the config variable before the import. In your case:
$ico-sprite-dimensions: true;
#import "ico/*png".
#include all-ico-sprites;
Sending true to the all include works, but as it's undocumented, it would seem that configuration variables are the preferred method.
Aside from dimensions these are the other configuration variables available:
$<map>-spacing // space in px around the sprites
$<map>-repeat // whether to repeat the sprite bg
$<map>-position // the x position of the sprite on the map
$<map>-sprite-base-class // the base class (default ".<map>-sprite")
$<map>-clean-up // whether to delete old image maps
$<map>-<sprite>-spacing // spacing, for individual sprites
$<map>-<sprite>-repeat // repeat, for individual sprites
$<map>-<sprite>-position // position, for individual sprites

I found the solution.
Just pass true as the second argument :
#include all-ico-sprites(true);
Quite simply.

Related

CSS: set fallback background-image without image()

The goal is is to set a fallback image in pure CSS, without using the image() notation. Otherwise, the goal would be this code:
#some-id{
background-image: image('default-image.png', 'fallback-image.png');
}
Indeed, in the context rising this question, the written CSS is processed and the follwing code :
#some-id{
background-image: /*#var default-image */;
}
will return:
#some-id{
background-image: url('/URL/TO/default-image.png');
}
As it is, there is no way to pass more than one parameter to this preprocessor.
One already explored idea would be to set immediately after the same id which have a background-image set to none. Indeed, the preprocessor do return none when there is no matching picture. So, in code:
#some-id{
background-image: /*#var default-image */;
}
#some-id[background-image=none]{
background-image: /*#var fallback-image */;
}
Unfortunately, it seems that it doesn't work.
You can use:
background-image: url("image.png"), url("fallback-image.png");
It will superimpose pictures and so you can play with the images transparency or no to get the expected result.
#some-id {
background-image: url('fallback-image.png');
background-image: image('default-image.png');
}

Capture and use all image URLs in a SASS file with a view to using css-only preload

I have recently started using css-only image preloading of background-images for a project.
//preload images
body:after{
display: none;
content: url(img01.png) url(img02.png);
}
//use images
li.one { background-image: (img01.png) }
li.two { background-image: (img02.png) }
I make my CSS files from SCSS, and was wondering if there would be some way I could use SASS to run through the file and create the body:after preload from the background-image URLs throughout the file?
If not, what would be your best solution, making a script to use Regex to do this step after the CSS file is compiled?
#yorbro solution works for this specific case but I think its better to use only a function to do this two things at once, add the image path to $preload-images list and returns the value. Here is the preload-img() function:
// This declare a list variable to store all images to preload
$preloaded-images: ();
// This function will append the image or images to $preload-images and returns img path values
#function preload-img($img-path) {
$output: ();
#each $img in $img-path {
$preloaded-images: append($preloaded-images, url($img));
$output: append($output, url($img), comma);
}
#return $output;
}
With this function you can use background or background-image property and you can pass more than one image path to create multiple backgrounds. As #yorbro says you should add body:after at the end of your entire CSS:
// Use images, you can use background or background-image
// Note that you can pass a list of paths to preload-image function
li.one { background: preload-img("img01.png" "img02.png"); }
li.two { background-image: preload-img("img02.png"); }
//preload images
body:after{
display: none;
content: $preloaded-images;
}
You can use SASS mixins, functions and lists for that. First, you create a mixin background-image that will add a background-image property and will append the image to a SASS list preload-images.
/* '$img-path' is in your case 'img01.png' or 'img02.png' */
#mixin background-image($img-path) {
background-image: url($img-path);
$tmp: preload-image($img-path);
}
Then you define the function preload-image along with a list $preloaded-images. The function appends url($img-path) to the $preloaded-images list.
/* Preloaded images */
$preloaded-images: null;
#function preload-image($image-path) {
$preloaded-images: $preloaded-images url($image-url);
#return $preloaded-images;
}
Every time you want to use a background image, you use the background-image mixin. Then, at the end of your entire CSS file, you add the body:after expression. This is important because you need to have added all the preloaded images to the list before outputting the body:after expression. So
//use images
li.one { #include background-image("img01.png"); }
li.two { #include background-image("img02.png"); }
//preload images
body:after{
display: none;
content: $preloaded-images;
}
Conclusion: SASS as a language is limited in some ways but still powerful enough to realise these kind of nice things!

Sprite loading multiple times, not caching as I would expect

I am trying to create a sprite mixin, based on the compass sprite mixins for SCSS.
The trouble is that the image is loading multiple times. One for each unique call of the image (so each new class name that refers to the sprite)
Here is the SCSS I am using. First we call the compass mixins:
$sprite-default-size:29px;
#import "compass/utilities/sprites/sprite-img";
Then I create my own mixin, designed to accept a column of images, with hover states to the right of each image:
$icons: "/assets/icons/socialMediaSprite.png";
#mixin verticalHoverSprite($row){
#include sprite-img("/assets/icons/socialMediaSprite.png",1,$row);
&:hover{
#include sprite-img($icons,2, $row);
}
}
The I use the apply the mixins to each required class:
.socialMediaLink{
#include verticalHoverSprite(1);
&.facebook{
#include verticalHoverSprite(2);
}
&.twitter{
#include verticalHoverSprite(3);
}
}
Here is the HTML I am attaching the images to:
<span class="socialMediaLink"></span>
<span class="facebook socialMediaLink"></span>
<span class="twitter socialMediaLink"></span>
Screen shot from Chrome network panel, which shows the image loading three times:
Check that caching is not disabled in your browser (it can be disabled from about v17).
Another idea is you include your image only once:
background: url(yourimage.png) no-repeat;
And then only change it's position with CSS without including the image again:
background-position: 0px 100px;
I guess you are trying to do this way I would just suggest not to include the image for every class, change only the position.
RynoRn was correct, but I thought his answer needed expanding to be specific to Compass SCSS, and not just CSS.
To fix it using compass and scss, I changed the code from the question to the following:
The mixin now has no reference to the image, just changes the position:
#mixin verticalHoverSprite($row){
#include sprite-position(1, $row);
&:hover{
#include sprite-position(2, $row);
}
}
and we add the background image to the socialMediaLink class:
.socialMediaLink{
#include sprite-background("/assets/icons/socialMediaSprite.png");
#include verticalHoverSprite(1);
&.facebook{
#include verticalHoverSprite(2);
}
&.twitter{
#include verticalHoverSprite(3);
}
}

Have a variable in images path in Sass?

I want to have one variable that contains the root path to all my images in my CSS file. I can't quite figure out if this is possible in pure Sass (the actual web project is not RoR, so can't use asset_pipeline or any of that fancy jazz).
Here's my example that doesn't work. On compile it balks at first instance of variable in the background url property saying ("Invalid CSS after "..site/background": expected ")").
Defining the function to return the path:
//Vars
$assetPath : "/assets/images";
//Functions
#function get-path-to-assets($assetPath){
#return $assetPath;
}
Using the function:
body {
margin: 0 auto;
background: url($get-path-to-assets/site/background.jpg) repeat-x fixed 0 0;
width: 100%; }
Any help would be appreciated.
Have you tried the Interpolation syntax?
background: url(#{$get-path-to-assets}/site/background.jpg) repeat-x fixed 0 0;
No need for a function:
$assetPath : "/assets/images";
...
body {
margin: 0 auto;
background: url(#{$assetPath}/site/background.jpg) repeat-x fixed 0 0;
width: 100%; }
See the interpolation docs for details.
Was searching around for an answer to the same question, but think I found a better solution: http://blog.grayghostvisuals.com/compass/image-url/
Basically, you can set your image path in config.rb and you use the image-url() helper
Adding something to the above correct answers. I am using netbeans IDE and it shows error while using url(#{$assetPath}/site/background.jpg) this method. It was just netbeans error and no error in sass compiling. But this error break code formatting in netbeans and code become ugly. But when I use it inside quotes like below, it show wonder!
url("#{$assetPath}/site/background.jpg")
We can use relative path instead of absolute path:
$assetPath: '~src/assets/images/';
$logo-img: '#{$assetPath}logo.png';
#mixin logo {
background-image: url(#{$logo-img});
}
.logo {
max-width: 65px;
#include logo;
}

Is there a way to set a common image path for LESS files?

I am using the LESS styling language.
Consider the following CSS:
.side-bg
{
background:url(../img/layout/side-bg.jpg) top no-repeat;
}
Right now all of my images are in the folder ../img/ I wanted to be able to set a variable as the image path and use it like so:
#image-path: ../img;
.side-bg
{
background:url(#image-path/layout/side-bg.jpg) top no-repeat;
}
This does not work however. Its not a huge deal, I could always use find and replace if the image folder ever changed. I am just starting to learn LESS and was wondering if something like this is possible.
Try using string interpolation for things like this. Look for “variable interpolation” in docs.
#base-url: "http://assets.fnord.com";
background-image: url("#{base-url}/images/bg.png");
The solution:
.side-bg
{
background : ~"url( '#{image-path}/layout/side-bg.jpg' )" top no-repeat;
}
I was searching for the same question and found this page. Thought I would post my solution as someone else might find it useful...
#iconpath: '/myicons/';
.icon (#icon) {
background: no-repeat url('#{iconpath}#{icon}');
}
.icon-foo { .icon('foo.png'); }
.icon-bar { .icon('bar.png'); }
.icon-spuds { .icon('spuds.png'); }
which compiles to (used http://winless.org/online-less-compiler)
.icon-foo {
background: no-repeat url('/myicons/foo.png');
}
.icon-bar {
background: no-repeat url('/myicons/bar.png');
}
.icon-spuds {
background: no-repeat url('/myicons/spuds.png');
}
Here is an updated and clean way to handle image paths with LESS:
Start with your variable:
#imagePath: ~"../images/bg/";
Then use it like this:
.main-bg {
background: url('#{imagePath}my-background-image.png') repeat scroll left top;
}
Make sure the #imagePath variable points to the images folder from wherever you have your compiled CSS, NOT from where you have your LESS files. Also, you have to escape the address in the variable as in the example above to ensure that it does not get rewritten by less.js.
Anton Strogonoff's answer is good but be aware of the Issue #294:
Using the above which comes straight from the docs, I get url://pathtolessfile/variable I set. Even though I'm trying to set an absolute URL instead of a relative one. For example this works
#base-url: "../../images/";
#background-image : url ("#{base-url}/bg.png");
But this does not work
$base-url: "http://localhost/ns/assets/images/";
#background-image : url ("#{base-url}/bg.png";
In the latter example, my final source path becomes
http://localhost/ns/assets/css/libs/http://localhost/ns/assets/images/bg.png
Relative urls can be handled by the command line compiler, supposedly. There's probably some similar option you can set in the file watcher.
https://github.com/cloudhead/less.js/wiki/Command-Line-Usage
EDIT: There totally is. Just look: http://lesscss.org/usage/#command-line-usage-options
relativeUrls: true

Resources