PDA

View Full Version : Opera template problem



OutpostMM
3 Sep 2010, 2:46 PM
Hello,

I've got a custom component which includes a template to render the data. If I use the default template I have defined in the class, then everything works fine. If I define a slightly different template when I create the component, then it seems to strip the HTML from the template in Opera only. From everything I've looked at, it literally looks like the HTML was stripped, everything else is there.

This is my "TicketResponsePanel" component:


Ext.ux.TicketResponsePanel = Ext.extend(Ext.Panel, {
autoScroll: true,
refreshDelay: 60, // in seconds
url: '',
params: {},
root: 'data',
store: null,
timeoutInterval: null,
lastRefresh: 0,
recsLoaded: 0,
alwaysRefresh: false,
toolbars: [],

initComponent: function()
{
Ext.ux.TicketResponsePanel.superclass.initComponent.call(this);

this.addEvents(
'beforeupdatepanel',
'updatepanel'
);

if (this.store == null)
{
// configure store
this.store = new Ext.data.JsonStore({
url: this.url,
baseParams: this.params,
root: this.root,
autoDestroy: true,
fields: [
'id',
'ticket',
'post_date',
'user',
'info',
'tech_hours_spent',
'billable_hours_spent',
'fname',
'lname',
'account',
'admin',
'location',
'account_name',
'location_name'
],
listeners: {
scope: this,
'load': this.onStoreLoad
}
});
}

if (!this.responseTpl)
{
this.responseTpl = new Ext.Template(
'<div class="ticket-response">',
'<div class="ticket-response-header">',
'<span class="ticket-response-timestamp">{post_date}</span>',
' by ',
'<span class="ticket-response-author">{author}</span>',
'</div>',
'<div class="ticket-response-info">{info}</div>',
'</div>'
);
}
this.responseTpl.compile();
},

onRender: function(ct, position)
{
Ext.ux.TicketResponsePanel.superclass.onRender.call(this, ct, position);

if (this.refreshDelay > 0)
{
this.refresh();
}
},

refresh: function()
{
if (this.timeoutInterval != null) clearTimeout(this.timeoutInterval);
this.lastRefresh = (new Date()).valueOf();
this.timeoutInterval = setTimeout(this.refresh.createDelegate(this), this.refreshDelay * 1000);
this.store.load();
},

onStoreLoad: function(s, recs, o)
{
var i,
author = '',
loadMask;

// don't refresh the panel if we have the same number of records
if (!this.alwaysRefresh && this.recsLoaded == recs.length) {return;}

// fire beforeupdatepanel event, cancel if it returns false
if (!this.fireEvent('beforeupdatepanel', this, recs, o)) {return;}

// update the panel
var loadMask = new Ext.LoadMask(this.getEl(), {msg: 'Updating...'});
loadMask.show();
this.body.update('');
for (i = 0; i < recs.length; i++)
{
author = recs[i].data.fname + ' ' + recs[i].data.lname;

if (TicketSys.main.userdata.account_id != recs[i].data.account || TicketSys.main.userdata.location_id != recs[i].data.location)
{
if (recs[i].data.account_name != '' || recs[i].data.location_name != '')
author += ' (';

if (recs[i].data.account_name != '')
{
author += recs[i].data.account_name;
if (recs[i].data.location_name != '')
author += ' - ';
}

if (recs[i].data.location_name != '')
author += recs[i].data.location_name

if (recs[i].data.account_name != '' || recs[i].data.location_name != '')
author += ')';
}

this.responseTpl.append(this.body, {
'post_date': recs[i].data.post_date,
'author': author,
'info': recs[i].data.info,
'tech_hours_spent': recs[i].data.tech_hours_spent,
'billable_hours_spent': recs[i].data.billable_hours_spent
});
}
this.recsLoaded = recs.length;
setTimeout(loadMask.hide.createDelegate(loadMask), 500);

/* var el = Ext.get(this.header.dom.parentNode.parentNode.parentNode);
var tmp = new Ext.Element('<div></div>', true);
tmp.appendTo(this.header);
tmp.show();;

tmp.setBox(el.getBox());
tmp.render();

tmp.highlight('FFCC00', {
easing: 'easeOut',
duration: 1
}); */

// fire updatepanel event
this.fireEvent('updatepanel', this, recs, o);
},

setRefresh: function(t)
{
t = parseFloat(t, 10);
if (isNaN(t)) return false;

if (this.getSecondsUntilRefresh() > t)
{
this.refreshDelay = t;
clearTimeout(this.timeoutInterval);
this.timeoutInterval = setTimeout(this.refresh.createDelegate(this), this.refreshDelay * 1000);
}
else
{
this.refreshDelay = t;
}
return true;
},

getSecondsSinceRefresh: function()
{
var ms = (new Date()).valueOf() - this.lastRefresh;
return ms / 1000;
},

getSecondsUntilRefresh: function()
{
return this.refreshDelay - this.getSecondsSinceRefresh();
},

beforeDestroy: function()
{
if (this.timeoutInterval != null)
{
clearTimeout(this.timeoutInterval);
}
}
});

Ext.reg('ticketresppanel', Ext.ux.TicketResponsePanel);

The default template defined there in initComponent shows up just fine in Opera. This is an example of creating that component that displays like it should:


Ext.getCmp(panel_id).add({
// response panel
xtype: 'ticketresppanel',
id: panel_id + '-response-panel',
title: 'Ticket History',
autoHeight: true,
maxHeight: 600,
params: {page_mode: 'get-ticket-responses', id: resp.data.id},
url: TicketSys.main.gateway,
collapsible: true,
titleCollapse: true,
border: false,
frame: true,
bodyStyle: 'padding: 3px;',
cls: 'top-margins'
});

Here's an instance where I create a new component and give it a different template to use, and this is what does not display correctly in Opera:


p.add({
// response panel
xtype: 'ticketresppanel',
id: guid + 'response-panel',
title: 'Ticket History',
autoHeight: true,
anchor: '-18',
params: {page_mode: 'get-ticket-responses', id: id},
url: TicketSys.main.gateway,
collapsible: true,
titleCollapse: true,
border: false,
frame: true,
bodyStyle: 'padding: 3px;',
cls: 'top-margins',
responseTpl: new Ext.Template(
'<div class="ticket-response">',
'<div class="ticket-response-header">',
'<span class="ticket-response-timestamp">{post_date}</span>',
' by ',
'<span class="ticket-response-author">{author}</span>',
'</div>',
'<div class="ticket-response-info">{info}</div>',
'<div class="ticket-response-time">Labor Hours: {tech_hours_spent}; Billable: {billable_hours_spent}</div>',
'</div>'
)
});

Can anyone spot the problem?

OutpostMM
3 Sep 2010, 3:01 PM
I think I found the problem, but I have no clue what this means.

Using Opera Dragonfly, I opened the source for the Javascript file that contains the code to add the misbehaving panel. This is what Dragonfly displays as the source:


p.add({
// response panel
xtype: 'ticketresppanel',
id: guid + 'response-panel',
title: 'Ticket History',
autoHeight: true,
anchor: '-18',
params: {page_mode: 'get-ticket-responses', id: id},
url: TicketSys.main.gateway,
collapsible: true,
titleCollapse: true,
border: false,
frame: true,
bodyStyle: 'padding: 3px;',
cls: 'top-margins',
responseTpl: new Ext.Template(
'',
'',
'{post_date}',
' by ',
'{author}',
'',
'{info}',
'Labor Hours: {tech_hours_spent}; Billable: {billable_hours_spent}',
''
)
});

Why would the HTML markup be missing from the version of the file that Opera is actually using? Why would that get stripped out like that?

Condor
6 Sep 2010, 3:00 AM
Could it be this issue (http://javascript.about.com/library/blxhtml.htm)?

OutpostMM
10 Sep 2010, 11:42 AM
It may have been something like that, although the page is using HTML4 strict instead of XHTML. I worked around it by splitting up the HTML tags, e.g.:


this.responseTpl = new Ext.Template(
'<' + 'div class="ticket-response">',
'<' + 'div class="ticket-response-header">',
'<' + 'span class="ticket-response-timestamp">{post_date}<' + '/span>',
' by ',
'<' + 'span class="ticket-response-author">{author}<' + '/span>',
'<' + '/div>',
'<' + 'div class="ticket-response-info">{info}<' + '/div>',
'<' + '/div>'
);