#1 Le 22/09/2008, à 17:28
- g_barthe
[Résolu] [Python] Encodage des caractère avec reportlab
Bonsoir,
Je créé un fichier pdf avec reportlab via mon application python. Le truc c'est que ça marche sous Ubuntu mais sous Xp il bloque sur les variables qui sont accentuées.
Alors je voulais savoir si l'un d'entre vous avait une idée. Il semble que cela soit lié à l'encodage mais la doc reportlab est tout en anglais et je comprend pas toutes les subtilités.
Il semblerait que l'encodage python du prog soit indépendant de la partie liée à reportlab.
# Ecriture du titre
my_canvas.setFillColor(colors.blue)
posX = 7*cm
posY = h-(2*cm)
titre = "FICHE MATERIEL DES POMPES"
my_canvas.drawString(posX, posY, titre)
my_canvas.setFillColor(colors.black)
# Définition du style d'écriture
font = "Helvetica"
font_size = 14
my_canvas.setFont(font, font_size)
# Ecriture du champs nom du projet
posX = 2*cm
posY = h-(4*cm)
affaire_projet = "Projet : " + affaire_projet
my_canvas.drawString(posX, posY, affaire_projet)
# Ecriture du champs réseau
posX = 2*cm
posY = h-(5*cm)
reseau = "Reseau : " + reseau
my_canvas.drawString(posX, posY, reseau)
# Dessin d'une ligne horizontale
posX = 2*cm
posY = h-(5.5*cm)
my_canvas.drawString(posX, posY, '________________________________________________________________')
# Ecriture du chapitre pompe
posX = 9*cm
posY = h-(6*cm)
pompe = "POMPE"
my_canvas.setFillColor(colors.orange)
my_canvas.drawString(posX, posY, pompe)
my_canvas.setFillColor(colors.black)
# Ecriture du type de pompe
posX = 2*cm
posY = h-(7*cm)
type_pompe = "Type de pompe : " + type_pompe
my_canvas.drawString(posX, posY, type_pompe)
# Ecriture de submersible
posX = 11*cm
posY = h-(7*cm)
submersible = "Submersible : " + submersible
my_canvas.drawString(posX, posY, submersible)
# Ecriture de rotor noye
posX = 2*cm
posY = h-(8*cm)
rotor_noye = "Rotor noye : " + rotor_noye
my_canvas.drawString(posX, posY, rotor_noye)
# Ecriture de multicellulaire
posX = 11*cm
posY = h-(8*cm)
multicellulaire = "Multicellulaire : " + multicellulaire
my_canvas.drawString(posX, posY, multicellulaire)
# Ecriture de rotor ventile
posX = 2*cm
posY = h-(9*cm)
rotor_ventile = "Rotor ventile : " + rotor_ventile
my_canvas.drawString(posX, posY, rotor_ventile)
# Ecriture de montage
posX = 11*cm
posY = h-(9*cm)
montage = "Montage : " + montage
my_canvas.drawString(posX, posY, montage)
# Ecriture de autoamorcante
posX = 2*cm
posY = h-(10*cm)
autoamorcante = "Auto-amorcante : " + autoamorcante
my_canvas.drawString(posX, posY, autoamorcante)
# Dessin d'une ligne horizontale
posX = 2*cm
posY = h-(10.5*cm)
my_canvas.drawString(posX, posY, '________________________________________________________________')
# Ecriture du caract_hydro
posX = 6.5*cm
posY = h-(11*cm)
caract_hydro = "CARACTERISTIQUES HYDRAULIQUES"
my_canvas.setFillColor(colors.orange)
my_canvas.drawString(posX, posY, caract_hydro)
my_canvas.setFillColor(colors.black)
# Ecriture de nature_fluide
posX = 2*cm
posY = h-(12*cm)
nature_fluide = "Nature du fluide : " + nature_fluide
my_canvas.drawString(posX, posY, nature_fluide)
# Ecriture de Ht mano nominale
posX = 11*cm
posY = h-(12*cm)
ht_mano_nominale = "Ht mano nominale : " + ht_mano_nominale + " mCE"
my_canvas.drawString(posX, posY, ht_mano_nominale)
# Ecriture de glycol
posX = 2*cm
posY = h-(13*cm)
glycol = "% glycol : " + glycol
my_canvas.drawString(posX, posY, glycol)
# Ecriture de Ht mano nominale
posX = 11*cm
posY = h-(13*cm)
ht_mano_fermees = "Ht mano a vannes fermees : " + ht_mano_fermees + " mCE"
my_canvas.drawString(posX, posY, ht_mano_fermees)
# Ecriture de temperature
posX = 2*cm
posY = h-(14*cm)
temperature = "Temperature : " + temperature + " C"
my_canvas.drawString(posX, posY, temperature)
# Ecriture de npsh_requis
posX = 11*cm
posY = h-(14*cm)
npsh_requis = "NPSH requis : " + npsh_requis + " mCE"
my_canvas.drawString(posX, posY, npsh_requis)
# Ecriture de debit_nominal
posX = 2*cm
posY = h-(15*cm)
debit_nominal = "Debit nominal : " + debit_nominal + " m3 / h"
my_canvas.drawString(posX, posY, debit_nominal)
# Ecriture de npsh_dispo
posX = 11*cm
posY = h-(15*cm)
npsh_dispo = "NPSH dispo : " + npsh_dispo + " mCE"
my_canvas.drawString(posX, posY, npsh_dispo)
# Ecriture de pression_max
posX = 2*cm
posY = h-(16*cm)
pression_max = "Pression max service : " + pression_max + " bars"
my_canvas.drawString(posX, posY, pression_max)
# Dessin d'une ligne horizontale
posX = 2*cm
posY = h-(16.5*cm)
my_canvas.drawString(posX, posY, '________________________________________________________________')
# Ecriture du chapitre caract_meca
posX = 6.5*cm
posY = h-(17*cm)
caract_meca = "CARACTERISTIQUES MECANIQUES"
my_canvas.setFillColor(colors.orange)
my_canvas.drawString(posX, posY, caract_meca)
my_canvas.setFillColor(colors.black)
# Ecriture de diametre_aspi
posX = 2*cm
posY = h-(18*cm)
diametre_aspi = "Diametre tube aspiration : " + diametre_aspi + " mm"
my_canvas.drawString(posX, posY, diametre_aspi)
# Ecriture du poids
posX = 11*cm
posY = h-(18*cm)
poids = "Poids total en marche : " + poids + " kg"
my_canvas.drawString(posX, posY, poids)
# Ecriture de diametre_refoulement
posX = 2*cm
posY = h-(19*cm)
diametre_refoulement = "Diametre tube refoulement : " + diametre_refoulement + " mm"
my_canvas.drawString(posX, posY, diametre_refoulement)
# Ecriture nature_materiaux
posX = 11*cm
posY = h-(19*cm)
nature_materiaux = "Nature des materiaux : " + nature_materiaux
my_canvas.drawString(posX, posY, nature_materiaux)
# Dessin d'une ligne horizontale
posX = 2*cm
posY = h-(19.5*cm)
my_canvas.drawString(posX, posY, '________________________________________________________________')
# Ecriture du chapitre caract_meca
posX = 6.5*cm
posY = h-(20*cm)
caract_meca = "CARACTERISTIQUES ELECTRIQUES"
my_canvas.setFillColor(colors.orange)
my_canvas.drawString(posX, posY, caract_meca)
my_canvas.setFillColor(colors.black)
# Ecriture de p_abs
posX = 2*cm
posY = h-(21*cm)
p_abs = "Puissance moteur abs. : " + p_abs + " W"
my_canvas.drawString(posX, posY, p_abs)
# Ecriture variateur
posX = 11*cm
posY = h-(21*cm)
variateur = "Variateur de vitesse : " + variateur
my_canvas.drawString(posX, posY, variateur)
# Ecriture de intensite
posX = 2*cm
posY = h-(22*cm)
intensite = "Intensite moteur abs. : " + intensite + " A"
my_canvas.drawString(posX, posY, intensite)
# Ecriture debit_mini
posX = 11*cm
posY = h-(22*cm)
debit_mini = "Debit mini necessaire : " + debit_mini + " m3 / h"
my_canvas.drawString(posX, posY, debit_mini)
# Ecriture de vitesse_rotation
posX = 2*cm
posY = h-(23*cm)
vitesse_rotation = "Vitesse rotation moteur : " + vitesse_rotation + " tr / s"
my_canvas.drawString(posX, posY, vitesse_rotation)
# Ecriture protection_ip
posX = 11*cm
posY = h-(23*cm)
protection_ip = "Degre de protection IP : " + protection_ip
my_canvas.drawString(posX, posY, protection_ip)
# Ecriture kit_hmt
posX = 2*cm
posY = h-(24*cm)
kit_hmt = "Kit HMT : " + kit_hmt
my_canvas.drawString(posX, posY, kit_hmt)
# Dessin d'une ligne horizontale
posX = 2*cm
posY = h-(24.5*cm)
my_canvas.drawString(posX, posY, '________________________________________________________________')
# Ecriture du chapitre observations
posX = 8*cm
posY = h-(25*cm)
chap_observations = "OBSERVATIONS"
my_canvas.setFillColor(colors.orange)
my_canvas.drawString(posX, posY, chap_observations)
my_canvas.setFillColor(colors.black)
# Ecriture observations
posX = 2*cm
posY = h-(26*cm)
my_canvas.drawString(posX, posY, observations)
# Ecriture de la version d'AstuGeClim en bas de page à gauche
astugeclim_version = 'AstuGeClim - ' + VERSION
posX = 2*cm
posY = h-(28.5*cm)
my_canvas.drawString(posX, posY, astugeclim_version)
# Affichage de la date du jour en bas de page à droite
date_du_jour = time.strftime('%d/%m/%y %H:%M',time.localtime())
posX = 16.5*cm
posY = h-(28.5*cm)
my_canvas.drawString(posX, posY, date_du_jour)
# Enregistrement du fichier pdf
my_canvas.save()
Merci à tous.
Edit : si je prend un exemple de chaine 'Dépression' en remplacant le é par \xe9 ca marche. Mais je n'arrive pas en faisant encode ma string à faire comprendre à reportlab les accents.
Dernière modification par g_barthe (Le 01/10/2008, à 19:55)
Mon forum perso sur le génie climatique http://le-genie-climatique.positifforum.com/
Le forum des travaux manuels : http://pausebroderie.fr/
Hors ligne
#2 Le 22/09/2008, à 21:59
- sebk
Re : [Résolu] [Python] Encodage des caractère avec reportlab
essai d'insérer la ligne suivante dans ton source :
# -*- coding: UTF-8 -*-
Iceberg Project : www.iceberg-linux.net
Hors ligne
#3 Le 23/09/2008, à 06:41
- g_barthe
Re : [Résolu] [Python] Encodage des caractère avec reportlab
elle y est déjà en tout début de script.
L'exemple que je vous ai mis et une petite partie.
Mais tout mon prog est bien en utf-8.
Mon forum perso sur le génie climatique http://le-genie-climatique.positifforum.com/
Le forum des travaux manuels : http://pausebroderie.fr/
Hors ligne
#4 Le 23/09/2008, à 17:41
- sebk
Re : [Résolu] [Python] Encodage des caractère avec reportlab
elle y est déjà en tout début de script.
L'exemple que je vous ai mis et une petite partie.
Mais tout mon prog est bien en utf-8.
J'ai vérifié au boulo dans nos sources on utilise l'encodage windows. essaye :
# -*- coding: iso-8859-15 -*-
ça devrait mieux aller
Iceberg Project : www.iceberg-linux.net
Hors ligne
#5 Le 23/09/2008, à 18:04
- g_barthe
Re : [Résolu] [Python] Encodage des caractère avec reportlab
Ca ne change rien.
Pour le moment j'ai contourné le pb en faisant :
nom_du_projet = unicode(nom_du_projet).encode('UTF-8')
Mais dans mon pdf ça me met des caractères à la con mais au moins le prog ne plante plus.
On dirait que c'est reportlab qui ne comprend pas l'encodage.
J'ai pourtant relu la doc mais c'est pas clair je trouve et je ne trouve pas d'exemple de prog fait avec reportlab qui gère cela.
A suivre si qqn à d'autre conseils.
Merci encore
Mon forum perso sur le génie climatique http://le-genie-climatique.positifforum.com/
Le forum des travaux manuels : http://pausebroderie.fr/
Hors ligne
#6 Le 23/09/2008, à 19:04
- aleph
Re : [Résolu] [Python] Encodage des caractère avec reportlab
> J'ai vérifié au boulo dans nos sources on utilise l'encodage windows. essaye :
# -*- coding: iso-8859-15 -*-
-----
Ce n'est pas le codage habituel utilisé sous Windows, mais c'est très intelligent.
#7 Le 23/09/2008, à 20:19
- g_barthe
Re : [Résolu] [Python] Encodage des caractère avec reportlab
Euh je dois le prendre comment ?
Mais l'encodage que l'on met en tout début de fichier est-il bien interprété par reportlab ?
Je suis également surpris que cela fonctionne sous Ubuntu et pas sous windows. Est-ce normal ?
Merci encore.
PS : aleph je sais que tes conseils sont d'habitudes très constructif c'est aussi pour cela que je pose la question des différences de fonctionnement selon l'OS
Dernière modification par g_barthe (Le 23/09/2008, à 20:21)
Mon forum perso sur le génie climatique http://le-genie-climatique.positifforum.com/
Le forum des travaux manuels : http://pausebroderie.fr/
Hors ligne
#8 Le 23/09/2008, à 23:18
- sebk
Re : [Résolu] [Python] Encodage des caractère avec reportlab
> J'ai vérifié au boulo dans nos sources on utilise l'encodage windows. essaye :
# -*- coding: iso-8859-15 -*------
Ce n'est pas le codage habituel utilisé sous Windows, mais c'est très intelligent.
sans vouloir pourir le post de g_barthe et dévier, c'est quoi qui est si intelligent ?
Pour revenir au sujet, quel outils de reportlab utilises tu ?
J'ai regardé les sources de pythonpoint et il n'utilise pas de commentaire d'encodage, ce qui veux dire que c'est le source qui fait le "import" qui détermine l'encodage à ma connaissance.
Iceberg Project : www.iceberg-linux.net
Hors ligne
#9 Le 25/09/2008, à 07:14
- aleph
Re : [Résolu] [Python] Encodage des caractère avec reportlab
> [...] c'est quoi qui est si intelligent ?
Dans le monde du "char - 8 bits", il n'y a que deux codages qui permettent d'écrire correctement en français, cp1252 et iso-8859-15. Si on ne veut pas le premier, le plus intelligent est de prendre le deuxième (peu répandu et rarement utilisé).
> [...] quel outils de reportlab utilises tu ?
Jamais utilisé.
> J'ai regardé les sources de pythonpoint et il n'utilise pas de commentaire d'encodage [...]
Si tu le dis. Ccomme la majorité des modules de Python core.
> [...] ce qui veux dire que c'est le source qui fait le "import" qui détermine l'encodage à ma connaissance.
Non.
#10 Le 25/09/2008, à 14:29
- bipede
Re : [Résolu] [Python] Encodage des caractère avec reportlab
reportlab n'accepte que deux types de chaines de caractères:
- les chaines unicode non encodées
- les chaines unicode encodées en utf-8
Pour travailler en cross-platform (Windows ou GNU/linux) avec python, la difficulté réside dans la gestion des divers encodages rencontrés.
La gestion des caractères sous Ubuntu se fait nativement en unicode utf-8. C'est ainsi que tous les affichages se font sous cette norme, aussi bien en fenêtre qu'en console, et que les fichiers texte sont également enregistrés par défaut dans ce format.
Sous Windows, c'est un peu plus compliqué. L'affichage général de l'interface graphique et l'enregistrement par défaut des fichiers sont encodés en table de caractères cp1252 (appelé aussi ANSI), alors que l'affichage en fenêtre DOS est encodé en table de caractères cp850. Cependant, Windows est parfaitement capable d'interpréter l'unicode.
Pour compliquer un peu le problème, pour pouvoir faire accepter à l'interpréteur python des caractères autres que ceux contenus dans la table ASCII (par exemple des caractères accentués), il est obligatoire de lui indiquer dans quelle table il doit chercher pour interpréter ces caractères. On le fait à la ligne 1 ou la ligne 2 du script de la façon suivante :
#-*- coding: cp1252 -*-
On pourrait mettre iso-8859-15 ou utf-8 à la place de cp1252 selon l'encodage qu'on veut utiliser.
Là où ça se corse, c'est à l'enregistrement du fichier. Car si on indique à python la table dont il doit se servir pour interpréter les caractères et qu'on enregistre le fichier du script dans un autre format (c'est tout à fait possible), dans le meilleur des cas les caractères seront mal affichés, et dans le pire des cas il y aura erreur à l'exécution, car les caractères ne sont en réalité pas encodés dans le format indiqués à python, mais dans celui de l'enregistrement du fichier.
Donc il est fortement recommandé que le format d'enregistrement du fichier soit le même que celui indiqué à python.
Maintenant, que se passe-t-il si on utilise de simples strings pour l'affichage ?
On écrit un script sous ubuntu chargé d'écrire une phrase en console :
#! /usr/bin/env python
#-*- coding: utf-8 -*-
phrase = "caractères accentués"
print phrase
Vous le rendez exécutable et vous le lancez...
La phrase s'affiche telle qu'on l'attendait.
Maintenant vous recopiez ce fichier sous Windows XP et vous le lancez... Catastrophe! les caractères accentués s'affichent bizarre...
Normal, car en fenêtre DOS, un string s'interprète en fonction de la table cp850 alors que la chaine est enregistrée en utf-8.
Essayez donc de modifier votre code comme suit:
#! /usr/bin/env python
#-*- coding: utf-8 -*-
phrase = "caractères accentués"
print phrase.decode("utf-8")
Prenez garde sous Windows d'enregistrer les modifications au format unicode utf-8, sinon le fichier sera réenregistré par défaut en ANSI, et ça ne marchera plus...
Lancez votre programme, et vous constatez que les caractères sont bien affichés. En fait, vous avez transformé votre chaine unicode utf-8 en chaine unicode non encodée, et laissé le soin à Windows de la réencoder en son format d'affichage préféré...
Il existe une façon beaucoup plus simple de procéder, en n'utilisant dans vos scripts que des chaines unicode non encodées. Le code se présentera alors comme suit:
#! /usr/bin/env python
#-*- coding: utf-8 -*-
phrase = u"caractères accentués"
print phrase
Pour récapituler, en tenant compte du fait que le dénominateur commun de toutes les plate-formes est l'unicode :
Règle n°1 : toujours indiquer l'encodage "UTF-8" au début du script
#! /usr/bin/env python
#-*- coding: utf-8 -*-
Règle n°2 : toujours enregistrer vos scripts au format utf-8
Règle n°3 : N'utilisez que des chaines unicodes non codées dans vos scripts (u"")
Règle n°4 : Si vous utilisez wxpython utilisez exclusivement la version unicode à l'exclusion de la version ANSI
Ainsi vous ne devriez jamais rencontrer de problèmes d'encodage...
Dernière modification par bipede (Le 25/09/2008, à 14:32)
Desktop: MSI - Intel® Core™ i5-3330 CPU @ 3.00GHz × 4 - RAM 8 go- Kubuntu 21.04 - Système sur SSD 64 Go - /home sur HDD 500 Go.
Laptop: DELL Inspiron-15 3567 - Intel® Core™ i5-7200 CPU @ 2.50GHz × 4 - RAM 8 go - HDD 1 To - Ubuntu 20.10 avec /home séparé.
Mon site: Les contributions du bipède
Hors ligne
#11 Le 25/09/2008, à 19:41
- bipede
Re : [Résolu] [Python] Encodage des caractère avec reportlab
Pour illustrer mon propos du post précédent, ci-dessous un petit script qui fonctionne aussi bien sous GNU/linux que sous Windows, pour peu qu'il soit sauvegardé en utf-8 :
#!/usr/bin/env python
#-*- coding: utf-8 -*-
import os.path
from reportlab.pdfgen import canvas
from reportlab.lib.pagesizes import A4
from reportlab.lib.units import cm
fichier = os.path.join(os.path.expanduser("~"), "test_reportlab.pdf")
c = canvas.Canvas(fichier, pagesize = A4)
w, h = A4
c.setFont("Helvetica-Bold", 14)
chaine = u"Chaine avec caractères accentués"
posX = (w - c.stringWidth(chaine, "Helvetica-Bold", 14))/2
posY = h-(2*cm)
c.drawString(posX, posY, chaine)
c.showPage()
c.save()
Desktop: MSI - Intel® Core™ i5-3330 CPU @ 3.00GHz × 4 - RAM 8 go- Kubuntu 21.04 - Système sur SSD 64 Go - /home sur HDD 500 Go.
Laptop: DELL Inspiron-15 3567 - Intel® Core™ i5-7200 CPU @ 2.50GHz × 4 - RAM 8 go - HDD 1 To - Ubuntu 20.10 avec /home séparé.
Mon site: Les contributions du bipède
Hors ligne
#12 Le 25/09/2008, à 19:45
- aleph
Re : [Résolu] [Python] Encodage des caractère avec reportlab
> Bipède
Ah la la, à mon humble avis, tu n'y es toujours pas ou ta compréhension n'est pas aboutie.
Un *string* (attention, j'utilise bien le mot string dans le sens "chaîne de caractères"),
unicode non encodé (utilisons ce mot), *ça n'existe pas*, ce n'est pas possible. Si l'on
ne connaissait pas son encodage originelle, il serait tout à fait impossible de le
transcoder...
Quelques informations abrégées qui complètent ou corrigent ce qui a été dit dans le message
précédent.
Il faut distinguer deux choses. L'encodage des scripts et l'encodage des strings dans
les scripts.
L'encodage des scripts (rapide).
Un script, fichier texte, a un encodage, peu importe lequel. Par défaut, Python assume
que le codage est en ascii. Si ton script a un autre encodage, parce que par commodité,
tu utilises des caratères non ascii, il faut en informer l'interpréteur avec une déclaration
d'encodage. En gros, c'est comme une page html (charset).
L'encodage des strings
Python 2.* connaît deux types de *string*, les <str> et les <unicode>. Indépedamment de
l'encodage du script, il est possible de définir n'importe quel *string* dans n'importe
quel encodage. Par contre, il est logiquement nécessaire pour définir ces *strings*
d'utiliser des caractères qui seront compris par l'interpréteur, c'est à dire conforme
à la déclaration de l'encodage du script.
Pour définir des *strings* de type <str>, tu tapes "blabla élève" dans ton script.
Celui-ci sera "encodé" en iso-8859-1 (en principe) sous Linux/Ubuntu et en cp1252 sous
Windows. A noter que le mot "encodé" est abusif car les tabelles de chars 8 bits
(iso-*** ou cp***) n'ont pas d'encodage, l'encodage *est* le code point.
Pour définir des *strings* de type <unicode>, deux méthodes sont possibles, la fonction
unicode() et la frappe u"bla bla élève". Je passe sur les détails et les inconvénients
de u"...". Quelques façons de créer un *string* de type unicode :
>>> u = unicode('élève', 'cp1252') #encodage d'entrée sur mon shell
>>> u = u'élève' #idem
>>> u = u'\xe9l\xe8ve'
>>> u = u'\u00e9l\u00e8ve'
>>> u
élève
Ce que tu ne sais pas ou ne comprends pas est que ce string unicode *est* encodé.
Autrement cela n'aurait aucun sens. Il est encodé en "unicode_internal" qui est
l'encodage natif des unicodes de Python. Ce nom vient du fais que selon le mode de
compilation de Python, le codage natif est UCS4 ou UCS2 avec des paires de
substitutions dans la plage d'adresse des "codes points" [...] pour les caractères
dont les "codes points" sont >FFFF. (Je ne sais plus de mémoire quels sont ces adresses).
C'est ce que l'on appelle en anglais les surrogates pairs.
Petit apparté.
utf-8 étant une catastrophe pour la manipulation, Python ne l'utilise pas,
comme d'ailleurs Microsoft dans ses API, Sun/Java et probablement bien d'autres.
Fin de l' apparté.
Pour voir la représentation interne en bytes d'un unicode
>>> s = u.encode('unicode_internal')
>>> len(s)
10
>>> type(s)
<type 'str'>
>>> repr(s)
'\xe9\x00l\x00\xe8\x00v\x00e\x00'
>>> # 10 bytes, c'est bien de l'UCS2
Le *string* s de type <str> contenant des bytes nuls, il est possible que Pun machin
ne le rende pas correctement.
A partir de là tout devient ou devrait devenir clair. Pous voir et utiliser ces
*unicodes* ou d'ailleurs ces *str*, il faut donc les transcoder en str ou en unicode,
c'est à dire en un encodage qui soit compatible avec le dispositif qui sert à les
manipuler par la suite. Cela peut être une base de données, une console d'affichage,
une interface graphique, une imprimante, bêtement un fichier texte ou que sais-je encore.
>>> u
élève
>>> u.encode('utf-8')
élève
>>> repr(u.encode('utf-8'))
'\xc3\xa9l\xc3\xa8ve'
>>> repr(u.encode('utf-16'))
'\xff\xfe\xe9\x00l\x00\xe8\x00v\x00e\x00'
>>> repr(u.encode('iso-8859-15'))
'\xe9l\xe8ve'
>>> repr(u.encode('iso-8859-1'))
'\xe9l\xe8ve'
>>> u.encode('iso-8859-1')
élève
Bref, on peut, puisque Python gère nativement les encodages, travailler en Python
avec des *scripts* dans n'importe quel encodage qui manipule des *strings* dans
n'importe quel encodage. Et, ***heureusement***, en gras, corps 50, rouge, souligné,
La gestion native des encodages en Python est une des très grande qualité de Python,
seulement ....
-----
> Règle n°1 : toujours indiquer l'encodage "UTF-8" au début du script
Toujours indiquer l'encodage, peu importe avec lequel on travaille.
> Règle n°2 : toujours enregistrer vos scripts au format utf-8
Cf remarque précédente. L'important étant, logiquement, que la déclaration
d'encodage soit conforme à l'encodage réel du fichier/script.
> Règle n°3 : N'utilisez que des chaines unicodes non codées dans vos scripts (u"")
Aucun sens. Voir explications précédentes.
> Règle n°4 : Si vous utilisez wxpython utilisez exclusivement la version unicode
à l'exclusion de la version ANSI
Non, parole de contributeur à wxPython, je passe sur le pourquoi et le comment.
A noter que wxPython est un bon exemple de ce que j'ai décrit plus précédamment.
Quelle que soit la version ansi ou unicode, elle est utilisable avec des scripts
dans n'importe quel encodage.
----
T'as capté ? Comme disent les jeunes.
#13 Le 25/09/2008, à 19:47
- g_barthe
Re : [Résolu] [Python] Encodage des caractère avec reportlab
merci à toi bipède.
Je regarde ça demain ou ce we si j'ai le tps la c la course.
Il me semble pourtant avoir déjà fait ça.
Mais le pb vient peut être du format d'enregistrement du fichier.
PS : j'analyse de temps en temps ton code de paprass pour certains trucs un exemple fonctionnel d'un prog permet de se sortir de certaines situations. Merci à toi.
Mon forum perso sur le génie climatique http://le-genie-climatique.positifforum.com/
Le forum des travaux manuels : http://pausebroderie.fr/
Hors ligne
#14 Le 26/09/2008, à 07:19
- aleph
Re : [Résolu] [Python] Encodage des caractère avec reportlab
> bipède
Addendum
Un petit oubli. Pour définir un *string* unicode, on peut aussi le construire en utilisant
les noms unicode des caractères unicode. Exemple :
>>> #unicode 'abc'
>>> u = u'\N{LATIN SMALL LETTER A}\N{LATIN SMALL LETTER B}\N{LATIN SMALL LETTER C}'
>>> u
u'abc'
>>>
Un unicode sera si nécessaire encodé pour qu'il soit conforme à l'encodage du dispositif de
sortie, ici IDLE en cp1252. Exemple :
>>> sys.stdout.encoding
'cp1252'
>>> u'a\ufbf9b'
u'a\ufbf9b'
>>> u = u'a\ufbf9b'
>>> u.encode('cp1252', 'replace')
'a?b'
>>>
Pourquoi, encoder de foutu *string* unicode avec des caractères de remplacement ?
Parce ce qu'il fort probable que le caractère unicode dont le code point est fbf9,
ne soit pas représentable (affichable) sur bien des plateformes.
Nom de ce caractère ?
'ARABIC LIGATURE UIGHUR KIRGHIZ YEH WITH HAMZA ABOVE WITH ALEF MAKSURA ISOLATED FORM'
A noter que les noms des caractères (code point) est composé de caractères ascii, ce qui
permet bien de définir n'importe quel *string* indépendamment de l'encodage du script
source.
#15 Le 26/09/2008, à 07:52
- g_barthe
Re : [Résolu] [Python] Encodage des caractère avec reportlab
Bonjour tout le monde,
Wouahouh, ca commence à devenir vachement technique cette histoire d'encodage.
Va falloir reprendre ça à tête reposée pck ca commence à fumer sous le scalp.
Merci aleph j'espère qd même tout comprendre.
Mon forum perso sur le génie climatique http://le-genie-climatique.positifforum.com/
Le forum des travaux manuels : http://pausebroderie.fr/
Hors ligne
#16 Le 26/09/2008, à 09:53
- bipede
Re : [Résolu] [Python] Encodage des caractère avec reportlab
@ aleph
Je me doutais bien que les conseils que j'ai donnés à g_barthe pour résoudre son problème d'accentués dans un PDF construit avec reportlab allaient très vite entrainer une réaction de ta part
J'ai volontairement parlé d'unicode non encodé (je sais bien que c'est une hérésie) en opposition à l'utf-8 pour souligner la différence entre la table unicode de référencement des caractères, et leur représentation binaire par l'utf-8.
C'est vrai aussi que j'aurais du utiliser <str> en opposition à <unicode>, ce qui aurait été plus clair.
Mais même si à ton sens je ne capte pas tout, il n'en reste pas moins que quand on développe sous ubuntu, comme le fait g_barthe, on travaille par défaut en utf-8 (que je considère en passant, comme étant beaucoup plus cohérent et portable que l'ANSI). Par ailleurs, j'ai également souligné le fait que reportlab acceptait aussi bien l'unicode natif python que le str codé utf-8.
Ainsi, pour ne pas avoir le moindre problème de portabilité je lui ai naturellement conseillé d'indiquer qu'il utilisait l'utf-8, de sauvegarder ses scripts en utf-8, et d'utiliser de l'unicode natif dans ses scripts plutôt que des str. (au passage, je ne vois pas ce que tu reproches à la syntaxe u' ').
Il peut tester, ça marche à tous les coups...
Bien sûr, si on doit transmettre, la chaine à un dispositif qui a besoin d'un encodage particulier et ne supporte pas l'unicode natif, il suffit alors de la transcoder dans le format attendu à l'aide de la fonction encode(codec, option), mais à la dernière minute, après avoir réalisé toutes les manipulations voulues sur de l'unicode.
Quant à wxpython ANSI je ne conteste pas qu'il peut travailler avec tous les encodages, mais il me semble qu'on ne peut lui passer que des str.
En tout cas, merci à toi d'avoir cherché à m'éclairer...
Dernière modification par bipede (Le 26/09/2008, à 09:54)
Desktop: MSI - Intel® Core™ i5-3330 CPU @ 3.00GHz × 4 - RAM 8 go- Kubuntu 21.04 - Système sur SSD 64 Go - /home sur HDD 500 Go.
Laptop: DELL Inspiron-15 3567 - Intel® Core™ i5-7200 CPU @ 2.50GHz × 4 - RAM 8 go - HDD 1 To - Ubuntu 20.10 avec /home séparé.
Mon site: Les contributions du bipède
Hors ligne
#17 Le 26/09/2008, à 12:01
- aleph
Re : [Résolu] [Python] Encodage des caractère avec reportlab
> bipède
> En tout cas, merci à toi d'avoir cherché à m'éclairer...
Vraiment aucun reproche de ma part. Juste une impression, un feeling que tu t'embrouilles un peu et/ou que tu ne formules pas les choses correctement. Ce qui prête, je le pense, confusion au lecteur.
> Quant à wxpython ANSI je ne conteste pas qu'il peut travailler avec tous les encodages, mais il me semble qu'on ne peut lui passer que des str.
wxPython ANSI ne peut pas travailler avec tous les encodages et effectivement on utilise des <str> pour les entrées/sorties de l'interface graphique. On peut l'utiliser avec des scripts Python dans n'importe quel encodage, tout l'art étant de décoder ou d'encoder judicieusement les *strings* Python. Solution utilisée par bien des utilisateurs, car certains widgets ne gèrent pas ou mal l' unicode et rendent l'utilisation de la version unicode problématique.
Pour le u'...', passons. De façon amusante, il y a dans Python 3.0 symétriquement les mêmes inconvénients avec le b'...'.
---
Quant à moi, c'est l'orthographe de mes messages qui est une vraie catastrophe. Ce n'est pas mes compétences dans ce domaine qui manquent, mais j'ai toujours une peine folle à taper du texte correctement quand je n'utilise pas du style machine à écrire. Les copier-coller jouant aussi de vilains tours.
#18 Le 26/09/2008, à 12:11
- bipede
Re : [Résolu] [Python] Encodage des caractère avec reportlab
> bipède
> En tout cas, merci à toi d'avoir cherché à m'éclairer...
Vraiment aucun reproche de ma part. Juste une impression, un feeling que tu t'embrouilles un peu et/ou que tu ne formules pas les choses correctement. Ce qui prête, je le pense, confusion au lecteur.
Il n'y avait aucune ironie de ma part dans ce propos.
Je te remercie sincèrement de tes contributions à la connaissance de python.
Desktop: MSI - Intel® Core™ i5-3330 CPU @ 3.00GHz × 4 - RAM 8 go- Kubuntu 21.04 - Système sur SSD 64 Go - /home sur HDD 500 Go.
Laptop: DELL Inspiron-15 3567 - Intel® Core™ i5-7200 CPU @ 2.50GHz × 4 - RAM 8 go - HDD 1 To - Ubuntu 20.10 avec /home séparé.
Mon site: Les contributions du bipède
Hors ligne
#19 Le 26/09/2008, à 12:58
- aleph
Re : [Résolu] [Python] Encodage des caractère avec reportlab
L'important est que g_barthe s'en sorte et si nos conversations peuvent être utiles à d'autres, tant mieux.
#20 Le 26/09/2008, à 13:09
- g_barthe
Re : [Résolu] [Python] Encodage des caractère avec reportlab
je vous dis ca dès que je peux
Merci à tous
Mon forum perso sur le génie climatique http://le-genie-climatique.positifforum.com/
Le forum des travaux manuels : http://pausebroderie.fr/
Hors ligne
#21 Le 01/10/2008, à 19:55
- g_barthe
Re : [Résolu] [Python] Encodage des caractère avec reportlab
Bonsoir à tous,
En fait j'ai pris l'exemple de bipede qui m'a dit fonctionner sous windows et linux et là moi forcément avec ma poisse j'ai eu un pb.
Alors j'ai creuser à la façon d'une taupe lampe frontale, pioche et tout...
Et devinez quoi !!!
J'ai trouvé que j'avais une version de reportlab de 2004 les boules.
Et là comme par hasard en passant en version 2.2 de 2008 c'est vachement très beaucoup mieux.
Donc je crois que mon pb est résolu vu que tout fonctionne impec.
J'ai pas tout tout pigé mais le temps me permettra d'apréhender les choses.
Vaste sujet que l'encodage des caractères. Ca parait pas pourtant.
Merci beaucoup à tous.
Mon forum perso sur le génie climatique http://le-genie-climatique.positifforum.com/
Le forum des travaux manuels : http://pausebroderie.fr/
Hors ligne