Creating many letters(mail merge) from a single template in C#

M

Mike9900

Hello,

How to create mail merge from a single word template? For example, the user
creates a template and adds MergeField from the word. But how to populate
these fields and create many documents, so the field names are different?
 
C

Cindy M -WordMVP-

Hi =?Utf-8?B?TWlrZTk5MDA=?=,
How to create mail merge from a single word template? For example, the user
creates a template and adds MergeField from the word. But how to populate
these fields and create many documents, so the field names are different?
I'm afraid I don't understand what you're asking; maybe because I'm steeped in
"traditional" mail merge and lack the angle you're viewing the problem from
:)

More specifically, it's the "so the field names are different" statement
that's throwing me.

The other part: populate the fields and create many documents, is simple
enough. I recommend you start in the Word UI, like an end-user, so that you
understand the process: the object model mirrors the end-user process.

Open the template. Tools/Letters and Mailings/Mail merge and display the mail
merge toolbar. (Note: I'm assuming Word 2002 or 2003 here. If you're using a
different version, please specify!)

At the left, you'll find a button for linking in a data source. Click it and
follow the steps to get the data you want to merge. Note that, if the data
fields in your data source don't match the mergefield inserted into the
document that you'll get a slew of prompts so that you can make the
substitutions. (This is NOT available in the object model!)

Now move to the right of the toolbar and merge into a new document to merge
all the records into the template.

At this point, we have a common ground on which to begin a discussion :), and
I can better understand any description of yours how the built-in
functionality does or does not meet your needs.

Cindy Meister
INTER-Solutions, Switzerland
http://homepage.swissonline.ch/cindymeister (last update Jun 8 2004)
http://www.word.mvps.org

This reply is posted in the Newsgroup; please post any follow question or
reply in the newsgroup and not by e-mail :)
 
M

Mike9900

I meant how to create mail merge from a template programmatically using C#.

We can create mail merge without using a template, but using a template is a
problem.
 
C

Cindy M -WordMVP-

Hi =?Utf-8?B?TWlrZTk5MDA=?=,
I meant how to create mail merge from a template programmatically using C#.

We can create mail merge without using a template, but using a template is a
problem.
Please explain WHY? You still haven't answered the concerns with your problem
description I stated in my first reply.

Taking your statement literally, it basically goes like this:
Word.Document doc = wdApp.Documents.Add(full path to template and all other
params here)
doc.MailMerge.OpenDataSource(all params here)
doc.MailMerge.Execute(params)

Cindy Meister
INTER-Solutions, Switzerland
http://homepage.swissonline.ch/cindymeister (last update Jun 8 2004)
http://www.word.mvps.org

This reply is posted in the Newsgroup; please post any follow question or reply
in the newsgroup and not by e-mail :)
 
M

Mike9900

Thank you, but I need to fill up the letters without using any datasource.
For example, I already have a list of names, it does not access any db. This
is typical because the user selects a list from the list and says to create
mail.
 
C

Cindy M -WordMVP-

Hi =?Utf-8?B?TWlrZTk5MDA=?=,
I need to fill up the letters without using any datasource.
For example, I already have a list of names, it does not access any db. This
is typical because the user selects a list from the list and says to create
mail.
If you don't have a data source, technically you can't use mail merge.

However, I understand that you and users decide to use the interface to insert
merge fields because it's there and one is familiar with it.

In this case, as a developer, you basically need to loop through all the fields
in the body of the document, extract the datafield name, look up the data and
insert it in place of the field.

Roughly, it would go like this (off the top of my head, so no guarantees on
the exact syntax):

Word.Document doc = WdApp.ActiveDocument
for each (Word.Field fld in doc.Fields)
{
if (fld.Type == wdApp.wdFieldType.wdFieldMergefield)
{
string sfldName = //Extract the field name, here, from the
fld.Code.Text
//Now look up the data
fld.Result.Text = "the data"
}
}

You'll need to look at the form fields the Word version your users have
generates in order to figure out how best to extract the information you need
for the field names.

Note that, because the data insertion could interfere with managing the Fields
collection, you might need to resort to a construct such as this, to loop all
the fields (VBA-speak):
For i = doc.Fields.Count to 0 Step -1

Cindy Meister
INTER-Solutions, Switzerland
http://homepage.swissonline.ch/cindymeister (last update Jun 8 2004)
http://www.word.mvps.org

This reply is posted in the Newsgroup; please post any follow question or reply
in the newsgroup and not by e-mail :)
 
M

Mike9900

Thanks for the help.

But I want to produce many of this letter, for example I have many
recipients. I can use for loop, but it does not work. My code is something
like this:

//Here fo 10 recipients generate 10 letters
for (int i = 0; i < 10; i++)
{
String company = "company " + i.ToString();
String address ="Address " + i.ToString();

foreach (Word.Field fld in doc.Fields)
{
if (fld.Type == Word.WdFieldType.wdFieldMergeField)
{
string sfldName = "";
if (fld.Result.Text == "«CompanyName»")
{
fld.Result.Text =company;
}
else if (fld.Result.Text ==
"«CompanyBusinessAddress»")
{
fld.Result.Text = address;
}
}
}
}

But this code does not produce 10 letters, only override the fields.
 
C

Cindy M -WordMVP-

Hi Mike,

For each repeat of the loop you must use the ADD method on the *.dot file to
create a new document. At the end of the loop you need to print the document
and save it (or close without saving to throw it away).

As I mentioned before: you cannot use the built-in mail merge functionality
without a data source. You have to "roll your own", which includes creating
each document for every record.
But I want to produce many of this letter, for example I have many
recipients. I can use for loop, but it does not work. My code is something
like this:

//Here fo 10 recipients generate 10 letters
for (int i = 0; i < 10; i++)
{
String company = "company " + i.ToString();
String address ="Address " + i.ToString();

foreach (Word.Field fld in doc.Fields)
{
if (fld.Type == Word.WdFieldType.wdFieldMergeField)
{
string sfldName = "";
if (fld.Result.Text == "«CompanyName»")
{
fld.Result.Text =company;
}
else if (fld.Result.Text ==
"«CompanyBusinessAddress»")
{
fld.Result.Text = address;
}
}
}
}

But this code does not produce 10 letters, only override the fields.

Cindy Meister
INTER-Solutions, Switzerland
http://homepage.swissonline.ch/cindymeister (last update Jun 8 2004)
http://www.word.mvps.org

This reply is posted in the Newsgroup; please post any follow question or
reply in the newsgroup and not by e-mail :)
 
M

Mike9900

Hello,

Thanks for your time.

Yes, but it creates a document for each recipient and this is not what is
desired.

I think there is a way to create a data source from the recipients, do you
know of any article that we can create text datasource, but not a db?
 
C

Cindy M -WordMVP-

Hi Mike,
Yes, but it creates a document for each recipient and this is not what is
desired.
In that case, you could use one of two possible approaches for the additional
"letters"

1. Insert/File (target range at the end of the document) to bring the text of
the template into the current file.

2. Save the template's content as an AutoText entry in the template, then
insert that AutoText entry.

For maintanence purposes, 1. is probably better.
I think there is a way to create a data source from the recipients, do you
know of any article that we can create text datasource, but not a db?
Mail merge can use a delimited text file as well as an HTML table as a data
source. Caveat: it must be saved to disk, in a "traditional" file path (URLs
are not recognized by mail merge). So all you need to do is serialize the
data in one of those two formats to disk. Since you haven't given any details
as to the form in which the data is held, I can't really be any more specific
than that.

Cindy Meister
INTER-Solutions, Switzerland
http://homepage.swissonline.ch/cindymeister (last update Jun 8 2004)
http://www.word.mvps.org

This reply is posted in the Newsgroup; please post any follow question or
reply in the newsgroup and not by e-mail :)
 
M

Mike9900

Thank Cindy.
--
Mike


Cindy M -WordMVP- said:
Hi Mike,

In that case, you could use one of two possible approaches for the additional
"letters"

1. Insert/File (target range at the end of the document) to bring the text of
the template into the current file.

2. Save the template's content as an AutoText entry in the template, then
insert that AutoText entry.

For maintanence purposes, 1. is probably better.

Mail merge can use a delimited text file as well as an HTML table as a data
source. Caveat: it must be saved to disk, in a "traditional" file path (URLs
are not recognized by mail merge). So all you need to do is serialize the
data in one of those two formats to disk. Since you haven't given any details
as to the form in which the data is held, I can't really be any more specific
than that.

Cindy Meister
INTER-Solutions, Switzerland
http://homepage.swissonline.ch/cindymeister (last update Jun 8 2004)


This reply is posted in the Newsgroup; please post any follow question or
reply in the newsgroup and not by e-mail :)
 
V

vanmuldersb

Hi Cindy,

I'm faced with a similar problem.
I'm still a student so consider me a n00b :)

(I'm working with Office 2007 and programming in VB.NET)
I also need to create mail merge starting from a template. This template is
completely generated in code.
Someone told me to use SmartTags, but in my opinion they're obsolete since i
only need to replace/insert text.
I've read about the merge fields in this discussion, is there any way i can
make my own in code to generate the template?
And then replace them with my own e.g. contactname when i'm creating the
..doc ?

Greets,
Ben
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top