-
14 Jul 2010 12:29 AM #1
Ext.ux.DownloadIframe -> opening downloads in an iframe
Ext.ux.DownloadIframe -> opening downloads in an iframe
Hi,
I needed to open downloads in an iframe that a download will not be blocked by a popup blocker.
So I wrote a little class to load my download into an iframe:
Sample usage:Code:Ext.ux.DownloadIframe = Ext.extend(Ext.util.Observable, function () { var BEFOREDOWNLOADSTART = "beforedownloadstart", DOWNLOADSTART = "downloadstart", iframe = null, loadMask = null; return { constructor: function (config) { if (!Ext.isEmpty(config)) { Ext.apply(this, config, { "name": "Ext_ux_DownloadIframe" }); } this.superclass().constructor.apply(this, arguments); }, initComponent: function () { this.superclass().initComponent.call(this); this.addEvents( BEFOREDOWNLOADSTART, DOWNLOADSTART); }, start: function (download, loadMaskCfg) { if (iframe !== null) iframe.destroy(); var on = { }; on[BEFOREDOWNLOADSTART] = { "fn": this.onBeforeDownloadStart, "single": true, "scope": this }; on[DOWNLOADSTART] = { "fn": this.onDownloadStart, "single": true, "scope": this }; this.on(on); if (!Ext.isEmpty(loadMaskCfg)) { if (loadMaskCfg instanceof Ext.Element) { loadMaskCfg = { "el": loadMaskCfg }; } var lmCfg = { "msg": "Loading..." }, el = loadMaskCfg.el || Ext.getBody(); Ext.apply(lmCfg, loadMaskCfg); loadMask = new Ext.LoadMask(el, lmCfg); } iframe = new Ext.BoxComponent( { "width": 0, "height": 0, "autoEl": { "tag": "iframe", "name": this.name, "frameBorder": 0, "src": download, "style": { "border": "0 none" } } }); this.fireEvent(BEFOREDOWNLOADSTART, this, iframe, download); iframe.render(this.renderTo || Ext.getBody()); iframe.el.dom.onload = this.onload.createDelegate(this, [this, iframe, download]); }, onload: function (o, iframe, download) { o.fireEvent(DOWNLOADSTART, o, iframe, download); }, onBeforeDownloadStart: function (o, iframe, download) { if (loadMask !== null) loadMask.show(); }, onDownloadStart: function (o, iframe, download) { if (loadMask !== null) loadMask.hide(); } } }());
-> On button click the download will open and a loadMask (on body) will appear till the download starts.Code:var download = new Ext.ux.DownloadIframe(); var downloadBtn = new Ext.Button({ "text": "download", "handler": function() { download.start("url/to/downloadfile.zip", true); } }); btn.render("content");
Greets eztam!
-
14 Jul 2010 6:06 AM #2Sencha - Community Support Team
- Join Date
- Mar 2007
- Location
- The Netherlands
- Posts
- 24,251
- Vote Rating
- 40
I assume you are downloading files with Content-disposition:attachment? In that case you will never get a load event on the IFRAME, so you would never hide the loadmask.
-
14 Jul 2010 11:06 PM #3
-
14 Jul 2010 11:28 PM #4Sencha - Community Support Team
- Join Date
- Mar 2007
- Location
- The Netherlands
- Posts
- 24,251
- Vote Rating
- 40
No, I've tried everything, but you just can't get notified when the download finishes.
-
14 Jul 2010 11:44 PM #5
My downloads are generated in a php script, so if I want to show a loadMask while download is generated, I have to generate it asynchronously (showing the loadMask till request is done), temporarily save the download, return the link and load the returned link into the iframe (without loadMask). Then I could delete the temporary file on download.
This is the only solution!?
-
15 Jul 2010 12:36 AM #6Sencha - Community Support Team
- Join Date
- Mar 2007
- Location
- The Netherlands
- Posts
- 24,251
- Vote Rating
- 40
Looks ok, but I wouldn't remove the temporary file on download - the user might want to retry. Instead I would use a batch job to delete old temporary files.
-
15 Jul 2010 2:02 AM #7
As Condor said there's no way to get notification when the download finishes, so I solved using the browser defaults.
Pratically when the form is submited (see code below) the browser open a new blank window during the server processing (e.g. report creation). When the processing is done the window is automatically closed by the browser and the 'normal' browser file download process begin ('save dialog' appears...etc..).
advantage:
- User can continue to work while the server is processing the request and while the browser is downloading the file.
- The progress of the file download is managed by the browser so it is visibible (in the status bar or in the download window...depends on the browser)
- Multiple file download at the same time (not possible with the iframe solution if the download iframe is always the same)
disadvantage:
- blank window during the long server process.
- no custom load mask
this is my code:
ciaoCode:exportReport : function(url, params) { // cannot add fields directly to the form due an IE bugs // that doesn't permit to change the form's action (url) // if inside there is a field named 'action' // // workaround: create the form, set the form's action and finally add the fields var form = new Ext.form.FormPanel({ url: url, hidden : true, hideMode: 'offsets', method: 'POST', standardSubmit : true, items: [{xtype: 'hidden', name : 'dummy', value: ''}] // extJs required at least on field }); form.render(document.body); // set the url and the target of the form form.getForm().getEl().dom.action = url; form.getForm().getEl().dom.target = "_blank"; // this is the trick!!!! // create hidden fields and add them to the form if(params) { for (p in params) { form.add({ xtype: 'hidden', name : p, value: params[p] }); } } // render the fields form.doLayout(); // form submit form.getForm().submit(); // destroy form and garbage stuff form.destroy(); delete form; }
-Mario
Similar Threads
-
Ext JS 3.2 Air and Titanium documentation downloads.
By jay@moduscreate.com in forum Community DiscussionReplies: 2Last Post: 21 Apr 2010, 10:18 AM -
Opening windows from iframe... (window.parent.etc...)
By josemsn in forum Ext 2.x: Help & DiscussionReplies: 2Last Post: 3 Apr 2008, 2:26 AM -
How many ext downloads/installations out there?
By deitch in forum Community DiscussionReplies: 6Last Post: 11 Feb 2008, 4:21 PM


Reply With Quote