I am having issues figuring out the best way to do this:
I have a word template for an interview pre-night. What I need to do is fill out the word template with the interviewer and the people who are interviewing them. There will always be 1 interviewee but up to 12 interviewers. The part giving me issue is that there will not always be 12 interviewers so the area that the data is moved to needs to be dynamic. Should I create a table or bookmarks in Word and use VBA to move the data, or design the report in Access? Thanks for your help!
I am going to assume that what you are trying to do is complicated enough that "mail merge" won't work for you.
It really depends on whether you need the end result to be a Word document or an Access report. Both easily convert to PDF for document archiving. If you prefer to work with Word, add the key fields into your document with all the formatting necessary and then use VBA to do a search replace.
Two ways you could go about dealing with the 1-12 interviewers issue:
Use VBA to create one long segment containing all interviewers as a
single "field".
Add 12 sets of key fields and use search/replace
(through VBA of course not manually) to fill in the exiting
interviewer info and delete the key fields for the non-existing ones.
Related
I'm trying to do a Word MailMerge via VBA from my Access project. I created a clsWordMerge class so I could declare the Word application WithEvents, and take advantage of Word's MailMerge events, mainly the AfterMerge event.
Everything works fine, and I get the finished Word documents created, except that the source fields containing RTF data end up in the document not as formatted text, but instead the RTF codes and data:
<div><font face="Times New Roman" size=3 color=black>This is my <strong><em>test </em></strong>paragraph.</font></div>
Where I would expect to see:
This is my test paragraph
This happens whether I do a mail merge using a CSV file for my data source or an Access table.
So is there any way to correct this, and show the formatted data? I have access to all of the MailMerge events that Word provides.
Thanks..
No, there's no way to merge in RTF and have it display as Word content. RTF is not Word's native file format - a converter is required to display RTF as Word content.
Mail merge literally displays the data text, as it appears in the data source. There are no "advanced features" that enable selectively formatting the mail merge result.
Also, based on painful experience, relying on MailMergeAfterMerge is not advisable. When it was introduced, I tried it, was enthusiastic... until it started failing. The event is unpredictable and not reliable.
Given your requirements, a fully VBA-driven data transfer from Access to Word is a better investment of time and energy.
It probably can be done in certain circumstances, but I agree with Cindy Meister that the Mail Merge Events have not proven reliable (unless they have been fixed - I haven't actually used them for years). The following description of real and likely problems that I have previously encountered when trying this may help:
Not sure any of it can be done if you are merging to Email.
AFAICR the event you are likely to need (MailMergeBeforeRecordMerge) only fires each time Word processes the Main Document, not each time it processes a record in the data source. So if your Mail Merge Main Document "consumes" more than one Data Source record, e.g. because it uses { NEXT } or { NEXTIF } fields, it may be very difficult to get MaiMergeBeforeRecordMerge to do what you need. If I am right about that, that would be enough to put me off making the attempt.
in order to insert your "RTF", you must either
a. Have code that can interpret the "RTF" encoding and do all the right things necessary to insert it in your document, or
b. Have code that saves the "RTF" to an external file, then uses (say) Range.InsertFile to insert it and have Word interpret its contents, or perhaps
c. Use the clipboard to help you do the conversion.
If any of your rich text fields actually contained RTF, (a) would be difficult unless you could find a suitable library to help you. But in fact your sample shows a typical Access rich text field value, which is HTML-like. In fact, I think it is all standard HTML tagging that Word can interpret, but I don't know for sure. That could be much easier to interpret, especially if you only need the plain text (at its simplest, you might be able to throw away the tagging and insert the result.
If your rich text is longer than 255 characters (including the markup), Word's Document.MailMerge.DataSource.DataFields("the case-sensitive field name as Word sees it").Value will be truncated. So if you need the whole of the text or more of it, you'll have to get it somewhere else
The value inserted in the document using a { MERGEFIELD } field is not truncated to 255 characters so you may be able to get the value from the document. Word MailMerge may impose another limit (can't remember, perhaps 64Kb for an OLE DB connection, perhaps less, or perhaps there is a length limit for the data as a whole.
If you can't get the data from the document, you can get it directly from Access. Probably rather easily if your code is running in Access, but it can be done by using ADODB or perhaps ADO from Word VBA code. Your Mail Merge Data Source will need to retrieve the key fields of the record if you want to do that reliably. During development, if your application is running from Access but you are using VBA code in Word, you will probably also need to make sure that you save your Access database each time you modify your Access VBA code, otherwise Access opens the database exclusively and Word won't be able to retrieve data from it.
If you need to use (b) or (c) to save your HTML to a file then you may need to surround the HTML that you get from Access with tags and possibly tags to get Word to recognise the HTML. You could use Scripting.FileSystemObject to save the text, or perhaps ADODB.Stream if you are already using ADODB to retrieve Access data.
You should be able to use VBA Range.InsertFile to insert it, as long as you have some placeholder that tells you what to put it. Or you could use an INCLUDETEXT field and ensure that your Event code updates that field. A snag with the INCLUDETEXT approach is that if you merge to a new document, the INCLUDETEXT fields remain in the document so if you update them, they will all end up with the same result if you do not also create a new file for each source record.
i.e. quite a lot to think about!
I am new on VBA, I am creating a script to generate a report from a DB, I have been able to assemble a general draft of my report but I need to insert a table into an existing cell inside a word document, I have been surfing around but I am unable either to do a websearch with the correct terms in order to find some guidance on how to achieve this, If I am able to do it with my mouse I am sure I am able to do it through scripting, any resources that would help me in the right direction will be deeply appreciated.
Ok I found a way, The secret is in the Range, to specify where do you want your nested table to be placed.
so, I am using Powershell so the syntax might vary a little
For creating the Table in the Document (assuming you already have a created document, if not you are missing that part which I am not going through since they already are several question/answer pairs on that subject).
$TableX = $oDoc.Tables.Add($oDoc.Bookmarks("TableX").Range, 4, 3)
So TableX is our actual table, then we are telling word to use the helper method on the oDoc (Which is the name of our document object) to add a table, with a Bookmark named TableX (I will again not do a large explanation on this one, just for practical purposes, we name the Bookmark so we can reference to the table by Bookmark name later if we need to add data to it or manipulate it in any way we need) and at the same time we are calling to the method Range which is going to tell the Document Object where do we want the table to be placed, since we have not defined the range explicitly it will insert it in the next available line on the document,
Finally we specify how many rows and columns we would like in the table.
That is what we need for creating a table, now the tricky part, how do we insert a nested table, and moreover how do we specify where do we want this second table to be nested.
Well, with this:
$oNestedTable = $oDoc.Tables.Add($TableX.Cell(4, 2).Range,7,3)
We name our nested table oNestedTable, then we are calling the same helper method we called before to add a new table to the document, but wait, look carefully at the differences, the range part of the command is pointing to a specific cell on in our first table, that is in the fourth row within the second cell, it is there where we are explicitly telling the document to insert a new table with 7 rows and 3 columns.
I hope this gives you some bare minimum guidance.
Regards
en
I have a program which outputs a collection of tables in a word document which I eventually want to post as an html file with bookmarks and an index. The tables are grouped by "Name:" where there is a 3 row table that contains detailed header information for a section of data, then there is a second table which can span multiple pages which contains the data for that section. There is then a page break so that the next sections header table is on a new page. This can occur for a variable number of sections numbers in the hundreds. I need to write a script that
searches my document for "Name:", which is unique and would not
appear anywhere but the header table,
grabs the text that follows "Name:" within that table cell (for example "Name: Line 1234)
replaces all the blanks in that text string with an underscore to
make it a suitable bookmark name,
creates a bookmark with the name,
goes back and creates an index at the front of the document
Saves the file as an html
I have a passing familiarity with VB for word, I have used it a bit in excel, but am by no means an expert. I would appreciate any advice on functions and objects that I should be using for this script.
Hey MikeV from what I can gather, your problem seems more conceptual, less specific. What I mean is, have you started yet? Or looking at a blank script page?
I'm relatively new to coding, so I get that myself. What I do is make a list of what I need to do (what you have). Then think of the code or psuedo-code that would go with each step. Then you can start to build your script. You don't have to start with step one (as step 2/3 is often the more interesting bit), but let's do that.
Now, you need to search for a text string containing "Name:". I am proficient with VBA in excel, but haven't done anything for word. So I'd look it up. Googling "VBA find word in word document" will bring you to this page, which shows you how to approach step one. So steal their code, alter it to fit your needs and move on to step 2. Repeat the process, and that's how you build your algorithm! :)
Just a FYI, typically StackOverflow is for specific questions with an answer that can be confirmed, whereas you asked for help building an algorithm. I'd reserve those questions for your programming professor or friend who can help.
cheers
I have a pretty complex VBA plugin for Word written that automatically creates a report for me, using XML input, cycling through the X objects within the report to create the output. It is currently embedded into a Word Template file .DOCM.
I need to insert into the report a static list of text, based on the name of the item within the XML. For example, within my XML I have entries with a name BLAH1, BLAH2, BLAH3. Every time I see BLAH1, I need to match it with the static INSERT1, and BLAH2 match it with INSERT2, etc.
This seems simple enough, but her lies the problem...
It appears there are no Hashmap's in VBA without requiring external libraries, which I can't really rely on, since I can't install items on the machines where this will be running. As a result I can't store this reference data in a Hashmap as far as I can tell.
I can't seem to concatenate more than about 20 lines of strings together without hitting a max within VBA, and just parsing the chunk of text for what I need since there are about 1500 "lines" in my reference data, which greatly exceeds 20.
I also haven't found a way to embed a text, or any other type of file to hold this information within the file, and then parse the data.
I really would like to have everything within the single template file, without requiring additional text or other files to be bundled with the document. If there is no other option, I will go that route, but I wanted to see what create ideas people at Stackoverflow might have first ;-)
Have you considered using Word's Document Variables? They are name/value pairs stored invisibly within the document. (ActiveDocument.Variables("BLAH1").Value = "INSERT1" to create one, debug.print ActiveDocument.Variables("BLAH1").Value to retrieve a value (you have to use an error handler to detect non-existent indices if you go that route). Word can store (at least) hundreds of thousands of these things).
I'm filling in a Word template with data that's been collected from user input. In particular a (variable) number of documents is chosen, and information about each document fills a row of a table.
I've bookmarked several items in the template and successfully filled information in the header from my macro, but the table I'm not so sure with. I bookmarked the first cell and tried tabbing (with Chr(9)) through, and also tried passing an array. (In the template the table has only a first row. Usually tabbing past the last column creates an additional row.)
I can retieve cell contents with
Word.Application.ActiveDocument.Tables(1).Cell(3, 1).Range.Text
but can't write to the any cell except the first, where I placed a bookmark.
Can anyone offer a possible solution to populate the table?
To populate table, use this code
ActiveDocument.Tables(1).Cell(1, 1).Range.Text = "Blah Blah"
This will write to the first cell in the first table. Use a loop to fill the rest of the cells.
I would also recommend see this link.
Topic: Automating Word Tables for Data Insertion and Extraction
Link: http://msdn.microsoft.com/en-us/library/aa537149%28v=office.11%29.aspx#Y1254
Extract:
Summary: Learn how to automate the creation and formatting of tables in Word. Get information about optimizing performance, populating a table with data, formatting table structure, linking table data, and extracting data from a table. (25 printed pages)
I've actually ran into a similar problem using Access to automate filling out a Word table template. I found that if I opened the template in Word prior to running the VBA script, then the Word document is successfully filled out with the table information. My code looks similar to yours as far as adding to it by row. Because the number of fields to be transferred to the form is dynamic it didn't seem like bookmarks for each section would work. If you have any update, I'd be happy to hear of a different way to resolve this.