eRIZ’s weblog

PHP, webdesign, Linux, Windows i inne, bo nie samym chlebem człowiek żyje
Serdecznie zapraszam do udziału w ANKIECIE

Komentarze warunkowe i expressions w Firefoksie

Pewnie wiele osób męczy się podczas cięcia z różnymi bolączkami przeglądarek. Jak to wszystkim (jeśli nie, to teraz już tak), nie ma dwóch przeglądarek identycznie renderujących konkretną stronę. Nawet mój weblog w każdej przeglądarce jest jakoś inaczej narysowany, najczęściej są to błędy rzędu złudzenia optycznego (np. margines, czy inaczej zrenderowane ramki obiektów).

Ale już grubą przesadą jest sytuacja, w której większość przeglądarek radzi sobie bezbłędnie z danym ostylowaniem, a jedna konkretna nie. Na ogół da się odpowiednio przeprojektować layout tak, aby wyeliminować artefakty. Niestety, nie zawsze się tak da. W tym celu wymyślono hacki.

Ach, geneza

Kochany IE, ilu z nas, webdesignerów go kocha… No dosłownie cud, miód i orzeszki, nie? Hehe, żartowałem, jak coś. ;) Mianowicie, w jego przypadku nie da się zrobić tak, ażeby nie skorzystać z osobnego CSS-a. Owszem, nieraz da się zminimalizować, ale np. półprzezroczyste PNG-i, czy pseudoklasy :before, :after, :hover, równe kolumny, etc. wymagają pewnych obejść, którymi nie ma sensu maltretować pozostałych przeglądarek. I tak mamy do dyspozycji komentarze warunkowe:

  1. <!--[if lte IE 7]>
  2.    <link rel="stylesheet" type="text/css" href="css/ieFix.css" />
  3. <![endif]-->

Składnia jest ogólnie taka, jak w powyższym listingu. Zmieniają się tylko warunki, w zalezności od IE:

  1. <!–[if IE]>

    jeśli IE

  2. <!–[if IE 6]>

    jeśli konkretnie IE 6

  3. <!–[if lt IE 6]>

    jeśli starsze niż IE 6

  4. <!–[if lte IE 6]>

    jeśli IE 6 lub starsze (lower than/equal)

  5. <!–[if gt IE 6]>

    jeśli nowsze niż IE 6

  6. <!–[if gte IE 6]>

    jeśli IE 6 lub nowsze

Mamy też tzw. expressions:

  1. .entry .meta, #addComment .comment
  2.     /* float fix */
  3.     { -ix: expression(this.parsed ? 0 : (
  4.             this.insertBefore(this.childNodes[this.childNodes.length-2], this.firstChild),
  5.             this.parsed = 1
  6.         ));
  7.     }

Expressions w IE mają to do siebie, że pozwalają korzystać z tylko niektórych konstrukcji języka i to pod zmienioną składnią. Muszę tylko koniecznie zaznaczyć, że sprawdzanie parsed jest konieczne, gdyż expressions są wywoływane nawet kilkaset razy na sekundę! Bez tej weryfikacji doszłoby do zawieszenia przeglądarki (sprawdź sam(a)).

nie wszystko jest idealne…

Niestety, Firefox również nie jest idealny. Do tej pory nikt go nie nauczył, jak powinno wyglądać generowanie treści przez pseudoklasy :before i :after. W związku z tym, eleganckie tworzenie zaokrąglonych rogów może pozostać tylko marzeniem. Na ten dziwny, a jednak dotkliwy problem natknąłem się przy wdrażaniu nowego layouta dla ZamCampa. Co ciekawe, z IE sobie poradziłem, Opera wszystko wyświetla jak najbardziej OK, Chrome też, Safari było formalnością. Ale już nie Firefox. Po wielu chwilach bezowocnej walki odłożyłem zabawki w kąt.

Po jakimś czasie, wróciłem do problemu i przypomniałem sobie, że Riddle kiedyś z tym walczył. Jednak jego technika nie działała idealnie. No i pobawiłem się nieco tym rozwiązaniem, jakim jest XBL.

na warsztacie

O ile technika XBL jest bardzo rozbudowana, skupię się tylko na dwóch najprostszych zastosowaniach - mianowicie - dołączenie dodatkowego arkusza stylów oraz podstawowych manipulacjach po drzewie DOM.

Cała filozofia sprowadza się do utworzenia odpowiedniego XML-a postaci:

  1. <?xml version="1.0"?>
  2. <bindings xmlns="http://www.mozilla.org/xbl" xmlns:html="http://www.w3.org/1999/xhtml">
  3.     <binding id="fixx">
  4.  
  5.         <implementation>
  6.             <constructor>
  7.                 //<![CDATA[
  8.                     alert('hello world!');
  9.                 //]]>
  10.             </constructor>
  11.         </implementation>
  12.     </binding>
  13. </bindings>

Struktura szczególnie trudna nie jest, dla nas przydatna będzie część <constructor>. To w niej dodajemy skrypty przeznaczone specjalnie dla Firefoksa. Jak dołączamy XBL-a? Bardzo prosto: w głównym CSS-ie strony tworzymy nową regułkę:

  1. body
  2. { -moz-binding: url('plik.xml#fixx'); }

i gra gitara. ;)

Manipulacje na drzewie DOM

Po dołączeniu XBL-a możemy korzystać z pełnej palety funkcji JavaScript dostępnej z poziomu przeglądarki. Dla przykładu, dodajmy klasę klasa dla elementu o identyfikatorze ident:

  1. <bindings xmlns="http://www.mozilla.org/xbl" xmlns:html="http://www.w3.org/1999/xhtml">
  2.     <binding id="fixx">
  3.  
  4.         <implementation>
  5.             <constructor>
  6.                 //<![CDATA[
  7.                     document.getElementById('ident').setAttribute('class', 'klasa');
  8.                 //]]>
  9.             </constructor>
  10.         </implementation>
  11.     </binding>
  12. </bindings>

Jak zapewne zauważyliście, ścieżka podana w arkuszu CSS zgadza się atrybutem id przy <binding>. Działa to na tej samej zasadzie, jak kotwice w HTML-u, czyli można bez problemu umieścić kilka takich implementacji w jednym pliku (tworzymy po prostu kolejnych “sąsiadów” <binding>…</binding>). ;)

dedykowany CSS

Aż korci, aby wykorzystać tę metodę do dodania przeznaczonego specjalnie dla Firefoksa CSS-a. Wystarczy utworzyć nowy węzeł w drzewie DOM naszej strony:

  1. <bindings xmlns="http://www.mozilla.org/xbl" xmlns:html="http://www.w3.org/1999/xhtml">
  2.     <binding id="fixx">
  3.  
  4.         <implementation>
  5.             <constructor>
  6.                 //<![CDATA[
  7.                     var CSS = document.createElement('link');
  8.                     CSS.setAttribute('rel', 'stylesheet');
  9.                     CSS.setAttribute('type', 'text/css');
  10.                     CSS.setAttribute('href', 'fxFix.css');
  11.  
  12.                     document.getElementsByTagName('head')[0].appendChild(CSS);
  13.                 //]]>
  14.             </constructor>
  15.         </implementation>
  16.     </binding>
  17. </bindings>

Dlaczego osobny CSS? Wbrew pozorom, przyda się, i to nieraz. Choćby w celu wyeliminowania błędów generowanej zawartości przez CSS. Wystarczy podstawić własną ścieżkę.

epilog

Dzisiaj omówiłem przykład zastosowania XBL-i na własnych stronach, nie tylko przy XUL (interfejs renderowany przez Firefoksa). W najbliższych notkach omówię parę innych przykładów z życia wziętych, które pomogą albo i całkowicie zniwelują największe bolączki Firefoksa. Działanie XBL-i możecie podejrzeć na stronach ZamCampu.

A za niespełna tydzień - jak powstają notki na eRIZ’s weblog. ;)

Brak komentarzy

dopisz swój :: trackback :: RSS z komentarzami

Nie ma jeszcze żadnych komentarzy.

RSS z komentarzami :: trackback

Skomentuj

Możesz używać znaczników XHTML. Dozwolone są następujące tagi: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <code> <em> <i> <strike> <strong>

Wszystkie komentarze przechodzą przez moderację oraz filtry antyspamowe. Nie zostanie opublikowany komentarz, jeśli:

  • Jego treść obraża kogokolwiek.
  • W treści znajdują się wulgaryzmy i słownictwo ogólnie uznane za nieprzyzwoite.
  • Mam wątpliwości co do autora wpisu (Wszelkie anonimy są kasowane - niezależnie od zawartości - wpisz prawdziwy e-mail. Jeśli usunąłem, Twoim zdaniem, komentarz niesłusznie - daj znać). Zdarza się, iż sprawdzam kim jest komentujący.
  • Zawiera jakąkolwiek formę reklamy.

Szufladka