Standard repeaters are a great all-in-one web part for displaying content, but sometimes you need finer control over the output. This post will show you how to create a content filter for news articles, so that content can be filtered by the categories: Press Releases, Product News and Partner News.
How it works
Content will be filtered by dynamically changing the Where condition of the data source depending on the query string parameter of the URL. E.g. if the page URL is /News?Category=PressRelease, only articles tagged as a Press Release will be shown. Category buttons will be used to reload the page with a specific query string parameter.
Category selection
First of all, add a method for editors to tag content. Open the News Document type in Site Manager and go to the Fields tab. Add a new field with the following properties:
New field properties | |
---|---|
Column name: | Category |
Attribute type: | Text |
Attribute size: | 300 |
Allow empty value: | Yes |
Field caption: | Category |
Form control type: | Input |
Form control: | Drop-down list |
Data source: | PressRelease; Press Release ProductNews;Product News PartnerNews;Partner News |
You can now select one of these options from the Form tab when editing or creating a news article.
Design set up
In the Design tab of the news listing page, add three separate web parts: Documents Data Source, Filter and a Basic Repeater. Link them together using the following settings:
Documents data source settings | |
---|---|
Web part control ID: | DocumentsDataSource |
Filter name: | CategoryFilter |
Path: | /News% |
Document types: | CMS.News |
Filter settings | |
---|---|
Filter name: | CategoryFilter |
Filter control path: | ~/Filters/CategoryFilter.ascx (we’ll create this file next) |
Basic Repeater settings | |
---|---|
Data source name: | DocumentsDataSource (The ID of the data source control) |
Transformation name: | CorporateSite.Transformations.NewsList (I’m building this in to the default Corporate site installation) |
Writing the filter control
Create a new folder on the server called Filters and add a new ASP control file inside named CategoryFilter.ascx. Within this file create an unordered HTML list with a CSS selector of ‘buttonGroup’ containing three list elements. Add an ASP Link Button to each list element changing the ID’s and OnClick properties relative to the button. The code should look like this:
<%@ Control Language="C#" AutoEventWireup="true" CodeFile="CategoryFilter.ascx.cs" Inherits="CategoryFilter" %>
<ul class="buttonGroup">
<li>
<asp:LinkButton ID="PressReleaseButton" runat="server" EnableViewState="false" OnClick="PressReleaseButton_Click" Text="Press Releases" />
</li>
<li>
<asp:LinkButton ID="ProductNewsButton" runat="server" EnableViewState="false" OnClick="ProductNewsButton_Click" Text="Product News" />
</li>
<li>
<asp:LinkButton ID="PartnerNewsButton" runat="server" EnableViewState="false" OnClick="PartnerNewsButton_Click" Text="Partner News" />
</li>
</ul>
The code behind file
Create a new code behind file for the above page, this must inherit the CMSAbstractBaseFilterControl. On page load, this will set the Where condition based on the URL query string parameter.
The code will also manage the click functions, which will simply reload the page with a different query string. (This doesn’t necessarily need to be set by the filter control, you could just add links in your page instead with different query strings.
using System;
using System.Data;
using System.Configuration;
using System.Collections;
using System.Web;
using System.Web.Security;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Web.UI.WebControls.WebParts;
using System.Web.UI.HtmlControls;
using CMS.GlobalHelper;
using CMS.CMSHelper;
using CMS.PortalControls;
using CMS.Controls;
public partial class CategoryFilter : CMSAbstractBaseFilterControl
{
protected void Page_Load(object sender, EventArgs e)
{
string where = this.WhereCondition;
string url = URLHelper.RawUrl;
string urlParam = URLHelper.GetUrlParameter(url, "category");
if (urlParam != "")
{
switch (urlParam)
{
case "PressRelease":
where += " Category='PressRelease' ";
break;
case "ProductNews":
where += " Category='ProductNews' ";
break;
case "PartnerNews":
where += " Category='PartnerNews' ";
break;
default:
where += "";
break;
}
}
if (where != "")
{
// Set where condition
this.WhereCondition = where;
}
// Invoke changed event
this.RaiseOnFilterChanged();
}
string Cat = "";
protected void PressReleaseButton_Click(object sender, EventArgs e)
{
Cat = "PressRelease";
redirectPage();
}
protected void ProductNewsButton_Click(object sender, EventArgs e)
{
Cat = "ProductNews";
redirectPage();
}
protected void PartnerNewsButton_Click(object sender, EventArgs e)
{
Cat = "PartnerNews";
redirectPage();
}
protected void redirectPage()
{
// Grab current URL
string url = URLHelper.RawUrl;
// Remove existing query parameters
url = URLHelper.RemoveParameterFromUrl(url, "category");
// Add new query parameters
url = URLHelper.AddParameterToUrl(url, "category", Cat);
// Redirect with new query parameters
URLHelper.Redirect(url);
}
}
Button styles
Add this CSS to create simple inline buttons that butt up against each other in a group:
.buttonGroup{
margin: 0;
padding: 0;
}
.buttonGroup li{
border: 1px solid #CCCCCC;
background: #F7F7F7;
display: inline;
list-style: none;
margin: 0;
padding: 4px 8px;
}
.buttonGroup li a{
text-decoration: none;
color: #66ADDF;
}
End result
All set! After setting a category for existing articles, clicking on a filter button will reload the page, adjusting the Where condition to display only the articles tagged with the category you selected.
Note: This is an adaptation of Kentico’s suggested custom filter in the Knowledge Base at devnet.kentico.com