Comment se fait-il que certaines chaînes aléatoires produisent des couleurs lorsqu'elles sont entrées en tant que couleurs d'arrière-plan en HTML? Par exemple:
<body bgcolor="chucknorris"> test </body>
... produit un document avec un arrière-plan rouge sur tous les navigateurs et toutes les plateformes.
Fait intéressant, bien que chucknorri
produise également un arrière-plan rouge, chucknorr
génère un arrière-plan jaune.
Que se passe t-il ici?
C'est une retenue de l'époque de Netscape:
Les chiffres manquants sont traités comme 0 [...]. Un chiffre incorrect est simplement interprété comme 0. Par exemple, les valeurs # F0F0F0, F0F0F0, F0F0F, #FxFxFx et FxFxFx sont toutes identiques.
C'est tiré de l'article de blog n petit discours sur l'analyse de la couleur de Microsoft Internet Explorer qui le traite en détail, y compris les longueurs variables des valeurs de couleur, etc.
Si nous appliquons les règles à partir de la publication de blog, nous obtenons ce qui suit:
Remplacer tous les caractères hexadécimaux non valides par des 0
chucknorris becomes c00c0000000
Pavé au prochain nombre total de caractères divisibles par 3 (11 -> 12)
c00c 0000 0000
Divisé en trois groupes égaux, chaque composant représentant le composant de couleur correspondant à une couleur RVB:
RGB (c00c, 0000, 0000)
Tronquer chacun des arguments de la droite vers le bas à deux caractères
Ce qui donne le résultat suivant:
RGB (c0, 00, 00) = #C00000 or RGB(192, 0, 0)
Voici un exemple démontrant l'attribut bgcolor
en action pour produire cette nuance de couleurs "étonnante":
<table>
<tr>
<td bgcolor="chucknorris" cellpadding="8" width="100" align="center">chuck norris</td>
<td bgcolor="mrt" cellpadding="8" width="100" align="center" style="color:#ffffff">Mr T</td>
<td bgcolor="ninjaturtle" cellpadding="8" width="100" align="center" style="color:#ffffff">ninjaturtle</td>
</tr>
<tr>
<td bgcolor="sick" cellpadding="8" width="100" align="center">sick</td>
<td bgcolor="crap" cellpadding="8" width="100" align="center">crap</td>
<td bgcolor="grass" cellpadding="8" width="100" align="center">grass</td>
</tr>
</table>
Cela répond également à l'autre partie de la question. pourquoi bgcolor="chucknorr"
produit-il une couleur jaune? Eh bien, si nous appliquons les règles, la chaîne est la suivante:
c00c00000 => c00 c00 000 => c0 c0 00 [RGB(192, 192, 0)]
Ce qui donne une couleur or jaune clair. Comme la chaîne commence par 9 caractères, nous conservons le deuxième C cette fois-ci et finissons donc dans la valeur de couleur finale.
Je l’ai rencontré à l’origine lorsque quelqu'un a fait remarquer que vous pouviez faire color="crap"
et, eh bien, le résultat est brun.
Je suis désolé de ne pas être d’accord, mais selon les règles pour analyser une valeur de couleur héritée postée par @ Yuhong Bao , chucknorris
n’équivalent pas à #CC0000
, mais plutôt à #C00000
, une teinte de rouge très similaire mais légèrement différente. J'ai utilisé le Firefox ColorZilla add-on pour le vérifier.
Les règles stipulent:
chucknorris0
chuc knor ris0
ch kn ri
C0 00 00
J'ai pu utiliser ces règles pour interpréter correctement les chaînes suivantes:
LuckyCharms
Luck
LuckBeALady
LuckBeALadyTonight
GangnamStyle
UPDATE: Les répondants ayant déclaré que la couleur était #CC0000
ont depuis modifié leurs réponses pour inclure la correction.
La plupart des navigateurs ignorent simplement les valeurs non hexadécimales de votre chaîne de couleur, en remplaçant les chiffres non hexadécimaux par des zéros.
ChuCknorris
se traduit par c00c0000000
. À ce stade, le navigateur divisera la chaîne en trois sections égales, en indiquant rouge , vert et Valeurs bleues : c00c 0000 0000
. Les bits supplémentaires dans chaque section seront ignorés, ce qui donne le résultat final #c00000
qui est de couleur rougeâtre.
Notez que cela ne s'applique pas à l'analyse des couleurs CSS, qui est conforme à la norme CSS.
<p><font color='chucknorris'>Redish</font></p>
<p><font color='#c00000'>Same as above</font></p>
<p><span style="color: chucknorris">Black</span></p>
Le navigateur tente de convertir chucknorris
en code de couleur hexadécimal, car cette valeur n'est pas valide.
chucknorris
, tout sauf c
n'est pas une valeur hexadécimale valide.c00c00000000
.Cela semble être un problème principalement avec Internet Explorer et Opera (12), étant donné que Chrome (31) et Firefox (26) l'ignorent.
P.S. Les nombres entre parenthèses sont les versions de navigateur sur lesquels j'ai testé.
.
Sur une note plus légère
Chuck Norris n'est pas conforme aux normes Web. Les normes Web lui sont conformes. # BADA55
La raison en est que le navigateur peut ne pas comprendre et essayer de le traduire d'une manière ou d'une autre en ce qu'il peut comprendre et dans ce cas en une valeur hexadécimale! ...
chucknorris
commence par c
qui est un caractère reconnu en hexadécimal et convertit également tous les caractères non reconnus en 0
!
Ainsi, chucknorris
au format hexadécimal devient: c00c00000000
, tous les autres caractères deviennent 0
et c
restent à leur place ...
Maintenant, ils sont divisés par 3 pour RGB
(rouge, vert, bleu) ... R: c00c, G: 0000, B:0000
...
Mais nous savons que l'hexadécimal valide pour le RVB ne contient que 2 caractères, ce qui signifie R: c0, G: 00, B:00
Le résultat réel est donc:
bgcolor="#c00000";
J'ai également ajouté les étapes dans l'image comme référence rapide pour vous:
La spécification HTML de WHATWG a l'algorithme exact pour l'analyse d'une valeur de couleur héritée: https://html.spec.whatwg.org/multipage/infrastructure.html#rules-for-parsing-a-legacy-colour-value
Le code utilisé par Netscape Classic pour analyser les chaînes de couleur est open source: https://dxr.mozilla.org/classic/source/lib/layout/layimage.c#155
Par exemple, notez que chaque caractère est analysé comme un chiffre hexadécimal, puis décalé dans un entier 32 bits sans vérification du débordement . Seuls huit chiffres hexadécimaux entrent dans un entier de 32 bits, ce qui explique pourquoi seuls les 8 derniers caractères sont pris en compte. Après avoir analysé les chiffres hexadécimaux en nombres entiers de 32 bits, ils sont ensuite tronqués en nombres de 8 bits en les divisant par 16 jusqu'à ce qu'ils entrent en 8 bits, ce qui explique pourquoi les zéros en tête sont ignorés.
Mise à jour: ce code ne correspond pas exactement à ce qui est défini dans la spécification, mais la seule différence est qu'il existe quelques lignes de code. Je pense que ce sont ces lignes qui ont été ajoutées (dans Netscape 4):
if (bytes_per_val > 4)
{
bytes_per_val = 4;
}
Réponse:
c
est le seul caractère hexadécimal valide de chucknorris, la valeur devient: c00c00000000
(pour toutes les valeurs non valides).Red = c00c
, Green = 0000
, Blue = 0000
.c00000
qui est une couleur rouge brique.chucknorris commence par c , et le navigateur le lit sous forme de valeur hexadécimale .
Parce que A, B, C, D, E et F sont caractères en hexadécimal .
Le navigateur convertit chucknorris
en une valeur hexadécimale, C00C00000000
.
Ensuite, la valeur hexadécimale C00C00000000
est convertie au format RGB (divisé par 3):
C00C00000000
=>R:C00C, G:0000, B:0000
Le navigateur n'a besoin que de deux chiffres pour indiquer la couleur:
R:C00C, G:0000, B:0000
=>R:C0, G:00, B:00
=>C00000
Enfin, affichez bgcolor = C00000
dans le navigateur Web.
Voici un exemple pour le démontrer:
<table>
<tr>
<td bgcolor="chucknorris" cellpadding="10" width="150" align="center">chucknorris</td>
<td bgcolor="c00c00000000" cellpadding="10" width="150" align="center">c00c00000000</td>
<td bgcolor="c00000" cellpadding="10" width="150" align="center">c00000</td>
</tr>
</table>
Le règles pour l'analyse des couleurs sur les attributs hérités implique des étapes supplémentaires par rapport à celles mentionnées dans les réponses existantes. Le composant tronqué à la partie à 2 chiffres est décrit comme suit:
Quelques exemples:
oooFoooFoooF
000F 000F 000F <- replace, pad and chunk
0F 0F 0F <- leading zeros truncated
0F 0F 0F <- truncated to 2 characters from right
oooFooFFoFFF
000F 00FF 0FFF <- replace, pad and chunk
00F 0FF FFF <- leading zeros truncated
00 0F FF <- truncated to 2 characters from right
ABCooooooABCooooooABCoooooo
ABC000000 ABC000000 ABC000000 <- replace, pad and chunk
BC000000 BC000000 BC000000 <- truncated to 8 characters from left
BC BC BC <- truncated to 2 characters from right
AoCooooooAoCooooooAoCoooooo
A0C000000 A0C000000 A0C000000 <- replace, pad and chunk
0C000000 0C000000 0C000000 <- truncated to 8 characters from left
C000000 C000000 C000000 <- leading zeros truncated
C0 C0 C0 <- truncated to 2 characters from right
Vous trouverez ci-dessous une implémentation partielle de l'algorithme. Il ne gère pas les erreurs ou les cas où l'utilisateur entre une couleur valide.
function parseColor(input) {
// todo: return error if input is ""
input = input.trim();
// todo: return error if input is "transparent"
// todo: return corresponding #rrggbb if input is a named color
// todo: return #rrggbb if input matches #rgb
// todo: replace unicode code points greater than U+FFFF with 00
if (input.length > 128) {
input = input.slice(0, 128);
}
if (input.charAt(0) === "#") {
input = input.slice(1);
}
input = input.replace(/[^0-9A-Fa-f]/g, "0");
while (input.length === 0 || input.length % 3 > 0) {
input += "0";
}
var r = input.slice(0, input.length / 3);
var g = input.slice(input.length / 3, input.length * 2 / 3);
var b = input.slice(input.length * 2 / 3);
if (r.length > 8) {
r = r.slice(-8);
g = g.slice(-8);
b = b.slice(-8);
}
while (r.length > 2 && r.charAt(0) === "0" && g.charAt(0) === "0" && b.charAt(0) === "0") {
r = r.slice(1);
g = g.slice(1);
b = b.slice(1);
}
if (r.length > 2) {
r = r.slice(0, 2);
g = g.slice(0, 2);
b = b.slice(0, 2);
}
return "#" + r.padStart(2, "0") + g.padStart(2, "0") + b.padStart(2, "0");
}
$(function() {
$("#input").on("change", function() {
var input = $(this).val();
var color = parseColor(input);
var $cells = $("#result tbody td");
$cells.eq(0).attr("bgcolor", input);
$cells.eq(1).attr("bgcolor", color);
var color1 = $cells.eq(0).css("background-color");
var color2 = $cells.eq(1).css("background-color");
$cells.eq(2).empty().append("bgcolor: " + input, "<br>", "getComputedStyle: " + color1);
$cells.eq(3).empty().append("bgcolor: " + color, "<br>", "getComputedStyle: " + color2);
});
});
body { font: medium monospace; }
input { width: 20em; }
table { table-layout: fixed; width: 100%; }
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.12.4/jquery.min.js"></script>
<p><input id="input" placeholder="Enter color e.g. chucknorris"></p>
<table id="result">
<thead>
<tr>
<th>Left Color</th>
<th>Right Color</th>
</tr>
</thead>
<tbody>
<tr>
<td> </td>
<td> </td>
</tr>
<tr>
<td> </td>
<td> </td>
</tr>
</tbody>
</table>