Question de conversion en UTF-8 pour une VBA qui enregistre un txt

stephsteph

XLDnaute Occasionnel
Bonjour le forum,


J’ai une macro VBA qui marche bien qui après plusieurs opérations sur un fichier xlsm, enregistre le résultat dans un fichier txt avec le code :

Set fs = CreateObject("Scripting.FileSystemObject")

Set a = fs.CreateTextFile(ThisWorkbook.Path & "\" & Liste(i - 1) & ".txt", True)

Le résultat délivré est, après ouverture de Notepad++, en caractères ANSI.

Je dois passer maintenant en UTF-8 et j’ai cherché sur le Net comment modifier le codage pour cela, je n’ai trouvé qu’une seule référence en Anglais qui indique qu’il faut ajouter un autre true comme :

Set a = fs.CreateTextFile(ThisWorkbook.Path & "\" & Liste(i - 1) & ".txt", True, True)

Hélas le résultat obtenu est en UCS-2 LE BOM , pas en UTF-8.


Quelqu’un a une idée ?

Merci de votre aide

Steph
 

Staple1600

XLDnaute Barbatruc
Bonsoir àtous

Apparemment c'est mieux au niveau du contenu des *.txt
Mais c'est toujours pas çà.
VB:
Sub blabla()
'Cocher ces réferences
' Microsoft ADO Ext.  6.0 for DDL and Security
' Microsoft ActiveX Data Objects 2.7 Library
Dim stream As New ADODB.stream
Dim i As Long, j As Long, k As Long, Ligne As String, Liste
Sheets("PnL").Select
'Liste des noms à parcourir et à enregistrer
Liste = Array("blabla1", "blabla2", "blabla3")
    'i passe de 1 à i pour les i plages
    For i = 1 To 3
       'on sélectionne les plages une à une
    Application.Goto Reference:=Liste(i - 1)
    'on crée le fichier
    stream.Open
    stream.Type = adTypeText
    stream.Charset = "utf-8"
          'Pour chaque ligne  de la plage
          For j = 1 To Range(Liste(i - 1)).Rows.Count
              Ligne = ""
              'Pour chaque colonne de la ligne on colle les informations avec un séparateur tabulation (chr(9))
              For k = 1 To Range(Liste(i - 1)).Columns.Count
                  Ligne = Ligne & Range(Liste(i - 1)).Cells(j, k).Value & Chr(9)
              Next k
              If Len(Ligne) > 0 Then Ligne = Left(Ligne, Len(Ligne) - 1)
              'On écrit la ligne dans le fichier texte
    stream.WriteText Ligne, 1
          Next j
          'on ferme le fichier
    stream.Position = 3 'skip BOM
    Dim BinaryStream As New ADODB.stream
    BinaryStream.Type = adTypeBinary
    BinaryStream.Mode = adModeReadWrite
    BinaryStream.Open
    ' Strips BOM (first 3 bytes)
    stream.CopyTo BinaryStream
    stream.Flush
    stream.Close
    BinaryStream.SaveToFile ThisWorkbook.Path & "\" & Liste(i - 1) & ".txt", adSaveCreateOverWrite
    BinaryStream.Flush
    BinaryStream.Close
    Next i
   End Sub
 

Staple1600

XLDnaute Barbatruc
Re à tous

Après quelques recherches sur le Web, j'ai testé ceci
1) On créé d'abord le fichier UTF-8
On vérifie dans le bloc-notes qu'on est bien en UTF-8
2) On lance Supprime_UTF8_Bom
Et on s'aperçoit dans le bloc-note qu'on est désormais en ANSI
Donc au final, je passe mon tour ;)
NB: Il faut cocher les références à Microsoft Scripting Runtime dans VBE
VB:
Public Const UTF8_BOM = ""
Public Const UTF16BE_BOM = "þÿ"
Public Const UTF16LE_BOM = "ÿþ"
Sub testUTF8()
Dim fsTrm As Object
Set fsTrm = CreateObject("ADODB.Stream")
With fsTrm
.Type = 2
.Charset = "utf-8"
.Open
.WriteText "Ligne de test"
.SaveToFile ThisWorkbook.Path & "\" & "Test1UTF8.txt", 2
End With
End Sub
Sub Supprime_UTF8_Bom()
'emprunté à :Christoph Schneegans
Dim F As String, t As String
Dim fso As New FileSystemObject
F = ThisWorkbook.Path & "\" & "Test1UTF8.txt"
t = fso.OpenTextFile(F, ForReading).ReadAll
If Left(t, 3) = UTF8_BOM Then
fso.OpenTextFile(F, ForWriting).Write (Mid(t, 4))
MsgBox "BOM supprimé"
Else
MsgBox "UTF-8-BOM non reconnu"
End If
End Sub
 

stephsteph

XLDnaute Occasionnel
Bonjour Staple 1600, bonjour le forum,



Merci de tous tes efforts en espérant que l’on va s’en sortir !

J’ai testé sur xlsm 2007 la macro proposée hier à 19h15.

Malheureusement elle bugue à

Dim stream As New ADODB.stream

Surligné en bleu avec une boîte qui dit

Erreur de compilation

Type défini par l’utilisateur non défini



Voilà

Il reste que la macro modèle que tu avais trouvé Jeudi dernier à 19h48 marchait chez moi avec 2007 et produisait du UTF-8 sans Bom... reste l'adaptation à ma macro qui apparaît comme très ardue!

Encore merci!

A+ peut-être

Steph
 

stephsteph

XLDnaute Occasionnel
Bonjour Staple 1600

Désolée de t'avoir énervé.
Aucune intention.
Je n'avais pas vu les 3 lignes de commentaires.
Je suis incompétente là.
Cocher ces 2 lignes?

' Microsoft ADO Ext. 6.0 for DDL and Security
' Microsoft ActiveX Data Objects 2.7 Library

Comment?
J'ai trouvé une réponse (très vieille) sur ce forum pour la 1ère, si elle est toujours valide.
Mais rien pour la seconde.

Je veux bien essayer si j'apprend comment les cocher.

Mais d'abord des questions.
Si on me dit comment faire, ta macro ne fera quand même pas le job (sauf erreur de ma part de compréhension de ton message), alors intérêt?
Si je le fais est-ce que cela aura un impact négatif sur mes dizaines de macro VBA Excel existantes (prudence inutile ?)
Les macros dans les fils en Anglais ne parlent pas de ces bibliothèques spéciales et elles marchent sans (là je suis carrément paumée).

Toujours merci!

A+

Steph
 

Staple1600

XLDnaute Barbatruc
Bonsoir à tous

Bonjour Staple 1600
Désolée de t'avoir énervé.
Aucune intention.
Le blister difficile à enlever sur les CD -> m’énerve!
Le mode du sans gluten -> m'énerve!
l'opprobre jetée sur les fromages au lait cru -> m'énerve!
la nomophobia, partout au boulot, au resto -> m'énerve
Mais un(e) camarade de Cellule qui trop pressé(e) de résoudre sa question lit les réponses en diagonale, ça m'énerve pas ;)
Ça peut à la rigueur faire surgir un tit sourire narquois au coin de mes lévres ;) (Ce qui explique le ;) et le :rolleyes:)

Maintenant pour revenir au vert
Il fallait comprendre : Cocher ces références dans VBE
ALT+F11 -> menu Outils -> Références, cocher à alors les deux cases idoines.

Ce faisant, cela ne résout pas ta question, mais ça empêchera le bug de la macro.

Maintenant puisque tu évoquais Notepad++
Tu as essayé ceci par hasard ?
d9I9m.png
 

stephsteph

XLDnaute Occasionnel
Bonjour Staple 1600

Ravie de voir que nous partageons la même cellule.

Je ne savais pas qu’il y avait des cellules mixtes.

Mais en terme de prison comme pour VBA je n’y connais pas grand chose !

Oui j’utilise notepad++ et je peux manuellement convertir chaque fichier en UTF-8 sans bom comme dans le modèle (3 fois), mais dans la vraie vie la VBA génère 113 fichiers textes et manuellement 1 à 2 fois par semaine c’est la galère (ce qui est différent de la prison je te l’accorde).

D’où ce fil !

Curieusement plus je cherche, moins je trouve ce thème en Français, et plus j’en trouve en Anglais (dur, dur).

Pourtant il doit y avoir une foule de gens qui utilise Excel pour générer des pages textes et maintenant avec html5, tout pousse à passer en UTF-8… donc cette foule doit avoir (eu) le même souci que moi !

Code:
Option Explicit




Sub WriteUTF8WithoutBOM()




Dim UTFStream As Object, BinaryStream As Object

With CreateObject("adodb.stream")

.Type = 2

.Mode = 3

.Charset = "UTF-8"

.LineSeparator = -1

.Open

.WriteText "qwertzuiopõúasdfghjkléáûyxcvbnm\|Ä€Í÷×äðÐ[]í³£;?¤>#&@{}<;>*~¡^¢°²`ÿ´½¨¸0", 1

.Position = 3 'skip BOM

Set BinaryStream = CreateObject("adodb.stream")

BinaryStream.Type = 1

BinaryStream.Mode = 3

BinaryStream.Open

'Strips BOM (first 3 bytes)

.CopyTo BinaryStream

.Flush

.Close

End With

BinaryStream.SaveToFile "testutf8.txt", 2

BinaryStream.Flush

BinaryStream.Close

End Sub

Ce code marche… j’ai essayé de bidouiller avec un seul champ, mais la fonction writetext je ne comprend pas bien ses options (comme par exemple en remplaçant un texte fixe par le contenu d’un champ !).
Mais je dois être naïve... tu y as sans doute pensé avant.

A+

Steph
 

stephsteph

XLDnaute Occasionnel
Bonjour Staple 1600,



C'est une bonne idée de contourner pour arriver à la soluce!

J’ai appliqué facilement dans mon notepad++ et dans complément python scripts, scripts, j’ai maintenant le script de conversion.

J'ai tout fait bien, je crois, mais lorsque je "run the script", j'ai une petite fenêtre qui apparaît avec

Exception

Unknown exception

OK



Et le job ne se fait pas.



En Anglais dans le message de départ (ton lien) c'est dit que si on a un problème il faut "show console" (le reste j'ai pas capté).

Dans la console si l'on fait "run" apparaissent dans la fenêtre les caractères >>>

Alors je ne me suis pas découragée et j’ai googelisé avec de nouveaux mots clés comprenant notepad++

Et j’ai trouvé cela :

Ce lien n'existe plus

Le principe est similaire mais c’est en Français et le code est différent (dans certains détails).

J’ai exécuté à nouveau et cette fois le script ne donne pas de message d’erreur mais il est inactif (les fichiers restent en Ansi).

Cela dit l’auteur mentionne que Python est spécial (dans les indentations de code ???) et j’ai essayé de bidouiller, mais rien de rien.

Il n’empêche : on progresse…

Donc à +



Steph
 

Staple1600

XLDnaute Barbatruc
Bonsoir çà tous


Tu as essayé le script publié dans les commentaires par
ghaliloo 1:05 PM on 10/22/2015

On peut lire aussi dans les commentaires, qu'il faut mettre dans cette ligne le nom exact localisé de la commande
Notepad.runMenuCommor(“Encoding”, “Convert to UTF-8 without BOM”)
D'ailleurs il y a une coquille ça devrait être
Notepad.runMenuCommand(“Encoding”, “Convert to UTF-8 without BOM”)
Donc si tu as ton menu en français, il faut le nom exact de la commande à la place des caractères en bleu
 

stephsteph

XLDnaute Occasionnel
Bonjour Staple 1600,

Je suis paumée !

J’ai essayé les 2 scripts (qui se ressemblent).

Le « français » (Ce lien n'existe plus)

Code:
import os;

import sys;

import time;

filePathSrc="C:\\Temp\\UTF8"

for root, dirs, files in os.walk(filePathSrc):

  for fn in files:

  if fn[-4:] == '.php' or fn[-3:] == '.js' or fn[-4:] == '.htm' or fn[-5:] == '.html' or fn[-4:] == '.css' or fn[-4:] == '.txt':

   console.write('-> Ouverture ' + root + "\\" + fn)

  notepad.open(root + "\\" + fn)

  encoding=str(notepad.getEncoding())

  if encoding != 'COOKIE':

  # COOKIE : UTF without BOM

  # ENC8BIT : ANSI

   console.write('  -> Conversion UTF-8 depuis ' + encoding)

  if notepad.runMenuCommand("Encodage", "Convertir en UTF-8 (sans BOM)")== True:

  notepad.save()

  console.write("  -> OK")

   else:

  console.write("  -> KO !!")

  else:

  console.write("  -> OK")

  notepad.close()

L’anglais de ghaliloo 1:05 PM on 10/22/2015 (après correction de commor en command)

Code:
import os;

import sys;

filePathSrc=”C:\\Temp\\UTF8”

for root, dirs, files in os.walk(filePathSrc):

for fn in files:

if fn[-4:] == ‘.php’ or fn[-6:] == ‘.phtml’ or fn[-4:] == ‘.htm’ or fn[-5:] == ‘.html’ or fn[-3:] == ‘.js’ or fn[-4:] == ‘.css’ or fn[-4:] == ‘.txt’:

Notepad.open(root + “\\” + fn)

console.write(root + “\\” + fn + “\r\n”)

Notepad.runMenuCommand(“Encoding”, “Convert to UTF-8 without BOM”)

Notepad.messageBox(‘Project successfully converted to UTF-8 boss’, ‘Converting current project to UTF-8’, 0)

Notepad.save()

Notepad.close()

Dans les 2 cas (j’ai bien 3 fichiers ansi dans le sous-dossier UTF8), le script ne produit pas de message d’erreur , mais ne fait rien (les 3 fichiers sont inchangés).

Si j’ai bien compris, avec le premier code j’aurais même dû avoir un affichage OK ou KO !

Désolée, je n’aurai jamais imaginé un jour toucher à un code Python !!! (dans pas longtemps je vais pouvoir concurrencer Jessie alias Zuckerberg dans le film de Fincher… humour).

A+

Steph
 

Staple1600

XLDnaute Barbatruc
Bonsoir à tous

Apparemment le script ne fonctionne pas avec la dernière version de notepad ++
Chez moi il se passe rien également.
(Peut-être parce que je suis en 64 bits)

Il faudrait que d'autres XDLnautes fassent le test. ;)

Ceci dit, si on fait ce test avec notepad++
1) Créer un fichier txt -> Encoder en UTF8
2) On ouvre le fichier avec le bloc-notes on voit qu'il est bien en UTF-8
puis on fait Convertir en UFT8 sans BOM
3) On ouvre le fichier dans le bloc-note, on voir qu'il est en ANSI.

Donc est-ce que Convertir en UTF-8 sans BOM, revient à le convertir et ANSI.
 
Dernière édition:

Staple1600

XLDnaute Barbatruc
Re à tous

Je suis reparti farfouiller sur la toile et suis retombé sur du VBA
NB: Cocher les références précédemment cités dans le fil
Code:
Sub CSVFileAsUTF8WithoutBOM()
'source:vba-corner
Dim SrcRange As Range
Dim CurrRow As Range
Dim CurrCell As Range
Dim CurrTextStr As String
Dim ListSep As String
Dim FName As Variant
Dim UTFStream As Object
Dim BinaryStream As Object

' ask for file name and path
  FName = Application.GetSaveAsFilename("", "CSV File (*.csv), *.csv")

' prepare UTF-8 stream
  Set UTFStream = CreateObject("adodb.stream")
  UTFStream.Type = adTypeText
  UTFStream.Mode = adModeReadWrite
  UTFStream.Charset = "UTF-8"
  UTFStream.LineSeparator = adLF
  UTFStream.Open

  'set field separator
  ListSep = ","
  'set source range with data for csv file
  If Selection.Cells.Count > 1 Then
    Set SrcRange = Selection
  Else
    Set SrcRange = ActiveSheet.UsedRange
  End If

  For Each CurrRow In SrcRange.Rows
    'enclose each value with quotation marks and escape quotation marks in values
    CurrTextStr = ""
    For Each CurrCell In CurrRow.Cells
      CurrTextStr = CurrTextStr & """" & Replace(CurrCell.Value, """", """""") & """" & ListSep
    Next
    'remove ListSep after the last value in line
    While Right(CurrTextStr, 1) = ListSep
      CurrTextStr = Left(CurrTextStr, Len(CurrTextStr) - 1)
    Wend
    'add line to UTFStream
    UTFStream.WriteText CurrTextStr, adWriteLine
  Next

  'skip BOM
  UTFStream.Position = 3

  'copy UTFStream to BinaryStream
  Set BinaryStream = CreateObject("adodb.stream")
  BinaryStream.Type = adTypeBinary
  BinaryStream.Mode = adModeReadWrite
  BinaryStream.Open

  'Strips BOM (first 3 bytes)
  UTFStream.CopyTo BinaryStream

  UTFStream.Flush
  UTFStream.Close

  'save to file
  BinaryStream.SaveToFile FName, adSaveCreateOverWrite
  BinaryStream.Flush
  BinaryStream.Close

End Sub
 

stephsteph

XLDnaute Occasionnel
Bonjour Staple 1600,



Ah, c’est pas de chance.

C’est curieux… je suis allée sur le forum de notepad++ et le sujet est souvent abordé mais pas résolu semble-t-il (et pour poster sur ce forum il faut un compte Facebook ou Twitter donc très peu pour moi).



Bon, je continue à chercher de mon côté !

Merci pour tout

A+, Steph


PS: j'ai testé la nouvelle VBA et j'ai une erreur 3000 sous Xlsm2007
UTF-8 avec ou sans bom, et, Ansi c'est très différent.
Dans la VBA qui marchait sous Notepad++ je passais de Ansi à UTF-8 sans bom (en bas à droite) avant et après, donc pas de souci (et le concepteur avait sciemment mis dans le texte des caractères spéciaux qui différencient les 2 jeux de caractères pour montrer que c'était tout bon). D'ailleurs si tu changes le doc type pour UTF-8 sans changer les caractères et bien tu as des problèmes d'affichage des pages Internet... donc c'est un vrai souci bien concret!
 

Staple1600

XLDnaute Barbatruc
Bonsoir à tous

PS: j'ai testé la nouvelle VBA et j'ai une erreur 3000 sous Xlsm2007
Tu as bien coché les références que nous avons évoqués plus haut dans la discussion ?

J'ai vu aussi que dans Notepad++ on pouvait enregistrer des macros
Mais pour le moment, je n'ai pas réussi à le faire.

Une autre piste
Utiliser un batch MSDOS* ou un script VBS avec cet utilitaire
https://www.mannaz.at/codebase/utf-byte-order-mark-bom-remover/
NB: J'ai pas testé ni la fiabilité/sécurité de cet utilitaire, ni cet utilitaire

*exemple adapté de David Norton (non testé)
cmd.exe /c "echo. | c:\Temp\bomremover c:\Temp *.txt";

Soit tu copies/colles cette ligne en gras dans le bloc-notes et enregistres sous Test.bat
(en mettant tes fichiers txt, bomremover.exe et test.bat dans le même répertoire, donc ici dans C:\Temp)
Soit tu fais: Touche WINDOWS+R et là tu saisis cette ligne et tu tapes sur ENTER

NB: Faire l'essai sans le ; final si message erreur
 
Dernière édition:

Discussions similaires

Statistiques des forums

Discussions
298 901
Messages
1 972 612
Membres
203 781
dernier inscrit
makam