Home
September 27
Getting Excited About the SharePoint Conference

SharePoint Conference 2011 is running next week in Anaheim, California. I will be presenting a session on Tuesday titled Developing SharePoint applications with HTML5 and JQuery. I have been working with jQuery in SharePoint 2010 and presenting on this topic for over a year now. However, this is the first event with a large audience where I get to present on integrating the features of HTML5 with SharePoint 2010. I have been working on the demos which include a few HTML5 master pages and some site page templates that leverage new HTML5 elements and the new JavaScript APIs. I will also be demoing how to use Modernizr to leverage HTML5 features in modern browsers while still having a fallback plan for browsers that don't support HTML5 such as IE8.

There will be several other Critical Path Training instructors delivering sessions including Scot Hillier, Matthew McDermott, Maurice Prather, David Mann, Asif Rehmani, John Holliday and, of course, my business partner Andrew Connell. We have 14 sessions in all which you can read about in detail at http://www.criticalpathtraining.com/Community/Pages/October.aspx.

If you are at the SharePoint Conference next week, please stop by the Critical Path Training booth. The booth itself is brand new with a cool design featuring a swirling digital vortex. We're also giving away free training prizes and a ton of the SharePoint books that we have authored. All in all, we will be giving away $25,000 worth of SharePoint 2010 training and 120 books with hourly drawings and eight book signings throughout the week. Anybody that comes to our booth will also get a discount code for 20% on any Critical Path Training classes through the end of the year. I hope to see you there.

September 08
Adding Items in SharePoint 2010 using REST and data.js

Early this morning about 6:17 AM I sat up in my office chair and said to myself "it can't really be this easy". But it is.

Here's my scenario. I am in need of writing client-side code in JavaScript which adds new items to a SharePoint 2010 Contacts list named Customers. I have been told that I'm required to accomplish this using the Open Data Protocol (OData) and the new REST-based API accessible through ListData.svc. This means I must add each item to a SharePoint list using an HTTP POST operation.

At first, I thought my inner code monkey would be challenged by writing the JavaScript required to reach my goal. However, for the last few months I have been hearing talk on the streets about this cool new JavaScript library named datajs - JavaScript Library for data-centric web applications. I can say first hand that it's powerful and that it's simple to use. Take a look at the following JavaScript code and notice how I create a new JavaScript object and initialize it with properties that match up to the names of the columns I need to modify in the target list.

function OnAddCustomer() {   

// create a JavaScript object with field values for the new item
  var newCustomer = {
    LastName: $("#txtLastName").val(),    
FirstName: $("#txtFirstName").val()
  };

// create JavaScript object required as a parameter to OData.request()
var requestOptions = {
    requestUri: GetWebUrl() + "_vti_bin/ListData.svc/Customers",
    method: "POST",
    data: newCustomer
  };

// call OData.request to add item with HTTP POST operation
OData.request(requestOptions, OnAddSuccess, OnAddError);
}

You can see that I am building an URL for the requestUri value by calling a helper function named GetWebUrl. I wrote this function to take the Web-relative URL from the _spPageContextInfo variable and to add a forward slash at the end if it's not already there.

function GetWebUrl() {
var webUrl = _spPageContextInfo.webServerRelativeUrl;
if (webUrl.substr(webUrl.length - 1, 1) != "/") {
webUrl += "/";
}
return webUrl;
}

The full requestUri value is built from the Web-relative URL parsed together with the relative path to ListData.svc and the list name which in my case is Customers. Once I have built the requestOptions object, I pass it in the call to the OData.request method along with two other parameters with callback methods that execute either after the POST operation completes successfully or with an error.

OData.request(requestOptions, OnAddSuccess, OnAddError);

One of these two callback methods will be executed once response to the HTTP POST operation is returned from the Web server.

function OnAddSuccess(data, request) {
  // handle success - reinitialize the user interface 
$("#txtLastName").val("");  
$("#txtFirstName").val("").focus();
} function OnAddError(error) { // handle error - notify user that something went wrong alert(JSON.stringify(error)); }

It's wonderful how little code you have to write to add items using the OData.request method. You can use Fiddler on your developer workstation to see what's going on behind the scenes and figure out what is actually being sent across the network to Web server.

image

Svweet!

September 01
Register for a Training Class with Our Back-To-School Discount

We have decided to offer an across-the-board 20% discount for anyone that registers for Critical Path Training class in September. That means you can register for a class that running this month and get a discount that is even better than our early bird discount. If you interested in learning jQuery with SharePoint 2010, the class I would recommend is the Brand Camp course I am teaching in Irvine, CA in two weeks beginning September 12th. Of course, you could also the opportunity to register for courses running in October, November and December and save your company some money while letting us teach you what you need to know.

CPT_SPT2011

We hope to see you sometime this fall.

August 07
Adding JavaScript code Behind a SharePoint 2010 Page

I have written this blog post to cover a few essential topics for those who are new to Javascript or just getting started using JavaScript in a SharePoint 2010 environment. In particular, I am going to walk through three popular techniques for adding JavaScript code behind a page in a SharePoint 2010 site. For example, let's say you are working the the following minimal site page named Demo1.aspx which links to a JavaScript file named Demo1.js.

<%@ Page MasterPageFile="~masterurl/default.master" %>
asp:Content runat="server" ContentPlaceHolderID="PlaceHolderAdditionalPageHead" >
<script src="Demo1.js" type="text/javascript"></script> </asp:Content>
<asp:Content ContentPlaceHolderId="PlaceHolderMain" runat="server">
<h2>JavaScript Demo</h2>
<div id="div1">boring default content</div>
</asp:Content>

By placing the script element shown above in a asp:Content control which has a ContentPlaceHolderID attribute value of PlaceHolderAdditionalPageHead, you can force the browser to download and load in the JavaScript code that has been added to Demo1.js. For our first example, imagine the source file named Demo1.js contains the following JavaScript code which has been written to access the div element with the id of div1 and to dynamically update its content.

var div1 = document.getElementById("Div1");
div1.innerHTML = "Hello World" 

You will find that this JavaScript code does not work as expected. The problem is that JavaScript code written at top-level scope (aka global scope) is executed as soon as it downloads before the page has fully loaded. More specifically, this code executes before the browser has parsed the HTML elements of the page which means that it executes too early to access an HTML element such div1 using the Document Object Model (DOM). This results in the JavaScript code experiencing a runtime error with a message such as 'div1' is null or not an object.

The important observation here is that you need to way to delay the execution of your JavaScript code until the browser has parsed and loaded the page's HTML elements so they are accessible through the DOM. As you will see, there are several different ways to accomplish this.

Understanding the window.load event and Why You Can't Use it

The first technique I will describe is actually a technique you cannot use. It involves registering an event handler for the window.onload event handler. While you might see this technique in JavaScript books for beginners, I just want to make sure you understand why you should avoid using it when working with SharePoint 2010.

DOM provides a onload event on the window object. The important concept (at least in theory) is that this event fires after the pages has loaded at a time when your code can access HTML elements through the DOM. If you were adding code behind a simple HTML page that was not running in a SharePoint environment, you can add your code to a function with a name such as OnPageLoad and assign that function to the window.onload event property so it fires at the right time.

window.onload = OnPageLoad;

function OnPageLoad() {
  var div1 = document.getElementById("Div1");
  div1.innerHTML = "Hello world";
}

Throughout the history of JavaScript programming, assigning a function to the window.onload event in this simple fashion has never really worked for anything except the most trivial of Web sites. The first problem is that the browser will not execute the window.onload event as early as you would like. After the page has loaded the HTML elements and made them accessible through the DOM, the browser continues to delay the firing of the window.onload event until the page has also completed downloading other resources including large graphic images and Adobe Flash files. This results in a delayed execution that is often unacceptable.

The second issue is that only one function can be assigned to the window.onload event at a time. It requires some tricky JavaScript programming to register multiple functions to execute when the window.onload event fires. There has been many a time when the JavaScript code written by one programmer has unintentionally unregistered the windows.onload event handler written by another. What's more, the built-in JavaScript code that's automatically added to SharePoint 2010 pages usually assigns its own function to the windows.onload event which will effectively unregister any function you have registered.

Suffice to say, the window.onload event works much better in theory than in practice and you should not be using this technique to control the execution of your JavaScript code behind pages in a SharePoint 2010 environment. Now that I have covered what you shouldn't do, let's move on and discuss what you should do.

There are three different techniques you can use in SharePoint 2010 to wire up your code so it executes at the correct point of time just after the HTML elements on the page have become accessible through the DOM. These three techniques rely on three different JavaScript libraries which are (1) ASP.NET AJAX, (2) The SharePoint 2010 JavaScript Class Library and (3) The jQuery Library. Each of these libraries serve to extend the basic functionality available through the JavaScript language and the DOM and each provides it own solution to this problem. Here is a list of the three different techniques I will discuss and the JavaScript library used by each one.

  • Using the Sys.Application.add_load method made available by ASP.NET AJAX
  • Using the _spBodyOnLoadFunctionNames.push method made available by the SharePoint 2010 JavaScript Class Library
  • Using the document.ready event handler made available by jQuery.

Yes, you have three different choices so you must decide which one to use on a case by case basis. In many scenarios, any of the three will work just fine. Therefore, I will provide a little more detail on each technique and demonstrate the required syntax.

Using Sys.Application.add_load

The ASP.NET AJAX library is built into ASP.NET 3.5 and is automatically made available behind all pages in a SharePoint 2010 farm. There is no need for you to explicitly link to any additional JavaScript files. You can simply call the Sys.Application.add_load method to register a function that will execute right after the HTML elements on the page have been made accessible through the DOM. Since we're leveraging the ASP.NET AJAX library, we can also leverage the convenience of $get function in place of document.getElementById as well.

Sys.Application.add_load(OnPageLoad);

function OnPageLoad() {
  $get("div1").innerHTML = "Hello from ASP.NET AJAX";
}

Note that you can call the add_load method more than once if you need to register multiple functions. The ASP.NET AJAX library will execute each one of them in the order that they have been registered.

Using _spBodyOnLoadFunctionNames.push

In addition to the ASP.NET AJAX library, pages in a SharePoint 2010 environment also load in a set of JavaScript files for a JavaScript library which goes by the name of the SharePoint 2010 JavaScript Class Library. This library contains quite a few JavaScript files including one named init.js which contains a global variable named _spBodyOnLoadFunctionNames. This variable references an array of string values containing a list of method names that will be executed after the body of the page has loaded. You can register a function by passing its name as a string value to the push method of the global _spBodyOnLoadFunctionNames variable.

_spBodyOnLoadFunctionNames.push("OnPageLoad");

function OnPageLoad() {
  $get("div1").innerHTML = "Hello from ASP.NET AJAX";
}

The underlying mechanics which make this technique work are different than using the Sys.Application.add_load. If you examine any of the master pages that ship with SharePoint 2010, you will see that Microsoft has added the following onload attribute to the body element.

<body onload="if (typeof(_spBodyOnLoadWrapper) != 'undefined') _spBodyOnLoadWrapper();" >

As you can see, the onload attribute has been configured with JavaScript code which calls the _spBodyOnLoadWrapper method from init.js. It is this call to _spBodyOnLoadWrapper which triggers the execution of all the functions that have been registered with a call to _spBodyOnLoadFunctionNames.push.

And now it's time for a quick tangential comment. If you are like me and you observe how the onload attribute on the body element works, you might be temped to experiment with the onload attribute on other HTML elements inside the body such as a div element to see if you can achieve similar results. Don't waste your time. It doesn't work. While the browser executes JavaScript code in the onload attribute of the body, it will ignore any JavaScript you add to onload attributes in other HTML elements such as a div element or a span element.

Using The document.ready Event Handler

The third technique relies on The jQuery Library and it is the technique that most Web designers and developers prefer if they are already using the jQuery library in their client-side development with SharePoint 2010. Note that this technique is different from the first two since it depends upon a library that is not automatically integrated into the pages in a SharePoint site. Therefore, you must explicitly link to one or more jQuery sources files from a master page or from the individual pages that use jQuery. You can read Deploying jQuery Library Source Files with a Feature if you need help getting started on linking to the required jQuery source files.

Now let's examine the jQuery code required to modify the contents of a div element on a page.

$(document).ready(OnPageLoad);

function OnPageLoad() {
  $("#div1").html("Hello from jQuery");
}

As you can see, there is a call to the jQuery function passing the DOM-based document object to obtain a jQuery wrapper. The jQuery wrapper for the document exposes the ready method which you can call passing your function to register it to execute it at the right time. This code listing also demonstrates how to create a jQuery wrapper object for the div element with the id of div1 and how to modify its content using the html method.

The jQuery mantra is write less, do more. jQuery lives up to its mantra by allowing you to pass your function directly to the jQuery function without having to explicitly deal with the document object or the ready method. The following code does the exact same thing as the previous listing because it has the effect of registering the OnPageLoad function with the ready event of the document object.

$(OnPageLoad);

function OnPageLoad() {
  $("#div1").html("Hello from jQuery");
}

Of course, if your goal is to be admitted to the jQuery cool kids club you can take things one step further. You can get rid of the OnPageLoad method altogether and move its code into an anonymous function. The following code has the exact same effect as the previous two listings.

$(function(){
$("#div1").html("Hello from jQuery");
});

Yes. this code has the same effect, yet it's faster to write and looks much cooler to the jQuery in-crowd. It also produces the desired effect of becoming completely unreadable to neophytes.

Summary

So, now you have seen three different ways of adding JavaScript code behind pages in a SharePoint 2010 site . All three techniques rely on some type of function registration to ensure that code execution is delayed until after the browser has created the HTML elements in the body of the page and they are accessible through the DOM. My personal preference is to use the last technique because I like to use jQuery whenever I can. However, you can fall back on the other two techniques in any scenario where the jQuery library is not being used.

July 26
Understanding the _spPageContextInfo variable in SharePoint 2010

For a while now I have been using the _spPageContextInfo variable in the JavaScript code I write for SharePoint 2010. I first learned about this variable when I saw in sample JavaScript code that others had blogged about. For example, what should you do when you need to parse together an URL to a page or a Web service that is relative to the root of the hosting Web application. You can easily discover the relative path between the current site collection and the root of the hosting Web application using a property named siteServerRelativeUrl which is available through the _spPageContextInfo variable.

var siteCollectionUrl = _spPageContextInfo.siteServerRelativeUrl;

While I have certainly appreciated the functionality of the _spPageContextInfo variable, my curiosity began to grow wondering why it works the way it does. I searched for information on Bing and Google trying to find an official Microsoft reference or any more information on this variable. However, all I was able to find was more examples of using the _spPageContextInfo variable in code samples but real insight into when and how this variable gets created and what information you can expect to find inside it. That led me to doing a little digging to find out how it really works behind the scenes.

As it turns out, the _spPageContextInfo variable is added to pages in SharePoint 2010 by the SPWebPartManager control. What's nice is that Microsoft has added the SPWebPartManager control to every Master Page that they deploy inside the Master Page Gallery including v4.master, minimal.master, default.master as well as all the master pages that are included as part of the SharePoint Server 2010 publishing features such as nightandday.master and BlueBand.master. That means you can expect the _spPageContextInfo variable to be included on any SharePoint 2010 page except in rare cases such as when the page is hardcoded to a legacy master page in the _layouts directory or when the page is using a custom master page that has not been implemented correctly because it does not include the SPWebPartManager control.

The SPWebPartManager control adds a client-side script block to each page with code which creates a JavaScript object and initializes it with a specific set of property values. This object is assigned to a global variable named _spPageContextInfo as shown in the following code fragment.

var _spPageContextInfo = {
   webServerRelativeUrl: "\u002fsites\u002fTestSite",
   webLanguage: 1033,
   currentLanguage: 1033,
   webUIVersion: 4,
   userId: 24,
   alertsEnabled: false,
   siteServerRelativeUrl: "\u002fsites\u002fTestSite",
   allowSilverlightPrompt: 'True' };

A key point is that the SPWebPartManager control uses the current SPSite and SPWeb objects on the Web server to query important property values and to make them available to client-side JavaScript code. This greatly simplifies writing JavaScript code when you need to create relative URLs or when you need to discover the current user's ID in the user information list for the current site collection. In general the use of the _spPageContextInfo variable is important to anyone writing JavaScript code that needs to access entry point functions exposed the SharePoint 2010 JavaScript libraries.

You will find that some page requests result in a JavaScript object behind the _spPageContextInfo variable that has more properties than other requests. For example, if the incoming request is processed inside the scope of a list such as the case when accessing AllItem.aspx, then the object behind the _spPageContextInfo variable will also provide a pageListId property containing the GUID-based ID for that list. If the incoming request targets a page stored inside a document library such as a Wiki page or a Publishing page, then the object behind the _spPageContextInfo variable will provide an additional property named pageItemId which provides the integer-based ID used to track the document for the current page in the containing document library.

Of course, if you really want to know the naked underlying truth about the _spPageContetInfo variable, you can simply inspect the implementation of a private method named SharePointClientJs_Register which the SPWebPartManager class uses to generate the client-side script block. Here's a screenshot of that method implementation as seen when inspecting the Microsoft.SharePoint.dll assembly with .NET Reflector.

SPPageContextInfo

Did you really just read through that entire block of code? What are you, some kind of inverted coding geek? Or maybe just someone that wants to learn SharePoint 2010 inside and out.

July 20
Using a customized favicon.ico file in SharePoint 2010

SharePoint 2010 introduces the SPShortcutIcon control which has been designed to add a favorites icon in the browser. For example, the standard SharePoint 2010 master page named v4.master uses the SPShortcutIcon control to to configure a favicon.ico file which is deployed in the IMAGES folder inside the SharePointRoot directory.

<SharePoint:SPShortcutIcon runat="server" IconUrl="/_layouts/images/favicon.ico" />

This control tag is what configures all unbranded sites in SharePoint 2010 with the standard three-headed orange favorites icon that screams "Look at me. I am a SharePoint site!".

Favicon

Now imagine your are creating a custom branding solution for SharePoint 2010 and one of your requirements is to replace the out-of-box favorites icon with one of your own. Also imagine you have decided to deploy the favicon.ico file with your custom favorites icon to the Style Library of each participating site collection instead of deploying the file to the IMAGES folder inside the SharePointRoot directory. This design approach will provide greater deployment flexibility in a branding solution because you don't need to update the file system of the front end Web server.

Once you have added the custom version of the favicon.ico file into a location within the Style Library, you then configure your custom master page with an instance of the SPSharePointIcon control that looks like this.

<SharePoint:SPShortcutIcon runat="server" IconUrl="/Style Library/Wingtip/Images/favicon.ico" />

You find that this control tag works in some cases but not in others. More specifically, in your testing you find that this control tag only works when used in site collections that have been created at the root of their hosting Web application. For example, it works fine when the URL to the root of the site collection looks like this.

http://intranet.wingtip.com

However, it doesn't work if the the URL to the root of the site collection looks like this.

http://intranet.wingtip.com/sites/sales

The problem with the control tag you have just seen is that the favicon.ico file must be configured with a path relative to the root of the Web application. At this point your intuition might tell you that you can use an $SPUrl expression in the SPShortcutIcon control just like you do in other SharePoint controls. For example, you can use an $SPUrl expression along with the dynamic ~SiteCollection token for the name attribute of the CssRegistration control inside a custom master page to link to a CSS file inside the Style Library with a path relative to the root of the current Web application.

<SharePoint:CssRegistration 
name="<% $SPUrl:~SiteCollection/Style Library/Wingtip/main.css %>"
After="corev4.css"
runat="server" />

Given the popularity of SharePoint branding techniques which use an $SPUrl expression containing the dynamic ~SiteCollection token, you might make a reasonable (yet incorrect) assumption that you can use the same approach when configuring the SPShortcutIcon control. For example, you might try and configure a control tag based on the SPShortcutIcon control like this.

<SharePoint:SPShortcutIcon 
IconUrl="<% $SPUrl:~SiteCollection/Style Library/Wingtip/Images/favicon.ico %>"
runat="server" />

Unfortunately, this technique not yield the desired results. However, it's worse then that. This control tag causes a runtime error and if used in a custom master page it will bring down any site that uses it. The core problem we have here involves a .NET runtime exception caused by a type mismatch. An $SPUrl expression returns a value of type System.String type while the IconUrl property of the SPShortcutIcon control expects a value of type System.Uri. Here is a quick look at the SPShortcutIcon control as seen through the object browser in Visual Studio 2010.

IconUrl

At the end of the day, it's best just to abandon the SPShotcutIcon control for our scenario because it cannot give us what we want. After all, Microsoft really only designed and tested this control to work with favicon.ico files deployed inside the SharePointRoot directory which can always be configured with static paths which do not change across sites or site collections.

The good news creating the same output that is created by the SPShotcutIcon control isn't rocket science. All you really need to do is create a link element with a rel attribute and an href attribute and add it to the head section of the hosting HTML page.

<link rel='shortcut icon' 
href='/sites/sales/Style Library/Wingtip/Images/favicon.ico' />

However, you don't want to add text like this to a custom master page because then you would be hard-coding it to only work inside a single site collection. Instead, you can add a set of ASP.NET literal controls along with an $SPUrl expression that includes the dynamic ~SiteCollection token. Here is a working sample that was first introduced to the SharePoint community in a blog by Joel Jeffery in November of last year.

<asp:literal runat="server" Text="&lt;link rel='shortcut icon' href='"/>
  <asp:literal runat="server" Text="<% $SPUrl:~SiteCollection/Style Library/Wingtip/Images/favicon.ico %>"/>
<asp:literal runat="server" Text="' /&gt;"/>

As it turns out, you can get rid of the asp:literal controls and just go with the $SPUrl expression which works just fine.

<link rel='shortcut icon' 
href='<% $SPUrl:~SiteCollection/Style Library/Wingtip/Images/favicon.ico %>' />

By using this technique to add a custom favorites icon, you can create a custom branding solution that works on any site collection in any SharePoint 2010 farm regardless of whether it has been created at the root of the hosting Web application.

CustomFavicon

July 14
Deploying jQuery Library Source Files with a Feature

When we completed our SharePoint 2010 development book earlier this year, I needed a break from the same old stuff. I started looking for something new and different to sink my teeth into. Last year my writing and research focused almost exclusively on server-side development techniques for SharePoint 2010. It occurred to me that a great way to refocus my passion and my research was diving into the client-side aspects of SharePoint 2010. I started by learning the ins and outs of how SharePoint 2010 integrates master pages and CSS rules. Before too long I had also become addicted to writing JavaScript code for SharePoint 2010 and starting to integrate the jQuery library. It's been a great outlet because there is so much to learn.

When you are writing JavaScript behind a page in a SharePoint 2010 site and you want to leverage the jQuery library, you must add the appropriate script links to download one or more jQuery libraries. In some scenarios it makes sense to link to a copy of the source code for the core jQuery library that has been published on a content delivery network (CDN) such as the ones sponsored by Microsoft and Google. For example, you can link to the core jQuery library source file on the Microsoft CDN by placing the following script tag into the head section of a master page or into a placeholder control with a ContentPlaceHoldserID attribute of PlaceHolderAdditonalPageHead.

<script 
language="javascript"  
src="http://ajax.aspnetcdn.com/ajax/jQuery/jquery-1.5.1.min.js"
type="text/javascript" > </script>

Likewise, you can link to the core jQuery library source file on the Google CDN with a script tag that looks like this.

<script   
language="javascript"  
src="https://ajax.googleapis.com/ajax/libs/jquery/1.5.1/jquery.min.js"
type="text/javascript" > </script>

While linking to a jQuery source file published on a CDN is often the best technique for an Internet-facing site, there are some scenarios where it might not be appropriate or it just doesn't work at all. For example, imagine you need the jQuery source code to be accessible from a virtual machine that doesn't have access to the Internet. Possibly in another scenario you are working with a beta version of one of the jQuery libraries or a jQuery plug-in that is not available on a public CDN. You could also find yourself working in a network environment with security restrictions and/or client-side caching restrictions that make it impractical or impossible to link to source code on a public CDN. In times like this, you must find a way to deploy the required jQuery library source code into the target SharePoint environment using a SharePoint solution created with Visual Studio 2010.

While you could create a SharePoint solution to deploy jQuery source files somewhere in the SharePointRoot folder such as the LAYOUTS directory, that would prevent the possibility of deploying your SharePoint solution as a sandboxed solution. This, in turn, would prevent you from deploying your SharePoint solution in a hosted environment such as Office 365. A modern, more flexible approach involves deploying jQuery source files and their dependencies using a Module and a Feature scoped at site collection level. Here are the basic steps to get started in Visual Studio 2010.

  1. Create a new project named MyFirstjQuertyProject using the project template named Empty SharePoint Project.
  2. Create a new feature named MainSite and set the feature scope to a value of Site so that the feature activates at site collection.
  3. Create a new Module named jQuerySource. This Module should be automatically associated with the MainSite feature.
  4. Add the required jQuery source files the new Module.
  5. Manually edit the Module's elements.xml file to modify the Url attribute of each File element to provision each jQuery source file within a folder named js. After you finish this step, your elements.xml file should look like this.
<Elements xmlns="http://schemas.microsoft.com/sharepoint/">
<Module Name="jQuerySource">
 
<File Path="jQuerySource\js\jquery-1.5.1.min.js"
           Url="js/jquery-1.5.1.min.js" />

     <File Path="jQuerySource\js\jquery-ui-1.8.13.custom.min.js"
           Url="js/jquery-ui-1.8.13.custom.min.js" />
</Module>
</Elements>

An important point is that when deploying this SharePoint solution as a farm solution, all the jQuery source files will be ghosted which means they will load from the file system of the front-end Web Server. Therefore, this technique using a Module provides the same level of performance as deploying files into the LAYOUTS directory. However, this technique provides the flexibility of deployment as a sandboxed solution while deployment to the LAYOUTS directory does not.

When you deploy this SharePoint solution and activate the MainSite feature in a specific site collection, it will provision each jQuery source file inside the root folder of the top-level site in a child folder named js. That means you can now link to these jQuery source files using the SharePoint:ScriptLink control.

<SharePoint:ScriptLink
runat="server"
Defer="false"
Name="~sitecollection/js/jquery-1.5.1.min.js"/>

<SharePoint:ScriptLink
runat="server"
Defer="false"
Name="~sitecollection/js/jquery-ui-1.8.13.custom.min.js"/>

As you can see, the SharePoint:ScriptLink control provides a Name attribute for you to provide the path to the target JavaScript file. The Name attribute of the SharePoint:ScriptLink control directly supports the dynamic ~sitecollection token which makes it easy to create a link for pages at any offset path from the root of the site collection. You should also observe that the Defer attribute has been assigned a value of false so that the target jQuery source file is downloaded synchronously which means it can be used before the page content is shown to the user.

I created a downloadable Visual Studio 2010 sample project named My First jQuery Project and posted it in our Critical Path Training Members section. This sample SharePoint solution provisions the core jQuery library using the technique described here. It also provisions the jQuery UI library and the files for a custom jQuery theme.

MyFirstjQueryProject

The My First jQuery Project project also provisions a single demonstration page named jQueryDemo1.aspx which uses the jQuery UI library to create an According widget. This means the page is also required to link to a CSS file containing a jQuery UI theme using the CssRegistration control. Note that the name attribute of the CssRegistration control does not directly support the SharePoint's dynamic tokens so you must configure the name attribute value with an $SPUrl expression which contains the dynamic ~SiteCollection token.

<SharePoint:CssRegistration 
name="<% $SPUrl:~SiteCollection/css/TedTheDramaQueen/jquery-ui-1.8.13.custom.css%>"
After="corev4.css"
runat="server" />

<SharePoint:ScriptLink
runat="server"
Defer="false"
Name="~sitecollection/js/jquery-1.5.1.min.js"/>

<SharePoint:ScriptLink
runat="server"
Defer="false"
Name="~sitecollection/js/jquery-ui-1.8.13.custom.min.js"/>

That's all the tough stuff. The body of the page named jQueryDemo1.aspx contains some HTML that is preformatted to work with the Accordion widget. The JavaScript code inside jQueryDemo1.js could not be any simpler.

$(function () {
  $("#rockstars").accordion({ header: "h3" });
});

While I know it is quite possible that you have previously seen a demo of the jQuery UI Accordion widget. But have you ever seen a demo based on dead rock stars? Probably not. I am hoping this demo will prove to be a SharePoint industry breakthrough in code samples.

Untitled

Here is a link to a live version of the same jQuery demo running on my blog site.

February 18
Support for Inside SharePoint 2010

We have finally completed our work on Inside SharePoint 2010. We shipped the final PDF layout to the printers last week. Thanks to my writing partners Scot, AC and Dave and thanks to all the production folks at O'Reilly. Sorry it took so long. I am relatively certain that each and every delay along the way was entirely my fault.

InsideSharePoint2010

Download The Sample Code

All the sample code for this book is contained in a single ZIP archive named InsideSharePoint2010.zip. Inside this ZIP archive there's a separate folder for each of the 15 chapters. These folders contain PowerShell scripts and sample projects that we created with Visual Studio 2010. We are including 64 sample projects in all. We encourage you to get a VM for SharePoint 2010 development so you can open these sample projects and test them out. After all, there's no better feeling of confidence than knowing you can hit the F5 key and see the stuff actually working.

Here's the URL to the official support page for this book on the O'Reilly site.

http://oreilly.com/catalog/9780735627468/

Here's the URL to the somewhat-less-official support page on the Critical Path Training site.

http://www.criticalpathtraining.com/Books/InsideSharePoint2010

Build a VM for SharePoint 2010 Development

In order to open and test out the sample projects, you will need a SharePoint 2010 development environment. On the Members page of the Critical Path Training website, we have posted a document named the SharePoint Server 2010 RTM Virtual Machine Setup Guide. The document contains detailed, step-by-step instructions you can use to build a SharePoint development VM from the ground up with Windows Server 2008 R2, Active Directory Domain Services, SQL Server 2008 R2, SharePoint Server 2010, SharePoint Designer, Office 2010 and Visual Studio 2010. The VM setup guide gives you the option of installing the required Microsoft software by using free trial keys or by using your own product keys which will prevent your VM from expiring.

Why should you build a VM using our setup guide? One reason is that our samples will run more smoothly because your VM will have the same machine name and domain name and the same URLs as the VMs we used when we write and tested the samples for each chapter. A second reason is that it provides a very robust development environment that will allow you to integrate your development efforts with some of the more advanced features and services of SharePoint Server 2010.

 

 About this blog

 
About this blog
Welcome to SharePoint Blogs. Use this space to provide a ;.;.;.message about this blog or blog authors. To edit this content, select "Edit Page" from the "Site Actions" menu.

© Copyright 2011 Ted Pattison.  |  All Rights Reserved
LOGIN