|
@@ -24,22 +24,23 @@ namespace OpenXmlPowerTools
|
|
{
|
|
{
|
|
public static XDocument GetXDocument(this OpenXmlPart part)
|
|
public static XDocument GetXDocument(this OpenXmlPart part)
|
|
{
|
|
{
|
|
- if (part == null) throw new ArgumentNullException("part");
|
|
|
|
|
|
+ if (part == null) throw new ArgumentNullException(nameof(part));
|
|
|
|
|
|
- XDocument partXDocument = part.Annotation<XDocument>();
|
|
|
|
|
|
+ var partXDocument = part.Annotation<XDocument>();
|
|
if (partXDocument != null) return partXDocument;
|
|
if (partXDocument != null) return partXDocument;
|
|
|
|
|
|
using (Stream partStream = part.GetStream())
|
|
using (Stream partStream = part.GetStream())
|
|
{
|
|
{
|
|
if (partStream.Length == 0)
|
|
if (partStream.Length == 0)
|
|
{
|
|
{
|
|
- partXDocument = new XDocument();
|
|
|
|
- partXDocument.Declaration = new XDeclaration("1.0", "UTF-8", "yes");
|
|
|
|
|
|
+ partXDocument = new XDocument { Declaration = new XDeclaration("1.0", "UTF-8", "yes") };
|
|
}
|
|
}
|
|
else
|
|
else
|
|
{
|
|
{
|
|
using (XmlReader partXmlReader = XmlReader.Create(partStream))
|
|
using (XmlReader partXmlReader = XmlReader.Create(partStream))
|
|
|
|
+ {
|
|
partXDocument = XDocument.Load(partXmlReader);
|
|
partXDocument = XDocument.Load(partXmlReader);
|
|
|
|
+ }
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
@@ -49,10 +50,10 @@ namespace OpenXmlPowerTools
|
|
|
|
|
|
public static XDocument GetXDocument(this OpenXmlPart part, out XmlNamespaceManager namespaceManager)
|
|
public static XDocument GetXDocument(this OpenXmlPart part, out XmlNamespaceManager namespaceManager)
|
|
{
|
|
{
|
|
- if (part == null) throw new ArgumentNullException("part");
|
|
|
|
|
|
+ if (part == null) throw new ArgumentNullException(nameof(part));
|
|
|
|
|
|
namespaceManager = part.Annotation<XmlNamespaceManager>();
|
|
namespaceManager = part.Annotation<XmlNamespaceManager>();
|
|
- XDocument partXDocument = part.Annotation<XDocument>();
|
|
|
|
|
|
+ var partXDocument = part.Annotation<XDocument>();
|
|
if (partXDocument != null)
|
|
if (partXDocument != null)
|
|
{
|
|
{
|
|
if (namespaceManager != null) return partXDocument;
|
|
if (namespaceManager != null) return partXDocument;
|
|
@@ -67,101 +68,148 @@ namespace OpenXmlPowerTools
|
|
{
|
|
{
|
|
if (partStream.Length == 0)
|
|
if (partStream.Length == 0)
|
|
{
|
|
{
|
|
- partXDocument = new XDocument();
|
|
|
|
- partXDocument.Declaration = new XDeclaration("1.0", "UTF-8", "yes");
|
|
|
|
-
|
|
|
|
|
|
+ partXDocument = new XDocument { Declaration = new XDeclaration("1.0", "UTF-8", "yes") };
|
|
part.AddAnnotation(partXDocument);
|
|
part.AddAnnotation(partXDocument);
|
|
|
|
|
|
return partXDocument;
|
|
return partXDocument;
|
|
}
|
|
}
|
|
- else
|
|
|
|
|
|
+
|
|
|
|
+ using (XmlReader partXmlReader = XmlReader.Create(partStream))
|
|
{
|
|
{
|
|
- using (XmlReader partXmlReader = XmlReader.Create(partStream))
|
|
|
|
- {
|
|
|
|
- partXDocument = XDocument.Load(partXmlReader);
|
|
|
|
- namespaceManager = new XmlNamespaceManager(partXmlReader.NameTable);
|
|
|
|
|
|
+ partXDocument = XDocument.Load(partXmlReader);
|
|
|
|
+ XmlNameTable nameTable = partXmlReader.NameTable ?? throw new Exception("NameTable is null.");
|
|
|
|
+ namespaceManager = new XmlNamespaceManager(nameTable);
|
|
|
|
|
|
- part.AddAnnotation(partXDocument);
|
|
|
|
- part.AddAnnotation(namespaceManager);
|
|
|
|
|
|
+ part.AddAnnotation(partXDocument);
|
|
|
|
+ part.AddAnnotation(namespaceManager);
|
|
|
|
|
|
- return partXDocument;
|
|
|
|
- }
|
|
|
|
|
|
+ return partXDocument;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
|
|
+ /// <summary>
|
|
|
|
+ /// Gets the given <see cref="OpenXmlPart" />'s root <see cref="XElement" />.
|
|
|
|
+ /// </summary>
|
|
|
|
+ /// <param name="part">The <see cref="OpenXmlPart" />.</param>
|
|
|
|
+ /// <returns>The root <see cref="XElement" />.</returns>
|
|
|
|
+ public static XElement GetXElement(this OpenXmlPart part)
|
|
|
|
+ {
|
|
|
|
+ if (part == null) throw new ArgumentNullException(nameof(part));
|
|
|
|
+
|
|
|
|
+ return part.GetXDocument().Root ?? throw new ArgumentException("Part does not contain a root element.");
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ /// <summary>
|
|
|
|
+ /// Saves the cached <see cref="XDocument"/> to the the given <see cref="OpenXmlPart"/>.
|
|
|
|
+ /// </summary>
|
|
|
|
+ /// <param name="part">The <see cref="OpenXmlPart"/>.</param>
|
|
public static void PutXDocument(this OpenXmlPart part)
|
|
public static void PutXDocument(this OpenXmlPart part)
|
|
{
|
|
{
|
|
- if (part == null) throw new ArgumentNullException("part");
|
|
|
|
|
|
+ if (part == null) throw new ArgumentNullException(nameof(part));
|
|
|
|
|
|
XDocument partXDocument = part.GetXDocument();
|
|
XDocument partXDocument = part.GetXDocument();
|
|
if (partXDocument != null)
|
|
if (partXDocument != null)
|
|
{
|
|
{
|
|
-#if true
|
|
|
|
using (Stream partStream = part.GetStream(FileMode.Create, FileAccess.Write))
|
|
using (Stream partStream = part.GetStream(FileMode.Create, FileAccess.Write))
|
|
using (XmlWriter partXmlWriter = XmlWriter.Create(partStream))
|
|
using (XmlWriter partXmlWriter = XmlWriter.Create(partStream))
|
|
|
|
+ {
|
|
partXDocument.Save(partXmlWriter);
|
|
partXDocument.Save(partXmlWriter);
|
|
-#else
|
|
|
|
- byte[] array = Encoding.UTF8.GetBytes(partXDocument.ToString(SaveOptions.DisableFormatting));
|
|
|
|
- using (MemoryStream ms = new MemoryStream(array))
|
|
|
|
- part.FeedData(ms);
|
|
|
|
-#endif
|
|
|
|
|
|
+ }
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
|
|
+ /// <summary>
|
|
|
|
+ /// Saves the cached <see cref="XDocument"/> to the the given <see cref="OpenXmlPart"/>,
|
|
|
|
+ /// indending the XML markup and creating new lines for attributes.
|
|
|
|
+ /// </summary>
|
|
|
|
+ /// <param name="part">The <see cref="OpenXmlPart"/>.</param>
|
|
public static void PutXDocumentWithFormatting(this OpenXmlPart part)
|
|
public static void PutXDocumentWithFormatting(this OpenXmlPart part)
|
|
{
|
|
{
|
|
- if (part == null) throw new ArgumentNullException("part");
|
|
|
|
|
|
+ if (part == null) throw new ArgumentNullException(nameof(part));
|
|
|
|
|
|
XDocument partXDocument = part.GetXDocument();
|
|
XDocument partXDocument = part.GetXDocument();
|
|
if (partXDocument != null)
|
|
if (partXDocument != null)
|
|
{
|
|
{
|
|
using (Stream partStream = part.GetStream(FileMode.Create, FileAccess.Write))
|
|
using (Stream partStream = part.GetStream(FileMode.Create, FileAccess.Write))
|
|
{
|
|
{
|
|
- XmlWriterSettings settings = new XmlWriterSettings();
|
|
|
|
- settings.Indent = true;
|
|
|
|
- settings.OmitXmlDeclaration = true;
|
|
|
|
- settings.NewLineOnAttributes = true;
|
|
|
|
|
|
+ var settings = new XmlWriterSettings
|
|
|
|
+ {
|
|
|
|
+ Indent = true,
|
|
|
|
+ OmitXmlDeclaration = true,
|
|
|
|
+ NewLineOnAttributes = true
|
|
|
|
+ };
|
|
|
|
+
|
|
using (XmlWriter partXmlWriter = XmlWriter.Create(partStream, settings))
|
|
using (XmlWriter partXmlWriter = XmlWriter.Create(partStream, settings))
|
|
|
|
+ {
|
|
partXDocument.Save(partXmlWriter);
|
|
partXDocument.Save(partXmlWriter);
|
|
|
|
+ }
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
public static void PutXDocument(this OpenXmlPart part, XDocument document)
|
|
public static void PutXDocument(this OpenXmlPart part, XDocument document)
|
|
{
|
|
{
|
|
- if (part == null) throw new ArgumentNullException("part");
|
|
|
|
- if (document == null) throw new ArgumentNullException("document");
|
|
|
|
|
|
+ if (part == null) throw new ArgumentNullException(nameof(part));
|
|
|
|
+ if (document == null) throw new ArgumentNullException(nameof(document));
|
|
|
|
|
|
- using (Stream partStream = part.GetStream(FileMode.Open, FileAccess.Read))
|
|
|
|
|
|
+ using (Stream partStream = part.GetStream(FileMode.Create, FileAccess.Write))
|
|
using (XmlWriter partXmlWriter = XmlWriter.Create(partStream))
|
|
using (XmlWriter partXmlWriter = XmlWriter.Create(partStream))
|
|
|
|
+ {
|
|
document.Save(partXmlWriter);
|
|
document.Save(partXmlWriter);
|
|
|
|
+ }
|
|
|
|
|
|
part.RemoveAnnotations<XDocument>();
|
|
part.RemoveAnnotations<XDocument>();
|
|
part.AddAnnotation(document);
|
|
part.AddAnnotation(document);
|
|
}
|
|
}
|
|
|
|
|
|
|
|
+ /// <summary>
|
|
|
|
+ /// Writes the cached root <see cref="XElement" /> to the given <see cref="OpenXmlPart" />.
|
|
|
|
+ /// </summary>
|
|
|
|
+ /// <param name="part">The <see cref="OpenXmlPart"/>.</param>
|
|
|
|
+ public static void PutXElement(this OpenXmlPart part)
|
|
|
|
+ {
|
|
|
|
+ if (part == null) throw new ArgumentNullException(nameof(part));
|
|
|
|
+
|
|
|
|
+ part.PutXDocument();
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ /// <summary>
|
|
|
|
+ /// Writes the given root <see cref="XElement" /> to the given <see cref="OpenXmlPart" />.
|
|
|
|
+ /// </summary>
|
|
|
|
+ /// <param name="part">The <see cref="OpenXmlPart" />.</param>
|
|
|
|
+ /// <param name="root">The root <see cref="XElement" />.</param>
|
|
|
|
+ public static void PutXElement(this OpenXmlPart part, XElement root)
|
|
|
|
+ {
|
|
|
|
+ if (root == null) throw new ArgumentNullException(nameof(root));
|
|
|
|
+
|
|
|
|
+ PutXDocument(part, new XDocument(new XDeclaration("1.0", "UTF-8", "yes"), root));
|
|
|
|
+ }
|
|
|
|
+
|
|
private static XmlNamespaceManager GetManagerFromXDocument(XDocument xDocument)
|
|
private static XmlNamespaceManager GetManagerFromXDocument(XDocument xDocument)
|
|
{
|
|
{
|
|
XmlReader reader = xDocument.CreateReader();
|
|
XmlReader reader = xDocument.CreateReader();
|
|
XDocument newXDoc = XDocument.Load(reader);
|
|
XDocument newXDoc = XDocument.Load(reader);
|
|
|
|
|
|
- XElement rootElement = xDocument.Elements().FirstOrDefault();
|
|
|
|
|
|
+ XElement rootElement = xDocument.Elements().First();
|
|
rootElement.ReplaceWith(newXDoc.Root);
|
|
rootElement.ReplaceWith(newXDoc.Root);
|
|
|
|
|
|
- XmlNameTable nameTable = reader.NameTable;
|
|
|
|
- XmlNamespaceManager namespaceManager = new XmlNamespaceManager(nameTable);
|
|
|
|
|
|
+ XmlNameTable nameTable = reader.NameTable ?? throw new Exception("NameTable is null.");
|
|
|
|
+ var namespaceManager = new XmlNamespaceManager(nameTable);
|
|
return namespaceManager;
|
|
return namespaceManager;
|
|
}
|
|
}
|
|
|
|
|
|
public static IEnumerable<XElement> LogicalChildrenContent(this XElement element)
|
|
public static IEnumerable<XElement> LogicalChildrenContent(this XElement element)
|
|
{
|
|
{
|
|
if (element.Name == W.document)
|
|
if (element.Name == W.document)
|
|
|
|
+ {
|
|
return element.Descendants(W.body).Take(1);
|
|
return element.Descendants(W.body).Take(1);
|
|
|
|
+ }
|
|
|
|
|
|
if (element.Name == W.body ||
|
|
if (element.Name == W.body ||
|
|
element.Name == W.tc ||
|
|
element.Name == W.tc ||
|
|
element.Name == W.txbxContent)
|
|
element.Name == W.txbxContent)
|
|
|
|
+ {
|
|
return element
|
|
return element
|
|
.DescendantsTrimmed(e =>
|
|
.DescendantsTrimmed(e =>
|
|
e.Name == W.tbl ||
|
|
e.Name == W.tbl ||
|
|
@@ -169,32 +217,42 @@ namespace OpenXmlPowerTools
|
|
.Where(e =>
|
|
.Where(e =>
|
|
e.Name == W.p ||
|
|
e.Name == W.p ||
|
|
e.Name == W.tbl);
|
|
e.Name == W.tbl);
|
|
|
|
+ }
|
|
|
|
|
|
if (element.Name == W.tbl)
|
|
if (element.Name == W.tbl)
|
|
|
|
+ {
|
|
return element
|
|
return element
|
|
.DescendantsTrimmed(W.tr)
|
|
.DescendantsTrimmed(W.tr)
|
|
.Where(e => e.Name == W.tr);
|
|
.Where(e => e.Name == W.tr);
|
|
|
|
+ }
|
|
|
|
|
|
if (element.Name == W.tr)
|
|
if (element.Name == W.tr)
|
|
|
|
+ {
|
|
return element
|
|
return element
|
|
.DescendantsTrimmed(W.tc)
|
|
.DescendantsTrimmed(W.tc)
|
|
.Where(e => e.Name == W.tc);
|
|
.Where(e => e.Name == W.tc);
|
|
|
|
+ }
|
|
|
|
|
|
if (element.Name == W.p)
|
|
if (element.Name == W.p)
|
|
|
|
+ {
|
|
return element
|
|
return element
|
|
.DescendantsTrimmed(e => e.Name == W.r ||
|
|
.DescendantsTrimmed(e => e.Name == W.r ||
|
|
- e.Name == W.pict ||
|
|
|
|
- e.Name == W.drawing)
|
|
|
|
|
|
+ e.Name == W.pict ||
|
|
|
|
+ e.Name == W.drawing)
|
|
.Where(e => e.Name == W.r ||
|
|
.Where(e => e.Name == W.r ||
|
|
- e.Name == W.pict ||
|
|
|
|
- e.Name == W.drawing);
|
|
|
|
|
|
+ e.Name == W.pict ||
|
|
|
|
+ e.Name == W.drawing);
|
|
|
|
+ }
|
|
|
|
|
|
if (element.Name == W.r)
|
|
if (element.Name == W.r)
|
|
|
|
+ {
|
|
return element
|
|
return element
|
|
.DescendantsTrimmed(e => W.SubRunLevelContent.Contains(e.Name))
|
|
.DescendantsTrimmed(e => W.SubRunLevelContent.Contains(e.Name))
|
|
.Where(e => W.SubRunLevelContent.Contains(e.Name));
|
|
.Where(e => W.SubRunLevelContent.Contains(e.Name));
|
|
|
|
+ }
|
|
|
|
|
|
if (element.Name == MC.AlternateContent)
|
|
if (element.Name == MC.AlternateContent)
|
|
|
|
+ {
|
|
return element
|
|
return element
|
|
.DescendantsTrimmed(e =>
|
|
.DescendantsTrimmed(e =>
|
|
e.Name == W.pict ||
|
|
e.Name == W.pict ||
|
|
@@ -203,11 +261,14 @@ namespace OpenXmlPowerTools
|
|
.Where(e =>
|
|
.Where(e =>
|
|
e.Name == W.pict ||
|
|
e.Name == W.pict ||
|
|
e.Name == W.drawing);
|
|
e.Name == W.drawing);
|
|
|
|
+ }
|
|
|
|
|
|
if (element.Name == W.pict || element.Name == W.drawing)
|
|
if (element.Name == W.pict || element.Name == W.drawing)
|
|
|
|
+ {
|
|
return element
|
|
return element
|
|
.DescendantsTrimmed(W.txbxContent)
|
|
.DescendantsTrimmed(W.txbxContent)
|
|
.Where(e => e.Name == W.txbxContent);
|
|
.Where(e => e.Name == W.txbxContent);
|
|
|
|
+ }
|
|
|
|
|
|
return XElement.EmptySequence;
|
|
return XElement.EmptySequence;
|
|
}
|
|
}
|
|
@@ -235,10 +296,10 @@ namespace OpenXmlPowerTools
|
|
{
|
|
{
|
|
yield return doc.MainDocumentPart;
|
|
yield return doc.MainDocumentPart;
|
|
|
|
|
|
- foreach (var hdr in doc.MainDocumentPart.HeaderParts)
|
|
|
|
|
|
+ foreach (HeaderPart hdr in doc.MainDocumentPart.HeaderParts)
|
|
yield return hdr;
|
|
yield return hdr;
|
|
|
|
|
|
- foreach (var ftr in doc.MainDocumentPart.FooterParts)
|
|
|
|
|
|
+ foreach (FooterPart ftr in doc.MainDocumentPart.FooterParts)
|
|
yield return ftr;
|
|
yield return ftr;
|
|
|
|
|
|
if (doc.MainDocumentPart.FootnotesPart != null)
|
|
if (doc.MainDocumentPart.FootnotesPart != null)
|
|
@@ -249,17 +310,17 @@ namespace OpenXmlPowerTools
|
|
}
|
|
}
|
|
|
|
|
|
/// <summary>
|
|
/// <summary>
|
|
- /// Creates a complete list of all parts contained in the <see cref="OpenXmlPartContainer"/>.
|
|
|
|
|
|
+ /// Creates a complete list of all parts contained in the <see cref="OpenXmlPartContainer" />.
|
|
/// </summary>
|
|
/// </summary>
|
|
/// <param name="container">
|
|
/// <param name="container">
|
|
- /// A <see cref="WordprocessingDocument"/>, <see cref="SpreadsheetDocument"/>, or
|
|
|
|
- /// <see cref="PresentationDocument"/>.
|
|
|
|
|
|
+ /// A <see cref="WordprocessingDocument" />, <see cref="SpreadsheetDocument" />, or
|
|
|
|
+ /// <see cref="PresentationDocument" />.
|
|
/// </param>
|
|
/// </param>
|
|
- /// <returns>list of <see cref="OpenXmlPart"/>s contained in the <see cref="OpenXmlPartContainer"/>.</returns>
|
|
|
|
|
|
+ /// <returns>list of <see cref="OpenXmlPart" />s contained in the <see cref="OpenXmlPartContainer" />.</returns>
|
|
public static List<OpenXmlPart> GetAllParts(this OpenXmlPartContainer container)
|
|
public static List<OpenXmlPart> GetAllParts(this OpenXmlPartContainer container)
|
|
{
|
|
{
|
|
// Use a HashSet so that parts are processed only once.
|
|
// Use a HashSet so that parts are processed only once.
|
|
- HashSet<OpenXmlPart> partList = new HashSet<OpenXmlPart>();
|
|
|
|
|
|
+ var partList = new HashSet<OpenXmlPart>();
|
|
|
|
|
|
foreach (IdPartPair p in container.Parts)
|
|
foreach (IdPartPair p in container.Parts)
|
|
AddPart(partList, p.OpenXmlPart);
|
|
AddPart(partList, p.OpenXmlPart);
|
|
@@ -275,6 +336,42 @@ namespace OpenXmlPowerTools
|
|
foreach (IdPartPair p in part.Parts)
|
|
foreach (IdPartPair p in part.Parts)
|
|
AddPart(partList, p.OpenXmlPart);
|
|
AddPart(partList, p.OpenXmlPart);
|
|
}
|
|
}
|
|
|
|
+
|
|
|
|
+ public static void IgnoreNamespace(this XElement root, string prefix, XNamespace @namespace)
|
|
|
|
+ {
|
|
|
|
+ // Declare markup compatibility extensions namespace as necessary.
|
|
|
|
+ if (root.Attributes().All(a => a.Value != MC.mc.NamespaceName))
|
|
|
|
+ {
|
|
|
|
+ root.Add(new XAttribute(XNamespace.Xmlns + "mc", MC.mc.NamespaceName));
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ // Declare ignored namespace as necessary.
|
|
|
|
+ string namespaceName = @namespace.NamespaceName;
|
|
|
|
+ bool IsIgnoredNamespaceDeclaration(XAttribute a) => a.Name.Namespace == XNamespace.Xmlns && a.Value == namespaceName;
|
|
|
|
+ XAttribute attribute = root.Attributes().FirstOrDefault(IsIgnoredNamespaceDeclaration);
|
|
|
|
+ if (attribute == null)
|
|
|
|
+ {
|
|
|
|
+ attribute = new XAttribute(XNamespace.Xmlns + prefix, namespaceName);
|
|
|
|
+ root.Add(attribute);
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ string effectivePrefix = root.GetPrefixOfNamespace(@namespace);
|
|
|
|
+
|
|
|
|
+ // Add prefix to mc:Ignorable attribute value.
|
|
|
|
+ var ignorable = (string)root.Attribute(MC.Ignorable);
|
|
|
|
+ if (ignorable != null)
|
|
|
|
+ {
|
|
|
|
+ string[] list = ignorable.Split(' ');
|
|
|
|
+ if (!list.Contains(effectivePrefix))
|
|
|
|
+ {
|
|
|
|
+ root.SetAttributeValue(MC.Ignorable, ignorable + " " + effectivePrefix);
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+ else
|
|
|
|
+ {
|
|
|
|
+ root.Add(new XAttribute(MC.Ignorable, effectivePrefix));
|
|
|
|
+ }
|
|
|
|
+ }
|
|
}
|
|
}
|
|
|
|
|
|
public static class FlatOpc
|
|
public static class FlatOpc
|
|
@@ -616,11 +713,10 @@ namespace OpenXmlPowerTools
|
|
{
|
|
{
|
|
public static XAttribute GetXmlSpaceAttribute(string value)
|
|
public static XAttribute GetXmlSpaceAttribute(string value)
|
|
{
|
|
{
|
|
- return (value.Length > 0) && ((value[0] == ' ') || (value[value.Length - 1] == ' '))
|
|
|
|
|
|
+ return value.Length > 0 && (value[0] == ' ' || value[value.Length - 1] == ' ')
|
|
? new XAttribute(XNamespace.Xml + "space", "preserve")
|
|
? new XAttribute(XNamespace.Xml + "space", "preserve")
|
|
: null;
|
|
: null;
|
|
}
|
|
}
|
|
-
|
|
|
|
public static XAttribute GetXmlSpaceAttribute(char value)
|
|
public static XAttribute GetXmlSpaceAttribute(char value)
|
|
{
|
|
{
|
|
return value == ' ' ? new XAttribute(XNamespace.Xml + "space", "preserve") : null;
|
|
return value == ' ' ? new XAttribute(XNamespace.Xml + "space", "preserve") : null;
|
|
@@ -629,16 +725,16 @@ namespace OpenXmlPowerTools
|
|
|
|
|
|
public static class WordprocessingMLUtil
|
|
public static class WordprocessingMLUtil
|
|
{
|
|
{
|
|
- private static HashSet<string> UnknownFonts = new HashSet<string>();
|
|
|
|
- private static HashSet<string> KnownFamilies = null;
|
|
|
|
|
|
+ private static readonly HashSet<string> UnknownFonts = new HashSet<string>();
|
|
|
|
+ private static HashSet<string> KnownFamilies;
|
|
|
|
|
|
public static int CalcWidthOfRunInTwips(XElement r)
|
|
public static int CalcWidthOfRunInTwips(XElement r)
|
|
{
|
|
{
|
|
if (KnownFamilies == null)
|
|
if (KnownFamilies == null)
|
|
{
|
|
{
|
|
KnownFamilies = new HashSet<string>();
|
|
KnownFamilies = new HashSet<string>();
|
|
- var families = FontFamily.Families;
|
|
|
|
- foreach (var fam in families)
|
|
|
|
|
|
+ FontFamily[] families = FontFamily.Families;
|
|
|
|
+ foreach (FontFamily fam in families)
|
|
KnownFamilies.Add(fam.Name);
|
|
KnownFamilies.Add(fam.Name);
|
|
}
|
|
}
|
|
|
|
|
|
@@ -650,7 +746,7 @@ namespace OpenXmlPowerTools
|
|
if (UnknownFonts.Contains(fontName))
|
|
if (UnknownFonts.Contains(fontName))
|
|
return 0;
|
|
return 0;
|
|
|
|
|
|
- var rPr = r.Element(W.rPr);
|
|
|
|
|
|
+ XElement rPr = r.Element(W.rPr);
|
|
if (rPr == null)
|
|
if (rPr == null)
|
|
throw new OpenXmlPowerToolsException("Internal Error, should have run properties");
|
|
throw new OpenXmlPowerToolsException("Internal Error, should have run properties");
|
|
var languageType = (string)r.Attribute(PtOpenXml.LanguageType);
|
|
var languageType = (string)r.Attribute(PtOpenXml.LanguageType);
|
|
@@ -662,7 +758,7 @@ namespace OpenXmlPowerTools
|
|
if (szn == null)
|
|
if (szn == null)
|
|
szn = 22m;
|
|
szn = 22m;
|
|
|
|
|
|
- var sz = szn.GetValueOrDefault();
|
|
|
|
|
|
+ decimal sz = szn.GetValueOrDefault();
|
|
|
|
|
|
// unknown font families will throw ArgumentException, in which case just return 0
|
|
// unknown font families will throw ArgumentException, in which case just return 0
|
|
if (!KnownFamilies.Contains(fontName))
|
|
if (!KnownFamilies.Contains(fontName))
|
|
@@ -679,9 +775,9 @@ namespace OpenXmlPowerTools
|
|
|
|
|
|
return 0;
|
|
return 0;
|
|
}
|
|
}
|
|
- FontStyle fs = FontStyle.Regular;
|
|
|
|
- var bold = GetBoolProp(rPr, W.b) || GetBoolProp(rPr, W.bCs);
|
|
|
|
- var italic = GetBoolProp(rPr, W.i) || GetBoolProp(rPr, W.iCs);
|
|
|
|
|
|
+ var fs = FontStyle.Regular;
|
|
|
|
+ bool bold = GetBoolProp(rPr, W.b) || GetBoolProp(rPr, W.bCs);
|
|
|
|
+ bool italic = GetBoolProp(rPr, W.i) || GetBoolProp(rPr, W.iCs);
|
|
if (bold && !italic)
|
|
if (bold && !italic)
|
|
fs = FontStyle.Bold;
|
|
fs = FontStyle.Bold;
|
|
if (italic && !bold)
|
|
if (italic && !bold)
|
|
@@ -689,12 +785,13 @@ namespace OpenXmlPowerTools
|
|
if (bold && italic)
|
|
if (bold && italic)
|
|
fs = FontStyle.Bold | FontStyle.Italic;
|
|
fs = FontStyle.Bold | FontStyle.Italic;
|
|
|
|
|
|
- var runText = r.DescendantsTrimmed(W.txbxContent)
|
|
|
|
|
|
+
|
|
|
|
+ string runText = r.DescendantsTrimmed(W.txbxContent)
|
|
.Where(e => e.Name == W.t)
|
|
.Where(e => e.Name == W.t)
|
|
.Select(t => (string)t)
|
|
.Select(t => (string)t)
|
|
.StringConcatenate();
|
|
.StringConcatenate();
|
|
|
|
|
|
- var tabLength = r.DescendantsTrimmed(W.txbxContent)
|
|
|
|
|
|
+ decimal tabLength = r.DescendantsTrimmed(W.txbxContent)
|
|
.Where(e => e.Name == W.tab)
|
|
.Where(e => e.Name == W.tab)
|
|
.Select(t => (decimal)t.Attribute(PtOpenXml.TabWidth))
|
|
.Select(t => (decimal)t.Attribute(PtOpenXml.TabWidth))
|
|
.Sum();
|
|
.Sum();
|
|
@@ -702,7 +799,7 @@ namespace OpenXmlPowerTools
|
|
if (runText.Length == 0 && tabLength == 0)
|
|
if (runText.Length == 0 && tabLength == 0)
|
|
return 0;
|
|
return 0;
|
|
|
|
|
|
- int multiplier = 1;
|
|
|
|
|
|
+ var multiplier = 1;
|
|
if (runText.Length <= 2)
|
|
if (runText.Length <= 2)
|
|
multiplier = 100;
|
|
multiplier = 100;
|
|
else if (runText.Length <= 4)
|
|
else if (runText.Length <= 4)
|
|
@@ -715,33 +812,65 @@ namespace OpenXmlPowerTools
|
|
multiplier = 6;
|
|
multiplier = 6;
|
|
if (multiplier != 1)
|
|
if (multiplier != 1)
|
|
{
|
|
{
|
|
- StringBuilder sb = new StringBuilder();
|
|
|
|
- for (int i = 0; i < multiplier; i++)
|
|
|
|
|
|
+ var sb = new StringBuilder();
|
|
|
|
+ for (var i = 0; i < multiplier; i++)
|
|
sb.Append(runText);
|
|
sb.Append(runText);
|
|
runText = sb.ToString();
|
|
runText = sb.ToString();
|
|
}
|
|
}
|
|
|
|
|
|
- var w = MetricsGetter.GetTextWidth(ff, fs, sz, runText);
|
|
|
|
|
|
+ int w = MetricsGetter.GetTextWidth(ff, fs, sz, runText);
|
|
|
|
|
|
return (int) (w / 96m * 1440m / multiplier + tabLength * 1440m);
|
|
return (int) (w / 96m * 1440m / multiplier + tabLength * 1440m);
|
|
}
|
|
}
|
|
|
|
|
|
public static bool GetBoolProp(XElement runProps, XName xName)
|
|
public static bool GetBoolProp(XElement runProps, XName xName)
|
|
{
|
|
{
|
|
- var p = runProps.Element(xName);
|
|
|
|
|
|
+ XElement p = runProps.Element(xName);
|
|
if (p == null)
|
|
if (p == null)
|
|
return false;
|
|
return false;
|
|
- var v = p.Attribute(W.val);
|
|
|
|
|
|
+
|
|
|
|
+ XAttribute v = p.Attribute(W.val);
|
|
if (v == null)
|
|
if (v == null)
|
|
return true;
|
|
return true;
|
|
- var s = v.Value.ToLower();
|
|
|
|
|
|
+
|
|
|
|
+ string s = v.Value.ToLower();
|
|
if (s == "0" || s == "false")
|
|
if (s == "0" || s == "false")
|
|
return false;
|
|
return false;
|
|
if (s == "1" || s == "true")
|
|
if (s == "1" || s == "true")
|
|
return true;
|
|
return true;
|
|
|
|
+
|
|
return false;
|
|
return false;
|
|
}
|
|
}
|
|
|
|
+ public static int StringToTwips(string twipsOrPoints)
|
|
|
|
+ {
|
|
|
|
+ // if the pos value is in points, not twips
|
|
|
|
+ if (twipsOrPoints.EndsWith("pt"))
|
|
|
|
+ {
|
|
|
|
+ decimal decimalValue = decimal.Parse(twipsOrPoints.Substring(0, twipsOrPoints.Length - 2));
|
|
|
|
+ return (int)(decimalValue * 20);
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ return int.Parse(twipsOrPoints);
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ public static int? AttributeToTwips(XAttribute attribute)
|
|
|
|
+ {
|
|
|
|
+ if (attribute == null)
|
|
|
|
+ {
|
|
|
|
+ return null;
|
|
|
|
+ }
|
|
|
|
|
|
|
|
+ var twipsOrPoints = (string)attribute;
|
|
|
|
+
|
|
|
|
+ // if the pos value is in points, not twips
|
|
|
|
+ if (twipsOrPoints.EndsWith("pt"))
|
|
|
|
+ {
|
|
|
|
+ decimal decimalValue = decimal.Parse(twipsOrPoints.Substring(0, twipsOrPoints.Length - 2));
|
|
|
|
+ return (int)(decimalValue * 20);
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ return int.Parse(twipsOrPoints);
|
|
|
|
+ }
|
|
private static readonly List<XName> AdditionalRunContainerNames = new List<XName>
|
|
private static readonly List<XName> AdditionalRunContainerNames = new List<XName>
|
|
{
|
|
{
|
|
W.w + "bdo",
|
|
W.w + "bdo",
|
|
@@ -768,6 +897,9 @@ namespace OpenXmlPowerTools
|
|
if (ce.Elements().Count(e => e.Name != W.rPr) != 1)
|
|
if (ce.Elements().Count(e => e.Name != W.rPr) != 1)
|
|
return dontConsolidate;
|
|
return dontConsolidate;
|
|
|
|
|
|
|
|
+ if (ce.Attribute(PtOpenXml.AbstractNumId) != null)
|
|
|
|
+ return dontConsolidate;
|
|
|
|
+
|
|
XElement rPr = ce.Element(W.rPr);
|
|
XElement rPr = ce.Element(W.rPr);
|
|
string rPrString = rPr != null ? rPr.ToString(SaveOptions.None) : string.Empty;
|
|
string rPrString = rPr != null ? rPr.ToString(SaveOptions.None) : string.Empty;
|
|
|
|
|
|
@@ -818,8 +950,8 @@ namespace OpenXmlPowerTools
|
|
}
|
|
}
|
|
|
|
|
|
// w:ins/w:r/w:t
|
|
// w:ins/w:r/w:t
|
|
- if ((ce.Elements().Elements().Count(e => e.Name != W.rPr) != 1) ||
|
|
|
|
- !ce.Elements().Elements(W.t).Any())
|
|
|
|
|
|
+ if (ce.Elements().Elements().Count(e => e.Name != W.rPr) != 1 ||
|
|
|
|
+ !ce.Elements().Elements(W.t).Any())
|
|
return dontConsolidate;
|
|
return dontConsolidate;
|
|
|
|
|
|
XAttribute dateIns2 = ce.Attribute(W.date);
|
|
XAttribute dateIns2 = ce.Attribute(W.date);
|
|
@@ -829,7 +961,7 @@ namespace OpenXmlPowerTools
|
|
? ((DateTime) dateIns2).ToString("s")
|
|
? ((DateTime) dateIns2).ToString("s")
|
|
: string.Empty;
|
|
: string.Empty;
|
|
|
|
|
|
- string idIns2 = (string)ce.Attribute(W.id);
|
|
|
|
|
|
+ var idIns2 = (string)ce.Attribute(W.id);
|
|
|
|
|
|
return "Wins2" +
|
|
return "Wins2" +
|
|
authorIns2 +
|
|
authorIns2 +
|
|
@@ -843,7 +975,7 @@ namespace OpenXmlPowerTools
|
|
|
|
|
|
if (ce.Name == W.del)
|
|
if (ce.Name == W.del)
|
|
{
|
|
{
|
|
- if ((ce.Elements(W.r).Elements().Count(e => e.Name != W.rPr) != 1) ||
|
|
|
|
|
|
+ if (ce.Elements(W.r).Elements().Count(e => e.Name != W.rPr) != 1 ||
|
|
!ce.Elements().Elements(W.delText).Any())
|
|
!ce.Elements().Elements(W.delText).Any())
|
|
return dontConsolidate;
|
|
return dontConsolidate;
|
|
|
|
|
|
@@ -869,12 +1001,12 @@ namespace OpenXmlPowerTools
|
|
groupedAdjacentRunsWithIdenticalFormatting.Select(g =>
|
|
groupedAdjacentRunsWithIdenticalFormatting.Select(g =>
|
|
{
|
|
{
|
|
if (g.Key == dontConsolidate)
|
|
if (g.Key == dontConsolidate)
|
|
- return (object) g;
|
|
|
|
|
|
+ return (object)g;
|
|
|
|
|
|
string textValue = g
|
|
string textValue = g
|
|
.Select(r =>
|
|
.Select(r =>
|
|
r.Descendants()
|
|
r.Descendants()
|
|
- .Where(d => (d.Name == W.t) || (d.Name == W.delText) || (d.Name == W.instrText))
|
|
|
|
|
|
+ .Where(d => d.Name == W.t || d.Name == W.delText || d.Name == W.instrText)
|
|
.Select(d => d.Value)
|
|
.Select(d => d.Value)
|
|
.StringConcatenate())
|
|
.StringConcatenate())
|
|
.StringConcatenate();
|
|
.StringConcatenate();
|
|
@@ -887,52 +1019,50 @@ namespace OpenXmlPowerTools
|
|
IEnumerable<IEnumerable<XAttribute>> statusAtt =
|
|
IEnumerable<IEnumerable<XAttribute>> statusAtt =
|
|
g.Select(r => r.Descendants(W.t).Take(1).Attributes(PtOpenXml.Status));
|
|
g.Select(r => r.Descendants(W.t).Take(1).Attributes(PtOpenXml.Status));
|
|
return new XElement(W.r,
|
|
return new XElement(W.r,
|
|
|
|
+ g.First().Attributes(),
|
|
g.First().Elements(W.rPr),
|
|
g.First().Elements(W.rPr),
|
|
new XElement(W.t, statusAtt, xs, textValue));
|
|
new XElement(W.t, statusAtt, xs, textValue));
|
|
}
|
|
}
|
|
|
|
|
|
if (g.First().Element(W.instrText) != null)
|
|
if (g.First().Element(W.instrText) != null)
|
|
return new XElement(W.r,
|
|
return new XElement(W.r,
|
|
|
|
+ g.First().Attributes(),
|
|
g.First().Elements(W.rPr),
|
|
g.First().Elements(W.rPr),
|
|
new XElement(W.instrText, xs, textValue));
|
|
new XElement(W.instrText, xs, textValue));
|
|
}
|
|
}
|
|
|
|
|
|
if (g.First().Name == W.ins)
|
|
if (g.First().Name == W.ins)
|
|
{
|
|
{
|
|
-#if false
|
|
|
|
- if (g.First().Elements(W.del).Any())
|
|
|
|
- return new XElement(W.ins,
|
|
|
|
- g.First().Attributes(),
|
|
|
|
- new XElement(W.del,
|
|
|
|
- g.First().Elements(W.del).Attributes(),
|
|
|
|
- new XElement(W.r,
|
|
|
|
- g.First().Elements(W.del).Elements(W.r).Elements(W.rPr),
|
|
|
|
- new XElement(W.delText, xs, textValue))));
|
|
|
|
-#endif
|
|
|
|
|
|
+ XElement firstR = g.First().Element(W.r);
|
|
return new XElement(W.ins,
|
|
return new XElement(W.ins,
|
|
g.First().Attributes(),
|
|
g.First().Attributes(),
|
|
new XElement(W.r,
|
|
new XElement(W.r,
|
|
|
|
+ firstR?.Attributes(),
|
|
g.First().Elements(W.r).Elements(W.rPr),
|
|
g.First().Elements(W.r).Elements(W.rPr),
|
|
new XElement(W.t, xs, textValue)));
|
|
new XElement(W.t, xs, textValue)));
|
|
}
|
|
}
|
|
|
|
|
|
if (g.First().Name == W.del)
|
|
if (g.First().Name == W.del)
|
|
|
|
+ {
|
|
|
|
+ XElement firstR = g.First().Element(W.r);
|
|
return new XElement(W.del,
|
|
return new XElement(W.del,
|
|
g.First().Attributes(),
|
|
g.First().Attributes(),
|
|
new XElement(W.r,
|
|
new XElement(W.r,
|
|
|
|
+ firstR?.Attributes(),
|
|
g.First().Elements(W.r).Elements(W.rPr),
|
|
g.First().Elements(W.r).Elements(W.rPr),
|
|
new XElement(W.delText, xs, textValue)));
|
|
new XElement(W.delText, xs, textValue)));
|
|
|
|
+ }
|
|
|
|
|
|
return g;
|
|
return g;
|
|
}));
|
|
}));
|
|
|
|
|
|
// Process w:txbxContent//w:p
|
|
// Process w:txbxContent//w:p
|
|
foreach (XElement txbx in runContainerWithConsolidatedRuns.Descendants(W.txbxContent))
|
|
foreach (XElement txbx in runContainerWithConsolidatedRuns.Descendants(W.txbxContent))
|
|
- foreach (XElement txbxPara in txbx.DescendantsTrimmed(W.txbxContent).Where(d => d.Name == W.p))
|
|
|
|
- {
|
|
|
|
- XElement newPara = CoalesceAdjacentRunsWithIdenticalFormatting(txbxPara);
|
|
|
|
- txbxPara.ReplaceWith(newPara);
|
|
|
|
- }
|
|
|
|
|
|
+ foreach (XElement txbxPara in txbx.DescendantsTrimmed(W.txbxContent).Where(d => d.Name == W.p))
|
|
|
|
+ {
|
|
|
|
+ XElement newPara = CoalesceAdjacentRunsWithIdenticalFormatting(txbxPara);
|
|
|
|
+ txbxPara.ReplaceWith(newPara);
|
|
|
|
+ }
|
|
|
|
|
|
// Process additional run containers.
|
|
// Process additional run containers.
|
|
List<XElement> runContainers = runContainerWithConsolidatedRuns
|
|
List<XElement> runContainers = runContainerWithConsolidatedRuns
|
|
@@ -948,7 +1078,7 @@ namespace OpenXmlPowerTools
|
|
return runContainerWithConsolidatedRuns;
|
|
return runContainerWithConsolidatedRuns;
|
|
}
|
|
}
|
|
|
|
|
|
- private static Dictionary<XName, int> Order_settings = new Dictionary<XName, int>
|
|
|
|
|
|
+ private static readonly Dictionary<XName, int> Order_settings = new Dictionary<XName, int>
|
|
{
|
|
{
|
|
{ W.writeProtection, 10},
|
|
{ W.writeProtection, 10},
|
|
{ W.view, 20},
|
|
{ W.view, 20},
|
|
@@ -1045,7 +1175,7 @@ namespace OpenXmlPowerTools
|
|
//{W.sl:schemaLibrary, 930},
|
|
//{W.sl:schemaLibrary, 930},
|
|
{ W.doNotEmbedSmartTags, 940},
|
|
{ W.doNotEmbedSmartTags, 940},
|
|
{ W.decimalSymbol, 950},
|
|
{ W.decimalSymbol, 950},
|
|
- { W.listSeparator, 960},
|
|
|
|
|
|
+ { W.listSeparator, 960},
|
|
};
|
|
};
|
|
|
|
|
|
#if false
|
|
#if false
|
|
@@ -1149,7 +1279,7 @@ decimalSymbol
|
|
listSeparator
|
|
listSeparator
|
|
#endif
|
|
#endif
|
|
|
|
|
|
- private static Dictionary<XName, int> Order_pPr = new Dictionary<XName, int>
|
|
|
|
|
|
+ private static readonly Dictionary<XName, int> Order_pPr = new Dictionary<XName, int>
|
|
{
|
|
{
|
|
{ W.pStyle, 10 },
|
|
{ W.pStyle, 10 },
|
|
{ W.keepNext, 20 },
|
|
{ W.keepNext, 20 },
|
|
@@ -1186,11 +1316,13 @@ listSeparator
|
|
{ W.cnfStyle, 340 },
|
|
{ W.cnfStyle, 340 },
|
|
{ W.rPr, 350 },
|
|
{ W.rPr, 350 },
|
|
{ W.sectPr, 360 },
|
|
{ W.sectPr, 360 },
|
|
- { W.pPrChange, 370 },
|
|
|
|
|
|
+ { W.pPrChange, 370 }
|
|
};
|
|
};
|
|
|
|
|
|
- private static Dictionary<XName, int> Order_rPr = new Dictionary<XName, int>
|
|
|
|
- {
|
|
|
|
|
|
+ private static readonly Dictionary<XName, int> Order_rPr = new Dictionary<XName, int>
|
|
|
|
+ {
|
|
|
|
+ { W.moveFrom, 5 },
|
|
|
|
+ { W.moveTo, 7 },
|
|
{ W.ins, 10 },
|
|
{ W.ins, 10 },
|
|
{ W.del, 20 },
|
|
{ W.del, 20 },
|
|
{ W.rStyle, 30 },
|
|
{ W.rStyle, 30 },
|
|
@@ -1236,10 +1368,10 @@ listSeparator
|
|
{ W.lang, 430 },
|
|
{ W.lang, 430 },
|
|
{ W.eastAsianLayout, 440 },
|
|
{ W.eastAsianLayout, 440 },
|
|
{ W.specVanish, 450 },
|
|
{ W.specVanish, 450 },
|
|
- { W.oMath, 460 },
|
|
|
|
|
|
+ { W.oMath, 460 }
|
|
};
|
|
};
|
|
|
|
|
|
- private static Dictionary<XName, int> Order_tblPr = new Dictionary<XName, int>
|
|
|
|
|
|
+ private static readonly Dictionary<XName, int> Order_tblPr = new Dictionary<XName, int>
|
|
{
|
|
{
|
|
{ W.tblStyle, 10 },
|
|
{ W.tblStyle, 10 },
|
|
{ W.tblpPr, 20 },
|
|
{ W.tblpPr, 20 },
|
|
@@ -1257,10 +1389,10 @@ listSeparator
|
|
{ W.tblCellMar, 140 },
|
|
{ W.tblCellMar, 140 },
|
|
{ W.tblLook, 150 },
|
|
{ W.tblLook, 150 },
|
|
{ W.tblCaption, 160 },
|
|
{ W.tblCaption, 160 },
|
|
- { W.tblDescription, 170 },
|
|
|
|
|
|
+ { W.tblDescription, 170 }
|
|
};
|
|
};
|
|
|
|
|
|
- private static Dictionary<XName, int> Order_tblBorders = new Dictionary<XName, int>
|
|
|
|
|
|
+ private static readonly Dictionary<XName, int> Order_tblBorders = new Dictionary<XName, int>
|
|
{
|
|
{
|
|
{ W.top, 10 },
|
|
{ W.top, 10 },
|
|
{ W.left, 20 },
|
|
{ W.left, 20 },
|
|
@@ -1272,7 +1404,7 @@ listSeparator
|
|
{ W.insideV, 80 },
|
|
{ W.insideV, 80 },
|
|
};
|
|
};
|
|
|
|
|
|
- private static Dictionary<XName, int> Order_tcPr = new Dictionary<XName, int>
|
|
|
|
|
|
+ private static readonly Dictionary<XName, int> Order_tcPr = new Dictionary<XName, int>
|
|
{
|
|
{
|
|
{ W.cnfStyle, 10 },
|
|
{ W.cnfStyle, 10 },
|
|
{ W.tcW, 20 },
|
|
{ W.tcW, 20 },
|
|
@@ -1287,10 +1419,10 @@ listSeparator
|
|
{ W.tcFitText, 110 },
|
|
{ W.tcFitText, 110 },
|
|
{ W.vAlign, 120 },
|
|
{ W.vAlign, 120 },
|
|
{ W.hideMark, 130 },
|
|
{ W.hideMark, 130 },
|
|
- { W.headers, 140 },
|
|
|
|
|
|
+ { W.headers, 140 }
|
|
};
|
|
};
|
|
|
|
|
|
- private static Dictionary<XName, int> Order_tcBorders = new Dictionary<XName, int>
|
|
|
|
|
|
+ private static readonly Dictionary<XName, int> Order_tcBorders = new Dictionary<XName, int>
|
|
{
|
|
{
|
|
{ W.top, 10 },
|
|
{ W.top, 10 },
|
|
{ W.start, 20 },
|
|
{ W.start, 20 },
|
|
@@ -1301,10 +1433,10 @@ listSeparator
|
|
{ W.insideH, 70 },
|
|
{ W.insideH, 70 },
|
|
{ W.insideV, 80 },
|
|
{ W.insideV, 80 },
|
|
{ W.tl2br, 90 },
|
|
{ W.tl2br, 90 },
|
|
- { W.tr2bl, 100 },
|
|
|
|
|
|
+ { W.tr2bl, 100 }
|
|
};
|
|
};
|
|
|
|
|
|
- private static Dictionary<XName, int> Order_pBdr = new Dictionary<XName, int>
|
|
|
|
|
|
+ private static readonly Dictionary<XName, int> Order_pBdr = new Dictionary<XName, int>
|
|
{
|
|
{
|
|
{ W.top, 10 },
|
|
{ W.top, 10 },
|
|
{ W.left, 20 },
|
|
{ W.left, 20 },
|
|
@@ -1316,7 +1448,7 @@ listSeparator
|
|
|
|
|
|
public static object WmlOrderElementsPerStandard(XNode node)
|
|
public static object WmlOrderElementsPerStandard(XNode node)
|
|
{
|
|
{
|
|
- XElement element = node as XElement;
|
|
|
|
|
|
+ var element = node as XElement;
|
|
if (element != null)
|
|
if (element != null)
|
|
{
|
|
{
|
|
if (element.Name == W.pPr)
|
|
if (element.Name == W.pPr)
|
|
@@ -1326,6 +1458,7 @@ listSeparator
|
|
{
|
|
{
|
|
if (Order_pPr.ContainsKey(e.Name))
|
|
if (Order_pPr.ContainsKey(e.Name))
|
|
return Order_pPr[e.Name];
|
|
return Order_pPr[e.Name];
|
|
|
|
+
|
|
return 999;
|
|
return 999;
|
|
}));
|
|
}));
|
|
|
|
|
|
@@ -1336,6 +1469,7 @@ listSeparator
|
|
{
|
|
{
|
|
if (Order_rPr.ContainsKey(e.Name))
|
|
if (Order_rPr.ContainsKey(e.Name))
|
|
return Order_rPr[e.Name];
|
|
return Order_rPr[e.Name];
|
|
|
|
+
|
|
return 999;
|
|
return 999;
|
|
}));
|
|
}));
|
|
|
|
|
|
@@ -1346,6 +1480,7 @@ listSeparator
|
|
{
|
|
{
|
|
if (Order_tblPr.ContainsKey(e.Name))
|
|
if (Order_tblPr.ContainsKey(e.Name))
|
|
return Order_tblPr[e.Name];
|
|
return Order_tblPr[e.Name];
|
|
|
|
+
|
|
return 999;
|
|
return 999;
|
|
}));
|
|
}));
|
|
|
|
|
|
@@ -1356,6 +1491,7 @@ listSeparator
|
|
{
|
|
{
|
|
if (Order_tcPr.ContainsKey(e.Name))
|
|
if (Order_tcPr.ContainsKey(e.Name))
|
|
return Order_tcPr[e.Name];
|
|
return Order_tcPr[e.Name];
|
|
|
|
+
|
|
return 999;
|
|
return 999;
|
|
}));
|
|
}));
|
|
|
|
|
|
@@ -1366,6 +1502,7 @@ listSeparator
|
|
{
|
|
{
|
|
if (Order_tcBorders.ContainsKey(e.Name))
|
|
if (Order_tcBorders.ContainsKey(e.Name))
|
|
return Order_tcBorders[e.Name];
|
|
return Order_tcBorders[e.Name];
|
|
|
|
+
|
|
return 999;
|
|
return 999;
|
|
}));
|
|
}));
|
|
|
|
|
|
@@ -1376,6 +1513,7 @@ listSeparator
|
|
{
|
|
{
|
|
if (Order_tblBorders.ContainsKey(e.Name))
|
|
if (Order_tblBorders.ContainsKey(e.Name))
|
|
return Order_tblBorders[e.Name];
|
|
return Order_tblBorders[e.Name];
|
|
|
|
+
|
|
return 999;
|
|
return 999;
|
|
}));
|
|
}));
|
|
|
|
|
|
@@ -1411,6 +1549,7 @@ listSeparator
|
|
{
|
|
{
|
|
if (Order_settings.ContainsKey(e.Name))
|
|
if (Order_settings.ContainsKey(e.Name))
|
|
return Order_settings[e.Name];
|
|
return Order_settings[e.Name];
|
|
|
|
+
|
|
return 999;
|
|
return 999;
|
|
}));
|
|
}));
|
|
|
|
|
|
@@ -1418,21 +1557,22 @@ listSeparator
|
|
element.Attributes(),
|
|
element.Attributes(),
|
|
element.Nodes().Select(n => WmlOrderElementsPerStandard(n)));
|
|
element.Nodes().Select(n => WmlOrderElementsPerStandard(n)));
|
|
}
|
|
}
|
|
|
|
+
|
|
return node;
|
|
return node;
|
|
}
|
|
}
|
|
|
|
|
|
public static WmlDocument BreakLinkToTemplate(WmlDocument source)
|
|
public static WmlDocument BreakLinkToTemplate(WmlDocument source)
|
|
{
|
|
{
|
|
- using (MemoryStream ms = new MemoryStream())
|
|
|
|
|
|
+ using (var ms = new MemoryStream())
|
|
{
|
|
{
|
|
ms.Write(source.DocumentByteArray, 0, source.DocumentByteArray.Length);
|
|
ms.Write(source.DocumentByteArray, 0, source.DocumentByteArray.Length);
|
|
using (WordprocessingDocument wDoc = WordprocessingDocument.Open(ms, true))
|
|
using (WordprocessingDocument wDoc = WordprocessingDocument.Open(ms, true))
|
|
{
|
|
{
|
|
- var efpp = wDoc.ExtendedFilePropertiesPart;
|
|
|
|
|
|
+ ExtendedFilePropertiesPart efpp = wDoc.ExtendedFilePropertiesPart;
|
|
if (efpp != null)
|
|
if (efpp != null)
|
|
{
|
|
{
|
|
- var xd = efpp.GetXDocument();
|
|
|
|
- var template = xd.Descendants(EP.Template).FirstOrDefault();
|
|
|
|
|
|
+ XDocument xd = efpp.GetXDocument();
|
|
|
|
+ XElement template = xd.Descendants(EP.Template).FirstOrDefault();
|
|
if (template != null)
|
|
if (template != null)
|
|
template.Value = "";
|
|
template.Value = "";
|
|
efpp.PutXDocument();
|
|
efpp.PutXDocument();
|
|
@@ -4192,7 +4332,11 @@ listSeparator
|
|
public static readonly XNamespace plegacy = "urn:schemas-microsoft-com:office:powerpoint";
|
|
public static readonly XNamespace plegacy = "urn:schemas-microsoft-com:office:powerpoint";
|
|
public static readonly XName textdata = plegacy + "textdata";
|
|
public static readonly XName textdata = plegacy + "textdata";
|
|
}
|
|
}
|
|
-
|
|
|
|
|
|
+ public static class SVG
|
|
|
|
+ {
|
|
|
|
+ public static readonly XNamespace svg = "http://schemas.microsoft.com/office/drawing/2016/SVG/main";
|
|
|
|
+ public static readonly XName svgBlip = svg + "svgBlip";
|
|
|
|
+ }
|
|
public static class R
|
|
public static class R
|
|
{
|
|
{
|
|
public static readonly XNamespace r =
|
|
public static readonly XNamespace r =
|
|
@@ -5797,6 +5941,9 @@ listSeparator
|
|
{
|
|
{
|
|
public static readonly XNamespace xsi =
|
|
public static readonly XNamespace xsi =
|
|
"http://www.w3.org/2001/XMLSchema-instance";
|
|
"http://www.w3.org/2001/XMLSchema-instance";
|
|
|
|
+
|
|
|
|
+ public static readonly XName schemaLocation = xsi + "schemaLocation";
|
|
|
|
+ public static readonly XName noNamespaceSchemaLocation = xsi + "noNamespaceSchemaLocation";
|
|
public static readonly XName type = xsi + "type";
|
|
public static readonly XName type = xsi + "type";
|
|
}
|
|
}
|
|
|
|
|
|
@@ -5805,40 +5952,44 @@ listSeparator
|
|
|
|
|
|
public static class PtOpenXml
|
|
public static class PtOpenXml
|
|
{
|
|
{
|
|
- public static XNamespace ptOpenXml = "http://powertools.codeplex.com/documentbuilder/2011/insert";
|
|
|
|
- public static XName Insert = ptOpenXml + "Insert";
|
|
|
|
- public static XName Id = "Id";
|
|
|
|
-
|
|
|
|
- public static XNamespace pt = "http://powertools.codeplex.com/2011";
|
|
|
|
- public static XName Uri = pt + "Uri";
|
|
|
|
- public static XName Unid = pt + "Unid";
|
|
|
|
- public static XName SHA1Hash = pt + "SHA1Hash";
|
|
|
|
- public static XName CorrelatedSHA1Hash = pt + "CorrelatedSHA1Hash";
|
|
|
|
- public static XName StructureSHA1Hash = pt + "StructureSHA1Hash";
|
|
|
|
- public static XName CorrelationSet = pt + "CorrelationSet";
|
|
|
|
- public static XName Status = pt + "Status";
|
|
|
|
-
|
|
|
|
- public static XName Level = pt + "Level";
|
|
|
|
- public static XName IndentLevel = pt + "IndentLevel";
|
|
|
|
- public static XName ContentType = pt + "ContentType";
|
|
|
|
-
|
|
|
|
- public static XName trPr = pt + "trPr";
|
|
|
|
- public static XName tcPr = pt + "tcPr";
|
|
|
|
- public static XName rPr = pt + "rPr";
|
|
|
|
- public static XName pPr = pt + "pPr";
|
|
|
|
- public static XName tblPr = pt + "tblPr";
|
|
|
|
- public static XName style = pt + "style";
|
|
|
|
-
|
|
|
|
- public static XName FontName = pt + "FontName";
|
|
|
|
- public static XName LanguageType = pt + "LanguageType";
|
|
|
|
- public static XName AbstractNumId = pt + "AbstractNumId";
|
|
|
|
- public static XName StyleName = pt + "StyleName";
|
|
|
|
- public static XName TabWidth = pt + "TabWidth";
|
|
|
|
- public static XName Leader = pt + "Leader";
|
|
|
|
-
|
|
|
|
- public static XName ListItemRun = pt + "ListItemRun";
|
|
|
|
-
|
|
|
|
- public static XName HtmlToWmlCssWidth = pt + "HtmlToWmlCssWidth";
|
|
|
|
|
|
+ public static readonly XNamespace ptOpenXml = "http://powertools.codeplex.com/documentbuilder/2011/insert";
|
|
|
|
+ public static readonly XName Insert = ptOpenXml + "Insert";
|
|
|
|
+ public static readonly XName Id = "Id";
|
|
|
|
+
|
|
|
|
+ public static readonly XNamespace pt = "http://powertools.codeplex.com/2011";
|
|
|
|
+ public static readonly XName Uri = pt + "Uri";
|
|
|
|
+ public static readonly XName Unid = pt + "Unid";
|
|
|
|
+ public static readonly XName SHA1Hash = pt + "SHA1Hash";
|
|
|
|
+ public static readonly XName CorrelatedSHA1Hash = pt + "CorrelatedSHA1Hash";
|
|
|
|
+ public static readonly XName StructureSHA1Hash = pt + "StructureSHA1Hash";
|
|
|
|
+ public static readonly XName CorrelationSet = pt + "CorrelationSet";
|
|
|
|
+ public static readonly XName Status = pt + "Status";
|
|
|
|
+
|
|
|
|
+ public static readonly XName Level = pt + "Level";
|
|
|
|
+ public static readonly XName IndentLevel = pt + "IndentLevel";
|
|
|
|
+ public static readonly XName ContentType = pt + "ContentType";
|
|
|
|
+
|
|
|
|
+ public static readonly XName trPr = pt + "trPr";
|
|
|
|
+ public static readonly XName tcPr = pt + "tcPr";
|
|
|
|
+ public static readonly XName rPr = pt + "rPr";
|
|
|
|
+ public static readonly XName pPr = pt + "pPr";
|
|
|
|
+ public static readonly XName tblPr = pt + "tblPr";
|
|
|
|
+ public static readonly XName style = pt + "style";
|
|
|
|
+
|
|
|
|
+ public static readonly XName instrText = pt + W.instrText.LocalName;
|
|
|
|
+
|
|
|
|
+ public static readonly XName FontName = pt + "FontName";
|
|
|
|
+ public static readonly XName LanguageType = pt + "LanguageType";
|
|
|
|
+ public static readonly XName AbstractNumId = pt + "AbstractNumId";
|
|
|
|
+ public static readonly XName HtmlStructure = pt + "HtmlStructure";
|
|
|
|
+ public static readonly XName HtmlStyle = pt + "HtmlStyle";
|
|
|
|
+ public static readonly XName StyleName = pt + "StyleName";
|
|
|
|
+ public static readonly XName TabWidth = pt + "TabWidth";
|
|
|
|
+ public static readonly XName Leader = pt + "Leader";
|
|
|
|
+
|
|
|
|
+ public static readonly XName ListItemRun = pt + "ListItemRun";
|
|
|
|
+
|
|
|
|
+ public static readonly XName HtmlToWmlCssWidth = pt + "HtmlToWmlCssWidth";
|
|
}
|
|
}
|
|
|
|
|
|
public static class Xhtml
|
|
public static class Xhtml
|