显示显示表单提交进度的进度条

这个问题没有完全解答,请免费捐赠!


我试图在提交大型表单时显示简单的progress bar

该表格包含十几个字段,以及一些文件上传字段,用户可以在其中选择图片。 然后,当他点击Create按钮时,将提交包含数据和图片的表单,并在数据库中创建该实体。 (只需点击一下提交表格和图片)。
一切工作正常,但我想在提交过程中显示进度栏。

我发现很多教程解释了如何显示进度条,但我没有找到任何人解释如何显示进度条,指示方法完成的工作百分比 ,即我希望看到10% 25%等...在提交过程中。

所以,基本上,这就是我所做的:(这是一个ASP.NET MVC3项目)

@model MyModel

@using (Html.BeginForm(null, null, FormMethod.Post, new { id = "target-form", enctype = "multipart/form-data" }))
{
    //some Html.TextBoxFor() and other @Html.DropDownListFor

    @Html.TextBoxFor(m => m.File, new { type = "file"})

    <input type="submit" value="Create" class="submitButton" />

    <div id="progressBar"></div>
}

和一个基本的控制器

[HttpPost]
public ActionResult Create(MyModel model)
{
    if (ModelState.IsValid)
    {
        DALLayer dal = new DALLayer()
        dal.AddEntity(model);

        return RedirectToAction("Index", "Home");
    }

    return null;
}

是否有可能改变我最后<div>progressBar显示的上传进度的状态?


这是我的要求:

  • 没有插件(这是个人项目,我想了解如何自己做这件事)。
  • 交叉兼容,IE8 +(如果可能)
  • jQuery确定,但没有Flash。

  • 非常感谢你 !

    更新1这里是一个JSFIDDLE,我试图改变这个链接,但没有成功......如果你认为你可以提供帮助,那么不用客气!


    更新2好吧,我用acarlon的答案来提交我的表单与XMLHttpRequest和数据是正确的张贴到控制器。 但是,ProgressBar仍然不会显示!
    我只是通过以下方式替换传递给控制器​​的数据:

    formData = new FormData(document.getElementById("target-form") );
    xhr.open("POST", "@Url.Action("MyMethod", "MyController")", true );
    

    并尝试一些不同的标题,如:

    xhr.setRequestHeader("X-File-Name", $('#Files_0__File')[0].files[0].name);
    xhr.setRequestHeader("X-File-Size", $('#Files_0__File')[0].files[0].size);
    xhr.setRequestHeader("X-File-Type", $('#Files_0__File')[0].files[0].type);
    //Also tried with "Content-Length" but it doesn't care about it.
    

    (这里硬编码确保它有很好的价值,当我更放心时,我会循环执行它。)

    当我提交表单时, XMLHttpRequest发送包含这些字段:

    readyState:4
    状态:0 <=应该是200,对吗?

    error handler ,我有这些值:

    加载:0
    总计:883526
    键入:“错误”

    所以数据被提交给我的控制器,但我无法显示这个该死的进度条...


    上传文件时,您可以使用XMLHttpRequest来接收更新。 也有各种jquery类型的包装实现相同。 我将使用XMLHttpRequest描述一个解决方案。 首先拦截表单提交。

    $("#target-form").submit(function () {
    

    然后创建XHR请求:

     xhr = new XMLHttpRequest();
    

    然后注册以通知进度事件:

    xhr.upload.addEventListener( "progress", function ( evt )
    {
        if( evt.lengthComputable )
        {
            var progressPercent = ( evt.loaded / evt.total ) * 100;
            showProgress( value );//your function.
        }
    }, false );
    
    
    //Some other events you will probably want to subscribe to
    xhr.addEventListener( "load", function ()
    {            
        fileUploadComplete( this.responseText );
    }, false );
    
    xhr.addEventListener( "error", function ( first, second, third )
    {
        fileUploadComplete( "Error: Image format not supported." );
    }, false );
    
    xhr.addEventListener( "abort", function ()
    {
        fileUploadComplete( "Error: Upload was cancelled. Please try again." );
    }, false );
    

    打开任何参数传递的XHR(以id为例)

    xhr.open( "post", '@Html.Raw( @Url.Action( "UploadImage", new { someId = id } ) )', true );
    
    // Set appropriate headers                
    xhr.setRequestHeader( "Content-Type", "multipart/form-data" );
    xhr.setRequestHeader( "X-File-Name", name );
    
    // Send the file
    xhr.send( file );
    

    然后在控制器中:

    public ActionResult UploadImage( int someId, HttpPostedFileBase userFile  )
    {
        ...    
    }
    

    您将在更新处理程序中收到更新。

    长时间运行服务器任务的扩展

    如果服务器上有一些长时间运行的任务(例如将数据写入数据库),则需要在服务器上对操作进行分块(以便可以在每个块的完成时提供更新),并实现代码以处理长时间运行的服务,您可以从javascript中查询。 看这里。 基本思想是在服务器端启动任务并定期检查Javascript的进度。 您可能希望有两个单独的进度条,一个用于上传,另一个用于服务器端操作。 这为用户提供了更多信息 - 他们会知道文件上传已完成,现在正在进行一些服务器端操作。


    添加一个ajax计时器控件,用于检查服务器的进度并设置时间间隔(比如每2秒)。

    在新线程上执行您的服务器任务。 这会导致您的帖子立即返回,同时在后台执行您的长时间任务。 启动ajax计时器。

    由于长期任务的工作原因,让它更新一个包含完成工作的会话变量。

    当计时器回传给服务器时,从会话变量中获取完成的工作。

    您可以通过设置内部div和外部div来设计进度条。 将内部div的宽度设置为%完成工作:$('#progressBarWorkDone')。css('width',WorkDone +'%');

    <div id="progressBar" style="width:400px;">    
    <div id="progressBarWorkDone" style="width:0px;height:10px;background-color:red;"><div/> 
    <div/>
    

    注意,如果你不知道如何使用定时器控件,你也可以使用setInterval(function(){AJAX CALLBACK GOES HERE},1000)从javascript执行AJAX调用。

    不过,尽管在进度条div中放置了一个动画gif,这样做更简单。 隐藏div,然后在点击提交按钮时显示div。

    <input type="submit" onclick="$('#progressBar').show();" value="Create" class="submitButton" />
    
    <div id="progressBar" style="display:none;"><img src="myProgressBar.gif" /></div>
    

    我曾经使用SWF上传器和perl后端文件(当时PHP不支持上传进度),但看起来它不再处于活跃的开发阶段。

    我没有使用Plupload,但它看起来非常适合你。 似乎你可以拥有一个asp后端。

    祝你好运,并保持干爽;)

    链接地址: http://www.djcxy.com/p/77591.html

    上一篇: Displaying a progress bar showing the progress of a form submission

    下一篇: automate deployment to sonatype's oss maven repository