Interop.Powerpoint equivalent of Interop.Word.Application.Visiblity = off - c#

If I want to create a word document in C# using Interop.Word, I can create the document without ever opening the program:
Microsoft.Office.Interop.Word.Application wordApp = new Microsoft.Office.Interop.Word.Application();
wordApp.Visibile = false;
I'm trying to find an equivalent when using Interop.Powerpoint, but I have been unable to find the appropriate property.
Any help would be much appreciated.
EDIT
Sorry, my question was not clear. I have tried:
Microsoft.Office.Interop.Powerpoint.Application pptApp = new Microsoft.Office.Interop.Powerpoint.Application();
pptApp.Visible = Microsoft.Office.Core.MsoTriState.msoFalse;
However, I received the following error:
Application (unknown member) : Invalid request. Hiding the application window is not allowed.

You can prevent from showing the window while opening the Presentation:
pptApp = new Microsoft.Office.Interop.Powerpoint.Application();
pptApp.Presentations.Open(fileName, WithWindow:Microsoft.Office.Core.MsoTriState.msoFalse);
I know you already utilized Open XML, but maybe someone else will need this.

MChmurski's answer inspired me but when I was trying it doesn't work as expected.
The signature for Presentations.Open() is as following:
Presentation Open(
string FileName,
MsoTriState ReadOnly,
MsoTriState Untitled,
MsoTriState WithWindow
)
I think we'd be set the last TriState option instead of the 2nd. So I changed it as following and it works perfectly:
var objApp = new Microsoft.Office.Interop.PowerPoint.Application();
var objPres = objApp.Presentations.Open(filePath, MsoTriState.msoTrue, MsoTriState.msoTrue, MsoTriState.msoFalse);

Related

Changing Footnote numbering fails for some word documents with Interop

I have the following code being used with Word 2016 installed, referencing Microsoft Word 16.0 Object Library:
private void RefreshFootnoteNumbering(FileManagement.FileManager FileManager)
{
Console.WriteLine(DateTime.Now.ToString() + " Refreshing footnotes DOCX");
// Opening and saving in word generates the required element
var Word = GetWordApp();
try
{
var DocxPath = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, Path.ChangeExtension(FileManager.HtmlFileLocation, "docx"));
Console.WriteLine(DateTime.Now.ToString() + "\tOpening document");
var Doc = GetWordDoc(Word, DocxPath);
try
{
// Fails on these lines below (both cause the same exception)
Doc.Footnotes.NumberingRule = InteropWord.WdNumberingRule.wdRestartPage;
Doc.Footnotes.Location = InteropWord.WdFootnoteLocation.wdBottomOfPage;
Doc.SaveAs2(DocxPath, InteropWord.WdSaveFormat.wdFormatXMLDocument, AddToRecentFiles: false, EmbedTrueTypeFonts: true);
}
finally
{
Doc.Close();
Doc = null;
}
}
finally
{
Word.Quit();
Word = null;
GC.Collect();
GC.WaitForPendingFinalizers();
}
}
This works for most documents, however for some I get the following exception:
System.Runtime.InteropServices.COMException was unhandled
ErrorCode=-2146823680
HResult=-2146823680
HelpLink=wdmain11.chm#37376
Message=Value out of range
Source=Microsoft Word
StackTrace:
at Microsoft.Office.Interop.Word.Footnotes.set_NumberingRule(WdNumberingRule prop)
Other interop functions (iterating/manipulating fields, sections etc) work fine, it seems to be just altering footnotes in this way that have an issue. Altering them from within Word itself works fine.
Has anyone encountered this issue before? Any work arounds or alternatives?
I've tried recording a macro, and it gave this VBA code:
With ActiveDocument.Range(Start:=ActiveDocument.Content.Start, End:= _
ActiveDocument.Content.End).FootnoteOptions
.Location = wdBottomOfPage
.NumberingRule = wdRestartContinuous
.StartingNumber = 1
.NumberStyle = wdNoteNumberStyleArabic
.NumberingRule = wdRestartPage
.LayoutColumns = 0
End With
If I run this macro, I get the same error (value out of range, error number 4608) on the .Location line, whether I run from the debugger, or just view macros -> run.
I've also tried to translate that VBA into C# code:
var Options = Doc.Range(Doc.Content.Start, Doc.Content.End).FootnoteOptions;
Options.Location = InteropWord.WdFootnoteLocation.wdBottomOfPage;
Options.NumberingRule = InteropWord.WdNumberingRule.wdRestartPage;
However, this gives the same error.
Still not sure of the exact cause (possibly something further up in my code creating different sections); still not clear on why it worked when word recorded the macro, but not when running it.
Anyway, I managed to alter the C# code to the below, which seems to do the job and actually works!
foreach(InteropWord.Footnote FootNote in Doc.Footnotes)
{
FootNote.Reference.FootnoteOptions.NumberingRule = InteropWord.WdNumberingRule.wdRestartPage;
FootNote.Reference.FootnoteOptions.Location = InteropWord.WdFootnoteLocation.wdBottomOfPage;
}

"Turn" printing using PrinterSettings using C#

I'm trying to print labels with a dynamic content. The print works fine but the problem is that the printing itself (the font) is 90 degrees twisted. It looks like this:
But it should look like this:
I cannot change the settings of the printer because other labels do print correct. So I think it must be something in the code. You can watch the C# code here:
System.Drawing.Printing.PrinterSettings printerSettings = new System.Drawing.Printing.PrinterSettings();
printerSettings.PrinterName = #"\\server\printer";
printerSettings.Copies = Convert.ToInt16((Convert.ToInt16(row.Cells["Counter"].Value.ToString()) - 1));
System.Drawing.Printing.PrintController standardPrintController = new System.Drawing.Printing.StandardPrintController();
Telerik.Reporting.Processing.ReportProcessor reportProcessor = new Telerik.Reporting.Processing.ReportProcessor();
reportProcessor.PrintController = standardPrintController;
Telerik.Reporting.InstanceReportSource instanceReportSource = new Telerik.Reporting.InstanceReportSource();
instanceReportSource.ReportDocument = myReport;
reportProcessor.PrintReport(instanceReportSource, printerSettings);
Does anyone know such a problem or a possible solution?
Suggestion very appreciated :)
I've had the same problem once, but never used Telerik for anything. I was trying to print a XPS file with the PrintServer object, and came up with this solution to rotate the print.
Basicly I change the page orientation of the queue before I print for the user, and then change it back afterwards.
It might be usefull to you as well.
PrintServer ps = new PrintServer("\\\\somePrintServer");
var queue = ps.GetPrintQueue("printerShareName");
var oldOrientation = queue.UserPrintTicket.PageOrientation;
queue.UserPrintTicket.PageOrientation = PageOrientation.Landscape;
//print job here
queue.UserPrintTicket.PageOrientation = oldOrientation;

Datagrid contents with UI Automation and .net

I'm having some trouble reading the contents of a Datagrid in an external application using UI Automation and could use some pointers. Here's what I have so far:
int id = System.Diagnostics.Process.GetProcessesByName("Book")[0].Id;
AutomationElement desktop = AutomationElement.RootElement;
AutomationElement bw = desktop.FindFirst(TreeScope.Children, new PropertyCondition(AutomationElement.ProcessIdProperty, id));
AutomationElement datagrid = bw.FindFirst(TreeScope.Children, new PropertyCondition(AutomationElement.AutomationIdProperty, "lv"));
AutomationElementCollection lines = datagrid.FindAll(TreeScope.Children, new PropertyCondition(AutomationElement.ControlTypeProperty, ControlType.DataItem));
AutomationElementCollection items = lines[1].FindAll(TreeScope.Children, new PropertyCondition(AutomationElement.ControlTypeProperty, ControlType.Custom));
GridItemPattern pattern = items[1].GetCurrentPattern(GridItemPattern.Pattern) as GridItemPattern;
TableItemPattern tablePattern = items[1].GetCurrentPattern(TableItemPattern.Pattern) as TableItemPattern;
This works in as much as I can access the column ids and row ids from the GridItemPattern and TableItemPattern but how do I access the value that is in that specific cell? Is it even possible?
Thanks.
I think you need to use ValuePattern for it. Just like that:
ValuePattern pattern = items[0].GetCurrentPattern(ValuePattern.Pattern) as ValuePattern;
string value = pattern.Current.Value;
I finally figured this out, it requires the use of CacheRequest to request the Name property on the AutomationElement. Here's the final code:
var cacheRequest = new CacheRequest
{
AutomationElementMode = AutomationElementMode.None,
TreeFilter = Automation.RawViewCondition
};
cacheRequest.Add(AutomationElement.NameProperty);
cacheRequest.Add(AutomationElement.AutomationIdProperty);
cacheRequest.Push();
var targetText = loginLinesDetails[i].FindFirst(TreeScope.Children, new PropertyCondition(AutomationElement.ClassNameProperty, "TextBlock"));
cacheRequest.Pop();
var myString = targetText.Cached.Name;
I am not familiar with the AutomationElement classes but I have used AutoIT to automate some simple windows stuff in the past (find a dialog, click a button, etc) and it was cake. You might consider it. The download contains a .dll you can reference from a .Net solution.
I'm not sure if the external app is a WinForm grid or not but here is an ASP.Net grid example: http://www.autoitscript.com/forum/topic/13709-how-to-get-the-contents-of-datagrid-control/
Then again, if you are scraping the info from the web I would recommend WatiN or Selenium
You can try using RawViewWalker on a element to get raw values (On controlview you might not be able to get few properties)

Update a RichTextBox on Sp2010 using Windows Forms & ListService.UpdateListItems Method

I'm having an issue updating a RichText box on a SharePoint 2010 list.
_batchElement.InnerXml =
string.Format(
"<Method ID='1' Cmd='New'><Field RichText='True' Name='Other_x0020_Items_x0020_of_x0020'>{0}</Field><Field Name='Overall_x0020_rating_x0020_of_x0'>{1}</Field><Field Name='Do_x0020_you_x0020_wish_x0020_to'>{2}</Field></Method>",
add_Report_Details.Rtf,
arrText,
addreportwish);
And the code to trigger the update:
ListService.UpdateListItems(ListName, _batchElement);
But, given that this xml element cannot have anything starting with a \ it doesn't want to work.
I have tried HTML as well, even passing HTML through agility pack, and it just doesn't work either.
What is the proper method or field name or something to update that richtextbox?
do i need a cdata? or something? I'm very confused, and the doco on MSDN isn't that great for this method.
Pass it through an HTML encode, and it seems to work fine:
private static string SetProperHTML(string sHtml)
{
var sb = new StringBuilder();
var stringWriter = new StringWriter(sb);
string input = sHtml;
var test = new HtmlAgilityPack.HtmlDocument();
test.LoadHtml(input);
test.OptionOutputAsXml = false;
test.OptionCheckSyntax = true;
test.OptionFixNestedTags = true;
test.OptionAutoCloseOnEnd = true;
test.OptionWriteEmptyNodes = true;
test.Save(stringWriter);
Console.WriteLine(sb.ToString());
return WebUtility.HtmlEncode(sb.ToString().Replace(Environment.NewLine, ""));
}
Also want to make sure that your field descriptor is setup properly:
_batchElement.InnerXml =
string.Format(
"<Method ID='1' Cmd='New'><Field Name='Other_x0020_Items_x0020_of_x0020'>{0}</Field><Field Name='Overall_x0020_rating_x0020_of_x0'>{1}</Field><Field Name='Do_x0020_you_x0020_wish_x0020_to'>{2}</Field></Method>",
SetProperHTML(add_Report_Details.Document.Body.InnerHtml),
arrText,
addreportwish);
it's a field like any other, no special child tags needed. As long as the Sp2010 field on the form is setup for 100% full HTML, this should work. There are other HTMLEncoders out there, which may be better than the WebUtility but, for the most part, this should work, given Agility Pack is fixing most of the HTML.

Problems with OpenOffice Writer using C#

I am creating a OO Writer document with C#.
Any help would be appreciated - I no longer know whether I am coming or going, I have tried so many variations....
using C#, has anybody successfully got the following to work? I just have a simple table of 2 columns and want to set the column widths to different values (actual value at this stage immaterial - just not identical widths).
This code is adapted from various web sources given as examples of how to do column widths. I cannot get it to work....
//For OpenOffice....
using unoidl.com.sun.star.lang;
using unoidl.com.sun.star.uno;
using unoidl.com.sun.star.bridge;
using unoidl.com.sun.star.frame;
using unoidl.com.sun.star.text;
using unoidl.com.sun.star.beans;
..............................
XTextTable odtTbl = (XTextTable) ((XMultiServiceFactory)oodt).createInstance("com.sun.star.text.TextTable");
odtTbl.initialize(10, 2);
XPropertySet xPS = (XPropertySet)odtTbl;
Object xObj = xPS.getPropertyValue("TableColumnSeparators")**; // << Runtime ERROR**
TableColumnSeparator[] xSeparators = (TableColumnSeparator[])xObj;
xSeparators[0].Position = 500;
xSeparators[1].Position = 5000;
xPS.setPropertyValue("TableColumnSeparators", new uno.Any(typeof(unoidl.com.sun.star.text.XTextTable),xSeparators));
// Runtime ERROR indicates the ; at the end of the Object line, with message of IllegalArgumentException
Now this is only one type of error out of all the combinations of attempts. Not many allowed execution at all, but the above code did actually run until the error.
What is the correct code for doing this in C# please?
In addition, what is the correct C# code to set an O'Writer heading to a particular style (such as "Heading 1") so that it looks and prints like that style in the document?
Thank you.
unoidl.com.sun.star.uno.XComponentContext localContext = uno.util.Bootstrap.bootstrap();
unoidl.com.sun.star.lang.XMultiServiceFactory multiServiceFactory = (unoidl.com.sun.star.lang.XMultiServiceFactory)localContext.getServiceManager();
XComponentLoader componentLoader =(XComponentLoader)multiServiceFactory.createInstance("com.sun.star.frame.Desktop");
XComponent xComponent = componentLoader.loadComponentFromURL(
"private:factory/swriter", //a blank writer document
"_blank", 0, //into a blank frame use no searchflag
new unoidl.com.sun.star.beans.PropertyValue[0]);//use no additional arguments.
//object odtTbl = null;
//odtTbl = ((XMultiServiceFactory)xComponent).createInstance("com.sun.star.text.TextTable");
XTextDocument xTextDocument = (unoidl.com.sun.star.text.XTextDocument)xComponent;
XText xText = xTextDocument.getText();
XTextCursor xTextCursor = xText.createTextCursor();
XPropertySet xTextCursorProps = (unoidl.com.sun.star.beans.XPropertySet) xTextCursor;
XSimpleText xSimpleText = (XSimpleText)xText;
XTextCursor xCursor = xSimpleText.createTextCursor();
object objTextTable = null;
objTextTable = ((XMultiServiceFactory)xComponent).createInstance("com.sun.star.text.TextTable");
XTextTable xTextTable = (XTextTable)objTextTable;
xTextTable.initialize(2,3);
xText.insertTextContent(xCursor, xTextTable, false);
XPropertySet xPS = (XPropertySet)objTextTable;
uno.Any xObj = xPS.getPropertyValue("TableColumnSeparators");
TableColumnSeparator[] xSeparators = (TableColumnSeparator[])xObj.Value; //!!!! xObj.Value
xSeparators[0].Position = 2000;
xSeparators[1].Position = 3000;
xPS.setPropertyValue("TableColumnSeparators", new uno.Any(typeof(TableColumnSeparator[]), xSeparators)); //!!!! TableColumnSeparator[]

Categories