jQWidgets Forums

jQuery UI Widgets Forums General Discussions Plugins AngularJS Problems using jqx-grid with dataAdapter and remote data

This topic contains 10 replies, has 2 voices, and was last updated by  Peter Stoev 10 years, 5 months ago.

Viewing 11 posts - 1 through 11 (of 11 total)
  • Author

  • badera
    Participant

    Dear jqWidgets Team

    I have a serious problem using jqx-grid with jqxDataAdapter retrieving remote data – yes, I need to use the jqxDataAdapter to do the AJAX calls rather than using $http service of angular, because I will need to switch the grid to “virtualmode” in the future.

    So I have taken your base example from http://www.jqwidgets.com/jquery-widgets-demo/demos/jqxgrid/bindingtojson.htm?arctic
    and changed it to angular accordingly:

    
    <!DOCTYPE html>
    <html ng-app="demoApp">
    <head>
        <title id="Description">Minimal Example</title>
        <link rel="stylesheet" type="text/css" href="http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/styles/jqx.base.css"/>
        <script type="text/javascript" src="http://www.jqwidgets.com/jquery-widgets-demo/scripts/angular.min.js"></script>
        <script type="text/javascript" src="http://www.jqwidgets.com/jquery-widgets-demo/scripts/jquery-1.11.1.min.js"></script>
        <script type="text/javascript" src="http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/jqxcore.js"></script>
        <script type="text/javascript" src="http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/jqxdata.js"></script>
        <script type="text/javascript" src="http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/jqxgrid.js"></script>
        <script type="text/javascript" src="http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/jqxgrid.selection.js"></script>
        <script type="text/javascript" src="http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/jqxmenu.js"></script>
        <script type="text/javascript" src="http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/jqxbuttons.js"></script>
        <script type="text/javascript" src="http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/jqxscrollbar.js"></script>
        <script type="text/javascript" src="http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/jqxdropdownlist.js"></script>
        <script type="text/javascript" src="http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/jqxlistbox.js"></script>
        <script type="text/javascript" src="http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/jqxgrid.sort.js"></script>
        <script type="text/javascript" src="http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/jqxangular.js"></script>
        <script type="text/javascript">
            var demoApp = angular.module("demoApp", ["jqwidgets"]);
    
            demoApp.controller("demoController", function ($scope) {
    
                var url = "http://www.jqwidgets.com/jquery-widgets-demo/demos/sampledata/beverages.txt";
    
                // prepare the data
                var source =
                {
                    datatype: "json",
                    datafields: [
                        { name: 'name', type: 'string' },
                        { name: 'type', type: 'string' },
                        { name: 'calories', type: 'int' },
                        { name: 'totalfat', type: 'string' },
                        { name: 'protein', type: 'string' }
                    ],
                    id: 'id',
                    url: url
                };
                var dataAdapter = new $.jqx.dataAdapter(source);
    
                $scope.text = "binding not completed";
                
                $scope.gridSettings =
                {
                    altrows: true,
                    width: '100%',
                    height: '100%',
                    source: dataAdapter,
    
                    bindingcomplete: function (event) {
                        $scope.text = "binding is completed";
                    },
    
                    columns: [
                      { text: 'Name', datafield: 'name', width: 250 },
                      { text: 'Beverage Type', datafield: 'type', width: 250 },
                      { text: 'Calories', datafield: 'calories', width: 180 },
                      { text: 'Total Fat', datafield: 'totalfat', width: 120 },
                      { text: 'Protein', datafield: 'protein', minwidth: 120 }
                    ]
                }
            })
            ;
        </script>
    </head>
    <body>
    <div ng-controller="demoController">
        <jqx-grid jqx-instance="grid" jqx-create="gridSettings" jqx-settings="gridSettings"></jqx-grid>
        <p>{{text}}</p>
    </div>
    </body>
    </html>
    

    As soon as I implement the bindingcomplete function, there is an endless loop raising errors (Chrome crashes after some minutes).
    You can easily reproduce it by copying the example abouve. Just make sure to have no Cross-Origin-Error preventing from getting the data e.g. by using “chrome.exe –disable-web-security”.

    What is wrong? – Please do not point me to your angular example (http://www.jqwidgets.com/jquery-widgets-demo/demos/jqxangular/grid-binding-to-json.htm?arctic) doing the same but performing the AJAX call with $http – I like to use jqxDataAdapter as I described.

    Thanks in advance for your help!
    – badera


    badera
    Participant

    It is even worse: Check the snippet below:

    
    <!DOCTYPE html>
    <html ng-app="demoApp">
    <head>
        <title id="Description">Minimal Example</title>
        <link rel="stylesheet" type="text/css" href="http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/styles/jqx.base.css"/>
        <script type="text/javascript" src="http://www.jqwidgets.com/jquery-widgets-demo/scripts/angular.min.js"></script>
        <script type="text/javascript" src="http://www.jqwidgets.com/jquery-widgets-demo/scripts/jquery-1.11.1.min.js"></script>
        <script type="text/javascript" src="http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/jqx-all.js"></script>
        <script type="text/javascript">
            var demoApp = angular.module("demoApp", ["jqwidgets"]);
    
            demoApp.controller("demoController", function ($scope) {
    
                var url = "http://www.jqwidgets.com/jquery-widgets-demo/demos/sampledata/beverages.txt";
    
                // prepare the data
                var source =
                {
                    datatype: "json",
                    datafields: [
                        { name: 'name', type: 'string' },
                        { name: 'type', type: 'string' },
                        { name: 'calories', type: 'int' },
                        { name: 'totalfat', type: 'string' },
                        { name: 'protein', type: 'string' }
                    ],
                    id: 'id',
                    url: url
                };
                var dataAdapter = new $.jqx.dataAdapter(source);
    
                $scope.gridSettings =
                {
                    altrows: true,
                    width: '100%',
                    height: '100%',
                    source: dataAdapter,
                    filterable: true,
                    showfilterrow: true,
                    
                    rowselect: function (event) {
                       console.log("Now, the filtering does no more work!");
                    },
    
                    columns: [
                      { text: 'Name', datafield: 'name', width: 250 },
                      { text: 'Beverage Type', datafield: 'type', width: 250 },
                      { text: 'Calories', datafield: 'calories', width: 180 },
                      { text: 'Total Fat', datafield: 'totalfat', width: 120 },
                      { text: 'Protein', datafield: 'protein', minwidth: 120 }
                    ]
                }
            })
            ;
        </script>
    </head>
    <body>
    <div ng-controller="demoController">
        <jqx-grid jqx-instance="grid" jqx-create="gridSettings" jqx-settings="gridSettings"></jqx-grid>
    </div>
    </body>
    </html>
    

    After selecting one row in the grid, the filtering (entering text in the filterrow) does no more work! And selecting a row causes a reload of data and raises a JavaScript error.

    I am really blocked in my work… can you help me? What am I doing wrong?
    – badera


    Peter Stoev
    Keymaster

    Hello badera,

    Find a working sample below:

    <!DOCTYPE html>
    <html ng-app="demoApp">
    <head>
        <title id="Description">jqxGrid Binding to JSON using AngularJS</title>
        <link rel="stylesheet" type="text/css" href="../../jqwidgets/styles/jqx.base.css" />
        <script type="text/javascript" src="../../scripts/angular.min.js"></script>
        <script type="text/javascript" src="../../scripts/jquery-1.11.1.min.js"></script>
        <script type="text/javascript" src="../../jqwidgets/jqxcore.js"></script>
        <script type="text/javascript" src="../../jqwidgets/jqxdata.js"></script>
        <script type="text/javascript" src="../../jqwidgets/jqxbuttons.js"></script>
        <script type="text/javascript" src="../../jqwidgets/jqxcheckbox.js"></script>
        <script type="text/javascript" src="../../jqwidgets/jqxgrid.js"></script>
        <script type="text/javascript" src="../../jqwidgets/jqxgrid.selection.js"></script>
        <script type="text/javascript" src="../../jqwidgets/jqxmenu.js"></script>
        <script type="text/javascript" src="../../jqwidgets/jqxscrollbar.js"></script>
         <script type="text/javascript" src="../../jqwidgets/jqxlistbox.js"></script>
        <script type="text/javascript" src="../../jqwidgets/jqxdropdownlist.js"></script>
       <script type="text/javascript" src="../../jqwidgets/jqxgrid.sort.js"></script>
        <script type="text/javascript" src="../../jqwidgets/jqxgrid.filter.js"></script>
        <script type="text/javascript" src="../../jqwidgets/jqxgrid.columnsresize.js"></script>
        <script type="text/javascript" src="../../jqwidgets/jqxangular.js"></script>
        <script type="text/javascript" src="../../scripts/demos.js"></script>
        <script type="text/javascript">
            var demoApp = angular.module("demoApp", ["jqwidgets"]);
    
            demoApp.controller("demoController", function ($scope, $http) {
                $scope.gridSettings =
                {
                    altrows: true,
                    width: '100%',
                    height: '100%',
                    source:  {
                        datatype: "json",
                        datafields: [
                            { name: 'name', type: 'string' },
                            { name: 'type', type: 'string' },
                            { name: 'calories', type: 'int' },
                            { name: 'totalfat', type: 'string' },
                            { name: 'protein', type: 'string' }
                        ],
                        id: 'id',
                        url: '../sampledata/beverages.txt'
                    },
                    filterable: true,
                    showfilterrow: true,
                    rowselect: function (event) {
                        console.log("Now, the filtering does no more work!");
                    },
                    columns: [
                      { text: 'Name', datafield: 'name', width: 250 },
                      { text: 'Beverage Type', datafield: 'type', width: 250 },
                      { text: 'Calories', datafield: 'calories', width: 180 },
                      { text: 'Total Fat', datafield: 'totalfat', width: 120 },
                      { text: 'Protein', datafield: 'protein', minwidth: 120 }
                    ]
                }
            });
        </script>
    </head>
    <body>
        <div ng-controller="demoController">
            <jqx-grid jqx-settings="gridSettings"></jqx-grid>
        </div>
    </body>
    </html>
    

    Best Regards,
    Peter Stoev

    jQWidgets Team
    http://www.jqwidgets.com/


    badera
    Participant

    Thank you Peter for the sample; the filtering will work, indeed, however, it does not fix all problems:
    – if there is a ‘bindingcomplete’ function, the java script error is still raised and the grid never stops displaying “loading”
    – In your example, the first time a row is selected still raises a java script error and the content is re-requested from server

    Is there a way to solve all this?


    Peter Stoev
    Keymaster

    Hi badera,

    Sorry, but I can’t reproduce these.

    Best Regards,
    Peter Stoev

    jQWidgets Team
    http://www.jqwidgets.com/


    badera
    Participant

    Here the two cases:

    First one:

    In your example, the first time, a row is selected, still raises a java script error and the content is re-requested from server

    Please check the snippet below: The grid is loaded, then click on a row -> you will see a javascript error in the developer console. And “loading” is displayed for a short time and if you look the ajax calls in the developer tools of your browser, you see that the first row select again retrieves the data.

    
    <!DOCTYPE html>
    <html ng-app="demoApp">
    <head>
        <title id="Description">jqxGrid Binding to JSON using AngularJS</title>
        <link rel="stylesheet" type="text/css" href="http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/styles/jqx.base.css"/>
        <script type="text/javascript" src="http://www.jqwidgets.com/jquery-widgets-demo/scripts/angular.min.js"></script>
        <script type="text/javascript" src="http://www.jqwidgets.com/jquery-widgets-demo/scripts/jquery-1.11.1.min.js"></script>
        <script type="text/javascript" src="http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/jqx-all.js"></script>
        <script type="text/javascript">
            var demoApp = angular.module("demoApp", ["jqwidgets"]);
    
            demoApp.controller("demoController", function ($scope, $http) {
                $scope.gridSettings =
                {
                    altrows: true,
                    width: '100%',
                    height: '100%',
                    source:  {
                        datatype: "json",
                        datafields: [
                            { name: 'name', type: 'string' },
                            { name: 'type', type: 'string' },
                            { name: 'calories', type: 'int' },
                            { name: 'totalfat', type: 'string' },
                            { name: 'protein', type: 'string' }
                        ],
                        id: 'id',
                        url: "http://www.jqwidgets.com/jquery-widgets-demo/demos/sampledata/beverages.txt"
                    },
                    filterable: true,
                    showfilterrow: true,
                    
                    rowselect: function (event) {
                        console.log("On first rowselect, after this, you see a js error in the console...");
                    },
                    
    
                    
                    columns: [
                      { text: 'Name', datafield: 'name', width: 250 },
                      { text: 'Beverage Type', datafield: 'type', width: 250 },
                      { text: 'Calories', datafield: 'calories', width: 180 },
                      { text: 'Total Fat', datafield: 'totalfat', width: 120 },
                      { text: 'Protein', datafield: 'protein', minwidth: 120 }
                    ]
                }
            });
        </script>
    </head>
    <body>
        <div ng-controller="demoController">
            <jqx-grid jqx-settings="gridSettings"></jqx-grid>
        </div>
    </body>
    </html>
    

    The second one:

    if there is a ‘bindingcomplete’ function, the java script error is still raised and the grid never stops displaying “loading”

    
    <!DOCTYPE html>
    <html ng-app="demoApp">
    <head>
        <title id="Description">jqxGrid Binding to JSON using AngularJS</title>
        <link rel="stylesheet" type="text/css" href="http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/styles/jqx.base.css"/>
        <script type="text/javascript" src="http://www.jqwidgets.com/jquery-widgets-demo/scripts/angular.min.js"></script>
        <script type="text/javascript" src="http://www.jqwidgets.com/jquery-widgets-demo/scripts/jquery-1.11.1.min.js"></script>
        <script type="text/javascript" src="http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/jqx-all.js"></script>
        <script type="text/javascript">
            var demoApp = angular.module("demoApp", ["jqwidgets"]);
    
            demoApp.controller("demoController", function ($scope, $http) {
                $scope.gridSettings =
                {
                    altrows: true,
                    width: '100%',
                    height: '100%',
                    source:  {
                        datatype: "json",
                        datafields: [
                            { name: 'name', type: 'string' },
                            { name: 'type', type: 'string' },
                            { name: 'calories', type: 'int' },
                            { name: 'totalfat', type: 'string' },
                            { name: 'protein', type: 'string' }
                        ],
                        id: 'id',
                        url: "http://www.jqwidgets.com/jquery-widgets-demo/demos/sampledata/beverages.txt"
                    },
                    filterable: true,
                    showfilterrow: true,
                   
                    bindingcomplete: function (event) {
                        console.log("this causes problems...");
                    },
                    
                    columns: [
                      { text: 'Name', datafield: 'name', width: 250 },
                      { text: 'Beverage Type', datafield: 'type', width: 250 },
                      { text: 'Calories', datafield: 'calories', width: 180 },
                      { text: 'Total Fat', datafield: 'totalfat', width: 120 },
                      { text: 'Protein', datafield: 'protein', minwidth: 120 }
                    ]
                }
            });
        </script>
    </head>
    <body>
        <div ng-controller="demoController">
            <jqx-grid jqx-settings="gridSettings"></jqx-grid>
        </div>
    </body>
    </html>
    

    Please try it out – you will get the same problems. Thanks in advance for your help!
    – badera


    Peter Stoev
    Keymaster

    Hi badera,

    I sent you a working sample. I cannot reproduce what you’re writing about with the current version and unfortunately there’s nothing more I can add to this topic. We will however continue our investigation.

    Best Regards,
    Peter Stoev

    jQWidgets Team
    http://www.jqwidgets.com/


    badera
    Participant

    Dear Peter

    Which Browsers in which environment do you use? – I just see, that there are differences in the behaviour e.g. between Firefox and Chrome and different versions.
    Since it is a big problem for me I kindly ask you to try to reproduce it using the links below in the described environment (it uses jqWidgets from your server, so we have certainly the same files):

    1)
    http://5.145.22.178/misc/issues/jqx/1/problem_a.html

    Chrome Versions: (on Windows 7 x64)
    – 39.0.2171.95 m (newest regular version)
    – 41.0.2270.0 canary (64-bit) (pre-release of future version)
    Behaviour with these Chrome versions: (Please open the F12 Tools and go to Network tab and disable the cache)
    – If the page (link above) is loaded/refreshed, the data of the grid (beverages.txt) is requested twice
    – You will see in the F12 Tools, that beverages.txt is requested twice.

    Firefox Version 34.0.5 (on Windows 7 x64)
    Behaviour with this Firefox Version: (please open the F12 Tools, deactivate the cache …)
    – If the page (link above) is loaded/refreshed, the data of the grid (beverages.txt) is requested once
    – If I click on a row of the grid (the first time only after page reload), beverages.txt is requested again; we quickly see again the “loading…” animation of the grid.
    – If I would remove the “rowselect” event from the grid settings, the first row click would not end up in requesting the data again.

    ==> Why is the ajax call fired twice? -> this is a problem, if the data is large.

    2)
    http://5.145.22.178/misc/issues/jqx/1/problem_b.html

    Chrome Versions: (on Windows 7 x64)
    – 39.0.2171.95 m
    – 41.0.2270.0 canary (64-bit)
    Firefox Version 34.0.5 (on Windows 7 x64)

    Behaviour with these browsers:
    – The “loading…” animation of the grid never disappears
    – The filterrow is not displayed
    – A JavaScript error is raised.
    On Chrome:
    TypeError: undefined is not a function
    at databind (http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/jqx-all.js:7:1484977)
    at b.extend.databind (http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/jqx-all.js:7:1314055)
    at b.extend.updatebounddata (http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/jqx-all.js:7:1332048)
    at b.extend.propertyChangedHandler (http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/jqx-all.js:7:1464870)
    at Object.a.jqx.setvalueraiseevent (http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/jqx-all.js:7:3832)
    at Object.<anonymous> (http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/jqx-all.js:7:3070)
    at Function.m.extend.each (http://www.jqwidgets.com/jquery-widgets-demo/scripts/jquery-1.11.1.min.js:2:3027)
    at Object.a.jqx.set (http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/jqx-all.js:7:2957)
    at Object.a.jqx.jqxWidgetProxy (http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/jqx-all.js:7:4954)
    at b.fn.jqxProxy (http://www.jqwidgets.com/jquery-widgets-demo/jqwidgets/jqx-all.js:7:33395)

    ==> The reason is the bindingcomplete function in the grid settings. Why is this a problem?

    I assume that you / or somebody from the jqWidgets team is able to reproduce the issues with same browsers.

    Thanks in advance for your help!
    – badera


    Peter Stoev
    Keymaster

    Hi badera,

    We will investigate this and if we reproduce an issue, we will add a work item for future jQWidgets version. For now, we do not have further comments about your topic and questions.

    Best Regards,
    Peter Stoev

    jQWidgets Team
    http://www.jqwidgets.com/


    badera
    Participant

    These problems have now be solved with version 3.7.0. Thanks very much.

    One question: You showed the exmample above, merging the dataAdapter inside the source of the grid settings.
    I like to set the autoBind to false (which would be a setting of the dataAdapter. I was not able yet to prevent from automatically send the ajax call.

    If I do

                $scope.gridSettings =
                {
                    altrows: true,
                    width: '100%',
                    height: '100%',
                    source:  {
                        autoBind: false,
                        datatype: "json",
                        datafields: [
                            { name: 'name', type: 'string' },
                            { name: 'type', type: 'string' },
                            { name: 'calories', type: 'int' },
                            { name: 'totalfat', type: 'string' },
                            { name: 'protein', type: 'string' }
                        ],
                        id: 'id',
                        url: "beverages.txt"
                    },
                    filterable: true,
                    showfilterrow: true,
                    
                    rowselect: function (event) {
                        console.log("grid.rowselect");
                    },
                    
                    columns: [
                      { text: 'Name', datafield: 'name', width: 250 },
                      { text: 'Beverage Type', datafield: 'type', width: 250 },
                      { text: 'Calories', datafield: 'calories', width: 180 },
                      { text: 'Total Fat', datafield: 'totalfat', width: 120 },
                      { text: 'Protein', datafield: 'protein', minwidth: 120 }
                    ]
                }
    

    it does not work.

    How can I get the behaviour that the grid does not load the data but after manually call to updatebounddata, it will fire the ajax call?

    Thanks in advance for your help.
    – badera


    Peter Stoev
    Keymaster

    Hi badera,

    jqxGrid automatically performs data bind. Setting the adapter’s autoBind to true will only mean that you’ll perform 2 data binding operations instead of the standard 1 done by the Grid. If you don’t want the Grid to perform data bind, then don’t set its “source” setting.

    Best Regards,
    Peter Stoev

    jQWidgets Team
    http://www.jqwidgets.com/

Viewing 11 posts - 1 through 11 (of 11 total)

You must be logged in to reply to this topic.