SharePoint 2013 JSLink OnPostRender not working after adding SP.SOD.executeFunc - javascript

I use JSLink to color rows in a SharePoint 2013 list
ExecuteOrDelayUntilBodyLoaded(function () {
SP.SOD.executeFunc('sp.js', 'SP.ClientContext', function () {
RegisterModuleInit(_spPageContextInfo.siteServerRelativeUrl + "/SiteAssets/jsLink.js", Highlight);
Highlight();
}
});
});
function Highlight() {
var HighlightFieldCtx = {};
HighlightFieldCtx.Templates = {};
HighlightFieldCtx.Templates.Fields = {};
HighlightFieldCtx.OnPostRender = postRenderHandler;
SPClientTemplates.TemplateManager.RegisterTemplateOverrides(HighlightFieldCtx);
}
function postRenderHandler(ctx)
{
var rows = ctx.ListData.Row;
for (var i=0;i<rows.length;i++)
{
// do stuff
row.classList.add("Color");
}
}
I need add SP.SOD.executeFunc() for activate _spPageContextInfo. But when I added SP.SOD.executeFunc(), function postRenderHandler not called in line with HighlightFieldCtx.OnPostRender = postRenderHandler.
When I dont have SP.SOD.ExecuteFunc() and static link on my JS and CSS, my code and rendering fully working. Can you please help me, how to make proper code with working _spPageContextInfo?

Try this:
<script type="text/javascript">
SP.SOD.executeFunc('sp.js', 'SP.ClientContext', function () {
//alert(_spPageContextInfo.siteServerRelativeUrl);
RegisterModuleInit(_spPageContextInfo.siteServerRelativeUrl + "/SiteAssets/jsLink.js", Highlight);
Highlight();
});
function Highlight() {
var HighlightFieldCtx = {};
HighlightFieldCtx.Templates = {};
HighlightFieldCtx.Templates.Fields = {};
HighlightFieldCtx.OnPostRender = postRenderHandler;
SPClientTemplates.TemplateManager.RegisterTemplateOverrides(HighlightFieldCtx);
}
function postRenderHandler(ctx)
{
var rows = ctx.ListData.Row;
alert('postRenderHandler');
}
</script>

Related

Quill.js add a custom javascript function into the editor

I am using Quill.js to have users create custom user designed pages off the main web page. I have a custom slider that I have written in javascript that will take images and rotate through them. I have the toolbar in quill setup to be able to click on the toolbar to setup the slider in a modal window.
When the user clicks to close the modal slider setup window, I'm trying to insert an edit button in the html editor where the cursor sits so the user can edit the information that was just entered or possible delete the button by removing all the information in the slider modal window.
I have written custom blots, followed all the examples I could find and nothing worked. I did get a custom html tag to show, but not a button. When I requested the html from quill when I setup the custom html tag in the editor, all I get is "" from quill.root.innerHTML none of the custom tag or the information in it even though I see it correctly in the editor.
I would like a button in the editor to make it easy to edit the slider data, as there could be more than one. I am not going to limit the number of sliders. It is up to the user to ruin their own page.
I will not be rendering the slider in the edit html window, just trying to display a button to click on. I do give the user a preview button on the modal window to view the slider if they so choose.
I also would like to store the setup information of the slider in a data tag in json format in the button and change that html button to a tag along with the json data when rendering the html in the browser window.
Can this be done in Quill.js?
I did this by using the import blots embed. I don't register as a button but clicking on the blot I do get a link to the embedded data and trigger the edit of the carousel data on that click.
var Quill;
const BlockEmbed = Quill.import("blots/block/embed");
const Link = Quill.import('formats/link');
class Carousel extends BlockEmbed {
static create(value) {
var self = this;
const node = super.create(value);
node.dataset.carousel = JSON.stringify(value);
value.file.frames.forEach(frame => {
const frameDiv = document.createElement("div");
frameDiv.innerText = frame.title;
frameDiv.className += "previewDiv";
node.appendChild(frameDiv);
});
node.onclick = function () {
if (Carousel.onClick) {
Carousel.onClick(self, node);
}
};
return node;
}
static value(domNode) {
return JSON.parse(domNode.dataset.carousel);
}
static onClick: any;
static blotName = "carousel";
static className = "ql-carousel";
static tagName = "DIV";
}
Quill.register("formats/carousel", Carousel);
I then include this as a script on the page where quill is editing the HTML
<script src="~/js/quilljs-carousel.js"></script>
And then this is the custom javascript to handle the events of the blot displayed in a custom modal dialog in a hidden div tag
<script>
function CarouselClicked(blot, node) {
editCarousel(JSON.parse(node.dataset.carousel), node);
}
var Carousel = Quill.import("formats/carousel");
Carousel.onClick = CarouselClicked;
function carouselToolbarClickHandler() {
createCarousel();
}
var Toolbar = Quill.import("modules/toolbar");
Toolbar.DEFAULTS.handlers.carousel = carouselToolbarClickHandler;
$(document).ready(function() {
var div = $("#editor-container");
var Image = Quill.import('formats/image');
Image.className = "img-fluid";
Quill.register(Image, true);
var quill = new Quill(div.get(0),
{
modules: {
syntax: true,
toolbar: '#toolbar-container'
},
theme: 'snow'
});
div.data('quill', quill);
// Only show the toolbar when quill is ready to go
$('#toolbar-container').css('display', 'block');
div.css('display', 'block');
$('#editor-loading').css('display', 'none');
// Override the quill Image handler and create our own.
quill.getModule("toolbar").addHandler("image", imageHandler);
});
function createCarousel() {
$("#carouselModalForm").removeClass("was-validated").get(0).reset();
$("#carouselModalList").empty();
$("#carouselModal")
.data("state", "unsaved")
.one("hidden.bs.modal",
function() {
var data = getCarouselData();
var carouselData = {};
carouselData['file'] = data;
carouselData['speed'] = $('#time').val();
carouselData['height'] = $('#height').val();
carouselData['width'] = $('#width').val();
var quill = $("#editor-container").data().quill;
var range = quill.getSelection(true);
if (range != null) {
quill.insertEmbed(
range.index,
"carousel",
carouselData,
Quill.sources.USER
);
quill.setSelection(range.index + 2, Quill.sources.USER);
}
})
.modal("show");
$('#title').get(0).outerText = "Create Carousel";
}
function editCarousel(value, node) {
$("#carouselModalForm").get(0).reset();
var elem = $("#carouselModalList").empty();
$.each(value.file.frames,
function(i, data) {
$("<option>").appendTo(elem).text(data.title).data("frame", data);
});
$('#time').val(value.speed);
$('#height').val(value.height);
$('#width').val(value.width);
var modal = $("#carouselModal");
modal.find("form").removeClass("was-validated");
modal
.data("state", "unsaved")
.one("hidden.bs.modal",
function() {
if ($("#carouselModal").data("state") !== "saved")
return;
var data = getCarouselData();
var carouselData = {};
carouselData['file'] = data;
carouselData['speed'] = $('#time').val();
carouselData['height'] = $('#height').val();
carouselData['width'] = $('#width').val();
var carousel = Quill.find(node, true);
carousel.replaceWith("carousel", carouselData);
})
.modal("show");
$('#title').get(0).outerText = "Edit Carousel";
}
function getCarouselData() {
var options = $("#carouselModalList").find("option");
var frames = $.map(options,
function(domNode) {
return $(domNode).data("frame");
});
return {
frames : frames
};
}
function getCarouselFrameFormData() {
// Get data from frame
function objectifyForm(formArray) { //serialize data function
var returnArray = {};
for (var i = 0; i < formArray.length; i++) {
returnArray[formArray[i]['name']] = formArray[i]['value'];
}
return returnArray;
}
return objectifyForm($("#carouselFrameModalForm").serializeArray());
}
$("#carouselModalNewFrame").click(function() {
$("#carouselFrameModalForm").removeClass("was-validated").get(0).reset();
$("#backgroundPreview").attr("src", "");
$("#mainPreview").attr("src", "");
$("#carouselFrameModal")
.data("state", "unsaved")
.one("hidden.bs.modal",
function() {
if ($("#carouselFrameModal").data("state") == "saved") {
var data = getCarouselFrameFormData();
$("<option>").appendTo($("#carouselModalList")).text(data.title).data("frame", data);
}
})
.modal("show");
// Fetch all the forms we want to apply custom Bootstrap validation styles to
});
$("#carouselModalEditFrame").click(function () {
var form = $("#carouselFrameModalForm");
form.removeClass("was-validated").get(0).reset();
var selected = $("#carouselModalList option:selected");
var frame = selected.data("frame");
$.each(Object.keys(frame),
function (i, e) {
$("input[name=" + e + "]", form).val(frame[e]);
});
$("#backgroundPreview").attr("src", frame.backgroundImg);
$("#mainPreview").attr("src", frame.mainImg);
$("#carouselFrameModal")
.data("state", "unsaved")
.one("hidden.bs.modal",
function() {
if ($("#carouselFrameModal").data("state") == "saved") {
var data = getCarouselFrameFormData();
selected.text(data.title).data("frame", data);
}
})
.modal("show");
});
$("#carouselModalRemoveFrame").click(function () {
$("#confirm-delete").modal("show");
});
$("#carouselFrameModalForm").find("input:file").change(function() {
var elem = $(this);
var target = elem.data("target");
var preview = elem.data("preview");
FiletoBase64(this, preview, target);
});
$("#carouselModalList").change(function() {
var selected = $("option:selected", this);
$("#carouselModalEditFrame,#carouselModalRemoveFrame").prop("disabled", !selected.length);
});
$("#carouselModalSave").click(function() {
// Validate frameset
var form = $("#carouselModalForm").get(0);
var select = $("#carouselModalList");
if (select.find("option").length == 0) {
select.get(0).setCustomValidity("Need at least one frame");
} else {
select.get(0).setCustomValidity("");
}
if (form.checkValidity()) {
$("#carouselModal").data("state", "saved");
$("#carouselModal").modal("hide");
}
else {
$("#carouselModalForm").addClass("was-validated");
}
});
$("#carouselFrameModalSave").click(function() {
// Validate frame
if ($("#carouselFrameModalForm").get(0).checkValidity()) {
$("#carouselFrameModal").data("state", "saved");
$("#carouselFrameModal").modal("hide");
}
else {
$("#carouselFrameModalForm").addClass("was-validated");
}
});
$('#confirm-delete-delete').click(function () {
$("#carouselModalList option:selected").remove();
$("#confirm-delete").modal("hide");
});
// #region Image FileExplorer Handler
function insertImageToEditor(url) {
var div = $("#editor-container");
var quill = div.data('quill');
var range = quill.getSelection();
quill.insertEmbed(range.index, 'image', url);
}
function CarouselMainimageHandler() {
$("#CarouselMainimageSelectFileExplorer").fileExplorer({
directoryListUrl: '#Url.Action("DirectoryList", "FileTree")',
fileListUrl: '#Url.Action("FileList", "FileTree")'
});
$("#CarouselMainimageSelectModal").modal("show");
}
$("#CarouselMainimageSelectModal").on("hide.bs.modal",
function() {
$("#CarouselMainimageSelectFileExplorer").fileExplorer("destroy");
});
$("#CarouselMainimageSelectSelectButton").click(function() {
var id = $("#CarouselMainimageSelectFileExplorer").fileExplorer("getSelectedFileId");
if (id == null) {
alert("Please select a file");
return;
}
var imageName = $("#CarouselMainimageSelectFileExplorer").fileExplorer("getSelectedFileName");
var imageLink = "#Url.Action("Render", "FileTree")?id=" + id;
$("#mainImageName").val(imageName);
$("#mainImageLink").val(imageLink);
$("#mainImage").attr("src",imageLink);
$("#mainImage").show();
$("#CarouselMainimageSelectModal").modal("hide");
});
function CarouselBackgroundimageHandler() {
$("#CarouselBackgroundimageSelectFileExplorer").fileExplorer({
directoryListUrl: '#Url.Action("DirectoryList", "FileTree")',
fileListUrl: '#Url.Action("FileList", "FileTree")'
});
$("#CarouselBackgroundimageSelectModal").modal("show");
}
$("#CarouselBackgroundimageSelectModal").on("hide.bs.modal",
function() {
$("#CarouselBackgroundimageSelectFileExplorer").fileExplorer("destroy");
});
$("#CarouselBackgroundimageSelectSelectButton").click(function() {
var id = $("#CarouselBackgroundimageSelectFileExplorer").fileExplorer("getSelectedFileId");
if (id == null) {
alert("Please select a file");
return;
}
var imageName = $("#CarouselBackgroundimageSelectFileExplorer").fileExplorer("getSelectedFileName");
var imageLink = "#Url.Action("Render", "FileTree")?id=" + id;
$("#backgroundImageName").val(imageName);
$("#backgroundImageLink").val(imageLink);
$("#backgroundImage").attr("src",imageLink);
$("#backgroundImage").show();
$("#CarouselBackgroundimageSelectModal").modal("hide");
});
function imageHandler() {
$("#imageSelectFileExplorer").fileExplorer({
directoryListUrl: '#Url.Action("DirectoryList", "FileTree")',
fileListUrl: '#Url.Action("FileList", "FileTree")'
});
$("#imageSelectModal").modal("show");
}
$("#imageSelectModal").on("hide.bs.modal",
function() {
$("#imageSelectFileExplorer").fileExplorer("destroy");
});
$("#imageSelectSelectButton").click(function() {
var id = $("#imageSelectFileExplorer").fileExplorer("getSelectedFileId");
if (id == null) {
alert("Please select a file");
return;
}
insertImageToEditor("#Url.Action("Render", "FileTree")?id=" + id);
$("#imageSelectModal").modal("hide");
});
// #endregion
function Save() {
var div = $("#editor-container");
var quill = div.data('quill');
$('#alertSave').show();
$.post({
url: '#Url.Action("Save")',
data: { BodyHtml: quill.root.innerHTML, locationId: #(Model.LocationId?.ToString() ?? "null") },
headers: {
'#Xsrf.HeaderName': '#Xsrf.RequestToken'
}
}).done(function() {
$('#alertSave').hide();
$('#alertSuccess').show();
setTimeout(function() { $('#alertSuccess').hide(); }, 5000);
}).fail(function(jqXhr, error) {
var alert = $('#alertFailure');
var text = $("#alertFailureText");
text.text(error.ErrorMessage);
alert.show();
});
}
function FiletoBase64(input, imgName, Base64TextName) {
var preview = document.getElementById(imgName);
var file = input.files[0];
var reader = new FileReader();
reader.addEventListener("load",
function() {
preview.src = reader.result;
document.getElementById(Base64TextName).value = reader.result;
},
false);
if (file) {
reader.readAsDataURL(file);
}
}
</script>

Overriding functions in javascript is not working, debugger skips my code

I am trying to modify an application by overriding certain functions. I cannot release the code due to enterprise ownership. My code looks like this:
<html>
<head>
<script type="text/javascript" src="https://mylink.scriptX.js"></script>
// Some other scripts and css references
</head>
<body>
<script>
$(document).ready(function () {
form_script = my_script =
{
initialization:function (mode, json_data) {
this.parent_class.initialization(mode, json_data);
//Mycode to override the functions in scriptX.js is below:
var x= {};
function inherit(x) {
var y= {};
y.prototype = x;
return y;
};
(function ($) {
var OverrideFunctions = inherit($.my_methods);
OverrideFunctions.function1 = function () { ...};
OverrideFunctions.function2 = function () { ...};
OverrideFunctions.function3 = function () { ...}
})(jQuery);
}
//some original code here
}
</script>
//some other code here
</body>
</html>
Now the content of the scriptX.js is something like this:
(function ($) {
var my_methods = {
function1 = function () { ...};
function2 = function () { ...};
function3 = function () { ...}
}
})(jQuery);
The problem is that, I am noticing that the debugger skips the whole block of code since OverrideFunctions.function1 = function () { to the end })(jQuery);
So my functions are not being executed and thus the application is not changed. I was wondering if that could be related

How do I get this function to work with my template

I got a function that works on another website, but somehow it won't work with this (free) template I am using.
The main js file groups all functions together somehow and just pasting the code in the main.js file gives me a dropdown is not defined.
My function:
dropdown = function(e){
var obj = $(e+'.dropdown');
var btn = obj.find('.btn-selector');
var dd = obj.find('ul');
var opt = dd.find('li');
obj.on("mouseenter", function() {
dd.show();
}).on("mouseleave", function() {
dd.hide();
})
opt.on("click", function() {
dd.hide();
var txt = $(this).text();
opt.removeClass("active");
$(this).addClass("active");
btn.text(txt);
});
}
Then inside a document ready wrap I call:
dropdown('#lang-selector');
For the following HTML code:
<div id="lang-selector" class="dropdown">
NL
<ul>
<li>EN</li>
<li>NL</li>
</ul>
</div>
This is a working function in that template:
// custom theme
var CustomTheme = function () {
var _initInstances = function () {
if ($('.vk-home-dark').length) {
$('#scrollUp').addClass('inverse');
}
};
return {
init: function () {
_initInstances();
}
};
}();
Which is then called like this:
$(document).ready(function(){
PreLoader.init();
CustomTheme.init();
MediaPlayer.init();
});
I tried turning dropdown to a variable by adding var before it and then calling dropdown.init(); but this gave me dropdown.init(); is not a function
How can I make it work like the other functions?
Preloader function as requested:
// preloader
var PreLoader = function () {
var _initInstances = function () {
$('.animsition').animsition({
// loadingClass: 'loader',
inDuration: 900,
outDuration: 500,
linkElement: 'a:not([target="_blank"]):not([href^="#"]):not([href^="javascript:void(0);"])',
});
};
return {
init: function () {
_initInstances();
}
};
}();

Call function in prototype from other prototype

I have two prototypes in my jquery script :
script1.prototype.initScript = function() {
//first one
this.saveGrid = function () {
alert("here");
}
};
script1.prototype.otherFunction = function () {
//second
//script1.initScript.saveGrid ?
};
I'd like to call saveGrid in otherFunction. How can I do that?
Edit :
And there ?
script1.prototype.initScript = function() {
//first one
this.saveGrid = function () {
alert("here");
}
};
script1.prototype.otherFunction = function () {
//second
$('button').on("click", function(){
//call savegrid here
});
};
Thanks.
You can access the function over this, like you already did in you example while creating the function saveGrid.
You should instead ask yourself, if this is a good idea, to create a function in another function and re-use them elsewere. What will happen, if you call otherFunction before initScript?
function script1() {}
script1.prototype.initScript = function() {
this.saveGrid = function() {
alert("here");
}
};
script1.prototype.otherFunction = function() {
this.saveGrid();
};
var s = new script1();
s.initScript();
s.otherFunction();
For you second example you have to store this before creating your event listener.
function script1() {}
script1.prototype.initScript = function() {
this.saveGrid = function() {
alert("here");
}
};
script1.prototype.otherFunction = function() {
var that = this;
$('button').on("click", function(){
that.saveGrid();
});
};
var s = new script1();
s.initScript();
s.otherFunction();
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<button>click me</button>
Prototype It depends on the type .
the correct way is defined as a prototype , so you can call them in different situations
script1.prototype.saveGrid=function () {
alert("here");
}
script1.prototype.initScript = function() {
//first one
this.saveGrid()
};
script1.prototype.otherFunction = function () {
//second
//this.saveGrid()
};`
or you can define an object which then associates the prototypes
var script1=(function () {
function initScript(){
this.saveGrid();
}
function otherFunction(){
this.saveGrid();
}
script1.prototype.saveGrid=function () {
alert("here");
}
});

JQuery .hover / .on('mouseleave') not functioning properly

I am trying to use the hover function which is pretty rudimentary, but I can't seem to get the mouseout/mouseleave to function properly.
Code:
$(document).ready(function(){
$('.SList').css('display','none');
$(".MList a").on('mouseenter',
function(){
var HTMLArr = $(this).children().html().split(':');
$(this).children('p').replaceWith('<p>'+HTMLArr[0]+':&nbsp◤</p>');
$(this).siblings('.SList').slideDown('slow');
})
.on('mouseleave',function(){
var HTMLArr = $(this).children().html().split(':');
$(this).children('p').replaceWith('<p>'+HTMLArr[0]+':&nbsp◢</p>');
$(this).siblings('.SList').slideUp('slow');
});
});
The mouseenter works properly, but it is not even entering the code for the mouseleave. Any ideas would be greatly appreciated.
Fiddle
See this: DEMO
$(".MList a").on('mouseenter',
function(){
var HTML = $(this).children('p').html();
$(this).children('p').html(HTML.replace('◢','◤'));
$(this).siblings('.SList').slideDown('slow');
})
.on('mouseleave',function(){
var HTML = $(this).children('p').html();
$(this).children('p').html(HTML.replace('◤','◢'));
$(this).siblings('.SList').slideUp('slow');
});
You have an issue with the anchor of the event.
Change to use this:
$(".MList a").on('mouseenter', function () {
var myP = $(this).children('p');
var HTMLArr = myP.text().split(':');
myP.html( HTMLArr[0] + ':&nbsp◤');
$(this).next('.SList').slideDown('slow');
}).on('mouseleave', function () {
var myP = $(this).children('p');
var HTMLArr = myP.text().split(':');
myP.html( HTMLArr[0] + ':&nbsp◢');
$(this).next('.SList').slideUp('slow');
});
You have the same issue with click, and redo same thing. SO, rework and reuse: (you could even make it better but this shows the start of that)
$(".MList a").on('mouseenter', function () {
down($(this).find('p').eq(0));
}).on('mouseleave', function () {
up($(this).find('p').eq(0));
});
$(".MList a").click(function () {
if ($(this).siblings('.SList').is(':visible')) {
up($(this).find('p').eq(0));
} else {
down($(this).find('p').eq(0));
}
});
function up(me) {
var HTMLArr = me.text().split(':');
me.html(HTMLArr[0] + ':&nbsp◢');
me.parent().next('.SList').slideUp('slow');
}
function down(me) {
var HTMLArr = me.text().split(':');
me.html(HTMLArr[0] + ':&nbsp◤');
me.parent().next('.SList').slideDown('slow');
}

Categories

Resources