Working with Callback and Control Rendering
 
Published: 05 Feb 2008
Abstract
In this article, Muhammad discusses the working of Callback and Controls rendering with the help of a sample application. He initially provides a short explanation of some of the important terms and then provides the steps required to accomplish the task along with both the callback server and client side codes.
by Muhammad ADnan Amanullah
Feedback
Average Rating: 
Views (Total / Last 10 Days): 41208/ 53

Introduction

In my previous article, I wrote about Callback and JSON based JavaScript serialization which you can find here. Callback doesn't cause postback and page rendering, neither full nor even partial. With it we can communicate with the server (IIS) and our server side code runs there successfully and could rebind our controls like DropDownList, GridView, ListView, DataList, Repeater, or any server side control to which you assign data. The problem is when the page won't render, its controls won't render, and if controls won't render then changes won't reflect. When changes don't reflect there won't be anything at the front end to show on the webpage.

This article is mainly about callback and rendering controls but through this tutorial you can also learn many other things; how postbacks work, how rendering works, how to dynamically create server-side controls, how to create DataTables dynamically in memory to bind with, how to get server-side controls during client-side execution and set their properties, and how to register client-side events of server side control from the server-side code.

Important Terms

First of all, I would like to briefly describe some terms of which I believe every web developer should be aware.

Postback

A postback is a mechanism of communication between client-side (browser) and server-side (IIS). Through a postback all contents of page/form(s) are sent to the server from client for processing. After following the page life cycle, all server-side contents get render into client-side code and the client (browser) displays the content. Callback is another form of communication between server and client. Callback doesn’t follow the page life cycle which is followed by standard postback, and it doesn't even cause rendering.

Rendering

Rendering is the process of converting server-side code/content into client-side code/content so the client (browser) can understand the code and could display the output. Browsers can understand, or you may say decode, code of client-side languages and scripts like HTML, DHTML, XHTML, JavaScript, VbScript, etc.

If rendering doesn't happen then changes won’t be reflected at client-side. Ajax leverages partial page postbacks automatically whereas callback doesn't, so programmer needs to perform that task manually.

The ASP.NET team has created a RenderControl method which is applied to the base control. By using that method we can render our controls very easily.

Callback

Callback is a lightweight process. It uses the well known XMLHTTP object internally to call server side methods. It doesn't cause page postback so doesn’t cause page rendering, so if we want to show output at client side, we need to make output html ourselves and render controls manually.

ICallbackEventHandler

ICallback is implemented in ASP.NET by using the ICallbackEventHandler interface, which has two methods, one of them used to be called from JavaScript (client-side code) and the other one returned results asynchronously back to the JavaScript function.

We just need to perform some action through server-side code at server-side and need to return results, but the results could be an instance or object of a class which might not be easy for JavaScript code to handle, so here we prefer JSON which stands for JavaScript Object Notation.

Real Time Scenario with implementation

Suppose we have categories, subcategories, products data, and we need to populate categories and subcategories which depend upon categories, and the data would be populated in two different DropDownLists. For products data which contains multiple columns so we need to show that data in tabular format so I would prefer GridView control.

So the situation would be load/populate categories on Page_Load and load/populate subcategories on the basis of selected category using callback and finally load products into Gridview on the basis of selected subcategory.

Before starting coding, I would like to write the Pseudo code for better understanding.

Steps

1.    Create Server side controls e.g. DropDownLists and GridView

2.    Load Categories on Page load

3.    Implement ICallbackEventHandler interface

4.    Create subcategories data in server memory to bind to Subcategory DropDownLists.

5.    Render control (subcategory DropDownLists) and show output.

6.    Create products data in server memory to bind to Products GridView.

7.    Render Control (products GridView) and return rendered contents to client side to show

8.    Set innerHTML of each control by rendered contents

Create DropDownLists and GridView Controls

Listing 1

<b>Categories:</b>
<br />
<asp:DropDownList ID="ddlCategories" runat="server" Width="100" onchange="CallSrv(this);">
</asp:DropDownList>
<br />
<b>Subcategories</b>:
<div id="ddlSubcategories">
</div>          
<b>Products:</b>
<div id="grvProducts">        
</div>
Callback Server side code

Let's implement the ICallbackEventHandler to call server side methods asynchronously step by step

Implement Server Side (C#) Page/Control class by System.Web.UI.ICallbackEventHandler

Following are definition of two methods which needs to implement:

RaiseCallbackEvent method invoke by JavaScript function

Listing 2

public void RaiseCallbackEvent(string eventArgument)
{
  string[]commands = eventArgument.Split("," .ToCharArray());
  if (commands[0].Equals("LoadSubCategory"))
  {
    DropDownList ddlSubcategories = new DropDownList();
    switch (commands[1])
    {
      case "Autos":
        ddlSubcategories.Items.Add("Cars");
        ddlSubcategories.Items.Add("Bikes");
        break;
      case "Electronics":
        ddlSubcategories.Items.Add("Computers");
        ddlSubcategories.Items.Add("TV");
        break;
    }
    ddlSubcategories.Attributes.Add("onchange""CallSrv(this);");
    System.Text.StringBuilder sb = new System.Text.StringBuilder();
    System.IO.StringWriter sw = new System.IO.StringWriter(sb);
    HtmlTextWriter htw = new HtmlTextWriter(sw);
 
    ddlSubcategories.RenderControl(htw);
    this.RenderedOutput = "LoadSubCategory," + sb.ToString();
  }
  else if (commands[0].Equals("LoadProducts"))
  {
    DataTable dtProducts = new DataTable();
    dtProducts.Columns.Add("ProductName");
    dtProducts.Columns.Add("ProductDescription");
    dtProducts.Columns.Add("ProductPrice");
    DataRow drProduct;
    switch (commands[1])
    {
      case "Cars":
        drProduct = dtProducts.NewRow();
        drProduct["ProductName"= "Honda";
        drProduct["ProductDescription"= "2000 CC";
        drProduct["ProductPrice"= "$1000";
        dtProducts.Rows.Add(drProduct);
        drProduct = dtProducts.NewRow();
        drProduct["ProductName"= "Toyota";
        drProduct["ProductDescription"= "1800 CC";
        drProduct["ProductPrice"= "$800";
        dtProducts.Rows.Add(drProduct);
        break;
      case "Bikes":
        drProduct = dtProducts.NewRow();
        drProduct["ProductName"= "Pak Hero";
        drProduct["ProductDescription"= "125 CC";
        drProduct["ProductPrice"= "$100";
        dtProducts.Rows.Add(drProduct);
        drProduct = dtProducts.NewRow();
        drProduct["ProductName"= "Honda";
        drProduct["ProductDescription"= "250 CC";
        drProduct["ProductPrice"= "$150";
        dtProducts.Rows.Add(drProduct);
        break;
      case "Computers":
        drProduct = dtProducts.NewRow();
        drProduct["ProductName"= "Dell";
        drProduct["ProductDescription"= "P4 Centrino";
        drProduct["ProductPrice"= "$400";
        dtProducts.Rows.Add(drProduct);
        drProduct = dtProducts.NewRow();
        drProduct["ProductName"= "IBM";
        drProduct["ProductDescription"= "P4 Think PAD";
        drProduct["ProductPrice"= "$350";
        dtProducts.Rows.Add(drProduct);
        break;
      case "TV":
        drProduct = dtProducts.NewRow();
        drProduct["ProductName"= "Sony";
        drProduct["ProductDescription"= "Plasma";
        drProduct["ProductPrice"= "$600";
        dtProducts.Rows.Add(drProduct);
        drProduct = dtProducts.NewRow();
        drProduct["ProductName"= "Philips";
        drProduct["ProductDescription"= "Projection";
        drProduct["ProductPrice"= "$550";
        dtProducts.Rows.Add(drProduct);
        break;
    }
    GridView grvProducts = new GridView();
    grvProducts.DataSource = dtProducts;
    grvProducts.DataBind();
 
    System.Text.StringBuilder sb = new System.Text.StringBuilder();
    System.IO.StringWriter sw = new System.IO.StringWriter(sb);
    HtmlTextWriter htw = new HtmlTextWriter(sw);
    grvProducts.RenderControl(htw);
    this.RenderedOutput = "LoadProducts," + sb.ToString();
  }
}
 
public string GetCallbackResult()
{
  return RenderedOutput;
}

In the Page_Load or Page_Init events

Following statements are used to register client side methods.

CallServer(arg, context) as name implies would use to call/raise server side method which was RaiseCallbackEvent string eventArgument)

ReceiveServerData(arg, context) would use to get result through arg parameter by GetCallbackResult()

Listing 3

//Register Client Script for Callback and populate categories
protected void Page_Load(object sender, EventArgs e)
{
  ClientScriptManager scriptMgr = Page.ClientScript;
  String cbReference = scriptMgr.GetCallbackEventReference(this"arg",
    "ReceiveServerData", "");
  String callbackScript = "function CallServer(arg, context) {" + cbReference +
    "; }";
  cm.RegisterClientScriptBlock(this.GetType(), "CallServer", callbackScript,
    true);
 
  if (!Page.IsPostBack)
  {
    //Load Products Data
    this.ddlCategories.Items.Add("Select");
    this.ddlCategories.Items.Add("Autos");
    this.ddlCategories.Items.Add("Electronics");
  }
}
Callback client side code

Listing 4

<script language = "JavaScript" type = "text/JavaScript">
function ReceiveServerData(arg, context)
{
  var cmd_content = arg.split(',');
  if (cmd_content[0] == 'LoadSubCategory')
  {
    document.getElementById('ddlSubcategories').innerHTML = cmd_content[1];
  }
  else
  {
    document.getElementById('grvProducts').innerHTML = cmd_content[1];
  }
}
function CallSrv(ddl)
{
 
  if (ddl.id == 'ddlCategories')
  {
    if (ddl.value != 'Select')
    {
      CallServer('LoadSubCategory' + ',' + ddl.value, '');
    }
  }
  else
  {
    CallServer('LoadProducts' + ',' + ddl.value, '');
  }
}
</script>

That's it. These are the steps which you need to use to call and get result from server side code using ICallback.

Asynchronously output would be within a millisecond and without Postback

Figure 1

Downloads

Conclusion

Callback is a lightweight technique used to call server side methods asynchronously from JavaScript without any postback and reloading/rendering of unnecessary parts of a page and unnecessary code.

So we can use that when we need to perform any operations at the backend on the server like updating records in database. You don't need to send all your contents of page in a request and make that object heavyweight which could cause slow performance.



User Comments

Title: NIKE NFL jerseys   
Name: NIKE NFL jerseys
Date: 2012-07-02 10:09:17 AM
Comment:
http://www.jersey2shop.com
http://www.cheapjersey2store.com
http://www.jerseycaptain.com
http://www.yourjerseyhome.com
We are professional jerseys manufacturer from china,wholesal.cheap nike nfl jerseys, mlb jerseys, nhl jerseys,nba jerseys and shoes
Cheap NFL,NBA,MLB,NHL
,heap jerseys,2012 nike nfl Jerseys,nba jersey and shorts,oklahoma city thunder jersey,official jeremy lin new york knicks jersey,NFL Jerseys Wholesale,blake griffin jersey blue,NFL jerseys For Sale online.All Our Jerseys Are Sewn On and Directly From Chinese Jerseys Factory
,Wholesale cheap jerseys,Cheap mlb jerseys,]Nike NFL Jerseys,Cheap China Wholesae,Wholesale jerseys From China,2012 nike nfl Jerseys,Jerseys From China,,2012 nike nfl Jerseys,Revolution 30 nba jerseys,jersey of nba chicago bulls direk rose ,nfl jerseys,green bay packers jerseys wholesale,Buffalo Bills nike nfl jerseys sale,good supplier soccer jerseys,cool base mlb jerseys,Revolution 30 nba jerseys,2012 stanley cup nhl jersey,
We are professional jerseys manufacturer from china,wholesal.cheap nike nfl jerseys, mlb jerseys, nhl jerseys,nba jerseys and shoes. www.yourjerseyhome.com
Title: rendered server controls   
Name: Jatin
Date: 2009-06-26 7:44:22 AM
Comment:
is it possible to render our gridview and datalist controls instead of "grvProducts" as DIV Tag. ?

Because i have one gridview and datalist now i just want to resfresh with callback ?
so how can i achieve this thing with render ?

thanks in advanced....
Title: Re: master pages   
Name: Muhammad Adnan (Author)
Date: 2009-01-15 10:59:12 AM
Comment:
It works for sure as i did many many times, you must be missing somewhere else. you might be using this somewhere else so i would suggest you to change its name and then try....

best of luck (y)
Title: master pages   
Name: sw
Date: 2009-01-15 10:54:06 AM
Comment:
the receiveserverdata function not called while using master pages.even the getcallbackresult returns the correct html.could you please let me know,the reason that could be with this.without master pages it works.[even after prefixing the exact id for the controls it doenot work with master pages]
Title: this.renderedoutput   
Name: snow white
Date: 2009-01-12 11:28:19 PM
Comment:
The HTML string is proper ,which was got from this.renderedoutput.The problem is ,the function receiveserverdata is not getting called, as i am not getting any alert messages during the button click,after the server side GetCallbackResult() and raisecallbackevents are called.But it works fine for the dropdown changes.
Title: Re: this.renderedoutput   
Name: Muhammad Adnan (Author)
Date: 2009-01-12 9:36:00 AM
Comment:
Ok its good that you are getting data. Did you check you are getting proper HTML in This.renderedoutput after it get assigned.

If that is also OK then check please in following function that either arg parameter is getting that html string

function ReceiveServerData(arg, context)

just do alert(arg);

HTH

If you still having problem, you can email me code or its screenshot.

Thanks and best of luck
Title: This.renderedoutput   
Name: snow white
Date: 2009-01-12 9:22:20 AM
Comment:
Hi,

Now i am able to bind the dropdown with the values.But,even if i get data from DB for the datagrid,the datagrid source and all are set fine,it is not visible.can you help me?Even i tried with a gridview.The parameters for the sql query and even the dataset from the query are coming fine.
Title: Re: Re: this.renderedoutput   
Name: Muhammad Adnan (Author)
Date: 2009-01-12 1:55:00 AM
Comment:
Check whether you are getting data from db or not or you email me at adnanaman@gmail.com your code i 'll try to see and fix

Thanks
Title: this.renderedoutput   
Name: snow white
Date: 2009-01-12 1:44:16 AM
Comment:
Hi,

Thanks for your quick response.I am now clear with that.But when i tried to bind the dropdowns with db data,everything is fine without any error on debug.But the new dropdowns (created similar to subcategories of this example) are not visible.Should i add any attributes to the controls for changing visibility property.But it works fine with the same example mentioned here.In my design part i have many trs and tds which contain the target div s.Can you help me.
Title: Re: this.renderedoutput   
Name: Muhammad Adnan (Author)
Date: 2009-01-12 12:36:46 AM
Comment:
You asked about this.renderedoutput
renderedoutput is class level string type variable which i am using in multiple methods/events

Let me know if you have any further query and thanks for your feedback
Title: this.renderedoutput   
Name: snow white
Date: 2009-01-12 12:23:26 AM
Comment:
Hi,

This is really a nice article.but i am a new bie.and i get the error "page doe not have a definition for renderedoutput".Can you help me in this.
Title: Re: CallServer   
Name: Author (Muhammad Adnan Amanullah)
Date: 2008-08-18 9:40:50 AM
Comment:
Thanks for your feedback,

Yes, It is changeable, but make sure wherever it's being using, rename.

Take care, Thanks,
Title: CallServer   
Name: Tapas Pati
Date: 2008-08-18 9:30:04 AM
Comment:
This topic very good.
Please can you tell mewhat is this (CallServer(arg, context)) function? this name is default or programmer can change it?
Please tell me.
Title: i realy like it   
Name: amol kagde
Date: 2008-08-14 6:46:45 AM
Comment:
hi

this article is very very useful for me.........

thsnk you for help!!
Title: Nice Article   
Name: Saurabh Maurya
Date: 2008-07-10 2:58:04 AM
Comment:
Dear Adnan,

Its really a very good article and going to help developers to implement callbacks in their applications.

Hope to hear some more useful information in near future.
Thanks a lot.

Saurabh
Title: Re: KS   
Name: Author
Date: 2008-03-18 1:03:10 AM
Comment:
First of all, thanks, for your feedback, i would like to explain rendering in somehow informal way, hope you could understand.
Rendering: is somehow conversion of server side code to client side code means when our code executed at web server IIS, it process that request (code) and then in response send back to browser. browser can't understand the code of asp.net, c#.net, vb.net or any server side language code, so it needs to be in that format which it could understand which is client side languages or scripts like html, xhtml, dhtml, javascript,... so in rendering process. our server side language code converted to client side language/script code and return back to browser to interpret.

in my article, i processed the dropdownlists and rendered their output in markup language format and send back to javascript code for browser to interpret.

ref: http://msdn2.microsoft.com/en-us/library/aa338806(VS.71).aspx
Title: Working with Callback and Control Rendering   
Name: KS
Date: 2008-03-17 4:37:46 PM
Comment:
Could you please explain what RenderedOutput is?
Title: Good One   
Name: Uzair Aziz
Date: 2008-03-14 8:17:45 AM
Comment:
Very good example,this will really helpful if somebody don't want to do programming on dropdown's SelectedIndexChanged Event handler.it is really time saving on server side.
Title: Re: Bobo   
Name: Author
Date: 2008-03-14 2:53:10 AM
Comment:
Yes you are right. it should be:

scriptMgr.RegisterClientScriptBlock(this.GetType(), "CallServer", callbackScript, true);

thanks :)
Title: A littlte wonder   
Name: Bobo
Date: 2008-03-14 2:47:44 AM
Comment:
Read,good,but what does "cm" mean in Listing3? it should be scriptMgr,is that correct?
Title: Re: Muhammad Nadeem   
Name: Author
Date: 2008-03-13 1:55:50 PM
Comment:
surely keep you update next time sir :)
Title: good work   
Name: Muhammad Nadeem
Date: 2008-03-13 10:47:23 AM
Comment:
hi man good work.. why u did not tell us..
Title: Great piece of work   
Name: Dan Bambling
Date: 2008-03-13 9:37:15 AM
Comment:
This great, a real help and easy to understand. This sertainly solves having to rely on nested update pannels.
Title: Excelent   
Name: aliraza
Date: 2008-03-13 8:17:38 AM
Comment:
excellent, very good article
Title: Great Effort i must say.   
Name: Muhammad Moazzam Humayun
Date: 2008-03-13 5:54:21 AM
Comment:
Wow, very nice article with a superb example.

i have tested it and i love the way u have explained this technique.

:-)

Moazzam
Title: Excelent!!!!!!!!!!!!!!!!!!!!!!!!   
Name: cto-Shaukat
Date: 2008-03-13 3:19:37 AM
Comment:
Excellent article ,it solved a lot of mine problem
Title: Excellent!!!   
Name: Rajasekhar Bathula
Date: 2008-03-13 12:17:02 AM
Comment:
I have been searching for an like this.Finally,I got it.

Excellent one!!
Title: Very Nice   
Name: Matt
Date: 2008-03-12 1:06:45 PM
Comment:
Excellent, we've been looking for somethign like this! AJAX partial-postback is just too heavy.
Title: Good Article   
Name: Kauser
Date: 2008-02-05 3:45:38 PM
Comment:
You have written a very useful article. I will surely try this code. Keep it up!
Title: comments?   
Name: Muhammad Adnan
Date: 2008-02-05 12:37:09 AM
Comment:
waiting for readerz comments :)

Product Spotlight
Product Spotlight 





Community Advice: ASP | SQL | XML | Regular Expressions | Windows


©Copyright 1998-2024 ASPAlliance.com  |  Page Processed at 2024-04-26 9:40:30 PM  AspAlliance Recent Articles RSS Feed
About ASPAlliance | Newsgroups | Advertise | Authors | Email Lists | Feedback | Link To Us | Privacy | Search