Microsoft Ribbon button to execute function from add-in - c#

OK, so I've done a lot of googling trying to find information on this topic and I've come up pretty much empty handed. Maybe I'm not searching for the correct terminology for what I'm trying to accomplish.
My issue is that I've written a function in a MS Excel add-in, I followed the instructions from Microsoft as a starting point, but their tutorial has the code execute every time the user saves the document. My goal is to have a button on the ribbon I designed execute this function rather than the save button.
This is the Microsoft article that I followed to get myself started: https://msdn.microsoft.com/en-us/library/cc668205.aspx
I also found this question on here, but it didn't have enough detail for me to figure out how to implement the solution for myself: How to connect a ribbon button to a function defined in an Excel add-in?
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Xml.Linq;
using Excel = Microsoft.Office.Interop.Excel;
using Office = Microsoft.Office.Core;
using Microsoft.Office.Tools.Excel;
namespace ExcelAddIn1
{
public partial class ThisAddIn
{
void FormatTime(Microsoft.Office.Interop.Excel.Workbook WB, bool SaveAsUi, ref bool Cancel)
{
/////MY FUNCTION BODY HERE//////
}
private void ThisAddIn_Startup(object sender, System.EventArgs e)
{
}
private void ThisAddIn_Shutdown(object sender, System.EventArgs e)
{
}
#region VSTO generated code
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private void InternalStartup()
{
this.Startup += new System.EventHandler(ThisAddIn_Startup);
this.Shutdown += new System.EventHandler(ThisAddIn_Shutdown);
}
#endregion
}
}
Thanks in advance for your assistance.

VSTO provides two ways for creating a custom UI:
The Ribbon designer - see Walkthrough: Creating a Custom Tab by Using the Ribbon Designer.
A raw XML markup - Walkthrough: Creating a Custom Tab by Using Ribbon XML.
In both cases you may access the add-in properties and methods using the Globals.ThisAddin property which returns an instance of the add-in class (shown in your code listed above).

Usually you can use Globals.ThisAddIn.Application to access application level and document level UI.
I hope this link can help. Here is a sample of adding a button to a worksheet like this:
Globals.Factory.GetVstoObject(
Globals.ThisAddIn.Application.ActiveWorkbook.Worksheets[1])
.Controls.AddControl(button, selection, buttonName);
Looks like

Related

Opening c# word 2013 project from inside Windows Form

I have successfully built a C# Word 2013 project (ReportGenerator) that opens an MS ACCESS database and generates a MS WORD 2013 report. The results are very good. The issue I have is at the moment it can only be run from inside Visual Studio. My boss wants it to run via a windows form.
I have the competence to build a new project (ReportRunner) that contains a windows form with a datagrid, populate it and put a button on it. What I lack is the competence to know how to:
Open the report generation code from ReportGenerator in the
onclick event of ReportRunner
Pass a variable from ReportRunner to ReportGenerator so to avoid
hard coding.
I was expecting to be able to write a line like “ReportGenerator.ThisDocument.ThisDocument_Startup” in the click event of the button. This isn't happening.
The significant bits of code in my projects are:
ReportGenerator
namespace ReportGenerator
{
public partial class ThisDocument
{
ReportData reportData = new ReportData();
public void ThisDocument_Startup(object sender, System.EventArgs e)
{
int idToLookFor = 2;
reportData = MyFunctionToReadAccessData(idToLookFor);
MyFunctionToPutDataIntoReport();
}
}
}
ReportRunner
using ReportGenerator;
namespace ReportRunner
{
public partial class Form1 : Form
private void button1_Click(object sender, EventArgs e)
{
int idToLookFor = int.Parse(dataGridView1.CurrentRow.Cells[0].Value.ToString());
//HOW DO I MAKE IT OPEN REPORT GENERATOR ThisDocument_Startup
// AND PASS IT THE idToLookFor
}
}
Update:
I'm having trouble understanding your comment so here's a few updates:
You can call method from a Document-level Addin from a seperate C# WinForm using the link I provided. It doesn't matter if it's an Application-level addin or a Document-level addin - the approach is the same. See this link.
Why did you build a ReportRunner Form project that is separate from your ReportGenerator Add-in project? As I said below, you can create a single VS solution with 2 projects - one is a Document-level addin, the other is a WinForm and you can simply call the WinForm from the Ribbon associated with the addin.
I assume that you're asking how to call a function from a Word Addin from a Winform? I recently explained how to do this here: How to call a VSTO AddIn method from a separate C# project?
That being said, I don't recommend doing this becaues you can simply package your WinForm together with your Addin and then open it like this using a Ribbon:
private void button1_Click(object sender, RibbonControlEventArgs e)
{
Form1 aForm = new Form1();
aForm.Show();

ribbon.Invalidate Null Exception in C# VSTO add-in

I am creating an application level add-in for Word 2010 using C# VSTO. The add-in has a Custom Task Pane with its visibility controlled by a toggle button on a ribbon. The ribbon has been created with XML (not the Visual Studio Designer).
When I call ribbon.Invalidate from outside the add-in's ribbon class I cannot refresh my ribbon because it is null. I get a System.NullReferenceException that issues the message:
Object reference not set to an instance of the object
I suspect that the ribbon is null because the underlying XML is not loaded when it is called. I have tried many things including
Invalidating Ribbon from Outside Ribbon
which suggests defining a class-level Office.IRibbonUI in the ThisAddIn class, and setting the value of this in the Ribbon_Load callback. I still received the exception with this and all other attempts I made. Here's my code:
In the myRibbon class I have:
[ComVisible(true)]
public class myRibbon : Office.IRibbonExtensibility
{
public Office.IRibbonUI ribbon;
private bool isTaskPaneVisible;
public bool IsTaskPaneVisible
{
get { return isTaskPaneVisible; }
set
{
isTaskPaneVisible = value;
// This is where the null exception is thrown
ribbon.Invalidate();
}
}
and
public void Ribbon_Load(Office.IRibbonUI ribbonUI)
{
this.ribbon = ribbonUI;
}
In the ThisAddin class I have:
public partial class ThisAddIn
{
internal myRibbon myRibbon;
and
protected override Microsoft.Office.Core.IRibbonExtensibility CreateRibbonExtensibilityObject()
{
myRibbon = new myRibbon();
return myRibbon;
}
Any assistance in getting ribbon.Invalidate to function correctly when called from outside the ribbon class would be greatly appreciated.
More than two and a half years after posting this question, the solution came to me while working on a different VSTO project. The issue was with the XML for the VSTO project.
ribbon.Invalidate was null because
public void Ribbon_Load(Office.IRibbonUI ribbonUI)
{
this.ribbon = ribbonUI;
}
assigned a null value to ribbon. And ribbonUI was null because the Ribbon XML file was missing a reference to Ribbon_Load.
So the original XML file read
<customUI xmlns="http://schemas.microsoft.com/office/2009/07/customui" xmlns:nsCustom="Custom Namespace">
But it should have had onLoad="Ribbon_Load" included
<customUI onLoad="Ribbon_Load" xmlns="http://schemas.microsoft.com/office/2009/07/customui" xmlns:nsCustom="Custom Namespace">
I revisited the code I wrote and confirmed that this resolved the issue.
Was the Ribbon_Load callback called before you try to use the IRibbonUi instance?
There is no need to call the Invalidate method if the Load callback is not yet called. The fact is that your callbacks will be invoked automatically for the first time right after the Load one.
Read more about the Fluent UI (aka Ribbon UI) in the following series of articles in MSDN:
Customizing the 2007 Office Fluent Ribbon for Developers (Part 1 of 3)
Customizing the 2007 Office Fluent Ribbon for Developers (Part 2 of 3)
Customizing the 2007 Office Fluent Ribbon for Developers (Part 3 of 3)

Having problems with simple EF6 (C#) Winform saving data from details form

I am pretty new to coding ADO.Net/entity framework stuff. I am trying to follow "Microsoft ADO.NET Entity Framework Step by Step", Microsoft Press Mueller. I'm using VS 2012 with EF6 installed.
Start a new project, and adding an new Empty ADO.NET Entity Data Model. It's pretty simple, a few scalars and one Enumeration called UserFavorites. Then add a data source > Object > Drilling down to my UserFavorites object and finishing. I change toe UserFavorites object on the data source tab to detail view ( and a couple other changes like combo box and label on the others). Then drag the UserFavorites object to the form. It creates a Binding source and binding navigator all as it should. After enabling the save button and entering the code below it runs great and gets the records from the database that can be scrolled between. The problem is when I click the plus to add a record, fill it in, and click save, I get validation errors. on the
Hide Copy Code
UserFavoritesContext.SaveChanges();
line. The first error is
"Exception:Thrown: "Value of '1/1/0001 12:00:00 AM' is not valid for 'Value'. 'Value' should be between 'MinDate' and 'MaxDate'." (System.ArgumentOutOfRangeException)"
There is a date picker on the form, and it's filled out correctly. If I remove that item from my model I get errors on the next item in the model. For some reason it's not pulling the data filled in on the form and trying to use defaults (or null).
I can't find anyone else with this problem online, so I guess I am missing something silly. I followed the book exactly ( and can't find a help forum for the book). I hope this is clear enough for someone to offer some guidance.
Images of Form and Data Source,Model,Error, and zip of project are at
https://www.dropbox.com/sh/z6yhvbp1uk7bobm/AADa7fnS82PzwNLlPrycnCYza?dl=0
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
namespace UserFavoritesEF6
{
public partial class Form1 : Form
{
// Define the context used to access the database.
UserFavoritesModelContainer UserFavoritesContext;
<pre>
public Form1()
{
InitializeComponent();
// Initialize the database context.
UserFavoritesContext = new UserFavoritesModelContainer();
// Query the database for the records you want.
var dbQuery =
UserFavoritesContext.UserFavorites.Where(id => id.UserId >= 0).ToArray();
}
private void userFavoritesBindingNavigatorSaveItem_Click(object sender, EventArgs e)
{
UserFavoritesContext.SaveChanges();
}
private void Form1_Load(object sender, EventArgs e)
{
// Assign a local copy of the queried records to the
// binding source.
userFavoritesBindingSource.DataSource =
UserFavoritesContext.UserFavorites.Local;
// Fill the Favorite Colors list with acceptable colors and
// choose a default.
favoriteColorComboBox.DataSource = Enum.GetValues(typeof(ColorNames));
favoriteColorComboBox.SelectedItem = ColorNames.Red;
}
}
}

C# Windows form App with SharePoint

Im new to the whole C# and Visual Studio program.
I have been given a task to create a windows form app using C# to connect to a SharePoint site and retrieve any data from there e.g. list, files.
I have designed my application so that you can manually add the site url which you want then click a button and this will generate a xml file with all the data which is in the site.
This is the way i need my xml to be set out:
The report should be in either csv or xml format e.g.
<SiteCollection Name=”SiteCollection”>
<Web Name=”Web Name”>
<Library Name=”Library Name”>
<Document Name=”DocName1”/>
<Folder Name=”Folder Name”>
<Document Name=”DocName2”/>
<Document Name=”DocName3”/>
</Folder>
</Library>
<List Name=”List Name”>
<Web Name=”Web Name”>
<Library Name=”Library Name”>
<Document Name=”DocName1”/>
<Folder Name=”Folder Name”>
<Document Name=”DocName2”/>
<Document Name=”DocName3”/>
</Folder>
</Library>
<List Name=”List Name”>
</Web>
</Web>
</SiteCollection>
This is how I have my code for my app set out so far:
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using Microsoft.SharePoint;
using Microsoft.SharePoint.Administration;
namespace SharePoint.College
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
private void Form1_Load(object sender, EventArgs e)
{
}
private void textBox1_TextChanged(object sender, EventArgs e)
{
}
private void btn1_Click(object sender, EventArgs e)
{
}
}
}
Im just looking for some advice and some help to start this off.
Thanks for any replies
As your new to this you should start with a few basic tutorials, a search for C# tutorials will turn up loads of results. You could start with MSDN C# Tutorials.
Once you are comfortable with C# take a look at some Winforms tutorials such as C# Corner - Tutorial: Working with Windows Forms - Part I
Assuming you are using SharePoint 2010 and you are not going to be running this code directly on the SharePoint server you will want to look at Using the SharePoint Foundation 2010 Managed Client Object Model in order to retrieve the information.
As a side note you will get better responses from this site if you do this kind of research first and then ask questions (with relevant code snippets) about specific difficulties you are encountering, see What types of questions should I avoid asking? on the help pages.
This code should give you access to a List or Library. Note that since you are a beginner, you may not be familiar with handling SPList so I have converted to a DataTable which I believe should be easier. Note that I have named the member variables (those starting with this.xxx)to indicate what they are/should contain.
using (SPSite site = new SPSite(this.siteUrl))
{
using (SPWeb web = site.OpenWeb(this.siteName))
{
SPList mylib = web.Lists[this.libraryName];
DataTable dt = mylib.Items.GetDataTable();
}
}
In the mean time please follow Aquila Sands suggestions, it pays off in the long run if you decide to stay with C# and SharePoint. Good luck.

c# simple skype app throws COM exception

I am making my first Skype app that can simply message a user but when I debug I get a exception that crashes my app.
Here is the code:
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using skype_app;
using SKYPE4COMLib;
namespace skype_app
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
private void Form1_Load(object sender, EventArgs e)
{
}
private void button2_Click(object sender, EventArgs e)
{
var oskype = new SKYPE4COMLib.Skype();
oskype.PlaceCall(textBox1.Text);
}
private void textBox1_TextChanged(object sender, EventArgs e)
{
}
private void button1_Click(object sender, EventArgs e)
{
var oskype = new SKYPE4COMLib.Skype();
oskype.SendMessage(textBox1.Text, textBox2.Text);
}
private void textBox2_TextChanged(object sender, EventArgs e)
{
}
}
}
i have use some extra references
references list:
Microsoft.Csharp
SKYPE4COMlib
SkypeDialoglib
system
system.core
system.data
system.data.DataSetEXTensions
system.deployment
system drawing
System.Windows.forms
System.xml.linq
Here is the exception i get:
System.RUntime.InteropServices.ComException : {"connection refused"}
So I guess my main question is why does my connection get refused when Skype dose not even open the dialogue asking if I want to allow the connection ?
The issue is that you're trying to debug in Visual Studio. Unfortunately, according to Skype themselves, they do not support using this API & debugging in VS:
Per the link:
The most comment cause for this is you are trying to debug the program
in Visual Studio. Going forward we will not be able to support using
the visual studio hosting process for debugging. You can turn it off
by:
Open your project in VS
Open your projects properies
click the debug tab
untick "use visual studio hosting process"
rebuild your application and begin debugging and it should work ok.
i face the same issue. this way i solved it.
here is my code
Skype skype;
skype = new SKYPE4COMLib.Skype();
Call call = skype.PlaceCall(txtPhonenNo.Text);
first thing login to skype and go to Tools > option > advanced settings
your screen would look like
click on manage other program's access to skype
then another window will come which will show all program name which try to access skype. if any exist just select all and remove it.
then run your program again and go to that screen where this option was available called click on manage other program's access to skype
click there and a windows will come which will display the name of your apps just select that name and click on change button then another window will come which looks like
in that window just select the option called allow this program to access skype then a dialog come on the skype window which looks like
where you need to click on allow access button and then your job will be done. hope this will help.

Categories

Resources