Pages tagged as ‘css’

Doctype Woes (back to HTML4)

October 3rd, 2007

At the moment I’m working together with the rest of the webteam of the ubuntuusers Team on the new portal of ubuntuusers.de based on django. One of the things we will do is consolidating all templates. And while doing so we have to decide to use an HTML/XHTML standard which we will use including the correct mimetype and doctype.

And selecting that is the hardest part because once you’ve decided on something you have to live with the consequences and cannot really change. For example HTML and XHTML have a slightly different DOM or different rules for CSS (CSS for example has an exception that allows background colors on the body-tag to affect the whole page, this exception does not exist for XHTML). Without a doubt many people use XHTML in a wrong way. Just have a look how many people serve their webpages as text/html and only use HTML semantics. They break if you serve them as application/xml+xhtml or render in a wrong way.

But why does XML and SGML have different semantics? SGML itself was created long ago (I assume IBM has something to do with it, at least it’s predecessor was created there) and is an insane specification. At least that’s what the web told me. I cannot tell you if that’s true or not because the standard itself is not available without paying for it :-/

From what sources tell me XML is an subset of SGML. I wonder how that’s possible tough, because there are syntactic elements that in my opinion are not compatible. For example clash XML’s self closing tags with null end tags in SGML:

XML <br /><br />
SGML: <p/This is some text in a paragraph/

Because the slash has a special meaning in tags in SGML it clashes with the closing slash of XML tags. Also SGML is apparently case insensitive where XML is not. Maybe I’m also wrong there and that part is up to the DTD, but quite frankly. I don’t care. I don’t even are about clashing slashes in tags because no browser implements the correct SGML behavior. And if they would do, we would all see invalid output because the web is not valid. It’s not and it will never be.

But what’s indeed ridiculous is that it’s incredible hard to write pages that are semantical and syntactical correct to both HTML4 and XHTML. However you have to make your documents compatible to both if you want to your page to be valid XHTML and render correctly. The reason is that no browser today selects the render mode by Doctype, and even if they would do, other browsers would break then on the huge number of pages that incorrectly use XHTML.

XML is strict, very strict. Syntactical errors appear as big red error messages. I for myself have to work on the wiki markup for the new portal and one of the things I have to deal with is balancing elements. That is possible and simple, but what’s harder is adding paragraphs without breaking things. And that’s not that easy because not every element is allowed in a paragraph and a paragraph cannot be mixed with every element thanks to inline versus block elements.

Even HTML5 disallows that mixing of different element types but at least it doesn’t complain. Sure, I could send the output through a validator and tell the user that his markup is bullshit and he should correct it. But I won’t do that. Users give a fuck about their markup. And I cannot bloat the parser more than it is now. Server resources are limited and additional validation for such a high traffic site is nearly impossible.

Fortunately browsers will never show you those errors because they parse XHTML with their tagsoup parser they use for HTML too. Even tough, if we cannot ensure that all of our pages are valid XML and XHTML we are not allowed to use the doctype because it would break browsers that support XHTML.

While this is hard for webdesigners and especially for programmers that want to create parsers that generate XHTML it’s an even harder job for the developers of browsers. In the end they have to have two independent parsers for HTML and XHTML. This makes it hard enough for the big browser vendors Microsoft, Mozilla, Opera and Apple, but even harder if you are new to the market and want to ship your own one. Because you not only have to be compatible with the new XHTML standard, but also the old HTML one. Nobody will translate all the old documents to XHTML I’m sure ;-)

Details about the issues are summarized here:

Without a doubt we will have fun with XHTML in the future. Probably the web stays like it’s today, we will still use the tag soup parsers, people will write XHTML that is HTML in fact and browsers will interpret it like that.

For me the decision is HTML4 at the moment, with the subset that is valid for both HTML4 and HTML5. That could make it easier for transition once the standard is ready (and I hope it’s earlier than 2022) and it’s good idea now too. Who needs an u-Tag anyway?

Using CleverCSS in Django

September 17th, 2007

A few minutes ago I pushed CleverCSS to the cheeseshop. So far there is no framework support, once again you have to hack up the bridge yourself, but in this post I’ll show a simple way to get CleverCSS running in django and simplify your CSS files.

The preferred way to use CleverCSS is compiling the clevercss files into css, and not doing that dynamically. But because during development this can be annoying, if you have to recompile your files by hand all the time, I suggest using a view that serves those files dynamically during development. In production usage you just overlay the view URL with an apache directive etc. that points to the folder with the static css files in.

Here the view function, you can store it directly in your urls.py because it’s that small. Otherwise move it into a application responsible for static stuff:

import clevercss
from os import path
from django.http import HttpResponse, Http404

def serve_ccss_file(request, filename):
    fn = path.join(path.dirname(__file__), path.pardir, 'styles', filename + '.dcss')
    if not path.exists(fn):
        raise Http404()
    f = file(fn):
    try:
        css = clevercss.convert(f.read().decode('utf-8'))
        return HttpResponse(css, mimetype='text/css')
    finally:
        f.close()

Now you only have to create an URL rule for that:

from django.conf.urls.defaults import *

urlpatterns = patterns('',
    (r'style/([a-zA-Z_]+).css', serve_ccss_file)
)

All you clevercss files now should go to yourproject/styles, as filename.ccss. If you enter production mode you just open your shell, go to that directory and execute clevercss.py *. (That requires that you have symlinked the clevercss.py file into your PATH.)

To test that, just drop a test.ccss file with the following contents in your styles folder and open http://localhost:8080/styles/test.css:

link_color = red

body:
  background-color: white.darken(10)
  font-family: 'Lucida Sans', Verdana, sans-serif;

a:
  color: $link_color
  &:hover:
    color: $link_color.brighten(10)
  &:visited:
    color: $link_color.darken(20)

CleverCSS

I was working on TextPress the last days, (I got motivated by the fact that WordPress has got security problems once more) and had to notice that CSS could need some variables. I wanted to write a simple preprocessor for css that inserts variables but ended up writing a small parser that accepts indented CSS code with inline expressions.

Basically what it does is converting this:

// Single Line Comment
foo = 4px
font_family = 'Verdana', sans-serif
base_size = 0.9em

/*
   this is a multiline comment
 */
body:
    padding: $foo * 4
    font ->
        family: $font_family
        size: $base_size + 0.2em

a.foo:
    background-image: url(foo.png)
    span:
        display: none

Into this:

body {
  padding: 16px;
  font-family: Verdana, sans-serif;
  font-size: 1.1em;
}

a.foo {
  background-image: url(foo.png);
}

a.foo span {
  display: none;
}

The advantage might not be visible in that small example but consider complex layouts etc. One thing I would love to add is some support for layout extending. Say you have a base layout and you can say @extends(’layout.ccss’) and would get all the layout informations from the layout file. But I don’t know how useful this is.

Right now the conversion process is quite slow, but I wouldn’t generate such stylesheets on request. It’s a much better idea to do generate them from a script. During development one could still generate them automatically.

The module is available in the sandbox hg repo: clevercss.py. Just call clevercss.convert and pass it the CleverCSS markup.

Things that don’t work yet are unit conversions. For example you cannot do “1cm + 11mm”.

cogitations driven by wordpress