在非ajax调用中在客户端执行JavaScript
在我的应用程序中,用户可以按下按钮创建和下载文件。这个过程需要一些时间,所以我想在此过程中阻止UI,直到出现下载窗口在非ajax调用中在客户端执行JavaScript,javascript,ajax,jsf-2,primefaces,callback,Javascript,Ajax,Jsf 2,Primefaces,Callback,在我的应用程序中,用户可以按下按钮创建和下载文件。这个过程需要一些时间,所以我想在此过程中阻止UI,直到出现下载窗口 <script type="text/javascript"> function start() { PF('crBui').show(); } function stop() { PF('crBui').hide(); } </script> 我正在处理响应的操作方法基本上如下所示: public void download() {
<script type="text/javascript">
function start() {
PF('crBui').show();
}
function stop() {
PF('crBui').hide();
}
</script>
我正在处理响应的操作方法基本上如下所示:
public void download() {
FacesContext facesContext = FacesContext.getCurrentInstance();
ExternalContext externalContext = facesContext.getExternalContext();
// set content disposition etc.
XSSFWorkbook wb = getWorkbook();
wb.write(externalContext.getResponseOutputStream());
facesContext.responseComplete();
}
<p:commandButton value="Doanload" id="b"
action="#{bean.doanload()}"
ajax="false"
onclick="PF('crBui').show();" />
<p:blockUI block=":trGrid" widgetVar="crBui" trigger="b">
<p:graphicImage value="/images/loading.gif" alt="loading..."/>
</p:blockUI>
<script type="text/javascript">
function start() {
PF('crBui').show();
}
function stop() {
PF('crBui').hide();
}
</script>
在我的JSF视图中,我触发了一个blockUI组件来禁用按钮,如下所示:
public void download() {
FacesContext facesContext = FacesContext.getCurrentInstance();
ExternalContext externalContext = facesContext.getExternalContext();
// set content disposition etc.
XSSFWorkbook wb = getWorkbook();
wb.write(externalContext.getResponseOutputStream());
facesContext.responseComplete();
}
<p:commandButton value="Doanload" id="b"
action="#{bean.doanload()}"
ajax="false"
onclick="PF('crBui').show();" />
<p:blockUI block=":trGrid" widgetVar="crBui" trigger="b">
<p:graphicImage value="/images/loading.gif" alt="loading..."/>
</p:blockUI>
<script type="text/javascript">
function start() {
PF('crBui').show();
}
function stop() {
PF('crBui').hide();
}
</script>
如果我使用ajax调用而不是非ajax调用,那么文件下载将不再有效
<script type="text/javascript">
function start() {
PF('crBui').show();
}
function stop() {
PF('crBui').hide();
}
</script>
有什么建议吗?我该如何归档我的功能?您应该使用,而不是尝试创建一些homebrewn解决方案。showcase中的修改示例:
<script type="text/javascript">
function start() {
PF('crBui').show();
}
function stop() {
PF('crBui').hide();
}
</script>
xhtml:
<script type="text/javascript">
function start() {
PF('crBui').show();
}
function stop() {
PF('crBui').hide();
}
</script>
函数start(){
PF('crBui').show();
}
函数停止(){
PF('crBui').hide();
}
Bean:
<script type="text/javascript">
function start() {
PF('crBui').show();
}
function stop() {
PF('crBui').hide();
}
</script>
import java.io.InputStream;
import javax.faces.bean.ManagedBean;
import javax.faces.context.FacesContext;
import javax.servlet.ServletContext;
import org.primefaces.model.DefaultStreamedContent;
import org.primefaces.model.StreamedContent;
@ManagedBean
public class FileDownloadView {
private StreamedContent file;
public FileDownloadView() {
InputStream stream = <create your stream>
file = new DefaultStreamedContent(stream, "<your mime-type>", "<your filename>");
}
public StreamedContent getFile() {
return file;
}
}
import java.io.InputStream;
导入javax.faces.bean.ManagedBean;
导入javax.faces.context.FacesContext;
导入javax.servlet.ServletContext;
导入org.primefaces.model.DefaultStreamedContent;
导入org.primefaces.model.StreamedContent;
@ManagedBean
公共类文件下载视图{
私有流内容文件;
公共文件下载视图(){
输入流=
文件=新的默认流内容(流“,”);
}
公共流内容getFile(){
返回文件;
}
}
您应该使用,而不是尝试创建一些自制解决方案。showcase中的修改示例:
<script type="text/javascript">
function start() {
PF('crBui').show();
}
function stop() {
PF('crBui').hide();
}
</script>
xhtml:
<script type="text/javascript">
function start() {
PF('crBui').show();
}
function stop() {
PF('crBui').hide();
}
</script>
函数start(){
PF('crBui').show();
}
函数停止(){
PF('crBui').hide();
}
Bean:
<script type="text/javascript">
function start() {
PF('crBui').show();
}
function stop() {
PF('crBui').hide();
}
</script>
import java.io.InputStream;
import javax.faces.bean.ManagedBean;
import javax.faces.context.FacesContext;
import javax.servlet.ServletContext;
import org.primefaces.model.DefaultStreamedContent;
import org.primefaces.model.StreamedContent;
@ManagedBean
public class FileDownloadView {
private StreamedContent file;
public FileDownloadView() {
InputStream stream = <create your stream>
file = new DefaultStreamedContent(stream, "<your mime-type>", "<your filename>");
}
public StreamedContent getFile() {
return file;
}
}
import java.io.InputStream;
导入javax.faces.bean.ManagedBean;
导入javax.faces.context.FacesContext;
导入javax.servlet.ServletContext;
导入org.primefaces.model.DefaultStreamedContent;
导入org.primefaces.model.StreamedContent;
@ManagedBean
公共类文件下载视图{
私有流内容文件;
公共文件下载视图(){
输入流=
文件=新的默认流内容(流“,”);
}
公共流内容getFile(){
返回文件;
}
}
我最终使用了PrimeFaces的PrimeFaces.monitorDownload()
<script type="text/javascript">
function start() {
PF('crBui').show();
}
function stop() {
PF('crBui').hide();
}
</script>
我认为:
<script type="text/javascript">
function start() {
PF('crBui').show();
}
function stop() {
PF('crBui').hide();
}
</script>
<p:commandButton value="Doanload" id="b"
action="#{bean.doanload()}"
ajax="false"
onclick="PrimeFaces.monitorDownload(start, stop);" />
<script type="text/javascript">
function start() {
PF('crBui').show();
}
function stop() {
PF('crBui').hide();
}
</script>
函数start(){
PF('crBui').show();
}
函数停止(){
PF('crBui').hide();
}
让DownloadMonitor工作的主要技巧是在响应中简单地设置Cookie:
<script type="text/javascript">
function start() {
PF('crBui').show();
}
function stop() {
PF('crBui').hide();
}
</script>
externalContext.addResponseCookie(
org.primefaces.util.Constants.DOWNLOAD_COOKIE,
"true",
Collections.<String, Object>emptyMap()
);
externalContext.addResponseCookie(
org.primefaces.util.Constants.DOWNLOAD_COOKIE,
“真的”,
Collections.emptyMap()
);
这样,UI元素将被阻止,直到出现文件下载窗口,这正是我最终想要实现的。我最终使用了PrimeFaces的PrimeFaces.monitorDownload()
<script type="text/javascript">
function start() {
PF('crBui').show();
}
function stop() {
PF('crBui').hide();
}
</script>
我认为:
<script type="text/javascript">
function start() {
PF('crBui').show();
}
function stop() {
PF('crBui').hide();
}
</script>
<p:commandButton value="Doanload" id="b"
action="#{bean.doanload()}"
ajax="false"
onclick="PrimeFaces.monitorDownload(start, stop);" />
<script type="text/javascript">
function start() {
PF('crBui').show();
}
function stop() {
PF('crBui').hide();
}
</script>
函数start(){
PF('crBui').show();
}
函数停止(){
PF('crBui').hide();
}
让DownloadMonitor工作的主要技巧是在响应中简单地设置Cookie:
<script type="text/javascript">
function start() {
PF('crBui').show();
}
function stop() {
PF('crBui').hide();
}
</script>
externalContext.addResponseCookie(
org.primefaces.util.Constants.DOWNLOAD_COOKIE,
"true",
Collections.<String, Object>emptyMap()
);
externalContext.addResponseCookie(
org.primefaces.util.Constants.DOWNLOAD_COOKIE,
“真的”,
Collections.emptyMap()
);
这样,UI元素将被阻止,直到出现文件下载窗口,这正是我最终想要实现的。感谢您的回答,如果我只想从服务器下载文件,“p:FileDownload”组件确实是件好事。但在我的情况下,ApachePOI库的工作方式与我直接写入OutputStream的方式相同,但StreamedContent只接受InputStream。我查看了PrimeFaces的源代码,发现它与我在代码中所做的几乎相同。因此,在这里使用PF组件,我最终会将文件写入ByteArrayOutputStream,然后再将其写入ByteInputStream,只需逐字节。。。只是让PF组件再次将其逐字节写入OutputSteam。听起来很难听。但是现在我了解了DownloadMonitor的工作原理,现在我可以不用p:fileDownload就可以使用它了。再次感谢你指出p:download的可能性,它让我朝着正确的方向前进:)谢谢你的回答,如果我只想从服务器下载一个文件,“p:fileDownload”组件确实是件好事,ApachePOI库的工作方式与我直接写入OutputStream的方式相同,但StreamedContent只接受InputStream。我查看了PrimeFaces的源代码,发现它与我在代码中所做的几乎相同。因此,在这里使用PF组件,我最终会将文件写入ByteArrayOutputStream,然后再将其写入ByteInputStream,只需逐字节。。。只是让PF组件再次将其逐字节写入OutputSteam。听起来很难听。但是现在我了解了DownloadMonitor的工作原理,现在我可以不用p:fileDownload就可以使用它了。因此再次感谢您通过p:download指出了这种可能性,它将我推向了正确的方向:)您的代码帮助我在
ajax=“false”
中使用了commandbutton
,但是为什么我需要使用org.primefaces.util.Constants.DOWNLOAD_COOKIE
?您的代码帮助我使用commandbutton
和ajax=“false”
,但是为什么我需要使用org.primefaces.util.Constants.DOWNLOAD_COOKIE
?
<script type="text/javascript">
function start() {
PF('crBui').show();
}
function stop() {
PF('crBui').hide();
}
</script>