jQuery UI Widgets Forums Grid Value-DisplayName combo in dropdownlist

This topic contains 9 replies, has 2 voices, and was last updated by  Dimitar 10 years, 8 months ago.

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

  • vasikgreif
    Participant

    I’m trying to get dropdownlist display and save different values for the ‘category’ column.

    I found this example: http://www.jqwidgets.com/jquery-widgets-demo/demos/jqxgrid/gridkeyvaluecolumn.htm?classic , but somehow I’m not able to adapt it to my code.

    My code is:

    // prepare the data
            var data = {};
            var theme = 'classic';
            var generaterow = function () {
                var row = {};
                $.ajaxSetup({async: false});
                id = $.post(Ajax.ajaxurl,
                    {
                        action:'add_table_row',
                        post_type: 'budget'
                    },
                    function(data,status){
    
                    });
    
                var response = $.parseJSON(id.responseText);
    
                row["id"] = response.id;
                row['nonce'] = response.nonce;
    
                return row;
            }
    
            var dropDownListSource =
            {
                datatype: "json",
                datafields: [
                    { name: 'name' },
                    { name: 'term_id' }
                ],
                id: 'id',
                url: Ajax.ajaxurl,
                mtype: 'POST',
                data: {
                    action: 'get_taxonomy_terms'
    
                }
    
            };
    
            var dropdownListAdapter = new $.jqx.dataAdapter(dropDownListSource, { autoBind: true, async: false });
    
            var source =
            {
                datatype: "json",
                datafields: [
                    { name: 'id' },
                    { name: 'title' },
                    { name: 'budget' },
                    { name: 'supplier_estimate' },
                    { name: 'spent' },
                    { name: 'paid' },
                    { name: 'note' },
                    { name: 'nonce' },
                    { name: 'category', value: 'term_id', values: { source: dropdownListAdapter, value: 'term_id', name: 'name' }}
                ],
                id: 'id',
                url: Ajax.ajaxurl,
                mtype: 'POST',
                data: {
                    action: 'get_table_data',
                    post_type: 'budget'
                },
                sortcolumn: 'id',
                sortdirection: 'asc',
    
                addrow: function (rowid, rowdata, position, commit) {
                    commit(true);
                },
                updaterow: function (rowid, rowdata, commit) {
                    get_total();
                    $.ajax({
                        url: Ajax.ajaxurl,
                        type: "POST",
                        data: {
                            action: 'update_table_row',
                            id: rowdata.id,
                            title: rowdata.title,
                            budget: rowdata.budget,
                            supplier_estimate: rowdata.supplier_estimate,
                            spent: rowdata.spent,
                            paid: rowdata.paid,
                            note: rowdata.note,
                            category: rowdata.category,
                            nonce: rowdata.nonce
                        },
                        success: function (data, status, xhr) {
                            // update command is executed.
                            console.log(data);
                            commit(true);
                        },
                        error: function () {
                            // cancel changes.
                            commit(false);
                        }
                    });
                },
                deleterow: function (rowid, commit) {
                    // synchronize with the server - send delete command
                    // call commit with parameter true if the synchronization with the server is successful
                    //and with parameter false if the synchronization failed.
                    commit(true);
                }
            };
    
            // initialize jqxGrid
            $("#jqxgrid").jqxGrid(
                {
                    width: 1200,
                    height: 350,
                    selectionmode: 'singlerow',
                    source: source,
                    theme: theme,
                    editable: true,
                    sortable: true,
                    columnsresize: true,
                    showaggregates: true,
                    filterable: true,
                    showtoolbar: true,
                    ready: function() {
                        get_total();
                    },
    
                    rendertoolbar: function (toolbar) {
                        var me = this;
                        var container = $("<div style='margin: 5px;'></div>");
                        toolbar.append(container);
                        container.append('<input id="addrowbutton" type="button" value="Add New Item" />');
                        container.append('<input style="margin-left: 5px;" id="addmultiplerowsbutton" type="button" value="Add Multiple New Rows" />');
                        $("#addrowbutton").jqxButton();
                        $("#addmultiplerowsbutton").jqxButton();
                        // create new row.
                        $("#addrowbutton").on('click', function () {
                            var datarow = generaterow();
                            console.log(datarow);
                            var commit = $("#jqxgrid").jqxGrid('addrow', null, datarow);
                        });
                        // create new rows.
                        $("#addmultiplerowsbutton").on('click', function () {
                            $("#jqxgrid").jqxGrid('beginupdate');
                            for (var i = 0; i < 10; i++) {
                                var datarow = generaterow();
                                var commit = $("#jqxgrid").jqxGrid('addrow', null, datarow);
                            }
                            $("#jqxgrid").jqxGrid('endupdate');
                        });
                    },
                    columns:
                        [
                            { text: 'ID', datafield: 'id', width: 100, hidden: true },
                            { text: 'Item', datafield: 'title', width: 100 },
                            { text: 'Budget', datafield: 'budget', width: 100 },
                            { text: 'Supplier estimate', datafield: 'supplier_estimate', width: 100 },
                            { text: 'Spent', datafield: 'spent', width: 100 },
                            { text: 'Note', datafield: 'note', width: 100,resizable: true },
                            { text: 'Paid', datafield: 'paid', columntype: 'dropdownlist', width: 100,
                                createeditor: function (row, column, editor) {
                                    var list = ['yes','no'];
                                    editor.jqxDropDownList({ source: list });
                                },
                                aggregates: [{ 'Total':
                                    function (aggregatedValue, currentValue) {
                                        if (currentValue) {
                                            return aggregatedValue + 1;
                                        }
                                        return aggregatedValue;
                                    }
                                }
                                ]
                            },
                            { text: 'Category', columntype: 'dropdownlist', datafield: 'category', width: 100, displayfield: 'name'
                                initeditor: function (row, cellvalue, editor) {
                                    editor.jqxDropDownList({ displayMember: 'name', valueMember: 'term_id',source: dropdownListAdapter });
                                }
                            },
                            { text: 'Nonce', datafield: 'nonce', width: 100, hidden: true },
                        ]
                });
        });

    The JSON source is:

    [{"term_id":"17","name":"category name","slug":"nova-kategorie-2","term_group":"0","term_taxonomy_id":"17","taxonomy":"budget-category","description":"","parent":"0","count":"0"}]

    Can someone help me display the name and save the term_id?


    Dimitar
    Participant

    Hello vasikgreif,

    The more suitable example to reference in your case is Custom DropDownList Column. We hope it is helpful to you.

    Best Regards,
    Dimitar

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


    vasikgreif
    Participant

    Thanks, I checked that example and tried to mimic it, but for some reason I cannot figure how to do that right. I don’t get what the countryCode column is doing there…

    My current code is:

    `
    // prepare the data
    var data = {};
    var theme = ‘classic’;
    var generaterow = function () {
    var row = {};
    $.ajaxSetup({async: false});
    id = $.post(Ajax.ajaxurl,
    {
    action:’add_table_row’,
    post_type: ‘budget’
    },
    function(data,status){

    });

    var response = $.parseJSON(id.responseText);

    row[“id”] = response.id;
    row[‘nonce’] = response.nonce;

    return row;
    }

    var dropDownListSource =
    {
    datatype: “json”,
    datafields: [
    { name: ‘name’ },
    { name: ‘term_id’ }
    ],
    id: ‘id’,
    url: Ajax.ajaxurl,
    mtype: ‘POST’,
    data: {
    action: ‘get_taxonomy_terms’
    }
    };

    var dropdownListAdapter = new $.jqx.dataAdapter(dropDownListSource, { autoBind: true, async: false });

    var source =
    {
    datatype: “json”,
    datafields: [
    { name: ‘id’ },
    { name: ‘title’ },
    { name: ‘budget’ },
    { name: ‘supplier_estimate’ },
    { name: ‘spent’ },
    { name: ‘paid’ },
    { name: ‘note’ },
    { name: ‘nonce’ },
    { name: ‘category’, value: ‘term_id’, values: { source: dropdownListAdapter, value: ‘term_id’, name: ‘name’ }}
    { name: ‘term_id’}

    ],
    id: ‘id’,
    url: Ajax.ajaxurl,
    mtype: ‘POST’,
    data: {
    action: ‘get_table_data’,
    post_type: ‘budget’
    },
    sortcolumn: ‘id’,
    sortdirection: ‘asc’,

    addrow: function (rowid, rowdata, position, commit) {
    // synchronize with the server – send insert command
    // call commit with parameter true if the synchronization with the server is successful
    //and with parameter false if the synchronization failed.
    // you can pass additional argument to the commit callback which represents the new ID if it is generated from a DB.
    commit(true);
    },
    updaterow: function (rowid, rowdata, commit) {
    get_total();
    $.ajax({
    url: Ajax.ajaxurl,
    type: “POST”,
    data: {
    action: ‘update_table_row’,
    id: rowdata.id,
    title: rowdata.title,
    budget: rowdata.budget,
    supplier_estimate: rowdata.supplier_estimate,
    spent: rowdata.spent,
    paid: rowdata.paid,
    note: rowdata.note,
    category: rowdata.category,
    term_id: rowdata.term_id,
    nonce: rowdata.nonce
    },
    success: function (data, status, xhr) {
    // update command is executed.
    console.log(data);
    commit(true);
    },
    error: function () {
    // cancel changes.
    commit(false);
    }
    });
    },
    deleterow: function (rowid, commit) {
    commit(true);
    }
    };

    // initialize jqxGrid
    $(“#jqxgrid”).jqxGrid(
    {
    width: 1200,
    height: 350,
    selectionmode: ‘singlerow’,
    source: source,
    theme: theme,
    editable: true,
    sortable: true,
    columnsresize: true,
    showaggregates: true,
    filterable: true,
    showtoolbar: true,
    ready: function() {
    get_total();
    },

    rendertoolbar: function (toolbar) {
    var me = this;
    var container = $(“<div style=’margin: 5px;’></div>”);
    toolbar.append(container);
    container.append(‘<input id=”addrowbutton” type=”button” value=”‘+ Ajax.add_new_item +'” />’);
    container.append(‘<input style=”margin-left: 5px;” id=”addmultiplerowsbutton” type=”button” value=”Add Multiple New Rows” />’);
    $(“#addrowbutton”).jqxButton();
    $(“#addmultiplerowsbutton”).jqxButton();
    // create new row.
    $(“#addrowbutton”).on(‘click’, function () {
    var datarow = generaterow();
    console.log(datarow);
    var commit = $(“#jqxgrid”).jqxGrid(‘addrow’, null, datarow);
    });
    // create new rows.
    $(“#addmultiplerowsbutton”).on(‘click’, function () {
    $(“#jqxgrid”).jqxGrid(‘beginupdate’);
    for (var i = 0; i < 10; i++) {
    var datarow = generaterow();
    var commit = $(“#jqxgrid”).jqxGrid(‘addrow’, null, datarow);
    }
    $(“#jqxgrid”).jqxGrid(‘endupdate’);
    });
    },
    columns:
    [
    { text: ‘ID’, datafield: ‘id’, width: 100, hidden: true },
    { text: Ajax.item, datafield: ‘title’, width: 100 },
    { text: Ajax.budget, datafield: ‘budget’, width: 100 },
    { text: ‘Supplier estimate’, datafield: ‘supplier_estimate’, width: 100 },
    { text: ‘Spent’, datafield: ‘spent’, width: 100 },
    { text: ‘Note’, datafield: ‘note’, width: 100,resizable: true },
    { text: ‘Paid’, datafield: ‘paid’, columntype: ‘dropdownlist’, width: 100,
    createeditor: function (row, column, editor) {
    var list = [‘yes’,’no’];
    editor.jqxDropDownList({ source: list });
    },
    aggregates: [{ ‘Total’:
    function (aggregatedValue, currentValue) {
    if (currentValue) {
    return aggregatedValue + 1;
    }
    return aggregatedValue;
    }
    }
    ]
    },
    { text: ‘Category’, columntype: ‘dropdownlist’, datafield: ‘term_id’, displayfield: ‘name’, width: 100,
    createeditor: function (row, value, editor) {
    editor.jqxDropDownList({ source: dropdownListAdapter , displayMember: ‘name’, valueMember: ‘term_id’ });
    }
    },
    { text: ‘Nonce’, datafield: ‘nonce’, width: 100, hidden: true }
    ]
    });
    });
    `

    Could you please help me to fix that? Thanks


    Dimitar
    Participant

    Hi vasikgreif,

    Please explain what you are trying to achieve again. As I understood from your previous post, you would like the dropdownlist editor to affect both the value and label of the grid cell. This is achieved in the demo.

    Also please remember to format your code before posting by selecting it and clicking on the code button in the toolbar.

    Best Regards,
    Dimitar

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


    vasikgreif
    Participant

    Hi Dimitar,
    thanks for trying to help.

    I’m trying to get the same funcionality as in the example you provided – display a dropdown with displayValues and save another value. I modified my code as per the example, but it still doesn’t work – the dropdown is displayed, the correct value term_id is saved to db, but on page refresh nothing is displayed in the dropdown. I’m obviously missing something, but cannot figure out what.

    For the code button, I tried that (the backticks are in there), but for some reason it didn’t work…


    Dimitar
    Participant

    Hi vasikgreif,

    Your code seems fine, except for a typo in your source datafields:

    var source =
    {
    datatype: “json”,
    datafields: [
    { name: 'id' },
    { name: 'title' },
    { name: 'budget' },
    { name: 'supplier_estimate' },
    { name: 'spent' },
    { name: 'paid' },
    { name: 'note' },
    { name: 'nonce' },
    { name: 'category', value: 'term_id', values: { source: dropdownListAdapter, value: 'term_id', name: 'name' }}, // missing comma here
    { name: 'term_id'}
    
    ],

    This may not be the cause of the issue but we will not be able to determine it until we have an example we can test locally.

    Best Regards,
    Dimitar

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


    vasikgreif
    Participant

    Thanks for your time. Here’s the edited version of code with local data, with the exact data I’m getting from my Ajax calls. Could you please check that? The problem is that while I’m getting the term_id value (in tableData), nothing is displayed in the dropdown.

    jQuery(document).ready(function ($) {
        $(document).ready(function () {
            // prepare the data
    
            var taxonomies = '[{"term_id":"17","name":"nova kategorie 2","slug":"nova-kategorie-2","term_group":"0","term_taxonomy_id":"17","taxonomy":"budget-category","description":"","parent":"0","count":"0"},{"term_id":"18","name":"dalsi kategorie","slug":"dalsi-kategorie","term_group":"0","term_taxonomy_id":"18","taxonomy":"budget-category","description":"","parent":"0","count":"0"}]';
            var data = {};
            var theme = 'classic';
            var dropDownListSource =
            {
                datatype: "json",
                datafields: [
                    { name: 'name', type: 'string' },
                    { name: 'term_id', type: 'string' }
                ],
                localdata: taxonomies
            };
    
            var dropdownListAdapter = new $.jqx.dataAdapter(dropDownListSource, { autoBind: true, async: false });
    
            var tableData= '[{"id":["221"],"action":["update_table_row"],"spent":["400"],"term_id":["17"],"nonce":"5dd2521156"},{"id":["216"],"action":["update_table_row"],"title":["Polozka 2"],"budget":["45454"],"supplier_estimate":["5555"],"spent":["444"],"note":[""],"category":["18"],"paid":[""],"term_id":["18"],"nonce":"de685bdea2"},{"id":["215"],"action":["update_table_row"],"title":["Polozka 1"],"budget":["1000"],"supplier_estimate":["500"],"spent":["500"],"note":["hhhaaa"],"paid":["yes"],"category":["17"],"term_id":["18"],"nonce":"44d19b78c2"}]';
            var source =
            {
                datatype: "json",
                localdata: tableData,
    
                datafields: [
                    { name: 'id' },
                    { name: 'title' },
                    { name: 'budget' },
                    { name: 'supplier_estimate' },
                    { name: 'spent' },
                    { name: 'paid' },
                    { name: 'note' },
                    { name: 'nonce' },
                    { name: 'category', value: 'term_id', values: { source: dropdownListAdapter, value: 'term_id', name: 'name' }},
                    { name: 'term_id'}
                ],
                id: 'id',
                sortcolumn: 'id',
                sortdirection: 'asc'
            };
    
            // initialize jqxGrid
            $("#jqxgrid").jqxGrid(
                {
                    width: 1200,
                    height: 350,
                    selectionmode: 'singlerow',
                    source: source,
                    theme: theme,
                    editable: true,
                    sortable: true,
                    columnsresize: true,
                    showaggregates: true,
                    filterable: true,
                    showtoolbar: true,
                    
                    columns:
                        [
                            { text: 'ID', datafield: 'id', width: 100, hidden: true },
                            { text: 'Item', datafield: 'title', width: 100 },
                            { text: 'Budget', datafield: 'budget', width: 100 },
                            { text: 'Supplier estimate', datafield: 'supplier_estimate', width: 100 },
                            { text: 'Spent', datafield: 'spent', width: 100 },
                            { text: 'Note', datafield: 'note', width: 100,resizable: true },
                            { text: 'Paid', datafield: 'paid', columntype: 'dropdownlist', width: 100,
                                createeditor: function (row, column, editor) {
                                    var list = ['yes','no'];
                                    editor.jqxDropDownList({ source: list });
                                },
                                aggregates: [{ 'Total':
                                    function (aggregatedValue, currentValue) {
                                        if (currentValue) {
                                            return aggregatedValue + 1;
                                        }
                                        return aggregatedValue;
                                    }
                                }
                                ]
                            },
                            { text: 'Category', columntype: 'dropdownlist', datafield: 'term_id', displayfield: 'name', width: 100,
                                createeditor: function (row, value, editor) {
                                    editor.jqxDropDownList({ source: dropdownListAdapter , displayMember: 'name', valueMember: 'term_id' });
                                }
                            },
                            { text: 'Nonce', datafield: 'nonce', width: 100, hidden: true }
    
                    ]
                });
        });
    });
    

    Dimitar
    Participant

    Hi vasikgreif,

    One issue your code has was the use of the undefined datafield “name” as a column displayfield. Another possible issue was the values.source being set to dropdownListAdapter and not to dropdownListAdapter.records. Here is an updated version of your example. Do you experience any issues with it?

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <link rel="stylesheet" href="../../jqwidgets/styles/jqx.base.css" type="text/css" />
        <script type="text/javascript" src="../../scripts/jquery-1.10.2.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/jqxscrollbar.js"></script>
        <script type="text/javascript" src="../../jqwidgets/jqxmenu.js"></script>
        <script type="text/javascript" src="../../jqwidgets/jqxcheckbox.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.js"></script>
        <script type="text/javascript" src="../../jqwidgets/jqxgrid.sort.js"></script>
        <script type="text/javascript" src="../../jqwidgets/jqxgrid.pager.js"></script>
        <script type="text/javascript" src="../../jqwidgets/jqxgrid.selection.js"></script>
        <script type="text/javascript" src="../../jqwidgets/jqxgrid.columnsresize.js"></script>
        <script type="text/javascript" src="../../jqwidgets/jqxgrid.aggregates.js"></script>
        <script type="text/javascript" src="../../jqwidgets/jqxgrid.filter.js"></script>
        <script type="text/javascript" src="../../jqwidgets/jqxgrid.edit.js"></script>
        <script type="text/javascript" src="../../scripts/demos.js"></script>
        <script type="text/javascript">
            jQuery(document).ready(function ($) {
                $(document).ready(function () {
                    // prepare the data
    
                    var taxonomies = '[{"term_id":"17","name":"nova kategorie 2","slug":"nova-kategorie-2","term_group":"0","term_taxonomy_id":"17","taxonomy":"budget-category","description":"","parent":"0","count":"0"},{"term_id":"18","name":"dalsi kategorie","slug":"dalsi-kategorie","term_group":"0","term_taxonomy_id":"18","taxonomy":"budget-category","description":"","parent":"0","count":"0"}]';
                    var data = {};
                    var theme = 'classic';
                    var dropDownListSource =
                    {
                        datatype: "json",
                        datafields: [
                            { name: 'name', type: 'string' },
                            { name: 'term_id', type: 'string' }
                        ],
                        localdata: taxonomies
                    };
    
                    var dropdownListAdapter = new $.jqx.dataAdapter(dropDownListSource, { autoBind: true, async: false });
    
                    var tableData = '[{"id":["221"],"action":["update_table_row"],"spent":["400"],"term_id":["17"],"nonce":"5dd2521156"},{"id":["216"],"action":["update_table_row"],"title":["Polozka 2"],"budget":["45454"],"supplier_estimate":["5555"],"spent":["444"],"note":[""],"category":["18"],"paid":[""],"term_id":["18"],"nonce":"de685bdea2"},{"id":["215"],"action":["update_table_row"],"title":["Polozka 1"],"budget":["1000"],"supplier_estimate":["500"],"spent":["500"],"note":["hhhaaa"],"paid":["yes"],"category":["17"],"term_id":["18"],"nonce":"44d19b78c2"}]';
                    var source =
                    {
                        datatype: "json",
                        localdata: tableData,
    
                        datafields: [
                            { name: 'id' },
                            { name: 'title' },
                            { name: 'budget' },
                            { name: 'supplier_estimate' },
                            { name: 'spent' },
                            { name: 'paid' },
                            { name: 'note' },
                            { name: 'nonce' },
                            { name: 'category', value: 'term_id', values: { source: dropdownListAdapter.records, value: 'term_id', name: 'name'} },
                            { name: 'term_id' }
                        ],
                        id: 'id',
                        sortcolumn: 'id',
                        sortdirection: 'asc'
                    };
    
                    var tableAdapter = new $.jqx.dataAdapter(source);
    
                    // initialize jqxGrid
                    $("#jqxgrid").jqxGrid(
                    {
                        width: 1200,
                        height: 350,
                        selectionmode: 'singlerow',
                        source: tableAdapter,
                        theme: theme,
                        editable: true,
                        sortable: true,
                        columnsresize: true,
                        showaggregates: true,
                        filterable: true,
                        showtoolbar: true,
    
                        columns:
                            [
                                { text: 'ID', datafield: 'id', width: 100, hidden: true },
                                { text: 'Item', datafield: 'title', width: 100 },
                                { text: 'Budget', datafield: 'budget', width: 100 },
                                { text: 'Supplier estimate', datafield: 'supplier_estimate', width: 100 },
                                { text: 'Spent', datafield: 'spent', width: 100 },
                                { text: 'Note', datafield: 'note', width: 100, resizable: true },
                                { text: 'Paid', datafield: 'paid', columntype: 'dropdownlist', width: 100,
                                    createeditor: function (row, column, editor) {
                                        var list = ['yes', 'no'];
                                        editor.jqxDropDownList({ source: list });
                                    },
                                    aggregates: [{ 'Total':
                                        function (aggregatedValue, currentValue) {
                                            if (currentValue) {
                                                return aggregatedValue + 1;
                                            }
                                            return aggregatedValue;
                                        }
                                    }
                                    ]
                                },
                                { text: 'Category', columntype: 'dropdownlist', datafield: 'term_id', displayfield: 'category', width: 100,
                                    createeditor: function (row, value, editor) {
                                        editor.jqxDropDownList({ source: dropdownListAdapter, displayMember: 'name', valueMember: 'term_id' });
                                    }
                                },
                                { text: 'Nonce', datafield: 'nonce', width: 100, hidden: true }
    
                        ]
                    });
                });
            });  
        </script>
    </head>
    <body class='default'>
        <div id='jqxWidget' style="font-size: 13px; font-family: Verdana; float: left;">
            <div id="jqxgrid">
            </div>
        </div>
    </body>
    </html>

    Best Regards,
    Dimitar

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


    vasikgreif
    Participant

    This one works! Thanks so much for help.

    Last question on this one: is there an easier way to have the same funcionality with two specific values values only? I mean, I need to display yes/no in another dropdown and save 1/0…?

    Thanks again


    Dimitar
    Participant

    Hi vasikgreif,

    If you wish to have different datafield and displayfield, this is the correct approach.

    Best Regards,
    Dimitar

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

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

You must be logged in to reply to this topic.