Web slices and Accelerators with Kentico CMS

   —   
This post will show you how you can use the new features of Internet Explorer 8, called Web slices and Accelerators with Kentico CMS.
Hi everybody,

Long time and almost no posts, shame on me! I was very busy with development of the new version and other things. It should be better now in June. I have recently launched my new sample web site for all the blog post examples (unleash.kentico.com) where I will show you the real-time examples of what I am writing here, so here is the first one.

Internet Explorer came with two very nice features (among all the others), called Web slices and Accelerators. I will show you how you can use them with Kentico CMS, and give you the exact components to do the same thing as I do.

Web slices

Web slice is a portion of the page which can be displayed separately in the web browser. Something like the visual RSS feed, I would say. You can find more details about it here: http://msdn.microsoft.com/en-us/library/cc848871(VS.85).aspx

As you can see, the slice is just some specific container for the content that can be used by the browser to get the content. Sounds familiar? Yes, it sounds like the Web part container, and this is exactly how we will do that.

So go to the Site manager and create a new web part container:

Display name: Web slice (for IE8)
Code name: WebSlice

Text before:

<div class="hslice" id="{%WebPartControlID%}{%ZoneID%}_slice">
 <div class="entry-title" style="display: none">{%ContainerTitle%}</div>
 <div class="entry-content">


Text after:

 </div>
</div>


And that's it. Now you can go straight to the web part properties and select the Web slice container for the web part (or even for the zone, the code can use both). If you do that and go to the live site (not preview, not CMSDesk, but strictly live site), you will get something similar to this:

http://unleash.kentico.com/Examples/Web-parts/Web-slices-and-Search-acccelerator.aspx

Web slice in the UI Web slice in the browser

There is really nothing more in it, simple isn't it? The good thing is that you can do the same with web part zone, so you can have the web slice done very easily, built from several web parts.

Accelerators

Accelerator is basically a service which can use current context of the user as a parameter. The context can be selected text, it can be current document, etc.

You can find more about accelerators here: http://msdn.microsoft.com/en-us/library/cc287851(VS.85).aspx

The main thing I can think of regarding any web site is the accelerator for search, so I will provide you with one that can take advantage of our search, allowing the users to search through your web site just by selecting the text and selecting the accelerator for your search.

This one is actually a web part which shows you two things:
  • First is how to produce an XML response from the web part without the need to have special page for it.
  • The second one is the actual accelerator.

Web part ASPX code is very simple:

<%@ Control Language="C#" AutoEventWireup="true" CodeFile="SearchAccelerator.ascx.cs" Inherits="CMSWebParts_SmartSearch_SearchAccelerator" %>
<asp:Button runat="server" ID="btnAcc" EnableViewState="false" />


While the code behind does everything:

using System;
using System.Collections;
using System.Configuration;
using System.Data;
using System.Web;
using System.Web.Security;
using System.Web.UI;
using System.Web.UI.HtmlControls;
using System.Web.UI.WebControls;
using System.Web.UI.WebControls.WebParts;

using CMS.PortalControls;
using CMS.GlobalHelper;
using CMS.Controls;
using CMS.ISearchEngine;

public partial class CMSWebParts_SmartSearch_SearchAccelerator : CMSAbstractWebPart
{
    #region "Variables"

    // Result page url
    protected string mResultPageUrl = UrlHelper.CurrentURL;

    #endregion


    #region "Properties"

    /// <summary>
    /// Gets or sets the accelerator description
    /// </summary>
    public string AcceleratorDescription
    {
        get
        {
            return DataHelper.GetNotEmpty(GetValue("AcceleratorDescription"), ResHelper.GetString("srch.accelerator.description"));
        }
        set
        {
            SetValue("AcceleratorDescription", value);
        }
    }


    /// <summary>
    /// Gets or sets the accelerator name
    /// </summary>
    public string AcceleratorName
    {
        get
        {
            return DataHelper.GetNotEmpty(GetValue("AcceleratorName"), ResHelper.GetString("srch.accelerator.name"));
        }
        set
        {
            SetValue("AcceleratorName", value);
        }
    }


    /// <summary>
    /// Gets or sets the accelerator button text
    /// </summary>
    public string AcceleratorButtonText
    {
        get
        {
            return DataHelper.GetNotEmpty(GetValue("AcceleratorButtonText"), ResHelper.GetString("srch.accelerator.addaccelerator"));
        }
        set
        {
            SetValue("AcceleratorButtonText", value);
        }
    }


    /// <summary>
    /// Gets or sets the search results page URL
    /// </summary>
    public string SearchResultsPageUrl
    {
        get
        {
            return DataHelper.GetNotEmpty(GetValue("SearchResultsPageUrl"), mResultPageUrl);
        }
        set
        {
            SetValue("SearchResultsPageUrl", value);
            mResultPageUrl = value;
        }
    }

   
    /// <summary>
    ///  Gets or sets the Search mode
    /// </summary>
    public SearchModeEnum SearchMode
    {
        get
        {
            return CMSSearchDialog.GetSearchMode(ValidationHelper.GetString(GetValue("SearchMode"), ""));
        }
        set
        {
            SetValue("SearchMode", value.ToString());
        }
    }

    #endregion


    #region "Methods"

    /// <summary>
    /// Content loaded event handler.
    /// </summary>
    public override void OnContentLoaded()
    {
        base.OnContentLoaded();

        // If the accelerator request matches the ID of the control,
        if (QueryHelper.GetString("getsearchaccelerator", "") == this.ClientID)
        {
            GetServiceDefinition();
        }

        SetupControl();
    }


    /// <summary>
    /// Initializes the control properties.
    /// </summary>
    protected void SetupControl()
    {
        if (this.StopProcessing)
        {
            return;
        }
        else
        {
            this.btnAcc.Text = this.AcceleratorButtonText;

            string serviceUrl = UrlHelper.GetAbsoluteUrl(UrlHelper.AddParameterToUrl(UrlHelper.CurrentURL, "getsearchaccelerator", this.ClientID));

            this.btnAcc.OnClientClick = "window.external.AddService('" + serviceUrl + "'); return false;";
        }
    }


    /// <summary>
    /// Gets the service definition for the accelerator
    /// </summary>
    public void GetServiceDefinition()
    {
        // Create a new XML response
        Response.Clear();
        Response.ContentType = "text/xml";

        string appUrl = UrlHelper.GetApplicationUrl();

        // Write acelerator definition
        Response.Write(
            @"<?xml version=""1.0"" encoding=""UTF-8"" ?>
                <os:openServiceDescription xmlns:os=""
http://www.microsoft.com/schemas/openservicedescription/1.0"">
                    <os:homepageUrl>" + appUrl + @"</os:homepageUrl>
                    <os:display>
                        <os:name>" + this.AcceleratorName + @"</os:name>
                        <os:icon>" + appUrl + @"/favicon.ico</os:icon>
                        <os:description>" + this.AcceleratorDescription + @"</os:description>
                    </os:display>
                    <os:activity category=""Search"">
                        <os:activityAction context=""selection"">
                            <os:execute action=""" + UrlHelper.GetAbsoluteUrl(this.SearchResultsPageUrl) + @""">
&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&; &&s:parameter name=&quo&;&quo&;searchtext&quo&;&quo&; value=&quo&;&quo&;{selection}&quo&;&quo&; type=&quo&;&quo&;text&quo&;&quo&; /&&br /> &&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&; &&s:parameter name=&quo&;&quo&;searchmode&quo&;&quo&; value=&quo&;&quo&;&quo&; + this.SearchMode.ToString() + @&quo&;&quo&;&quo&; /&&br /> &&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&; &&os:execute&&br /> &&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&; &&os:activityAction&&br /> &&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&; &&os:activity&&br /> &&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&;&&; &&os:openServiceDescription&");&br /> &nbs&p;nbs&p;nbs&p;nbs&p;nbs&p;nbs&p;nbs& /> &nbs&p;nbs&p;nbs&p;nbs&p;nbs&p;nbs&p;nbs&sponse.End();
&nbs&p;nbs&p;nbs&/span>

    #endregion
}



You can see that the most of the code are just properties. The most important thing is the setup and GetServiceDefinition. In a standard view, the web part displays the button, which attempts to register the accelerator. It basically adds the query parameter ?getsearchaccelerator=<id> so on the request for the accelerator definition, the GetServiceDefinition takes over and renders the XML as soon as it can and ends the request.

So we have a single page, that can generate both standard live content and the XML for the accelerator. Nice, isn't it? In our case, the accelerator calls the search page with the same parameters as does our Search box so if you select some text and activate the accelerator, you are redirected straight to the Search page with the selected text as the search expression. Just try that on the live site:

http://unleash.kentico.com/Examples/Web-parts/Web-slices-and-Search-acccelerator.aspx

Accelerator web part Accelerator option

Here is the package for the search accelerator web part: cms_webpart_SearchAccelerator_20090602_1713.zip 

Just import it to your solution and try for yourselves.

And that's it, I am done with this post. One last good news: Both these options will be in the upcoming version 4.1

See you at the next post and definitely let me and others know if you create something cool with the accelerators or web slices.

Share this article on   LinkedIn

Martin Hejtmanek

Hi, I am the CTO of Kentico and I will be constantly providing you the information about current development process and other interesting technical things you might want to know about Kentico.

Comments