Objective:
- implement custom sort functionality for list items
- make order number (rank) visible on the list
First, let’s create custom action for reordering items and make hidden field Order visible and sortable on default view with PowerShell.
[void] [System.reflection.Assembly]::LoadWithPartialName("Microsoft.SharePoint") | out-null # Add "Change item Order" button at target List $siteUrl = "yourSiteCollectionUrl"; $listTitle = "yourListTitle"; $site = Get-SPSite -Identity $siteUrl; $web = $site.OpenWeb(); $list = $web.Lists[$listTitle]; $list.UserCustomActions.Clear(); $action = $list.UserCustomActions.Add(); $action.Location = "CommandUI.Ribbon"; $action.Sequence = 85; $action.Title = "PS.OrderItems"; $action.CommandUIExtension = [string]::Format( "<CommandUIExtension> <CommandUIDefinitions> <CommandUIDefinition Location=""Ribbon.ListItem.Actions.Controls._children""> <Button Id=""ReOrderAction.Button"" TemplateAlias=""o1"" Command=""ReOrderCommand"" CommandType=""General"" LabelText=""Change Item Order"" Image16by16=""/_layouts/1033/images/formatmap16x16.png"" Image16by16Top=""-192"" Image16by16Left=""-144"" Image32by32=""/_layouts/1033/images/formatmap32x32.png"" Image32by32Top=""-192"" Image32by32Left=""-288""/> </CommandUIDefinition> </CommandUIDefinitions> <CommandUIHandlers> <CommandUIHandler Command =""ReOrderCommand"" CommandAction=""{0}/_layouts/15/Reorder.aspx?List={1}"" /> </CommandUIHandlers> </CommandUIExtension>", $web.ServerRelativeUrl.TrimEnd('/'), $list.ID); $action.Update(); $view = $list.DefaultView; $view.Query = [string]::Format("<OrderBy><FieldRef Name=""Order"" Ascending=""TRUE""/></OrderBy>"); $view.Update(); Write-Host "-------------------------------------" Write-Host "Change item order button added successfully for the list : " $list.Title -foregroundcolor Green -nonewline Write-Host " in the site : " $site.Url -foregroundcolor Green Write-Host "-------------------------------------" $web.Dispose(); $site.Dispose();
or use your preferred method. But you can’t change it in SharePoint Manager 2013.
Now we can sort the list based on order, but, we have one issue: how to display order number on the list. This is tricky, because Order field contains double numbers and it has nothing to do with position/rank number. We can use CSR/JSLink to rank Order value within Order value array. Then let’s write a JSLink script for Order field override on view
(function() { varmyarray = []; varordFieldCtx = {}; // Define template variable ordFieldCtx.Templates = {}; ordFieldCtx.Templates.Fields = { "Order": { "View": OrderFieldViewTemplate } }; // Register the template override with SP2013 SPClientTemplates.TemplateManager.RegisterTemplateOverrides( ordFieldCtx ); })(); functiongetRank(item, orderval) { varranks = $.grep(orderval, function(item, idx) { returnitem != orderval[idx - 1]; });//.reverse(); add this if you want to have reverse ranking varrank = $.inArray(item, ranks) + 1; returnrank; } // Override Order field with rank functionOrderFieldViewTemplate(ctx) { var_orderValue = ctx.CurrentItem.Order; varordervalues=[]; varObjKeys = Object.keys(ctx.ListData.Row); ObjKeys.forEach(function(ord){ ordervalues.push(ctx.ListData.Row[ord].Order); }); returngetRank(_orderValue,ordervalues); }
Save it to the file and place in to master page gallery as JS Display template. (Read this if need info how to). Do not forget to include JQuery link on list webpart JSLink field property in format like:
~site/SiteAssets/jquery-1.8.3.min.js|~site/_catalogs/masterpage/Display Templates/rankNumbers.js