You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289
  1. using System;
  2. using System.Collections.Generic;
  3. using System.Linq;
  4. using System.Text;
  5. using System.Xml.Linq;
  6. using Novacode;
  7. using System.IO.Packaging;
  8. using System.IO;
  9. using System.Reflection;
  10. namespace Novacode
  11. {
  12. /// <summary>
  13. /// Designs\Styles that can be applied to a table.
  14. /// </summary>
  15. public enum TableDesign { TableNormal, TableGrid, LightShading, LightShadingAccent1, LightShadingAccent2, LightShadingAccent3, LightShadingAccent4, LightShadingAccent5, LightShadingAccent6, LightList, LightListAccent1, LightListAccent2, LightListAccent3, LightListAccent4, LightListAccent5, LightListAccent6, LightGrid, LightGridAccent1, LightGridAccent2, LightGridAccent3, LightGridAccent4, LightGridAccent5, LightGridAccent6, MediumShading1, MediumShading1Accent1, MediumShading1Accent2, MediumShading1Accent3, MediumShading1Accent4, MediumShading1Accent5, MediumShading1Accent6, MediumShading2, MediumShading2Accent1, MediumShading2Accent2, MediumShading2Accent3, MediumShading2Accent4, MediumShading2Accent5, MediumShading2Accent6, MediumList1, MediumList1Accent1, MediumList1Accent2, MediumList1Accent3, MediumList1Accent4, MediumList1Accent5, MediumList1Accent6, MediumList2, MediumList2Accent1, MediumList2Accent2, MediumList2Accent3, MediumList2Accent4, MediumList2Accent5, MediumList2Accent6, MediumGrid1, MediumGrid1Accent1, MediumGrid1Accent2, MediumGrid1Accent3, MediumGrid1Accent4, MediumGrid1Accent5, MediumGrid1Accent6, MediumGrid2, MediumGrid2Accent1, MediumGrid2Accent2, MediumGrid2Accent3, MediumGrid2Accent4, MediumGrid2Accent5, MediumGrid2Accent6, MediumGrid3, MediumGrid3Accent1, MediumGrid3Accent2, MediumGrid3Accent3, MediumGrid3Accent4, MediumGrid3Accent5, MediumGrid3Accent6, DarkList, DarkListAccent1, DarkListAccent2, DarkListAccent3, DarkListAccent4, DarkListAccent5, DarkListAccent6, ColorfulShading, ColorfulShadingAccent1, ColorfulShadingAccent2, ColorfulShadingAccent3, ColorfulShadingAccent4, ColorfulShadingAccent5, ColorfulShadingAccent6, ColorfulList, ColorfulListAccent1, ColorfulListAccent2, ColorfulListAccent3, ColorfulListAccent4, ColorfulListAccent5, ColorfulListAccent6, ColorfulGrid, ColorfulGridAccent1, ColorfulGridAccent2, ColorfulGridAccent3, ColorfulGridAccent4, ColorfulGridAccent5, ColorfulGridAccent6, None};
  16. public enum AutoFit{Contents, Window, ColoumnWidth};
  17. /// <summary>
  18. /// Represents a Table in a document.
  19. /// </summary>
  20. public class Table
  21. {
  22. private Alignment alignment;
  23. private AutoFit autofit;
  24. private List<Row> rows;
  25. private int rowCount, columnCount;
  26. internal XElement xml;
  27. /// <summary>
  28. /// Returns the number of rows in this table.
  29. /// </summary>
  30. public int RowCount { get { return rowCount; } }
  31. /// <summary>
  32. /// Returns the number of coloumns in this table.
  33. /// </summary>
  34. public int ColumnCount { get { return columnCount; } }
  35. /// <summary>
  36. /// Returns a list of rows in this table.
  37. /// </summary>
  38. public List<Row> Rows { get { return rows; } }
  39. DocX document;
  40. private TableDesign design;
  41. internal Table(DocX document, XElement xml)
  42. {
  43. autofit = AutoFit.ColoumnWidth;
  44. this.xml = xml;
  45. this.document = document;
  46. XElement properties = xml.Element(XName.Get("tblPr", DocX.w.NamespaceName));
  47. rows = (from r in xml.Elements(XName.Get("tr", DocX.w.NamespaceName))
  48. select new Row(document, r)).ToList();
  49. rowCount = rows.Count;
  50. if (rows.Count > 0)
  51. if (rows[0].Cells.Count > 0)
  52. columnCount = rows[0].Cells.Count;
  53. XElement style = properties.Element(XName.Get("tblStyle", DocX.w.NamespaceName));
  54. if (style != null)
  55. {
  56. XAttribute val = style.Attribute(XName.Get("val", DocX.w.NamespaceName));
  57. if (val != null)
  58. design = (TableDesign)Enum.Parse(typeof(TableDesign), val.Value.Replace("-", string.Empty));
  59. else
  60. design = TableDesign.None;
  61. }
  62. else
  63. design = TableDesign.None;
  64. }
  65. public Alignment Alignment
  66. {
  67. get { return alignment; }
  68. set
  69. {
  70. string alignmentString = string.Empty;
  71. switch (value)
  72. {
  73. case Alignment.left:
  74. {
  75. alignmentString = "left";
  76. break;
  77. }
  78. case Alignment.both:
  79. {
  80. alignmentString = "both";
  81. break;
  82. }
  83. case Alignment.right:
  84. {
  85. alignmentString = "right";
  86. break;
  87. }
  88. case Alignment.center:
  89. {
  90. alignmentString = "center";
  91. break;
  92. }
  93. }
  94. XElement tblPr = xml.Descendants(XName.Get("tblPr", DocX.w.NamespaceName)).First();
  95. XElement jc = tblPr.Descendants(XName.Get("jc", DocX.w.NamespaceName)).FirstOrDefault();
  96. if(jc != null)
  97. jc.Remove();
  98. jc = new XElement(XName.Get("jc", DocX.w.NamespaceName), new XAttribute(XName.Get("val", DocX.w.NamespaceName), alignmentString));
  99. tblPr.Add(jc);
  100. alignment = value;
  101. }
  102. }
  103. /// <summary>
  104. /// Auto size this table according to some rule.
  105. /// </summary>
  106. public AutoFit AutoFit
  107. {
  108. get{return autofit;}
  109. set
  110. {
  111. string attributeValue = string.Empty;
  112. switch(value)
  113. {
  114. case AutoFit.ColoumnWidth:
  115. {
  116. attributeValue = "dxa";
  117. break;
  118. }
  119. case AutoFit.Contents:
  120. {
  121. attributeValue = "auto";
  122. break;
  123. }
  124. case AutoFit.Window:
  125. {
  126. attributeValue = "pct";
  127. break;
  128. }
  129. }
  130. var query = from d in xml.Descendants()
  131. let type = d.Attribute(XName.Get("type", DocX.w.NamespaceName))
  132. where (d.Name.LocalName == "tcW" || d.Name.LocalName == "tblW") && type != null
  133. select type;
  134. foreach (XAttribute type in query)
  135. type.Value = attributeValue;
  136. autofit = value;
  137. }
  138. }
  139. /// <summary>
  140. /// The design\style to apply to this table.
  141. /// </summary>
  142. public TableDesign Design
  143. {
  144. get { return design; }
  145. set
  146. {
  147. XElement tblPr = xml.Element(XName.Get("tblPr", DocX.w.NamespaceName));
  148. XElement style = tblPr.Element(XName.Get("tblStyle", DocX.w.NamespaceName));
  149. if (style == null)
  150. {
  151. tblPr.Add(new XElement(XName.Get("tblStyle", DocX.w.NamespaceName)));
  152. style = tblPr.Element(XName.Get("tblStyle", DocX.w.NamespaceName));
  153. }
  154. XAttribute val = style.Attribute(XName.Get("val", DocX.w.NamespaceName));
  155. if(val == null)
  156. {
  157. style.Add(new XAttribute(XName.Get("val", DocX.w.NamespaceName), ""));
  158. val = style.Attribute(XName.Get("val", DocX.w.NamespaceName));
  159. }
  160. design = value;
  161. if (design == TableDesign.None)
  162. {
  163. if (style != null)
  164. style.Remove();
  165. }
  166. switch (design)
  167. {
  168. case TableDesign.TableNormal: val.Value = "TableNormal"; break;
  169. case TableDesign.TableGrid: val.Value = "TableGrid"; break;
  170. case TableDesign.LightShading: val.Value = "LightShading"; break;
  171. case TableDesign.LightShadingAccent1: val.Value = "LightShading-Accent1"; break;
  172. case TableDesign.LightShadingAccent2: val.Value = "LightShading-Accent2"; break;
  173. case TableDesign.LightShadingAccent3: val.Value = "LightShading-Accent3"; break;
  174. case TableDesign.LightShadingAccent4: val.Value = "LightShading-Accent4"; break;
  175. case TableDesign.LightShadingAccent5: val.Value = "LightShading-Accent5"; break;
  176. case TableDesign.LightShadingAccent6: val.Value = "LightShading-Accent6"; break;
  177. case TableDesign.LightList: val.Value = "LightList"; break;
  178. case TableDesign.LightListAccent1: val.Value = "LightList-Accent1"; break;
  179. case TableDesign.LightListAccent2: val.Value = "LightList-Accent2"; break;
  180. case TableDesign.LightListAccent3: val.Value = "LightList-Accent3"; break;
  181. case TableDesign.LightListAccent4: val.Value = "LightList-Accent4"; break;
  182. case TableDesign.LightListAccent5: val.Value = "LightList-Accent5"; break;
  183. case TableDesign.LightListAccent6: val.Value = "LightList-Accent6"; break;
  184. case TableDesign.LightGrid: val.Value = "LightGrid"; break;
  185. case TableDesign.LightGridAccent1: val.Value = "LightGrid-Accent1"; break;
  186. case TableDesign.LightGridAccent2: val.Value = "LightGrid-Accent2"; break;
  187. case TableDesign.LightGridAccent3: val.Value = "LightGrid-Accent3"; break;
  188. case TableDesign.LightGridAccent4: val.Value = "LightGrid-Accent4"; break;
  189. case TableDesign.LightGridAccent5: val.Value = "LightGrid-Accent5"; break;
  190. case TableDesign.LightGridAccent6: val.Value = "LightGrid-Accent6"; break;
  191. case TableDesign.MediumShading1: val.Value = "MediumShading1"; break;
  192. case TableDesign.MediumShading1Accent1: val.Value = "MediumShading1-Accent1"; break;
  193. case TableDesign.MediumShading1Accent2: val.Value = "MediumShading1-Accent2"; break;
  194. case TableDesign.MediumShading1Accent3: val.Value = "MediumShading1-Accent3"; break;
  195. case TableDesign.MediumShading1Accent4: val.Value = "MediumShading1-Accent4"; break;
  196. case TableDesign.MediumShading1Accent5: val.Value = "MediumShading1-Accent5"; break;
  197. case TableDesign.MediumShading1Accent6: val.Value = "MediumShading1-Accent6"; break;
  198. case TableDesign.MediumShading2: val.Value = "MediumShading2"; break;
  199. case TableDesign.MediumShading2Accent1: val.Value = "MediumShading2-Accent1"; break;
  200. case TableDesign.MediumShading2Accent2: val.Value = "MediumShading2-Accent2"; break;
  201. case TableDesign.MediumShading2Accent3: val.Value = "MediumShading2-Accent3"; break;
  202. case TableDesign.MediumShading2Accent4: val.Value = "MediumShading2-Accent4"; break;
  203. case TableDesign.MediumShading2Accent5: val.Value = "MediumShading2-Accent5"; break;
  204. case TableDesign.MediumShading2Accent6: val.Value = "MediumShading2-Accent6"; break;
  205. case TableDesign.MediumList1: val.Value = "MediumList1"; break;
  206. case TableDesign.MediumList1Accent1: val.Value = "MediumList1-Accent1"; break;
  207. case TableDesign.MediumList1Accent2: val.Value = "MediumList1-Accent2"; break;
  208. case TableDesign.MediumList1Accent3: val.Value = "MediumList1-Accent3"; break;
  209. case TableDesign.MediumList1Accent4: val.Value = "MediumList1-Accent4"; break;
  210. case TableDesign.MediumList1Accent5: val.Value = "MediumList1-Accent5"; break;
  211. case TableDesign.MediumList1Accent6: val.Value = "MediumList1-Accent6"; break;
  212. case TableDesign.MediumList2: val.Value = "MediumList2"; break;
  213. case TableDesign.MediumList2Accent1: val.Value = "MediumList2-Accent1"; break;
  214. case TableDesign.MediumList2Accent2: val.Value = "MediumList2-Accent2"; break;
  215. case TableDesign.MediumList2Accent3: val.Value = "MediumList2-Accent3"; break;
  216. case TableDesign.MediumList2Accent4: val.Value = "MediumList2-Accent4"; break;
  217. case TableDesign.MediumList2Accent5: val.Value = "MediumList2-Accent5"; break;
  218. case TableDesign.MediumList2Accent6: val.Value = "MediumList2-Accent6"; break;
  219. case TableDesign.MediumGrid1: val.Value = "MediumGrid1"; break;
  220. case TableDesign.MediumGrid1Accent1: val.Value = "MediumGrid1-Accent1"; break;
  221. case TableDesign.MediumGrid1Accent2: val.Value = "MediumGrid1-Accent2"; break;
  222. case TableDesign.MediumGrid1Accent3: val.Value = "MediumGrid1-Accent3"; break;
  223. case TableDesign.MediumGrid1Accent4: val.Value = "MediumGrid1-Accent4"; break;
  224. case TableDesign.MediumGrid1Accent5: val.Value = "MediumGrid1-Accent5"; break;
  225. case TableDesign.MediumGrid1Accent6: val.Value = "MediumGrid1-Accent6"; break;
  226. case TableDesign.MediumGrid2: val.Value = "MediumGrid2"; break;
  227. case TableDesign.MediumGrid2Accent1: val.Value = "MediumGrid2-Accent1"; break;
  228. case TableDesign.MediumGrid2Accent2: val.Value = "MediumGrid2-Accent2"; break;
  229. case TableDesign.MediumGrid2Accent3: val.Value = "MediumGrid2-Accent3"; break;
  230. case TableDesign.MediumGrid2Accent4: val.Value = "MediumGrid2-Accent4"; break;
  231. case TableDesign.MediumGrid2Accent5: val.Value = "MediumGrid2-Accent5"; break;
  232. case TableDesign.MediumGrid2Accent6: val.Value = "MediumGrid2-Accent6"; break;
  233. case TableDesign.MediumGrid3: val.Value = "MediumGrid3"; break;
  234. case TableDesign.MediumGrid3Accent1: val.Value = "MediumGrid3-Accent1"; break;
  235. case TableDesign.MediumGrid3Accent2: val.Value = "MediumGrid3-Accent2"; break;
  236. case TableDesign.MediumGrid3Accent3: val.Value = "MediumGrid3-Accent3"; break;
  237. case TableDesign.MediumGrid3Accent4: val.Value = "MediumGrid3-Accent4"; break;
  238. case TableDesign.MediumGrid3Accent5: val.Value = "MediumGrid3-Accent5"; break;
  239. case TableDesign.MediumGrid3Accent6: val.Value = "MediumGrid3-Accent6"; break;
  240. case TableDesign.DarkList: val.Value = "DarkList"; break;
  241. case TableDesign.DarkListAccent1: val.Value = "DarkList-Accent1"; break;
  242. case TableDesign.DarkListAccent2: val.Value = "DarkList-Accent2"; break;
  243. case TableDesign.DarkListAccent3: val.Value = "DarkList-Accent3"; break;
  244. case TableDesign.DarkListAccent4: val.Value = "DarkList-Accent4"; break;
  245. case TableDesign.DarkListAccent5: val.Value = "DarkList-Accent5"; break;
  246. case TableDesign.DarkListAccent6: val.Value = "DarkList-Accent6"; break;
  247. case TableDesign.ColorfulShading: val.Value = "ColorfulShading"; break;
  248. case TableDesign.ColorfulShadingAccent1: val.Value = "ColorfulShading-Accent1"; break;
  249. case TableDesign.ColorfulShadingAccent2: val.Value = "ColorfulShading-Accent2"; break;
  250. case TableDesign.ColorfulShadingAccent3: val.Value = "ColorfulShading-Accent3"; break;
  251. case TableDesign.ColorfulShadingAccent4: val.Value = "ColorfulShading-Accent4"; break;
  252. case TableDesign.ColorfulShadingAccent5: val.Value = "ColorfulShading-Accent5"; break;
  253. case TableDesign.ColorfulShadingAccent6: val.Value = "ColorfulShading-Accent6"; break;
  254. case TableDesign.ColorfulList: val.Value = "ColorfulList"; break;
  255. case TableDesign.ColorfulListAccent1: val.Value = "ColorfulList-Accent1"; break;
  256. case TableDesign.ColorfulListAccent2: val.Value = "ColorfulList-Accent2"; break;
  257. case TableDesign.ColorfulListAccent3: val.Value = "ColorfulList-Accent3"; break;
  258. case TableDesign.ColorfulListAccent4: val.Value = "ColorfulList-Accent4"; break;
  259. case TableDesign.ColorfulListAccent5: val.Value = "ColorfulList-Accent5"; break;
  260. case TableDesign.ColorfulListAccent6: val.Value = "ColorfulList-Accent6"; break;
  261. case TableDesign.ColorfulGrid: val.Value = "ColorfulGrid"; break;
  262. case TableDesign.ColorfulGridAccent1: val.Value = "ColorfulGrid-Accent1"; break;
  263. case TableDesign.ColorfulGridAccent2: val.Value = "ColorfulGrid-Accent2"; break;
  264. case TableDesign.ColorfulGridAccent3: val.Value = "ColorfulGrid-Accent3"; break;
  265. case TableDesign.ColorfulGridAccent4: val.Value = "ColorfulGrid-Accent4"; break;
  266. case TableDesign.ColorfulGridAccent5: val.Value = "ColorfulGrid-Accent5"; break;
  267. case TableDesign.ColorfulGridAccent6: val.Value = "ColorfulGrid-Accent6"; break;
  268. default: break;
  269. }
  270. XDocument style_doc;
  271. PackagePart word_styles = document.package.GetPart(new Uri("/word/styles.xml", UriKind.Relative));
  272. using (TextReader tr = new StreamReader(word_styles.GetStream()))
  273. style_doc = XDocument.Load(tr);
  274. var tableStyle =
  275. (
  276. from e in style_doc.Descendants()
  277. let styleId = e.Attribute(XName.Get("styleId", DocX.w.NamespaceName))
  278. where (styleId != null && styleId.Value == val.Value)
  279. select e
  280. ).FirstOrDefault();
  281. if (tableStyle == null)
  282. {
  283. XDocument external_style_doc = DocX.DecompressXMLResource("Novacode.Resources.styles.xml.gz");
  284. var styleElement =
  285. (
  286. from e in external_style_doc.Descendants()
  287. let styleId = e.Attribute(XName.Get("styleId", DocX.w.NamespaceName))
  288. where (styleId != null && styleId.Value == val.Value)
  289. select e
  290. ).First();
  291. style_doc.Element(XName.Get("styles", DocX.w.NamespaceName)).Add(styleElement);
  292. using (TextWriter tw = new StreamWriter(word_styles.GetStream(FileMode.Create)))
  293. style_doc.Save(tw, SaveOptions.None);
  294. }
  295. }
  296. }
  297. /// <summary>
  298. /// Insert a row at the end of this table.
  299. /// </summary>
  300. /// <example>
  301. /// <code>
  302. /// // Load a document.
  303. /// using (DocX document = DocX.Load(@"C:\Example\Test.docx"))
  304. /// {
  305. /// // Get the first table in this document.
  306. /// Table table = document.Tables[0];
  307. ///
  308. /// // Insert a new row at the end of this table.
  309. /// Row row = table.InsertRow();
  310. ///
  311. /// // Loop through each cell in this new row.
  312. /// foreach (Cell c in row.Cells)
  313. /// {
  314. /// // Set the text of each new cell to "Hello".
  315. /// c.Paragraph.InsertText("Hello", false);
  316. /// }
  317. ///
  318. /// // Save the document to a new file.
  319. /// document.SaveAs(@"C:\Example\Test2.docx");
  320. /// }// Release this document from memory.
  321. /// </code>
  322. /// </example>
  323. /// <returns>A new row.</returns>
  324. public Row InsertRow()
  325. {
  326. return InsertRow(rows.Count);
  327. }
  328. /// <summary>
  329. /// Returns the index of this Table.
  330. /// </summary>
  331. /// <example>
  332. /// Replace the first table in this document with a new Table.
  333. /// <code>
  334. /// // Load a document into memory.
  335. /// using (DocX document = DocX.Load(@"Test.docx"))
  336. /// {
  337. /// // Get the first Table in this document.
  338. /// Table t = document.Tables[0];
  339. ///
  340. /// // Get the character index of Table t in this document.
  341. /// int index = t.Index;
  342. ///
  343. /// // Remove Table t.
  344. /// t.Remove();
  345. ///
  346. /// // Insert a new Table at the original index of Table t.
  347. /// Table newTable = document.InsertTable(index, 4, 4);
  348. ///
  349. /// // Set the design of this new Table, so that we can see it.
  350. /// newTable.Design = TableDesign.LightShadingAccent1;
  351. ///
  352. /// // Save all changes made to the document.
  353. /// document.Save();
  354. /// } // Release this document from memory.
  355. /// </code>
  356. /// </example>
  357. public int Index
  358. {
  359. get
  360. {
  361. int index = 0;
  362. IEnumerable<XElement> previous = xml.ElementsBeforeSelf();
  363. foreach (XElement e in previous)
  364. index += Paragraph.GetElementTextLength(e);
  365. return index;
  366. }
  367. }
  368. /// <summary>
  369. /// Remove this Table from this document.
  370. /// </summary>
  371. /// <example>
  372. /// Remove the first Table from this document.
  373. /// <code>
  374. /// // Load a document into memory.
  375. /// using (DocX document = DocX.Load(@"Test.docx"))
  376. /// {
  377. /// // Get the first Table in this document.
  378. /// Table t = d.Tables[0];
  379. ///
  380. /// // Remove this Table.
  381. /// t.Remove();
  382. ///
  383. /// // Save all changes made to the document.
  384. /// document.Save();
  385. /// } // Release this document from memory.
  386. /// </code>
  387. /// </example>
  388. public void Remove()
  389. {
  390. xml.Remove();
  391. }
  392. /// <summary>
  393. /// Insert a column to the right of a Table.
  394. /// </summary>
  395. /// <example>
  396. /// <code>
  397. /// // Load a document.
  398. /// using (DocX document = DocX.Load(@"C:\Example\Test.docx"))
  399. /// {
  400. /// // Get the first Table in this document.
  401. /// Table table = document.Tables[0];
  402. ///
  403. /// // Insert a new column to this right of this table.
  404. /// table.InsertColumn();
  405. ///
  406. /// // Set the new coloumns text to "Row no."
  407. /// table.Rows[0].Cells[table.ColumnCount - 1].Paragraph.InsertText("Row no.", false);
  408. ///
  409. /// // Loop through each row in the table.
  410. /// for (int i = 1; i &lt; table.Rows.Count; i++)
  411. /// {
  412. /// // The current row.
  413. /// Row row = table.Rows[i];
  414. ///
  415. /// // The cell in this row that belongs to the new coloumn.
  416. /// Cell cell = row.Cells[table.ColumnCount - 1];
  417. ///
  418. /// // The Paragraph that this cell houses.
  419. /// Paragraph p = cell.Paragraph;
  420. ///
  421. /// // Insert this rows index.
  422. /// p.InsertText(i.ToString(), false);
  423. /// }
  424. ///
  425. /// document.Save();
  426. /// }// Release this document from memory.
  427. /// </code>
  428. /// </example>
  429. public void InsertColumn()
  430. {
  431. InsertColumn(columnCount);
  432. }
  433. /// <summary>
  434. /// Remove the last row from this Table.
  435. /// </summary>
  436. /// <example>
  437. /// Remove the last row from a Table.
  438. /// <code>
  439. /// // Load a document.
  440. /// using (DocX document = DocX.Load(@"C:\Example\Test.docx"))
  441. /// {
  442. /// // Get the first table in this document.
  443. /// Table table = document.Tables[0];
  444. ///
  445. /// // Remove the last row from this table.
  446. /// table.RemoveRow();
  447. ///
  448. /// // Save the document.
  449. /// document.Save();
  450. /// }// Release this document from memory.
  451. /// </code>
  452. /// </example>
  453. public void RemoveRow()
  454. {
  455. RemoveRow(rowCount - 1);
  456. }
  457. /// <summary>
  458. /// Remove a row from this Table.
  459. /// </summary>
  460. /// <param name="index">The row to remove.</param>
  461. /// <example>
  462. /// Remove the first row from a Table.
  463. /// <code>
  464. /// // Load a document.
  465. /// using (DocX document = DocX.Load(@"C:\Example\Test.docx"))
  466. /// {
  467. /// // Get the first table in this document.
  468. /// Table table = document.Tables[0];
  469. ///
  470. /// // Remove the first row from this table.
  471. /// table.RemoveRow(0);
  472. ///
  473. /// // Save the document.
  474. /// document.Save();
  475. /// }// Release this document from memory.
  476. /// </code>
  477. /// </example>
  478. public void RemoveRow(int index)
  479. {
  480. if (index < 0 || index > rows.Count)
  481. throw new IndexOutOfRangeException();
  482. rows[index].xml.Remove();
  483. }
  484. /// <summary>
  485. /// Remove the last column for this Table.
  486. /// </summary>
  487. /// <example>
  488. /// Remove the last column from a Table.
  489. /// <code>
  490. /// // Load a document.
  491. /// using (DocX document = DocX.Load(@"C:\Example\Test.docx"))
  492. /// {
  493. /// // Get the first table in this document.
  494. /// Table table = document.Tables[0];
  495. ///
  496. /// // Remove the last column from this table.
  497. /// table.RemoveColumn();
  498. ///
  499. /// // Save the document.
  500. /// document.Save();
  501. /// }// Release this document from memory.
  502. /// </code>
  503. /// </example>
  504. public void RemoveColumn()
  505. {
  506. RemoveColumn(columnCount - 1);
  507. }
  508. /// <summary>
  509. /// Remove a coloumn from this Table.
  510. /// </summary>
  511. /// <param name="index">The coloumn to remove.</param>
  512. /// <example>
  513. /// Remove the first column from a Table.
  514. /// <code>
  515. /// // Load a document.
  516. /// using (DocX document = DocX.Load(@"C:\Example\Test.docx"))
  517. /// {
  518. /// // Get the first table in this document.
  519. /// Table table = document.Tables[0];
  520. ///
  521. /// // Remove the first column from this table.
  522. /// table.RemoveColumn(0);
  523. ///
  524. /// // Save the document.
  525. /// document.Save();
  526. /// }// Release this document from memory.
  527. /// </code>
  528. /// </example>
  529. public void RemoveColumn(int index)
  530. {
  531. if (index < 0 || index > columnCount - 1)
  532. throw new IndexOutOfRangeException();
  533. foreach (Row r in rows)
  534. r.Cells[index].xml.Remove();
  535. }
  536. /// <summary>
  537. /// Insert a row into this table.
  538. /// </summary>
  539. /// <example>
  540. /// <code>
  541. /// // Load a document.
  542. /// using (DocX document = DocX.Load(@"C:\Example\Test.docx"))
  543. /// {
  544. /// // Get the first table in this document.
  545. /// Table table = document.Tables[0];
  546. ///
  547. /// // Insert a new row at index 1 in this table.
  548. /// Row row = table.InsertRow(1);
  549. ///
  550. /// // Loop through each cell in this new row.
  551. /// foreach (Cell c in row.Cells)
  552. /// {
  553. /// // Set the text of each new cell to "Hello".
  554. /// c.Paragraph.InsertText("Hello", false);
  555. /// }
  556. ///
  557. /// // Save the document to a new file.
  558. /// document.SaveAs(@"C:\Example\Test2.docx");
  559. /// }// Release this document from memory.
  560. /// </code>
  561. /// </example>
  562. /// <param name="index">Index to insert row at.</param>
  563. /// <returns>A new Row</returns>
  564. public Row InsertRow(int index)
  565. {
  566. if (index < 0 || index > rows.Count)
  567. throw new IndexOutOfRangeException();
  568. List<XElement> content = new List<XElement>();
  569. foreach (Cell c in rows[0].Cells)
  570. content.Add(new XElement(XName.Get("tc", DocX.w.NamespaceName), new XElement(XName.Get("p", DocX.w.NamespaceName))));
  571. XElement e = new XElement(XName.Get("tr", DocX.w.NamespaceName), content);
  572. Row newRow = new Row(document, e);
  573. XElement rowXml;
  574. if (index == rows.Count)
  575. {
  576. rowXml = rows.Last().xml;
  577. rowXml.AddAfterSelf(newRow.xml);
  578. }
  579. else
  580. {
  581. rowXml = rows[index].xml;
  582. rowXml.AddBeforeSelf(newRow.xml);
  583. }
  584. rows.Insert(index, newRow);
  585. rowCount = rows.Count;
  586. return newRow;
  587. }
  588. /// <summary>
  589. /// Insert a column into a table.
  590. /// </summary>
  591. /// <param name="index">The index to insert the column at.</param>
  592. /// <example>
  593. /// Insert a column to the left of a table.
  594. /// <code>
  595. /// // Load a document.
  596. /// using (DocX document = DocX.Load(@"C:\Example\Test.docx"))
  597. /// {
  598. /// // Get the first Table in this document.
  599. /// Table table = document.Tables[0];
  600. ///
  601. /// // Insert a new column to this left of this table.
  602. /// table.InsertColumn(0);
  603. ///
  604. /// // Set the new coloumns text to "Row no."
  605. /// table.Rows[0].Cells[table.ColumnCount - 1].Paragraph.InsertText("Row no.", false);
  606. ///
  607. /// // Loop through each row in the table.
  608. /// for (int i = 1; i &lt; table.Rows.Count; i++)
  609. /// {
  610. /// // The current row.
  611. /// Row row = table.Rows[i];
  612. ///
  613. /// // The cell in this row that belongs to the new coloumn.
  614. /// Cell cell = row.Cells[table.ColumnCount - 1];
  615. ///
  616. /// // The Paragraph that this cell houses.
  617. /// Paragraph p = cell.Paragraph;
  618. ///
  619. /// // Insert this rows index.
  620. /// p.InsertText(i.ToString(), false);
  621. /// }
  622. ///
  623. /// document.Save();
  624. /// }// Release this document from memory.
  625. /// </code>
  626. /// </example>
  627. public void InsertColumn(int index)
  628. {
  629. if (rows.Count > 0)
  630. {
  631. foreach (Row r in rows)
  632. {
  633. if(columnCount == index)
  634. r.Cells[index - 1].xml.AddAfterSelf(new XElement(XName.Get("tc", DocX.w.NamespaceName), new XElement(XName.Get("p", DocX.w.NamespaceName))));
  635. else
  636. r.Cells[index].xml.AddBeforeSelf(new XElement(XName.Get("tc", DocX.w.NamespaceName), new XElement(XName.Get("p", DocX.w.NamespaceName))));
  637. }
  638. rows = (from r in xml.Elements(XName.Get("tr", DocX.w.NamespaceName))
  639. select new Row(document, r)).ToList();
  640. rowCount = rows.Count;
  641. if (rows.Count > 0)
  642. if (rows[0].Cells.Count > 0)
  643. columnCount = rows[0].Cells.Count;
  644. }
  645. }
  646. /// <summary>
  647. /// Insert a page break after a Table.
  648. /// </summary>
  649. /// <example>
  650. /// Insert a Table and a Paragraph into a document with a page break between them.
  651. /// <code>
  652. /// // Create a new document.
  653. /// using (DocX document = DocX.Create(@"Test.docx"))
  654. /// {
  655. /// // Insert a new Table.
  656. /// Table t1 = document.InsertTable(2, 2);
  657. /// t1.Design = TableDesign.LightShadingAccent1;
  658. ///
  659. /// // Insert a page break after this Table.
  660. /// t1.InsertPageBreakAfterSelf();
  661. ///
  662. /// // Insert a new Paragraph.
  663. /// Paragraph p1 = document.InsertParagraph("Paragraph", false);
  664. ///
  665. /// // Save this document.
  666. /// document.Save();
  667. /// }// Release this document from memory.
  668. /// </code>
  669. /// </example>
  670. public void InsertPageBreakAfterSelf()
  671. {
  672. XElement p = new XElement
  673. (
  674. XName.Get("p", DocX.w.NamespaceName),
  675. new XElement
  676. (
  677. XName.Get("r", DocX.w.NamespaceName),
  678. new XElement
  679. (
  680. XName.Get("br", DocX.w.NamespaceName),
  681. new XAttribute(XName.Get("type", DocX.w.NamespaceName), "page")
  682. )
  683. )
  684. );
  685. xml.AddAfterSelf(p);
  686. }
  687. /// <summary>
  688. /// Insert a page break before a Table.
  689. /// </summary>
  690. /// <example>
  691. /// Insert a Table and a Paragraph into a document with a page break between them.
  692. /// <code>
  693. /// // Create a new document.
  694. /// using (DocX document = DocX.Create(@"Test.docx"))
  695. /// {
  696. /// // Insert a new Paragraph.
  697. /// Paragraph p1 = document.InsertParagraph("Paragraph", false);
  698. ///
  699. /// // Insert a new Table.
  700. /// Table t1 = document.InsertTable(2, 2);
  701. /// t1.Design = TableDesign.LightShadingAccent1;
  702. ///
  703. /// // Insert a page break before this Table.
  704. /// t1.InsertPageBreakBeforeSelf();
  705. ///
  706. /// // Save this document.
  707. /// document.Save();
  708. /// }// Release this document from memory.
  709. /// </code>
  710. /// </example>
  711. public void InsertPageBreakBeforeSelf()
  712. {
  713. XElement p = new XElement
  714. (
  715. XName.Get("p", DocX.w.NamespaceName),
  716. new XElement
  717. (
  718. XName.Get("r", DocX.w.NamespaceName),
  719. new XElement
  720. (
  721. XName.Get("br", DocX.w.NamespaceName),
  722. new XAttribute(XName.Get("type", DocX.w.NamespaceName), "page")
  723. )
  724. )
  725. );
  726. xml.AddBeforeSelf(p);
  727. }
  728. /// <summary>
  729. /// Insert a new Table before this Table, this Table can be from this document or another document.
  730. /// </summary>
  731. /// <param name="t">The Table t to be inserted</param>
  732. /// <returns>A new Table inserted before this Table.</returns>
  733. /// <example>
  734. /// Insert a new Table before this Table.
  735. /// <code>
  736. /// // Place holder for a Table.
  737. /// Table t;
  738. ///
  739. /// // Load document a.
  740. /// using (DocX documentA = DocX.Load(@"a.docx"))
  741. /// {
  742. /// // Get the first Table from this document.
  743. /// t = documentA.Tables[0];
  744. /// }
  745. ///
  746. /// // Load document b.
  747. /// using (DocX documentB = DocX.Load(@"b.docx"))
  748. /// {
  749. /// // Get the first Table in document b.
  750. /// Table t2 = documentB.Tables[0];
  751. ///
  752. /// // Insert the Table from document a before this Table.
  753. /// Table newTable = t2.InsertTableBeforeSelf(t);
  754. ///
  755. /// // Save all changes made to document b.
  756. /// documentB.Save();
  757. /// }// Release this document from memory.
  758. /// </code>
  759. /// </example>
  760. public Table InsertTableBeforeSelf(Table t)
  761. {
  762. xml.AddBeforeSelf(t.xml);
  763. XElement newlyInserted = xml.ElementsBeforeSelf().First();
  764. t.xml = newlyInserted;
  765. DocX.RebuildTables(document);
  766. DocX.RebuildParagraphs(document);
  767. return t;
  768. }
  769. /// <summary>
  770. /// Insert a new Table into this document before this Table.
  771. /// </summary>
  772. /// <param name="rowCount">The number of rows this Table should have.</param>
  773. /// <param name="coloumnCount">The number of coloumns this Table should have.</param>
  774. /// <returns>A new Table inserted before this Table.</returns>
  775. /// <example>
  776. /// <code>
  777. /// // Create a new document.
  778. /// using (DocX document = DocX.Create(@"Test.docx"))
  779. /// {
  780. /// //Insert a Table into this document.
  781. /// Table t = document.InsertTable(2, 2);
  782. /// t.Design = TableDesign.LightShadingAccent1;
  783. /// t.Alignment = Alignment.center;
  784. ///
  785. /// // Insert a new Table before this Table.
  786. /// Table newTable = t.InsertTableBeforeSelf(2, 2);
  787. /// newTable.Design = TableDesign.LightShadingAccent2;
  788. /// newTable.Alignment = Alignment.center;
  789. ///
  790. /// // Save all changes made to this document.
  791. /// document.Save();
  792. /// }// Release this document from memory.
  793. /// </code>
  794. /// </example>
  795. public Table InsertTableBeforeSelf(int rowCount, int coloumnCount)
  796. {
  797. XElement newTable = DocX.CreateTable(rowCount, coloumnCount);
  798. xml.AddBeforeSelf(newTable);
  799. XElement newlyInserted = xml.ElementsBeforeSelf().First();
  800. DocX.RebuildTables(document);
  801. DocX.RebuildParagraphs(document);
  802. return new Table(document, newlyInserted);
  803. }
  804. /// <summary>
  805. /// Insert a new Table after this Table, this Table can be from this document or another document.
  806. /// </summary>
  807. /// <param name="t">The Table t to be inserted</param>
  808. /// <returns>A new Table inserted after this Table.</returns>
  809. /// <example>
  810. /// Insert a new Table after this Table.
  811. /// <code>
  812. /// // Place holder for a Table.
  813. /// Table t;
  814. ///
  815. /// // Load document a.
  816. /// using (DocX documentA = DocX.Load(@"a.docx"))
  817. /// {
  818. /// // Get the first Table from this document.
  819. /// t = documentA.Tables[0];
  820. /// }
  821. ///
  822. /// // Load document b.
  823. /// using (DocX documentB = DocX.Load(@"b.docx"))
  824. /// {
  825. /// // Get the first Table in document b.
  826. /// Table t2 = documentB.Tables[0];
  827. ///
  828. /// // Insert the Table from document a after this Table.
  829. /// Table newTable = t2.InsertTableAfterSelf(t);
  830. ///
  831. /// // Save all changes made to document b.
  832. /// documentB.Save();
  833. /// }// Release this document from memory.
  834. /// </code>
  835. /// </example>
  836. public Table InsertTableAfterSelf(Table t)
  837. {
  838. xml.AddAfterSelf(t.xml);
  839. XElement newlyInserted = xml.ElementsAfterSelf().First();
  840. t.xml = newlyInserted;
  841. DocX.RebuildTables(document);
  842. DocX.RebuildParagraphs(document);
  843. return t;
  844. }
  845. /// <summary>
  846. /// Insert a new Table into this document after this Table.
  847. /// </summary>
  848. /// <param name="rowCount">The number of rows this Table should have.</param>
  849. /// <param name="coloumnCount">The number of coloumns this Table should have.</param>
  850. /// <returns>A new Table inserted before this Table.</returns>
  851. /// <example>
  852. /// <code>
  853. /// // Create a new document.
  854. /// using (DocX document = DocX.Create(@"Test.docx"))
  855. /// {
  856. /// //Insert a Table into this document.
  857. /// Table t = document.InsertTable(2, 2);
  858. /// t.Design = TableDesign.LightShadingAccent1;
  859. /// t.Alignment = Alignment.center;
  860. ///
  861. /// // Insert a new Table after this Table.
  862. /// Table newTable = t.InsertTableAfterSelf(2, 2);
  863. /// newTable.Design = TableDesign.LightShadingAccent2;
  864. /// newTable.Alignment = Alignment.center;
  865. ///
  866. /// // Save all changes made to this document.
  867. /// document.Save();
  868. /// }// Release this document from memory.
  869. /// </code>
  870. /// </example>
  871. public Table InsertTableAfterSelf(int rowCount, int coloumnCount)
  872. {
  873. XElement newTable = DocX.CreateTable(rowCount, coloumnCount);
  874. xml.AddAfterSelf(newTable);
  875. XElement newlyInserted = xml.ElementsAfterSelf().First();
  876. DocX.RebuildTables(document);
  877. DocX.RebuildParagraphs(document);
  878. return new Table(document, newlyInserted);
  879. }
  880. /// <summary>
  881. /// Insert a Paragraph before this Table, this Paragraph may have come from the same or another document.
  882. /// </summary>
  883. /// <param name="p">The Paragraph to insert.</param>
  884. /// <returns>The Paragraph now associated with this document.</returns>
  885. /// <example>
  886. /// Take a Paragraph from document a, and insert it into document b before this Table.
  887. /// <code>
  888. /// // Place holder for a Paragraph.
  889. /// Paragraph p;
  890. ///
  891. /// // Load document a.
  892. /// using (DocX documentA = DocX.Load(@"a.docx"))
  893. /// {
  894. /// // Get the first paragraph from this document.
  895. /// p = documentA.Paragraphs[0];
  896. /// }
  897. ///
  898. /// // Load document b.
  899. /// using (DocX documentB = DocX.Load(@"b.docx"))
  900. /// {
  901. /// // Get the first Table in document b.
  902. /// Table t = documentB.Tables[0];
  903. ///
  904. /// // Insert the Paragraph from document a before this Table.
  905. /// Paragraph newParagraph = t.InsertParagraphBeforeSelf(p);
  906. ///
  907. /// // Save all changes made to document b.
  908. /// documentB.Save();
  909. /// }// Release this document from memory.
  910. /// </code>
  911. /// </example>
  912. public Paragraph InsertParagraphBeforeSelf(Paragraph p)
  913. {
  914. xml.AddBeforeSelf(p.xml);
  915. XElement newlyInserted = xml.ElementsBeforeSelf().First();
  916. p.xml = newlyInserted;
  917. DocX.RebuildParagraphs(document);
  918. return p;
  919. }
  920. /// <summary>
  921. /// Insert a new Paragraph before this Table.
  922. /// </summary>
  923. /// <param name="text">The initial text for this new Paragraph.</param>
  924. /// <returns>A new Paragraph inserted before this Table.</returns>
  925. /// <example>
  926. /// Insert a new Paragraph before the first Table in this document.
  927. /// <code>
  928. /// // Create a new document.
  929. /// using (DocX document = DocX.Create(@"Test.docx"))
  930. /// {
  931. /// // Insert a Table into this document.
  932. /// Table t = document.InsertTable(2, 2);
  933. ///
  934. /// t.InsertParagraphBeforeSelf("I was inserted before the next Table.");
  935. ///
  936. /// // Save all changes made to this new document.
  937. /// document.Save();
  938. /// }// Release this new document form memory.
  939. /// </code>
  940. /// </example>
  941. public Paragraph InsertParagraphBeforeSelf(string text)
  942. {
  943. return InsertParagraphBeforeSelf(text, false, new Formatting());
  944. }
  945. /// <summary>
  946. /// Insert a new Paragraph before this Table.
  947. /// </summary>
  948. /// <param name="text">The initial text for this new Paragraph.</param>
  949. /// <param name="trackChanges">Should this insertion be tracked as a change?</param>
  950. /// <returns>A new Paragraph inserted before this Table.</returns>
  951. /// <example>
  952. /// Insert a new paragraph before the first Table in this document.
  953. /// <code>
  954. /// // Create a new document.
  955. /// using (DocX document = DocX.Create(@"Test.docx"))
  956. /// {
  957. /// // Insert a Table into this document.
  958. /// Table t = document.InsertTable(2, 2);
  959. ///
  960. /// t.InsertParagraphBeforeSelf("I was inserted before the next Table.", false);
  961. ///
  962. /// // Save all changes made to this new document.
  963. /// document.Save();
  964. /// }// Release this new document form memory.
  965. /// </code>
  966. /// </example>
  967. public Paragraph InsertParagraphBeforeSelf(string text, bool trackChanges)
  968. {
  969. return InsertParagraphBeforeSelf(text, trackChanges, new Formatting());
  970. }
  971. /// <summary>
  972. /// Insert a new Paragraph before this Table.
  973. /// </summary>
  974. /// <param name="text">The initial text for this new Paragraph.</param>
  975. /// <param name="trackChanges">Should this insertion be tracked as a change?</param>
  976. /// <param name="formatting">The formatting to apply to this insertion.</param>
  977. /// <returns>A new Paragraph inserted before this Table.</returns>
  978. /// <example>
  979. /// Insert a new paragraph before the first Table in this document.
  980. /// <code>
  981. /// // Create a new document.
  982. /// using (DocX document = DocX.Create(@"Test.docx"))
  983. /// {
  984. /// // Insert a Table into this document.
  985. /// Table t = document.InsertTable(2, 2);
  986. ///
  987. /// Formatting boldFormatting = new Formatting();
  988. /// boldFormatting.Bold = true;
  989. ///
  990. /// t.InsertParagraphBeforeSelf("I was inserted before the next Table.", false, boldFormatting);
  991. ///
  992. /// // Save all changes made to this new document.
  993. /// document.Save();
  994. /// }// Release this new document form memory.
  995. /// </code>
  996. /// </example>
  997. public Paragraph InsertParagraphBeforeSelf(string text, bool trackChanges, Formatting formatting)
  998. {
  999. XElement newParagraph = new XElement
  1000. (
  1001. XName.Get("p", DocX.w.NamespaceName), new XElement(XName.Get("pPr", DocX.w.NamespaceName)), DocX.FormatInput(text, formatting.Xml)
  1002. );
  1003. if (trackChanges)
  1004. newParagraph = Paragraph.CreateEdit(EditType.ins, DateTime.Now, newParagraph);
  1005. xml.AddBeforeSelf(newParagraph);
  1006. XElement newlyInserted = xml.ElementsBeforeSelf().First();
  1007. Paragraph p = new Paragraph(document, -1, newlyInserted);
  1008. DocX.RebuildParagraphs(document);
  1009. return p;
  1010. }
  1011. /// <summary>
  1012. /// Insert a Paragraph after this Table, this Paragraph may have come from the same or another document.
  1013. /// </summary>
  1014. /// <param name="p">The Paragraph to insert.</param>
  1015. /// <returns>The Paragraph now associated with this document.</returns>
  1016. /// <example>
  1017. /// Take a Paragraph from document a, and insert it into document b after this Table.
  1018. /// <code>
  1019. /// // Place holder for a Paragraph.
  1020. /// Paragraph p;
  1021. ///
  1022. /// // Load document a.
  1023. /// using (DocX documentA = DocX.Load(@"a.docx"))
  1024. /// {
  1025. /// // Get the first paragraph from this document.
  1026. /// p = documentA.Paragraphs[0];
  1027. /// }
  1028. ///
  1029. /// // Load document b.
  1030. /// using (DocX documentB = DocX.Load(@"b.docx"))
  1031. /// {
  1032. /// // Get the first Table in document b.
  1033. /// Table t = documentB.Tables[0];
  1034. ///
  1035. /// // Insert the Paragraph from document a after this Table.
  1036. /// Paragraph newParagraph = t.InsertParagraphAfterSelf(p);
  1037. ///
  1038. /// // Save all changes made to document b.
  1039. /// documentB.Save();
  1040. /// }// Release this document from memory.
  1041. /// </code>
  1042. /// </example>
  1043. public Paragraph InsertParagraphAfterSelf(Paragraph p)
  1044. {
  1045. xml.AddAfterSelf(p.xml);
  1046. XElement newlyInserted = xml.ElementsAfterSelf().First();
  1047. p.xml = newlyInserted;
  1048. DocX.RebuildParagraphs(document);
  1049. return p;
  1050. }
  1051. /// <summary>
  1052. /// Insert a new Paragraph after this Table.
  1053. /// </summary>
  1054. /// <param name="text">The initial text for this new Paragraph.</param>
  1055. /// <param name="trackChanges">Should this insertion be tracked as a change?</param>
  1056. /// <param name="formatting">The formatting to apply to this insertion.</param>
  1057. /// <returns>A new Paragraph inserted after this Table.</returns>
  1058. /// <example>
  1059. /// Insert a new paragraph after the first Table in this document.
  1060. /// <code>
  1061. /// // Create a new document.
  1062. /// using (DocX document = DocX.Create(@"Test.docx"))
  1063. /// {
  1064. /// // Insert a Table into this document.
  1065. /// Table t = document.InsertTable(2, 2);
  1066. ///
  1067. /// Formatting boldFormatting = new Formatting();
  1068. /// boldFormatting.Bold = true;
  1069. ///
  1070. /// t.InsertParagraphAfterSelf("I was inserted after the previous Table.", false, boldFormatting);
  1071. ///
  1072. /// // Save all changes made to this new document.
  1073. /// document.Save();
  1074. /// }// Release this new document form memory.
  1075. /// </code>
  1076. /// </example>
  1077. public Paragraph InsertParagraphAfterSelf(string text, bool trackChanges, Formatting formatting)
  1078. {
  1079. XElement newParagraph = new XElement
  1080. (
  1081. XName.Get("p", DocX.w.NamespaceName), new XElement(XName.Get("pPr", DocX.w.NamespaceName)), DocX.FormatInput(text, formatting.Xml)
  1082. );
  1083. if (trackChanges)
  1084. newParagraph = Paragraph.CreateEdit(EditType.ins, DateTime.Now, newParagraph);
  1085. xml.AddAfterSelf(newParagraph);
  1086. XElement newlyInserted = xml.ElementsAfterSelf().First();
  1087. Paragraph p = new Paragraph(document, -1, newlyInserted);
  1088. DocX.RebuildParagraphs(document);
  1089. return p;
  1090. }
  1091. /// <summary>
  1092. /// Insert a new Paragraph after this Table.
  1093. /// </summary>
  1094. /// <param name="text">The initial text for this new Paragraph.</param>
  1095. /// <param name="trackChanges">Should this insertion be tracked as a change?</param>
  1096. /// <returns>A new Paragraph inserted after this Table.</returns>
  1097. /// <example>
  1098. /// Insert a new paragraph after the first Table in this document.
  1099. /// <code>
  1100. /// // Create a new document.
  1101. /// using (DocX document = DocX.Create(@"Test.docx"))
  1102. /// {
  1103. /// // Insert a Table into this document.
  1104. /// Table t = document.InsertTable(2, 2);
  1105. ///
  1106. /// t.InsertParagraphAfterSelf("I was inserted after the previous Table.", false);
  1107. ///
  1108. /// // Save all changes made to this new document.
  1109. /// document.Save();
  1110. /// }// Release this new document form memory.
  1111. /// </code>
  1112. /// </example>
  1113. public Paragraph InsertParagraphAfterSelf(string text, bool trackChanges)
  1114. {
  1115. return InsertParagraphAfterSelf(text, trackChanges, new Formatting());
  1116. }
  1117. /// <summary>
  1118. /// Insert a new Paragraph after this Table.
  1119. /// </summary>
  1120. /// <param name="text">The initial text for this new Paragraph.</param>
  1121. /// <returns>A new Paragraph inserted after this Table.</returns>
  1122. /// <example>
  1123. /// Insert a new Paragraph after the first Table in this document.
  1124. /// <code>
  1125. /// // Create a new document.
  1126. /// using (DocX document = DocX.Create(@"Test.docx"))
  1127. /// {
  1128. /// // Insert a Table into this document.
  1129. /// Table t = document.InsertTable(2, 2);
  1130. ///
  1131. /// t.InsertParagraphAfterSelf("I was inserted after the previous Table.");
  1132. ///
  1133. /// // Save all changes made to this new document.
  1134. /// document.Save();
  1135. /// }// Release this new document form memory.
  1136. /// </code>
  1137. /// </example>
  1138. public Paragraph InsertParagraphAfterSelf(string text)
  1139. {
  1140. return InsertParagraphAfterSelf(text, false, new Formatting());
  1141. }
  1142. }
  1143. /// <summary>
  1144. /// Represents a single row in a Table.
  1145. /// </summary>
  1146. public class Row
  1147. {
  1148. DocX document;
  1149. internal XElement xml;
  1150. private List<Cell> cells;
  1151. /// <summary>
  1152. /// A list of Cells in this Row.
  1153. /// </summary>
  1154. public List<Cell> Cells { get { return cells; } }
  1155. internal Row(DocX document, XElement xml)
  1156. {
  1157. this.document = document;
  1158. this.xml = xml;
  1159. cells = (from c in xml.Elements(XName.Get("tc", DocX.w.NamespaceName))
  1160. select new Cell(document, c)).ToList();
  1161. }
  1162. }
  1163. public class Cell
  1164. {
  1165. private Paragraph p;
  1166. private DocX document;
  1167. internal XElement xml;
  1168. public Paragraph Paragraph
  1169. {
  1170. get { return p; }
  1171. set { p = value; }
  1172. }
  1173. internal Cell(DocX document, XElement xml)
  1174. {
  1175. this.document = document;
  1176. this.xml = xml;
  1177. XElement properties = xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  1178. p = new Paragraph(document, 0, xml.Element(XName.Get("p", DocX.w.NamespaceName)));
  1179. }
  1180. }
  1181. }