Feeds:
Posts
Comments

Here is a small script written in PHP for rendering of vendor-specific CSS3 properties on the fly, by defining them just once using the official W3C syntax. The css3 function generates not only vendor-specific properties, such as -moz-user-select, but also vendor-specific property values like the various CSS3 functions such as calc(), element(), linear- and radial-gradient(). You can download it from this link.

Below is an example for defining a vendor-specific property:

div
{
<? css3('transition', 'opacity 200ms linear'); ?>
}

… Which will output:

div
{
-moz-transition: opacity 200ms linear;
-webkit-transition: opacity 200ms linear;
-o-transition: opacity 200ms linear;
-ms-transition: opacity 200ms linear;
transition: opacity 200ms linear;
}

And here’s an example for defining the CSS3 function element():

div
{
<? css3('background', 'element(#background-div)'); ?>
}

… Which will give you:

div
{
background: -moz-element(#background-div);
background: -webkit-element(#background-div);
background: -o-element(#background-div);
background: -ms-element(#background-div);
background: element(#background-div);
}

* As of January 2012, the element() function is supported only by Mozilla FireFox, so you may consider using normal CSS to define that function.

All Features:

  • Detects and renders both vendor-specific properties and vendor-specific values, such as CSS3 functions;
  • Combines multiple CSS files into one;
  • If GZIP is available, the output stylesheet is gzipped and its size is much smaller than the size of all CSS files;
  • Supports multiple CSS3 property values, such as:
    div
    {
    <? css3('background', 'url("background.png") no-repeat center, linear-gradient(#ccc, #333)'); ?>
    }
    

Requirements:

  • Web-server with PHP support;

Usage:

  1. Register the script the way you normally register style sheets on the page:
    <link rel="stylesheet" href="css3.php?files=" />
    
  2. In the files parameter, define the path to all of the stylesheets that you want to merge:
    <link rel="stylesheet" href="css3.php?files=Styles/styles-01.css,Styles/styles-02.css" />
    

    The order in which you define them is going to be their inclusion order in the final PHP-processed file. Make sure that URLs, pointing to external assets such as background images and fonts are set relatively to the css3.php file, otherwise, they will not be requested correctly.

  3. In each of the CSS files, use the css3($property, $value) function to define CSS3 properties:
    div
    {
    <? css3('background', 'element(#background-div)'); ?>
    }
    
  4. If you wish to exclude some specific vendor properties, you can just remove them from the $prefixes array in the css3.php file:
    $prefixes = array('-moz-', '-webkit-', '-o-', '-ms-');
    

    The script can be easily changed to allow passing of prefixes as a function argument, if you wish to define the properties per function usage. Even better – the third argument can be an exclusion array, which will be checked against the vendor-specific array in the script itself (in_array()). Basically, you can change the function to this:

    div
    {
    <? css3('background', 'element(#background-div)', array('-moz-', '-webkit-')); ?>
    }
    
  5. Is is recommended to extend the script so it checks for already existing processed file on the server, instead of processing and merging it each time the page is requested. If the file does not exist, then the result of the PHP processing can be output to a static file that will be served.

The script can be downloaded from here. Other cool HTML5, CSS3 and JavaScript experiments can be found on this page.

2011 in Review

The WordPress.com stats helper monkeys prepared a 2011 annual report for this blog.

Here’s an excerpt:

The Louvre Museum has 8.5 million visitors per year. This blog was viewed about 180,000 times in 2011. If it were an exhibit at the Louvre Museum, it would take about 8 days for that many people to see it.

Click here to see the complete report.

In this post I will continue the series dedicated to HTML5 and enabling certain features of the language for browsers that still do not support them.

This tutorial also assumes the YUI JavaScript library and its code is in the same namespace as the HTML5 Details Element Enabler I wrote about last week.

According to WhatWG, “The placeholder attribute represents a short hint (a word or short phrase) intended to aid the user with data entry. A hint could be a sample value or a brief description of the expected format. The attribute, if specified, must have a value that contains no U+000A LINE FEED (LF) or U+000D CARRIAGE RETURN (CR) characters.“.  As of October 2011 it is not yet supported by Internet Explorer.

The solution presented in this post checks for the availability of the placeholder attribute in textboxes, and if it is not available applies its content as value to the elements that contain it. In order to achieve similar appearance as the real placeholder element we will also add or respectively remove a special CSS class name:

In short, the feature detection is:

var textarea = document.createElement("textarea");

if(undefined === textarea.placeholder) {
// execute code only for browsers that do not support placeholder
}

The _bind() method is pretty straightforward – we assign handlers for the focus() and blur() events, and according to the value of the input we set or unset the placeholder text:

_enable = function(e) {

var
element = e.currentTarget,
type = e.type;

switch(type){
case "focus":
if(element.get("value") === element.getAttribute("placeholder")) {
_set(element, false);
}
break;
case "blur":
if(element.get("value") === "") {
_set(element, true);
}
break;
}
}

The Markup:

<input type="text" placeholder="my placeholder text" />
<textarea placeholder="my placeholder text"></textarea>
<input type="password" placeholder="my placeholder text" />

The CSS Emulating the System Placeholder Style:

.placeholder-enabler
{
color: #ccc;
}

The demo is available on this page or you can download the code straight away from here. If you are curious about more HTML5, CSS3 and JavaScript experiments, bookmark this page.

According to WhatWG, the “<details /> element represents a disclosure widget from which the user can obtain additional information or controls“. In brief, you can use it to create panelbar elements without JavaScript, as the expand / collapse functionality is native to it. Currently (October, 2011), the only browser which supports <details /> is Google Chrome, so if you are eager to start using this element on your pages, you can do so with the help of a few lines of JavaScript to make sure it works on all browsers.

The implementation I am going to present today assumes YUI library, but it can also be accomplished easily with jQuery or with pure JavaScript. Basically, the most important part of the script is the feature detection:

if (!(OPEN in document.createElement("details"))) {
// enable expand / collapse with JavaScript for unsupported browsers
}

The code above will check for native availability of expand / collapse functionality, and if it is not present in the browser, it will bind click event to the <summary /> element that will toggle the open attribute of it’s parent – the <details /> element:

Y.one("body").delegate("click", function() {
var details = this.get('parentNode');

details.getAttribute(OPEN) ? details.removeAttribute(OPEN) : details.setAttribute(OPEN, OPEN);
}, "summary");

And the rest is just CSS:

details:not([open]) > div
{
display: none;
}

details[open] > div
{
display: block;
}

By using the :not() selector we make sure that if the open attribute is added by default to the <details /> element, its content will be expanded.

In case we need a custom expand / collapse arrow instead of the default one provided in Google Chrome we can hide it by using a proprietary pseudo element:

details summary::-webkit-details-marker
{
display: none;
}

… And then play with the ::before pseudo element of the <summary /> tag like this:

summary::before
{
content: "+";
}

details[open] summary::before
{
content: "-";
}

How to Use the HTML5 Details Enabler:

Script Assets:

<script src="http://yui.yahooapis.com/3.4.1/build/yui/yui-min.js"></script>
<script src="html-5-details-element-enabler/html-5-details-element-enabler.js"></script>

Stylesheet:

<link rel="stylesheet" href="html-5-details-element-enabler/html-5-details-element-enabler.css" />

Initializer:

YUI().use("html5-details", function (Y) {
var details = new Y.HTML5.Details();
details.enable();
});

The possibilities are numerous – you can apply cool transition effects for the expand / collapse, play with gradients and shadows, CSS3 makes most of the stuff really easy to achieve.

The HTML5 Details enabler is available for download from this link, the demo is here, and if you want to check other cool experiments, go to this page.

A disclaimer before I start this post – the solution I will present works with best with AJAX applications and can be applied for elements that are not present when the page initially loads.

According to Paul IrishFOUT is what I’m calling the flash of unstyled text that you get while using @font-face in Firefox and Opera.” and this could be quite annoying. Fortunately, on the Internet there are a few good solutions. The issues with the correct (expected) and timely download and application of web-fonts are three:

  1. The actual download of an embedded font starts after the load event of the page;
  2. The downloading of the font will not start until the browser parser encounters elements on the page that atually need this font regardless of the fact that the font is registered in the stylesheet using the @font-face directive.
  3. The font downloading will not start on elements with initial display: none.

Recently I was working on a web project that required the use of embedded fonts, and as the design guys needed a really bullet-proof solution, none of the articles I found was really suitable. Luckily, the project was fully ajax-driven and the embedded fonts were used on elements that were not initially on the page, so the solution I came up with was pretty obvious and easy to achieve – I created a few hidden elements (one for each font), whose font properties required the embedded fonts when page is initially loaded and in this manner the browser was forced to start downloading the font files, so they were available for the “real” elements that needed them later.

The Markup:

<span class="font-loader">
<span class="embedded-font-regular"><!-- / --></span>
<span class="embedded-font-bold"><!-- / --></span>
</span>

The @font-face Directives:

@font-face
{
font-family: "EmbeddedFontRegular";
src: url("../fonts/embedded-font-regular.eot?") format("eot"),
url("../fonts/embedded-font-regular.woff") format("woff"),
url("../fonts/embedded-font-regular.ttf") format("truetype"),
url("../fonts/embedded-font-regular.svg#webfontPPfl10JY") format("svg");
font-weight: normal;
font-style: normal;
}

@font-face
{
font-family: "EmbeddedFontBold";
src: url("../fonts/embedded-font-bold.eot?") format("eot"),
url("../fonts/embedded-font-bold.woff") format("woff"),
url("../fonts/embedded-font-bold.ttf") format("truetype"),
url("../fonts/embedded-font-bold.svg#webfontV2lCDIXN") format("svg");
font-weight: normal;
font-style: normal;
}

The .font-loader rules:

.font-loader
{
visibility: hidden;
position: absolute;
}

.font-loader .embedded-font-regular
{
font-family: EmbeddedFontRegular, Arial, Sans-serif;
}

.font-loader .embedded-font-bold
{
font-family: EmbeddedFontBold, Arial, Sans-serif;
}

Notice that I used position: absolute and visibility: hidden instead of just display: none, because affected browsers would not start downloading the font resources for elements with display: none;

Finally, if you don’t want to add meaningless and non-semantic empty elements on the page, you can easily recreate the solution I have offered with JavaScript that will create the markup on the client from a simple array.

More CSS3, HTML5 and JavaScript experiments on this page.

Recently I was asked to find a CSS-only solution for image (or anything) reflections, and since the only browsers that support box reflections (-webkit-reflect) out of the box are Google Chrome and Apple Safari, I had to find a crossbrowser solution, and this is what I would like to present today.

The Markup

Actually we need just a single element. A <div /> will do the job:

<div class="css-reflection"></div>

The CSS

In order to save myself from using nested tags, I decided to utilize the ::before and ::after pseudo elements. The ::before element will hold the actual reflection, and the ::after – the gradient blur.

The Reflection

In the ::before element, I set border and background to inherit, so the properties get their values from the parent element. Then I just flipped the element and offest it to 100% top:

transform: scaley(-1);
top: 100%;

The Reflection Gradient

In the first implementation I used CSS3 gradients to achieve the gradient blur, but since the application was supposed to run only on latest browsers, I decided to switch to SVG and keep the gradient definitions in a single place rather than boosting my CSS with vendor-specific -bula-bula-linear-gradients:

The SVG

<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
    <defs>
        <linearGradient id="gradient-to-white" x1="0%" y1="0%" x2="0%" y2="100%">
            <stop offset="0" stop-color="#fff" stop-opacity=".7"/>
            <stop offset="60%" stop-color="#fff" stop-opacity="1"/>
        </linearGradient>
    </defs>
    <rect width="100%" height="100%" style="fill:url(#gradient-to-white); " />
</svg>

The CSS

.css-reflection::after
{
background: url("gradient-to-white.svg");
}

The above is pretty straightforward – we create a rectangle that occupies 100% of its parent, then define a white semi-transparent to fully opaque white gradient. The SVG file is then set as background image to the ::after pseudo element of .css-reflection. Actually in the SVG file we can define any gradient color(s) that will match the parent of the element with reflection.

Displaying Pictures as Background Images

In order to display different images, I set a secondary class name to the .css-reflection reflection element:

<div class="css-reflection kitten-01"></div>

… And the following CSS:

.kitten-01
{
background: url("images/kitten-01.jpg");
}

So, that was it – quick and dirty. And a few ideas for consideration and maybe inspiration:

  • You can set the border-radius of the ::before and ::after elements to inherit, so the reflection will get the border-radius of the parent.
  • If you wish to have text which can be also flipped, you can use two nested elements with the same content, and flip vertically the second one and position it according to the reflection.
  • You may play with the -moz-element() property of Firefox to draw arbitrary elements as background to other elements, it’s very cool and can also be used to create CSS-only reflections.
  • You can use <img /> tag, clone it, and then flip the clone and again play with the SVG/CSS3 gradients if you wish to have a real image reflection.

The demo is available on this page, or you can download the example from this link. Find more experiments here.

Due to the growing popularity of the tips and tricks series on my blog, I  created a special secion on the Acid.JS Web UI website that will be used as a portal to all of the live examples of the experiments I write about. Here’s the link.

Enjoy your time there and feel free to contact me if you have questions or comments.

Can you believe that the treeview on the image below does not use any JavaScript, but relies only on CSS3?

Go to the live example

CSS3 Treeview. No JavaScript.

Today I’m going to show you a really easy and absolutely JavaScript-less solution for creating multi-level treeviews with minimal markup and with the power of CSS3. Basically what we need is a simple list:

<div class="css-treeview">
<ul></ul>
</div>

… With any number of nested items and subtrees. Each item that is going to be a container of a subtree should be supplied with a label and a checkbox.

Normal (non-clickable) item:

<li><a href="./">item</a></li>
<li><a href="./">item</a></li>

Expandable (clickable) submenu item:

<li><input type="checkbox" id="item-0" /><label for="item-0">folder</label>
<ul>
<li><input type="checkbox" id="item-0-0" /><label for="item-0-0">folder</label>
<ul>
<li><input type="checkbox" id="item-0-0-0" /><label for="item-0-0-0">folder</label>
<ul>
<li><a href="./">item</a></li>
<li><a href="./">item</a></li>
<li><a href="./">item</a></li>
<li><a href="./">item</a></li>
</ul>
</li>
</ul>
</li>
</ul>
</li>

Making it work is pretty simple and straightforward. All we need is to query the normal and :checked states of the checkboxes and set the adjacent <ul /> element to visible or hidden in the stylesheet:

Unchecked checkbox:

.css-treeview input + label + ul
{
display: none;
}

Selected checkbox:

.css-treeview input:checked + label + ul
{
display: block;
}
<pre>

For aesthetic purposes we hide the checkboxes like this:

.css-treeview input
{
position: absolute;
opacity: 0;
}

It is recommended to hide the checkbox with position/opacity rather than with display: none, otherwise you will have problems with certain browsers.

If your treeview is going to contain disabled subtrees, you can utilize the :not() selector, so disabled items with submenus will not be clickable:

.css-treeview input:checked:not(:disabled) + label + ul
{
display: block;
}

The visual representation of the disabled items can be accomplished by changing the opacity and the cursor of the label element:

.css-treeview input:disabled + label
{
cursor: default; /* or no-drop */
opacity: .6;
}

Finally, for the +/- buttons on the left, we can use generated content with the :before pseudo element:

.css-treeview label,
.css-treeview label::before
{
background: url("icons.png") no-repeat;
}

.css-treeview label::before
{
content: "";
width: 16px;
margin: 0 22px 0 0;
vertical-align: middle;
background-position: 0 -32px;
}

.css-treeview input:checked + label::before
{
background-position: 0 -16px;
}

All of the icons that have been used in the example are in the icons.png sprite. The solution will work with any browser supporting the adjacent element selector (E + E) and the attribute selectors of CSS3. Do not forget that the values of the for/id attribute pairs for the label and checkbox elements should be unique, otherwise the treeview will not work. Tab/Spacebar navigation is supported natively. The demo is availble on this page, or you can download it straight away from this link.

Of course this is just the basic concept that you can use for inspiration. A few ideas that can bring you even further:

- By adding the disabled attribute to a checkbox in your markup, the nested subtree will become expanded by default.
- You can use the cool CSS3 transitions to achieve cool behaviors.
- You can use additional classes to display different “folder” items.
- You can use :hover in order to show the pluses and minuse only when the treeview is hovered.
- You can use an additional class name that will show the pluses and minuses only when applied.
- You can use the attribute selectors to display different icons for each normal item according to the extension in the href attribute, for example:

li a[href$=".js"]
{
background: url("js.png") no-repeat center;
}

li a[href$=".css"]
{
background: url("css.png") no-repeat center;
}

View the demo or download it here. Find more experiments here.

GuitarChords.JS is the result of a fun experiment with CSS3, HTML5 and JavaScript that eventually went crazy with the ability to play the selected chord (no Flash, but real HTML5 audio), chord inversions and types and cool real-life stompbox interface with customizable LED display, knobs, buttons and large play button.

GuitarChords.JS - HTML5 Chord Finder and Player

GuitarChords.JS

And this is just the Beta release! Even more to come in the official release soon.

BETA Release Features:

  • Ability to play the current chord from small external .mp3 or .ogg sounds (no Flash, but real HTML5 audio) depending on the browser support.
  • Cool and friendly stompbox-like interface with LED display, knobs and large play button.
  • Chord data is stored in easy to understand json file(s) that can be easily edited.
  • User-defined chords data files.
  • User-defined chord types.
  • Any chord can be added and played.
  • Sounds are loaded on demand.
  • Incredibly small footprint.
  • Ability to display 3 inversions for each chord.
  • Customizable backlit color of the LED display.
  • Fully localizable.
  • Easy to install, setup and use on any standards-compliant website.
  • Fully AJAX driven.

Planned Features for the Official Release

  • Support for multiple chord data files that can be changed on the fly.
  • Add more chords and inversions.
  • Add flat and sharp variants of the current chord.
  • All sounds will be embedded as base64-encoded data in a cacheable json file.
  • Convenient tuner.
  • Volume control.
  • Continuous chord playing.
  • Highlighting of the currently played note.
  • UI improvements.
  • Export of the current chord in text format.

Supported Browsers:

  • Internet Explorer 9+
  • Mozilla Firefox
  • Google Chrome
  • Apple Safari
  • Opera

GuitarChords.JS does not initialize on older versions of Internet Explorer.

Technologies Used:

JavaScript, CSS3, HTML5 Audio, JSON and SVG. SVG has been used in Internet Explorer to achieve consistent gradients instead of using the classic filter gradient that bleeds through on elements with rounded borders.

Requirements:

  • Standards-compliant webpage (XHTML, HTML5) or optionally Skinny DTD. GuitarChords.JS will not initialize on pages with non-standards compliant DTDs and will display a warning.
  • Web server.

Screenshots

Visit the info page for GuitarChords.JS, view the demo or download it straight away. The component is included in the latest version of Acid.JS Web UI too.

I am happy to announce that the new website for the Acid.JS Web UI toolkit is already up and running with new design, improved accessibility, better user experience and loads of new and cool features.

Here are some of the highlights:

  • The Personal Bar at the top of each page allows you to:
    • Use Google to search Acid.JS.
    • Add pages to your very own bookmarks directly on the page that will be accessible when you return back to the site.
    • Add your very own notes in cool PostIt notes fashion which will be available after you return back to the site and will never expire unless you delete them.
  • New component purchase system for buying single components or component bundles via PayPal.
  • Improved user experience on component information pages with convenient tabs and direct access to the component demo, news, help page, purchase page, etc.
  • Tag cloud to see what is currently trending on Acid.JS.

The website is making heavy use of HTML5, CSS3, JavaScript, offline storage and client/server-side JSON and XML.

Below are a few screenshots from the new website, or you can just go and give it a try!

Older Posts »

Follow

Get every new post delivered to your Inbox.