Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

jQuery, MVC3: Submitting a partial view form within a modal dialog

I'm just playing around with jQuery and MVC3 at the moment, and am wondering how I can submit a form, which has been dynamically loaded into a jQueryUI dialog?

My code so far consists of...

Javascript/jQuery

$(document).ready(function () {

    $('.trigger').live('click', function (event) {

       var id = $(this).attr('rel');

       var dialogBox = $("<div>");

       $(dialogBox).dialog({
           autoOpen: false,
           resizable: false,
           title: 'Edit',
           modal: true,
           show: "blind",
           hide: "blind",
           open: function (event, ui) {
               $(this).load("PartialEdit/" + id.toString());
           }
        }
    });

    $(dialogBox).dialog('open');

})    });

cshtml

<h2>Detail</h2><a href="#" class="trigger" rel="1">Open</a>

Controller

public ActionResult PartialEdit(int id)
    {
        return PartialView(new EditViewModel() { Name = id.ToString() });
    }

    [HttpPost]
    public ActionResult PartialEdit(int id, FormCollection collection)
    {
        // What to put here???            
    }

The Partial View

....@using (Html.BeginForm()){....Html.EditorFor(model => model.Name).....}....

As you can see the load() in jQuery calls a PartialView named PartialEdit.

The form is loading up just fine, but I'm stuck working out how I actually submit the form?

Questions

How do I get the UI to submit the form, and close the dialog? What should the [HttpPost]PartialEdit return?

At the moment I have the submit button within the partial view. When clicked, the form is submitted, and the browser does whatever the [HttpPost]PartialEdit returns (currently resulting in a blank page being displayed).

However, after a submit I would like instead to trigger an event on the client side (Maybe a full page refresh, or a partial page refresh depending on the context it is used). I'm not sure where to start?

Also, should I be placing a submit button within the PartialView, or should I use the buttons on the jQuery-UI dialog?

Any suggestions/pointers appreciated.

like image 528
ETFairfax Avatar asked Jun 22 '11 16:06

ETFairfax


2 Answers

Try something among the lines:

open: function (event, ui) {
    $(this).load("PartialEdit/" + id.toString(), function(html) {
        $('form', html).submit(function() {
            $.ajax({
                url: this.action,
                type: this.method,
                data: $(this).serialize(),
                success: function(res) {
                    if (res.success) {
                        $(dialogBox).dialog('close');
                    }
                }
            });
            return false;
        });
    });
}

and the controller action could return JSON:

[HttpPost]
public ActionResult PartialEdit(int id, FormCollection collection)
{ 
    // do some processing ...

    // obviously you could also return false and some error message
    // so that on the client side you could act accordingly
    return Json(new { success = true });
}

The final part for improvement is this:

"PartialEdit/" + id.toString()

Never do such url hardcoding in an ASP.NET MVC application. Always use url helpers when dealing with urls. So make your anchor a little more dynamic and instead of:

<a href="#" class="trigger" rel="1">Open</a>

use:

@Html.ActionLink(
    "Open", 
    "PartialEdit", 
    new {
        id = "1" // you probably don't need a rel attribute
    }, 
    new { 
        @class = "trigger"
    }
)

and then:

$(this).load(this.href, function(html) {
    ...
    return false; // now that the anchor has a href don't forget this
});
like image 123
Darin Dimitrov Avatar answered Oct 20 '22 05:10

Darin Dimitrov


Thanks for all your input, the solution that is working for me at the moment is having this function attached to the "Submit" button on the dialog....

"Submit": function () {
    var $this = this;
    var form = $('form', $this);
    if (!$(form).valid()) {
       return false;
    }

    $.post(form.attr("action"), JSON.stringify($(form).serializeObject()), function () {
        $($this).dialog("close").dialog("distroy").remove();
    });
}

...which is a bit of a combination of the answers above.

Thanks again.

like image 1
ETFairfax Avatar answered Oct 20 '22 03:10

ETFairfax