Archive

Posts Tagged ‘csharp’

Automatically connect WebParts on a SharePoint page

August 6th, 2010 Jeffrey Tummers 3 comments

For a recent project we had several WebParts (Provider and Consumer webparts) on a page which had to be connected to each other when the page was provisioned by our solution.

Unfortunately this cannot be done within the Module.xml :(

So I created a method which automatically connects the consumer WebParts to their correct provider WebParts.

To do this I basically used the SPLimitedWebPartManager, ProviderConnectionPoint, ConsumerConnectionPoint and some other nice classes.

The method (warning long block of code)

/// <summary>
/// Connects the web parts on page.
/// </summary>
/// <param name="web">The web.</param>
/// <param name="pageUrl">The page URL.</param>
/// <param name="publish">if set to <c>true</c> [publish].</param>
public static void ConnectWebPartsOnPage(SPWeb web, string pageUrl, bool publish)
{
	// get the page from the url
	SPFile page = web.GetFile(pageUrl);

	// make sure the page exists
	if (page.Exists)
	{
		// if the page is checked out, check it in because then the user can do an rollback
		if (page.Level == SPFileLevel.Checkout)
		{
			page.CheckIn("Page was checked out, needs to be checked in before connecting webparts", SPCheckinType.MinorCheckIn);
		}

		// check out the page because we are going to do changes on it
		page.CheckOut();

		// get the webpartmanager for the page
		using (Microsoft.SharePoint.WebPartPages.SPLimitedWebPartManager mgr = page.GetLimitedWebPartManager(PersonalizationScope.Shared))
		{
			try
			{
				// try to connect the webparts on the page
				if (ConnectWebParts(mgr))
				{
					string checkinComment = "Auto connected WebParts on page";

					// webparts are connected so update the page and check it in
					page.Update();
					page.CheckIn(checkinComment);

					if (publish)
					{
						page.Publish(checkinComment);
						page.Approve(checkinComment);
					}
				}
			}
			catch (Exception ex)
			{
				page.UndoCheckOut();
				throw ex;
			}
		}
	}
}

/// <summary>
/// Checks if a WebPart connection exists.
/// </summary>
/// <param name="connections">The connections.</param>
/// <param name="provider">The provider.</param>
/// <param name="consumer">The consumer.</param>
/// <returns></returns>
private static bool WebPartConnectionExist(Microsoft.SharePoint.WebPartPages.SPWebPartConnectionCollection connections,
	System.Web.UI.WebControls.WebParts.WebPart provider, System.Web.UI.WebControls.WebParts.WebPart consumer)
{
	foreach (Microsoft.SharePoint.WebPartPages.SPWebPartConnection conn in connections)
	{
		if (conn.Provider == provider && conn.Consumer == consumer)
		{
			return true;
		}
	}

	return false;
}

/// <summary>
/// Connects the web parts.
/// </summary>
/// <param name="manager">The manager.</param>
/// <returns></returns>
private static bool ConnectWebParts(Microsoft.SharePoint.WebPartPages.SPLimitedWebPartManager manager)
{
	bool connectionMade = false;

	// get the webparts on the page
	Microsoft.SharePoint.WebPartPages.SPLimitedWebPartCollection webparts = manager.WebParts;

	// only continu if there are any webparts
	if (webparts.Count > 0)
	{
		ProviderConnectionPointCollection provColl;
		ConsumerConnectionPointCollection consColl;
		// walk through all the webparts on the page to find provider webparts
		foreach (System.Web.UI.WebControls.WebParts.WebPart providerPart in webparts)
		{

			// check if the webpart is a Provider webpart
			provColl = manager.GetProviderConnectionPoints(providerPart);
			if (provColl != null && provColl.Default != null)
			{

				// walk through all the webparts on the page again now to find the consumer webparts
				foreach (System.Web.UI.WebControls.WebParts.WebPart consumerPart in webparts)
				{

					// first make sure the webpart isn't the provider webpart
					if (consumerPart != providerPart)
					{
						// check if the webpart is a Consumer webpart,
						// then make sure the consumer webpart isn't already connected to the provider webpart
						// then check if the interface of the consumer webpart is assignable from the interface of the provider webpart
						consColl = manager.GetConsumerConnectionPoints(consumerPart);
						if (consColl != null && consColl.Default != null
							&& !WebPartConnectionExist(manager.SPWebPartConnections, providerPart, consumerPart)
							&& consColl.Default.InterfaceType.IsAssignableFrom(provColl.Default.InterfaceType))
						{
							// connect the webparts
							manager.SPConnectWebParts(providerPart, provColl.Default, consumerPart, consColl.Default);
							connectionMade = true;
						}
					}
				}
			}
		}
	}
	return connectionMade;
}

Sample usage (console application)

try
{
	using (SPSite site = new SPSite("http://localhost"))
	using (SPWeb web = site.OpenWeb())
	{
		ConnectWebPartsOnPage(web, "pages/default.aspx", false);
	}
}
catch (Exception ex)
{
	Console.WriteLine();
	Console.WriteLine("Message:\n{0}\n\nStack:\n{1}\n\n", ex.Message, ex.StackTrace);
}

C# 4.0 .NET becomes dynamic

May 29th, 2009 Jeffrey Tummers No comments

This post is about the session called C# 4.0 / The Future of C# given by Krishnan Subramanian.

csharp4-dlr

First off let me start with a quick summary of main new feauture for the different versions of the C# that are released.

  • C# 1.0, Managed code
  • C# 2.0, Generics
  • C# 3.0, Language Integrated Query, short LINQ
  • C# 4.0, Dynamic programming

Some off the innovation for C# 4.0 are:

Dynamic Language Runtime
The new version of C# has a new type of object declaration, called dynamic. This looks a bit the var keyword. With the var keyword the compiler replaced the var with the object type on compile time, intellisense and code completion still was available in Visual Studio. With the new dynamic keyword the compiler doesn’t replace this and even more important the compiler can’t check for syntax error on a dynamic object. Intellisense and code complition are also not available for objects defined with dynamic.

Dynamic objects are losely typed instead of strongly.

After reading this you might think whats the use of this new DLR, in the following sample I’ll try to explain this. We have a simple C# class called Calculator, and use it like below.

Calculator calc = GetCalculator();
int sum = calc.Add(10, 20);

Now suppose the calculator class is not strongly typed, the code would like something like the following

object calc = GetCalculator();
Type calcType = calc.GetType();
object res = calcType.InvokeMember("Add", BindingFlags.InvokeMethod, null, new object[] { 10, 20 });
int sum = Convert.ToInt32(res);

With the new dynamic keyword in C# 4.0 it would simply be

dynamic calc = GetCalculator();
int sum = calc.Add(10, 20);

Optional Named Parameters
To show you the what this means take a look at the examples below.

In previous version of C# method overloads would be used.

public void Add(string lineOfText);
public void Add(string lineOfText, bool isError);
public void Add(string lineOfText, int repeat);
public void Add(string lineOfText, int repeat, bool isError);

With the new C# 4.0, the method declaration would like this

public void Add(string lineOfText, int repeat = 1, bool isError = false);

As you can see in the sample above, it’s now possible to specify default values for a method parameter. Some samples of how to use the Add method are:

Add("This is the line", repeat : 5);
Add(isError : true, lineOfText : "Another line of text");

For people using JavaScript this might look very familiar.

Another cewl new thing I saw at the demo, was the ability to interpret and compile a string of C# code at runtime. This functionality offers some great new possibilities. Again for the Javascript people reading this it’s like the eval function.

Categories: DevDays09 Tags: , ,