Вы не можете выбрать более 25 тем Темы должны начинаться с буквы или цифры, могут содержать дефисы(-) и должны содержать не более 35 символов.

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367136813691370137113721373137413751376137713781379138013811382138313841385138613871388138913901391139213931394139513961397139813991400140114021403140414051406140714081409141014111412141314141415141614171418141914201421142214231424142514261427142814291430143114321433143414351436143714381439144014411442144314441445144614471448144914501451145214531454145514561457145814591460146114621463146414651466146714681469147014711472147314741475147614771478147914801481148214831484148514861487148814891490149114921493149414951496149714981499150015011502150315041505150615071508150915101511151215131514151515161517151815191520152115221523152415251526152715281529153015311532153315341535153615371538153915401541154215431544154515461547154815491550155115521553155415551556155715581559156015611562156315641565156615671568156915701571157215731574157515761577157815791580158115821583158415851586158715881589159015911592159315941595159615971598159916001601160216031604160516061607160816091610161116121613161416151616161716181619162016211622162316241625162616271628162916301631163216331634163516361637163816391640164116421643164416451646164716481649165016511652165316541655165616571658165916601661166216631664166516661667166816691670167116721673167416751676167716781679168016811682168316841685168616871688168916901691169216931694169516961697169816991700170117021703170417051706170717081709171017111712171317141715171617171718171917201721172217231724172517261727172817291730173117321733173417351736173717381739174017411742174317441745174617471748174917501751175217531754175517561757175817591760176117621763176417651766176717681769177017711772177317741775177617771778177917801781178217831784178517861787178817891790179117921793179417951796179717981799180018011802180318041805180618071808180918101811181218131814181518161817181818191820182118221823182418251826182718281829183018311832183318341835183618371838183918401841184218431844184518461847184818491850185118521853185418551856185718581859186018611862186318641865186618671868186918701871187218731874187518761877187818791880188118821883188418851886188718881889189018911892189318941895189618971898189919001901190219031904190519061907190819091910191119121913191419151916191719181919192019211922192319241925192619271928192919301931193219331934193519361937193819391940194119421943194419451946194719481949195019511952195319541955195619571958195919601961196219631964196519661967196819691970197119721973197419751976197719781979198019811982198319841985198619871988198919901991199219931994199519961997199819992000200120022003200420052006200720082009201020112012201320142015201620172018201920202021202220232024202520262027202820292030203120322033203420352036203720382039204020412042204320442045204620472048204920502051205220532054205520562057205820592060206120622063206420652066206720682069207020712072207320742075207620772078207920802081208220832084208520862087208820892090209120922093209420952096209720982099210021012102210321042105210621072108210921102111211221132114211521162117211821192120212121222123212421252126212721282129213021312132213321342135213621372138213921402141214221432144214521462147214821492150215121522153215421552156215721582159216021612162216321642165216621672168216921702171217221732174217521762177217821792180218121822183218421852186218721882189219021912192219321942195219621972198219922002201220222032204220522062207220822092210221122122213221422152216221722182219222022212222222322242225222622272228222922302231223222332234223522362237223822392240224122422243224422452246224722482249225022512252225322542255225622572258225922602261226222632264226522662267226822692270227122722273227422752276227722782279228022812282228322842285228622872288228922902291229222932294229522962297229822992300230123022303230423052306230723082309231023112312231323142315231623172318231923202321232223232324232523262327232823292330233123322333233423352336233723382339234023412342234323442345234623472348234923502351235223532354235523562357235823592360236123622363236423652366236723682369237023712372237323742375237623772378237923802381238223832384238523862387238823892390239123922393239423952396239723982399240024012402240324042405240624072408240924102411241224132414241524162417241824192420242124222423242424252426242724282429243024312432243324342435243624372438243924402441244224432444244524462447244824492450245124522453245424552456245724582459246024612462246324642465246624672468246924702471247224732474247524762477247824792480248124822483248424852486248724882489249024912492249324942495249624972498249925002501250225032504250525062507250825092510251125122513251425152516251725182519252025212522252325242525252625272528252925302531253225332534253525362537253825392540254125422543254425452546254725482549255025512552255325542555255625572558255925602561256225632564256525662567256825692570257125722573257425752576257725782579258025812582258325842585258625872588258925902591259225932594259525962597259825992600260126022603260426052606260726082609261026112612261326142615261626172618261926202621262226232624262526262627262826292630263126322633263426352636263726382639264026412642264326442645264626472648264926502651265226532654265526562657265826592660266126622663266426652666266726682669267026712672267326742675267626772678267926802681268226832684268526862687268826892690269126922693269426952696269726982699270027012702270327042705270627072708270927102711271227132714271527162717271827192720272127222723272427252726272727282729273027312732273327342735273627372738273927402741274227432744274527462747274827492750275127522753275427552756275727582759276027612762276327642765276627672768276927702771277227732774277527762777277827792780278127822783278427852786278727882789279027912792279327942795279627972798279928002801280228032804280528062807280828092810281128122813281428152816281728182819282028212822282328242825282628272828282928302831283228332834283528362837283828392840284128422843284428452846284728482849285028512852285328542855285628572858285928602861286228632864286528662867286828692870287128722873287428752876287728782879288028812882288328842885288628872888288928902891289228932894289528962897289828992900290129022903290429052906290729082909291029112912291329142915291629172918291929202921292229232924292529262927292829292930293129322933293429352936293729382939294029412942294329442945294629472948294929502951295229532954295529562957295829592960296129622963296429652966296729682969297029712972297329742975297629772978297929802981298229832984298529862987298829892990299129922993299429952996299729982999300030013002300330043005300630073008300930103011301230133014301530163017301830193020302130223023302430253026302730283029303030313032303330343035303630373038303930403041304230433044304530463047304830493050305130523053305430553056305730583059306030613062306330643065306630673068306930703071307230733074307530763077307830793080308130823083308430853086308730883089309030913092309330943095309630973098309931003101310231033104310531063107310831093110311131123113311431153116311731183119312031213122312331243125312631273128312931303131313231333134313531363137313831393140314131423143314431453146314731483149315031513152315331543155315631573158315931603161316231633164316531663167316831693170317131723173317431753176317731783179318031813182318331843185318631873188318931903191319231933194319531963197319831993200320132023203320432053206320732083209321032113212321332143215321632173218321932203221322232233224322532263227322832293230323132323233323432353236323732383239324032413242324332443245324632473248324932503251325232533254325532563257325832593260326132623263326432653266326732683269327032713272327332743275327632773278327932803281328232833284328532863287328832893290329132923293329432953296329732983299330033013302330333043305330633073308330933103311331233133314331533163317331833193320332133223323332433253326332733283329333033313332333333343335333633373338333933403341334233433344334533463347334833493350335133523353335433553356335733583359336033613362336333643365336633673368336933703371337233733374337533763377337833793380338133823383338433853386338733883389339033913392339333943395339633973398339934003401340234033404340534063407340834093410341134123413341434153416341734183419342034213422342334243425342634273428342934303431343234333434343534363437343834393440344134423443344434453446344734483449345034513452345334543455345634573458345934603461346234633464346534663467346834693470347134723473347434753476347734783479348034813482348334843485348634873488348934903491349234933494349534963497349834993500350135023503350435053506350735083509351035113512351335143515351635173518351935203521352235233524352535263527352835293530353135323533353435353536353735383539354035413542354335443545354635473548354935503551355235533554355535563557355835593560356135623563356435653566356735683569357035713572357335743575357635773578357935803581358235833584358535863587358835893590359135923593359435953596359735983599360036013602360336043605360636073608360936103611361236133614361536163617361836193620362136223623362436253626362736283629363036313632363336343635363636373638363936403641364236433644364536463647364836493650365136523653365436553656365736583659366036613662366336643665366636673668366936703671367236733674367536763677367836793680368136823683368436853686368736883689369036913692369336943695369636973698369937003701370237033704370537063707370837093710371137123713371437153716371737183719372037213722372337243725372637273728372937303731373237333734373537363737373837393740374137423743374437453746374737483749375037513752375337543755375637573758375937603761376237633764376537663767376837693770377137723773377437753776377737783779378037813782378337843785378637873788378937903791379237933794379537963797379837993800380138023803380438053806380738083809381038113812381338143815381638173818381938203821382238233824382538263827382838293830383138323833383438353836383738383839384038413842384338443845384638473848384938503851385238533854385538563857385838593860386138623863386438653866386738683869387038713872387338743875387638773878387938803881388238833884388538863887388838893890389138923893389438953896389738983899390039013902390339043905390639073908390939103911391239133914391539163917391839193920392139223923392439253926392739283929393039313932393339343935393639373938393939403941394239433944394539463947394839493950395139523953395439553956395739583959396039613962396339643965396639673968396939703971397239733974397539763977397839793980398139823983398439853986398739883989399039913992399339943995399639973998399940004001400240034004400540064007400840094010401140124013401440154016401740184019402040214022402340244025
  1. using System;
  2. using System.Collections.Generic;
  3. using System.Linq;
  4. using System.Xml.Linq;
  5. using System.IO.Packaging;
  6. using System.IO;
  7. using System.Drawing;
  8. using System.Globalization;
  9. using System.Collections.ObjectModel;
  10. namespace Novacode
  11. {
  12. /// <summary>
  13. /// Represents a Table in a document.
  14. /// </summary>
  15. public class Table : InsertBeforeOrAfter
  16. {
  17. private Alignment alignment;
  18. private AutoFit autofit;
  19. private float[] ColumnWidthsValue;
  20. /// <summary>
  21. /// Merge cells in given column starting with startRow and ending with endRow.
  22. /// </summary>
  23. /// <remarks>
  24. /// Added by arudoy patch: 11608
  25. /// </remarks>
  26. public void MergeCellsInColumn(int columnIndex, int startRow, int endRow)
  27. {
  28. // Check for valid start and end indexes.
  29. if (columnIndex < 0 || columnIndex >= ColumnCount)
  30. throw new IndexOutOfRangeException();
  31. if (startRow < 0 || endRow <= startRow || endRow >= Rows.Count)
  32. throw new IndexOutOfRangeException();
  33. // Foreach each Cell between startIndex and endIndex inclusive.
  34. foreach (Row row in Rows.Where((z, i) => i > startRow && i <= endRow))
  35. {
  36. Cell c = row.Cells[columnIndex];
  37. XElement tcPr = c.Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  38. if (tcPr == null)
  39. {
  40. c.Xml.SetElementValue(XName.Get("tcPr", DocX.w.NamespaceName), string.Empty);
  41. tcPr = c.Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  42. }
  43. XElement vMerge = tcPr.Element(XName.Get("vMerge", DocX.w.NamespaceName));
  44. if (vMerge == null)
  45. {
  46. tcPr.SetElementValue(XName.Get("vMerge", DocX.w.NamespaceName), string.Empty);
  47. vMerge = tcPr.Element(XName.Get("vMerge", DocX.w.NamespaceName));
  48. }
  49. }
  50. /*
  51. * Get the tcPr (table cell properties) element for the first cell in this merge,
  52. * null will be returned if no such element exists.
  53. */
  54. XElement start_tcPr = null;
  55. if (columnIndex > Rows[startRow].Cells.Count)
  56. start_tcPr = Rows[startRow].Cells[Rows[startRow].Cells.Count - 1].Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  57. else
  58. start_tcPr = Rows[startRow].Cells[columnIndex].Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  59. if (start_tcPr == null)
  60. {
  61. Rows[startRow].Cells[columnIndex].Xml.SetElementValue(XName.Get("tcPr", DocX.w.NamespaceName), string.Empty);
  62. start_tcPr = Rows[startRow].Cells[columnIndex].Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  63. }
  64. /*
  65. * Get the gridSpan element of this row,
  66. * null will be returned if no such element exists.
  67. */
  68. XElement start_vMerge = start_tcPr.Element(XName.Get("vMerge", DocX.w.NamespaceName));
  69. if (start_vMerge == null)
  70. {
  71. start_tcPr.SetElementValue(XName.Get("vMerge", DocX.w.NamespaceName), string.Empty);
  72. start_vMerge = start_tcPr.Element(XName.Get("vMerge", DocX.w.NamespaceName));
  73. }
  74. start_vMerge.SetAttributeValue(XName.Get("val", DocX.w.NamespaceName), "restart");
  75. }
  76. /// <summary>
  77. /// Returns a list of all Paragraphs inside this container.
  78. /// </summary>
  79. ///
  80. public virtual List<Paragraph> Paragraphs
  81. {
  82. get
  83. {
  84. List<Paragraph> paragraphs = new List<Paragraph>();
  85. foreach (Row r in Rows)
  86. paragraphs.AddRange(r.Paragraphs);
  87. return paragraphs;
  88. }
  89. }
  90. /// <summary>
  91. /// Returns a list of all Pictures in a Table.
  92. /// </summary>
  93. /// <example>
  94. /// Returns a list of all Pictures in a Table.
  95. /// <code>
  96. /// <![CDATA[
  97. /// // Create a document.
  98. /// using (DocX document = DocX.Load(@"Test.docx"))
  99. /// {
  100. /// // Get the first Table in a document.
  101. /// Table t = document.Tables[0];
  102. ///
  103. /// // Get all of the Pictures in this Table.
  104. /// List<Picture> pictures = t.Pictures;
  105. ///
  106. /// // Save this document.
  107. /// document.Save();
  108. /// }
  109. /// ]]>
  110. /// </code>
  111. /// </example>
  112. public List<Picture> Pictures
  113. {
  114. get
  115. {
  116. List<Picture> pictures = new List<Picture>();
  117. foreach (Row r in Rows)
  118. pictures.AddRange(r.Pictures);
  119. return pictures;
  120. }
  121. }
  122. /// <summary>
  123. /// Set the direction of all content in this Table.
  124. /// </summary>
  125. /// <param name="direction">(Left to Right) or (Right to Left)</param>
  126. /// <example>
  127. /// Set the content direction for all content in a table to RightToLeft.
  128. /// <code>
  129. /// // Load a document.
  130. /// using (DocX document = DocX.Load(@"Test.docx"))
  131. /// {
  132. /// // Get the first table in a document.
  133. /// Table table = document.Tables[0];
  134. ///
  135. /// // Set the content direction for all content in this table to RightToLeft.
  136. /// table.SetDirection(Direction.RightToLeft);
  137. ///
  138. /// // Save all changes made to this document.
  139. /// document.Save();
  140. /// }
  141. /// </code>
  142. /// </example>
  143. public void SetDirection(Direction direction)
  144. {
  145. XElement tblPr = GetOrCreate_tblPr();
  146. tblPr.Add(new XElement(DocX.w + "bidiVisual"));
  147. foreach (Row r in Rows)
  148. r.SetDirection(direction);
  149. }
  150. /// <summary>
  151. /// Get all of the Hyperlinks in this Table.
  152. /// </summary>
  153. /// <example>
  154. /// Get all of the Hyperlinks in this Table.
  155. /// <code>
  156. /// // Create a document.
  157. /// using (DocX document = DocX.Load(@"Test.docx"))
  158. /// {
  159. /// // Get the first Table in this document.
  160. /// Table t = document.Tables[0];
  161. ///
  162. /// // Get a list of all Hyperlinks in this Table.
  163. /// List&lt;Hyperlink&gt; hyperlinks = t.Hyperlinks;
  164. ///
  165. /// // Save this document.
  166. /// document.Save();
  167. /// }
  168. /// </code>
  169. /// </example>
  170. public List<Hyperlink> Hyperlinks
  171. {
  172. get
  173. {
  174. List<Hyperlink> hyperlinks = new List<Hyperlink>();
  175. foreach (Row r in Rows)
  176. hyperlinks.AddRange(r.Hyperlinks);
  177. return hyperlinks;
  178. }
  179. }
  180. public void SetWidths(float[] widths)
  181. {
  182. this.ColumnWidthsValue = widths;
  183. //set widths for existing rows
  184. foreach (var r in Rows)
  185. {
  186. for (var c = 0; c < widths.Length; c++)
  187. {
  188. if (r.Cells.Count > c)
  189. r.Cells[c].Width = widths[c];
  190. }
  191. }
  192. }
  193. /// <summary>
  194. /// Set Table column width by prescribing percent
  195. /// </summary>
  196. /// <param name="widthsPercentage">column width % list</param>
  197. /// <param name="totalWidth">Total table width. Will be calculated if null sent.</param>
  198. public void SetWidthsPercentage(float[] widthsPercentage, float? totalWidth)
  199. {
  200. if (totalWidth == null) totalWidth = this.Document.PageWidth - this.Document.MarginLeft - this.Document.MarginRight; // calculate total table width
  201. List<float> widths = new List<float>(widthsPercentage.Length); // empty list, will hold actual width
  202. widthsPercentage.ToList().ForEach(pWidth => { widths.Add(pWidth * totalWidth.Value / 100); }); // convert percentage to actual width for all values in array
  203. SetWidths(widths.ToArray()); // set actual column width
  204. }
  205. /// <summary>
  206. /// If the tblPr element doesent exist it is created, either way it is returned by this function.
  207. /// </summary>
  208. /// <returns>The tblPr element for this Table.</returns>
  209. internal XElement GetOrCreate_tblPr()
  210. {
  211. // Get the element.
  212. XElement tblPr = Xml.Element(XName.Get("tblPr", DocX.w.NamespaceName));
  213. // If it dosen't exist, create it.
  214. if (tblPr == null)
  215. {
  216. Xml.AddFirst(new XElement(XName.Get("tblPr", DocX.w.NamespaceName)));
  217. tblPr = Xml.Element(XName.Get("tblPr", DocX.w.NamespaceName));
  218. }
  219. // Return the pPr element for this Paragraph.
  220. return tblPr;
  221. }
  222. /// <summary>
  223. /// Set the specified cell margin for the table-level.
  224. /// </summary>
  225. /// <param name="type">The side of the cell margin.</param>
  226. /// <param name="margin">The value for the specified cell margin.</param>
  227. /// <remarks>More information can be found <see cref="http://msdn.microsoft.com/en-us/library/documentformat.openxml.wordprocessing.tablecellmargindefault.aspx">here</see></remarks>
  228. public void SetTableCellMargin(TableCellMarginType type, double margin)
  229. {
  230. XElement tblPr = GetOrCreate_tblPr();
  231. // find (or create) the element with the cell margins
  232. XElement tblCellMar = tblPr.Element(XName.Get("tblCellMar", DocX.w.NamespaceName));
  233. if (tblCellMar == null)
  234. {
  235. tblPr.AddFirst(new XElement(XName.Get("tblCellMar", DocX.w.NamespaceName)));
  236. tblCellMar = tblPr.Element(XName.Get("tblCellMar", DocX.w.NamespaceName));
  237. }
  238. // find (or create) the element with cell margin for the specified side
  239. XElement tblMargin = tblCellMar.Element(XName.Get(type.ToString(), DocX.w.NamespaceName));
  240. if (tblMargin == null)
  241. {
  242. tblCellMar.AddFirst(new XElement(XName.Get(type.ToString(), DocX.w.NamespaceName)));
  243. tblMargin = tblCellMar.Element(XName.Get(type.ToString(), DocX.w.NamespaceName));
  244. }
  245. tblMargin.RemoveAttributes();
  246. // set the value for the cell margin
  247. tblMargin.Add(new XAttribute(XName.Get("w", DocX.w.NamespaceName), margin));
  248. // set the side of cell margin
  249. tblMargin.Add(new XAttribute(XName.Get("type", DocX.w.NamespaceName), "dxa"));
  250. }
  251. /// <summary>
  252. /// Gets the column width for a given column index.
  253. /// </summary>
  254. /// <param name="index"></param>
  255. public Double GetColumnWidth(Int32 index)
  256. {
  257. List<Double> widths = ColumnWidths;
  258. if (widths == null || index > widths.Count - 1) return Double.NaN;
  259. return widths[index];
  260. }
  261. /// <summary>
  262. /// Sets the column width for the given index.
  263. /// </summary>
  264. /// <param name="index">Column index</param>
  265. /// <param name="width">Colum width</param>
  266. public void SetColumnWidth(Int32 index, Double width)
  267. {
  268. List<Double> widths = ColumnWidths;
  269. if (widths == null || index > widths.Count - 1)
  270. {
  271. if (Rows.Count == 0) throw new Exception("There is at least one row required to detect the existing columns.");
  272. // use width of last row cells
  273. // may not work for merged cell!
  274. widths = new List<Double>();
  275. foreach (Cell c in Rows[Rows.Count - 1].Cells)
  276. {
  277. widths.Add(c.Width);
  278. }
  279. }
  280. // check if index is matching table columns
  281. if (index > widths.Count - 1) throw new Exception("The index is greather than the available table columns.");
  282. // get the table grid props
  283. XElement grid = Xml.Element(XName.Get("tblGrid", DocX.w.NamespaceName));
  284. // if null; append a new grid below tblPr
  285. if (grid == null)
  286. {
  287. XElement tblPr = GetOrCreate_tblPr();
  288. tblPr.AddAfterSelf(new XElement(XName.Get("tblGrid", DocX.w.NamespaceName)));
  289. grid = Xml.Element(XName.Get("tblGrid", DocX.w.NamespaceName));
  290. }
  291. // remove all existing values
  292. grid.RemoveAll();
  293. // append new column widths
  294. XElement gridCol = null;
  295. Int32 i = 0;
  296. Double value = width;
  297. Double total = 0;
  298. foreach (var w in widths)
  299. {
  300. value = w;
  301. if (i == index) value = width;
  302. gridCol = new XElement(XName.Get("gridCol", DocX.w.NamespaceName),
  303. new XAttribute(XName.Get("w", DocX.w.NamespaceName), value));
  304. grid.Add(gridCol);
  305. i += 1;
  306. total += value;
  307. }
  308. // remove cell widths
  309. foreach (Row r in Rows)
  310. foreach (Cell c in r.Cells)
  311. c.Width = -1;
  312. // set fitting to fixed; this will add/set additional table properties
  313. this.AutoFit = AutoFit.Fixed;
  314. }
  315. /// <summary>
  316. /// Gets a list of all column widths for this table.
  317. /// </summary>
  318. public List<Double> ColumnWidths
  319. {
  320. get
  321. {
  322. List<Double> widths = new List<Double>();
  323. // get the table grid props
  324. XElement grid = Xml.Element(XName.Get("tblGrid", DocX.w.NamespaceName));
  325. if (grid == null) return null;
  326. // get col properties
  327. var cols = grid.Elements(XName.Get("gridCol", DocX.w.NamespaceName));
  328. if (cols == null) return null;
  329. String value = String.Empty;
  330. foreach (var col in cols)
  331. {
  332. value = col.GetAttribute(XName.Get("w", DocX.w.NamespaceName));
  333. widths.Add(Convert.ToDouble(value));
  334. }
  335. return widths;
  336. }
  337. }
  338. /// <summary>
  339. /// Returns the number of rows in this table.
  340. /// </summary>
  341. public Int32 RowCount
  342. {
  343. get
  344. {
  345. return Xml.Elements(XName.Get("tr", DocX.w.NamespaceName)).Count();
  346. }
  347. }
  348. private int _cachedColCount = -1;
  349. /// <summary>
  350. /// Returns the number of columns in this table.
  351. /// </summary>
  352. public Int32 ColumnCount
  353. {
  354. get
  355. {
  356. if (RowCount == 0)
  357. return 0;
  358. if (_cachedColCount == -1)
  359. _cachedColCount = Rows.First().ColumnCount;
  360. return _cachedColCount;
  361. }
  362. }
  363. /// <summary>
  364. /// Returns a list of rows in this table.
  365. /// </summary>
  366. public List<Row> Rows
  367. {
  368. get
  369. {
  370. List<Row> rows =
  371. (
  372. from r in Xml.Elements(XName.Get("tr", DocX.w.NamespaceName))
  373. select new Row(this, Document, r)
  374. ).ToList();
  375. return rows;
  376. }
  377. }
  378. private TableDesign design;
  379. internal Table(DocX document, XElement xml)
  380. : base(document, xml)
  381. {
  382. autofit = AutoFit.ColumnWidth;
  383. this.Xml = xml;
  384. this.mainPart = document.mainPart;
  385. XElement properties = xml.Element(XName.Get("tblPr", DocX.w.NamespaceName));
  386. XElement style = properties.Element(XName.Get("tblStyle", DocX.w.NamespaceName));
  387. if (style != null)
  388. {
  389. XAttribute val = style.Attribute(XName.Get("val", DocX.w.NamespaceName));
  390. if (val != null)
  391. {
  392. String cleanValue = val.Value.Replace("-", string.Empty);
  393. if (Enum.IsDefined(typeof(TableDesign), cleanValue))
  394. {
  395. design = (TableDesign)Enum.Parse(typeof(TableDesign), cleanValue);
  396. }
  397. else
  398. {
  399. design = TableDesign.Custom;
  400. }
  401. }
  402. else
  403. design = TableDesign.None;
  404. }
  405. else
  406. design = TableDesign.None;
  407. XElement tableLook = properties.Element(XName.Get("tblLook", DocX.w.NamespaceName));
  408. if (tableLook != null)
  409. {
  410. TableLook = new TableLook();
  411. TableLook.FirstRow = tableLook.GetAttribute(XName.Get("firstRow", DocX.w.NamespaceName)) == "1";
  412. TableLook.LastRow = tableLook.GetAttribute(XName.Get("lastRow", DocX.w.NamespaceName)) == "1";
  413. TableLook.FirstColumn = tableLook.GetAttribute(XName.Get("firstColumn", DocX.w.NamespaceName)) == "1";
  414. TableLook.LastColumn = tableLook.GetAttribute(XName.Get("lastColumn", DocX.w.NamespaceName)) == "1";
  415. TableLook.NoHorizontalBanding = tableLook.GetAttribute(XName.Get("noHBand", DocX.w.NamespaceName)) == "1";
  416. TableLook.NoVerticalBanding = tableLook.GetAttribute(XName.Get("noVBand", DocX.w.NamespaceName)) == "1";
  417. }
  418. }
  419. /// <summary>
  420. /// Extra property for Custom Table Style provided by carpfisher - Thanks
  421. /// </summary>
  422. private string _customTableDesignName;
  423. /// <summary>
  424. /// Extra property for Custom Table Style provided by carpfisher - Thanks
  425. /// </summary>
  426. public string CustomTableDesignName
  427. {
  428. set
  429. {
  430. _customTableDesignName = value;
  431. this.Design = TableDesign.Custom;
  432. }
  433. get
  434. {
  435. return _customTableDesignName;
  436. }
  437. }
  438. /// <summary>
  439. /// String containing the Table Caption value (the table's Alternate Text Title)
  440. /// </summary>
  441. private string _tableCaption;
  442. /// <summary>
  443. /// Gets or Sets the value of the Table Caption (Alternate Text Title) of this table.
  444. /// </summary>
  445. public string TableCaption
  446. {
  447. set
  448. {
  449. XElement tblPr = Xml.Element(XName.Get("tblPr", DocX.w.NamespaceName));
  450. if (tblPr != null)
  451. {
  452. XElement tblCaption =
  453. tblPr.Descendants(XName.Get("tblCaption", DocX.w.NamespaceName)).FirstOrDefault();
  454. if (tblCaption != null)
  455. tblCaption.Remove();
  456. tblCaption = new XElement(XName.Get("tblCaption", DocX.w.NamespaceName),
  457. new XAttribute(XName.Get("val", DocX.w.NamespaceName), value));
  458. tblPr.Add(tblCaption);
  459. }
  460. }
  461. get
  462. {
  463. XElement tblPr = Xml.Element(XName.Get("tblPr", DocX.w.NamespaceName));
  464. if (tblPr != null)
  465. {
  466. XElement caption = tblPr.Element(XName.Get("tblCaption", DocX.w.NamespaceName));
  467. if (caption != null)
  468. {
  469. _tableCaption = caption.GetAttribute(XName.Get("val", DocX.w.NamespaceName));
  470. }
  471. }
  472. return _tableCaption;
  473. }
  474. }
  475. /// <summary>
  476. /// String containing the Table Description (the table's Alternate Text Description).
  477. /// </summary>
  478. private string _tableDescription;
  479. /// <summary>
  480. /// Gets or Sets the value of the Table Description (Alternate Text Description) of this table.
  481. /// </summary>
  482. public string TableDescription
  483. {
  484. set
  485. {
  486. XElement tblPr = Xml.Element(XName.Get("tblPr", DocX.w.NamespaceName));
  487. if (tblPr != null)
  488. {
  489. XElement tblDescription =
  490. tblPr.Descendants(XName.Get("tblDescription", DocX.w.NamespaceName)).FirstOrDefault();
  491. if (tblDescription != null)
  492. tblDescription.Remove();
  493. tblDescription = new XElement(XName.Get("tblDescription", DocX.w.NamespaceName),
  494. new XAttribute(XName.Get("val", DocX.w.NamespaceName), value));
  495. tblPr.Add(tblDescription);
  496. }
  497. }
  498. get
  499. {
  500. XElement tblPr = Xml.Element(XName.Get("tblPr", DocX.w.NamespaceName));
  501. if (tblPr != null)
  502. {
  503. XElement caption = tblPr.Element(XName.Get("tblDescription", DocX.w.NamespaceName));
  504. if (caption != null)
  505. {
  506. _tableDescription = caption.GetAttribute(XName.Get("val", DocX.w.NamespaceName));
  507. }
  508. }
  509. return _tableDescription;
  510. }
  511. }
  512. public TableLook TableLook { get; set; }
  513. public Alignment Alignment
  514. {
  515. get { return alignment; }
  516. set
  517. {
  518. string alignmentString = string.Empty;
  519. switch (value)
  520. {
  521. case Alignment.left:
  522. {
  523. alignmentString = "left";
  524. break;
  525. }
  526. case Alignment.both:
  527. {
  528. alignmentString = "both";
  529. break;
  530. }
  531. case Alignment.right:
  532. {
  533. alignmentString = "right";
  534. break;
  535. }
  536. case Alignment.center:
  537. {
  538. alignmentString = "center";
  539. break;
  540. }
  541. }
  542. XElement tblPr = Xml.Descendants(XName.Get("tblPr", DocX.w.NamespaceName)).First();
  543. XElement jc = tblPr.Descendants(XName.Get("jc", DocX.w.NamespaceName)).FirstOrDefault();
  544. if (jc != null)
  545. jc.Remove();
  546. jc = new XElement(XName.Get("jc", DocX.w.NamespaceName), new XAttribute(XName.Get("val", DocX.w.NamespaceName), alignmentString));
  547. tblPr.Add(jc);
  548. alignment = value;
  549. }
  550. }
  551. /// <summary>
  552. /// Auto size this table according to some rule.
  553. /// </summary>
  554. /// <remarks>Added by Roger Saele, April 2012. Thank you for your contribution Roger.</remarks>
  555. public AutoFit AutoFit
  556. {
  557. get { return autofit; }
  558. set
  559. {
  560. string tableAttributeValue = string.Empty;
  561. string columnAttributeValue = string.Empty;
  562. switch (value)
  563. {
  564. case AutoFit.ColumnWidth:
  565. {
  566. tableAttributeValue = "auto";
  567. columnAttributeValue = "dxa";
  568. // Disable "Automatically resize to fit contents" option
  569. XElement tblPr = Xml.Element(XName.Get("tblPr", DocX.w.NamespaceName));
  570. if (tblPr != null)
  571. {
  572. XElement layout = tblPr.Element(XName.Get("tblLayout", DocX.w.NamespaceName));
  573. if (layout == null)
  574. {
  575. tblPr.Add(new XElement(XName.Get("tblLayout", DocX.w.NamespaceName)));
  576. layout = tblPr.Element(XName.Get("tblLayout", DocX.w.NamespaceName));
  577. }
  578. XAttribute type = layout.Attribute(XName.Get("type", DocX.w.NamespaceName));
  579. if (type == null)
  580. {
  581. layout.Add(new XAttribute(XName.Get("type", DocX.w.NamespaceName), String.Empty));
  582. type = layout.Attribute(XName.Get("type", DocX.w.NamespaceName));
  583. }
  584. type.Value = "fixed";
  585. }
  586. break;
  587. }
  588. case AutoFit.Contents:
  589. {
  590. tableAttributeValue = columnAttributeValue = "auto";
  591. break;
  592. }
  593. case AutoFit.Window:
  594. {
  595. tableAttributeValue = columnAttributeValue = "pct";
  596. break;
  597. }
  598. case AutoFit.Fixed:
  599. // DL added - 20150816:
  600. // Set fixed width for the whole table; columns width is definied in the node: tblGrid
  601. {
  602. tableAttributeValue = columnAttributeValue = "dxa";
  603. XElement tblPr = Xml.Element(XName.Get("tblPr", DocX.w.NamespaceName));
  604. XElement tblLayout = tblPr.Element(XName.Get("tblLayout", DocX.w.NamespaceName));
  605. if (tblLayout == null)
  606. {
  607. XElement tmp = tblPr.Element(XName.Get("tblInd", DocX.w.NamespaceName));
  608. if (tmp == null)
  609. {
  610. tmp = tblPr.Element(XName.Get("tblW", DocX.w.NamespaceName));
  611. }
  612. tmp.AddAfterSelf(new XElement(XName.Get("tblLayout", DocX.w.NamespaceName)));
  613. tmp = tblPr.Element(XName.Get("tblLayout", DocX.w.NamespaceName));
  614. tmp.SetAttributeValue(XName.Get("type", DocX.w.NamespaceName), "fixed");
  615. tmp = tblPr.Element(XName.Get("tblW", DocX.w.NamespaceName));
  616. Double i = 0;
  617. foreach (Double w in ColumnWidths)
  618. i += w;
  619. tmp.SetAttributeValue(XName.Get("w", DocX.w.NamespaceName), i.ToString());
  620. break;
  621. }
  622. else
  623. {
  624. var qry = from d in Xml.Descendants()
  625. let type = d.Attribute(XName.Get("type", DocX.w.NamespaceName))
  626. where (d.Name.LocalName == "tblLayout") && type != null
  627. select type;
  628. foreach (XAttribute type in qry)
  629. type.Value = "fixed";
  630. XElement tmp = tblPr.Element(XName.Get("tblW", DocX.w.NamespaceName));
  631. Double i = 0;
  632. foreach (Double w in ColumnWidths)
  633. i += w;
  634. tmp.SetAttributeValue(XName.Get("w", DocX.w.NamespaceName), i.ToString());
  635. break;
  636. }
  637. }
  638. }
  639. // Set table attributes
  640. var query = from d in Xml.Descendants()
  641. let type = d.Attribute(XName.Get("type", DocX.w.NamespaceName))
  642. where (d.Name.LocalName == "tblW") && type != null
  643. select type;
  644. foreach (XAttribute type in query)
  645. type.Value = tableAttributeValue;
  646. // Set column attributes
  647. query = from d in Xml.Descendants()
  648. let type = d.Attribute(XName.Get("type", DocX.w.NamespaceName))
  649. where (d.Name.LocalName == "tcW") && type != null
  650. select type;
  651. foreach (XAttribute type in query)
  652. type.Value = columnAttributeValue;
  653. autofit = value;
  654. }
  655. }
  656. /// <summary>
  657. /// The design\style to apply to this table.
  658. ///
  659. /// Patch1. Patch to code for Custom Table Style support by carpfisher
  660. /// </summary>
  661. /// <example>
  662. /// Example code for custom table style usage
  663. ///
  664. /// <code>
  665. /// Novacode.DocX document = Novacode.DocX.Load(“DOC01.doc”); // load document with custom table style defined
  666. /// Novacode.Table t = document.AddTable(2, 2); // adds table
  667. /// t.CustomTableDesignName = “MyStyle01”; // assigns Custom Table Design style to newly created table
  668. /// </code>
  669. /// </example>
  670. ///
  671. ///
  672. ///
  673. public TableDesign Design
  674. {
  675. get { return design; }
  676. set
  677. {
  678. XElement tblPr = Xml.Element(XName.Get("tblPr", DocX.w.NamespaceName));
  679. XElement style = tblPr.Element(XName.Get("tblStyle", DocX.w.NamespaceName));
  680. if (style == null)
  681. {
  682. tblPr.Add(new XElement(XName.Get("tblStyle", DocX.w.NamespaceName)));
  683. style = tblPr.Element(XName.Get("tblStyle", DocX.w.NamespaceName));
  684. }
  685. XAttribute val = style.Attribute(XName.Get("val", DocX.w.NamespaceName));
  686. if (val == null)
  687. {
  688. style.Add(new XAttribute(XName.Get("val", DocX.w.NamespaceName), ""));
  689. val = style.Attribute(XName.Get("val", DocX.w.NamespaceName));
  690. }
  691. design = value;
  692. if (design == TableDesign.None)
  693. style.Remove();
  694. if (design == TableDesign.Custom)
  695. {
  696. if (string.IsNullOrEmpty(_customTableDesignName))
  697. {
  698. design = TableDesign.None;
  699. if (style != null)
  700. style.Remove();
  701. }
  702. else
  703. {
  704. val.Value = _customTableDesignName;
  705. }
  706. }
  707. else
  708. {
  709. switch (design)
  710. {
  711. case TableDesign.TableNormal:
  712. val.Value = "TableNormal";
  713. break;
  714. case TableDesign.TableGrid:
  715. val.Value = "TableGrid";
  716. break;
  717. case TableDesign.LightShading:
  718. val.Value = "LightShading";
  719. break;
  720. case TableDesign.LightShadingAccent1:
  721. val.Value = "LightShading-Accent1";
  722. break;
  723. case TableDesign.LightShadingAccent2:
  724. val.Value = "LightShading-Accent2";
  725. break;
  726. case TableDesign.LightShadingAccent3:
  727. val.Value = "LightShading-Accent3";
  728. break;
  729. case TableDesign.LightShadingAccent4:
  730. val.Value = "LightShading-Accent4";
  731. break;
  732. case TableDesign.LightShadingAccent5:
  733. val.Value = "LightShading-Accent5";
  734. break;
  735. case TableDesign.LightShadingAccent6:
  736. val.Value = "LightShading-Accent6";
  737. break;
  738. case TableDesign.LightList:
  739. val.Value = "LightList";
  740. break;
  741. case TableDesign.LightListAccent1:
  742. val.Value = "LightList-Accent1";
  743. break;
  744. case TableDesign.LightListAccent2:
  745. val.Value = "LightList-Accent2";
  746. break;
  747. case TableDesign.LightListAccent3:
  748. val.Value = "LightList-Accent3";
  749. break;
  750. case TableDesign.LightListAccent4:
  751. val.Value = "LightList-Accent4";
  752. break;
  753. case TableDesign.LightListAccent5:
  754. val.Value = "LightList-Accent5";
  755. break;
  756. case TableDesign.LightListAccent6:
  757. val.Value = "LightList-Accent6";
  758. break;
  759. case TableDesign.LightGrid:
  760. val.Value = "LightGrid";
  761. break;
  762. case TableDesign.LightGridAccent1:
  763. val.Value = "LightGrid-Accent1";
  764. break;
  765. case TableDesign.LightGridAccent2:
  766. val.Value = "LightGrid-Accent2";
  767. break;
  768. case TableDesign.LightGridAccent3:
  769. val.Value = "LightGrid-Accent3";
  770. break;
  771. case TableDesign.LightGridAccent4:
  772. val.Value = "LightGrid-Accent4";
  773. break;
  774. case TableDesign.LightGridAccent5:
  775. val.Value = "LightGrid-Accent5";
  776. break;
  777. case TableDesign.LightGridAccent6:
  778. val.Value = "LightGrid-Accent6";
  779. break;
  780. case TableDesign.MediumShading1:
  781. val.Value = "MediumShading1";
  782. break;
  783. case TableDesign.MediumShading1Accent1:
  784. val.Value = "MediumShading1-Accent1";
  785. break;
  786. case TableDesign.MediumShading1Accent2:
  787. val.Value = "MediumShading1-Accent2";
  788. break;
  789. case TableDesign.MediumShading1Accent3:
  790. val.Value = "MediumShading1-Accent3";
  791. break;
  792. case TableDesign.MediumShading1Accent4:
  793. val.Value = "MediumShading1-Accent4";
  794. break;
  795. case TableDesign.MediumShading1Accent5:
  796. val.Value = "MediumShading1-Accent5";
  797. break;
  798. case TableDesign.MediumShading1Accent6:
  799. val.Value = "MediumShading1-Accent6";
  800. break;
  801. case TableDesign.MediumShading2:
  802. val.Value = "MediumShading2";
  803. break;
  804. case TableDesign.MediumShading2Accent1:
  805. val.Value = "MediumShading2-Accent1";
  806. break;
  807. case TableDesign.MediumShading2Accent2:
  808. val.Value = "MediumShading2-Accent2";
  809. break;
  810. case TableDesign.MediumShading2Accent3:
  811. val.Value = "MediumShading2-Accent3";
  812. break;
  813. case TableDesign.MediumShading2Accent4:
  814. val.Value = "MediumShading2-Accent4";
  815. break;
  816. case TableDesign.MediumShading2Accent5:
  817. val.Value = "MediumShading2-Accent5";
  818. break;
  819. case TableDesign.MediumShading2Accent6:
  820. val.Value = "MediumShading2-Accent6";
  821. break;
  822. case TableDesign.MediumList1:
  823. val.Value = "MediumList1";
  824. break;
  825. case TableDesign.MediumList1Accent1:
  826. val.Value = "MediumList1-Accent1";
  827. break;
  828. case TableDesign.MediumList1Accent2:
  829. val.Value = "MediumList1-Accent2";
  830. break;
  831. case TableDesign.MediumList1Accent3:
  832. val.Value = "MediumList1-Accent3";
  833. break;
  834. case TableDesign.MediumList1Accent4:
  835. val.Value = "MediumList1-Accent4";
  836. break;
  837. case TableDesign.MediumList1Accent5:
  838. val.Value = "MediumList1-Accent5";
  839. break;
  840. case TableDesign.MediumList1Accent6:
  841. val.Value = "MediumList1-Accent6";
  842. break;
  843. case TableDesign.MediumList2:
  844. val.Value = "MediumList2";
  845. break;
  846. case TableDesign.MediumList2Accent1:
  847. val.Value = "MediumList2-Accent1";
  848. break;
  849. case TableDesign.MediumList2Accent2:
  850. val.Value = "MediumList2-Accent2";
  851. break;
  852. case TableDesign.MediumList2Accent3:
  853. val.Value = "MediumList2-Accent3";
  854. break;
  855. case TableDesign.MediumList2Accent4:
  856. val.Value = "MediumList2-Accent4";
  857. break;
  858. case TableDesign.MediumList2Accent5:
  859. val.Value = "MediumList2-Accent5";
  860. break;
  861. case TableDesign.MediumList2Accent6:
  862. val.Value = "MediumList2-Accent6";
  863. break;
  864. case TableDesign.MediumGrid1:
  865. val.Value = "MediumGrid1";
  866. break;
  867. case TableDesign.MediumGrid1Accent1:
  868. val.Value = "MediumGrid1-Accent1";
  869. break;
  870. case TableDesign.MediumGrid1Accent2:
  871. val.Value = "MediumGrid1-Accent2";
  872. break;
  873. case TableDesign.MediumGrid1Accent3:
  874. val.Value = "MediumGrid1-Accent3";
  875. break;
  876. case TableDesign.MediumGrid1Accent4:
  877. val.Value = "MediumGrid1-Accent4";
  878. break;
  879. case TableDesign.MediumGrid1Accent5:
  880. val.Value = "MediumGrid1-Accent5";
  881. break;
  882. case TableDesign.MediumGrid1Accent6:
  883. val.Value = "MediumGrid1-Accent6";
  884. break;
  885. case TableDesign.MediumGrid2:
  886. val.Value = "MediumGrid2";
  887. break;
  888. case TableDesign.MediumGrid2Accent1:
  889. val.Value = "MediumGrid2-Accent1";
  890. break;
  891. case TableDesign.MediumGrid2Accent2:
  892. val.Value = "MediumGrid2-Accent2";
  893. break;
  894. case TableDesign.MediumGrid2Accent3:
  895. val.Value = "MediumGrid2-Accent3";
  896. break;
  897. case TableDesign.MediumGrid2Accent4:
  898. val.Value = "MediumGrid2-Accent4";
  899. break;
  900. case TableDesign.MediumGrid2Accent5:
  901. val.Value = "MediumGrid2-Accent5";
  902. break;
  903. case TableDesign.MediumGrid2Accent6:
  904. val.Value = "MediumGrid2-Accent6";
  905. break;
  906. case TableDesign.MediumGrid3:
  907. val.Value = "MediumGrid3";
  908. break;
  909. case TableDesign.MediumGrid3Accent1:
  910. val.Value = "MediumGrid3-Accent1";
  911. break;
  912. case TableDesign.MediumGrid3Accent2:
  913. val.Value = "MediumGrid3-Accent2";
  914. break;
  915. case TableDesign.MediumGrid3Accent3:
  916. val.Value = "MediumGrid3-Accent3";
  917. break;
  918. case TableDesign.MediumGrid3Accent4:
  919. val.Value = "MediumGrid3-Accent4";
  920. break;
  921. case TableDesign.MediumGrid3Accent5:
  922. val.Value = "MediumGrid3-Accent5";
  923. break;
  924. case TableDesign.MediumGrid3Accent6:
  925. val.Value = "MediumGrid3-Accent6";
  926. break;
  927. case TableDesign.DarkList:
  928. val.Value = "DarkList";
  929. break;
  930. case TableDesign.DarkListAccent1:
  931. val.Value = "DarkList-Accent1";
  932. break;
  933. case TableDesign.DarkListAccent2:
  934. val.Value = "DarkList-Accent2";
  935. break;
  936. case TableDesign.DarkListAccent3:
  937. val.Value = "DarkList-Accent3";
  938. break;
  939. case TableDesign.DarkListAccent4:
  940. val.Value = "DarkList-Accent4";
  941. break;
  942. case TableDesign.DarkListAccent5:
  943. val.Value = "DarkList-Accent5";
  944. break;
  945. case TableDesign.DarkListAccent6:
  946. val.Value = "DarkList-Accent6";
  947. break;
  948. case TableDesign.ColorfulShading:
  949. val.Value = "ColorfulShading";
  950. break;
  951. case TableDesign.ColorfulShadingAccent1:
  952. val.Value = "ColorfulShading-Accent1";
  953. break;
  954. case TableDesign.ColorfulShadingAccent2:
  955. val.Value = "ColorfulShading-Accent2";
  956. break;
  957. case TableDesign.ColorfulShadingAccent3:
  958. val.Value = "ColorfulShading-Accent3";
  959. break;
  960. case TableDesign.ColorfulShadingAccent4:
  961. val.Value = "ColorfulShading-Accent4";
  962. break;
  963. case TableDesign.ColorfulShadingAccent5:
  964. val.Value = "ColorfulShading-Accent5";
  965. break;
  966. case TableDesign.ColorfulShadingAccent6:
  967. val.Value = "ColorfulShading-Accent6";
  968. break;
  969. case TableDesign.ColorfulList:
  970. val.Value = "ColorfulList";
  971. break;
  972. case TableDesign.ColorfulListAccent1:
  973. val.Value = "ColorfulList-Accent1";
  974. break;
  975. case TableDesign.ColorfulListAccent2:
  976. val.Value = "ColorfulList-Accent2";
  977. break;
  978. case TableDesign.ColorfulListAccent3:
  979. val.Value = "ColorfulList-Accent3";
  980. break;
  981. case TableDesign.ColorfulListAccent4:
  982. val.Value = "ColorfulList-Accent4";
  983. break;
  984. case TableDesign.ColorfulListAccent5:
  985. val.Value = "ColorfulList-Accent5";
  986. break;
  987. case TableDesign.ColorfulListAccent6:
  988. val.Value = "ColorfulList-Accent6";
  989. break;
  990. case TableDesign.ColorfulGrid:
  991. val.Value = "ColorfulGrid";
  992. break;
  993. case TableDesign.ColorfulGridAccent1:
  994. val.Value = "ColorfulGrid-Accent1";
  995. break;
  996. case TableDesign.ColorfulGridAccent2:
  997. val.Value = "ColorfulGrid-Accent2";
  998. break;
  999. case TableDesign.ColorfulGridAccent3:
  1000. val.Value = "ColorfulGrid-Accent3";
  1001. break;
  1002. case TableDesign.ColorfulGridAccent4:
  1003. val.Value = "ColorfulGrid-Accent4";
  1004. break;
  1005. case TableDesign.ColorfulGridAccent5:
  1006. val.Value = "ColorfulGrid-Accent5";
  1007. break;
  1008. case TableDesign.ColorfulGridAccent6:
  1009. val.Value = "ColorfulGrid-Accent6";
  1010. break;
  1011. default:
  1012. break;
  1013. }
  1014. }
  1015. if (Document.styles == null)
  1016. {
  1017. PackagePart word_styles = Document.package.GetPart(new Uri("/word/styles.xml", UriKind.Relative));
  1018. using (TextReader tr = new StreamReader(word_styles.GetStream()))
  1019. Document.styles = XDocument.Load(tr);
  1020. }
  1021. var tableStyle =
  1022. (
  1023. from e in Document.styles.Descendants()
  1024. let styleId = e.Attribute(XName.Get("styleId", DocX.w.NamespaceName))
  1025. where (styleId != null && styleId.Value == val.Value)
  1026. select e
  1027. ).FirstOrDefault();
  1028. if (tableStyle == null)
  1029. {
  1030. XDocument external_style_doc = HelperFunctions.DecompressXMLResource("Novacode.Resources.styles.xml.gz");
  1031. var styleElement =
  1032. (
  1033. from e in external_style_doc.Descendants()
  1034. let styleId = e.Attribute(XName.Get("styleId", DocX.w.NamespaceName))
  1035. where (styleId != null && styleId.Value == val.Value)
  1036. select e
  1037. ).First();
  1038. Document.styles.Element(XName.Get("styles", DocX.w.NamespaceName)).Add(styleElement);
  1039. }
  1040. }
  1041. }
  1042. /// <summary>
  1043. /// Returns the index of this Table.
  1044. /// </summary>
  1045. /// <example>
  1046. /// Replace the first table in this document with a new Table.
  1047. /// <code>
  1048. /// // Load a document into memory.
  1049. /// using (DocX document = DocX.Load(@"Test.docx"))
  1050. /// {
  1051. /// // Get the first Table in this document.
  1052. /// Table t = document.Tables[0];
  1053. ///
  1054. /// // Get the character index of Table t in this document.
  1055. /// int index = t.Index;
  1056. ///
  1057. /// // Remove Table t.
  1058. /// t.Remove();
  1059. ///
  1060. /// // Insert a new Table at the original index of Table t.
  1061. /// Table newTable = document.InsertTable(index, 4, 4);
  1062. ///
  1063. /// // Set the design of this new Table, so that we can see it.
  1064. /// newTable.Design = TableDesign.LightShadingAccent1;
  1065. ///
  1066. /// // Save all changes made to the document.
  1067. /// document.Save();
  1068. /// } // Release this document from memory.
  1069. /// </code>
  1070. /// </example>
  1071. public int Index
  1072. {
  1073. get
  1074. {
  1075. int index = 0;
  1076. IEnumerable<XElement> previous = Xml.ElementsBeforeSelf();
  1077. foreach (XElement e in previous)
  1078. index += Paragraph.GetElementTextLength(e);
  1079. return index;
  1080. }
  1081. }
  1082. /// <summary>
  1083. /// Remove this Table from this document.
  1084. /// </summary>
  1085. /// <example>
  1086. /// Remove the first Table from this document.
  1087. /// <code>
  1088. /// // Load a document into memory.
  1089. /// using (DocX document = DocX.Load(@"Test.docx"))
  1090. /// {
  1091. /// // Get the first Table in this document.
  1092. /// Table t = d.Tables[0];
  1093. ///
  1094. /// // Remove this Table.
  1095. /// t.Remove();
  1096. ///
  1097. /// // Save all changes made to the document.
  1098. /// document.Save();
  1099. /// } // Release this document from memory.
  1100. /// </code>
  1101. /// </example>
  1102. public void Remove()
  1103. {
  1104. Xml.Remove();
  1105. }
  1106. /// <summary>
  1107. /// Insert a row at the end of this table.
  1108. /// </summary>
  1109. /// <example>
  1110. /// <code>
  1111. /// // Load a document.
  1112. /// using (DocX document = DocX.Load(@"C:\Example\Test.docx"))
  1113. /// {
  1114. /// // Get the first table in this document.
  1115. /// Table table = document.Tables[0];
  1116. ///
  1117. /// // Insert a new row at the end of this table.
  1118. /// Row row = table.InsertRow();
  1119. ///
  1120. /// // Loop through each cell in this new row.
  1121. /// foreach (Cell c in row.Cells)
  1122. /// {
  1123. /// // Set the text of each new cell to "Hello".
  1124. /// c.Paragraphs[0].InsertText("Hello", false);
  1125. /// }
  1126. ///
  1127. /// // Save the document to a new file.
  1128. /// document.SaveAs(@"C:\Example\Test2.docx");
  1129. /// }// Release this document from memory.
  1130. /// </code>
  1131. /// </example>
  1132. /// <returns>A new row.</returns>
  1133. public Row InsertRow()
  1134. {
  1135. return InsertRow(RowCount);
  1136. }
  1137. /// <summary>
  1138. /// Insert a copy of a row at the end of this table.
  1139. /// </summary>
  1140. /// <returns>A new row.</returns>
  1141. public Row InsertRow(Row row)
  1142. {
  1143. return InsertRow(row, RowCount);
  1144. }
  1145. /// <summary>
  1146. /// Insert a column to the right of a Table.
  1147. /// </summary>
  1148. /// <example>
  1149. /// <code>
  1150. /// // Load a document.
  1151. /// using (DocX document = DocX.Load(@"C:\Example\Test.docx"))
  1152. /// {
  1153. /// // Get the first Table in this document.
  1154. /// Table table = document.Tables[0];
  1155. ///
  1156. /// // Insert a new column to this right of this table.
  1157. /// table.InsertColumn();
  1158. ///
  1159. /// // Set the new columns text to "Row no."
  1160. /// table.Rows[0].Cells[table.ColumnCount - 1].Paragraph.InsertText("Row no.", false);
  1161. ///
  1162. /// // Loop through each row in the table.
  1163. /// for (int i = 1; i &lt; table.Rows.Count; i++)
  1164. /// {
  1165. /// // The current row.
  1166. /// Row row = table.Rows[i];
  1167. ///
  1168. /// // The cell in this row that belongs to the new column.
  1169. /// Cell cell = row.Cells[table.ColumnCount - 1];
  1170. ///
  1171. /// // The first Paragraph that this cell houses.
  1172. /// Paragraph p = cell.Paragraphs[0];
  1173. ///
  1174. /// // Insert this rows index.
  1175. /// p.InsertText(i.ToString(), false);
  1176. /// }
  1177. ///
  1178. /// document.Save();
  1179. /// }// Release this document from memory.
  1180. /// </code>
  1181. /// </example>
  1182. public void InsertColumn()
  1183. {
  1184. InsertColumn(ColumnCount, true);
  1185. }
  1186. /// <summary>
  1187. /// Remove the last row from this Table.
  1188. /// </summary>
  1189. /// <example>
  1190. /// Remove the last row from a Table.
  1191. /// <code>
  1192. /// // Load a document.
  1193. /// using (DocX document = DocX.Load(@"C:\Example\Test.docx"))
  1194. /// {
  1195. /// // Get the first table in this document.
  1196. /// Table table = document.Tables[0];
  1197. ///
  1198. /// // Remove the last row from this table.
  1199. /// table.RemoveRow();
  1200. ///
  1201. /// // Save the document.
  1202. /// document.Save();
  1203. /// }// Release this document from memory.
  1204. /// </code>
  1205. /// </example>
  1206. public void RemoveRow()
  1207. {
  1208. RemoveRow(RowCount - 1);
  1209. }
  1210. /// <summary>
  1211. /// Remove a row from this Table.
  1212. /// </summary>
  1213. /// <param name="index">The row to remove.</param>
  1214. /// <example>
  1215. /// Remove the first row from a Table.
  1216. /// <code>
  1217. /// // Load a document.
  1218. /// using (DocX document = DocX.Load(@"C:\Example\Test.docx"))
  1219. /// {
  1220. /// // Get the first table in this document.
  1221. /// Table table = document.Tables[0];
  1222. ///
  1223. /// // Remove the first row from this table.
  1224. /// table.RemoveRow(0);
  1225. ///
  1226. /// // Save the document.
  1227. /// document.Save();
  1228. /// }// Release this document from memory.
  1229. /// </code>
  1230. /// </example>
  1231. public void RemoveRow(int index)
  1232. {
  1233. if (index < 0 || index > RowCount - 1)
  1234. throw new IndexOutOfRangeException();
  1235. Rows[index].Xml.Remove();
  1236. if (Rows.Count == 0)
  1237. Remove();
  1238. }
  1239. /// <summary>
  1240. /// Remove the last column for this Table.
  1241. /// </summary>
  1242. /// <example>
  1243. /// Remove the last column from a Table.
  1244. /// <code>
  1245. /// // Load a document.
  1246. /// using (DocX document = DocX.Load(@"C:\Example\Test.docx"))
  1247. /// {
  1248. /// // Get the first table in this document.
  1249. /// Table table = document.Tables[0];
  1250. ///
  1251. /// // Remove the last column from this table.
  1252. /// table.RemoveColumn();
  1253. ///
  1254. /// // Save the document.
  1255. /// document.Save();
  1256. /// }// Release this document from memory.
  1257. /// </code>
  1258. /// </example>
  1259. public void RemoveColumn()
  1260. {
  1261. RemoveColumn(ColumnCount - 1);
  1262. }
  1263. /// <summary>
  1264. /// Remove a column from this Table.
  1265. /// </summary>
  1266. /// <param name="index">The column to remove.</param>
  1267. /// <example>
  1268. /// Remove the first column from a Table.
  1269. /// <code>
  1270. /// // Load a document.
  1271. /// using (DocX document = DocX.Load(@"C:\Example\Test.docx"))
  1272. /// {
  1273. /// // Get the first table in this document.
  1274. /// Table table = document.Tables[0];
  1275. ///
  1276. /// // Remove the first column from this table.
  1277. /// table.RemoveColumn(0);
  1278. ///
  1279. /// // Save the document.
  1280. /// document.Save();
  1281. /// }// Release this document from memory.
  1282. /// </code>
  1283. /// </example>
  1284. public void RemoveColumn(int index)
  1285. {
  1286. if (index < 0 || index > ColumnCount - 1)
  1287. throw new IndexOutOfRangeException();
  1288. foreach (Row r in Rows)
  1289. if (r.Cells.Count < ColumnCount)
  1290. {
  1291. var positionIndex = 0;
  1292. var actualPosition = 0;
  1293. var gridAfterVal = 0;
  1294. // checks to see if there is a deleted cell
  1295. gridAfterVal = r.gridAfter;
  1296. // goes through iteration of cells to find the one the that contains the index number
  1297. foreach (Cell rowCell in r.Cells)
  1298. {
  1299. // checks if the cell has a gridspan
  1300. var gridSpanVal = 0;
  1301. if (rowCell.GridSpan != 0)
  1302. {
  1303. gridSpanVal = rowCell.GridSpan - 1;
  1304. }
  1305. // checks to see if the index is within its lowest and highest cell value
  1306. if ((index - gridAfterVal) >= actualPosition
  1307. && (index - gridAfterVal) <= (actualPosition + gridSpanVal))
  1308. {
  1309. r.Cells[positionIndex].Xml.Remove();
  1310. break;
  1311. }
  1312. positionIndex += 1;
  1313. actualPosition += gridSpanVal + 1;
  1314. }
  1315. }
  1316. else
  1317. {
  1318. r.Cells[index].Xml.Remove();
  1319. }
  1320. _cachedColCount = -1;
  1321. }
  1322. /// <summary>
  1323. /// Insert a row into this table.
  1324. /// </summary>
  1325. /// <example>
  1326. /// <code>
  1327. /// // Load a document.
  1328. /// using (DocX document = DocX.Load(@"C:\Example\Test.docx"))
  1329. /// {
  1330. /// // Get the first table in this document.
  1331. /// Table table = document.Tables[0];
  1332. ///
  1333. /// // Insert a new row at index 1 in this table.
  1334. /// Row row = table.InsertRow(1);
  1335. ///
  1336. /// // Loop through each cell in this new row.
  1337. /// foreach (Cell c in row.Cells)
  1338. /// {
  1339. /// // Set the text of each new cell to "Hello".
  1340. /// c.Paragraphs[0].InsertText("Hello", false);
  1341. /// }
  1342. ///
  1343. /// // Save the document to a new file.
  1344. /// document.SaveAs(@"C:\Example\Test2.docx");
  1345. /// }// Release this document from memory.
  1346. /// </code>
  1347. /// </example>
  1348. /// <param name="index">Index to insert row at.</param>
  1349. /// <returns>A new Row</returns>
  1350. public Row InsertRow(int index)
  1351. {
  1352. if (index < 0 || index > RowCount)
  1353. throw new IndexOutOfRangeException();
  1354. List<XElement> content = new List<XElement>();
  1355. for (int i = 0; i < ColumnCount; i++)
  1356. {
  1357. var w = 2310d;
  1358. if (ColumnWidthsValue != null && ColumnWidthsValue.Length > i)
  1359. w = ColumnWidthsValue[i] * 15;
  1360. XElement cell = HelperFunctions.CreateTableCell(w);
  1361. content.Add(cell);
  1362. }
  1363. return InsertRow(content, index);
  1364. }
  1365. /// <summary>
  1366. /// Insert a copy of a row into this table.
  1367. /// </summary>
  1368. /// <param name="row">Row to copy and insert.</param>
  1369. /// <param name="index">Index to insert row at.</param>
  1370. /// <returns>A new Row</returns>
  1371. public Row InsertRow(Row row, int index)
  1372. {
  1373. if (row == null)
  1374. throw new ArgumentNullException(nameof(row));
  1375. if (index < 0 || index > RowCount)
  1376. throw new IndexOutOfRangeException();
  1377. List<XElement> content = row.Xml.Elements(XName.Get("tc", DocX.w.NamespaceName)).Select(element => HelperFunctions.CloneElement(element)).ToList();
  1378. return InsertRow(content, index);
  1379. }
  1380. private Row InsertRow(List<XElement> content, Int32 index)
  1381. {
  1382. Row newRow = new Row(this, Document, new XElement(XName.Get("tr", DocX.w.NamespaceName), content));
  1383. XElement rowXml;
  1384. if (index == Rows.Count)
  1385. {
  1386. rowXml = Rows.Last().Xml;
  1387. rowXml.AddAfterSelf(newRow.Xml);
  1388. }
  1389. else
  1390. {
  1391. rowXml = Rows[index].Xml;
  1392. rowXml.AddBeforeSelf(newRow.Xml);
  1393. }
  1394. return newRow;
  1395. }
  1396. /// <summary>
  1397. /// Insert a column into a table.
  1398. /// </summary>
  1399. /// <param name="index">The index to insert the column at.</param>
  1400. /// <param name="direction">The side in which you wish to place the colum(True right, false left)</param>
  1401. /// <example>
  1402. /// Insert a column to the left of a table.
  1403. /// <code>
  1404. /// // Load a document.
  1405. /// using (DocX document = DocX.Load(@"C:\Example\Test.docx"))
  1406. /// {
  1407. /// // Get the first Table in this document.
  1408. /// Table table = document.Tables[0];
  1409. ///
  1410. /// // Insert a new column to this left of this table.
  1411. /// table.InsertColumn(0, false);
  1412. ///
  1413. /// // Set the new columns text to "Row no."
  1414. /// table.Rows[0].Cells[table.ColumnCount - 1].Paragraph.InsertText("Row no.", false);
  1415. ///
  1416. /// // Loop through each row in the table.
  1417. /// for (int i = 1; i &lt; table.Rows.Count; i++)
  1418. /// {
  1419. /// // The current row.
  1420. /// Row row = table.Rows[i];
  1421. ///
  1422. /// // The cell in this row that belongs to the new column.
  1423. /// Cell cell = row.Cells[table.ColumnCount - 1];
  1424. ///
  1425. /// // The first Paragraph that this cell houses.
  1426. /// Paragraph p = cell.Paragraphs[0];
  1427. ///
  1428. /// // Insert this rows index.
  1429. /// p.InsertText(i.ToString(), false);
  1430. /// }
  1431. ///
  1432. /// document.Save();
  1433. /// }// Release this document from memory.
  1434. /// </code>
  1435. /// </example>
  1436. public void InsertColumn(int index, bool direction)
  1437. {
  1438. var columnCount = ColumnCount;
  1439. if (RowCount > 0)
  1440. {
  1441. if (index > 0 && index <= columnCount)
  1442. {
  1443. _cachedColCount = -1;
  1444. foreach (Row r in Rows)
  1445. {
  1446. // create cell
  1447. XElement cell = HelperFunctions.CreateTableCell();
  1448. // insert cell
  1449. // checks if it is in bounds of index
  1450. if (r.Cells.Count < columnCount)
  1451. {
  1452. if (index >= columnCount)
  1453. {
  1454. AddCellToRow(r, cell, r.Cells.Count, direction);
  1455. }
  1456. else
  1457. {
  1458. bool directionTest = true;
  1459. var positionIndex = 1;
  1460. var actualPosition = 1;
  1461. var gridAfterVal = 0;
  1462. // checks to see if there is a deleted cell
  1463. gridAfterVal = r.gridAfter;
  1464. // goes through iteration of cells to find the one the that contains the index number
  1465. foreach (Cell rowCell in r.Cells)
  1466. {
  1467. // checks if the cell has a gridspan
  1468. var gridSpanVal = 0;
  1469. if (rowCell.GridSpan != 0)
  1470. {
  1471. gridSpanVal = rowCell.GridSpan - 1;
  1472. }
  1473. // checks to see if the index is within its lowest and highest cell value
  1474. if ((index - gridAfterVal) >= actualPosition
  1475. && (index - gridAfterVal) <= (actualPosition + gridSpanVal))
  1476. {
  1477. if (index == (actualPosition + gridSpanVal) && direction == true)
  1478. {
  1479. directionTest = true;
  1480. }
  1481. else
  1482. {
  1483. directionTest = false;
  1484. }
  1485. AddCellToRow(r, cell, positionIndex, directionTest);
  1486. break;
  1487. }
  1488. positionIndex += 1;
  1489. actualPosition += gridSpanVal + 1;
  1490. }
  1491. }
  1492. }
  1493. else if (r.Cells.Count == index)
  1494. {
  1495. AddCellToRow(r, cell, index, direction);
  1496. }
  1497. else
  1498. AddCellToRow(r, cell, index, direction);
  1499. }
  1500. }
  1501. else
  1502. {
  1503. throw new IndexOutOfRangeException("Out of index bounds, column count is " + columnCount + " you input " + index);
  1504. }
  1505. }
  1506. }
  1507. /// <summary>
  1508. /// Adds a cell to the right or left of a cell
  1509. /// </summary>
  1510. /// <param name="row">is the row you are adding</param>
  1511. /// <param name="cell">is the cell you are adding</param>
  1512. /// <param name="index">the cell index position you are refferencing from</param>
  1513. /// <param name="direction">which side of the cell you wish to add cell</param>
  1514. private void AddCellToRow(Row row, XElement cell, int index, bool direction)
  1515. {
  1516. index -= 1;
  1517. if (direction)
  1518. {
  1519. row.Cells[index].Xml.AddAfterSelf(cell);
  1520. }
  1521. else
  1522. {
  1523. row.Cells[index].Xml.AddBeforeSelf(cell);
  1524. }
  1525. }
  1526. /// <summary>
  1527. /// Deletes a cell in a row
  1528. /// </summary>
  1529. /// <param name="rowIndex">index of the row you want to remove the cell</param>
  1530. /// <param name="celIndex">index of the cell you want to remove</param>
  1531. public void DeleteAndShiftCellsLeft(int rowIndex, int celIndex)
  1532. {
  1533. XAttribute gridAfterVal = new XAttribute(XName.Get("val", DocX.w.NamespaceName), 0);
  1534. var trPr = Rows[rowIndex].Xml.Element(XName.Get("trPr", DocX.w.NamespaceName));
  1535. if (trPr != null)
  1536. {
  1537. var gridAfter = trPr.Element(XName.Get("gridAfter", DocX.w.NamespaceName));
  1538. if (gridAfter != null)
  1539. {
  1540. var val = gridAfter.Attribute(XName.Get("val", DocX.w.NamespaceName));
  1541. if (val != null)
  1542. {
  1543. val.Value = (int.Parse(val.Value) + 1).ToString();
  1544. }
  1545. else
  1546. {
  1547. val.Value = "1";
  1548. }
  1549. }
  1550. else
  1551. {
  1552. var gridAfterElement = new XElement("gridAfter");
  1553. var gridAfterValAttribute = new XAttribute("val", 1);
  1554. gridAfter.SetAttributeValue("val", 1);
  1555. }
  1556. }
  1557. else
  1558. {
  1559. XElement trPrXElement = new XElement(XName.Get("trPr", DocX.w.NamespaceName));
  1560. XElement gridAfterElement = new XElement(XName.Get("gridAfter", DocX.w.NamespaceName));
  1561. XAttribute gridAfterValAttribute = new XAttribute(XName.Get("val", DocX.w.NamespaceName), 1);
  1562. gridAfterElement.Add(gridAfterValAttribute);
  1563. trPrXElement.Add(gridAfterElement);
  1564. Rows[rowIndex].Xml.AddFirst(trPrXElement);
  1565. }
  1566. var columnCount = this.ColumnCount;
  1567. if (celIndex <= this.ColumnCount && this.Rows[rowIndex].ColumnCount <= this.ColumnCount)
  1568. {
  1569. Rows[rowIndex].Cells[celIndex].Xml.Remove();
  1570. }
  1571. }
  1572. /// <summary>
  1573. /// Insert a page break before a Table.
  1574. /// </summary>
  1575. /// <example>
  1576. /// Insert a Table and a Paragraph into a document with a page break between them.
  1577. /// <code>
  1578. /// // Create a new document.
  1579. /// using (DocX document = DocX.Create(@"Test.docx"))
  1580. /// {
  1581. /// // Insert a new Paragraph.
  1582. /// Paragraph p1 = document.InsertParagraph("Paragraph", false);
  1583. ///
  1584. /// // Insert a new Table.
  1585. /// Table t1 = document.InsertTable(2, 2);
  1586. /// t1.Design = TableDesign.LightShadingAccent1;
  1587. ///
  1588. /// // Insert a page break before this Table.
  1589. /// t1.InsertPageBreakBeforeSelf();
  1590. ///
  1591. /// // Save this document.
  1592. /// document.Save();
  1593. /// }// Release this document from memory.
  1594. /// </code>
  1595. /// </example>
  1596. public override void InsertPageBreakBeforeSelf()
  1597. {
  1598. base.InsertPageBreakBeforeSelf();
  1599. }
  1600. /// <summary>
  1601. /// Insert a page break after a Table.
  1602. /// </summary>
  1603. /// <example>
  1604. /// Insert a Table and a Paragraph into a document with a page break between them.
  1605. /// <code>
  1606. /// // Create a new document.
  1607. /// using (DocX document = DocX.Create(@"Test.docx"))
  1608. /// {
  1609. /// // Insert a new Table.
  1610. /// Table t1 = document.InsertTable(2, 2);
  1611. /// t1.Design = TableDesign.LightShadingAccent1;
  1612. ///
  1613. /// // Insert a page break after this Table.
  1614. /// t1.InsertPageBreakAfterSelf();
  1615. ///
  1616. /// // Insert a new Paragraph.
  1617. /// Paragraph p1 = document.InsertParagraph("Paragraph", false);
  1618. ///
  1619. /// // Save this document.
  1620. /// document.Save();
  1621. /// }// Release this document from memory.
  1622. /// </code>
  1623. /// </example>
  1624. public override void InsertPageBreakAfterSelf()
  1625. {
  1626. base.InsertPageBreakAfterSelf();
  1627. }
  1628. /// <summary>
  1629. /// Insert a new Table before this Table, this Table can be from this document or another document.
  1630. /// </summary>
  1631. /// <param name="t">The Table t to be inserted</param>
  1632. /// <returns>A new Table inserted before this Table.</returns>
  1633. /// <example>
  1634. /// Insert a new Table before this Table.
  1635. /// <code>
  1636. /// // Place holder for a Table.
  1637. /// Table t;
  1638. ///
  1639. /// // Load document a.
  1640. /// using (DocX documentA = DocX.Load(@"a.docx"))
  1641. /// {
  1642. /// // Get the first Table from this document.
  1643. /// t = documentA.Tables[0];
  1644. /// }
  1645. ///
  1646. /// // Load document b.
  1647. /// using (DocX documentB = DocX.Load(@"b.docx"))
  1648. /// {
  1649. /// // Get the first Table in document b.
  1650. /// Table t2 = documentB.Tables[0];
  1651. ///
  1652. /// // Insert the Table from document a before this Table.
  1653. /// Table newTable = t2.InsertTableBeforeSelf(t);
  1654. ///
  1655. /// // Save all changes made to document b.
  1656. /// documentB.Save();
  1657. /// }// Release this document from memory.
  1658. /// </code>
  1659. /// </example>
  1660. public override Table InsertTableBeforeSelf(Table t)
  1661. {
  1662. return base.InsertTableBeforeSelf(t);
  1663. }
  1664. /// <summary>
  1665. /// Insert a new Table into this document before this Table.
  1666. /// </summary>
  1667. /// <param name="rowCount">The number of rows this Table should have.</param>
  1668. /// <param name="columnCount">The number of columns this Table should have.</param>
  1669. /// <returns>A new Table inserted before this Table.</returns>
  1670. /// <example>
  1671. /// <code>
  1672. /// // Create a new document.
  1673. /// using (DocX document = DocX.Create(@"Test.docx"))
  1674. /// {
  1675. /// //Insert a Table into this document.
  1676. /// Table t = document.InsertTable(2, 2);
  1677. /// t.Design = TableDesign.LightShadingAccent1;
  1678. /// t.Alignment = Alignment.center;
  1679. ///
  1680. /// // Insert a new Table before this Table.
  1681. /// Table newTable = t.InsertTableBeforeSelf(2, 2);
  1682. /// newTable.Design = TableDesign.LightShadingAccent2;
  1683. /// newTable.Alignment = Alignment.center;
  1684. ///
  1685. /// // Save all changes made to this document.
  1686. /// document.Save();
  1687. /// }// Release this document from memory.
  1688. /// </code>
  1689. /// </example>
  1690. public override Table InsertTableBeforeSelf(int rowCount, int columnCount)
  1691. {
  1692. return base.InsertTableBeforeSelf(rowCount, columnCount);
  1693. }
  1694. /// <summary>
  1695. /// Insert a new Table after this Table, this Table can be from this document or another document.
  1696. /// </summary>
  1697. /// <param name="t">The Table t to be inserted</param>
  1698. /// <returns>A new Table inserted after this Table.</returns>
  1699. /// <example>
  1700. /// Insert a new Table after this Table.
  1701. /// <code>
  1702. /// // Place holder for a Table.
  1703. /// Table t;
  1704. ///
  1705. /// // Load document a.
  1706. /// using (DocX documentA = DocX.Load(@"a.docx"))
  1707. /// {
  1708. /// // Get the first Table from this document.
  1709. /// t = documentA.Tables[0];
  1710. /// }
  1711. ///
  1712. /// // Load document b.
  1713. /// using (DocX documentB = DocX.Load(@"b.docx"))
  1714. /// {
  1715. /// // Get the first Table in document b.
  1716. /// Table t2 = documentB.Tables[0];
  1717. ///
  1718. /// // Insert the Table from document a after this Table.
  1719. /// Table newTable = t2.InsertTableAfterSelf(t);
  1720. ///
  1721. /// // Save all changes made to document b.
  1722. /// documentB.Save();
  1723. /// }// Release this document from memory.
  1724. /// </code>
  1725. /// </example>
  1726. public override Table InsertTableAfterSelf(Table t)
  1727. {
  1728. return base.InsertTableAfterSelf(t);
  1729. }
  1730. /// <summary>
  1731. /// Insert a new Table into this document after this Table.
  1732. /// </summary>
  1733. /// <param name="rowCount">The number of rows this Table should have.</param>
  1734. /// <param name="columnCount">The number of columns this Table should have.</param>
  1735. /// <returns>A new Table inserted before this Table.</returns>
  1736. /// <example>
  1737. /// <code>
  1738. /// // Create a new document.
  1739. /// using (DocX document = DocX.Create(@"Test.docx"))
  1740. /// {
  1741. /// //Insert a Table into this document.
  1742. /// Table t = document.InsertTable(2, 2);
  1743. /// t.Design = TableDesign.LightShadingAccent1;
  1744. /// t.Alignment = Alignment.center;
  1745. ///
  1746. /// // Insert a new Table after this Table.
  1747. /// Table newTable = t.InsertTableAfterSelf(2, 2);
  1748. /// newTable.Design = TableDesign.LightShadingAccent2;
  1749. /// newTable.Alignment = Alignment.center;
  1750. ///
  1751. /// // Save all changes made to this document.
  1752. /// document.Save();
  1753. /// }// Release this document from memory.
  1754. /// </code>
  1755. /// </example>
  1756. public override Table InsertTableAfterSelf(int rowCount, int columnCount)
  1757. {
  1758. return base.InsertTableAfterSelf(rowCount, columnCount);
  1759. }
  1760. /// <summary>
  1761. /// Insert a Paragraph before this Table, this Paragraph may have come from the same or another document.
  1762. /// </summary>
  1763. /// <param name="p">The Paragraph to insert.</param>
  1764. /// <returns>The Paragraph now associated with this document.</returns>
  1765. /// <example>
  1766. /// Take a Paragraph from document a, and insert it into document b before this Table.
  1767. /// <code>
  1768. /// // Place holder for a Paragraph.
  1769. /// Paragraph p;
  1770. ///
  1771. /// // Load document a.
  1772. /// using (DocX documentA = DocX.Load(@"a.docx"))
  1773. /// {
  1774. /// // Get the first paragraph from this document.
  1775. /// p = documentA.Paragraphs[0];
  1776. /// }
  1777. ///
  1778. /// // Load document b.
  1779. /// using (DocX documentB = DocX.Load(@"b.docx"))
  1780. /// {
  1781. /// // Get the first Table in document b.
  1782. /// Table t = documentB.Tables[0];
  1783. ///
  1784. /// // Insert the Paragraph from document a before this Table.
  1785. /// Paragraph newParagraph = t.InsertParagraphBeforeSelf(p);
  1786. ///
  1787. /// // Save all changes made to document b.
  1788. /// documentB.Save();
  1789. /// }// Release this document from memory.
  1790. /// </code>
  1791. /// </example>
  1792. public override Paragraph InsertParagraphBeforeSelf(Paragraph p)
  1793. {
  1794. return base.InsertParagraphBeforeSelf(p);
  1795. }
  1796. /// <summary>
  1797. /// Insert a new Paragraph before this Table.
  1798. /// </summary>
  1799. /// <param name="text">The initial text for this new Paragraph.</param>
  1800. /// <returns>A new Paragraph inserted before this Table.</returns>
  1801. /// <example>
  1802. /// Insert a new Paragraph before the first Table in this document.
  1803. /// <code>
  1804. /// // Create a new document.
  1805. /// using (DocX document = DocX.Create(@"Test.docx"))
  1806. /// {
  1807. /// // Insert a Table into this document.
  1808. /// Table t = document.InsertTable(2, 2);
  1809. ///
  1810. /// t.InsertParagraphBeforeSelf("I was inserted before the next Table.");
  1811. ///
  1812. /// // Save all changes made to this new document.
  1813. /// document.Save();
  1814. /// }// Release this new document form memory.
  1815. /// </code>
  1816. /// </example>
  1817. public override Paragraph InsertParagraphBeforeSelf(string text)
  1818. {
  1819. return base.InsertParagraphBeforeSelf(text);
  1820. }
  1821. /// <summary>
  1822. /// Insert a new Paragraph before this Table.
  1823. /// </summary>
  1824. /// <param name="text">The initial text for this new Paragraph.</param>
  1825. /// <param name="trackChanges">Should this insertion be tracked as a change?</param>
  1826. /// <returns>A new Paragraph inserted before this Table.</returns>
  1827. /// <example>
  1828. /// Insert a new paragraph before the first Table in this document.
  1829. /// <code>
  1830. /// // Create a new document.
  1831. /// using (DocX document = DocX.Create(@"Test.docx"))
  1832. /// {
  1833. /// // Insert a Table into this document.
  1834. /// Table t = document.InsertTable(2, 2);
  1835. ///
  1836. /// t.InsertParagraphBeforeSelf("I was inserted before the next Table.", false);
  1837. ///
  1838. /// // Save all changes made to this new document.
  1839. /// document.Save();
  1840. /// }// Release this new document form memory.
  1841. /// </code>
  1842. /// </example>
  1843. public override Paragraph InsertParagraphBeforeSelf(string text, bool trackChanges)
  1844. {
  1845. return base.InsertParagraphBeforeSelf(text, trackChanges);
  1846. }
  1847. /// <summary>
  1848. /// Insert a new Paragraph before this Table.
  1849. /// </summary>
  1850. /// <param name="text">The initial text for this new Paragraph.</param>
  1851. /// <param name="trackChanges">Should this insertion be tracked as a change?</param>
  1852. /// <param name="formatting">The formatting to apply to this insertion.</param>
  1853. /// <returns>A new Paragraph inserted before this Table.</returns>
  1854. /// <example>
  1855. /// Insert a new paragraph before the first Table in this document.
  1856. /// <code>
  1857. /// // Create a new document.
  1858. /// using (DocX document = DocX.Create(@"Test.docx"))
  1859. /// {
  1860. /// // Insert a Table into this document.
  1861. /// Table t = document.InsertTable(2, 2);
  1862. ///
  1863. /// Formatting boldFormatting = new Formatting();
  1864. /// boldFormatting.Bold = true;
  1865. ///
  1866. /// t.InsertParagraphBeforeSelf("I was inserted before the next Table.", false, boldFormatting);
  1867. ///
  1868. /// // Save all changes made to this new document.
  1869. /// document.Save();
  1870. /// }// Release this new document form memory.
  1871. /// </code>
  1872. /// </example>
  1873. public override Paragraph InsertParagraphBeforeSelf(string text, bool trackChanges, Formatting formatting)
  1874. {
  1875. return base.InsertParagraphBeforeSelf(text, trackChanges, formatting);
  1876. }
  1877. /// <summary>
  1878. /// Insert a Paragraph after this Table, this Paragraph may have come from the same or another document.
  1879. /// </summary>
  1880. /// <param name="p">The Paragraph to insert.</param>
  1881. /// <returns>The Paragraph now associated with this document.</returns>
  1882. /// <example>
  1883. /// Take a Paragraph from document a, and insert it into document b after this Table.
  1884. /// <code>
  1885. /// // Place holder for a Paragraph.
  1886. /// Paragraph p;
  1887. ///
  1888. /// // Load document a.
  1889. /// using (DocX documentA = DocX.Load(@"a.docx"))
  1890. /// {
  1891. /// // Get the first paragraph from this document.
  1892. /// p = documentA.Paragraphs[0];
  1893. /// }
  1894. ///
  1895. /// // Load document b.
  1896. /// using (DocX documentB = DocX.Load(@"b.docx"))
  1897. /// {
  1898. /// // Get the first Table in document b.
  1899. /// Table t = documentB.Tables[0];
  1900. ///
  1901. /// // Insert the Paragraph from document a after this Table.
  1902. /// Paragraph newParagraph = t.InsertParagraphAfterSelf(p);
  1903. ///
  1904. /// // Save all changes made to document b.
  1905. /// documentB.Save();
  1906. /// }// Release this document from memory.
  1907. /// </code>
  1908. /// </example>
  1909. public override Paragraph InsertParagraphAfterSelf(Paragraph p)
  1910. {
  1911. return base.InsertParagraphAfterSelf(p);
  1912. }
  1913. /// <summary>
  1914. /// Insert a new Paragraph after this Table.
  1915. /// </summary>
  1916. /// <param name="text">The initial text for this new Paragraph.</param>
  1917. /// <param name="trackChanges">Should this insertion be tracked as a change?</param>
  1918. /// <param name="formatting">The formatting to apply to this insertion.</param>
  1919. /// <returns>A new Paragraph inserted after this Table.</returns>
  1920. /// <example>
  1921. /// Insert a new paragraph after the first Table in this document.
  1922. /// <code>
  1923. /// // Create a new document.
  1924. /// using (DocX document = DocX.Create(@"Test.docx"))
  1925. /// {
  1926. /// // Insert a Table into this document.
  1927. /// Table t = document.InsertTable(2, 2);
  1928. ///
  1929. /// Formatting boldFormatting = new Formatting();
  1930. /// boldFormatting.Bold = true;
  1931. ///
  1932. /// t.InsertParagraphAfterSelf("I was inserted after the previous Table.", false, boldFormatting);
  1933. ///
  1934. /// // Save all changes made to this new document.
  1935. /// document.Save();
  1936. /// }// Release this new document form memory.
  1937. /// </code>
  1938. /// </example>
  1939. public override Paragraph InsertParagraphAfterSelf(string text, bool trackChanges, Formatting formatting)
  1940. {
  1941. return base.InsertParagraphAfterSelf(text, trackChanges, formatting);
  1942. }
  1943. /// <summary>
  1944. /// Insert a new Paragraph after this Table.
  1945. /// </summary>
  1946. /// <param name="text">The initial text for this new Paragraph.</param>
  1947. /// <param name="trackChanges">Should this insertion be tracked as a change?</param>
  1948. /// <returns>A new Paragraph inserted after this Table.</returns>
  1949. /// <example>
  1950. /// Insert a new paragraph after the first Table in this document.
  1951. /// <code>
  1952. /// // Create a new document.
  1953. /// using (DocX document = DocX.Create(@"Test.docx"))
  1954. /// {
  1955. /// // Insert a Table into this document.
  1956. /// Table t = document.InsertTable(2, 2);
  1957. ///
  1958. /// t.InsertParagraphAfterSelf("I was inserted after the previous Table.", false);
  1959. ///
  1960. /// // Save all changes made to this new document.
  1961. /// document.Save();
  1962. /// }// Release this new document form memory.
  1963. /// </code>
  1964. /// </example>
  1965. public override Paragraph InsertParagraphAfterSelf(string text, bool trackChanges)
  1966. {
  1967. return base.InsertParagraphAfterSelf(text, trackChanges);
  1968. }
  1969. /// <summary>
  1970. /// Insert a new Paragraph after this Table.
  1971. /// </summary>
  1972. /// <param name="text">The initial text for this new Paragraph.</param>
  1973. /// <returns>A new Paragraph inserted after this Table.</returns>
  1974. /// <example>
  1975. /// Insert a new Paragraph after the first Table in this document.
  1976. /// <code>
  1977. /// // Create a new document.
  1978. /// using (DocX document = DocX.Create(@"Test.docx"))
  1979. /// {
  1980. /// // Insert a Table into this document.
  1981. /// Table t = document.InsertTable(2, 2);
  1982. ///
  1983. /// t.InsertParagraphAfterSelf("I was inserted after the previous Table.");
  1984. ///
  1985. /// // Save all changes made to this new document.
  1986. /// document.Save();
  1987. /// }// Release this new document form memory.
  1988. /// </code>
  1989. /// </example>
  1990. public override Paragraph InsertParagraphAfterSelf(string text)
  1991. {
  1992. return base.InsertParagraphAfterSelf(text);
  1993. }
  1994. /// <summary>
  1995. /// Set a table border
  1996. /// Added by lckuiper @ 20101117
  1997. /// </summary>
  1998. /// <example>
  1999. /// <code>
  2000. /// // Create a new document.
  2001. ///using (DocX document = DocX.Create("Test.docx"))
  2002. ///{
  2003. /// // Insert a table into this document.
  2004. /// Table t = document.InsertTable(3, 3);
  2005. ///
  2006. /// // Create a large blue border.
  2007. /// Border b = new Border(BorderStyle.Tcbs_single, BorderSize.seven, 0, Color.Blue);
  2008. ///
  2009. /// // Set the tables Top, Bottom, Left and Right Borders to b.
  2010. /// t.SetBorder(TableBorderType.Top, b);
  2011. /// t.SetBorder(TableBorderType.Bottom, b);
  2012. /// t.SetBorder(TableBorderType.Left, b);
  2013. /// t.SetBorder(TableBorderType.Right, b);
  2014. ///
  2015. /// // Save the document.
  2016. /// document.Save();
  2017. ///}
  2018. /// </code>
  2019. /// </example>
  2020. /// <param name="borderType">The table border to set</param>
  2021. /// <param name="border">Border object to set the table border</param>
  2022. public void SetBorder(TableBorderType borderType, Border border)
  2023. {
  2024. /*
  2025. * Get the tblPr (table properties) element for this Table,
  2026. * null will be return if no such element exists.
  2027. */
  2028. XElement tblPr = Xml.Element(XName.Get("tblPr", DocX.w.NamespaceName));
  2029. if (tblPr == null)
  2030. {
  2031. Xml.SetElementValue(XName.Get("tblPr", DocX.w.NamespaceName), string.Empty);
  2032. tblPr = Xml.Element(XName.Get("tblPr", DocX.w.NamespaceName));
  2033. }
  2034. /*
  2035. * Get the tblBorders (table borders) element for this Table,
  2036. * null will be return if no such element exists.
  2037. */
  2038. XElement tblBorders = tblPr.Element(XName.Get("tblBorders", DocX.w.NamespaceName));
  2039. if (tblBorders == null)
  2040. {
  2041. tblPr.SetElementValue(XName.Get("tblBorders", DocX.w.NamespaceName), string.Empty);
  2042. tblBorders = tblPr.Element(XName.Get("tblBorders", DocX.w.NamespaceName));
  2043. }
  2044. /*
  2045. * Get the 'borderType' (table border) element for this Table,
  2046. * null will be return if no such element exists.
  2047. */
  2048. string tbordertype;
  2049. tbordertype = borderType.ToString();
  2050. // only lower the first char of string (because of insideH and insideV)
  2051. tbordertype = tbordertype.Substring(0, 1).ToLower() + tbordertype.Substring(1);
  2052. XElement tblBorderType = tblBorders.Element(XName.Get(borderType.ToString(), DocX.w.NamespaceName));
  2053. if (tblBorderType == null)
  2054. {
  2055. tblBorders.SetElementValue(XName.Get(tbordertype, DocX.w.NamespaceName), string.Empty);
  2056. tblBorderType = tblBorders.Element(XName.Get(tbordertype, DocX.w.NamespaceName));
  2057. }
  2058. // get string value of border style
  2059. string borderstyle = border.Tcbs.ToString().Substring(5);
  2060. borderstyle = borderstyle.Substring(0, 1).ToLower() + borderstyle.Substring(1);
  2061. // The val attribute is used for the border style
  2062. tblBorderType.SetAttributeValue(XName.Get("val", DocX.w.NamespaceName), borderstyle);
  2063. if (border.Tcbs != BorderStyle.Tcbs_nil)
  2064. {
  2065. int size;
  2066. switch (border.Size)
  2067. {
  2068. case BorderSize.one: size = 2; break;
  2069. case BorderSize.two: size = 4; break;
  2070. case BorderSize.three: size = 6; break;
  2071. case BorderSize.four: size = 8; break;
  2072. case BorderSize.five: size = 12; break;
  2073. case BorderSize.six: size = 18; break;
  2074. case BorderSize.seven: size = 24; break;
  2075. case BorderSize.eight: size = 36; break;
  2076. case BorderSize.nine: size = 48; break;
  2077. default: size = 2; break;
  2078. }
  2079. // The sz attribute is used for the border size
  2080. tblBorderType.SetAttributeValue(XName.Get("sz", DocX.w.NamespaceName), (size).ToString());
  2081. // The space attribute is used for the cell spacing (probably '0')
  2082. tblBorderType.SetAttributeValue(XName.Get("space", DocX.w.NamespaceName), (border.Space).ToString());
  2083. // The color attribute is used for the border color
  2084. tblBorderType.SetAttributeValue(XName.Get("color", DocX.w.NamespaceName), border.Color.ToHex());
  2085. }
  2086. }
  2087. /// <summary>
  2088. /// Get a table border
  2089. /// Added by lckuiper @ 20101117
  2090. /// </summary>
  2091. /// <param name="borderType">The table border to get</param>
  2092. public Border GetBorder(TableBorderType borderType)
  2093. {
  2094. // instance with default border values
  2095. Border b = new Border();
  2096. /*
  2097. * Get the tblPr (table properties) element for this Table,
  2098. * null will be return if no such element exists.
  2099. */
  2100. XElement tblPr = Xml.Element(XName.Get("tblPr", DocX.w.NamespaceName));
  2101. if (tblPr == null)
  2102. {
  2103. // uses default border style
  2104. }
  2105. /*
  2106. * Get the tblBorders (table borders) element for this Table,
  2107. * null will be return if no such element exists.
  2108. */
  2109. XElement tblBorders = tblPr.Element(XName.Get("tblBorders", DocX.w.NamespaceName));
  2110. if (tblBorders == null)
  2111. {
  2112. // uses default border style
  2113. }
  2114. /*
  2115. * Get the 'borderType' (table border) element for this Table,
  2116. * null will be return if no such element exists.
  2117. */
  2118. string tbordertype;
  2119. tbordertype = borderType.ToString();
  2120. // only lower the first char of string (because of insideH and insideV)
  2121. tbordertype = tbordertype.Substring(0, 1).ToLower() + tbordertype.Substring(1);
  2122. XElement tblBorderType = tblBorders.Element(XName.Get(tbordertype, DocX.w.NamespaceName));
  2123. if (tblBorderType == null)
  2124. {
  2125. // uses default border style
  2126. }
  2127. // The val attribute is used for the border style
  2128. XAttribute val = tblBorderType.Attribute(XName.Get("val", DocX.w.NamespaceName));
  2129. // If val is null, this table contains no border information.
  2130. if (val == null)
  2131. {
  2132. // uses default border style
  2133. }
  2134. else
  2135. {
  2136. try
  2137. {
  2138. string bordertype = "Tcbs_" + val.Value;
  2139. b.Tcbs = (BorderStyle)Enum.Parse(typeof(BorderStyle), bordertype);
  2140. }
  2141. catch
  2142. {
  2143. val.Remove();
  2144. // uses default border style
  2145. }
  2146. }
  2147. // The sz attribute is used for the border size
  2148. XAttribute sz = tblBorderType.Attribute(XName.Get("sz", DocX.w.NamespaceName));
  2149. // If sz is null, this border contains no size information.
  2150. if (sz == null)
  2151. {
  2152. // uses default border style
  2153. }
  2154. else
  2155. {
  2156. // If sz is not an int, something is wrong with this attributes value, so remove it
  2157. int numerical_size;
  2158. if (!int.TryParse(sz.Value, out numerical_size))
  2159. sz.Remove();
  2160. else
  2161. {
  2162. switch (numerical_size)
  2163. {
  2164. case 2: b.Size = BorderSize.one; break;
  2165. case 4: b.Size = BorderSize.two; break;
  2166. case 6: b.Size = BorderSize.three; break;
  2167. case 8: b.Size = BorderSize.four; break;
  2168. case 12: b.Size = BorderSize.five; break;
  2169. case 18: b.Size = BorderSize.six; break;
  2170. case 24: b.Size = BorderSize.seven; break;
  2171. case 36: b.Size = BorderSize.eight; break;
  2172. case 48: b.Size = BorderSize.nine; break;
  2173. default: b.Size = BorderSize.one; break;
  2174. }
  2175. }
  2176. }
  2177. // The space attribute is used for the border spacing (probably '0')
  2178. XAttribute space = tblBorderType.Attribute(XName.Get("space", DocX.w.NamespaceName));
  2179. // If space is null, this border contains no space information.
  2180. if (space == null)
  2181. {
  2182. // uses default border style
  2183. }
  2184. else
  2185. {
  2186. // If space is not an int, something is wrong with this attributes value, so remove it
  2187. int borderspace;
  2188. if (!int.TryParse(space.Value, out borderspace))
  2189. {
  2190. space.Remove();
  2191. // uses default border style
  2192. }
  2193. else
  2194. {
  2195. b.Space = borderspace;
  2196. }
  2197. }
  2198. // The color attribute is used for the border color
  2199. XAttribute color = tblBorderType.Attribute(XName.Get("color", DocX.w.NamespaceName));
  2200. if (color == null)
  2201. {
  2202. // uses default border style
  2203. }
  2204. else
  2205. {
  2206. // If color is not a Color, something is wrong with this attributes value, so remove it
  2207. try
  2208. {
  2209. b.Color = ColorTranslator.FromHtml(string.Format("#{0}", color.Value));
  2210. }
  2211. catch
  2212. {
  2213. color.Remove();
  2214. // uses default border style
  2215. }
  2216. }
  2217. return b;
  2218. }
  2219. }
  2220. /// <summary>
  2221. /// Represents a single row in a Table.
  2222. /// </summary>
  2223. public class Row : Container
  2224. {
  2225. /// <summary>
  2226. /// Calculates columns count in the row, taking spanned cells into account
  2227. /// </summary>
  2228. public Int32 ColumnCount
  2229. {
  2230. get
  2231. {
  2232. int gridSpanSum = 0;
  2233. gridSpanSum += gridAfter;
  2234. // Foreach each Cell between startIndex and endIndex inclusive.
  2235. foreach (Cell c in Cells)
  2236. {
  2237. if (c.GridSpan != 0)
  2238. {
  2239. gridSpanSum += c.GridSpan - 1;
  2240. }
  2241. }
  2242. // return cells count + count of spanned cells
  2243. return Cells.Count + gridSpanSum;
  2244. }
  2245. }
  2246. /// <summary>
  2247. /// Returns the GridAfter of a row ie. The amount of cells that are deleted
  2248. /// </summary>
  2249. public int gridAfter
  2250. {
  2251. get
  2252. {
  2253. var gridAfterValue = 0;
  2254. var trPr = Xml.Element(XName.Get("trPr", DocX.w.NamespaceName));
  2255. if (trPr != null)
  2256. {
  2257. var gridAfter = trPr.Element(XName.Get("gridAfter", DocX.w.NamespaceName));
  2258. if (gridAfter != null)
  2259. {
  2260. var val = gridAfter.Attribute(XName.Get("val", DocX.w.NamespaceName));
  2261. if (val != null)
  2262. {
  2263. gridAfterValue += int.Parse(val.Value);
  2264. }
  2265. }
  2266. }
  2267. return gridAfterValue;
  2268. }
  2269. }
  2270. /// <summary>
  2271. /// A list of Cells in this Row.
  2272. /// </summary>
  2273. public List<Cell> Cells
  2274. {
  2275. get
  2276. {
  2277. List<Cell> cells =
  2278. (
  2279. from c in Xml.Elements(XName.Get("tc", DocX.w.NamespaceName))
  2280. select new Cell(this, Document, c)
  2281. ).ToList();
  2282. return cells;
  2283. }
  2284. }
  2285. public void Remove()
  2286. {
  2287. XElement table = Xml.Parent;
  2288. Xml.Remove();
  2289. if (table.Elements(XName.Get("tr", DocX.w.NamespaceName)).Count() == 0)
  2290. table.Remove();
  2291. }
  2292. public override ReadOnlyCollection<Paragraph> Paragraphs
  2293. {
  2294. get
  2295. {
  2296. List<Paragraph> paragraphs =
  2297. (
  2298. from p in Xml.Descendants(DocX.w + "p")
  2299. select new Paragraph(Document, p, 0)
  2300. ).ToList();
  2301. foreach (Paragraph p in paragraphs)
  2302. p.PackagePart = table.mainPart;
  2303. return paragraphs.AsReadOnly();
  2304. }
  2305. }
  2306. internal Table table;
  2307. internal Row(Table table, DocX document, XElement xml)
  2308. : base(document, xml)
  2309. {
  2310. this.table = table;
  2311. this.mainPart = table.mainPart;
  2312. }
  2313. /// <summary>
  2314. /// The property name to set when specifiying an exact height
  2315. /// </summary>
  2316. /// <created>Nick Kusters</created>
  2317. const string _hRule_Exact = "exact";
  2318. /// <summary>
  2319. /// The property name to set when specifying a minimum height
  2320. /// </summary>
  2321. /// <created>Nick Kusters</created>
  2322. const string _hRule_AtLeast = "atLeast";
  2323. /// <summary>
  2324. /// Height in pixels. // Added by Joel, refactored by Cathal.
  2325. /// </summary>
  2326. public double Height
  2327. {
  2328. get
  2329. {
  2330. /*
  2331. * Get the trPr (table row properties) element for this Row,
  2332. * null will be return if no such element exists.
  2333. */
  2334. XElement trPr = Xml.Element(XName.Get("trPr", DocX.w.NamespaceName));
  2335. // If trPr is null, this row contains no height information.
  2336. if (trPr == null)
  2337. return double.NaN;
  2338. /*
  2339. * Get the trHeight element for this Row,
  2340. * null will be return if no such element exists.
  2341. */
  2342. XElement trHeight = trPr.Element(XName.Get("trHeight", DocX.w.NamespaceName));
  2343. // If trHeight is null, this row contains no height information.
  2344. if (trHeight == null)
  2345. return double.NaN;
  2346. // Get the val attribute for this trHeight element.
  2347. XAttribute val = trHeight.Attribute(XName.Get("val", DocX.w.NamespaceName));
  2348. // If w is null, this cell contains no width information.
  2349. if (val == null)
  2350. return double.NaN;
  2351. // If val is not a double, something is wrong with this attributes value, so remove it and return double.NaN;
  2352. double heightInWordUnits;
  2353. if (!double.TryParse(val.Value, out heightInWordUnits))
  2354. {
  2355. val.Remove();
  2356. return double.NaN;
  2357. }
  2358. // 15 "word units" in one pixel
  2359. return (heightInWordUnits / 15);
  2360. }
  2361. set
  2362. {
  2363. SetHeight(value, true);
  2364. }
  2365. }
  2366. /// <summary>
  2367. /// Helper method to set either the exact height or the min-height
  2368. /// </summary>
  2369. /// <param name="height">The height value to set (in pixels)</param>
  2370. /// <param name="exact">
  2371. /// If true, the height will be forced.
  2372. /// If false, it will be treated as a minimum height, auto growing past it if need be.
  2373. /// </param>
  2374. /// <created>Nick Kusters</created>
  2375. void SetHeight(double height, bool exact)
  2376. {
  2377. /*
  2378. * Get the trPr (table row properties) element for this Row,
  2379. * null will be return if no such element exists.
  2380. */
  2381. XElement trPr = Xml.Element(XName.Get("trPr", DocX.w.NamespaceName));
  2382. if (trPr == null)
  2383. {
  2384. Xml.SetElementValue(XName.Get("trPr", DocX.w.NamespaceName), string.Empty);
  2385. trPr = Xml.Element(XName.Get("trPr", DocX.w.NamespaceName));
  2386. }
  2387. /*
  2388. * Get the trHeight element for this Row,
  2389. * null will be return if no such element exists.
  2390. */
  2391. XElement trHeight = trPr.Element(XName.Get("trHeight", DocX.w.NamespaceName));
  2392. if (trHeight == null)
  2393. {
  2394. trPr.SetElementValue(XName.Get("trHeight", DocX.w.NamespaceName), string.Empty);
  2395. trHeight = trPr.Element(XName.Get("trHeight", DocX.w.NamespaceName));
  2396. }
  2397. // The hRule attribute needs to be set to exact.
  2398. trHeight.SetAttributeValue(XName.Get("hRule", DocX.w.NamespaceName), exact ? _hRule_Exact : _hRule_AtLeast);
  2399. // 15 "word units" is equal to one pixel.
  2400. trHeight.SetAttributeValue(XName.Get("val", DocX.w.NamespaceName), (height * 15).ToString());
  2401. }
  2402. /// <summary>
  2403. /// Min-Height in pixels. // Added by Nick Kusters.
  2404. /// </summary>
  2405. /// <remarks>
  2406. /// Value will be treated as a minimum height, auto growing past it if need be.
  2407. /// </remarks>
  2408. /// <created>Nick Kusters</created>
  2409. public double MinHeight
  2410. {
  2411. get
  2412. {
  2413. // Just return the value from the normal height property since it doesn't care if you've set an exact or minimum height.
  2414. return Height;
  2415. }
  2416. set
  2417. {
  2418. SetHeight(value, false);
  2419. }
  2420. }
  2421. /// <summary>
  2422. /// Set to true to make this row the table header row that will be repeated on each page
  2423. /// </summary>
  2424. public bool TableHeader
  2425. {
  2426. get
  2427. {
  2428. XElement trPr = Xml.Element(XName.Get("trPr", DocX.w.NamespaceName));
  2429. XElement tblHeader = trPr.Element(XName.Get("tblHeader", DocX.w.NamespaceName));
  2430. if (tblHeader == null)
  2431. {
  2432. return false;
  2433. }
  2434. else
  2435. {
  2436. return true;
  2437. }
  2438. }
  2439. set
  2440. {
  2441. XElement trPr = Xml.Element(XName.Get("trPr", DocX.w.NamespaceName));
  2442. if (trPr == null)
  2443. {
  2444. Xml.SetElementValue(XName.Get("trPr", DocX.w.NamespaceName), string.Empty);
  2445. trPr = Xml.Element(XName.Get("trPr", DocX.w.NamespaceName));
  2446. }
  2447. XElement tblHeader = trPr.Element(XName.Get("tblHeader", DocX.w.NamespaceName));
  2448. if (tblHeader == null && value)
  2449. {
  2450. trPr.SetElementValue(XName.Get("tblHeader", DocX.w.NamespaceName), string.Empty);
  2451. }
  2452. if (tblHeader != null && !value)
  2453. {
  2454. tblHeader.Remove();
  2455. }
  2456. }
  2457. }
  2458. /// <summary>
  2459. /// Allow row to break across pages.
  2460. /// The default value is true: Word will break the contents of the row across pages.
  2461. /// If set to false, the contents of the row will not be split across pages, the entire row will be moved to the next page instead.
  2462. /// </summary>
  2463. public bool BreakAcrossPages
  2464. {
  2465. get
  2466. {
  2467. XElement trPr = Xml.Element(XName.Get("trPr", DocX.w.NamespaceName));
  2468. if (trPr == null)
  2469. return true;
  2470. XElement trCantSplit = trPr.Element(XName.Get("cantSplit", DocX.w.NamespaceName));
  2471. if (trCantSplit == null)
  2472. return true;
  2473. return false;
  2474. }
  2475. set
  2476. {
  2477. if (value == false)
  2478. {
  2479. XElement trPr = Xml.Element(XName.Get("trPr", DocX.w.NamespaceName));
  2480. if (trPr == null)
  2481. {
  2482. Xml.SetElementValue(XName.Get("trPr", DocX.w.NamespaceName), string.Empty);
  2483. trPr = Xml.Element(XName.Get("trPr", DocX.w.NamespaceName));
  2484. }
  2485. XElement trCantSplit = trPr.Element(XName.Get("cantSplit", DocX.w.NamespaceName));
  2486. if (trCantSplit == null)
  2487. trPr.SetElementValue(XName.Get("cantSplit", DocX.w.NamespaceName), string.Empty);
  2488. }
  2489. if (value == true)
  2490. {
  2491. XElement trPr = Xml.Element(XName.Get("trPr", DocX.w.NamespaceName));
  2492. if (trPr != null)
  2493. {
  2494. XElement trCantSplit = trPr.Element(XName.Get("cantSplit", DocX.w.NamespaceName));
  2495. if (trCantSplit != null)
  2496. trCantSplit.Remove();
  2497. }
  2498. }
  2499. }
  2500. }
  2501. /// <summary>
  2502. /// Merge cells starting with startIndex and ending with endIndex.
  2503. /// </summary>
  2504. public void MergeCells(int startIndex, int endIndex)
  2505. {
  2506. // Check for valid start and end indexes.
  2507. if (startIndex < 0 || endIndex <= startIndex || endIndex > Cells.Count + 1)
  2508. throw new IndexOutOfRangeException();
  2509. // The sum of all merged gridSpans.
  2510. int gridSpanSum = 0;
  2511. // Foreach each Cell between startIndex and endIndex inclusive.
  2512. foreach (Cell c in Cells.Where((z, i) => i > startIndex && i <= endIndex))
  2513. {
  2514. XElement tcPr = c.Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  2515. if (tcPr != null)
  2516. {
  2517. XElement gridSpan = tcPr.Element(XName.Get("gridSpan", DocX.w.NamespaceName));
  2518. if (gridSpan != null)
  2519. {
  2520. XAttribute val = gridSpan.Attribute(XName.Get("val", DocX.w.NamespaceName));
  2521. int value = 0;
  2522. if (val != null)
  2523. if (int.TryParse(val.Value, out value))
  2524. gridSpanSum += value - 1;
  2525. }
  2526. }
  2527. // Add this cells Pragraph to the merge start Cell.
  2528. Cells[startIndex].Xml.Add(c.Xml.Elements(XName.Get("p", DocX.w.NamespaceName)));
  2529. // Remove this Cell.
  2530. c.Xml.Remove();
  2531. }
  2532. /*
  2533. * Get the tcPr (table cell properties) element for the first cell in this merge,
  2534. * null will be returned if no such element exists.
  2535. */
  2536. XElement start_tcPr = Cells[startIndex].Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  2537. if (start_tcPr == null)
  2538. {
  2539. Cells[startIndex].Xml.SetElementValue(XName.Get("tcPr", DocX.w.NamespaceName), string.Empty);
  2540. start_tcPr = Cells[startIndex].Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  2541. }
  2542. /*
  2543. * Get the gridSpan element of this row,
  2544. * null will be returned if no such element exists.
  2545. */
  2546. XElement start_gridSpan = start_tcPr.Element(XName.Get("gridSpan", DocX.w.NamespaceName));
  2547. if (start_gridSpan == null)
  2548. {
  2549. start_tcPr.SetElementValue(XName.Get("gridSpan", DocX.w.NamespaceName), string.Empty);
  2550. start_gridSpan = start_tcPr.Element(XName.Get("gridSpan", DocX.w.NamespaceName));
  2551. }
  2552. /*
  2553. * Get the val attribute of this row,
  2554. * null will be returned if no such element exists.
  2555. */
  2556. XAttribute start_val = start_gridSpan.Attribute(XName.Get("val", DocX.w.NamespaceName));
  2557. int start_value = 0;
  2558. if (start_val != null)
  2559. if (int.TryParse(start_val.Value, out start_value))
  2560. gridSpanSum += start_value - 1;
  2561. // Set the val attribute to the number of merged cells.
  2562. start_gridSpan.SetAttributeValue(XName.Get("val", DocX.w.NamespaceName), (gridSpanSum + (endIndex - startIndex + 1)).ToString());
  2563. }
  2564. }
  2565. public class Cell : Container
  2566. {
  2567. internal Row row;
  2568. internal Cell(Row row, DocX document, XElement xml)
  2569. : base(document, xml)
  2570. {
  2571. this.row = row;
  2572. this.mainPart = row.mainPart;
  2573. }
  2574. public override ReadOnlyCollection<Paragraph> Paragraphs
  2575. {
  2576. get
  2577. {
  2578. ReadOnlyCollection<Paragraph> paragraphs = base.Paragraphs;
  2579. foreach (Paragraph p in paragraphs)
  2580. p.PackagePart = row.table.mainPart;
  2581. return paragraphs;
  2582. }
  2583. }
  2584. /// <summary>
  2585. /// Returns the GridSpan of a specific Cell ie. How many cells are merged
  2586. /// </summary>
  2587. public int GridSpan
  2588. {
  2589. get
  2590. {
  2591. var gridSpanVal = 0;
  2592. XElement tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  2593. if (tcPr != null)
  2594. {
  2595. XElement gridSpan = tcPr.Element(XName.Get("gridSpan", DocX.w.NamespaceName));
  2596. if (gridSpan != null)
  2597. {
  2598. XAttribute val = gridSpan.Attribute(XName.Get("val", DocX.w.NamespaceName));
  2599. int value = 0;
  2600. if (val != null)
  2601. if (int.TryParse(val.Value, out value))
  2602. gridSpanVal = value;
  2603. }
  2604. }
  2605. return gridSpanVal;
  2606. }
  2607. }
  2608. /// <summary>
  2609. /// Gets or Sets this Cells vertical alignment.
  2610. /// </summary>
  2611. /// <!--Patch 7398 added by lckuiper on Nov 16th 2010 @ 2:23 PM-->
  2612. /// <example>
  2613. /// Creates a table with 3 cells and sets the vertical alignment of each to 1 of the 3 available options.
  2614. /// <code>
  2615. /// // Create a new document.
  2616. ///using(DocX document = DocX.Create("Test.docx"))
  2617. ///{
  2618. /// // Insert a Table into this document.
  2619. /// Table t = document.InsertTable(3, 1);
  2620. ///
  2621. /// // Set the design of the Table such that we can easily identify cell boundaries.
  2622. /// t.Design = TableDesign.TableGrid;
  2623. ///
  2624. /// // Set the height of the row bigger than default.
  2625. /// // We need to be able to see the difference in vertical cell alignment options.
  2626. /// t.Rows[0].Height = 100;
  2627. ///
  2628. /// // Set the vertical alignment of cell0 to top.
  2629. /// Cell c0 = t.Rows[0].Cells[0];
  2630. /// c0.InsertParagraph("VerticalAlignment.Top");
  2631. /// c0.VerticalAlignment = VerticalAlignment.Top;
  2632. ///
  2633. /// // Set the vertical alignment of cell1 to center.
  2634. /// Cell c1 = t.Rows[0].Cells[1];
  2635. /// c1.InsertParagraph("VerticalAlignment.Center");
  2636. /// c1.VerticalAlignment = VerticalAlignment.Center;
  2637. ///
  2638. /// // Set the vertical alignment of cell2 to bottom.
  2639. /// Cell c2 = t.Rows[0].Cells[2];
  2640. /// c2.InsertParagraph("VerticalAlignment.Bottom");
  2641. /// c2.VerticalAlignment = VerticalAlignment.Bottom;
  2642. ///
  2643. /// // Save the document.
  2644. /// document.Save();
  2645. ///}
  2646. /// </code>
  2647. /// </example>
  2648. public VerticalAlignment VerticalAlignment
  2649. {
  2650. get
  2651. {
  2652. /*
  2653. * Get the tcPr (table cell properties) element for this Cell,
  2654. * null will be return if no such element exists.
  2655. */
  2656. XElement tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  2657. // If tcPr is null, this cell contains no width information.
  2658. if (tcPr == null)
  2659. return VerticalAlignment.Center;
  2660. /*
  2661. * Get the vAlign (table cell vertical alignment) element for this Cell,
  2662. * null will be return if no such element exists.
  2663. */
  2664. XElement vAlign = tcPr.Element(XName.Get("vAlign", DocX.w.NamespaceName));
  2665. // If vAlign is null, this cell contains no vertical alignment information.
  2666. if (vAlign == null)
  2667. return VerticalAlignment.Center;
  2668. // Get the val attribute of the vAlign element.
  2669. XAttribute val = vAlign.Attribute(XName.Get("val", DocX.w.NamespaceName));
  2670. // If val is null, this cell contains no vAlign information.
  2671. if (val == null)
  2672. return VerticalAlignment.Center;
  2673. // If val is not a VerticalAlign enum, something is wrong with this attributes value, so remove it and return VerticalAlignment.Center;
  2674. try
  2675. {
  2676. return (VerticalAlignment)Enum.Parse(typeof(VerticalAlignment), val.Value, true);
  2677. }
  2678. catch
  2679. {
  2680. val.Remove();
  2681. return VerticalAlignment.Center;
  2682. }
  2683. }
  2684. set
  2685. {
  2686. /*
  2687. * Get the tcPr (table cell properties) element for this Cell,
  2688. * null will be return if no such element exists.
  2689. */
  2690. XElement tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  2691. if (tcPr == null)
  2692. {
  2693. Xml.SetElementValue(XName.Get("tcPr", DocX.w.NamespaceName), string.Empty);
  2694. tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  2695. }
  2696. /*
  2697. * Get the vAlign (table cell vertical alignment) element for this Cell,
  2698. * null will be return if no such element exists.
  2699. */
  2700. XElement vAlign = tcPr.Element(XName.Get("vAlign", DocX.w.NamespaceName));
  2701. if (vAlign == null)
  2702. {
  2703. tcPr.SetElementValue(XName.Get("vAlign", DocX.w.NamespaceName), string.Empty);
  2704. vAlign = tcPr.Element(XName.Get("vAlign", DocX.w.NamespaceName));
  2705. }
  2706. // Set the VerticalAlignment in 'val'
  2707. vAlign.SetAttributeValue(XName.Get("val", DocX.w.NamespaceName), value.ToString().ToLower());
  2708. }
  2709. }
  2710. public Color Shading
  2711. {
  2712. get
  2713. {
  2714. /*
  2715. * Get the tcPr (table cell properties) element for this Cell,
  2716. * null will be return if no such element exists.
  2717. */
  2718. XElement tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  2719. // If tcPr is null, this cell contains no Color information.
  2720. if (tcPr == null)
  2721. return Color.White;
  2722. /*
  2723. * Get the shd (table shade) element for this Cell,
  2724. * null will be return if no such element exists.
  2725. */
  2726. XElement shd = tcPr.Element(XName.Get("shd", DocX.w.NamespaceName));
  2727. // If shd is null, this cell contains no Color information.
  2728. if (shd == null)
  2729. return Color.White;
  2730. // Get the w attribute of the tcW element.
  2731. XAttribute fill = shd.Attribute(XName.Get("fill", DocX.w.NamespaceName));
  2732. // If fill is null, this cell contains no Color information.
  2733. if (fill == null)
  2734. return Color.White;
  2735. return ColorTranslator.FromHtml(string.Format("#{0}", fill.Value));
  2736. }
  2737. set
  2738. {
  2739. /*
  2740. * Get the tcPr (table cell properties) element for this Cell,
  2741. * null will be return if no such element exists.
  2742. */
  2743. XElement tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  2744. if (tcPr == null)
  2745. {
  2746. Xml.SetElementValue(XName.Get("tcPr", DocX.w.NamespaceName), string.Empty);
  2747. tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  2748. }
  2749. /*
  2750. * Get the shd (table shade) element for this Cell,
  2751. * null will be return if no such element exists.
  2752. */
  2753. XElement shd = tcPr.Element(XName.Get("shd", DocX.w.NamespaceName));
  2754. if (shd == null)
  2755. {
  2756. tcPr.SetElementValue(XName.Get("shd", DocX.w.NamespaceName), string.Empty);
  2757. shd = tcPr.Element(XName.Get("shd", DocX.w.NamespaceName));
  2758. }
  2759. // The val attribute needs to be set to clear
  2760. shd.SetAttributeValue(XName.Get("val", DocX.w.NamespaceName), "clear");
  2761. // The color attribute needs to be set to auto
  2762. shd.SetAttributeValue(XName.Get("color", DocX.w.NamespaceName), "auto");
  2763. // The fill attribute needs to be set to the hex for this Color.
  2764. shd.SetAttributeValue(XName.Get("fill", DocX.w.NamespaceName), value.ToHex());
  2765. }
  2766. }
  2767. /// <summary>
  2768. /// Width in pixels. // Added by Joel, refactored by Cathal
  2769. /// </summary>
  2770. public double Width
  2771. {
  2772. get
  2773. {
  2774. /*
  2775. * Get the tcPr (table cell properties) element for this Cell,
  2776. * null will be return if no such element exists.
  2777. */
  2778. XElement tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  2779. // If tcPr is null, this cell contains no width information.
  2780. if (tcPr == null)
  2781. return double.NaN;
  2782. /*
  2783. * Get the tcW (table cell width) element for this Cell,
  2784. * null will be return if no such element exists.
  2785. */
  2786. XElement tcW = tcPr.Element(XName.Get("tcW", DocX.w.NamespaceName));
  2787. // If tcW is null, this cell contains no width information.
  2788. if (tcW == null)
  2789. return double.NaN;
  2790. // Get the w attribute of the tcW element.
  2791. XAttribute w = tcW.Attribute(XName.Get("w", DocX.w.NamespaceName));
  2792. // If w is null, this cell contains no width information.
  2793. if (w == null)
  2794. return double.NaN;
  2795. // If w is not a double, something is wrong with this attributes value, so remove it and return double.NaN;
  2796. double widthInWordUnits;
  2797. if (!double.TryParse(w.Value, out widthInWordUnits))
  2798. {
  2799. w.Remove();
  2800. return double.NaN;
  2801. }
  2802. // 15 "word units" is equal to one pixel.
  2803. return (widthInWordUnits / 15);
  2804. }
  2805. set
  2806. {
  2807. /*
  2808. * Get the tcPr (table cell properties) element for this Cell,
  2809. * null will be return if no such element exists.
  2810. */
  2811. XElement tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  2812. if (tcPr == null)
  2813. {
  2814. Xml.SetElementValue(XName.Get("tcPr", DocX.w.NamespaceName), string.Empty);
  2815. tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  2816. }
  2817. /*
  2818. * Get the tcW (table cell width) element for this Cell,
  2819. * null will be return if no such element exists.
  2820. */
  2821. XElement tcW = tcPr.Element(XName.Get("tcW", DocX.w.NamespaceName));
  2822. if (tcW == null)
  2823. {
  2824. tcPr.SetElementValue(XName.Get("tcW", DocX.w.NamespaceName), string.Empty);
  2825. tcW = tcPr.Element(XName.Get("tcW", DocX.w.NamespaceName));
  2826. }
  2827. if (value == -1)
  2828. {
  2829. // remove cell width; due to set on table prop.
  2830. tcW.Remove();
  2831. return;
  2832. //tcW.SetAttributeValue(XName.Get("type", DocX.w.NamespaceName), "auto");
  2833. //return;
  2834. }
  2835. // The type attribute needs to be set to dxa which represents "twips" or twentieths of a point. In other words, 1/1440th of an inch.
  2836. tcW.SetAttributeValue(XName.Get("type", DocX.w.NamespaceName), "dxa");
  2837. // 15 "word units" is equal to one pixel.
  2838. tcW.SetAttributeValue(XName.Get("w", DocX.w.NamespaceName), (value * 15).ToString());
  2839. }
  2840. }
  2841. /// <summary>
  2842. /// LeftMargin in pixels. // Added by lckuiper
  2843. /// </summary>
  2844. /// <example>
  2845. /// <code>
  2846. /// // Create a new document.
  2847. ///using (DocX document = DocX.Create("Test.docx"))
  2848. ///{
  2849. /// // Insert table into this document.
  2850. /// Table t = document.InsertTable(3, 3);
  2851. /// t.Design = TableDesign.TableGrid;
  2852. ///
  2853. /// // Get the center cell.
  2854. /// Cell center = t.Rows[1].Cells[1];
  2855. ///
  2856. /// // Insert some text so that we can see the effect of the Margins.
  2857. /// center.Paragraphs[0].Append("Center Cell");
  2858. ///
  2859. /// // Set the center cells Left, Margin to 10.
  2860. /// center.MarginLeft = 25;
  2861. ///
  2862. /// // Save the document.
  2863. /// document.Save();
  2864. ///}
  2865. /// </code>
  2866. /// </example>
  2867. public double MarginLeft
  2868. {
  2869. get
  2870. {
  2871. /*
  2872. * Get the tcPr (table cell properties) element for this Cell,
  2873. * null will be return if no such element exists.
  2874. */
  2875. XElement tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  2876. // If tcPr is null, this cell contains no width information.
  2877. if (tcPr == null)
  2878. return double.NaN;
  2879. /*
  2880. * Get the tcMar
  2881. *
  2882. */
  2883. XElement tcMar = tcPr.Element(XName.Get("tcMar", DocX.w.NamespaceName));
  2884. // If tcMar is null, this cell contains no margin information.
  2885. if (tcMar == null)
  2886. return double.NaN;
  2887. // Get the left (LeftMargin) element
  2888. XElement tcMarLeft = tcMar.Element(XName.Get("left", DocX.w.NamespaceName));
  2889. // If tcMarLeft is null, this cell contains no left margin information.
  2890. if (tcMarLeft == null)
  2891. return double.NaN;
  2892. // Get the w attribute of the tcMarLeft element.
  2893. XAttribute w = tcMarLeft.Attribute(XName.Get("w", DocX.w.NamespaceName));
  2894. // If w is null, this cell contains no width information.
  2895. if (w == null)
  2896. return double.NaN;
  2897. // If w is not a double, something is wrong with this attributes value, so remove it and return double.NaN;
  2898. double leftMarginInWordUnits;
  2899. if (!double.TryParse(w.Value, out leftMarginInWordUnits))
  2900. {
  2901. w.Remove();
  2902. return double.NaN;
  2903. }
  2904. // 15 "word units" is equal to one pixel.
  2905. return (leftMarginInWordUnits / 15);
  2906. }
  2907. set
  2908. {
  2909. /*
  2910. * Get the tcPr (table cell properties) element for this Cell,
  2911. * null will be return if no such element exists.
  2912. */
  2913. XElement tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  2914. if (tcPr == null)
  2915. {
  2916. Xml.SetElementValue(XName.Get("tcPr", DocX.w.NamespaceName), string.Empty);
  2917. tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  2918. }
  2919. /*
  2920. * Get the tcMar (table cell margin) element for this Cell,
  2921. * null will be return if no such element exists.
  2922. */
  2923. XElement tcMar = tcPr.Element(XName.Get("tcMar", DocX.w.NamespaceName));
  2924. if (tcMar == null)
  2925. {
  2926. tcPr.SetElementValue(XName.Get("tcMar", DocX.w.NamespaceName), string.Empty);
  2927. tcMar = tcPr.Element(XName.Get("tcMar", DocX.w.NamespaceName));
  2928. }
  2929. /*
  2930. * Get the left (table cell left margin) element for this Cell,
  2931. * null will be return if no such element exists.
  2932. */
  2933. XElement tcMarLeft = tcMar.Element(XName.Get("left", DocX.w.NamespaceName));
  2934. if (tcMarLeft == null)
  2935. {
  2936. tcMar.SetElementValue(XName.Get("left", DocX.w.NamespaceName), string.Empty);
  2937. tcMarLeft = tcMar.Element(XName.Get("left", DocX.w.NamespaceName));
  2938. }
  2939. // The type attribute needs to be set to dxa which represents "twips" or twentieths of a point. In other words, 1/1440th of an inch.
  2940. tcMarLeft.SetAttributeValue(XName.Get("type", DocX.w.NamespaceName), "dxa");
  2941. // 15 "word units" is equal to one pixel.
  2942. tcMarLeft.SetAttributeValue(XName.Get("w", DocX.w.NamespaceName), (value * 15).ToString());
  2943. }
  2944. }
  2945. /// <summary>
  2946. /// RightMargin in pixels. // Added by lckuiper
  2947. /// </summary>
  2948. /// <example>
  2949. /// <code>
  2950. /// // Create a new document.
  2951. ///using (DocX document = DocX.Create("Test.docx"))
  2952. ///{
  2953. /// // Insert table into this document.
  2954. /// Table t = document.InsertTable(3, 3);
  2955. /// t.Design = TableDesign.TableGrid;
  2956. ///
  2957. /// // Get the center cell.
  2958. /// Cell center = t.Rows[1].Cells[1];
  2959. ///
  2960. /// // Insert some text so that we can see the effect of the Margins.
  2961. /// center.Paragraphs[0].Append("Center Cell");
  2962. ///
  2963. /// // Set the center cells Right, Margin to 10.
  2964. /// center.MarginRight = 25;
  2965. ///
  2966. /// // Save the document.
  2967. /// document.Save();
  2968. ///}
  2969. /// </code>
  2970. /// </example>
  2971. public double MarginRight
  2972. {
  2973. get
  2974. {
  2975. /*
  2976. * Get the tcPr (table cell properties) element for this Cell,
  2977. * null will be return if no such element exists.
  2978. */
  2979. XElement tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  2980. // If tcPr is null, this cell contains no width information.
  2981. if (tcPr == null)
  2982. return double.NaN;
  2983. /*
  2984. * Get the tcMar
  2985. *
  2986. */
  2987. XElement tcMar = tcPr.Element(XName.Get("tcMar", DocX.w.NamespaceName));
  2988. // If tcMar is null, this cell contains no margin information.
  2989. if (tcMar == null)
  2990. return double.NaN;
  2991. // Get the right (RightMargin) element
  2992. XElement tcMarRight = tcMar.Element(XName.Get("right", DocX.w.NamespaceName));
  2993. // If tcMarRight is null, this cell contains no right margin information.
  2994. if (tcMarRight == null)
  2995. return double.NaN;
  2996. // Get the w attribute of the tcMarRight element.
  2997. XAttribute w = tcMarRight.Attribute(XName.Get("w", DocX.w.NamespaceName));
  2998. // If w is null, this cell contains no width information.
  2999. if (w == null)
  3000. return double.NaN;
  3001. // If w is not a double, something is wrong with this attributes value, so remove it and return double.NaN;
  3002. double rightMarginInWordUnits;
  3003. if (!double.TryParse(w.Value, out rightMarginInWordUnits))
  3004. {
  3005. w.Remove();
  3006. return double.NaN;
  3007. }
  3008. // 15 "word units" is equal to one pixel.
  3009. return (rightMarginInWordUnits / 15);
  3010. }
  3011. set
  3012. {
  3013. /*
  3014. * Get the tcPr (table cell properties) element for this Cell,
  3015. * null will be return if no such element exists.
  3016. */
  3017. XElement tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  3018. if (tcPr == null)
  3019. {
  3020. Xml.SetElementValue(XName.Get("tcPr", DocX.w.NamespaceName), string.Empty);
  3021. tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  3022. }
  3023. /*
  3024. * Get the tcMar (table cell margin) element for this Cell,
  3025. * null will be return if no such element exists.
  3026. */
  3027. XElement tcMar = tcPr.Element(XName.Get("tcMar", DocX.w.NamespaceName));
  3028. if (tcMar == null)
  3029. {
  3030. tcPr.SetElementValue(XName.Get("tcMar", DocX.w.NamespaceName), string.Empty);
  3031. tcMar = tcPr.Element(XName.Get("tcMar", DocX.w.NamespaceName));
  3032. }
  3033. /*
  3034. * Get the right (table cell right margin) element for this Cell,
  3035. * null will be return if no such element exists.
  3036. */
  3037. XElement tcMarRight = tcMar.Element(XName.Get("right", DocX.w.NamespaceName));
  3038. if (tcMarRight == null)
  3039. {
  3040. tcMar.SetElementValue(XName.Get("right", DocX.w.NamespaceName), string.Empty);
  3041. tcMarRight = tcMar.Element(XName.Get("right", DocX.w.NamespaceName));
  3042. }
  3043. // The type attribute needs to be set to dxa which represents "twips" or twentieths of a point. In other words, 1/1440th of an inch.
  3044. tcMarRight.SetAttributeValue(XName.Get("type", DocX.w.NamespaceName), "dxa");
  3045. // 15 "word units" is equal to one pixel.
  3046. tcMarRight.SetAttributeValue(XName.Get("w", DocX.w.NamespaceName), (value * 15).ToString());
  3047. }
  3048. }
  3049. /// <summary>
  3050. /// TopMargin in pixels. // Added by lckuiper
  3051. /// </summary>
  3052. /// <example>
  3053. /// <code>
  3054. /// // Create a new document.
  3055. ///using (DocX document = DocX.Create("Test.docx"))
  3056. ///{
  3057. /// // Insert table into this document.
  3058. /// Table t = document.InsertTable(3, 3);
  3059. /// t.Design = TableDesign.TableGrid;
  3060. ///
  3061. /// // Get the center cell.
  3062. /// Cell center = t.Rows[1].Cells[1];
  3063. ///
  3064. /// // Insert some text so that we can see the effect of the Margins.
  3065. /// center.Paragraphs[0].Append("Center Cell");
  3066. ///
  3067. /// // Set the center cells Top, Margin to 10.
  3068. /// center.MarginTop = 25;
  3069. ///
  3070. /// // Save the document.
  3071. /// document.Save();
  3072. ///}
  3073. /// </code>
  3074. /// </example>
  3075. public double MarginTop
  3076. {
  3077. get
  3078. {
  3079. /*
  3080. * Get the tcPr (table cell properties) element for this Cell,
  3081. * null will be return if no such element exists.
  3082. */
  3083. XElement tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  3084. // If tcPr is null, this cell contains no width information.
  3085. if (tcPr == null)
  3086. return double.NaN;
  3087. /*
  3088. * Get the tcMar
  3089. *
  3090. */
  3091. XElement tcMar = tcPr.Element(XName.Get("tcMar", DocX.w.NamespaceName));
  3092. // If tcMar is null, this cell contains no margin information.
  3093. if (tcMar == null)
  3094. return double.NaN;
  3095. // Get the top (TopMargin) element
  3096. XElement tcMarTop = tcMar.Element(XName.Get("top", DocX.w.NamespaceName));
  3097. // If tcMarTop is null, this cell contains no top margin information.
  3098. if (tcMarTop == null)
  3099. return double.NaN;
  3100. // Get the w attribute of the tcMarTop element.
  3101. XAttribute w = tcMarTop.Attribute(XName.Get("w", DocX.w.NamespaceName));
  3102. // If w is null, this cell contains no width information.
  3103. if (w == null)
  3104. return double.NaN;
  3105. // If w is not a double, something is wrong with this attributes value, so remove it and return double.NaN;
  3106. double topMarginInWordUnits;
  3107. if (!double.TryParse(w.Value, out topMarginInWordUnits))
  3108. {
  3109. w.Remove();
  3110. return double.NaN;
  3111. }
  3112. // 15 "word units" is equal to one pixel.
  3113. return (topMarginInWordUnits / 15);
  3114. }
  3115. set
  3116. {
  3117. /*
  3118. * Get the tcPr (table cell properties) element for this Cell,
  3119. * null will be return if no such element exists.
  3120. */
  3121. XElement tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  3122. if (tcPr == null)
  3123. {
  3124. Xml.SetElementValue(XName.Get("tcPr", DocX.w.NamespaceName), string.Empty);
  3125. tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  3126. }
  3127. /*
  3128. * Get the tcMar (table cell margin) element for this Cell,
  3129. * null will be return if no such element exists.
  3130. */
  3131. XElement tcMar = tcPr.Element(XName.Get("tcMar", DocX.w.NamespaceName));
  3132. if (tcMar == null)
  3133. {
  3134. tcPr.SetElementValue(XName.Get("tcMar", DocX.w.NamespaceName), string.Empty);
  3135. tcMar = tcPr.Element(XName.Get("tcMar", DocX.w.NamespaceName));
  3136. }
  3137. /*
  3138. * Get the top (table cell top margin) element for this Cell,
  3139. * null will be return if no such element exists.
  3140. */
  3141. XElement tcMarTop = tcMar.Element(XName.Get("top", DocX.w.NamespaceName));
  3142. if (tcMarTop == null)
  3143. {
  3144. tcMar.SetElementValue(XName.Get("top", DocX.w.NamespaceName), string.Empty);
  3145. tcMarTop = tcMar.Element(XName.Get("top", DocX.w.NamespaceName));
  3146. }
  3147. // The type attribute needs to be set to dxa which represents "twips" or twentieths of a point. In other words, 1/1440th of an inch.
  3148. tcMarTop.SetAttributeValue(XName.Get("type", DocX.w.NamespaceName), "dxa");
  3149. // 15 "word units" is equal to one pixel.
  3150. tcMarTop.SetAttributeValue(XName.Get("w", DocX.w.NamespaceName), (value * 15).ToString());
  3151. }
  3152. }
  3153. /// <summary>
  3154. /// BottomMargin in pixels. // Added by lckuiper
  3155. /// </summary>
  3156. /// <example>
  3157. /// <code>
  3158. /// // Create a new document.
  3159. ///using (DocX document = DocX.Create("Test.docx"))
  3160. ///{
  3161. /// // Insert table into this document.
  3162. /// Table t = document.InsertTable(3, 3);
  3163. /// t.Design = TableDesign.TableGrid;
  3164. ///
  3165. /// // Get the center cell.
  3166. /// Cell center = t.Rows[1].Cells[1];
  3167. ///
  3168. /// // Insert some text so that we can see the effect of the Margins.
  3169. /// center.Paragraphs[0].Append("Center Cell");
  3170. ///
  3171. /// // Set the center cells Top, Margin to 10.
  3172. /// center.MarginBottom = 25;
  3173. ///
  3174. /// // Save the document.
  3175. /// document.Save();
  3176. ///}
  3177. /// </code>
  3178. /// </example>
  3179. public double MarginBottom
  3180. {
  3181. get
  3182. {
  3183. /*
  3184. * Get the tcPr (table cell properties) element for this Cell,
  3185. * null will be return if no such element exists.
  3186. */
  3187. XElement tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  3188. // If tcPr is null, this cell contains no width information.
  3189. if (tcPr == null)
  3190. return double.NaN;
  3191. /*
  3192. * Get the tcMar
  3193. *
  3194. */
  3195. XElement tcMar = tcPr.Element(XName.Get("tcMar", DocX.w.NamespaceName));
  3196. // If tcMar is null, this cell contains no margin information.
  3197. if (tcMar == null)
  3198. return double.NaN;
  3199. // Get the bottom (BottomMargin) element
  3200. XElement tcMarBottom = tcMar.Element(XName.Get("bottom", DocX.w.NamespaceName));
  3201. // If tcMarBottom is null, this cell contains no bottom margin information.
  3202. if (tcMarBottom == null)
  3203. return double.NaN;
  3204. // Get the w attribute of the tcMarBottom element.
  3205. XAttribute w = tcMarBottom.Attribute(XName.Get("w", DocX.w.NamespaceName));
  3206. // If w is null, this cell contains no width information.
  3207. if (w == null)
  3208. return double.NaN;
  3209. // If w is not a double, something is wrong with this attributes value, so remove it and return double.NaN;
  3210. double bottomMarginInWordUnits;
  3211. if (!double.TryParse(w.Value, out bottomMarginInWordUnits))
  3212. {
  3213. w.Remove();
  3214. return double.NaN;
  3215. }
  3216. // 15 "word units" is equal to one pixel.
  3217. return (bottomMarginInWordUnits / 15);
  3218. }
  3219. set
  3220. {
  3221. /*
  3222. * Get the tcPr (table cell properties) element for this Cell,
  3223. * null will be return if no such element exists.
  3224. */
  3225. XElement tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  3226. if (tcPr == null)
  3227. {
  3228. Xml.SetElementValue(XName.Get("tcPr", DocX.w.NamespaceName), string.Empty);
  3229. tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  3230. }
  3231. /*
  3232. * Get the tcMar (table cell margin) element for this Cell,
  3233. * null will be return if no such element exists.
  3234. */
  3235. XElement tcMar = tcPr.Element(XName.Get("tcMar", DocX.w.NamespaceName));
  3236. if (tcMar == null)
  3237. {
  3238. tcPr.SetElementValue(XName.Get("tcMar", DocX.w.NamespaceName), string.Empty);
  3239. tcMar = tcPr.Element(XName.Get("tcMar", DocX.w.NamespaceName));
  3240. }
  3241. /*
  3242. * Get the bottom (table cell bottom margin) element for this Cell,
  3243. * null will be return if no such element exists.
  3244. */
  3245. XElement tcMarBottom = tcMar.Element(XName.Get("bottom", DocX.w.NamespaceName));
  3246. if (tcMarBottom == null)
  3247. {
  3248. tcMar.SetElementValue(XName.Get("bottom", DocX.w.NamespaceName), string.Empty);
  3249. tcMarBottom = tcMar.Element(XName.Get("bottom", DocX.w.NamespaceName));
  3250. }
  3251. // The type attribute needs to be set to dxa which represents "twips" or twentieths of a point. In other words, 1/1440th of an inch.
  3252. tcMarBottom.SetAttributeValue(XName.Get("type", DocX.w.NamespaceName), "dxa");
  3253. // 15 "word units" is equal to one pixel.
  3254. tcMarBottom.SetAttributeValue(XName.Get("w", DocX.w.NamespaceName), (value * 15).ToString());
  3255. }
  3256. }
  3257. /// <summary>
  3258. /// Set the table cell border
  3259. /// Added by lckuiper @ 20101117
  3260. /// </summary>
  3261. /// <example>
  3262. /// <code>
  3263. /// // Create a new document.
  3264. ///using (DocX document = DocX.Create("Test.docx"))
  3265. ///{
  3266. /// // Insert a table into this document.
  3267. /// Table t = document.InsertTable(3, 3);
  3268. ///
  3269. /// // Get the center cell.
  3270. /// Cell center = t.Rows[1].Cells[1];
  3271. ///
  3272. /// // Create a large blue border.
  3273. /// Border b = new Border(BorderStyle.Tcbs_single, BorderSize.seven, 0, Color.Blue);
  3274. ///
  3275. /// // Set the center cells Top, Bottom, Left and Right Borders to b.
  3276. /// center.SetBorder(TableCellBorderType.Top, b);
  3277. /// center.SetBorder(TableCellBorderType.Bottom, b);
  3278. /// center.SetBorder(TableCellBorderType.Left, b);
  3279. /// center.SetBorder(TableCellBorderType.Right, b);
  3280. ///
  3281. /// // Save the document.
  3282. /// document.Save();
  3283. ///}
  3284. /// </code>
  3285. /// </example>
  3286. /// <param name="borderType">Table Cell border to set</param>
  3287. /// <param name="border">Border object to set the table cell border</param>
  3288. public void SetBorder(TableCellBorderType borderType, Border border)
  3289. {
  3290. /*
  3291. * Get the tcPr (table cell properties) element for this Cell,
  3292. * null will be return if no such element exists.
  3293. */
  3294. XElement tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  3295. if (tcPr == null)
  3296. {
  3297. Xml.SetElementValue(XName.Get("tcPr", DocX.w.NamespaceName), string.Empty);
  3298. tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  3299. }
  3300. /*
  3301. * Get the tblBorders (table cell borders) element for this Cell,
  3302. * null will be return if no such element exists.
  3303. */
  3304. XElement tcBorders = tcPr.Element(XName.Get("tcBorders", DocX.w.NamespaceName));
  3305. if (tcBorders == null)
  3306. {
  3307. tcPr.SetElementValue(XName.Get("tcBorders", DocX.w.NamespaceName), string.Empty);
  3308. tcBorders = tcPr.Element(XName.Get("tcBorders", DocX.w.NamespaceName));
  3309. }
  3310. /*
  3311. * Get the 'borderType' (table cell border) element for this Cell,
  3312. * null will be return if no such element exists.
  3313. */
  3314. string tcbordertype;
  3315. switch (borderType)
  3316. {
  3317. case TableCellBorderType.TopLeftToBottomRight:
  3318. tcbordertype = "tl2br";
  3319. break;
  3320. case TableCellBorderType.TopRightToBottomLeft:
  3321. tcbordertype = "tr2bl";
  3322. break;
  3323. default:
  3324. // enum to string
  3325. tcbordertype = borderType.ToString();
  3326. // only lower the first char of string (because of insideH and insideV)
  3327. tcbordertype = tcbordertype.Substring(0, 1).ToLower() + tcbordertype.Substring(1);
  3328. break;
  3329. }
  3330. XElement tcBorderType = tcBorders.Element(XName.Get(borderType.ToString(), DocX.w.NamespaceName));
  3331. if (tcBorderType == null)
  3332. {
  3333. tcBorders.SetElementValue(XName.Get(tcbordertype, DocX.w.NamespaceName), string.Empty);
  3334. tcBorderType = tcBorders.Element(XName.Get(tcbordertype, DocX.w.NamespaceName));
  3335. }
  3336. // get string value of border style
  3337. string borderstyle = border.Tcbs.ToString().Substring(5);
  3338. borderstyle = borderstyle.Substring(0, 1).ToLower() + borderstyle.Substring(1);
  3339. // The val attribute is used for the border style
  3340. tcBorderType.SetAttributeValue(XName.Get("val", DocX.w.NamespaceName), borderstyle);
  3341. int size;
  3342. switch (border.Size)
  3343. {
  3344. case BorderSize.one: size = 2; break;
  3345. case BorderSize.two: size = 4; break;
  3346. case BorderSize.three: size = 6; break;
  3347. case BorderSize.four: size = 8; break;
  3348. case BorderSize.five: size = 12; break;
  3349. case BorderSize.six: size = 18; break;
  3350. case BorderSize.seven: size = 24; break;
  3351. case BorderSize.eight: size = 36; break;
  3352. case BorderSize.nine: size = 48; break;
  3353. default: size = 2; break;
  3354. }
  3355. // The sz attribute is used for the border size
  3356. tcBorderType.SetAttributeValue(XName.Get("sz", DocX.w.NamespaceName), (size).ToString());
  3357. // The space attribute is used for the cell spacing (probably '0')
  3358. tcBorderType.SetAttributeValue(XName.Get("space", DocX.w.NamespaceName), (border.Space).ToString());
  3359. // The color attribute is used for the border color
  3360. tcBorderType.SetAttributeValue(XName.Get("color", DocX.w.NamespaceName), border.Color.ToHex());
  3361. }
  3362. /// <summary>
  3363. /// Get a table cell border
  3364. /// Added by lckuiper @ 20101117
  3365. /// </summary>
  3366. /// <param name="borderType">The table cell border to get</param>
  3367. public Border GetBorder(TableCellBorderType borderType)
  3368. {
  3369. // instance with default border values
  3370. Border b = new Border();
  3371. /*
  3372. * Get the tcPr (table cell properties) element for this Cell,
  3373. * null will be return if no such element exists.
  3374. */
  3375. XElement tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  3376. if (tcPr == null)
  3377. {
  3378. // uses default border style
  3379. }
  3380. /*
  3381. * Get the tcBorders (table cell borders) element for this Cell,
  3382. * null will be return if no such element exists.
  3383. */
  3384. XElement tcBorders = tcPr.Element(XName.Get("tcBorders", DocX.w.NamespaceName));
  3385. if (tcBorders == null)
  3386. {
  3387. // uses default border style
  3388. }
  3389. /*
  3390. * Get the 'borderType' (cell border) element for this Cell,
  3391. * null will be return if no such element exists.
  3392. */
  3393. string tcbordertype;
  3394. tcbordertype = borderType.ToString();
  3395. switch (tcbordertype)
  3396. {
  3397. case "TopLeftToBottomRight":
  3398. tcbordertype = "tl2br";
  3399. break;
  3400. case "TopRightToBottomLeft":
  3401. tcbordertype = "tr2bl";
  3402. break;
  3403. default:
  3404. // only lower the first char of string (because of insideH and insideV)
  3405. tcbordertype = tcbordertype.Substring(0, 1).ToLower() + tcbordertype.Substring(1);
  3406. break;
  3407. }
  3408. XElement tcBorderType = tcBorders.Element(XName.Get(tcbordertype, DocX.w.NamespaceName));
  3409. if (tcBorderType == null)
  3410. {
  3411. // uses default border style
  3412. }
  3413. // The val attribute is used for the border style
  3414. XAttribute val = tcBorderType.Attribute(XName.Get("val", DocX.w.NamespaceName));
  3415. // If val is null, this cell contains no border information.
  3416. if (val == null)
  3417. {
  3418. // uses default border style
  3419. }
  3420. else
  3421. {
  3422. try
  3423. {
  3424. string bordertype = "Tcbs_" + val.Value;
  3425. b.Tcbs = (BorderStyle)Enum.Parse(typeof(BorderStyle), bordertype);
  3426. }
  3427. catch
  3428. {
  3429. val.Remove();
  3430. // uses default border style
  3431. }
  3432. }
  3433. // The sz attribute is used for the border size
  3434. XAttribute sz = tcBorderType.Attribute(XName.Get("sz", DocX.w.NamespaceName));
  3435. // If sz is null, this border contains no size information.
  3436. if (sz == null)
  3437. {
  3438. // uses default border style
  3439. }
  3440. else
  3441. {
  3442. // If sz is not an int, something is wrong with this attributes value, so remove it
  3443. int numerical_size;
  3444. if (!int.TryParse(sz.Value, out numerical_size))
  3445. sz.Remove();
  3446. else
  3447. {
  3448. switch (numerical_size)
  3449. {
  3450. case 2: b.Size = BorderSize.one; break;
  3451. case 4: b.Size = BorderSize.two; break;
  3452. case 6: b.Size = BorderSize.three; break;
  3453. case 8: b.Size = BorderSize.four; break;
  3454. case 12: b.Size = BorderSize.five; break;
  3455. case 18: b.Size = BorderSize.six; break;
  3456. case 24: b.Size = BorderSize.seven; break;
  3457. case 36: b.Size = BorderSize.eight; break;
  3458. case 48: b.Size = BorderSize.nine; break;
  3459. default: b.Size = BorderSize.one; break;
  3460. }
  3461. }
  3462. }
  3463. // The space attribute is used for the border spacing (probably '0')
  3464. XAttribute space = tcBorderType.Attribute(XName.Get("space", DocX.w.NamespaceName));
  3465. // If space is null, this border contains no space information.
  3466. if (space == null)
  3467. {
  3468. // uses default border style
  3469. }
  3470. else
  3471. {
  3472. // If space is not an int, something is wrong with this attributes value, so remove it
  3473. int borderspace;
  3474. if (!int.TryParse(space.Value, out borderspace))
  3475. {
  3476. space.Remove();
  3477. // uses default border style
  3478. }
  3479. else
  3480. {
  3481. b.Space = borderspace;
  3482. }
  3483. }
  3484. // The color attribute is used for the border color
  3485. XAttribute color = tcBorderType.Attribute(XName.Get("color", DocX.w.NamespaceName));
  3486. if (color == null)
  3487. {
  3488. // uses default border style
  3489. }
  3490. else
  3491. {
  3492. // If color is not a Color, something is wrong with this attributes value, so remove it
  3493. try
  3494. {
  3495. b.Color = ColorTranslator.FromHtml(string.Format("#{0}", color.Value));
  3496. }
  3497. catch
  3498. {
  3499. color.Remove();
  3500. // uses default border style
  3501. }
  3502. }
  3503. return b;
  3504. }
  3505. /// <summary>
  3506. /// Gets or Sets the fill color of this Cell.
  3507. /// </summary>
  3508. /// <example>
  3509. /// <code>
  3510. /// // Create a new document.
  3511. /// using (DocX document = DocX.Create("Test.docx"))
  3512. /// {
  3513. /// // Insert a table into this document.
  3514. /// Table t = document.InsertTable(3, 3);
  3515. ///
  3516. /// // Fill the first cell as Blue.
  3517. /// t.Rows[0].Cells[0].FillColor = Color.Blue;
  3518. /// // Fill the middle cell as Red.
  3519. /// t.Rows[1].Cells[1].FillColor = Color.Red;
  3520. /// // Fill the last cell as Green.
  3521. /// t.Rows[2].Cells[2].FillColor = Color.Green;
  3522. ///
  3523. /// // Save the document.
  3524. /// document.Save();
  3525. /// }
  3526. /// </code>
  3527. /// </example>
  3528. public Color FillColor
  3529. {
  3530. get
  3531. {
  3532. /*
  3533. * Get the tcPr (table cell properties) element for this Cell,
  3534. * null will be return if no such element exists.
  3535. */
  3536. XElement tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  3537. if (tcPr == null)
  3538. return Color.Empty;
  3539. else
  3540. {
  3541. XElement shd = tcPr.Element(XName.Get("shd", DocX.w.NamespaceName));
  3542. if (shd == null)
  3543. return Color.Empty;
  3544. else
  3545. {
  3546. XAttribute fill = shd.Attribute(XName.Get("fill", DocX.w.NamespaceName));
  3547. if (fill == null)
  3548. return Color.Empty;
  3549. else
  3550. {
  3551. int argb = Int32.Parse(fill.Value.Replace("#", ""), NumberStyles.HexNumber);
  3552. return Color.FromArgb(argb);
  3553. }
  3554. }
  3555. }
  3556. }
  3557. set
  3558. {
  3559. /*
  3560. * Get the tcPr (table cell properties) element for this Cell,
  3561. * null will be return if no such element exists.
  3562. */
  3563. XElement tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  3564. if (tcPr == null)
  3565. {
  3566. Xml.SetElementValue(XName.Get("tcPr", DocX.w.NamespaceName), string.Empty);
  3567. tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  3568. }
  3569. /*
  3570. * Get the tcW (table cell width) element for this Cell,
  3571. * null will be return if no such element exists.
  3572. */
  3573. XElement shd = tcPr.Element(XName.Get("shd", DocX.w.NamespaceName));
  3574. if (shd == null)
  3575. {
  3576. tcPr.SetElementValue(XName.Get("shd", DocX.w.NamespaceName), string.Empty);
  3577. shd = tcPr.Element(XName.Get("shd", DocX.w.NamespaceName));
  3578. }
  3579. shd.SetAttributeValue(XName.Get("val", DocX.w.NamespaceName), "clear");
  3580. shd.SetAttributeValue(XName.Get("color", DocX.w.NamespaceName), "auto");
  3581. shd.SetAttributeValue(XName.Get("fill", DocX.w.NamespaceName), value.ToHex());
  3582. }
  3583. }
  3584. public override Table InsertTable(int rowCount, int columnCount)
  3585. {
  3586. Table table = base.InsertTable(rowCount, columnCount);
  3587. table.mainPart = mainPart;
  3588. InsertParagraph(); //Dmitchern, It is necessary to put paragraph in the end of the cell, without it MS-Word will say that the document is corrupted
  3589. //IMPORTANT: It will be better to check all methods that work with adding anything to cells
  3590. return table;
  3591. }
  3592. public TextDirection TextDirection
  3593. {
  3594. get
  3595. {
  3596. XElement tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  3597. // If tcPr is null, this cell contains no width information.
  3598. if (tcPr == null)
  3599. return TextDirection.right;
  3600. XElement textDirection = tcPr.Element(XName.Get("textDirection", DocX.w.NamespaceName));
  3601. if (textDirection == null)
  3602. return TextDirection.right;
  3603. XAttribute val = textDirection.Attribute(XName.Get("val", DocX.w.NamespaceName));
  3604. if (val == null)
  3605. return TextDirection.right;
  3606. // If val is not a VerticalAlign enum, something is wrong with this attributes value, so remove it and return VerticalAlignment.Center;
  3607. try
  3608. {
  3609. return (TextDirection)Enum.Parse(typeof(TextDirection), val.Value, true);
  3610. }
  3611. catch
  3612. {
  3613. val.Remove();
  3614. return TextDirection.right;
  3615. }
  3616. }
  3617. set
  3618. {
  3619. /*
  3620. * Get the tcPr (table cell properties) element for this Cell,
  3621. * null will be return if no such element exists.
  3622. */
  3623. XElement tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  3624. if (tcPr == null)
  3625. {
  3626. Xml.SetElementValue(XName.Get("tcPr", DocX.w.NamespaceName), string.Empty);
  3627. tcPr = Xml.Element(XName.Get("tcPr", DocX.w.NamespaceName));
  3628. }
  3629. /*
  3630. * Get the vAlign (table cell vertical alignment) element for this Cell,
  3631. * null will be return if no such element exists.
  3632. */
  3633. XElement textDirection = tcPr.Element(XName.Get("textDirection", DocX.w.NamespaceName));
  3634. if (textDirection == null)
  3635. {
  3636. tcPr.SetElementValue(XName.Get("textDirection", DocX.w.NamespaceName), string.Empty);
  3637. textDirection = tcPr.Element(XName.Get("textDirection", DocX.w.NamespaceName));
  3638. }
  3639. // Set the VerticalAlignment in 'val'
  3640. textDirection.SetAttributeValue(XName.Get("val", DocX.w.NamespaceName), value.ToString());
  3641. }
  3642. }
  3643. }
  3644. public class TableLook
  3645. {
  3646. public bool FirstRow { get; set; }
  3647. public bool LastRow { get; set; }
  3648. public bool FirstColumn { get; set; }
  3649. public bool LastColumn { get; set; }
  3650. public bool NoHorizontalBanding { get; set; }
  3651. public bool NoVerticalBanding { get; set; }
  3652. }
  3653. }