3.2.0

Editable date fields from an XML file...

Hi - excellent datagrid tool. But, as far as I am new in these subjects, I need some assistance:

I'm trying to load an XML file that's structured roughly like this (I named it grid.xml):
<excepciones>
<excepcion>
<desde>15/12/2006</desde>
<hasta>10/10/2005</hasta>
</excepcion>
<excepcion>
<desde>12/12/2003</desde>
<hasta>11/10/2002</hasta>
</excepcion>
</excepciones>

Reading some posted comments, I was able to implement a grid that displays the XML data and gives the chance to edit each cell by providing a calendar control, but after correctly selecting the desired date from the calendar it stops the editing and returns the following script error message:"Line: 24 Char: 8187 Error: Object doesn't support this property or method Code: 0".

My code, thus far, looks like this:
<html>
<head>
<title>Grid :: Test</title>
<style> body, html {margin:0px; padding: 0px; overflow: hidden;} </style>

<!-- stylesheet and scripts -->
<link type="text/css" rel="stylesheet" href="css/grid/xp/grid.css" >
<link type="text/css" rel="StyleSheet" href="css/calendar-system.css" />
<script type="text/javascript" src="js/jscal/calendar.js"></script>
<script type="text/javascript" src="js/jscal/lang/calendar-en.js"></script>
<script type="text/javascript" src="js/jscal/calendar-setup.js"></script>
<script type="text/javascript" src="js/grid/grid.js"></script>
<script type="text/javascript" src="js/templates.js"></script>
<style>

.active-controls-grid {height: 100%; font: menu;}
#ddgrid .active-controls-grid {height: 200; width: 160;}
#ddgrid .active-column-0 {width: 80px;}
#ddgrid .active-column-1 {width: 80px;}
#ddgrid .active-grid-column {border-right: 1px solid threedlightshadow;}

#maingrid .active-column-0 {width: 80px; vertical-align: middle;}
#maingrid .active-column-1 {width: 80px; vertical-align: middle;}
#maingrid .active-column-2 {width: 50px; vertical-align: middle;}
#maingrid .active-column-3 {width: 25px; vertical-align: middle;}
#maingrid .active-grid-column {border-right: 1px solid threedlightshadow;}
#maingrid .active-grid-row {border-bottom: 1px solid threedlightshadow;}

#maingrid .active-grid-row.gecko, .active-box-normal.gecko { overflow-y: visible; }

.active-templates-input {
overflow: hidden;
height: 100%;
padding: 0px 5px;
margin: -1px 0px;
border: 1px solid #666;
vertical-align: middle;
font: menu;
line-height: 1.4em;
}

.active-templates-input.gecko {
display: block;
margin: 0px;
}

.active-input-checkbox {
overflow: hidden;
width: 100%;
height: 100%;
padding: 0px 5px;
margin: 0px 0px 1px 0px;
vertical-align: middle;
}

.active-templates-ddgrid {
width: 100%;
height: 100%;
padding: 0px 5px;
margin: 0px 0px;
border: 0px solid #666;
vertical-align: top;
font: menu;
line-height: 1.4em;
OVERFLOW: auto;
POSITION: absolute;
background-color: white;
}

.active-templates-ddgrid.gecko {
display: block;
margin: 0px;
}
</style>
</head>
<body>

<table height="200" width="100%"><tr><td>
<script>
var table = new Active.XML.Table;
table.setURL("grid.xml");
table.request();

var obj = new Active.Controls.Grid;

obj.setId("maingrid");
var myColumns = [
"Desde", "Hasta"
];
obj.setColumnProperty("count", myColumns.length);
obj.setRowHeaderWidth("0px");
obj.setColumnHeaderHeight("20px");
obj.setSelectionProperty("multiple", true);
obj.setModel("data", table);

/* Need to add this so objects edited in grid customization don't get changed if user cancels */
function clone (deep) {
var objectClone = new this.constructor();
for (var property in this)
if (!deep)
objectClone[property] = this[property];
else if (typeof this[property] == 'object')
objectClone[property] = this[property].clone(deep);
else
objectClone[property] = this[property];
return objectClone;
}
Object.prototype.clone = clone;
/**************************************/

/* Code for making column ordering work */
var indices = [];
for(i=0; i<obj.getColumnProperty("count");i++) indices[i] = i; // populate from db
obj.setColumnTexts(myColumns);
obj.setColumnValues(indices);
/************************************/

obj.setDataText = function(value, i, j){table[i][j] = value};

var dateTemplate1 = new My.Templates.Date;
obj.setColumnTemplate(dateTemplate1,0);

var dateTemplate2 = new My.Templates.Date;
obj.setColumnTemplate(dateTemplate2,1);

/**** Column dragging ************/
var header = obj.getTemplate("top/item");
var mousedown = false;
var startX;
var startY;
var startElement;
var startElementChild;

var dragStart = function(event) {
startX=event.screenX;
startY=event.screenY;
startElementChild=event.srcElement;
startElement=startElementChild.parentNode;
startElement.width=startElement.offsetWidth;
startElement.height=startElement.offsetHeight;
if (startElement.height==0) startElement.parent.offsetHeight;

var offsetObj = startElement;
startElement.x = 0;
startElement.y = 0;
while(offsetObj.offsetParent.tagName!='BODY') {
startElement.x += offsetObj.offsetLeft
startElement.y += offsetObj.offsetTop
offsetObj = offsetObj.offsetParent
}
mousedown = true;
}

var drag = function(event) {
var x=event.screenX;
var y=event.screenY;
var dragHeaderDiv = document.getElementById('dragHeaderDiv');
if(dragHeaderDiv) dragHeaderDiv.style.left = x;
else if(mousedown && (x<startElement.x || x>(startElement.x+startElement.width))) {
var dragHeaderDiv = startElement.cloneNode(true)
dragHeaderDiv.id = "dragHeaderDiv";
dragHeaderDiv.className = dragHeaderDiv.className.replace(RegExp("sort-(ascending|descending)", "g"), "sort-none");
dragHeaderDiv.className += " active-header-over";
dragHeaderDiv.setAttribute("onmouseleave","")
dragHeaderDiv.setAttribute("onmouseenter","")
dragHeaderDiv.style.position = "absolute";
dragHeaderDiv.style.left = x;
dragHeaderDiv.style.top = startElement.y;
dragHeaderDiv.style.width = startElement.width;
dragHeaderDiv.style.height = startElement.height;
dragHeaderDiv.style.zIndex = 10000;
dragHeaderDiv.style.MozOpacity = 0.7;
dragHeaderDiv.style.filter = "alpha(opacity=70)"
startElement.parentNode.appendChild(dragHeaderDiv);
}
}

var getIndexFromId = function(id) {
var colonPos = id.indexOf(":");
var slashPos = id.indexOf("/");
var index = id.substring(colonPos+1);
if(slashPos!=-1) index = id.substring(0,slashPos);
var indices = obj.getColumnValues();
for(i=0;i<indices.length;i++) if(indices[i]==Number(index)) {index=i; break;}
return index;
}

var getHeaderIndexAt = function(x) {
var headersDiv = document.getElementById(obj.getId()+".layout/top");
var offsetObj = headersDiv;
var offsetX = 0;
while(offsetObj.offsetParent.tagName!='BODY') {
offsetX += offsetObj.offsetLeft
offsetObj = offsetObj.offsetParent
}

var headers = headersDiv.childNodes;
var column = 0;
for(i=0;i<headers.length;i++) {
if(x>=offsetX && x<(headers[i].offsetWidth+offsetX)) { column=i; break; }
offsetX+=headers[i].offsetWidth;
}
return column;
}

var dragEnd = function(event) {
mousedown = false;
var dragHeaderDiv = document.getElementById('dragHeaderDiv');
if(dragHeaderDiv) {
startElement.parentNode.removeChild(dragHeaderDiv);
var x=event.screenX;
var dragIndex = getIndexFromId(startElement.id);
var dropIndex = getHeaderIndexAt(x);
var indices = obj.getColumnValues();
dropIndex = dropIndex>(indices.length-1)?(indices.length-1):dropIndex;
var move = false;
var dragValue = indices[dragIndex];
if(dragIndex<dropIndex) for(i=dragIndex;i<dropIndex;i++) indices[i]=indices[i+1];
else for(i=dragIndex;i>dropIndex;i--) indices[i]=indices[i-1];
indices[dropIndex] = dragValue;
obj.setColumnValues(indices);
obj.refresh();
}
else if(event.srcElement==startElementChild) {
header.setClass("encabezado", "pulsado");
window.status = "Ordenando...";
header.timeout(function(){header.action("columnSort")});
}
}

header.setEvent("onmousedown", dragStart);
obj.setEvent("onmouseup", dragEnd);
obj.setEvent("onmousemove", drag);
/*******************************/
document.write(obj);

</script>
</td>
</tr>
</table>
</body>
</html>

Please let me know your comments, any help will be very much appreciated. Regards
German
December 26,
I figured it out, but I would have really appreciated a lot your comments or advice. Anyway, this was solved by replacing:

obj.setDataText = function(value, i, j){table[i][j] = value};

with:

table.setText = function(value, i, j){
var node = this.getNode(i, j);
node.text = value;
}

I hope this helps anyone else.
German
December 28,

This topic is archived.

See also:


Back to support forum