Field controls in Sitefinity are the main units to read/write field values in the backend. You can either create simple field controls representing textboxes or more complicated ones. See Sitefinity documentation for an overview and types of field controls.

You can either use built-in field controls in Sitefinity or implement custom ones. To create a scaffold of a custom field control with selector for dynamic items use Sitefinity Thunder. Read the full steps in documentation.

Today's blog post will demonstrate how to be able to drag & drop field control's items to reorder them. See the image below:

If you already built-up a custom field control with selector, see the steps below how to add option to reorder the items.

Update the template

You must add several css classes: sfDragNDropListWrp, sfDragNDropList, sfDragNDropItem, etc. to be able to display the items of the field control in the well-known Sitefinity interface for drag & drop. See the code below:

<div class="sfDragNDropListWrp">
 <ul id="selectedItemsList" data-template="ul-template-ClientListSelector" 
    data-bind="source: items" runat="server" class="sfDragNDropList"></ul>
 <script id="ul-template-ClientListSelector" type="text/x-kendo-template">
  <li class="sfDragNDropItem" style="float:left;">
    <div id="data" class="sfDragPoint">
        <span data-bind="text: Title.Value, attr: {data-id: OriginalContentId}"> </span>
        <a class="remove sfRemoveBtn">Remove</a>
    </div>
 </li>
</script>
</div>

Default UI:

After adding the css styles:

Next step is to add the logic for drag & drop.

Update the client component

We'll take advantage of the jQuery sortable. Follow the steps below:

  1. Instantiate sorting delegates:

Add the following code just before the end of the SitefinityWebApp.Fields.VideoSelectorControl.VideoSelector.initializeBase(this, [element]);

// delegates
this._sortStopDelegate = null;
this._sortStartDelegate = null;
  1. Subscribe to the events of the jQuery sortable.

In initialize method add the following code after the kendo.bind syntax:

    this._sortStopDelegate = Function.createDelegate(this, this._sortStopHandler);
    this._sortStartDelegate = Function.createDelegate(this, this._sortStartHandler);

    $(this.get_selectedItemsList()).sortable(
                                        {
                                            update: this._sortStopDelegate,
                                            start: this._sortStartDelegate,
                                            forcePlaceholderSize: true
                                        }
                                    );
  1. Implement the sorting handler's logic.

Put the following code at the end of the event handler's section:

_sortStopHandler: function (event, ui) {
    var el = ui.item;

    var toIndex = $(this.get_selectedItemsList()).children().index(el);
    var fromIndex = $(el).data("startIndex");
    var element = this._selectedItems.items[fromIndex];
    this._selectedItems.items.splice(fromIndex, 1);
    this._selectedItems.items.splice(toIndex, 0, element);
},

_sortStartHandler: function (event, ui) {
    var el = ui.item;
    var startIndex = jQuery(this.get_selectedItemsList()).children().index(el);
    jQuery(el).data("startIndex", startIndex);
},

In the code above, on start of dragging - the start event is triggered in the jQuery sortable element. In the start handler we are preserving the start index of the element. Next, when the item is dropped the update event is fired. Here you must preserve the index where the item is dropped. Also you need to manually reorder the items of the kendo observable collection that is used as a View-Model to the unordered list of field control items.

Standart logic for reordering an item in array is used:

    var element = this._selectedItems.items[fromIndex];
    this._selectedItems.items.splice(fromIndex, 1);
    this._selectedItems.items.splice(toIndex, 0, element);

Next, the get_value function of the field control is called. It will iterate through all of the selectedItems and add their OriginalContentId values in the order that the selectedItems are in the kendo observable collection.

Build the solution and enjoy reordering your field control items.

Veronica Milcheva

About Veronica Milcheva

I am a passionate Sitefinity blogger, developer and consultant. In my spare time I enjoy running and listening to music. My personal quote: There's no tough problem, just not enough coffee :)

View Comments

comments powered by Disqus