【ASP.NET MVC】HTML 5+MVCアップロードファイル表示進捗

16442 ワード

head>

    <title>Index</title>

    <style type="text/css">

        #statusBorder

        {

            position:relative;

            height:5px;

            width:100px;

            border:solid 1px gray;

            display:none;

            }

        #statusFill{

            position:absolute;

            top:0;

            left:0;

            width:0px;

            background-color:Blue;

            height:5px;

}

    </style>

    <script src="../../Scripts/jquery-1.5.1.min.js" type="text/javascript"></script>

    <script type="text/javascript">

        var uniqueId = " @Guid.NewGuid().ToString()";



        $(document).ready(function (event) {

            $('#startProcess').click(function () {

                $.post("Home/StartLongRunningProcess",{ id: uniqueId }, function (data) {

                    if (data = "null") {

                        alert("");

                    }

                    else {

                        $('#statusBorder').show();

                        getStatus();

                    }

                }, "multipart/form-data");

                event.preventDefault;

            });

        });



        function getStatus() {

            var url = 'Home/GetCurrentProgress/' + uniqueId;

            $.get(url, function (data) {

                if (data != "100") {

                    $('#status').html(data);

                    $('#statusFill').width(data);

                    window.setTimeout("getStatus()", 100);

                }

                else {

                    $('#status').html("Done");

                    $('#statusBorder').hide();

                    alert("      ");

                };

            });

        }

    </script>

</head>

<body>

    <div>

     <div id="status">

            </div>

        <h2>@Html.Encode(ViewData["Message"]) </h2>

        <div>

            <input id="File1" type="file" name="file" />

            <input id="startProcess" type="submit" value="  " />

        </div>

        <br />

        <div id="statusBorder">

            <div id="statusFill">

            </div>

        </div>

    </div>

</body>

</html>

アクションコード
    public class HomeController : Controller

    {

        //

        // GET: /Home/



        public ActionResult Index()

        {

            ViewData["Message"] = "Ajax Progress Bar Example";

            return View();

        }



        delegate string ProcessTask(string id);

        MyLongRunningClass longRunningClass = new MyLongRunningClass();



        public ContentResult StartLongRunningProcess(string id)

        {

            var file=Request.Files["file"];

            if (file != null)

            {

                file.SaveAs(Server.MapPath("~/Content/" + file.FileName));

                longRunningClass.Add(id);

                ProcessTask processTask = new ProcessTask(longRunningClass.ProcessLongRunningAction);

                processTask.BeginInvoke(id, new AsyncCallback(EndLongRunningProcess), processTask);

                return Content("ok");

            }

            else

            {

                return Content("null");

            }

        }



        public void EndLongRunningProcess(IAsyncResult result)

        {

            ProcessTask processTask = (ProcessTask)result.AsyncState;

            string id = processTask.EndInvoke(result);

            longRunningClass.Remove(id);

        }



        public ContentResult GetCurrentProgress(string id)

        {

            this.ControllerContext.HttpContext.Response.AddHeader("cache-control", "no-cache");

            var currentProgress = longRunningClass.GetStatus(id).ToString();

            return Content(currentProgress);

        }

        public ActionResult Upload(HttpPostedFileBase[] fileToUpload)

        {

            ViewBag.Message = "File(s) uploaded successfully"; 

            return RedirectToAction("Index");

        }

csコード
public class MyLongRunningClass

    {

        private static object syncRoot = new object();



        private static IDictionary<string, int> ProcessStatus { get; set; }



        public MyLongRunningClass()

        {

            if (ProcessStatus == null)

            {

                ProcessStatus = new Dictionary<string, int>();

            }

        }



        public string ProcessLongRunningAction(string id)

        {

            for (int i = 1; i <= 100; i++)

            {

                Thread.Sleep(100);

                lock (syncRoot)

                {

                    ProcessStatus[id] = i;

                }

            }

            return id;

        }



        public void Add(string id)

        {

            lock (syncRoot)

            {

                ProcessStatus.Add(id,0);

            }

        }



        public void Remove(string id)

        {

            lock (syncRoot)

            {

                ProcessStatus.Remove(id);

            }

        }



        public int GetStatus(string id)

        {

            lock (syncRoot)

            {

                if (ProcessStatus.Keys.Count(x => x == id) == 1)

                {

                    return ProcessStatus[id];

                }

                else

                {

                    return 100;

                }

            }

        }

    }