如何在下载文件后隐藏动画gif?

在执行某些服务器端Java代码并且客户端从Web服务器获取HTTP响应而不使用Ajax时,有没有办法让动画gif图像消失?

我使用以下Struts2提交按钮:

 

显示动画gif图像的方法:

 function myJsFunction(){ $("#containerWithGifImage").fadeIn("fast"); } 

消除动画gif图像的方法(但我不知道,如何在没有Ajax的情况下调用它):

  function myJsFunction2(){ $("#containerWithGifImage").fadeOut("fast"); } 

现在gif出现了,但是在执行webserver上的java代码之后它并没有消失。

你的问题(这个和另一个 )都是XY问题的例子。

在寻找特定技术,技术或黑客之前,请先明确定义您的目标:

目标

  1. 下载文件而不移动到其他页面;
  2. 同时,显示一个指标(进度条,动画gif,叠加等…);
  3. 下载文件后,隐藏指示器。

解决方案

将您的触发器绑定到javascript函数, 如下所述 :

  download  

在你的Javascript函数中:显示指标,启动计时器以检查下载是否结束(然后隐藏指标),然后下载文件:

  function myJsFunction(){ $("#containerWithGifImage").fadeIn("fast"); // Show the indicator setInterval(function(){ $.ajax({ url : "/isDownloadFinished.action", type : "GET", success : function(data,textStatus,jqXHR) { $("#containerWithGifImage").fadeOut("fast"); // Hide the indicator },error : function(jqXHR, textStatus, errorThrown) { console.log("Download is still in progress, do nothing..."); } }); }, 1000); // Check every second if download has finished window.location='/download.action'; // Start the download } 

Download.action必须在会话中放入一个指示下载已开始的属性,并在结束时进行更新。
由于使用stream结果,您将控制对浏览器的响应(因此在完成后无法运行代码),您可以直接写入响应,然后返回NONE , 如下所述 :

 public class Download extends ActionSupport implements SessionAware, ServletResponseAware { @Setter private Map session; @Setter private HttpServletResponse response; public String execute(){ ServletOutputStream os = null; try { session.put("DOWNLOAD_STATUS","active"); response.setContentType("myContentType"); response.addHeader("Content-Disposition", "attachment; filename=\"foo.bar\""); os = response.getOutputStream(); IOUtils.copy(getMyFileInputStreamSomeHow(), os); } finally { IOUtils.closeQuietly(os); session.put("DOWNLOAD_STATUS","finished"); } return NONE; } } 

您还可以让浏览器通过指定Content-Length响应头( response.setHeader("Content-Length", 1337); )来为您绘制进度条, 如此处所述 ,您还可以在其中查看类似的机制以防止并发下载。

IsDownloadFinished.action中 ,您需要检查会话属性。 我它不存在或与完成不同,这意味着下载尚未开始,或仍在进行中,因此什么都不做。 否则,返回一个成功的httpheader,它将使你的jQuery $ .ajax函数运行success:回调。 您可以使用httpHeaderjson , 如下所述 :

 @Results({ @Result(name = ActionSupport.SUCCESS, type="httpheader", params = {"status", "200"}), @Result(name = ActionSupport.ERROR, type="httpheader", params = {"error", "500"}) }) public class IsDownloadFinished extends ActionSupport implements SessionAware { @Setter private Map session; public String execute(){ if ("finished".equals(session.get("DOWNLOAD_STATUS")) { session.remove("DW_STATUS"); return SUCCESS; } return ERROR; } } 

这个问题有不同的解决方案,我向你展示了最简单的解决方案。
更优雅和复杂的解决方案将涉及长期请求和Comet技术 (读取:WebSocket),但我想您可以从此启动示例开始使用轮询计时器,根据您的需求进行自定义,并最终在更多时候进行演变对论点感到满意。