Enregistrer le fichier texte UTF-8 encodé avec VBA
Comment puis-je écrire des chaînes encodées UTF-8 à un fichier texte de vba, comme
Dim fnum As Integer
fnum = FreeFile
Open "myfile.txt" For Output As fnum
Print #fnum, "special characters: äöüß" 'latin-1 or something by default
Close fnum
y a-t-il un réglage au niveau de L'Application?
5 réponses
j'ai trouvé la réponse sur le web :
Dim fsT As Object
Set fsT = CreateObject("ADODB.Stream")
fsT.Type = 2 'Specify stream type - we want To save text/string data.
fsT.Charset = "utf-8" 'Specify charset For the source text data.
fsT.Open 'Open the stream And write binary data To the object
fsT.WriteText "special characters: äöüß"
fsT.SaveToFile sFileName, 2 'Save binary data To disk
Certainement pas comme je l'espérais...
vous pouvez utiliser la méthode CreateTextFile ou OpenTextFile, les deux ont un attribut" unicode " utile pour les paramètres d'encodage.
object.CreateTextFile(filename[, overwrite[, unicode]])
object.OpenTextFile(filename[, iomode[, create[, format]]])
Exemple: Remplacer:
CreateTextFile:
fileName = "filename"
Set fso = CreateObject("Scripting.FileSystemObject")
Set out = fso.CreateTextFile(fileName, True, True)
out.WriteLine ("Hello world!")
...
out.close
Exemple: Ajouter:
OpenTextFile Set fso = CreateObject("Scripting.FileSystemObject")
Set out = fso.OpenTextFile("filename", ForAppending, True, 1)
out.Write "Hello world!"
...
out.Close
voir plus sur MSDN docs
écrit un octet au début du fichier, ce qui est inutile dans un fichier UTF-8 et certaines applications (dans mon cas, SAP) ne l'aiment pas. Solution ici: puis-je exporter des données excel avec UTF-8 sans BOM?
Voici une autre façon de le faire-en utilisant la fonction API WideCharToMultiByte:
Option Explicit
Private Declare Function WideCharToMultiByte Lib "kernel32.dll" ( _
ByVal CodePage As Long, _
ByVal dwFlags As Long, _
ByVal lpWideCharStr As Long, _
ByVal cchWideChar As Long, _
ByVal lpMultiByteStr As Long, _
ByVal cbMultiByte As Long, _
ByVal lpDefaultChar As Long, _
ByVal lpUsedDefaultChar As Long) As Long
Private Sub getUtf8(ByRef s As String, ByRef b() As Byte)
Const CP_UTF8 As Long = 65001
Dim len_s As Long
Dim ptr_s As Long
Dim size As Long
Erase b
len_s = Len(s)
If len_s = 0 Then _
Err.Raise 30030, , "Len(WideChars) = 0"
ptr_s = StrPtr(s)
size = WideCharToMultiByte(CP_UTF8, 0, ptr_s, len_s, 0, 0, 0, 0)
If size = 0 Then _
Err.Raise 30030, , "WideCharToMultiByte() = 0"
ReDim b(0 To size - 1)
If WideCharToMultiByte(CP_UTF8, 0, ptr_s, len_s, VarPtr(b(0)), size, 0, 0) = 0 Then _
Err.Raise 30030, , "WideCharToMultiByte(" & Format$(size) & ") = 0"
End Sub
Public Sub writeUtf()
Dim file As Integer
Dim s As String
Dim b() As Byte
s = "äöüßµ@€|~{}[]²³\ .." & _
" OMEGA" & ChrW$(937) & ", SIGMA" & ChrW$(931) & _
", alpha" & ChrW$(945) & ", beta" & ChrW$(946) & ", pi" & ChrW$(960) & vbCrLf
file = FreeFile
Open "C:\Temp\TestUtf8.txt" For Binary Access Write Lock Read Write As #file
getUtf8 s, b
Put #file, , b
Close #file
End Sub
j'ai regardé la réponse de Máťa dont le nom suggère des qualifications et de l'expérience d'encodage. Le VBA docs say CreateTextFile(filename, [overwrite [, unicode]])
crée un fichier "comme un fichier Unicode ou ASCII. La valeur est True si le fichier est créé en tant que fichier Unicode; False s'il est créé en tant que fichier ASCII. S'il est omis, un fichier ASCII est présumé."C'est bien qu'un fichier stocke des caractères unicode, mais dans quel encodage? Unicode non codé ne peut pas être représenté dans un fichier.
Le VBA doc page pour OpenTextFile(filename[, iomode[, create[, format]]])
offre une troisième option pour le format:
- Tristatateefault 2 " ouvre le fichier en utilisant la valeur par défaut du système."
- TriStateTrue 1 " ouvre le fichier en Unicode."
- TriStateFalse 0 " ouvre le fichier ASCII."
Máťa passes -1 pour cet argument.
à en juger par VB.NET documentation (pas VBA mais je pense reflète des réalités sur la façon dont Windows OS sous-jacent représente chaînes unicode et échos jusqu'à MS Office, Je ne sais pas) le système par défaut est un encodage utilisant 1 octet/caractère unicode en utilisant une page de code ANSI pour la locale. UnicodeEncoding
est UTF-16. Les docs décrivent aussi UTF-8 est aussi un "encodage Unicode", ce qui a du sens pour moi. Mais je ne sais pas encore comment spécifier UTF-8 pour la sortie VBA ni être sûr que les données que j'écris sur le disque avec le OpenTextFile (,, 1) est encodé UTF-16. Tamalek post est utile.