Gregory's Blog
long meetins stink

Kendo template with void to consume a function in an anchor link


I have a Kendo template that is used to display real-time statuses for contracts and programmed a href tag that was intended to consume a javascript function rather than opening up a link. On my first attempt, I was having problems as I could not program a pound symbol into the Kendo template (like ColdFusion, a pound symbol indicates a variable within a Kendo template), so I escaped it using two pounds and found myself struggling to figure out why my window was suddenly being refreshed. I spent around ten minutes stepping through my code only to find out that the href tag refreshed the entire page, even though it was blank as the double pound sign escaped. On further introspection, this is understandable as I just had inadvertently programmed a typical link. To fix this issue, I used a simple javascript:void(0); within the link, and the javascript function is called without the default href tag opening up the link. Essentially, the void(0) code prevents the default behavior of the link, and it acts like a a href="#". I would not typically use void in other code, but using it within a Kendo MVVM template is an appropriate place. Here is the code:

<script type="text/x-kendo-template" id="myApprovalTemplate">
	/* Note: dynamic vars can be displayed like so: #: myApprovalDs.total() # */
	 /* Alternate row colors. */
	# if(window.altRow) { #
		<tr class='k-alt'>
	# } else { #
		<tr class='k-content'>
		 # } #
         # if(ApprovalId > 0){ #
          	<td class="border">
          	<input type="checkbox" name="approved#: ApprovalId #" id="approved#: ApprovalId #" value="1" /></td>
          	<td class="border">#: ApproverTitle #</td>
          	<td class="border"><a href="javascript:void(0);" onClick="openContractDetailWindow(#: ContractId #, #: ApprovalId #, '')">#: Contract #</a></td>
          	<td class="border">#: Contractor #</td> 
          	<td class="border">pdf</td>
          	<td class="border"></td> 
         #} else {#
          	<td colspan="6"<!---  class="k-loading-image k-loading-color" --->>
          	<br/>There are no contracts eligible for you to approve
         	</td>
         #}#
	 </tr>
        <!--- Toggle the window variable. --->
        # window.altRow = !window.altRow; #
 </script>

This entry was posted on April 24, 2019 at 9:51 PM and has received 750 views.

Reopen an existing Kendo window.


Type in "Cannot call method 'destroy' of kendoWindow before it is initialized" into google, you won't find a single result. You'll find many other topics, but not one that matches this particular error message. Here is a solution on how I overcame this error, and why I think that it may have happened in the first place. My personal website uses a Greensock animation carriage. It is my guess that the errors are due to having a lot of subtle animations there, and it is resource intensive as it has extensive scroll and touch listeners. Along with the Kendo map widget, the site is very resource intensive on the client end. This is probably freezing the destroy methods that are used to typically close a Kendo window. Whatever the actual reason, when I try to destroy the window that contains the map, as I usually do, I run into multiple errors and the window will not open again. My approach was to build a function that would check if the window was previously opened, and then closed, to simply re-open it and then refresh the content (it has dynamic content). If the window was not already created (by someone opening it), then I would create the window, as usual, but I eliminated Kendo's destroy method when the window is closed. I don't want to destroy it- in fact- I can't. It causes errors. If the window was opened, and closed (making the window hidden since it does not have the destroy method), I would re-open the existing window. Here is the code:

function openMapWindow() {
			
	$( document ).ready(function() {
				
	/*  This is a totally weird approach to open a kendo window. I have coded kendo windows for several years, and have probably coded several hundred windows, but using a Kendo window in this greensock platform, especially with Kendo maps, just does not work. Here, I am testing to see if the window is: 
	1) defined (the first mapWindow line of code will error out if the window has not already been opened)
	2) and if the window is defined, is it hidden (it will be- I am not destroying the window like I always do in other code as I have problems with that here.)
	If both conditions ARE true, then I merely reopen the existing window that was hidden when the user clicked on the 'x' at the top of the window.
	If both conditions are NOT true, then I create the window as usual (but I don't destroy it as usual as I had problems there too). 
	Essentially what I am doing is:
		- Creating the window if the window was not first opened and then closed.
		- Or reopening the window if it was opened and then closed. 
	*/
	// This must be put into a try block as the 'var mapWindow = 		$("#mapWindow").data("kendoWindow");' will cause errors if the window has not already bee already opened.
	try {
		// Get a reference to the opened window.
		var mapWindow = $("#mapWindow").data("kendoWindow");
		// Determine if the window was closed...
		var mapWindowIsHidden = mapWindow.element.is(":hidden"); //returns true or false
		// If the window was closed (and now hidden), re-open the existing window.
		if (mapWindowIsHidden){
			// Change the title
			mapWindow.title(getMapDataByScene(sceneIndex));
			// Open it.
			mapWindow.open();
			// And refresh the window.
			mapWindow.bind("refresh", window_refresh);
					}
		// Otherwise create the window (for the first time)...
		} catch(e) {
					
			// Initialize the window.
			var mapWindow = $('#mapWindow').kendoWindow({
			title: getMapDataByScene(sceneIndex),
			actions: ["Refresh", <cfif not session.isMobile>"Minimize", </cfif>"Close"],
			modal: false,
			resizable: true,
			draggable: true,
			pinned: true, // Note: we must pin this window, or it will open at the top of the page at all times when we use this approach.
			position: { top: 100 },
			width: getGrizzlyWindowWidth(),
			height: getGrizzlyWindowHeight(),
			iframe: false, // Don't use iframes unless it is content derived outside of your own site. 
			content: "/includes/layers/map.cfm?sceneIndex=" + sceneIndex,// Make sure to create an absolute path here. I had problems with a cached page.
		<cfif session.isMobile>
			animation: {
				close: {
				effects: "slideIn:right",
				reverse: true,
				duration: 500
			}
		}
	</cfif>
	}).data('kendoWindow').center();// Center the window.
								  
	}//..try
});
			
}//..function openMapWindow() {

Additionally, if you don't need a dynamic window where the content changes, you can simply use the following simple approach:

	// Dynamic window for the approval routing picker. 
	// This window also has an id variable.
	// Original inspiration provided by Ona Bai (http://dojo.telerik.com/@OnaBai/ekIba/2). 
	// To use, first create a div at the top of the page like so: <div id="dynamicDetailWindow"></div>
	function dynamicRoutingPickerWindow(id, id2, name, width, height) {
		var thisWin = $("#" + name).data("kendoWindow");
		if (thisWin) {
			thisWin.open();
		} else {
			thisWin = $("<div id='" + name + "'></div>").kendoWindow({
			actions: ["Minimize", "Maximize", "Refresh", "Close"],
			title: "Contract Details",
			content: "includes/routingPicker.cfm?contractId=" + id,
			width: width,
			height: height,
			modal: false,
			resizable: true,
			draggable: true,
			// Open the window near the top of the page.
			position:{
				top:"15%",
			},
			appendTo: "#dynamicRoutingPickerWindow",
			visible: true
			}).data("kendoWindow").center();
		}
    }

This entry was posted on April 19, 2019 at 2:15 AM and has received 2658 views.

Kendo scrollview


I have been using the scroll view on my home site at gregoryalexander.com quite a bit, and wanted to pass along a few tips. If you want to change the button size on the scroll view, use the following css. The default font-size is around 2em, to make the right and left arrows bigger, use anywhere from 6-8em, and 1em to make the arrows a bit smaller.

#nameOfScrollViewDiv .k-scrollview-next span, .k-scrollview-prev span {
	font-size: 8em;
} 

To use the scrollview to display a lot of text, I used the following approach. First, we need to use data-role='page' and create a 'white-space:normal' style for every element in order to allow for the text to wrap properly instead of going off of the scrollview page:

<div id="developmentScrollView" class="blueGradient">
	<!-- This is used for every page -->
	<div class="getConnected" data-role="page" style="white-space:normal;">
</div>

To constrain the text and allow the arrows to be seen visibility on the right and left, I created a css class for the div that contains the actual scrollview, and wrapper classes that constrain the text information in the proper spot. The class for the scrollview div (the outer class in this case):

/* Scroll view outer containers within the content blocks. */
#developmentScrollView {
	/* Text color */
	color: rgba(255, 255, 255, 0.9); 
	height: var(--scrollViewHeight);
	width: var(--scrollViewWidth); /* Don't use dynamic css vars set when the page loads. It screws stuff up. */
	margin: auto;	
	z-index: 2; /* This needs to be higher than the nav blocks */
}

And the three wrapper classes: the first class (firstScrollviewWrapper) is used on the first slide, and the second class (scrollviewWrapper) controls all of the slides after the first and last slide, and the last class (lastScrollviewWrapper) is used for the very last slide. These are used to keep the text separated from the arrows in order to make the arrows more visible.

.firstScrollviewWrapper {
	position: relative;
	display: table;
	left: 0%; /* The 2nd and x slides there after start to the right of the left arrow. */
	right: 10%; 
	margin: auto;
	width: 80%; /* the width of the scroll view container. */
	text-align: left;
	font-family: var(--scrollViewFont);
	font-size: var(--scrollViewFontSize);
}

.scrollviewWrapper {
	position: relative;
	display: table;
	left: 0%; /* The 2nd and x slides there after start to the right of the left arrow. */
	right: 10%; 
	margin: auto;
	width: 80%; /* the width of the scroll view container. */
	text-align: left;
	font-family: var(--scrollViewFont);
	font-size: var(--scrollViewFontSize);
}

.lastScrollviewWrapper {
	position: relative;
	display: table;
	left: 0%; /* The 2nd and x slides there after start to the right of the left arrow. */
	right: 0%; /* The last slide does not have a right arrow that we need to leave room for. */
	margin: auto;
	width: 80%; /* the width of the scroll view container. */
	text-align: left;
	font-family: var(--scrollViewFont);
	font-size: var(--scrollViewFontSize);
}

A demonstration of my approach can be seen on my www.gregoryalexander.com/index.cfm home page. Note: I am using css variables for the font family and font size.

This entry was posted on April 16, 2019 at 9:57 PM and has received 996 views.