<?xml version="1.0" encoding="UTF-8"?><rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom">
<channel>
	<title>jQuery Grid Plugin - jqGrid - Topic: more flexibility in the xmlReader</title>
	<link>http://www.trirand.com/blog/?page_id=393/feature-request/more-flexibility-in-the-xmlreader</link>
	<description><![CDATA[Grid plugin]]></description>
	<generator>Simple:Press Version 5.7.5.3</generator>
	<atom:link href="http://www.trirand.com/blog/?page_id=393/feature-request/more-flexibility-in-the-xmlreader/rss" rel="self" type="application/rss+xml" />
        <item>
        	<title>OlegK on more flexibility in the xmlReader</title>
        	<link>http://www.trirand.com/blog/?page_id=393/feature-request/more-flexibility-in-the-xmlreader#p25156</link>
        	<category>Feature Request</category>
        	<guid isPermaLink="true">http://www.trirand.com/blog/?page_id=393/feature-request/more-flexibility-in-the-xmlreader#p25156</guid>
        	        	<description><![CDATA[<p>Hallo Tony!</p>
<p>I tesed the code, but it would be very good if you test it also carefully.</p>
<p>To make youe easy to read the code the following comments can be interesting for you.</p>
<p>I made some changes in code of getXmlData which I originally posted. It&#39;s small changes in the RegEx (parameter of expr.match) and the last lines of getXmlData. New version of the code is</p>
<p><input type='button' class='sfcodeselect' name='sfselectit1642' value='Select Code' data-codeid='sfcode1642' /></p>
<div class='sfcode' id='sfcode1642'>getXmlData: function (obj, expr, returnObj) {<br />&#160; &#160; var ret, m = typeof (expr) === &#39;string&#39; ? expr.match(/^(<strong>.*</strong>)\[(\w+)\]$/) : null;&#160;<br />&#160; &#160; if (typeof (expr) === &#39;function&#39;) { return expr(obj); }<br />&#160; &#160; if (m &#38;&#38; m[2]) {<br />&#160; &#160; &#160; &#160; // m[2] is the attribute selector<br />&#160; &#160; &#160; &#160; // m[1] is an optional element selector<br />&#160; &#160; &#160; &#160; // examples: &#34;[id]&#34;, &#34;rows[page]&#34;, &#34;rows&#62;row[id=13]:first[id]&#34;<br />&#160; &#160; &#160; &#160; return m[1] ? $(m[1], obj).attr(m[2]) : $(obj).attr(m[2]);<br />&#160; &#160; } else {<br />&#160; &#160; &#160; &#160; <strong>ret = $(expr, obj);<br />&#160; &#160; &#160; &#160; if (returnObj) { return ret; }<br />&#160; &#160; &#160; &#160; $(expr, obj).filter(&#39;:last&#39;); // we use &#39;:last&#39; to be more compatible with old version of jqGrid<br />&#160; &#160; &#160; &#160; return ret.length &#62; 0 ? $(ret).text() : undefined;</strong><br />&#160; &#160; }<br />}&#160;</div>
<p>The main change in the code of the <strong>reader</strong> function is the usage of <strong>xmlmap</strong> instead of <strong>jsonmap</strong> in case of datatype equal to <strong>"xmlstring"</strong>. The full code is the following:</p>
<p><input type='button' class='sfcodeselect' name='sfselectit8621' value='Select Code' data-codeid='sfcode8621' /></p>
<div class='sfcode' id='sfcode8621'>reader = function (datatype) {<br />&#160; &#160; var field, fieldName, f = [], j = 0, i, l, cm = ts.p.colModel;<br />&#160; &#160; for (i = 0, l = cm.length; i &#60; l; i++) {<br />&#160; &#160; &#160; &#160; field = cm[i];<br />&#160; &#160; &#160; &#160; fieldName = field.name;<br />&#160; &#160; &#160; &#160; if (fieldName !== &#39;cb&#39; &#38;&#38; fieldName !== &#39;subgrid&#39; &#38;&#38; fieldName !== &#39;rn&#39;) {<br />&#160; &#160; &#160; &#160; &#160; &#160; f[j] = datatype === &#34;local&#34; ?<br />&#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; fieldName :<br />&#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; (datatype === &#34;xml&#34; &#124;&#124; <strong>datatype === &#34;xmlstring&#34;</strong> ?<br />&#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; field.xmlmap &#124;&#124; fieldName :<br />&#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; field.jsonmap &#124;&#124; fieldName);<br />&#160; &#160; &#160; &#160; &#160; &#160; j++;<br />&#160; &#160; &#160; &#160; }<br />&#160; &#160; }<br />&#160; &#160; return f;<br />}&#160;</div>
<p>The code of new <strong>addData</strong> function are based on <strong>addJsonData</strong>. Some optimization changes and some small bug fixes (improvements) are made. For example</p>
<ul>
<li>assignmant of variables <strong>gi</strong>, <strong>si</strong> and <strong>ni</strong> based on <strong>multiselect</strong>, <strong>subGrid</strong> and <strong>rownumbers</strong> parameters of jqGrid was in the loop. In <strong>addData</strong>&#160;function it is moved to initialization of <strong>gi</strong>,&#160;<strong>si</strong>&#160;and&#160;<strong>ni</strong>.</li>
<li><strong>ts.p</strong>, <strong>ts.p.datatype</strong> and <strong>$(ts)</strong> used frequently in the code of <strong>addJsonData</strong>. The new variables <strong>p</strong>, <strong>datatype</strong> and <strong>$t</strong> was introduced in <strong>addData</strong>.</li>
<li>on the other side some variables which are used only once like <strong>altr</strong>, <strong>cn1</strong> are removed.</li>
<li>variable <strong>br=ts.p.scroll?$.jgrid.randId():1</strong> used in the loop as <strong>idr = br+i;</strong> in <strong>addJsonData</strong>&#160;could follow to problem in case of usage scroll option of jqGrid. The problem is that the method <strong>$.jgrid.randId()</strong>&#160;was called only once and then used ids <strong>$.jgrid.randId()+1</strong>, <strong>$.jgrid.randId()+2</strong>&#160;and so on <span style="text-decoration: underline;">without</span> increasing of internal <strong>guid</strong>&#160;property of jqGrid. So at the next call of <strong>$.jgrid.randId()</strong>&#160;<span style="text-decoration: underline;">the same id which is already used</span> could be generated and be used in the same grid. The bug was fixed and in <strong>addData</strong>&#160;it will be used the code <strong>id = (p.scroll ? $.jgrid.randId() : 1) + index;</strong>&#160;directly.</li>
<li>there are some situations where not all required properties are included in the JSON or XML input. For example, if no page property are included the <strong>p.page</strong> will be set to <strong>0</strong>. In the same way the <strong>p.lastpage</strong> can be set to default value 1. In there are some items in the grid and the <strong>rownumbers</strong>&#160;parameter is true the value <strong>p.page</strong>&#160;will follow to including negative row numbers. Additionally the value 0 in the pager is not good if there are at least one item. In code of <strong>addData</strong>&#160;are included one additional line which change zero value of <strong>p.page</strong>&#160;to 1 if there are at least one item in the grid.</li>
<li>in the same way it can be displayed in the pager "Page 1 from 0" in some not full filled empty data. In code of <strong>addData</strong>&#160;are included one additional line which change the value of <strong>p.lastpage</strong>&#160;to the <strong>Math.min(p.page, Math.ceil(len / rn));</strong>.</li>
<li>Sometime the statement <strong>ccur = $.jgrid.getAccessor(cur,dReader.cell);</strong>&#160;will assign <strong>undefined</strong> value to <strong>ccur</strong>. The next statement <strong>idr = ccur[idn] &#124;&#124; idr;</strong>&#160;produce an exception in the case. In the code of <strong>addData</strong>&#160;are included additional test to of variable&#39;s <strong>typeof</strong> to <strong>"undefined"</strong> value.</li>
<li>The variable <strong>F</strong> are replaced to another existing variable <strong>f</strong>&#160;having the same value. Moreover the usage F variable like other names with the first capical character are reservated in JavaScript for classes.</li>
<li>In <strong>addJsonData</strong>&#160;the calling of <strong>afterInsertRow</strong> and appending current data from array <strong>rowData</strong> to the grid body will be done in case <strong>ts.p.gridview === false</strong>. In <strong>addData</strong> the same will be done in case of <strong>afterInsRow</strong>&#160;(if <strong>afterInsertRow</strong>&#160;is a function). It can follow theoretically to some compatibility problem, but because the default value of <strong>gridview</strong>&#160;is false it can improve the performance. Probably you know some more seldom cases like usage of subgrids or some other cases where the test should be stay <strong>!ts.p.gridview</strong>. You can consider to make the changes back to <strong>if (!ts.p.gridview) {</strong></li>
</ul>
<p>It&#39;s the most importand changes in the code which I want commented. Some other small reordering of lines should be clear. Moreover I wrote you some time before about the problem of usage custom formatters or <strong>cellattr</strong> callbacks in case of getting gata from the server and usage <strong>loadonce:true</strong> option. I wrote long comment before the loop</p>
<p><input type='button' class='sfcodeselect' name='sfselectit9213' value='Select Code' data-codeid='sfcode9213' /></p>
<div class='sfcode' id='sfcode9213'>for (j = 0, rd = {}; j &#60; f.length; j++) {<br />&#160; &#160; v = getData(cur, f[j]);<br />&#160; &#160; rowData.push(addCell(idr, v, j + gi + si + ni, i + rcnt, cur));<br />&#160; &#160; rd[p.colModel[j + gi + si + ni].name] = v;<br />}&#160;</div>
<p>I think that the loop could be devided in two loops: one which fill <strong>rd</strong> object with <span style="text-decoration: underline;">named</span> properties and another which called <strong>addCell</strong> and appended the array <strong>rowData</strong>. In the case one could add an aditional <strong>rd</strong> parameter to <strong>addCell</strong>&#160;which can be forwarded to the custom formatter or the&#160;<strong>cellattr</strong>&#160;callback as also additional parameter. I think that additional parameter will be better to hold compatibility to the previous vesrions.</p>
<p>I hope my above comments could help you better understend and probably improve the code of <strong>addData</strong>&#160;which I suggested.</p>
<p>Best regards<br />Oleg&#160;</p>
]]></description>
        	        	<pubDate>Tue, 15 Nov 2011 12:13:21 +0200</pubDate>
        </item>
        <item>
        	<title>tony on more flexibility in the xmlReader</title>
        	<link>http://www.trirand.com/blog/?page_id=393/feature-request/more-flexibility-in-the-xmlreader#p25153</link>
        	<category>Feature Request</category>
        	<guid isPermaLink="true">http://www.trirand.com/blog/?page_id=393/feature-request/more-flexibility-in-the-xmlreader#p25153</guid>
        	        	<description><![CDATA[<p>Hello Oleg,</p>
<p>The idea is very good and I will implement it step by step.</p>
<p>This way we can test it better and I can look deeper into your code</p>
<p>Thanks</p>
<p>Tony</p>
]]></description>
        	        	<pubDate>Tue, 15 Nov 2011 08:57:05 +0200</pubDate>
        </item>
        <item>
        	<title>OlegK on more flexibility in the xmlReader</title>
        	<link>http://www.trirand.com/blog/?page_id=393/feature-request/more-flexibility-in-the-xmlreader#p25142</link>
        	<category>Feature Request</category>
        	<guid isPermaLink="true">http://www.trirand.com/blog/?page_id=393/feature-request/more-flexibility-in-the-xmlreader#p25142</guid>
        	        	<description><![CDATA[<p>Hello Tony!</p>
<p>You can find&#160;<a href="http://www.ok-soft-gmbh.com/jqGrid/jquery.jqGrid-4.2.0-20111111/js/grid.base-addData.js" target="_blank">here</a>&#160;modified version of <strong>grid.base.js</strong>. The methods <strong>getXmlData</strong> and <strong>addData</strong> are added and the function reader&#160;are modified a little. The method <strong>addData</strong>&#160;can be used instead of both <strong>addXmlData</strong>&#160;and <strong>addJSONData</strong>. I included some small fixes to some problems which I found. I tested this and it seem to work.</p>
<p>Take a look on my modification. If you want I can place the code in github.</p>
<p>Best regards<br />Oleg&#160;</p>
]]></description>
        	        	<pubDate>Sat, 12 Nov 2011 17:22:15 +0200</pubDate>
        </item>
        <item>
        	<title>tony on more flexibility in the xmlReader</title>
        	<link>http://www.trirand.com/blog/?page_id=393/feature-request/more-flexibility-in-the-xmlreader#p25085</link>
        	<category>Feature Request</category>
        	<guid isPermaLink="true">http://www.trirand.com/blog/?page_id=393/feature-request/more-flexibility-in-the-xmlreader#p25085</guid>
        	        	<description><![CDATA[<p>Hello Oleg,</p>
<p>As usual very good addition from you.</p>
<p>I plan to include it ASAP.</p>
<p>Thank you.</p>
<p>Tony</p>
]]></description>
        	        	<pubDate>Mon, 07 Nov 2011 12:04:43 +0200</pubDate>
        </item>
        <item>
        	<title>OlegK on more flexibility in the xmlReader</title>
        	<link>http://www.trirand.com/blog/?page_id=393/feature-request/more-flexibility-in-the-xmlreader#p25084</link>
        	<category>Feature Request</category>
        	<guid isPermaLink="true">http://www.trirand.com/blog/?page_id=393/feature-request/more-flexibility-in-the-xmlreader#p25084</guid>
        	        	<description><![CDATA[<p>Hello Tony,</p>
<p>the current implementation of <strong>xmlReader</strong> and <strong>xmlmap</strong> is much less flexible as <strong>jsonReader</strong> and <strong>jsonmap</strong>. The most important restriction is that <strong>xmlReader</strong>&#160;and&#160;<strong>xmlmap</strong>&#160;don&#39;t support reading from attributes. Function are also not supported.</p>
<p>I suggest to use <strong>getXmlData</strong> in the same way like <strong>getAccessor</strong> are used in <strong>jsonReader</strong>&#160;and&#160;<strong>jsonmap</strong>. The implementation can be for example the following:</p>
<p><input type='button' class='sfcodeselect' name='sfselectit2232' value='Select Code' data-codeid='sfcode2232' /></p>
<div class='sfcode' id='sfcode2232'>getXmlData: function (obj, expr, returnObj) {<br />&#160; &#160; var ret, m = typeof (expr) === &#39;string&#39; ? expr.match(/^([.]*)[(w+)]$/) : null;<br />&#160; &#160; if (typeof (expr) === &#39;function&#39;) {<br />&#160; &#160; &#160; &#160; return expr(obj);<br />&#160; &#160; }<br />&#160; &#160; if (m &#38;&#38; m[2]) {<br />&#160; &#160; &#160; &#160; // m[2] is the attribute selector<br />&#160; &#160; &#160; &#160; // m[1] is an optional element selector<br />&#160; &#160; &#160; &#160; // examples: &#34;[id]&#34;, &#34;rows[page]&#34;, &#34;rows&#62;row[id=13]:first[id]&#34;<br />&#160; &#160; &#160; &#160; return m[1] ? $(m[1], obj).attr(m[2]) : $(obj).attr(m[2]);<br />&#160; &#160; } else {<br />&#160; &#160; &#160; &#160; ret = $(expr, obj).filter(&#39;:last&#39;);<br />&#160; &#160; &#160; &#160; return !returnObj &#38;&#38; ret.length &#62; 0 ? $(ret).text() : ret;<br />&#160; &#160; }<br />}&#160;</div>
<p>The method will allow selectors like <strong>getXmlData(data, &#39;rows[page]&#39;)</strong> or <strong>getXmlData(data, &#39;rows&#62;row[id=13]:first[id]&#39;)</strong>&#160;to get the data from the following XML</p>
<p><input type='button' class='sfcodeselect' name='sfselectit5124' value='Select Code' data-codeid='sfcode5124' /></p>
<div class='sfcode' id='sfcode5124'>&#60;?xml version=&#39;1.0&#39; encoding=&#39;utf-8&#39;?&#62;<br />&#60;rows page=&#34;1&#34; total=&#34;2&#34; records=&#34;13&#34;&#62;<br />&#160; &#160; &#60;row id=&#39;13&#39; firstName=&#34;Oleg&#34; lastName=&#34;Kiriljuk&#34; /&#62;<br />&#60;/rows&#62;&#160;</div>
<p>Additionally functions will be also supported. For example</p>
<p><input type='button' class='sfcodeselect' name='sfselectit1758' value='Select Code' data-codeid='sfcode1758' /></p>
<div class='sfcode' id='sfcode1758'>getXmlData(getXmlData(data, &#39;rows&#39;, true), function (x) {<br />&#160; &#160; return $(x).children(&#39;row:first&#39;).attr(&#39;firstName&#39;);<br />});&#160;</div>
<p>will return "Oleg" from the above XML. As the result one will receive close flexibility in reading of XML data like one has now in reading of JSON data</p>
<p>Best regards<br />Oleg&#160;</p></p>
]]></description>
        	        	<pubDate>Sun, 06 Nov 2011 00:48:31 +0200</pubDate>
        </item>
</channel>
</rss>