Advanced CSS Sprites using pseudo-elements, Cropping and LESS (Cross-Browser, IE6+)

A common way to use images on websites are CSS sprites. I assume that you are familiar with this technique for the following explanations.

The Problem with the Classic Method

If you are using sprites for icons, there are not many problems in any browser. You would just use the classic solution, which is something like

.icon {
    background: url(sprite.png) no-repeat 0 -16px;
    width: 16px;
    height: 16px;
}

But there are several problems with this method, when using e.g. an image (16×16) in the bottom left of a 100×100 box without additional markup. Have a look at this example.

Here is the sprite:

and here is the example we want to create with the given sprite

Some example text.

In this case you need to add extra space (84px) to the top and to the right of the image to hide the other images in the sprite. This can be a problem, when the size of the box becomes larger. You have to move images in the sprite, because lack of spacing. That’s bad.

Cropping clips from the sprite using the url()/clip Method

I’ve used a technique mentioned in the article Styling Elements With Glyphs, Sprites and Pseudo-Elements on Smashing Magazine. This method makes use of the CSS property clip and adds some extra code for IE6+ support (using an expression on the background-image property).

Here is the adapted code example of this technique, which results in exactly what we want, using the optimized sprite shown at the beginning of the article.

.clip-example-2 {
  position: relative;
  background-image: expression(this.runtimeStyle.backgroundImage='none', this.innerHTML = '<img alt="" src="http://www.rogerdudler.com/files/sprite.png">' + this.innerHTML);
  width: 100px;
  height: 100px;
  border: 1px solid #999;
}
.clip-example-2:before,
.clip-example-2 img {
  content: url(http://www.rogerdudler.com/files/sprite.png);
  position: absolute;
  clip: rect(0px 30px 15px 15px);
  bottom: 0;
  left: -15px;
  height: 15px;
}
<div class="clip-example-2">Some example text.</div>

This will result in the example shown above

Some example text.

Additional Advantages over classic method

  • Unlike background images, these images are printed with the document
  • Unlike background images, these images will not disappear in high contrast modes
  • Works in IE6 and IE7
  • More flexibility on sprite layouts
  • Less problems with dynamic sized container elements

Examples

You can play around with this technique on my jsFiddle Playground.

Open the example

Steps further – Compile the CSS using LESS

You need to write a lot of CSS and calculations when using the cropping technique. So, I decided to create a LESS template, which does the work for me. With a lot of elements in the sprite, this can be very useful.

.sprite {
    @sprite: "http://www.rogerdudler.com/files/sprite.png";
    &:before, img {
        content: url(@sprite);
        position: absolute;
    }
    position: relative;
    background-image: ~`"expression(this.runtimeStyle.backgroundImage='none', this.innerHTML = '<img alt=\"\" src=\"http://www.rogerdudler.com/files/sprite.png\">' + this.innerHTML)"`;
}

// clipping function for image sprites
.clip(@top, @left, @width: 15px, @height: 15px) {
    width: @width;
    height: @height;
    &:before, img {
        clip: rect(@top @left+@width @top+@height @left);
        bottom: 0;
        left: -@left;
        height: @height;
    }
}

.sprite-delete  { .clip(0px, 15px); }
.sprite-warning { .clip(0px, 30px); }

This will result in a CSS like this

.sprite {
  position: relative;
  background-image: expression(this.runtimeStyle.backgroundImage='none', this.innerHTML = '<img alt="" src="http://www.rogerdudler.com/files/sprite.png">' + this.innerHTML);
}
.sprite:before, .sprite img {
  content: url(http://www.rogerdudler.com/files/sprite.png);
  position: absolute;
}
.sprite-delete {
  width: 15px;
  height: 15px;
}
.sprite-delete:before, .sprite-delete img {
  clip: rect(0px 30px 15px 15px);
  bottom: 0;
  left: -15px;
  height: 15px;
}
.sprite-warning {
  width: 15px;
  height: 15px;
}
.sprite-warning:before, .sprite-warning img {
  clip: rect(0px 45px 15px 30px);
  bottom: 0;
  left: -30px;
  height: 15px;
}

Simplified Search Input Field Design

I love to design sometimes. This time, I decided to create a very simplified search field. You can see the initial state in the first example, the focus state on the second one and the button hover state in the last one. Hope you like it :) You can download the PSD here. There is a dark version as well.

I’ve created an example on JSFiddle without any images. The search icon is made with HTML5 canvas. View Example: http://jsfiddle.net/rogerdudler/ArdJ6/

Quick Tip: Typo3 – Richtext Editor (RTE) in Extension verwenden

Um in einer eigenen Typo3 Extension den Rich Text Editor verwenden zu können, muss in der TCA folgende Konfiguration für das entsprechende Feld verwendet werden.

'content' => array(
    'exclude' => 0,
    'label' => 'Content',
    'config' => array (
        'type' => 'text',
        'cols' => 40,
        'rows' => 10,
        'wizards' => array(
            '_PADDING' => 2,
            'RTE' => array(
                'notNewRecords' => 1,
                'RTEonly' => 1,
                'type' => 'script',
                'title' => 'Full screen Rich Text Editing|Formatteret redigering i hele vinduet',
                'icon' => 'wizard_rte2.gif',
                'script' => 'wizard_rte.php',
            ),
        ),
    ),
)

Wichtig ist auch, dass man folgende Konfiguration im TCA ‘showitem’ Element vornimmt. Hier werden nur Bold und Italic als Formatierungen zugelassen. Dies kann an die eigenen Bedürfnisse angepasst werden.

content;;;richtext[bold|italic]:rte_transform[mode=ts]

Frontend 2011 – A summary

UPDATE: The videos of all talks are available on http://www.frontend2011.com/#videos

From October 10 to 12, the Frontend 2011 Conference took place in Oslo. This is an international web conference with well-known speakers and a good mixture of topics like UX Design, Frontend Engineering and conception, but also marketing and research. I had the opportunity to participate and I would like to sum up some interesting talks and impressions in this article. I deliberately chose talks outside my daily business topic, development. In my opinion, this broadened my horizon extremely, and I can only recommend that. The conference consisted of two days of talks and one day of masterclasses, a kind of workshop.

Embracing the ebb and flow by Simon Collison (@colly)

Simon Collison gave the conference an inspirational kick-off. His talk was about general topics regarding finding new ideas and the recent development in UX Design. We should try to understand why in real life as well as in the internet we like some things within few seconds and others we dislike. In his opinion, we should not be misled to make decisions regarding the design based on tools (like e.g. CSS3 effects), but to make them because the user gets an advantage. In additon, the browser window should not be considered to be a closed frame, but an extract of a whole. Of course, he also talked about Trending Topic Responsive Design. In the future, Simon would like people to work on a kind of visual grammar, like with the concept Responsive Design by Ethan Marcotte, so that customers can also get a better understanding for these topics.

Sketchnotes by Eva-Lotta Lamm, Designer (@evalottchen)

A not exactly new but exciting way to make notes was presented by design expert Eva-Lotta Lamm with her talk about Sketchnotes which is about making notes in form of visual elements away from classic text notes to a universally understandable mix of text and picture. According to this creative talk, not being able to draw is not an excuse. Of course, I tried this approach during the next talk by the Standardistas. Besides having fun while listening, I really had the feeling that I got more out of my notes. Definitely try it yourself! Here my notes


What it looks like when Eva-Lotta does it can be seen in her Flickr Collection “Sketchnotes”.

Designing the Fluid Web by the Standardistas

The Web Standardistas gave us an interesting exercusion into the history of the web. I have to admit that the OLMA (a Swiss thing) poster on one of the slides might have influenced me, though. The two gentlemen from Belfast talked about Responsive Design, but also about the so called secret formula for good websites. It includes proportions (size, spaces, ratios), hierarchy, typography, compositions & systems (consistent, recognizable concepts, e.g. with colours, titles, content, etc.) Many book recommendations, a case study about the german railway and a bit more Responsive Design rounded this talk off nicely.

Crafting the User Experience by Sarah Parmenter, Designer

In my opinion, Sarah Parmenter gave a very good talk. She works as UX designer in the iOS field. Her talk was mainly about examples of small but effective actions or changes which influence customers, just like Coca Cola did with the Happiness Machine Project . Or like 7-up which got a notable increase in turnover with the simple increase of yellow (+15%) on the can design, which made customers think that the drink was now more refreshing. Beside many more examples, colours were also an important topic because they can cause problems since their meaning can be different from one culture to the other (Colours in Cultures) or Dark Patterns. In the end, many impressive and helpful examples from Amazon and Co. gave a good overview about simple and effective methods to (fairly) influence your customers.

Lettering by Jessica Hische, Designer

With her talk about Lettering, Jessica has proven that passion is an important ingredient in the work of a designer or a developer. She talked a lot about the design of single letters or typodesign. She explained why fonts may seem so expensive but are really a fair price. Just think of the popular type Gotham, whose production cost an estimated million dollar.

Ecosystems by Albert Shum, Designer, Microsoft

The presentation by Albert Shum was about that topic Microsoft is having difficulties competing with their competitiors, above all Apple, namely the Ecosystem. In his talk, Albert has shown what is important when building a new ecosystem around one’s product. I’ve listed some of the mentioned principles:

• Give people something to participate
• Don’t try to do everything yourself, only plant seeds
• Leave it open, but set constraints
• Make it easy to build on it
• Start a conversation
• The design is only finished when the community takes it over

Time will show if Microsoft succeeds in building a successful ecosystem with Metro.

Everyone acts differently by Joseph O’Sullivan

Joseph works as „problem solver“ for Intuit, an US american software company, which nearly completely dominates the market for private tax software. With creative methods, Joseph has changed the corporate culture and has made it very customer oriented by applying the following principles:

1. Principles over processes
2. Companies are networks, not hierarchies
3. Swim downstream
4. Say / Do ratio
5. Hand over control (e.g. every employee can design)

According to Joseph, it is important to treat every problem in a company as a design problem. In practice this means many workshops with storyboarding, sketching, testing, as well as hands-on of the management and the involvement of the creativity of all employees. In my opinion, this is a extremely fruitful strategy, although it might be risky in an organization of this size.

Here is an example of the first storyboard made by me in Josephs Masterclass about Storyboarding.

Persuasive Web Design by Andy Budd

O think this was one of the best talks at the conference. There was a lot of psychology but a very intersting talk given by Andy Budd from ClearLeft. Andy started to intensively examine the behaviour of people in certain situations as well as their influencing, if in Las Vegas in front of the Wheel of Fortune, at the supermarket, in the classic advertisement or in the internet. Everywhere we are influenced. Also primary instincts like „What’s beautiful is good“ have a lot of influence especially in the web. Or let’s take the facebook button as an example: We always try to orient ourselves by others to find the social standard. As a result, we are more willing to press the “Like” button if we see a high number of likes than if we see a small number or even 0. Or another example is the facebook wall: analyses have shown that remarks on the wall get responses in 99% of all cases. Just because we don’t want to seem impolite but want to be answering friends. This knowledge can be used in the web as well. Other topics like Gamification or that a limited offer can boost the demand (see Apple) were also mentioned.

A short break with an image of the stunning Oslo harbour :)

Object-oriented JavaScript by Sara Chipps

Sara Chipps’ talk was mostly about the basics of the application of object orientation in JavaScript without libraries. Besides many code examples Sara also showed some examples related to maintability. For beginners, especially those without any background of object oriented programming, this presentation was very helpful. Sara briefly mentioned projects like the JS Template Engine Tempo, as well. An important bottom line is that a clear, maintainable Frontend Code will get more important in the future. I am convinced that future frameworks like Terrific will significantly contribute to this goal.

CSS3 Secrets by Lea Verou (@leaverou)

As far as CSS is concerned, this lady cannot be fooled. Her talk, similar to a talk at the Frontend Conference in Zürich, was definitely worth a visit. Lea presented 10 CSS techniques, which have not been seen before in this particular form. She surprised the majority of her audience with tricks like diagonal stripes with pure CSS (gradients), clean styling of check boxes, animation magic with Bezier Curves and many more. Naturally, essential parts of the presented functions are not availabe in older browser versions. But in recent versions of FF, Webkit, Opera and also IE the support is appealing. Lea presented what can be done now and especially in the future with the help of CSS3 and that is fantastic. These 10 CSS3 secrets can be found on SlideShare. By the way, during the conference Lea put her latest project PrefixFree online and it is definitely worth a visit.

Lea is a very nice person and really passionated about what she’s doing, we had a great time at the IXD afterparty. Do you see the Dreamweaver & Flash pillows, they were added against her will ;) Because of the bad image quality, i had to make the image a little bit artistic, sorry about that.

Module Driven Development von Dustin Diaz (@ded)

Dustion Diaz was certainly one of the most famous speakers. He has worked as a developer for Yahoo, Google, and Twitter, was responsible for the new Twitter and is considered to be the JavaScript expert. For a few months, he has been working for a startup called Obvious. In his talk he presented Ender. In short, Ender is a package manager of JavaScript modules. Based on npm (package manager for node.js) modules can be installed (e.g. Selector Engine, Query Engine, Animations, etc.) and that limited on those which you really need for the respective project. As a result, the JavaScript gets in parts significantly smaller. It is supposed to be an alternative to libraries like JQuery. It is an ambitions but certainly interesting project.

That’s it

This was a brief glimpse into the contents of this year’s Frontend 2011 conference. If somebody likes more details about one of the talks, you can reach me via twitter (@rogerdudler) or skype (rogerdudler).

Many thanks to the IXD Team (@ixdnorge) for organising this conference. I met some very interesting and cool people like Matthias (@digitalcult), Elisabeth (@sortenke), The French Guy (@stratosferik), Roooooger (@rogerguttormsen), Jenny (@jennysjogren), @mikkelrom and the danish lego team, Wolf from HotGloo (@wdbecvar) or Joisten (@jhuglen) and many more (Tonje, Morten, etc.). Hopefully, I will be back next year. This article was originally written in german and was thankfully translated by my brothers future wife Sandra. Thanks!

Quick Tip: Redirect URLs with underscore to new permalinks with dashes in WordPress

If you need to migrate blogs from another system to WordPress, it might be a problem, that your permalink structure changes from underscores (“_”) to dashes (“-”) like in the following example.

Old: http://www.example.com/2011/09/my_new_blog_post.html
New: http://www.example.com/2011/09/my-new-blog-post.html

You probably want both of them to work in your new system. Here is a way to achieve this goal in WordPress using the pre_get_posts filter. This filter is not really documented, but I found this one in the get_posts function in wp-includes/query.php. The old URL will be redirected using a 301 Moved Permanently header, to avoid SEO problems like duplicate content. A canonical link would be another alternative, if you don’t want to have a redirect.

// Define old and new separators (default WP is the dash)
define('SLUG_SEPARATOR_NEW', '-');
define('SLUG_SEPARATOR_OLD', '_');

// we make use of the pre_get_posts hook
add_filter('pre_get_posts', 'custom_pre_get_posts');

/**
 * Redirects slugs with old separator to new permalinks.
 *
 * @param $query the query object
 * @return void
 * @since 1.0
 */

function custom_pre_get_posts($query) {
    global $wpdb;
    $name = $query->query_vars['name'];
    if (strpos($name, SLUG_SEPARATOR_OLD) > 0) {
        $name = sanitize_title_for_query($name);
        $new_name = str_replace(SLUG_SEPARATOR_OLD, SLUG_SEPARATOR_NEW, $name);
        $posts = $wpdb->get_results("
            SELECT ID, post_title, post_name
            FROM $wpdb->posts
            WHERE
                post_name = '"
. $new_name . "' AND
                post_status = 'publish' AND
                post_type = 'post'
            LIMIT 1
        "
);
        foreach ($posts as $post) {
            $permalink = get_permalink($post->ID);
            header('HTTP/1.1 301 Moved Permanently');
            header('Location: ' . $permalink);
            exit();
        }
        wp_reset_query();
    }
}