NET Core导出word文档(表格循环插入)
本文以一个简单的小例子,简述利用C#语言开发word表格相关的知识,仅供学习分享使用,如有不足之处,还请指正。
在工程中引用word的动态库
在项目中,点击项目名称右键-->管理NuGet程序包,打开NuGet包管理器窗口,进行搜索下载即可,如下图所示:
涉及的知识点
- _Application: 表示word应用程序的接口,对应的实现类是Application类。
- _Document:表示一个word文档,通过_Application对应的文档接口进行创建。
- Paragraph:表示一个段落,通过_Document对象的相关方法进行创建。
- Table:表示一个表格,通过_Document对象的相关方法进行创建。
- Range:表示一个区域,可以是一个段落,也可以是一个表格,也可以是一个单元格,可以Range.select()将光标移动到当前区域。
- 移动焦点:wordApp.Selection.MoveDown(ref wdLine, ref ncount, ref oMissing);//移动焦点
Microsoft.Office.Interop.Word中涉及的知识点:
1、WdUnits枚举类型说明
wdCharacter |
1 |
字符。 |
wdCharacterFormatting |
13 |
字符格式。 |
wdColumn |
9 |
列。 |
wdItem |
16 |
所选项。 |
wdLine |
5 |
一个线段。 |
wdParagraph |
4 |
段落。 |
wdParagraphFormatting |
14 |
段落格式。 |
wdRow |
10 |
行。 |
wdScreen |
7 |
屏幕尺寸。 |
wdSection |
8 |
一节。 |
wdSentence |
3 |
句子。 |
wdStory |
6 |
部分。 |
wdTable |
15 |
一个表格。 |
wdWindow |
11 |
窗口。 |
wdWord |
2 |
字。 |
2、WdBuiltinStyle枚举类型说明
wdStyleBlockQuotation |
-85 |
文本块。 |
wdStyleBodyText |
-67 |
正文文本。 |
wdStyleBodyText2 |
-81 |
正文文本 2。 |
wdStyleBodyText3 |
-82 |
正文文本 3。 |
wdStyleBodyTextFirstIndent |
-78 |
正文首行缩进。 |
wdStyleBodyTextFirstIndent2 |
-79 |
正文首行缩进 2。 |
wdStyleBodyTextIndent |
-68 |
正文文本缩进。 |
wdStyleBodyTextIndent2 |
-83 |
正文文本缩进 2。 |
wdStyleBodyTextIndent3 |
-84 |
正文文本缩进 3。 |
wdStyleBookTitle |
-265 |
书籍标题。 |
wdStyleCaption |
-35 |
题注。 |
wdStyleClosing |
-64 |
结束语。 |
wdStyleCommentReference |
-40 |
批注引用。 |
wdStyleCommentText |
-31 |
批注文字。 |
wdStyleDate |
-77 |
日期。 |
wdStyleDefaultParagraphFont |
-66 |
默认段落字体。 |
wdStyleEmphasis |
-89 |
强调。 |
wdStyleEndnoteReference |
-43 |
尾注引用。 |
wdStyleEndnoteText |
-44 |
尾注文本。 |
wdStyleEnvelopeAddress |
-37 |
收信人地址。 |
wdStyleEnvelopeReturn |
-38 |
寄信人地址。 |
wdStyleFooter |
-33 |
页脚。 |
wdStyleFootnoteReference |
-39 |
脚注引用。 |
wdStyleFootnoteText |
-30 |
脚注文本。 |
wdStyleHeader |
-32 |
页眉。 |
wdStyleHeading1 |
-2 |
标题 1。 |
wdStyleHeading2 |
-3 |
标题 2。 |
wdStyleHeading3 |
-4 |
标题 3。 |
wdStyleHeading4 |
-5 |
标题 4。 |
wdStyleHeading5 |
-6 |
标题 5。 |
wdStyleHeading6 |
-7 |
标题 6。 |
wdStyleHeading7 |
-8 |
标题 7。 |
wdStyleHeading8 |
-9 |
标题 8。 |
wdStyleHeading9 |
-10 |
标题 9。 |
wdStyleHtmlAcronym |
-96 |
HTML 缩写。 |
wdStyleHtmlAddress |
-97 |
HTML 地址。 |
wdStyleHtmlCite |
-98 |
HTML 引文。 |
wdStyleHtmlCode |
-99 |
HTML 代码。 |
wdStyleHtmlDfn |
-100 |
HTML 定义。 |
wdStyleHtmlKbd |
-101 |
HTML 键盘。 |
wdStyleHtmlNormal |
-95 |
普通(网站)。 |
wdStyleHtmlPre |
-102 |
HTML 预设格式。 |
wdStyleHtmlSamp |
-103 |
HTML 样本。 |
wdStyleHtmlTt |
-104 |
HTML 打字机。 |
wdStyleHtmlVar |
-105 |
HTML 变量。 |
wdStyleHyperlink |
-86 |
超链接。 |
wdStyleHyperlinkFollowed |
-87 |
访问过的超链接。 |
wdStyleIndex1 |
-11 |
索引 1。 |
wdStyleIndex2 |
-12 |
索引 2。 |
wdStyleIndex3 |
-13 |
索引 3。 |
wdStyleIndex4 |
-14 |
索引 4。 |
wdStyleIndex5 |
-15 |
索引 5。 |
wdStyleIndex6 |
-16 |
索引 6。 |
wdStyleIndex7 |
-17 |
索引 7。 |
wdStyleIndex8 |
-18 |
索引 8。 |
wdStyleIndex9 |
-19 |
索引 9。 |
wdStyleIndexHeading |
-34 |
索引标题。 |
wdStyleIntenseEmphasis |
-262 |
明显强调。 |
wdStyleIntenseQuote |
-182 |
明显引用。 |
wdStyleIntenseReference |
-264 |
明显参考。 |
wdStyleLineNumber |
-41 |
行号。 |
wdStyleList |
-48 |
列表。 |
wdStyleList2 |
-51 |
列表 2。 |
wdStyleList3 |
-52 |
列表 3。 |
wdStyleList4 |
-53 |
列表 4。 |
wdStyleList5 |
-54 |
列表 5。 |
wdStyleListBullet |
-49 |
列表项目符号。 |
wdStyleListBullet2 |
-55 |
列表项目符号 2。 |
wdStyleListBullet3 |
-56 |
列表项目符号 3。 |
wdStyleListBullet4 |
-57 |
列表项目符号 4。 |
wdStyleListBullet5 |
-58 |
列表项目符号 5。 |
wdStyleListContinue |
-69 |
列表接续。 |
wdStyleListContinue2 |
-70 |
列表接续 2。 |
wdStyleListContinue3 |
-71 |
列表接续 3。 |
wdStyleListContinue4 |
-72 |
列表接续 4。 |
wdStyleListContinue5 |
-73 |
列表接续 5。 |
wdStyleListNumber |
-50 |
列表编号。 |
wdStyleListNumber2 |
-59 |
列表编号 2。 |
wdStyleListNumber3 |
-60 |
列表编号 3。 |
wdStyleListNumber4 |
-61 |
列表编号 4。 |
wdStyleListNumber5 |
-62 |
列表编号 5。 |
wdStyleListParagraph |
-180 |
列出段落。 |
wdStyleMacroText |
-46 |
宏文本。 |
wdStyleMessageHeader |
-74 |
信息标题。 |
wdStyleNavPane |
-90 |
文档结构图。 |
wdStyleNormal |
-1 |
正文。 |
wdStyleNormalIndent |
-29 |
正文缩进。 |
wdStyleNormalObject |
-158 |
正文(应用于对象)。 |
wdStyleNormalTable |
-106 |
正文(在表格中应用)。 |
wdStyleNoteHeading |
-80 |
注释标题。 |
wdStylePageNumber |
-42 |
页码。 |
wdStylePlainText |
-91 |
纯文本。 |
wdStyleQuote |
-181 |
引用。 |
wdStyleSalutation |
-76 |
称呼。 |
wdStyleSignature |
-65 |
签名。 |
wdStyleStrong |
-88 |
要点。 |
wdStyleSubtitle |
-75 |
副标题。 |
wdStyleSubtleEmphasis |
-261 |
不明显强调。 |
wdStyleSubtleReference |
-263 |
不明显参考。 |
wdStyleTableColorfulGrid |
-172 |
彩色网格。 |
wdStyleTableColorfulList |
-171 |
彩色列表。 |
wdStyleTableColorfulShading |
-170 |
彩色底纹。 |
wdStyleTableDarkList |
-169 |
深色列表。 |
wdStyleTableLightGrid |
-161 |
浅色网格。 |
wdStyleTableLightGridAccent1 |
-175 |
浅色网格强调文字颜色 1。 |
wdStyleTableLightList |
-160 |
浅色列表。 |
wdStyleTableLightListAccent1 |
-174 |
浅色列表强调文字颜色 1。 |
wdStyleTableLightShading |
-159 |
浅色底纹。 |
wdStyleTableLightShadingAccent1 |
-173 |
浅色底纹强调文字颜色 1。 |
wdStyleTableMediumGrid1 |
-166 |
中间色网格 1。 |
wdStyleTableMediumGrid2 |
-167 |
中间色网格 2。 |
wdStyleTableMediumGrid3 |
-168 |
中间色网格 3。 |
wdStyleTableMediumList1 |
-164 |
中间色列表 1。 |
wdStyleTableMediumList1Accent1 |
-178 |
中间色列表 1 强调文字颜色 1。 |
wdStyleTableMediumList2 |
-165 |
中间色列表 2。 |
wdStyleTableMediumShading1 |
-162 |
中间色底纹 1。 |
wdStyleTableMediumShading1Accent1 |
-176 |
中间色底纹 1 强调文字颜色 1。 |
wdStyleTableMediumShading2 |
-163 |
中间色底纹 2。 |
wdStyleTableMediumShading2Accent1 |
-177 |
中间色底纹 2 强调文字颜色 1。 |
wdStyleTableOfAuthorities |
-45 |
引文目录。 |
wdStyleTableOfFigures |
-36 |
图表目录。 |
wdStyleTitle |
-63 |
标题。 |
wdStyleTOAHeading |
-47 |
引文目录标题。 |
wdStyleTOC1 |
-20 |
目录 1。 |
wdStyleTOC2 |
-21 |
目录 2。 |
wdStyleTOC3 |
-22 |
目录 3。 |
wdStyleTOC4 |
-23 |
目录 4。 |
wdStyleTOC5 |
-24 |
目录 5。 |
wdStyleTOC6 |
-25 |
目录 6。 |
wdStyleTOC7 |
-26 |
目录 7。 |
wdStyleTOC8 |
-27 |
目录 8。 |
wdStyleTOC9 |
-28 |
目录 9。 |
3、_Application进程打开open()括号中的参数说明
表达式.打开 (FileName、ConfirmConversions、ReadOnly、AddToRecentFiles、PasswordDocument、PasswordTemplate、Revert、WritePasswordDocument、WritePasswordTemplate、Format、Encoding、Visible、OpenConflictDocument、OpenAndRepair、DocumentDirection、NoEncodingDialog)
名称 |
必需/可选 |
数据类型 |
说明 |
FileName |
必需 |
Variant |
文档名(可包含路径)。 |
ConfirmConversions |
可选 |
Variant |
True 显示 转换文件 对话框中,如果该文件不是 Microsoft Word 格式。 |
ReadOnly |
可选 |
Variant |
为 True,则以只读方式打开文档。 此参数不会覆盖已保存文档的只读推荐设置。 例如,如果在打开只读推荐设置的情况下保存文档,则将 ReadOnly 参数设置为 False 将不会导致文件以读/写方式打开。 |
AddToRecentFiles |
可选 |
Variant |
真 要将文件名添加到列表中最近使用的文件在 文件 菜单的底部。 |
PasswordDocument |
可选 |
Variant |
打开文档时所需的密码。 |
PasswordTemplate |
可选 |
Variant |
打开模板时所需的密码。 |
Revert |
可选 |
Variant |
控制如果 FileName 是打开文档的名称会进行什么操作。 为 True,则放弃对打开文档的任何未保存更改并重新打开文件。 为 False,则激活打开的文档。 |
WritePasswordDocument |
可选 |
Variant |
用于保存文档更改的密码。 |
WritePasswordTemplate |
可选 |
Variant |
用于保存模板更改的密码。 |
Format |
可选 |
Variant |
用于打开文档的文件转换器。 可为以下 WdOpenFormat 常量之一。 默认值为 wdOpenFormatAuto。 若要指定外部文件格式,请将 OpenFormat 属性应用于 FileConverter 对象,以确定要与此参数一起使用的值。 |
Encoding |
可选 |
Variant |
当你查看保存的文档时 Microsoft Word 所使用的文档编码(代码页或字符集)。 可以是任何有效的 MsoEncoding 常量。 要查看有效 MsoEncoding 常量的列表,请参阅“Visual Basic 编辑器”中的“对象浏览器”。 默认值是系统代码页。 |
Visible |
可选 |
Variant |
如此 如果在可见窗口中打开文档。 默认值为 True 。 |
OpenConflictDocument |
可选 |
Variant |
指定是否打开具有脱机冲突的文档的冲突文件。 |
OpenAndRepair |
可选 |
Variant |
如果该属性为 True ,则修复文档,以防止文档毁坏。 |
DocumentDirection |
可选 |
WdDocumentDirection |
表示文档中的横排文字。 默认值为 wdLeftToRight。 |
NoEncodingDialog |
可选 |
Variant |
为 True,如果无法识别文本编码,则跳过显示 Word 所显示的“编码”对话框。 默认值为 False。 |
4、Selection.MoveDown()方法中参数说明
Unit |
选用 |
WdUnits |
选取范围是要移动的单位。 默认值为 wdLine 。 |
Count |
选用 |
Variant |
移动选中项目的单位数。 默认值为 1。 |
Extend |
选用 |
Variant |
可以是 wdMove 或 wdExtend。 如果使用 wdMove ,则选取范围已折叠成结束点和向下移动。 如果使用 wdExtend 时,就会向下延伸选取项目。 默认值是 wdMove 。 |
5.Table表添加新表格
Add (Range, NumRows, NumColumns, DefaultTableBehavior, AutoFitBehavior)
Range |
必要 |
Range object |
要显示表的范围。如果范围未折叠,则该表将替换该区域。 |
NumRows |
必要 |
Long |
要包括在表中的行数。 |
NumColumns |
必要 |
Long |
要包括在表中的列数。 |
DefaultTableBehavior |
選用 |
Variant |
设置一个值,该值指定 Microsoft Word 是否自动调整表中单元格的大小以适合单元格的内容 (AutoFit)。可以是以下常量之一:wdWord8TableBehavior(已禁用 AutoFit)或 wdWord9TableBehavior(已启用 AutoFit)。默认常量为 wdWord8TableBehavior。 |
AutoFitBehavior |
選用 |
Variant |
设置 Word 大小如何调整表格的自动调整规则。可以是 WdAutoFitBehavior 常量之一。 |
5.WdLineStyle枚举说明
名称 |
值 |
说明 |
wdLineStyleDashDot |
5 |
划线后跟点。 |
wdLineStyleDashDotDot |
6 |
划线后跟两个点。 |
wdLineStyleDashDotStroked |
20 |
划线后跟粗点,使边框的外观类似于理发店招牌。 |
wdLineStyleDashLargeGap |
4 |
划线后跟大间隙。 |
wdLineStyleDashSmallGap |
3 |
划线后跟小间隙。 |
wdLineStyleDot |
2 |
点。 |
wdLineStyleDouble |
7 |
双实线。 |
wdLineStyleDoubleWavy |
19 |
波浪型双实线。 |
wdLineStyleEmboss3D |
21 |
边框看起来具有 3D 浮现外观。 |
wdLineStyleEngrave3D |
22 |
边框看起来具有 3D 阴文外观。 |
wdLineStyleInset |
24 |
边框呈现凹进效果。 |
wdLineStyleNone |
0 |
无边框。 |
wdLineStyleOutset |
23 |
边框呈现凸起效果。 |
wdLineStyleSingle |
1 |
单实线 |
wdLineStyleSingleWavy |
18 |
波浪型单实线。 |
wdLineStyleThickThinLargeGap |
16 |
里面是一条粗实线,外面是一条细实线,两条线的间隙较大。 |
wdLineStyleThickThinMedGap |
13 |
里面是一条粗实线,外面是一条细实线,两条线的间隙中等。 |
wdLineStyleThickThinSmallGap |
10 |
里面是一条粗实线,外面是一条细实线,两条线的间隙较小。 |
wdLineStyleThinThickLargeGap |
15 |
里面是一条细实线,外面是一条粗实线,两条线的间隙较大。 |
wdLineStyleThinThickMedGap |
12 |
里面是一条细实线,外面是一条粗实线,两条线的间隙中等。 |
wdLineStyleThinThickSmallGap |
9 |
里面是一条细实线,外面是一条粗实线,两条线的间隙较小。 |
wdLineStyleThinThickThinLargeGap |
17 |
最里面是一条细实线,其次是一条粗实线,最外面是一条细实线,所有线之间的间隙较大。 |
wdLineStyleThinThickThinMedGap |
14 |
最里面是一条细实线,其次是一条粗实线,最外面是一条细实线,所有线之间的间隙中等。 |
wdLineStyleThinThickThinSmallGap |
11 |
最里面一条细实线,其次一条粗实线,最外面是一条细实线,所有线之间的间隙较小。 |
wdLineStyleTriple |
8 |
三条细实线。 |
生成文档效果图
核心代码:
using Microsoft.Office.Interop.Word; using System; using System.Collections.Generic; using System.Data; using System.IO; using System.Linq; using System.Reflection; using System.Text; using System.Threading.Tasks; namespace ETWord { public class WordHelper { public static void CreateWordFile(string filePath) { try { CreateFile(filePath); // MessageFilter.Register(); object wdLine = WdUnits.wdLine;//一个线段 object oMissing = Missing.Value;//表示这个参数可以传入缺省值 object fileName = filePath; object heading2 = WdBuiltinStyle.wdStyleHeading2;//标题一 object heading3 = WdBuiltinStyle.wdStyleHeading3;//标题二 _Application wordApp = new Application();//创建一个word进程 wordApp.Visible = true;//word进程是否可见 _Document wordDoc = wordApp.Documents.Open(ref fileName, ref oMissing, ref oMissing, ref oMissing, ref oMissing, ref oMissing, ref oMissing, ref oMissing, ref oMissing, ref oMissing, ref oMissing, ref oMissing, ref oMissing, ref oMissing, ref oMissing, ref oMissing);//打开word进程 System.Data.DataTable dtDepts = DatabaseHelper.getDept();//获取大标题 int ii = 0; foreach (DataRow dr in dtDepts.Rows) { string dept = dr["dept"].ToString();//标题一 Paragraph oPara0 = wordDoc.Content.Paragraphs.Add(ref oMissing);//创建前三行表格 oPara0.Range.Text = string.Format("{0}-{1}", ii + 1, dept);//设置第二标题的序号 oPara0.Range.Select(); oPara0.set_Style(ref heading2);//设置样式 oPara0.Range.InsertParagraphAfter();//在范围之后插入段落标记 System.Data.DataTable dtTemplate = DatabaseHelper.getTemplateByDept(dept);//循环前三行 int jj = 0; foreach (DataRow dr1 in dtTemplate.Rows) { string template = dr1["template"].ToString();//创建模板时设置的 string user1 = dr1["user1"].ToString();//创建模板时设置的 string remark = dr1["remark"].ToString();//创建模板时设置的 System.Data.DataTable dtData = DatabaseHelper.getDataByDeptAndTemplate(dept, template);//获取数据 int count = dtData.Rows.Count;//获取集合中总数量 int row = count + 4;//行数 int column = 5; object ncount = 1; wordApp.Selection.MoveDown(ref wdLine, ref ncount, ref oMissing); wordApp.Selection.TypeParagraph();//插入一个新空白段落 Paragraph oPara1 = wordDoc.Content.Paragraphs.Add(ref oMissing);//创建第二个表格 oPara1.Range.Select(); oPara1.Range.Text = string.Format("{0}-{1}、{2}", ii + 1, jj + 1, template);//标题二 //oPara1.Range.Font.Bold = 1; //oPara1.Format.SpaceAfter = 5; oPara1.set_Style(ref heading3);//设置样式 oPara1.Range.InsertParagraphAfter();//在范围之后插入段落标记 wordApp.Selection.MoveDown(ref wdLine, ref ncount, ref oMissing); wordApp.Selection.TypeParagraph();//插入一个新空白段落 //设置表格 Table table = wordDoc.Tables.Add(wordApp.Selection.Range, row, column, ref oMissing, ref oMissing);//创建新表格 table.Borders.OutsideLineStyle = WdLineStyle.wdLineStyleSingle;//外边框单实线 table.Borders.InsideLineStyle = WdLineStyle.wdLineStyleSingle;//内边框单实线 table.Range.Font.Bold = 0;//字体粗细 table.PreferredWidthType = WdPreferredWidthType.wdPreferredWidthAuto;//设置表格宽度,基于当前所选内容自动选择要使用的度量单位。 table.Columns[1].Width = 60f; table.Columns[2].Width = 100f; table.Columns[3].Width = 100f; table.Columns[4].Width = 60f; table.Columns[5].Width = 100f; //列的合并 Cell cell = table.Cell(1, 2); cell.Merge(table.Cell(1, 5)); Cell cell2 = table.Cell(2, 2); cell2.Merge(table.Cell(2, 5)); Cell cell3 = table.Cell(3, 2); cell3.Merge(table.Cell(3, 5)); //赋值 table.Cell(1, 1).Range.Text = "流程名称:"; table.Cell(2, 1).Range.Text = "使用人:"; table.Cell(3, 1).Range.Text = "流程说明:"; table.Cell(4, 1).Range.Text = "节点"; table.Cell(4, 2).Range.Text = "节点名"; table.Cell(4, 3).Range.Text = "处理人员"; table.Cell(4, 4).Range.Text = "处理方式"; table.Cell(4, 5).Range.Text = "跳转信息"; table.Cell(1, 2).Range.Text = template;//把值赋给第一行第二列表格 table.Cell(2, 2).Range.Text = user1;//把值赋给第二行第二列表格 table.Cell(3, 2).Range.Text = remark;//把值赋给第三行第二列表格 int kk = 5; foreach (DataRow dr2 in dtData.Rows) { table.Cell(kk, 1).Range.Text = (kk - 4).ToString(); table.Cell(kk, 2).Range.Text = dr2["NodeName"].ToString(); table.Cell(kk, 3).Range.Text = dr2["DoName"].ToString(); table.Cell(kk, 4).Range.Text = dr2["DoType"].ToString(); table.Cell(kk, 5).Range.Text = string.Empty; kk++; } table.Cell(kk - 1, 5).Range.Select(); wordApp.Selection.MoveDown(ref wdLine, ref ncount, ref oMissing);//移动焦点 wordApp.Selection.TypeParagraph();//插入段落 jj++; } ii++; } //保存文档 wordDoc.Save(); wordDoc.Close(ref oMissing, ref oMissing, ref oMissing); wordApp.Quit(ref oMissing, ref oMissing, ref oMissing); MessageFilter.Revoke(); } catch (Exception e) { Console.WriteLine(e.Message); Console.WriteLine(e.StackTrace); } } private static void CreateFile(string filePath) { if (!File.Exists(filePath)) { using (FileStream fs = File.Create(filePath)) { } } } } }
操作数据库,模板的方法类:
using System; using System.Collections.Generic; using System.Data; using System.Linq; using System.Text; using System.Threading.Tasks; namespace ETWord { public class DatabaseHelper { /// <summary> /// 获取部门 /// </summary> /// <returns></returns> public static DataTable getDept() { DataTable dt = new DataTable(); dt.Columns.Add("dept"); for (int i = 0; i < 5; i++) { DataRow dr = dt.NewRow(); dr["dept"] = string.Format("部门_{0}_T", i + 1); dt.Rows.Add(dr); } return dt; } /// <summary> /// 获取模板 /// </summary> /// <param name="dept"></param> /// <returns></returns> public static DataTable getTemplateByDept(string dept) { DataTable dt = new DataTable(); dt.Columns.Add("template"); dt.Columns.Add("user1"); dt.Columns.Add("remark"); for (int i = 0; i < 5; i++) { DataRow dr = dt.NewRow(); dr["template"] = string.Format("小组_{0}_A_{1}", i + 1,dept); dr["user1"] = string.Format("B_{0}_B_{1}", i + 1, dept); dr["remark"] = string.Format("C_{0}_C_{1}", i + 1, dept); dt.Rows.Add(dr); } return dt; } /// <summary> /// 获取数据 /// </summary> /// <param name="dept"></param> /// <param name="template"></param> /// <returns></returns> public static DataTable getDataByDeptAndTemplate(string dept, string template) { DataTable dt = new DataTable(); dt.Columns.Add("NodeName"); dt.Columns.Add("DoName"); dt.Columns.Add("DoType"); for (int i = 0; i < 5; i++) { DataRow dr = dt.NewRow(); dr["NodeName"] = string.Format("AA_{0}_{1}", i,template); dr["DoName"] = string.Format("BB_{0}", i); dr["DoType"] = string.Format("CC_{0}", i); dt.Rows.Add(dr); } return dt; } } }
using System; using System.Collections.Generic; using System.Linq; using System.Runtime.InteropServices; using System.Text; using System.Threading.Tasks; namespace ETWord { public class MessageFilter : IOleMessageFilter { // // Class containing the IOleMessageFilter // thread error-handling functions. // Start the filter. public static void Register() { IOleMessageFilter newFilter = new MessageFilter(); IOleMessageFilter oldFilter = null; CoRegisterMessageFilter(newFilter, out oldFilter); } // Done with the filter, close it. public static void Revoke() { IOleMessageFilter oldFilter = null; CoRegisterMessageFilter(null, out oldFilter); } // // IOleMessageFilter functions. // Handle incoming thread requests. int IOleMessageFilter.HandleInComingCall(int dwCallType, IntPtr hTaskCaller, int dwTickCount, IntPtr lpInterfaceInfo) { //Return the flag SERVERCALL_ISHANDLED. return 0; } // Thread call was rejected, so try again. int IOleMessageFilter.RetryRejectedCall(IntPtr hTaskCallee, int dwTickCount, int dwRejectType) { if (dwRejectType == 2) // flag = SERVERCALL_RETRYLATER. { // Retry the thread call immediately if return >=0 & // <100. return 99; } // Too busy; cancel call. return -1; } int IOleMessageFilter.MessagePending(System.IntPtr hTaskCallee, int dwTickCount, int dwPendingType) { //Return the flag PENDINGMSG_WAITDEFPROCESS. return 2; } // Implement the IOleMessageFilter interface. [DllImport("Ole32.dll")] private static extern int CoRegisterMessageFilter(IOleMessageFilter newFilter, out IOleMessageFilter oldFilter); } [ComImport(), Guid("00000016-0000-0000-C000-000000000046"), InterfaceTypeAttribute(ComInterfaceType.InterfaceIsIUnknown)] interface IOleMessageFilter { [PreserveSig] int HandleInComingCall(int dwCallType, IntPtr hTaskCaller, int dwTickCount, IntPtr lpInterfaceInfo); [PreserveSig] int RetryRejectedCall(IntPtr hTaskCallee, int dwTickCount, int dwRejectType); [PreserveSig] int MessagePending(IntPtr hTaskCallee, int dwTickCount, int dwPendingType); } }