PDA

Vollständige Version anzeigen : Rich-Text Memofeld mit Formatierungen an Word-Serienbrief


Köbi
04.06.2012, 11:05
Hallo

Diese Frage habe ich vor einiger Zeit schon in einem andern Forum gestellt, dort aber keine Er"lösung" gefunden.:(
http://www.office_loesung.de/ftopic525499_0_0_asc.php
(zwischen office und loesung Bindestrich statt Underline)


Mit folgendem Code erstelle ich bisher aus Acc2003 heraus einen Word-Serienbrief.

Private Sub cmdSerienbriefErstellen_Click()
Dim Dokumente As String
Dim Vorlagen As String

Vorlagen = CurrentProject.Path & "\Vorlagen"
Dokumente = CurrentProject.Path & "\Seriendokumente"
WordSeriendruck Dokumente, Vorlagen
End Sub

Private Sub WordSeriendruck(strPfadDokumente As String, strPfadVorlagen As String)
On Error GoTo WordSeriendruck_Error
Dim oWordApp As Object
Dim oWord As Object
Dim sSQL As String
Dim PathDokumentVorlage As String
Dim WordDateiPath As String
Dim sDateiname As String
Dim rstData As DAO.Recordset
Dim strEingabe As String, strMldg As String
Dim strZieldatei As String

' Datenquelle öffnen
Set rstData = CurrentDb.OpenRecordset("qrySeriendok")
If rstData.RecordCount = 0 Then
MsgBox "Es sind keine Serienbriefe zu drucken.", vbExclamation
Exit Sub
End If

strMldg = "Geben Sie bitte einen Dateinamen für das fertige Seriendokument ein."
strEingabe = InputBox(Prompt:=strMldg, Title:="Bitte Dateinamen eingeben.", XPos:=4000, YPos:=4000)

' Daten in CSV-Datei exportieren
strZieldatei = strPfadDokumente & "\" & strEingabe & Format(Now, "_yyyyMMdd_hhmmss") & ".txt"

DoCmd.TransferText acExportMerge, , "qrySeriendok", strZieldatei
PathDokumentVorlage = strPfadVorlagen & "\" & "OrdnerSeriendokA4.dotx"

If IstWordGestartet() Then
Set oWordApp = GetObject(, "Word.Application") ' Word war schon gestartet
Else
Set oWordApp = CreateObject("Word.Application") ' Word starten
End If

' Neues Word-Dokument anlegen
Set oWord = oWordApp.Documents.Add(PathDokumentVorlage)
' Seriendruck-Datenquelle anbinden
oWordApp.ActiveDocument.MailMerge.OpenDataSource Name:=strZieldatei _
, ConfirmConversions:=False, ReadOnly:=False, LinkToSource:=True
DoEvents

sDateiname = strPfadDokumente & "\" & strEingabe & Format(Date, "_yyyyMMdd")

oWord.SaveAs sDateiname
oWordApp.Visible = True
oWordApp.WindowState = vbext_ws_Maximize
oWordApp.Activate

rstData.Close
Set rstData = Nothing
Exit Sub

WordSeriendruck_Error:
WordDateiPath = ""
MsgBox Error, vbCritical, "Fehler beim Erzeugen der Word-Datei."
End Sub

Public Function IstWordGestartet() As Boolean
' Stellt fest, ob Word gerade geladen ist
Dim obj As Object

On Error Resume Next
Set obj = GetObject(, "Word.Application") ' nach Word suchen
IstWordGestartet = (err.Number = 0)
Set obj = Nothing
End Function


Die Tabelle, auf welcher die Abfrage "qrySeriendok" basiert, enthält mehrere Memofelder.

Unter Acc2007 habe ich nun diesen Memofeldern das Rich-Textformat verpasst, damit der Text ein wenig formatiert werden kann.
Bei der Erstellung des Seriebriefs sollen die Formatierungen in Word übernommen werden. Was aber leider nicht funktioniert.

Ich habe hier zum Thema diesen Thread gefunden,
http://www.office_loesung.de/ftopic246970_0_0_asc.php
(zwischen office und loesung Bindestrich statt Underline)
muss aber gestehen, dass ich damit nicht klar komme.

Kann mir jemand mit einem guten Tipp oder einem angepassten Code helfen? Mein Dank würde diesen Jemand lebenslänglich verfolgen.

Ach ja, noch was. Weshalb bleibt Word trotz diesem Code im Hintergrund?

oWordApp.Visible = True
oWordApp.WindowState = vbext_ws_Maximize
oWordApp.Activate

maikek
04.06.2012, 13:40
Moin, das Thema gab es hier auch schon ;) :
http://www.ms-office-forum.de/forum/showthread.php?t=241514
maike

Köbi
04.06.2012, 15:56
Hallo maike

Vielen Dank für die Antwort.

Leider habe ich vergessen zu erwähnen, dass ich diesen Beitrag bereits kenne. Es scheint darin aber um eine Variante unter Acc2002 und mit einem "fremden" ActiveX zu gehen. Ein solches darf ich nicht verwenden (Kundenanforderung).

Access2007 bietet nun aber eine eigene Möglichkeit, Memofelder als Rich-Text zu deklarieren und darin eine (etwas eingeschränkte, aber immerhin) Formatierung vorzunehmen.
Es sollte doch möglich sein, diese Formatierung einem WORD-Serienbrief zu übergeben. Es handelt sich ja dabei auch um ein Office-Produkt.

Ich bin seeeehr ratlos.

ebs17
04.06.2012, 17:45
Access2007 bietet nun aber eine eigene Möglichkeit, Memofelder als Rich-Text zu deklarieren
In einem Formulartextfeld oder auch in einem Tabellenfeld?
Was steht im Tabellenfeld genau drin?

Spätestens der Zwischenschritt CSV (Textdatei) erzeugt Plaintext. Dort müssten also Formatierungsangaben als Text sichtbar sein, da es keine externe versteckte Speicherung von solchen Zusatzinformationen gibt.

maikek
04.06.2012, 17:55
Es scheint darin aber um eine Variante unter Acc2002 und mit einem "fremden" ActiveX zu gehen.
Im Prinzip wird doch der Inhalt des Feldes als .pdf zwischengespeichert - ob das jetzt ein ActiveX ist oder ein "normales" Memofeld sollte dabei eigentlich wurscht sein ... oder? Kann es leider mangels 2007 nicht selbst testen :-).
maike

Köbi
07.06.2012, 10:06
Danke für die Antworten.

@Eberhard
Im Tabellenfeld ist der Text richtig, also mit der Formatierung, dargestellt.
Im Word-Serienbrief kommt der Text dann aber ohne Formatierung, dafür mit den entsprechenden Formatierungsanweisungen, an.

@maike
Im Prinzip wird doch der Inhalt des Feldes als .pdf zwischengespeichert
Von einem .pdf ist nirgends die Rede.

Mit folgendem Code schaffe ich es, den Text richtig, mit der gewünschten Formatierung, nach Word zu schaufeln. Aber leider nur mit einem einzigen Memofeld und nur für ein einzelnes Dokument.

Function Memortf(strHTML As String) As String
Dim F As Integer
strHTML = "<html><body>" & strHTML & "</body></html>"
Memortf = "U:\AGG\AccVers2007\temp.html"
F = FreeFile
Open Memortf For Binary As F
Put F, , strHTML
Close F
End Function

Private Sub WordSeriendruck()
On Error GoTo OffAutoProblem

Dim oWordApp As Object
Dim oWord As Object
Dim sSQL As String
Dim PathDokumentVorlage As String
Dim WordDateiPath As String
Dim sDateiname As String
Dim objWord As New Word.Application
Dim objDoc As Word.Document

Dim strFile As String
strFile = Memortf(Forms!frmStammdaten!Dienstleistungen)

If Not IstWordGestartet() Then
Set objWord = New Word.Application
Set objDoc = objWord.Documents.Add("normal.dotx")
Else
Set objWord = GetObject(, "Word.Application")
If objWord.Documents.Count = 0 Then
Beep


MsgBox "Kein Dokument in Word geöffnet!", _
vbOKOnly + vbInformation, "!!! Problem !!!"
GoTo EndeProc
End If
Set objDoc = objWord.ActiveDocument
End If

objWord.Visible = True
objWord.WindowState = wdWindowStateMaximize
objWord.Activate

objWord.Selection.InsertFile FileName:=strFile, Range:="", ConfirmConversions:= _
False, Link:=False, Attachment:=False

Kill strFile

Set objWord = Nothing

EndeProc:
Set objWord = Nothing
Exit Sub

OffAutoProblem:
Beep
MsgBox "Fehler bei der Kommunikation mit Word!" + _
vbCrLf + vbCrLf + err.Description, _
vbOKOnly + vbCritical, "!!! Fehler !!!"
Resume EndeProc

End Sub


Public Function IstWordGestartet() As Boolean
' Stellt fest, ob Word gerade geladen ist
Dim obj As Object
On Error Resume Next
Set obj = GetObject(, "Word.Application") ' nach Word suchen
IstWordGestartet = (err.Number = 0)
Set obj = Nothing
End Function


Ich muss aber mehrere Felder für mehrere Adressen in die Mergefields im Word-Serienbrief bringen. Und daran scheitere ich.

Ich bin um jede Hilfe sehr dankbar.

Köbi
08.06.2012, 16:59
Hallo

Natürlich hätte ich gerne eine Lösung für mein Problem. Deshalb getraue ich mich, diesen Beitrag nochmals nach oben zu schieben.

Stefan Dase
10.06.2012, 11:56
Hallo Köbi,

der gezeigte Code speichert den Inhalt des Memo-Feldes als HTML-Datei zwischen, fügt diesen als Datei in Word ein und löscht die Datei ganz am Ende wieder. Du müsstest ihn also so umbauen, dass das speichern als Datei und Einfügen in Word für jedes Memo-Feld und jedes Word-Dokument durchgeführt wird.

Hier mal abgewandelter Code, Feinheiten solltest du aber schon selber einfügen:


Public Function Memortf(strHTML As String, strFile As String) As Boolean

Dim F As Integer

On Error GoTo Memortf_Error

strHTML = "" & strHTML & ""
F = FreeFile
Open strFile For Binary As F
Put F, , strHTML
Close F

Memortf = True
Exit Function

Memortf_Error:
Memortf = False

End Function

Private Sub WordSeriendruck()

On Error GoTo OffAutoProblem

Dim objWord As New Word.Application
Dim objDoc As Word.Document
Dim strFile As String

If Not IstWordGestartet() Then
Set objWord = New Word.Application
Else
Set objWord = GetObject(, "Word.Application")
End If

'dies is m.E. nicht erforderlich; ansonsten wieder aktivieren
'objWord.Visible = True
'objWord.WindowState = wdWindowStateMaximize
'objWord.Activate

'hier Schleife über alle deine Dokumente starten
strFile = "U:\AGG\AccVers2007\temp.html"

Set objDoc = objWord.Documents.Add("normal.dotx")

'hier Schleife über alle deine Memofelder einbauen
If Memortf(Forms!frmStammdaten!Dienstleistungen, strFile) Then
objDoc.Selection.InsertFile FileName:=strFile, Range:="", ConfirmConversions:= _
False, Link:=False, Attachment:=False


Kill strFile
End If
'hier Schleife über Memofelder beenden

objDoc.SaveAs2 "DeinDateiname"
objDoc.Close

'hier Schleife über alle deine Dokumente beenden

EndeProc:
Set objDoc = Nothing
Set objWord = Nothing
Exit Sub

OffAutoProblem:
Beep
MsgBox "Fehler bei der Kommunikation mit Word!" + _
vbCrLf + vbCrLf + Err.Description, _
vbOKOnly + vbCritical, "!!! Fehler !!!"
Resume EndeProc

End Sub

Public Function IstWordGestartet() As Boolean
' Stellt fest, ob Word gerade geladen ist
Dim obj As Object
On Error Resume Next
Set obj = GetObject(, "Word.Application") ' nach Word suchen
IstWordGestartet = (Err.Number = 0)
Set obj = Nothing
End Function


Viele Grüße,
Stefan

Köbi
12.06.2012, 13:24
Grüezi Stefan

Vielen Dank für Deine Antwort.

Ich werde mich morgen oder am Donnerstag genauer damit befassen. Bis jetzt sind die ersten Gehversuche mit Deinem Code leider nicht sehr befriedigend verlaufen.

Ein Detail vorerst:
objDoc.Selection.InsertFile FileName:=strFile, Range:="", ConfirmConversions:= _
False, Link:=False, Attachment:=False
muss heissen
objWord.Selection.InsertFile FileName:=strFile, Range:="", ConfirmConversions:= _
False, Link:=False, Attachment:=False

Dann funktioniert die Sache für die Übergabe des formatierten Textes an die Cursorposition im WORD-Dokument.

Ich möchte aber einen Serienbrief in WORD erstellen. Damit habe ich Probleme.
Der Serienbrief wird wie folgt angestossen (nur Code-Schnipsel):
DoCmd.TransferText acExportMerge, , "qrySeriendok", strZieldatei
PathDokumentVorlage = strPfadVorlagen & "\" & "OrdnerSeriendokA4.dotx"

' Neues Word-Dokument anlegen
Set oWord = oWordApp.Documents.Add(PathDokumentVorlage)
' Seriendruck-Datenquelle anbinden
oWordApp.ActiveDocument.MailMerge.OpenDataSource Name:=strZieldatei _
, ConfirmConversions:=False, ReadOnly:=False, LinkToSource:=True

Das WORD-Dokument hat dafür sogenannte "MailmergeFields", welche die Daten aus der Datenquelle (hier aus Access) übernehmen. Aber leider ohne die Text-Formatierung.

Dein Vorschlag scheint mir darauf hinaus zu laufen, dass ich nicht einen Serienbrief erstelle, sondern Tausende von Einzelbriefen. Das möchte ich aber nicht.
Abgesehen davon, müsste das WORD-Dokument dann mit Textmarken bestückt werden, anstelle der Mailmergefelder. Aber die Übergabe der Formatierung an Textfelder scheint auch nicht zu funktionieren.

Soweit der Zwischenbericht. Wie schon anfangs angedeutet, melde ich mich wieder.
Aber wenn Du oder jemand Anders vorher schon einen Vorschlag hat: Immer her damit!

Stefan Dase
13.06.2012, 08:00
Hallo Köbi,

dann warte ich mal deine Gehversuche ab.


Ein Detail vorerst:
objDoc (...) muss heißen objWord (...)


Ich habe es nicht getestet, würde jetzt aber erwarten, dass es auch auf das Document-Objekt funktioniert? objWord ist ja in dem Muster ein Word.Application-Objekt, die Selection sollte sich aber auf das Document-Objekt beziehen. Aber versuche es einfach selber.


Ich möchte aber einen Serienbrief in WORD erstellen. Damit habe ich Probleme.

Dann kann der von dir vorgeschlagene Code zur Übernahme der Formatierung gar nicht funktionieren. Ein Word-Serienbrief liest die Daten ja direkt aus einer Access- oder Excel-Tabelle aus. Um die RTF-Einstellungen mitzunehmen, werden diese durch die Memortf-Funktion als HTML in einer Datei gespeichert, in Word eingefügt und die HTML-Datei dann wieder gelöscht. Dies funktioniert aber nur durch den VBA-Aufruf an dieser Stelle, nicht beim Lesen der Daten aus der Tabelle oder Abfrage.

Einzig möglicher Weg aus meiner Sicht wäre also, die Word-Dateien aus Access heraus erstellen zu lassen. Und du hast schon Recht, dafür müsstest du dann ein anderes Verfahren als MailMerge verwenden.

Viele Grüße,
Stefan

ebs17
13.06.2012, 11:12
@Köbi: Lies Dir mal das folgende durch:
Acc2007 - Daten via Email einsammeln

Ich interpretiere das so, dass ein Worddokument mit diesem Data Store eine eigene Datenbank hat, mit der man an Inhaltssteuerelemente auch formatierte Daten übergeben kann.
Wenn es nun gelingt, die Tabelleninhalte der Datenbank an diesen Data Store in der richtigen Form zu übergeben, sollte man nahe an der Umsetzung eines Seriendruckes sein.

Unter mit dem Stichwort "Content Control Toolkit" findet man dann auch einiges.

Praktische Erfahrungen habe ich allerdings noch nicht, da ich noch auf Office 2000 verharre. Du kannst aber gerne praktische Erfahrungen wiedergeben.

fr0sch
08.08.2012, 12:59
Hallo,
ich benutze den obigen Code für meine Datenbank. Funktioniert soweit auch, nur haut er mir voll die riesigen Abstände ober- und unterhalb von Aufzählungen rein und ich hätte gern eine andere Schriftart. Ich habe mehrere Vorlagen, die leider alle unterschiedliche Schriftarten haben. Ich dachte es würde reichen, wenn ich die Daten aus dem Bericht statt dem Formular nehme, aber wohl nicht. Die Schriftgröße stimmt. Kann aber auch Zufall sein...
Ich dachte auch man könnte die gewünschte Schriftart dem htmlstring zuweisen, aber das klappt nicht, weil für jede Zeile wieder die Standardschrift eingestellt ist... (hab mir den Quellcode mal angeschaut)
Gibt es eine Möglichkeit die Schrift im Nachhinein zu ändern also außer manuell? Vielleicht für die gesamte Zelle (Vorlagen sind Worddokumente mit Tabellen) in die das Memofeld reinkopiert wird?

Wäre super, wenn ihr da eine Idee hättet. Achso meine Programmierkenntnisse bestehen hauptsächlich aus copy und paste...hab also nicht viel Ahnung.

Köbi
08.08.2012, 13:37
Hallo

Ich merke gerade, dass ich meine Antwort verschlampt habe. Leider habe ich mein Problem mit der Formatierung bis jetzt noch nicht lösen können.

@Eberhard
Dein Vorschlag wäre wahrscheinlich zielführend, aber ich darf keine Fremd-Software installieren.:(