The easiest way to understand building a new client side component by using the JavaScript behavior mechanism is to do follow a step by step sample. It is first implemented without using any server side help by only implementing JavaScript in a plain html file. Then the JavaScript Behavior is modeled and at last it is migrated into an ASP.NET user control.
There are 2 advantages when working this way. First you can focus on the JavaScript implementation from the beginning and can avoid the typical cache issues when using included JavaScript files and second you can see some of the reasons where Behaviors take advantage over plain JavaScript
implementation.
The sample functionality I use to show this is a simple dice (German: Würfel). It basically consists of defining new properties, specific methods and event handlers by building a JavaScript prototype object for each behavior. Also a common binding functionality is needed that attaches these definitions to a HTML object after the page is loaded. Script include files can be used to bring the prototype objects into the pages.
You can download all files from
http://www.mathertel.de/Downloads/Start_JSBTutorial.aspx.
Building the JavaScript Behavior Basics
1. Coding it all in one place
The best place for writing a new control is inside a single HTML file that contains all the fragments that you will separate later into different locations:
<script type="text/javascript" src="../controls/jcl.js"></script> in the <head> element.
• A CSS section inside the <head> element that will hold all the style rules that we will later move out into the common css file. You can code all the css rules into the html elements first if you like. Later you should not include any CSS code inside the rendered html elements mo make some personalization and style adoption easier.
• The <script type="text/javascript"> element that will contain the
JavaScript behavior definition using a object notation in the JSON coding style and the statement for binding the JavaScript behavior object to the HTML element.
• A HTML object structure that will be used for rendering the new control. This should be a single outer element that may contain complex inner HTML elements. Give it a unique id that can be used to identify the first prototype.
• And a small <script type="text/javascript"> element that will cause to bind the defined Behavior to the HTML element.
The advantage of using this intermediate development state is that you can hit F5 in the browser and can be sure that all your code will reload as expected. You also will not have any timing problems that may happen when JavaScript or CSS files are cached locally. You need no server side functionality so a *.htm file is fine for now.
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Strict//EN"> <html xmlns="http://www.w3.org/1999/xhtml">
<head>
<title>Ein Wuerfel</title>
<script type="text/javascript" src="jcl.js"></script>
<style type="text/css"> .Wuerfel {
border: solid 2px green; width:40px; height:40px; overflow:hidden; cursor: pointer; background-color:#EEFFEE;
font-size: 30px; padding:20px; text-align: center; } </style> <script type="text/javascript"> var WuerfelBehaviour = { onclick: function(evt) { Wuerfel1.innerText = Math.floor(Math.random()*6)+1; } } // WuerfelBehaviour </script> </head> <body>
<div id="Wuerfel1" class="Wuerfel" unselectable="on">click</div>
<script defer="defer" type="text/javascript"> jcl.LoadBehaviour("Wuerfel1", WuerfelBehaviour); </script>
</body> </html>
The filewuerfel_01.htm contains an implementation in this state. 2. replacing all hard-coded references
If you want to make it possible to use the same control multiple times on the same page then you must avoid using hard coded ids or names. The only place where you should find the id of the outer HTML element is inside the first parameter of the jcl.LoadBehaviour function call.
The other thing you should take care too are the parameters / attributes that you want to use together with the new control. You should define the as attributes in the outer HTML element and as properties of the JavaScript behavior definition. There should not be any constants inside the JSON object.
If everything is well done you can make a second copy of the outer HTML element with a new id and can bind the same behavior definition to it. Both elements should now work as expected independently. Check also if the parameters work as expected.
The filewuerfel_02.htm contains an implementation in this state. 3. separating the behavior code
The next step is to extract the core of the behavior into a new *.js file and reference this file by using a new <script type="text/javascript"
src="wuerfel.js"></script> in the <head> element.
The advantage of a separate file for the behavior definition is that the implementation can be cached by the browser independently from the individual use and If the control is reused in different pages you can see dramatic performance improvements.
The filewuerfel_03.htm andwuerfel.js file contain an implementation in this state and wuerfel.js has also got some more functionality.
4. separating the CSS style definitions
The style of the new control should not be coded inline into the html code but should be separated into some css statements. So I use a classname for the top element of the control by using the name of the behavior. If you have special inner elements they can be prefixed by the same name or you might use css selectors by specifying the outer and inner class names. Sample:
div.TreeView .do { ... } div.TreeView .dc { ... }
Because the css statements are usually much smaller then the JavaScript code for a control I do not extract the css statements into separate files but include them all in a single css file for all the controls I've done. The *.css files are cached by the browser so loading them from the server doesn't occur too often.