补充知识点:form表单target会指定的action跳转目标 ,因为不知道这个知识点浪费好久去找Ext如何把response回写到iframe中
Ext3.0实现表单提交的代码如下
function doFormUpload(o, ps, url){
var id = Ext.id(),
doc = document,
frame = doc.createElement('iframe'),
form = Ext.getDom(o.form),
hiddens = [],
hd,
encoding = 'multipart/form-data',
buf = {
target: form.target,
method: form.method,
encoding: form.encoding,
enctype: form.enctype,
action: form.action
};
Ext.apply(frame, {
id: id,
name: id,
className: 'x-hidden',
src: Ext.SSL_SECURE_URL // for IE
});
doc.body.appendChild(frame);
// This is required so that IE doesn't pop the response up in a new window.
if(Ext.isIE){
document.frames[id].name = id;
}
Ext.apply(form, {
target: id,
method: POST,
enctype: encoding,
encoding: encoding,
action: url || buf.action
});
// add dynamic params
ps = Ext.urlDecode(ps, false);
for(var k in ps){
if(ps.hasOwnProperty(k)){
hd = doc.createElement('input');
hd.type = 'hidden';
hd.value = ps[hd.name = k];
form.appendChild(hd);
hiddens.push(hd);
}
}
function cb(){
var me = this,
// bogus response object
r = {responseText : '',
responseXML : null,
argument : o.argument},
doc,
firstChild;
try{
doc = frame.contentWindow.document || frame.contentDocument || WINDOW.frames[id].document;
if(doc){
if(doc.body){
if(/textarea/i.test((firstChild = doc.body.firstChild || {}).tagName)){ // json response wrapped in textarea
r.responseText = firstChild.value;
}else{
r.responseText = doc.body.innerHTML;
}
}
//in IE the document may still have a body even if returns XML.
r.responseXML = doc.XMLDocument || doc;
}
}
catch(e) {}
Ext.EventManager.removeListener(frame, LOAD, cb, me);
me.fireEvent(REQUESTCOMPLETE, me, r, o);
function runCallback(fn, scope, args){
if(Ext.isFunction(fn)){
fn.apply(scope, args);
}
}
runCallback(o.success, o.scope, [r, o]);
runCallback(o.callback, o.scope, [o, true, r]);
if(!me.debugUploads){
setTimeout(function(){
try{
Ext.removeNode(frame);
}catch(e){}
}, 100);
}
}
Ext.EventManager.on(frame, LOAD, cb, this);
form.submit();
Ext.apply(form, buf);
Ext.each(hiddens, function(h) {
Ext.removeNode(h);
});
}
仔细研读代码,Ext的提交实际上调用的是dom的submit,并且Ext新建了一个iframe作为form提交后跳转的target,但因为IE9及之前的跨域安全机制需要添加这么个src,导致iframe加载的时候会出现src里的Ext.SSL_SECURE_URL和真正的表单提交response顺序在chrome某些版本下出现问题。
- response加载比Ext.SSL_SECURE_URL快那么请求正常,页面正常;
- response虽然完成但是Ext.SSL_SECURE_URL快一步先load到iframe中,导致请求虽然是200但是callback获取的却是Ext.SSL_SECURE_URL,页面报错;
- Ext.SSL_SECURE_URL在response返回前加载完成Ext会取消请求,页面获取到的依然是Ext.SSL_SECURE_URL,报错;
所以在iframe属性设置的时候判断下是不是IE,非IE下取消src的值即可
Ext.apply(frame, {
id: id,
name: id,
className: 'x-hidden',
src: Ext.isIE ? Ext.SSL_SECURE_URL : '' // for IE
});