Changing Bullet Styles with Word 2007 Automation in C# - c#

I am trying to change the style of my bullets in a word document (Word 2007).... I currently place a bullet and it comes out as a circle. I want it to be a square... here's my code for applying bullets...
public void ToggleBullets(bool bulletsOn)
{
Microsoft.Office.Interop.Word.Application wd;
Object _oMissing = Type.Missing;
Object _numberType = WdNumberType.wdNumberListNum;
if (bulletsOn)
{
wd.Selection.Range.ListFormat.ApplyBulletDefault(ref _oMissing);
}
else
{
wd.Selection.Range.ListFormat.RemoveNumbers(ref _numberType);
}
}
any ideas? Let me know if you need more details

I use the Open XML SDK 2.0 Productivity Tool for Microsoft Office:
http://www.microsoft.com/downloads/en/details.aspx?FamilyID=c6e744e5-36e9-45f5-8d8c-331df206e0d0&displaylang=en
When I want to to do these kinds of things. Just launch the Productivity tool, load up the .docx that has what you want and then let the tool generate the code for you.
I just whipped up an example and this was the code it generated:
using DocumentFormat.OpenXml.Wordprocessing;
using DocumentFormat.OpenXml;
....
public Paragraph GenerateParagraph()
{
Paragraph paragraph1 = new Paragraph(){ RsidParagraphAddition = "00EA7FFB", RsidParagraphProperties = "00EA7FFB", RsidRunAdditionDefault = "00EA7FFB" };
ParagraphProperties paragraphProperties1 = new ParagraphProperties();
ParagraphStyleId paragraphStyleId1 = new ParagraphStyleId(){ Val = "ListParagraph" };
NumberingProperties numberingProperties1 = new NumberingProperties();
NumberingLevelReference numberingLevelReference1 = new NumberingLevelReference(){ Val = 0 };
NumberingId numberingId1 = new NumberingId(){ Val = 2 };
numberingProperties1.Append(numberingLevelReference1);
numberingProperties1.Append(numberingId1);
paragraphProperties1.Append(paragraphStyleId1);
paragraphProperties1.Append(numberingProperties1);
Run run1 = new Run();
Text text1 = new Text(){ Space = SpaceProcessingModeValues.Preserve };
text1.Text = "Item ";
run1.Append(text1);
paragraph1.Append(paragraphProperties1);
paragraph1.Append(run1);
return paragraph1;
}
This is using the OpenXml headers, and not Word specifically

Related

How to apply margin in Presentation Document using OpenXml

I wrote code to create Presentation Document using open-xml SDK. I follow this sample code. MSDD Sample Code. Now i need to apply margin before starting my text. I've tried below code but didn't get expected result.
slidePart1.Slide = new Slide(
new CommonSlideData(
new ShapeTree(
new P.NonVisualGroupShapeProperties(
new P.NonVisualDrawingProperties() { Id = (UInt32Value)1U, Name = "" },
new P.NonVisualGroupShapeDrawingProperties(),
new ApplicationNonVisualDrawingProperties()),
new GroupShapeProperties(new A.TransformGroup()),
new P.Shape(
new P.NonVisualShapeProperties(
new P.NonVisualDrawingProperties() { Id = (UInt32Value)2U, Name = "Title 1" },
new P.NonVisualShapeDrawingProperties(new D.ShapeLocks() { NoGrouping = true }),
new ApplicationNonVisualDrawingProperties(new PlaceholderShape())),
new P.ShapeProperties(),
new P.TextBody(
new D.BodyProperties(),
new D.ListStyle(),
new A.Paragraph(new D.EndParagraphRunProperties() { Language = "en-US" }, new D.ParagraphProperties() { LeftMargin = 10 }),
//new A.Paragraph(new A.Run(new A.RunProperties() { Bold = true, Italic = true, Underline = D.TextUnderlineValues.Single }, new A.Text()
//{ Text = text })))))),
new A.Paragraph(textListWithStyle.ToArray()))))),
new ColorMapOverride(new D.MasterColorMapping()));
My generated PPT File looks like:
No left margin applied but in code i applied 10 left margin.
It seems not so easy to add an indented paragraph using Open XML SDK. With Aspose.Slides for .NET, this can be done like this:
// Create a new presentation.
using var presentation = new Presentation();
// Add a text box to the first slide.
var slide = presentation.Slides[0];
var rectangle = slide.Shapes.AddAutoShape(ShapeType.Rectangle, 20, 20, 200, 150);
// Create a new paragraph.
var paragraph = new Paragraph();
paragraph.Text = "Some text.";
// Set left margin for the paragraph.
paragraph.ParagraphFormat.MarginLeft = 10;
// Add the paragraph to the text box.
rectangle.TextFrame.Paragraphs.Add(paragraph);
// Save the presentation to PPTX format.
presentation.Save("example.pptx", SaveFormat.Pptx);
This is a paid product, but you can get a temporary license to evaluate all features of this library. I work as a Support Developer at Aspose.

How to dynamically add a page number in footer in Microsoft OXML c#

I'm creating a word document using OXML in Visual Studio. I don't know how long it is going to be and I need to add a simple page number in the footer of the document.
To generate headers and footers I used this:
https://msdn.microsoft.com/en-us/library/ee355228(v=office.12).aspx
As I understand, this presets the default headers/footers before I even write anything in the document. So I'm not quite sure if I can add page numbering to this? I'd really appreciate the help, because I've been stuck on this for a whole day...
You can add dynamic page numbers by adding a SimpleField with an Instruction of "PAGE". Word will automatically update any such field with the correct page number.
In order to code that you can adapt the GeneratePageFooterPart in the link you provided to include a SimpleField in the Run that gets added to the Footer:
private static Footer GeneratePageFooterPart(string FooterText)
{
var element =
new Footer(
new Paragraph(
new ParagraphProperties(
new ParagraphStyleId() { Val = "Footer" }),
new Run(
new Text(FooterText),
// *** Adaptation: This will output the page number dynamically ***
new SimpleField() { Instruction = "PAGE" })
));
return element;
}
Note that you can change the format of the page number by postfixing the PAGE text. From the Ecma Office Open XML Part 1 - Fundamentals And Markup Language Reference.pdf:
When the current page number is 19 and the following fields are updated:
PAGE
PAGE \* ArabicDash
PAGE \* ALPHABETIC
PAGE \* roman
the results are:
19
- 19 -
S
xix
So to get roman numerals for example you would need to change the SimpleField line of code above to:
new SimpleField() { Instruction = "PAGE \\* roman" })
or (if you prefer)
new SimpleField() { Instruction = #"PAGE \* roman" })
Try this:
private static void GenerateFooterPartContent(WordprocessingDocument package, string text = null)
{
FooterPart footerPart1 = package.MainDocumentPart.FooterParts.FirstOrDefault();
if (footerPart1 == null)
{
footerPart1 = package.MainDocumentPart.AddNewPart<FooterPart>();
}
var relationshipId = package.MainDocumentPart.GetIdOfPart(footerPart1);
// Get SectionProperties and set HeaderReference and FooterRefernce with new Id
SectionProperties sectionProperties1 = new SectionProperties();
FooterReference footerReference2 = new FooterReference() { Type = HeaderFooterValues.Default, Id = relationshipId };
sectionProperties1.Append(footerReference2);
package.MainDocumentPart.Document.Body.Append(sectionProperties1);
Footer footer1 = new Footer();
Paragraph paragraph2 = CreateParagraph(package, string.Empty, "Footer");
Run r = new Run(new SimpleField() { Instruction = "DATE" });
paragraph2.Append(r);
if (!string.IsNullOrWhiteSpace(text))
{
r = new Run();
PositionalTab positionalTab1 = new PositionalTab() { Alignment = AbsolutePositionTabAlignmentValues.Center,
RelativeTo = AbsolutePositionTabPositioningBaseValues.Margin,
Leader = AbsolutePositionTabLeaderCharValues.None };
r.Append(positionalTab1);
paragraph2.Append(r);
r = new Run(new Text(text) { Space = SpaceProcessingModeValues.Preserve });
paragraph2.Append(r);
}
r = new Run();
PositionalTab positionalTab2 = new PositionalTab() { Alignment = AbsolutePositionTabAlignmentValues.Right,
RelativeTo = AbsolutePositionTabPositioningBaseValues.Margin,
Leader = AbsolutePositionTabLeaderCharValues.None };
r.Append(positionalTab2);
paragraph2.Append(r);
r = new Run(new Text("Page: ") { Space = SpaceProcessingModeValues.Preserve },
// *** Adaptation: This will output the page number dynamically ***
new SimpleField() { Instruction = "PAGE" },
new Text(" of ") { Space = SpaceProcessingModeValues.Preserve },
// *** Adaptation: This will output the number of pages dynamically ***
new SimpleField() { Instruction = "NUMPAGES" });
paragraph2.Append(r);
footer1.Append(paragraph2);
footerPart1.Footer = footer1;
}
Refer to the following link for more instructions.

Apply style on Content Control in a Word Document using OpenXML

I'm trying to generate Word documents using OpenXML SDK and Word Document Generator. I need to apply my custom style on ContentControls (Repeating Section).
For Recursive Placeholders, I use
foreach (var item in list)
{
var datacontext = new OpenXmlElementDataContext()
{
Element = openXmlElementDataContext.Element,
DataContext = item.Value
};
var clonedElement = CloneElementAndSetContentInPlaceholders(datacontext);
SetContentOfContentControl(clonedElement, item.Value);
}
openXmlElementDataContext.Element.Remove();
I need to apply my style on this element. How to I can do ?
I try to see generated code with "Open XML SDK 2.5 Productivity Tool for Microsoft Office" to inspire me:
var moduleDatacontext = new OpenXmlElementDataContext()
{
Element = openXmlElementDataContext.Element,
DataContext = module.Valeur
};
var moduleClonedElement = CloneElementAndSetContentInPlaceholders(moduleDatacontext);
var sdtProperties1 = new SdtProperties();
var styleId1 = new StyleId() { Val = "FormationTitre2" };
ParagraphMarkRunProperties paragraphMarkRunProperties1 = new ParagraphMarkRunProperties();
RunFonts runFonts1 = new RunFonts() { ComplexScriptTheme = ThemeFontValues.MinorHighAnsi };
paragraphMarkRunProperties1.Append(runFonts1);
sdtProperties1.Append(styleId1);
sdtProperties1.Append(paragraphMarkRunProperties1);
Run run1 = new Run() { RsidRunProperties = "00C463E5" };
RunProperties runProperties1 = new RunProperties();
RunFonts runFonts2 = new RunFonts() { ComplexScriptTheme = ThemeFontValues.MinorHighAnsi };
runProperties1.Append(runFonts2);
run1.Append(runProperties1);
moduleClonedElement.Append(sdtProperties1);
moduleClonedElement.Append(run1);
When I open the generated document, I have this error :
We're sorry. We can't open "...docx" because we found a problem with its contents.
I validate the document and I can see 15 errors:
Full Size
I've found the solution. I search first paragraph and apply my custom style on it.
// clone element
var clonedElement = CloneElementAndSetContentInPlaceholders(datacontext);
// search the first created paragraph on my clonedElement
Paragraph p = clonedElement.Descendants<Paragraph>().FirstOrDefault();
if (p != null)
p.PrependChild<ParagraphProperties>(new ParagraphProperties());
// get the paragraph properties
ParagraphProperties pPr = p.Elements<ParagraphProperties>().First();
// apply style
pPr.ParagraphStyleId = new ParagraphStyleId { Val = "FormationTitre2" };
// set content of content control
SetContentOfContentControl(clonedElement, item.Value);

highlighting text in Docx using c#

I need to highlight a sentence in docx file, I have this code, and its working fine for many documents , but i noticed that for some document the text inside the document is set word by word, not whole sentence, I mean each word with its own Run, so when searching for that sentence, it is not found because it is word by word in the docx.
NOTE: I am working with Arabic text.
private void HighLightText_userSentence(Paragraph paragraph, string text, string title, string author, decimal percentage, string _color)
{
string textOfRun = string.Empty;
var runCollection = paragraph.Descendants<Run>();
Run runAfter = null;
//find the run part which contains the characters
foreach (Run run in runCollection)
{
if (run.GetFirstChild<Text>() != null)
{
textOfRun = run.GetFirstChild<Text>().Text.Trim();
if (textOfRun.Contains(text))
{
//remove the character from thsi run part
run.GetFirstChild<Text>().Text = textOfRun.Replace(text, "");
runAfter = run;
break;
}
}
}
// create a new run with your customization font and the character as its text
Run HighLightRun = new Run();
RunProperties runPro = new RunProperties();
RunFonts runFont = new RunFonts() { Ascii = "Curlz MT", HighAnsi = "Curlz MT" };
Bold bold = new Bold();
DocumentFormat.OpenXml.Wordprocessing.Color color = new DocumentFormat.OpenXml.Wordprocessing.Color() { Val = _color };
DocumentFormat.OpenXml.Wordprocessing.FontSize fontSize = new DocumentFormat.OpenXml.Wordprocessing.FontSize() { Val = "22" };
FontSizeComplexScript fontSizeComplex = new FontSizeComplexScript() { Val = "24" };
Text runText = new Text() { Text = text };
//runPro.Append(runFont);
runPro.Append(bold);
runPro.Append(color);
//runPro.Append(fontSize);
// runPro.Append(fontSizeComplex);
HighLightRun.Append(runPro);
HighLightRun.Append(runText);
//HighLightRun.AppendChild(new Break());
//HighLightRun.PrependChild(new Break());
//insert the new created run part
paragraph.InsertBefore(HighLightRun, runAfter);
}
I recently used docX and was facing problems with searching and higlighting text. I tried an indirect way. It simple and works in most situations. I do it using the replace statement.
here search text is the text you want to highlight
using (DocX doc = DocX.Load("d:\\Sample.docx"))
{
for (int i = 0; i < doc.Paragraphs.Count; i++)
{
foreach (var item in doc.Paragraphs[i])
{
if (doc.Paragraphs[i] is Paragraph)
{
Paragraph sen = doc.Paragraphs[i] as Paragraph;
Formatting form = new Formatting();
form.Highlight = Highlight.yellow;
form.Bold = true;
sen.ReplaceText(searchText, searchText, false,
System.Text.RegularExpressions.RegexOptions.IgnoreCase,
form, null, MatchFormattingOptions.ExactMatch);
}
}
}
doc.Save();
}

Open XML SDK: How to get a valid Word document for WordprocessingDocument.Open

For unit testing purposes, I would like to generate some sample data to be stored as a stream in the dataToImport variable in the following statement:
WordprocessingDocument.Open(dataToImport, false);
Does anyone know how to create a decent set of sample data?
You could potentially use something like the following:
using (WordprocessingDocument wpd = WordprocessingDocument.Open(filename, false)
{
wpd.MainDocumentPart.Document.Body.Append(GenerateParagraph(...text ...);
}
private Paragraph GenerateParagraph(string input)
{
Paragraph paragraph1 = new Paragraph();
Run run1 = new Run();
Break break1 = new Break() { Type = BreakValues.Page };
Text txt = new Text() { Space = SpaceProcessingModeValues.Preserve };
txt.Text = input;
run1.Append(break1);
run1.Append(txt);
paragraph1.Append(run1);
return paragraph1;
}
The value of the ...text... itself could come from any file using FileInputStream objects.
Hope it helps!

Categories

Resources