Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
261 views
in Technique[技术] by (71.8m points)

jqGrid : Get data from a row that has been clicked within a heirarchical grid

Im currently working on a project which uses jqGrid with multiple subgrids. I'm trying to get the rowid (and get at the data within the row) when a row is clicked or double clicked. Eventually I would like to fill a text box with data from a clicked row.

I've tried a few variations using ondblClickRow and onSelectRow examples on here but wans't able to get it working. I think I'm missing something really simple but don't see what. So I went back and simplified it down as much as possible to just recognize the row click and display an alert. This won't work for me either.

(based on the example in jqGrid : issue loading nested sub grid with local datatype) Look for the //*************** part near the bottom..

var myData = [
// main grid data
     { id: "1", col1: "11", col2: "12",
         subgrid: [
                // data for subgrid for the id=m1
                    { id: "1", c1: "aa", c2: "ab", c3: "ac",
                        subgrid: [
                            // data for subgrid for the id=m1, subgridId=s1a
                            { id: "1", d1: "2aa", d2: "2ab", d3: "2ac" },
                            { id: "2", d1: "2ba", d2: "2bb", d3: "2bc" },
                            { id: "3", d1: "2ca", d2: "2cb", d3: "2cc" }
                        ]},
                { id: "2", c1: "ba", c2: "bb", c3: "bc" },
                { id: "3", c1: "ca", c2: "cb", c3: "cc" }
         ]},
    { id: "2", col1: "21", col2: "22",
        subgrid: [
            // data for subgrid for the id=m2
            { id: "1", c1: "1xx", c2: "1xy", c3: "1xz",
                subgrid: [
                    // data for subgrid for the id=m2, subgridId=s2a
                    { id: "1", d1: "2xx", d2: "2xy", d3: "2xz" }
                ]}
        ]},
    { id: "3", col1: "31", col2: "32" }
],
removeSubgridIcon = function () {
    var $this = $(this),
        idPrefix = $this.jqGrid("getGridParam", "idPrefix");
    $this.find(">tbody>tr.jqgrow>td.ui-sgcollapsed").filter(function () {
        var rowData = $this.jqGrid("getLocalRow",
                $.jgrid.stripPref(idPrefix, $(this).closest("tr.jqgrow").attr("id")));
        return rowData.subgrid == null;
    }).unbind("click").html("");
},
isHasSubrids = function (data) {
    var l = data.length, i;
    for (i = 0; i < l; i++) {
        if (data[i].subgrid != null) {
            return true;
        }
    }
    return false;
},
specificGridOptions = [
    {
        colNames: ["Column 1", "Column 2"],
        colModel: [
            { name: "col1" },
            { name: "col2" }
        ],
        cmTemplate: { width: 200 },
        sortname: "col1",
        sortorder: "desc",
        idPrefix: "s_",
        pager: "#pager",
        caption: "Demonstrate how to create subgrid from local hierarchical data"
    },
    {
        colNames: ["Colunm1", "Colunm2", "Colunm3"],
        colModel: [
            { name: "c1" },
            { name: "c2" },
            { name: "c3" }
        ],
        cmTemplate: { width: 112 },
        sortname: "c1",
        sortorder: "desc"
    },
    {
        colNames: ["Col 1", "Col 2", "Col 3"],
        colModel: [
            { name: "d1" },
            { name: "d2" },
            { name: "d3" }
        ],
        cmTemplate: { width: 90 },
        sortname: "d1",
        sortorder: "desc"
    }
],
commonGridOptions = {
    datatype: "local",
    gridview: true,
    rownumbers: true,
    autoencode: true,
    height: "100%",
    //***************
    onSelectRow : function () 
    {
        alert('test!');
    },
    //also tried many variation on this
    ondblClickRow: function(rowid) 
    {
        alert(rowid);
    }
    //***************
    loadComplete: function () {
        // one can use loadComplete: removeSubgridIcon, but I included
        // curent implementation of loadComplete only to show how to call
        // removeSubgridIcon from your loadComplete callback handler
    removeSubgridIcon.call(this);
},
subGridRowExpanded: function (subgridDivId, rowId) {
    var $subgrid = $("<table id='" + subgridDivId + "_t'></table>"),
        subgridLevel = $(this).jqGrid("getGridParam", "subgridLevel") + 1,
        parentIdPrefix = $(this).jqGrid("getGridParam", "idPrefix"),
        pureRowId = $.jgrid.stripPref(parentIdPrefix, rowId),
        localRowData = $(this).jqGrid("getLocalRow", pureRowId);
    $subgrid.appendTo("#" + $.jgrid.jqID(subgridDivId));
    $subgrid.jqGrid($.extend(true, {}, commonGridOptions, specificGridOptions       [subgridLevel], {
        data: localRowData.subgrid,
        subGrid: isHasSubrids(localRowData.subgrid),
        subgridLevel: subgridLevel,
        idPrefix: rowId + "_",
        rowNum: 10000 // we use this to have no pager in the subgrids
    }));
}
};

$("#list").jqGrid($.extend(true, {}, commonGridOptions, specificGridOptions[0], {
    data: myData,
    subgridLevel: 0,
    subGrid: isHasSubrids(myData)
}));

Anyone have any ideas why it won't recognize the row click/double click?

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Answer

0 votes
by (71.8m points)

You wrote in comment that you get the data for the grid from the server. I suppose that the usage of datatype: "local" in the case is not the best choice. Look at the answer where I described the way how to do the same, but using datatype: "json".

Now I come back to your main question. I don't understand what text box (HTML input element) you want to fill and whether the input element is inside of the grid or outside of it. Nevertheless the only problem which you could probably have is the correct usage of idPrefix option of jqGrid.

It's very important to understand, that jqGrid use HTML <table> for representing of the body of grids. Every <tr> element of the <table> must have id attribute in the current implementation of jqGrid. So the id property from the input data will be used to assign the value of id attribute of <tr> elements. If one has more as one grid on the page or if one has grid with subgrids it's very easy to receive id duplicates which not allowed in all versions of HTML or XHTML.

Additional potential problem is the usage of numbers as id values. The most databases support auto-incremental datatype which is very practical as the key of the tables. In the case the native id (the key) for the database table and for the grid rows will be integer numbers. On the other side there are some additional restrictions depend on the version of HTML/XHTML which one uses. For example HTML5 specification says (see here)

The value must be unique amongst all the IDs in the element's home subtree and must contain at least one character. The value must not contain any space characters.

So even though the most web browsers allows to use numbers as the values of id attribute it's not permitted and one can get compatibility problems in case of usage of this.

To solve all the described above problem jqGrid supports idPrefix options (which was introduced by the way based on my suggestion). In the case the value of id attribute will be build as concatination of idPrefix and the id from the input data. For example in case of idPrefix: "s_" and id values "1", "2", "3" used in the main grid of the example jqGrid will assign "s_1", "s_2", "s_3" as values of id attribute of <tr> elements of the main grid. The rowid of all callbacks will be the value from id attribute ("s_1", "s_2", "s_3"). If you need get the original id you can use $.jgrid.stripPref to strip the prefix. All ids which will be sent to the server by jqGrid will be normalized ($.jgrid.stripPref will be called) by jqGrid itself.

So the code which shows how to get data onSelectRow and ondblClickRow could be the following

onSelectRow: function (rowid, stat, e) {
    myDebugTrace.call(this, "onSelectRow", rowid);
},
ondblClickRow: function (rowid, iRow, iCol, e) {
    myDebugTrace.call(this, "ondblClickRow", rowid);
    e.stopPropagation();
},
...

where myDebugTrace function can be declared as

var myDebugTrace = function (startingText, rowid) {
        var $this = $(this), p = $this.jqGrid("getGridParam"), rowData, col1,
            firstCol = (p.rownumbers ? 1 : 0) + (p.subGrid ? 1 : 0);

        rowData = $this.jqGrid("getRowData", rowid);
        col1 = rowData[p.colModel[firstCol].name];
        $("<span>" + startingText + " on " + rowid + " (original id=" +
            $.jgrid.stripPref($(this).jqGrid("getGridParam", "idPrefix"), rowid) +
            "). Data from the first column: "" + col1 +""</span><br/>").appendTo("body");
    };

The corresponding demo display the following on double-click on the row from the internal subgrid.

enter image description here


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

2.1m questions

2.1m answers

60 comments

56.8k users

...