US An english version of this website is available, would you like to check it out ?

YES | NO, stay on the french website


FR Une version anglophone du site est disponible, souhaitez-vous la consulter ?

OUI | NON, rester sur le site français

Close / Fermer

Expression reguliere pour corriger la=?windows-1252?Q?_typographie_d'un_texte?

26/03/2006 11:54 par Sebastien | Signaler un contenu abusif
Bonjour à tous,

Je cherche à corriger automatiquement la typographie d'un texte, saisi
par l'utilisateur dans un textarea HTML.
Cette correction est facultative, une case à cocher permet de l'activer
ou non et de plus il y a une prévisualisation avant soumission
définitive. Voici pour le décor.

-> essais de regexp en fin de post.

Objectifs :

Il s'agit de corrections pour les erreurs les plus fréquentes, comme
l'oubli de l'espace (insécable) avant les ponctuations doubles : ; ! ?
et à l'intérieur des guillemets français « et ».

Si l'espace est absent on ajoute un espace insécable, si un espace
normal est présent on le transforme en espace insécable.

Raffinement ultime (et complications à l'horizon), auquel je tiens
beaucoup, l'apostrophe droite est transformée en apostrophe «
typographiquement correcte » (').

Complication supplémentaire (voir point précédent), le texte peut
contenir du pseudo-code Wiki, avec en particulier '' (deux apostrophes
droites) entourant du texte devant être rendu en italique.

Pour finir, le tout est à destination d'une base de données MySQL, mais
cela n'a aucune incidence (si je ne m'abuse) car la chaîne sera insérée
avec mysql_real_escape_string(). On considère que la chaîne (reçue en
POST) est passée par stripslashes() si nécessaire avant tout traitement.


Les expressions :

<?php
function cleanup_typo($str)
{
$patterns[0] = '/([^\'].)\'([^\'].|0)/'; // Apostrophe droite non
précédée d'une autre apostrophe
$patterns[1] = '/([^ ]):/'; // Deux-points non précédé d'un espace
$patterns[2] = '/([^ ]);/'; // Point-virgule non précédé d'un espace
$patterns[3] = '/«([^ ])/'; // Guillemet ouvrant non suivi d'un espace
$patterns[4] = '/([^ ])»/'; // Guillemet fermant non précédé d'un espace
$patterns[5] = '/([^ ])!/'; // Point d'exclamation non précédé d'un espace
$patterns[6] = '/([^ ])\?/'; // Point d'interrogation non précédé d'un
espace
$patterns[7] = '/\.{3}/'; // Trois-points

$replacements[0] = '$1'$2';
$replacements[1] = '$1 :';
$replacements[2] = '$1 ;';
$replacements[3] = '« $1';
$replacements[4] = '$1 »';
$replacements[5] = '$1 !';
$replacements[6] = '$1 ?';
$replacements[7] = '--';

$str = preg_replace($patterns, $replacements, $str);

/* Ces 2 lignes sont issues de wiki2html : conversion en espaces
insécable des espaces existants */
$str = preg_replace('/[ ]+([:?!;»])/',' $1',$str);
$str = preg_replace('/(«)[ ]+/','$1 ',$str);

return $str;
}
?>

Si vous avez lu jusqu'ici sans tricher, bravo et merci.

Je suis intéressé par vos observations à tous les niveaux :
- problèmes liés aux risques de remplacer du texte qui ne devrait pas l'être
- erreurs dans les regexp (pourtant testée, mais peut-être pas sur tous
les cas)
- Possibilités d'optimisation
- Mauvaise interprêtation des règles de typographie française
-

Ceci n'est qu'un premier jet, je ne suis toujours pas un expert en
expressions régulières. Je n'ai fait que quelques tests e tje sens que
mes expressions sont pleines de trous


Sébastien
email Suivre cette discussionRéponses Lire les 10 réponsesReplies Répondre

Lire les réponses

#1 Sebastien
27/03/2006 20h47 | Contenu abusif
Bonjour à tous,

Je ne sais pas si mon idée vous paraît trop farfelue ou quoi, laissez
quand même vos impressions.

Quelques modifications :

Pour ne pas transformer "http:" en "http :"
j'ai ajouté ces lignes en fin de fonction :

<?php
$str = preg_replace('/(http|https|ftp|news|mailto) :/','$1:',$str);
$str = preg_replace('/(http|https|ftp|news|mailto) :/','$1:',$str);
?>

De plus j'ai oublié de préciser que dans les remplacements les espaces
insérés ou remplacés sont des espaces insécables directement saisis sous
forme de caractère, pour éviter que les esperluettes des appels &#160;,
&#xa0; ou &nbsp; ne soient à leur tour convertis en &amp; (donnant
respectivement &amp;#160;, &amp;#xa0; et &amp;nbsp;) par
htmlspecialchars() ou htmlentities().

Sébastien
 

Questions similaires