[CLOSED] Rendering Ext.Net control (generated during Ajax event) to an ExtJs client side object?

  1. #1

    [CLOSED] Rendering Ext.Net control (generated during Ajax event) to an ExtJs client side object?

    Hi,

    I have an ExtJs tab panel created in JavaScript using ExtJs (not Ext.Net. I am not in a position to change this at the moment, unfortunately).

    What I'd like to do is when a tab is activated for the first time,

    1. Make an ajax call to the server
    2. Generate a grid panel there using Ext.Net, and
    3. send the generated JavaScript back so I can place it in the tab.

    I've seen examples such as these:


    These are close to what I want, except those examples load their content into a Panel or Window generated using Ext.Net so all the wireup code is already there, whereas my TabPanel is generated directly using ExtJs.

    The reason I'd like to get the server to send me a grid panel is that we already have custom code to generate our grids using Ext.Net, so I'd like to reuse that (as we work out the columns and their types on the fly based on some other info) so it is not easy to generate this using ExtJs directly on the client side, which is what I'd otherwise do.

    Are there any pointers or examples that I may have missed?

    E.g. I am guessing the ajax call could be made to a custom ashx handler which will return the right JavaScript that I then manually invoke/execute and add the resulting grid to the tab. If that is right, I guess in a ProcessRequest of an ashx if I just did a new Ext.Net.GridPanel() could I just return a rendered version of it to the response stream, using something like RenderControl(writer) and write it to my own html writer which is then returned in a Response.Write(), or does it need to be wrapped in another object which I JSON.Serialize() instead? Or what is best/recommended practice if trying to do this?

    I notice in your Remote_Load example above, in the source, it generates this bit of relevant script:
    directEvents:{click:{fn:function(item,e){var params=arguments;Ext.net.DirectEvent.confirmRequest({control:this});},delay:20}
    What is Ext.net.DirectEvent.confirmRequest(). Is that something I should be trying to use?

    Thanks!
    Last edited by Daniil; Dec 08, 2010 at 8:30 PM. Reason: [CLOSED]
  2. #2
    Hi,

    Please see the following sample
    <%@ Page Language="C#" %>
    
    <%@ Import Namespace="Button=Ext.Net.Button" %>
    
    <%@ Register Assembly="Ext.Net" Namespace="Ext.Net" TagPrefix="ext" %>
    
    <script runat="server">
        [DirectMethod(Namespace="XRender", ShowMask = true)]
        public void RenderGrid(string container)
        {
            this.BuildGridPanel().AddTo(container);
        }
    
        private GridPanel BuildGridPanel()
        {
            return new GridPanel
            {
                Border = false,
                StripeRows = true,
                TrackMouseOver = true,
                AutoExpandColumn = "Company",
                Store =  
                {
                    this.BuildStore()
                },
                SelectionModel = 
                { 
                    new RowSelectionModel { SingleSelect = true }
                },
                ColumnModel =
                {
                    Columns =
                    {
                        new Column 
                        { 
                            ColumnID = "Company", 
                            Header = "Company", 
                            DataIndex = "company"  
                        },
                        new Column
                        {
                            Header = "Price",
                            DataIndex = "price",
                            Renderer = { Format = RendererFormat.UsMoney }
                        },
                        new Column
                        {
                            Header = "Change",
                            DataIndex = "change",
                            Renderer = { Fn = "change" }
                        },
                        new Column
                        {
                            Header = "Change",
                            DataIndex = "pctChange",
                            Renderer = { Fn = "pctChange" }
                        },
                        new DateColumn
                        {
                            Header = "Last Updated",
                            DataIndex = "lastChange"
                        }
                    }
                }
            };
        }
    
        private Store BuildStore()
        {
            Store store = new Store
            {
                ID = "Store1", // <-- ID is Required
                Reader = 
                { 
                    new ArrayReader 
                    {
                        Fields = 
                        {
                            new RecordField("company"),
                            new RecordField("price", RecordFieldType.Float),
                            new RecordField("change", RecordFieldType.Float),
                            new RecordField("pctChange", RecordFieldType.Float),
                            new RecordField("lastChange", RecordFieldType.Date, "M/d hh:mmtt")
                        }
                    }
                }
            };
    
            store.DataSource = this.Data;
            store.DataBind();
    
            return store;
        }
        
        private object[] Data
        {
            get
            {
                return new object[]
                {
                    new object[] { "3m Co", 71.72, 0.02, 0.03, "9/1 12:00am" },
                    new object[] { "Alcoa Inc", 29.01, 0.42, 1.47, "9/1 12:00am" },
                    new object[] { "Altria Group Inc", 83.81, 0.28, 0.34, "9/1 12:00am" },
                    new object[] { "American Express Company", 52.55, 0.01, 0.02, "9/1 12:00am" },
                    new object[] { "American International Group, Inc.", 64.13, 0.31, 0.49, "9/1 12:00am" },
                    new object[] { "AT&T Inc.", 31.61, -0.48, -1.54, "9/1 12:00am" },
                    new object[] { "Boeing Co.", 75.43, 0.53, 0.71, "9/1 12:00am" },
                    new object[] { "Caterpillar Inc.", 67.27, 0.92, 1.39, "9/1 12:00am" },
                    new object[] { "Citigroup, Inc.", 49.37, 0.02, 0.04, "9/1 12:00am" },
                    new object[] { "E.I. du Pont de Nemours and Company", 40.48, 0.51, 1.28, "9/1 12:00am" },
                    new object[] { "Exxon Mobil Corp", 68.1, -0.43, -0.64, "9/1 12:00am" },
                    new object[] { "General Electric Company", 34.14, -0.08, -0.23, "9/1 12:00am" },
                    new object[] { "General Motors Corporation", 30.27, 1.09, 3.74, "9/1 12:00am" },
                    new object[] { "Hewlett-Packard Co.", 36.53, -0.03, -0.08, "9/1 12:00am" },
                    new object[] { "Honeywell Intl Inc", 38.77, 0.05, 0.13, "9/1 12:00am" },
                    new object[] { "Intel Corporation", 19.88, 0.31, 1.58, "9/1 12:00am" },
                    new object[] { "International Business Machines", 81.41, 0.44, 0.54, "9/1 12:00am" },
                    new object[] { "Johnson & Johnson", 64.72, 0.06, 0.09, "9/1 12:00am" },
                    new object[] { "JP Morgan & Chase & Co", 45.73, 0.07, 0.15, "9/1 12:00am" },
                    new object[] { "McDonald\"s Corporation", 36.76, 0.86, 2.40, "9/1 12:00am" },
                    new object[] { "Merck & Co., Inc.", 40.96, 0.41, 1.01, "9/1 12:00am" },
                    new object[] { "Microsoft Corporation", 25.84, 0.14, 0.54, "9/1 12:00am" },
                    new object[] { "Pfizer Inc", 27.96, 0.4, 1.45, "9/1 12:00am" },
                    new object[] { "The Coca-Cola Company", 45.07, 0.26, 0.58, "9/1 12:00am" },
                    new object[] { "The Home Depot, Inc.", 34.64, 0.35, 1.02, "9/1 12:00am" },
                    new object[] { "The Procter & Gamble Company", 61.91, 0.01, 0.02, "9/1 12:00am" },
                    new object[] { "United Technologies Corporation", 63.26, 0.55, 0.88, "9/1 12:00am" },
                    new object[] { "Verizon Communications", 35.57, 0.39, 1.11, "9/1 12:00am" },
                    new object[] { "Wal-Mart Stores, Inc.", 45.45, 0.73, 1.63, "9/1 12:00am" }
                };
            }
        }
    </script>
    
    <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" 
        "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
    
    <html xmlns="http://www.w3.org/1999/xhtml">
    <head id="Head1" runat="server">
        <title>Ext.NET Example</title>
        <link href="../../../../resources/css/examples.css" rel="stylesheet" type="text/css" />    
    
        <script type="text/javascript">
            var template = '<span style="color:{0};">{1}</span>';
    
            var change = function (value) {
                return String.format(template, (value > 0) ? "green" : "red", value);
            };
    
            var pctChange = function (value) {
                return String.format(template, (value > 0) ? "green" : "red", value + "%");
            };
            
            var buildTabPanel = function () {
                var tabs = new Ext.TabPanel({
                    height: 500,
                    activeItem : 0,
                    renderTo : Ext.getBody(),
                    
                    items : [
                        {
                            title : "Tab1",
                            html : "Please activate second tab to see the grid"
                        }, 
                        {
                            id : "tab2",                        
                            title : "Tab2",
                            layout : "fit",
                            listeners : {
                                activate : {
                                    fn : function () {
                                        XRender.RenderGrid("tab2");
                                    },
                                    single : true
                                }
                            }                        
                        }
                    ]
                });
            };
        </script>
    </head>
    <body>
        <ext:ResourceManager ID="ResourceManager1" runat="server">
            <Listeners>
                <DocumentReady Handler="buildTabPanel();" />
            </Listeners>
        </ext:ResourceManager>
        
        
    </body>
    </html>
    Vladimir Shcheglov
    Sr. Developer
  3. #3
    Vladimir,

    Many thanks for that example. Seems to work very nicely.

    I wonder, is there a way to generate this GridPanel in a generic handler (ashx) that I can just return as application/json perhaps? In that scenario, I would imagine that my activate handler will make an ajax request to the ashx more directly.

    If this is not possible, then probably not a big issue, as the DirectMethod approach you provide will also work in many of my cases.

    I used your code example below and put the C# into an ashx and added the following:

    public void ProcessRequest(HttpContext context)
    {
        context.Response.ContentType = "application/json";
    
        GridPanel grid = BuildGridPanel();
    
        grid.Render("blah", RenderMode.Auto, true);
    
    }
    This seems to work, but it is not clear to me what the right overload of Render() I should use or what those 3 parameters mean. I just directly visited the ashx in the browser and saw the JavaScript come back, but it includes this bit in it:

    {script:"Ext.net.ResourceMgr.load([{url:\"/extnet/extnet-data-js/ext.axd?v=26099\"}], function(){Ext.net.append(Ext.net.getEl(Ext.getBody()),[\"<div id=\\\"id9e44a62000d64ce48d6769fa52cd8428_Container\\\">\",\"</div>\"].join(''));Ext.net.ResourceMgr.destroyCmp(\"id9e44a62000d64ce48d6769fa52cd8428\");new Ext.net.GridPanel(
    // rest of the grid panel construction snipped
    I didn't quite follow these divs with guid-like Ids so I am not clear on how I could get it to render where I want... Maybe the request to the ashx needs to be given an id of a component I need to render it to and the handler code can get that off the Request and use that as the first paramter to grid.Render()?

    I've got as far as doing something like this in the tab's activate function handler that you have:

    Ext.Ajax.request({
        url:'GridGenerator.ashx',
        success: function(response, requestConfig) { console.log(response); },
        method:'GET'
    });
    I guess I'd then need to JSON.parse() the response.responseText (is there a safer way to do that?) etc. But that seems like I am moving away from the effort ExtJS has already made in this area, and trying to re-invent what is already available. Maybe it is my lack of ExtJs knowledge here, but any pointers would be useful.

    The reason I am contemplating the ashx approach is so that existing ASPX pages don't need modifications to reuse this capability (only JavaScript + new ashx)... and I can also call it from non ASPX pages potentially...
  4. #4
    Hi,

    You can create Ext.Net widget anywhere (http handler, web service and etc)
    Please see the following sample

    Page
    <%@ Page Language="C#" %>
    <%@ Register Assembly="Ext.Net" Namespace="Ext.Net" TagPrefix="ext" %>
     
    <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" 
        "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
     
    <html xmlns="http://www.w3.org/1999/xhtml">
    <head id="Head1" runat="server">
        <title>Ext.NET Example</title>
        <link href="../../../../resources/css/examples.css" rel="stylesheet" type="text/css" />    
     
        <script type="text/javascript">
            var template = '<span style="color:{0};">{1}</span>';
     
            var change = function (value) {
                return String.format(template, (value > 0) ? "green" : "red", value);
            };
     
            var pctChange = function (value) {
                return String.format(template, (value > 0) ? "green" : "red", value + "%");
            };
             
            var buildTabPanel = function () {
                var tabs = new Ext.TabPanel({
                    height: 500,
                    activeItem : 0,
                    renderTo : Ext.getBody(),
                     
                    items : [
                        {
                            title : "Tab1",
                            html : "Please activate second tab to see the grid"
                        }, 
                        {
                            id : "tab2",                        
                            title : "Tab2",
                            layout : "fit",
                            listeners : {
                                activate : {
                                    fn : function () {
                                        Ext.net.DirectEvent.request({
                                            url : "Handler1.ashx",
                                            cleanRequest : true,
                                            extraParams : {
                                                container : "tab2"
                                            },
                                            eventMask : {
                                                showMask:true
                                            }
                                        });
                                    },
                                    single : true
                                }
                            }                        
                        }
                    ]
                });
            };
        </script>
    </head>
    <body>
        <ext:ResourceManager ID="ResourceManager1" runat="server">
            <Listeners>
                <DocumentReady Handler="buildTabPanel();" />
            </Listeners>
        </ext:ResourceManager>
         
         
    </body>
    </html>
    Http handler
    using System;
    using System.Collections.Generic;
    using System.Web;
    using System.Web.Services;
    using Ext.Net;
    
    namespace Test
    {
        /// <summary>
        /// Summary description for $codebehindclassname$
        /// </summary>
        [WebService(Namespace = "http://tempuri.org/")]
        [WebServiceBinding(ConformsTo = WsiProfiles.BasicProfile1_1)]
        public class Handler1 : IHttpHandler
        {
    
            public void ProcessRequest(HttpContext context)
            {
                new DirectResponse(this.BuildGridPanel().ToScript(RenderMode.AddTo, context.Request["container"])).Return();            
            }
    
            private GridPanel BuildGridPanel()
            {            
                return new GridPanel
                {
                    Border = false,
                    StripeRows = true,
                    TrackMouseOver = true,
                    AutoExpandColumn = "Company",
                    Store =  
                {
                    this.BuildStore()
                },
                    SelectionModel = 
                { 
                    new RowSelectionModel { SingleSelect = true }
                },
                    ColumnModel =
                    {
                        Columns =
                    {
                        new Column 
                        { 
                            ColumnID = "Company", 
                            Header = "Company", 
                            DataIndex = "company"  
                        },
                        new Column
                        {
                            Header = "Price",
                            DataIndex = "price",
                            Renderer = { Format = RendererFormat.UsMoney }
                        },
                        new Column
                        {
                            Header = "Change",
                            DataIndex = "change",
                            Renderer = { Fn = "change" }
                        },
                        new Column
                        {
                            Header = "Change",
                            DataIndex = "pctChange",
                            Renderer = { Fn = "pctChange" }
                        },
                        new DateColumn
                        {
                            Header = "Last Updated",
                            DataIndex = "lastChange"
                        }
                    }
                    }
                };
            }
    
            private Store BuildStore()
            {
                Store store = new Store
                {
                    ID = "Store1", // <-- ID is Required
                    Reader = 
                { 
                    new ArrayReader 
                    {
                        Fields = 
                        {
                            new RecordField("company"),
                            new RecordField("price", RecordFieldType.Float),
                            new RecordField("change", RecordFieldType.Float),
                            new RecordField("pctChange", RecordFieldType.Float),
                            new RecordField("lastChange", RecordFieldType.Date, "M/d hh:mmtt")
                        }
                    }
                }
                };
    
                store.DataSource = this.Data;
                store.DataBind();
    
                return store;
            }
    
            private object[] Data
            {
                get
                {
                    return new object[]
                {
                    new object[] { "3m Co", 71.72, 0.02, 0.03, "9/1 12:00am" },
                    new object[] { "Alcoa Inc", 29.01, 0.42, 1.47, "9/1 12:00am" },
                    new object[] { "Altria Group Inc", 83.81, 0.28, 0.34, "9/1 12:00am" },
                    new object[] { "American Express Company", 52.55, 0.01, 0.02, "9/1 12:00am" },
                    new object[] { "American International Group, Inc.", 64.13, 0.31, 0.49, "9/1 12:00am" },
                    new object[] { "AT&T Inc.", 31.61, -0.48, -1.54, "9/1 12:00am" },
                    new object[] { "Boeing Co.", 75.43, 0.53, 0.71, "9/1 12:00am" },
                    new object[] { "Caterpillar Inc.", 67.27, 0.92, 1.39, "9/1 12:00am" },
                    new object[] { "Citigroup, Inc.", 49.37, 0.02, 0.04, "9/1 12:00am" },
                    new object[] { "E.I. du Pont de Nemours and Company", 40.48, 0.51, 1.28, "9/1 12:00am" },
                    new object[] { "Exxon Mobil Corp", 68.1, -0.43, -0.64, "9/1 12:00am" },
                    new object[] { "General Electric Company", 34.14, -0.08, -0.23, "9/1 12:00am" },
                    new object[] { "General Motors Corporation", 30.27, 1.09, 3.74, "9/1 12:00am" },
                    new object[] { "Hewlett-Packard Co.", 36.53, -0.03, -0.08, "9/1 12:00am" },
                    new object[] { "Honeywell Intl Inc", 38.77, 0.05, 0.13, "9/1 12:00am" },
                    new object[] { "Intel Corporation", 19.88, 0.31, 1.58, "9/1 12:00am" },
                    new object[] { "International Business Machines", 81.41, 0.44, 0.54, "9/1 12:00am" },
                    new object[] { "Johnson & Johnson", 64.72, 0.06, 0.09, "9/1 12:00am" },
                    new object[] { "JP Morgan & Chase & Co", 45.73, 0.07, 0.15, "9/1 12:00am" },
                    new object[] { "McDonald\"s Corporation", 36.76, 0.86, 2.40, "9/1 12:00am" },
                    new object[] { "Merck & Co., Inc.", 40.96, 0.41, 1.01, "9/1 12:00am" },
                    new object[] { "Microsoft Corporation", 25.84, 0.14, 0.54, "9/1 12:00am" },
                    new object[] { "Pfizer Inc", 27.96, 0.4, 1.45, "9/1 12:00am" },
                    new object[] { "The Coca-Cola Company", 45.07, 0.26, 0.58, "9/1 12:00am" },
                    new object[] { "The Home Depot, Inc.", 34.64, 0.35, 1.02, "9/1 12:00am" },
                    new object[] { "The Procter & Gamble Company", 61.91, 0.01, 0.02, "9/1 12:00am" },
                    new object[] { "United Technologies Corporation", 63.26, 0.55, 0.88, "9/1 12:00am" },
                    new object[] { "Verizon Communications", 35.57, 0.39, 1.11, "9/1 12:00am" },
                    new object[] { "Wal-Mart Stores, Inc.", 45.45, 0.73, 1.63, "9/1 12:00am" }
                };
                }
            }
    
            public bool IsReusable
            {
                get
                {
                    return false;
                }
            }
        }
    }
    Vladimir Shcheglov
    Sr. Developer
  5. #5
    Thanks again for your prompt reply. That answer looks perfect! I didn't know about the "DirectResponse" class, so that is great to come across!

    You can mark this as solved.

    Many thanks!
  6. #6
    By the way, while this does work nicely, I've noticed a slight issue:

    In ExtJs, as I understand, you don't have to provide an id for the new tab (or any control, I think?), and if you don't, a unique one will be created for you, something like ext-comp-123.

    In your code example where you created a tab with id of "tab2", if you remove that line you'll get an error, when the code subsequently tries to execute ext-comp-123.addAndDoLayout() because this of course causes a parser/syntax error.

    Is there a way to address this, or is this an ExtJs level issue? Are you able to use Ext.getCmp() -- or whatever the right method is -- instead of directly using that id? I tried to look at the overloads for DirectResponse().ToScript() but couldn't see anything obvious to me...

    Its probably not a big deal for me, but sometimes in my Js, I can't know for sure that I will have a unique id.
  7. #7
    Hi anup,

    Probably the following method can help you.
    http://dev.sencha.com/deploy/dev/doc...=Ext&member=id

    You could generate it, save somewhere and use as id. Then you can retrieve a Component by Ext.getCmp(id) that you mentioned.
  8. #8
    Maybe it needs to change .ToScript() (or something else) method. I will discuss this with Dev Team.

    For now there is a solution for you using Ext.id(...) I mentioned. There is "ext-gen" prefix by default. You could change it.

    Example (see '// changed' comments)
    {
        id : Ext.id(null, "myIdPrefix"),     // changed
        title : "Tab2",
        layout : "fit",
        listeners : {
            activate : {
                fn : function () {
                    Ext.net.DirectEvent.request({
                        url : "Handler1.ashx",
                        cleanRequest : true,
                        extraParams : {
                            container : this.id     // changed
                        },
                        eventMask : {
                            showMask:true
                        }
                    });
                },
                single : true
            }
        }                       
    }
  9. #9
    Thanks for the tip to use Ext.id(). That's perfect!

Similar Threads

  1. Execute Ajax/Direct Event from Client-Side?
    By Tbaseflug in forum 1.x Help
    Replies: 5
    Last Post: Dec 16, 2010, 5:35 PM
  2. client side script after ajax event
    By [WP]joju in forum 1.x Help
    Replies: 0
    Last Post: Nov 25, 2009, 2:30 AM
  3. Replies: 6
    Last Post: Sep 01, 2009, 1:06 PM
  4. [CLOSED] About Coolite client side object model
    By pumpkin in forum 1.x Premium Help
    Replies: 2
    Last Post: Jun 11, 2009, 2:50 AM
  5. Replies: 2
    Last Post: Mar 08, 2009, 10:11 AM

Posting Permissions