Using the Ext Scheduler, Part 1

Fellow developer Mats Bryntse has kindly asked me to review his Ext Scheduler component, and this is the first of a series of articles where I talk about the Ext Scheduler while I use it to build a hypothetical conference room reservations interface.

The goal for this first article is to build a scheduler that displays the reservations that exist for a number of conference rooms.  In future articles I will be adding the ability to create, edit and remove reservations.

At the end of this phase, we will have a scheduler that looks like the following screenshot:

The business domain model the scheduler is based on

The scheduler component is based on a business domain model consisting of resources and events. You can think of a resource as an entity that can be assigned domain events.  People, places, tasks, classes and cars are real-life examples of resources.  Meetings, appointments and other activities are examples of events.

In this model, there is a multiplicity relationship where a resource can be assigned one or more business domain events:

Visually, the scheduler can be thought of as two views:

  • A resources view. This view displays a list of business domain entities or “resources” to which business domain events can be assigned.  It can include any number of properties of the resources, shown in one or more columns of the scheduler.
  • A time view. This view consists of a number of columns representing a time interval, and displays the business domain events occurring within this interval for the given resources.  The time columns adhere to one of various precision levels: hour, day, week, month, year, or your own.

These are the views in our example:

The scheduler’s API

As a system, the scheduler can be roughly divided into the following discrete parts:

  • A grid panel that serves as the container where the information is displayed.
  • A “resource” data store, which provides the information consumed by the resources view, for example, people, tasks, classes or places.
  • An “event” data store, which provides the data for the time view, for example, events’ start date, duration, name and description.
  • An autoViews array containing one or more objects, each defining the configuration of a time view that the scheduler will use (Yes, you can interchange time views) .  A time view’s configuration includes the precision used (hour, day, week or month), the number of days to display, a renderer function used to display the event information within the view,  and an optional “behavior” object where you can put code specific to the view type.
  • A number of templates and plugins that provide features such as showing event tooltips, drag and drop, and event edition.

The scheduler API’s is currently a moving target, but this is something to be expected of a very young component under active development.

Now that we know the main concepts, let’s see what we can do with the scheduler.

Setting up the Ext Scheduler

Setting up the scheduler involves adding references to its JavaScript and css sources. You can obtain the Ext Scheduler at http://www.ext-scheduler.com.  While the JavaScript source currently resides in a single file, the styles come in files that are named after the piece of functionality they address. You will only need to include the styles related to the scheduler features you will use in your application. In my example, I use the following:

<!-- Scheduler includes -->
<link href="ext-sch/css/sch.schedulerpanel.css" rel="stylesheet" type="text/css" />
<link href="ext-sch/css/sch.plugins.resize.css" rel="stylesheet" type="text/css" />
<link href="ext-sch/css/sch.plugins.common.css" rel="stylesheet" type="text/css" />
<link href="ext-sch/css/sch.event.css" rel="stylesheet" type="text/css" />
<script src="ext-sch/js/Scheduler/sch-all-eval.js" type="text/javascript" ></script>

I will also use a few extra classes to change the look of the rendered events:


<style type="text/css">
 .sch-event     {
 background:url(ext3/images/default/grid/grid-blue-hd.gif) repeat-x;

border-color:#6699cc;

border-style:solid;

color:#1C417C;

cursor:pointer;

text-align: center;

top:0px;

}

.sch-event-inner    {        padding:1px;                   }

.sch-event-selected     {        border-color:#3366cc !important;        border-width:1px !important;    }

div.sch-event:hover     {        border-color:#3366cc;    }

</style>

These classes will give me a nice gradient for the event background, as well as different border colors for the hover and selected states.  This is how an event looks when rendered:

Configuring the resource and event data stores

The resource store contains the conference rooms id’s and names. I’m using data from a local array to keep my example simple:

// Resource store
ConfRooms.confRoomStore = new Ext.data.JsonStore({
fields: ['Id', 'name'],
data: [        { Id: '1', name: 'Conference Room A' },
        { Id: '2', name: 'Conference Room B' },
        { Id: '3', name: 'Conference Room C' },
       { Id: '4', name: 'Conference Room D' },
       { Id: '5', name: 'Conference Room E' }
]});

The event store in turn contains the reservations that exist for the available conference rooms:

// Event store
ConfRooms.reservationsStore = new Ext.data.JsonStore({
	url: 'reservations.aspx',
	autoLoad: true,
	root: 'records',
	idProperty: 'Id',
	fields: [         ?
                 // Mandatory
		 {name: 'Id' },
		 { name: 'StartDate', type: 'date', dateFormat: 'Y-m-d G:i:s' },
		 { name: 'EndDate', type: 'date', dateFormat: 'Y-m-d G:i:s' },
		 { name: 'ResourceId', type: 'string', mapping: 'RoomId' },
		// Application-specific
		 {name: 'ReservedTo', type: 'string', mapping: 'ReservedTo' },
		 { name: 'Description', type: 'string', mapping: 'Description' }    ],
	writer: new Ext.data.JsonWriter({autoSave: false,encode: true    })
});

Some fields are mandatory in the event store: Id, StartDate, EndDate and ResourceId. The scheduler needs these fields in order to properly render the events. In particular, the relationship between resources and events is expressed in the scheduler’s API via the ResourceId property of an event, which maps to the Id of a resource. (A conference room in this example) The rest of the fields are application-specific. For this example I use a couple of application-specific fields, but you can use any fields your business domain requires.

Creating the scheduler panel and configuring the time view

To define the start and end date of my time view, I will use hard-coded values:

ConfRooms.start = new Date(2009, 11, 16, 8, 00, 00);
ConfRooms.end = new Date(2009, 11, 16, 18, 00, 00);

Now I can go ahead and create the scheduler panel:

ConfRooms.sch = new Sch.SchedulerPanel({
	height: 300,  width: 800,
	renderTo: 'conf-rooms-1',
	title: 'Conference Room Reservations',
	trackMouseOver: false,
	stripeRows: true,
	store: ConfRooms.confRoomStore,
	eventStore: ConfRooms.reservationsStore,
	startParamName: 'StartDate',
	endParamName: 'EndDate',
	viewConfig: {forceFit: true },
	columns: [{ header: 'Room Name', sortable: true, width: 150, dataIndex: 'name' }],
	eventTemplate: new Ext.Template( '&lt;div id="{id}" style="width:{width}px;left:{leftOffset}px" class="sch-event {cls}"&gt;',  '&lt;div class="sch-event-inner"&gt;{text}&lt;/div&gt;',  '&lt;/div&gt;').compile(),
	tooltipTpl: new Ext.Template('&lt;div class="eventTip"&gt;',  '&lt;div&gt;&lt;b&gt;{Description}&lt;/b&gt;&lt;/div&gt;',  '&lt;div&gt;Reserved by: {ReservedTo}&lt;/div&gt;',  '&lt;/div&gt;').compile()  });  

In this source code, mixed with configuration options inherited from the GridPanel class, you will find options like the eventTemplate and tooltipTpl templates, which define the html markup for the events and event tooltips respectively. The startParamName and endParamName options, although not used in the example, map the start and end dates of the time view to event store parameters. Finally, I will configure the view I want to use:

ConfRooms.sch.setView(ConfRooms.start, ConfRooms.end, 'hour', Sch.ViewBehaviour.HourView, function(item, m, r, row, col, ds, index) {    return {        text: item.get('Description')    };});
 

An alternative to using the autoViews array, the setView function allows you to configure the scheduler’s view.  Here I use the start and end date variables created previously, define the precision to be used (hour) and a behavior for the view, and create a renderer function for the events.  The renderer function will simply provide the reservation’s description as the text to be rendered for the event. At this point we can check out the panel and confirm that the resources and events are displaying correctly:

The only detail I’m not happy with is that the column headers are displaying the time using the 24-hr format. We can change this format defining a new header renderer function before the scheduler panel is instantiated: Sch.ColumnFactory.headerRenderers.hour = function(a) { return a.format(“g:i A”) }; This function will produce the familiar 12-hr format:

Conclusion

In this first Ext Scheduler article I talked about the concepts behind the Ext Scheduler, and showed you how to use this component to put together a simple UI that displays conference room reservations.  In the next article of this series we will resume development and add the ability to create, edit and remove reservations. I encourage you to try and experiment with the source code for this article, as well as check out the scheduler’s examples and support materials.

Downloads

Grab the code for the sample: ExtScheduler1.zip. You can obtain the Ext Scheduler at http://www.ext-scheduler.com.

Comments

    • says

      @Joe:

      Just updated the post with the link to the source. I did not realize the article was still pointing to the now retired downloads page.

      Be mindful that the second part of the series contains the source for the complete example. Also, the component has evolved. You will need to check its website for API changes, etc.

Leave a Comment

Your email address will not be published. Required fields are marked *