Monday, September 23, 2013

Provisioning TermSets/Terms to Terms Store from Apps

I was reading Deploying Managed Metadata Fields by Luis Manez, in the blog he mentions about creating TermSets and Terms with PowerShell. I couldn't get it working and instead created an APP to provision the TermSets and Terms.

Below are brief steps:

1. Create a "App for SharePoint 2013" Project (SharePoint-hosted)

2. Open AppMainifest.xml and set the Permissions


3. below is the js code

var hostweburl;
var appweburl;
var scriptbase = hostweburl + "/_layouts/15/";
function InitiateTaxonomy() {
hostweburl = decodeURIComponent(getQueryStringParameter("SPHostUrl"));
appweburl = decodeURIComponent(getQueryStringParameter("SPAppWebUrl"));
$.getScript(scriptbase + "SP.Taxonomy.js",
function () {
$.getScript(scriptbase + "SP.RequestExecutor.js", CreateTerms);
}
);
}
function getQueryStringParameter(paramToRetrieve) {
var params =
document.URL.split("?")[1].split("&");
var strParams = "";
for (var i = 0; i < params.length; i = i + 1) {
var singleParam = params[i].split("=");
if (singleParam[0] == paramToRetrieve)
return singleParam[1];
}
}
function StartRequest() {
$.getScript(scriptbase + "SP.RequestExecutor.js", CreateTerms);
}
function CreateTerms() {
var locationTerms = [];
var obj;
locationTerms.push(obj = { Name: "Perth", Locale: 1033, GUID: "6E0FDC96-7E59-4545-820F-CCB8BFD0AB32" });
locationTerms.push(obj = { Name: "Melbourne", Locale: 1033, GUID: "BE1C37D3-D98D-4447-9310-FDA3156E7EDE" });
locationTerms.push(obj = { Name: "Sydney", Locale: 1033, GUID: "DBFDBA00-B08A-4B47-9152-AE084CD80EA5" });
var obj1;
var businessUnitTerms = [];
businessUnitTerms.push(obj1 = { Name: "HR", Locale: 1033, GUID: "278707D7-52F8-4B49-9163-F9A0FC6650AF" });
businessUnitTerms.push(obj1 = { Name: "IT", Locale: 1033, GUID: "9185E703-2D41-4D7A-BE5E-26A6BEA56960" });
var context;
var factory;
var appContextSite;
var siteCollection;
var i;
context = new SP.ClientContext(appweburl);
factory = new SP.ProxyWebRequestExecutorFactory(appweburl);
context.set_webRequestExecutorFactory(factory);
appContextSite = new SP.AppContextSite(context, hostweburl);
siteCollection = context.get_site();
//Current Taxonomy Session
var taxSession = SP.Taxonomy.TaxonomySession.getTaxonomySession(context);
//Term Store under which to create the group.
var termStore = taxSession.getDefaultSiteCollectionTermStore();
context.load(termStore);
context.executeQueryAsync(function () {
var id = termStore.get_id();
//Get site collection group
var defaultGroup = termStore.getSiteCollectionGroup(siteCollection);
context.load(defaultGroup);
context.executeQueryAsync(function () {
//Create New Term Set
var newTermSet = defaultGroup.createTermSet("Location", "74A786C1-8613-4ED8-9680-13493D94AD45", 1033);
var newTermSet1 = defaultGroup.createTermSet("BusinessUnit", "683E8BDE-D2A5-4D7F-B15F-789217B95F21", 1033);
for (i = 0 ; i < locationTerms.length; i++) {
var newTerm = newTermSet.createTerm(locationTerms[i].Name, locationTerms[i].Locale, locationTerms[i].GUID);
context.load(newTerm);
}
for (i = 0; i < businessUnitTerms.length; i++) {
var newTerm = newTermSet1.createTerm(businessUnitTerms[i].Name, businessUnitTerms[i].Locale, businessUnitTerms[i].GUID);
context.load(newTerm);
}
context.executeQueryAsync(function () {
$('#message').text("Terms Created");
}, function (sender, args) {
$('#message').text(args.get_message());
});
}, function (sender, args) {
$('#message').text(args.get_message());
});
}, function (sender, args) {
$('#message').text(args.get_message());
});
}
view raw termstore.js hosted with ❤ by GitHub


call the InitiateTaxonomy from the onGetUserNameSuccess method.

4. Deploy the app and verify by navigating to the Term Store Management.



Note: I used the publishing site template, the Site Collection was already created.

Thursday, September 19, 2013

Tiles view with Client Side Rendering

In my previous post I wrote about Tiles view with CQWP. You can also achieve this using Client Side Rendering (CSR examples by Wesley).

I wanted my custom list to have Tiles view:



I created a Javascript Display Template file & uploaded to the masterpage gallery and set the JS Link in the Miscellaneous section.

Below is the sample CSR code (update the styles..):
(function () {
/*
* Initialize the variable that store the overrides objects.
*/
var overrideCtx = {};
overrideCtx.Templates = {};
// Assign functions or plain html strings to the templateset objects:
// header, footer and item.
overrideCtx.Templates.Header = "<ul class='dfwp-column dfwp-list' style='width:100%;'>";
overrideCtx.Templates.Footer = "</ul>";
// This template is assigned to the CustomItem function.
overrideCtx.Templates.Item = CustomItem;
overrideCtx.BaseViewID = 1;
//overrideCtx.ListTemplateType = 0;
// Register the template overrides.
SPClientTemplates.TemplateManager.RegisterTemplateOverrides(overrideCtx);
})();
/*
* This function builds the output for the item template.
* Uses the Context object to access announcement data.
*/
function CustomItem(ctx) {
// Build a listitem entry for every announcement in the list.
var ret = "<li class='dfwp-item'>";
ret += "<div id='Div2' style='width: 160px; height: 160px;' class='ms-tileview-tile-root'><div id='Div3' style='width: 150px; height: 150px;' aria-haspopup='true' class='ms-tileview-tile-content'>";
ret += "<a href='"+ctx.CurrentItem.FileRef.substr(0, ctx.CurrentItem.FileRef.lastIndexOf('/'))+ "/dispform.aspx?ID=" + ctx.CurrentItem.ID +"'>";
ret += "<img height='150' class=' ms-positionRelative' style='visibility: visible;' src='"+ctx.CurrentItem.AImage+"'>";
ret += "<div id='Div4' offy='100' class='ms-tileview-tile-detailsBox'>";
ret += " <ul class='ms-noList ms-tileview-tile-detailsListMedium'><li id='Li3' collapsed='ms-tileview-tile-titleMedium ms-tileview-tile-titleMediumCollapsed' expanded='ms-tileview-tile-titleMedium ms-tileview-tile-titleMediumExpanded' class='ms-tileview-tile-titleMedium ms-tileview-tile-titleMediumCollapsed'>";
ret += "<div collapsed='ms-tileview-tile-titleTextMediumCollapsed' expanded='ms-tileview-tile-titleTextMediumExpanded' class='ms-tileview-tile-titleTextMediumCollapsed'>";
ret += ctx.CurrentItem.Title;
ret += "</div></li>";
ret += "<li id='Li4' class='ms-tileview-tile-descriptionMedium'>";
ret += ctx.CurrentItem.ADescription;
ret += "</li></ul></div></a></div></li>";
return ret;
}
view raw tiles.js hosted with ❤ by GitHub



CSS:

<style type="text/css">
. ms-tileview-tile-detailsBox {
width: 150px; height: 150px; top: 100px; left: 0px;
-webkit-transition: 300ms 0ms;
-webkit-transform-origin-x: -25px; }
.ms-tileview-tile-content:hover .ms-tileview-tile-detailsBox {
top:0px !important;
-webkit-transition: 300ms 0ms;
-webkit-transform-origin-x: -25px;
}
</style>
view raw tiles.css hosted with ❤ by GitHub


Note: I have the DisForm hard coded, I couldn't find a way to get the DisplayUrl property like in REST. I shall update this when I come across a better way.

Output: