Pourquoi de grandes quantités de nombres magiques sont-elles acceptables dans les CSS et les SVG?

63

Souvent , je vois des questions sur la liste des questions Réseau Hot comme ce qui demande essentiellement « comment puis-je dessine cette forme arbitraire en CSS ». Invariablement, la réponse consiste en quelques blocs de données CSS ou SVG avec un ensemble de valeurs apparemment aléatoires codées en dur qui forment la forme demandée.

Quand je regarde ça, je me dis 'Beurk! Quel bloc de code moche. J'espère ne jamais voir ce genre de choses dans mon projet '. Cependant, je vois ces types de questions-réponses assez fréquemment et avec un grand nombre de votes positifs, de sorte que la communauté ne pense clairement pas qu'ils sont mauvais.

Mais pourquoi est-ce acceptable? Venant de mon expérience en arrière-plan, cela n’a aucun sens pour moi. Alors pourquoi est-ce OK pour CSS / SVG?

Rétablir Monica
la source
38
Qu'est-ce qu'un dessin, si ce n'est un tas de nombres magiques aléatoires (imaginez des traits compris entre 2 (x, y) points, ou des tableaux de pixels, etc.) qui ont l'air sympa?
68
Est-ce que CSS a des variables? Est-ce que SVG?
Oded
36
C'est pourquoi de nombreux projets plus importants ont un pré-processeur CSS comme SASS ou LESS qui prend en charge les variables.
Ixrec
2
@Oded Pour CSS, il existe environ 40% de prise en charge globale des variables (donc non recommandé sauf si vous souhaitez dire à tous vos visiteurs Microsoft qu'ils ne sont pas les bienvenus). Microsoft suivra probablement la tendance dans Edge et les appareils mobiles finiront par rattraper son retard. SVG, d’autre part, a le concept de variables dans certains brouillons de statut, mais ils ne seront probablement jamais mis en œuvre.
phyrfox
12
Pourquoi? Parce que ce ne sont pas des nombres magiques. CSS contient des données, contrairement à un programme contenant des instructions. Bien que le CSS soit sans doute complet, ce n’est pas un langage de programmation.
Derek 朕 會 功夫

Réponses:

117

Tout d'abord, les valeurs magiques sont évitées dans la programmation en utilisant des variables ou des constantes. CSS ne supporte pas les variables, donc même si les valeurs magiques étaient mal vues, vous n'avez pas beaucoup de choix (sauf d'utiliser un pré-processeur comme SASS, mais vous ne le feriez pas pour un seul extrait de code).

Deuxièmement, les valeurs pourraient ne pas être aussi magiques dans un langage spécifique à un domaine tel que CSS. En programmation, un nombre magique est un nombre dont le sens ou l'intention n'est pas évident. Si une ligne dit:

x += 23;

Vous allez demander "pourquoi 23"? Quel est le raisonnement? Une variable pourrait clarifier l'intention:

x += defaultHttpTimeoutSeconds;

Cela est dû au fait qu'un nombre unique pourrait signifier absolument n'importe quoi dans un code d'usage général. Mais considérons CSS:

background-color: #ffffff;
font-size: 16px;

La hauteur et la couleur ne sont pas magiques, car la signification est parfaitement claire du contexte. Et la raison du choix de la valeur spécifique est simple car les concepteurs ont pensé que cela aurait l'air bien. Introduire une variable n’aiderait à rien, puisque vous l’appelleriez simplement comme " defaultBackgroundColor" et " defaultFontSize" de toute façon.

JacquesB
la source
16
Certaines valeurs ne sont en effet choisies que "parce qu'elles ont bonne apparence". Mais l'exemple que l'OP lié contient plusieurs fois la même valeur, mais il n'est pas clair s'ils représentent la même chose ou s'ils ont la même valeur par hasard. En outre, il utilise une valeur 198pxdont la différence entre la taille de quelque chose d'autre ( 200px) et une 2pxbordure.
CodesInChaos
1
@CodesInChaos: Oui, il y a des cas où des variables ou des expressions de dépendance seraient cool.
JacquesB
21
Notez que CSS fait des variables de soutien
phihag
28
@phihag Dans les spécifications, oui, mais dans la nature , non pas tant (je ne considère pas 40% un soutien global au moment de ce commentaire comme « largement pris en charge ». Toutefois, vous avez raison de dire que, dans le Nous aurons des variables CSS à l' avenir . Et j'ai appris quelque chose de nouveau aujourd'hui, alors merci pour cela.
phyrfox
2
@ JaredSmith C'est bien pour une application web à une échelle relativement grande, mais pour des pages communes (peut-être statiques) comprenant un polyfill énorme, il y a trop de travail.
Derek 會 功夫
80

C'est acceptable car ces formats ne sont pas du code , mais des données . Si vous supprimiez tous les "nombres magiques", vous dupliqueriez essentiellement chaque étiquette et aboutiriez à des fichiers ridicules comme:

mainkite_width = 200px
...
.mainkite {
  width: mainkite_width;
  ...

Chaque fois que vous avez besoin de modifier certaines données, vous devez rechercher à deux endroits. Certes, il est bon d’éviter les doublons dans certaines situations, par exemple si une couleur est répétée fréquemment et que vous souhaitez peut-être changer afin de changer de thème. Il existe des pré-processeurs et des extensions proposées pour remédier à ces situations, mais en général, il est souhaitable que les nombres soient associés à la structure dans un format de données.

Karl Bielefeldt
la source
22
+1 parce que: "C'est acceptable parce que ces formats ne sont pas du code, mais des données."
Pieter B
1
"Certes, dans certaines situations, il est bon d'éviter les doublons, par exemple si une couleur est répétée fréquemment et que vous souhaitez peut-être changer afin de changer de thème." - Probablement mieux faire avec les classes quand même .main_color { color: .. }
:,
1
Le code qui détermine l'apparence d'une application est toujours du code et non des données.
ESR
25

L'interdiction des nombres magiques est la version primordiale de ce principe de conception:

Prendre des décisions en un seul endroit .

Mais ce ne sont pas des nombres magiques . Du moins, pas en ce qui concerne les guides de style de codage que je connaisse.

largeur: 200px;
hauteur: 200px;

Ils sont clairement étiquetés. Bien sûr, les chiffres sont les mêmes. Mais la largeur est la largeur et la hauteur est la hauteur. Ils sont conçus pour varier indépendamment.

Maintenant , si vous avez 5 objets que tous avaient d'avoir la même largeur et chaque indépendamment de leur largeur codées en dur je vous battre avec le indirection bâton.

Je ne les appellerais pas des nombres magiques s'ils sont étiquetés, mais je vous battrais quand même avec le bâton d' indirection .

confits_orange
la source
4
Si vous avez assez d'objets pour avoir besoin d'une variable, vous en avez assez pour créer une nouvelle classe.
Jaketr00
1
C'est la meilleure réponse, car cela montre bien le point: ce ne sont pas des nombres magiques.
TheBlastOne
2
"5 objets qui devaient tous avoir la même largeur et chacun indépendamment codé en dur, je vous battrais avec un bâton." Bienvenue dans le monde amusant de la conception Web.
Whatsisname
2
Les nombres magiques sont non seulement problématiques à cause de "Prendre des décisions en un seul endroit" (aka DRY), mais aussi parce qu'ils sont difficiles à comprendre.
Sleske
Existe-t-il une alternative à battre avec un bâton?
Djechlin
10

Comme CSS n’est pas un langage de programmation, c’est le fichier de configuration qui contient les données variables de votre programme.

Actuellement, le CSS est si puissant que vous pouvez réellement le programmer, mais c’est d’autre chose. En substance, c'est toujours un langage de feuille de style .

Faisons un pas en arrière. Imaginez que nous ayons un langage de programmation capable de dessiner sur un écran. Imaginons que nous voulions le programmer pour peindre une page Web.

Au début, nous entrions des tonnes de nombres magiques dans notre code. La largeur de la marge, la hauteur du texte, les indentations, etc., etc.

jump(100) // The margin
drawTable(500, 500)
writeText("Hello World", 12)

Nous extrayons donc les nombres magiques et les plaçons au-dessus de notre fichier.

int margin = 100
int table = 500
int text_size = 12
jump(margin) // The margin
drawTable(table, table)
writeText("Hello World", text_size)

Maintenant c'est un peu moche. Nous lisons plutôt nos nombres variables dans un fichier de configuration.

margin 100
table 500
text size 12

Mm, c'est un peu flou ... Que signifient ces chiffres? Que signifient ces noms? Formalisons cela un peu.

margin_left 10em
table_width 500px
table_height 500px
font_size 12px

Mais vous savez, nous voulons élargir un peu notre programme. Nous voulons également qu’il dessine des pages avec plusieurs tableaux, des pages sans tableaux, des pages avec des paragraphes ou des boutons, entre autres choses. Ajoutons des sélecteurs à notre fichier de configuration afin de pouvoir spécifier le paragraphe qui doit avoir une police plus grande ou une couleur de texte différente, peut-être que nous pouvons prendre en charge des éléments imbriqués, peut-être que nous pouvons utiliser une propriété générale dans notre fichier de configuration, puis la remplacer par un paramètre spécifique. un dans quelques éléments imbriqués.


Vous sentez où cela se passe, vous finissez par arriver en CSS. (Et un navigateur pour le rendre.)

Devrions-nous alors ajouter des fonctionnalités à notre fichier de configuration afin d’éviter à nouveau les nombres magiques? Ajouter des variables? Ajouter un fichier de configuration pour notre fichier CSS? Cela semble un peu inutile si vous vous souvenez que notre fichier CSS est déjà le même fichier de configuration.

Mais ce n'est pas vrai bien sûr; votre fichier CSS grossit de plus en plus, et vous rencontrez finalement les mêmes problèmes que pour les nombres magiques d'origine, le même nombre répété partout, parfois avec de petites transformations, etc.

Le CSS moderne permet cependant plusieurs façons d’éviter cette répétition. Vous pouvez utiliser des classes qui s'appliquent à de nombreux éléments, vous pouvez définir un style pour tous les divobjets, mais en substituer un en particulier, et CSS 3 autorise même un type d'utilisation variable.

Cela ne signifie pas que vous devez commencer à utiliser des variables CSS dans tous les emplacements possibles. Utilisez-le là où cela vous semble utile et évitez la duplication ou d'autres techniques également disponibles.

En fin de compte, vous ne voulez pas trop de nombres magiques dans votre fichier de configuration :-)

Dorus
la source
Pourquoi est-il important que la redondance soit? La maintenance ne sera-t-elle pas un problème, peu importe où il se trouve?
Peter Mortensen
@PeterMortensen C'est toujours un facteur à prendre en compte entre temps de développement faible ou maintenabilité élevée. Il est facile de développer une redondance élevée car vous pouvez changer rapidement les choses ici et là. Une maintenance réduite est facile à entretenir car vous pouvez rapidement changer de style global. En pratique, vous voulez vous situer quelque part entre les deux, car il est évident qu'il est beaucoup plus facile d'ajouter un style global, même si vous ajoutez de nouvelles pages, mais que la moindre des dernières fonctionnalités obscures adhère à tout changement de style global possible qui prend une éternité.
Dorus
C'est bon CSS a des fonctionnalités dans les deux sens. Et il appartient au développeur Web de décider combien de temps il faut consacrer à la réduction de la redondance et à l’augmentation de la facilité de maintenance, ou à la création de nouvelles pages / fonctionnalités. Il est intéressant de noter qu'il en va de même pour tout autre langage de programmation dans lequel vous pouvez passer des mois à présenter le design parfait, des jours à traiter votre programme et des mois à rechercher des bogues impossibles.
Dorus
Assez intéressant, je viens de tomber sur cette question qui parle de pousser trop loin l'abstraction et de perdre du temps de maintenance et de développement.
Dorus
5

Pourquoi est-il [un tas de valeurs apparemment aléatoires codées en dur] OK pour CSS / SVG?

Ce n'est pas OK Il est possible d'écrire et de gérer des fichiers ".css" simples, mais des valeurs aléatoires codées de manière définitive deviendront un fardeau dominant.

Pour toute autre chose que des pages Web extrêmement simples, vous devrez soit développer une stratégie disciplinée de "recherche et remplacement", soit utiliser un pré-processeur CSS avec des variables, ou définir des styles via JavaScript.

Jackson
la source