Hopp til innholdet

cjohansen.no

17. mai-HTML

Hvor mange bytes trenger du for å lage et norskt flagg som kan vises i Firefox? Uten bilder trengte jeg 258. Velkommen til alternativ bruk av HTML/CSS-kunnskaper.

Hva snakker du om?

Via en kompis ble jeg tipset om den noe uvanlige 17. mai-konkurransen som ble arrangert på en IRC-kanal: Med færrest mulig bytes, implementer et norskt flagg i HTML/CSS/JavaScript som er minst 576 piksler bredt og som følger spesifikasjonene for det norske flagg på Wikipedia.

Vel, dette er for bra nerdemoro til at jeg kunne la være å prøve.

Løsningsplan

Dette var min første idé:

  1. Et element wrapper flagget og holder den røde bakgrunnen
  2. Et element har blå bakgrunn og hvit ramme for å dekke opp for den vertikale linja. Denne absoluttposisjoneres
  3. Et element har hvit bakgrunn for å dekke det hvite i den horisontale linja
  4. Et element inne i foregående har blå bakgrunn. Dette posisjoneres relativt for ikke å flytte seg, men fortsatt ligge over den vertikale streken

Hvilke elementer er hipp som happ, validering og semantikk er ikke et issue for denne oppgaven. Det er da naturlig å gå for elementene med kortest navn siden vi ønsker å få løsningen så kompakt som mulig.

Førsteutkastet blir dermed som følger:

<html>
  <head>
    <style>
      html, div {
        background: #fff;
        padding: 0.001em;
      }

      p, body {
        background: #002868;
        position: relative;
        min-height: 2em;
      }

      body {
        font-size: 2em;
        background: #ef2b2d;
        padding: 6em 0;
        width: 22em;
      }
    </style>
  </head>
  <body>
    <p style="position: absolute; top: -1em; left: 6em; border: 1em solid #fff; width: 2em; height: 16em;"></p>
    <div>
      <p></p>
    </div>
  </body>
</html>

Åpenbare forbedringer

Slutt-tagger

Ok, det funker, la oss komprimere. Det første vi gjør er selvsagt å fjerne alle slutt-tagger. Lukke elementer for Firefox ta seg av. Desverre må vi beholde slutten på style-elementet for å unngå at resten av siden leses som CSS.

div -> dt

div-elementet tar opp tre bokstaver. dt er et tilfeldig blokkelement som er en byte mindre. Vi bytter.

Kompakt CSS

Den siste regelen i en blokk med CSS trenger ikke semikolon etter seg. Bort med dem. Siste blokk i style-elementet trenger heller ikke avsluttende krøllparantes. Mange av mellomrommene er helt unødvendige.

Foreløpig resultat ser da ut som:

<html>
<style>
html,dt{
background:#fff;
padding:0.001em
}
p,body{
background:#002868;
position:relative;
min-height:2em
}
body{
font-size:2em;
background:#ef2b2d;
padding:6em 0;
width:22em
</style>
<body>
<p style="position:absolute;top:-1em;left:6em;border:1em solid #fff;width:2em;height:16em">
<dt>
<p>

Denne løsningen er allerede nede i 307 bytes. Ikke verst, men det er noe mer tyning å gjøre.

Mindre åpenbare tweaks

Så kommer de av triksene som går ut på å fjerne så mye som mulig og håpe at flagget fortsatt funker.

Implisitte elementer

Dagens festlige triks: HTML har en del implisitte elementer. Det vil si at dersom du ikke angir dem så finnes de i DOM alikevel, og kan behandles med både CSS og JavaScript. Heldigvis for oss er både html og body implisitte, så "out they go".

Fjerne </style>

Tidligere fikk vi ikke fjernet </style> fordi det gjør at resten av dokumentet leses som CSS. Vel, om vi flytter style-elementet nederst i fila er problemet løst, og vi kan fjerne sluttaggen.

Hakeparanteser

Ok, nå begynner det å bli skikkelig stygt. Det viser seg at den eneste høyrevendte hakeparantesen vi trenger er den som avslutter åpnetaggen <style>. De andre utgår.

Lange selectorer

Ok, vi har to lange selectorer. Den første kan forkortes til

*

, da denne velger alle elementer. Samtlige påfølgende elementer får uansett overskrevet verdiene, så om den treffer for mange elementer er ikke noe problem.

Fjerner vi nå all unødvendig white space ender vi opp med en skikkelig lang linje på 258 byte som representerer det norske flagg implementert med HTML og CSS (på helt gal måte):

<p style="position:absolute;top:-1em;left:6em;border:1em solid #fff;width:2em;height:16em"<dt<p<style>*{background:#fff;padding:0.001em}p,body{background:#002868;position:relative;min-height:2em}body{font-size:2em;background:#ef2b2d;padding:6em 0;width:22em

Andre løsninger

Jeg forsøkte en annen løsning også. Denne baserte seg på blå bakgrunn og fire røde bokser som floatet med margin mellom. Det ble flagg av det au, men jeg fikk den ikke forbi groteske 319 bytes.

Andre idéer jeg hadde var å lage en bitteliten superkomprimert gif, og inkludere den via img-tag med data-URL og en width til å skalere opp bildet. Mange av de innsendte løsningene var varianter av denne. Personlig syns jeg det var artigere å løse dette uten bruk av bilder.

Jeg vurderte også å prøve en tabell, men fikk ikke til noen god løsning med dette. Den innsendte løsningen som var minst bruke en tabell og kreativ bruk av clip i CSS og realiserte på 212 bytes.

Hva er det beste du klarer?

Muligens relatert

2006 - 2010 Christian Johansen Creative Commons Lisens