0

I'm having some trouble determining a good solution to save a Matrix field using Safecracker and AJAX.

From what I see matrix creates new rows by using field_name[row_new_0][col_id_xxx] or field_name[row_id_xxxx][col_id_xxx] when editing an existing row. I would have hoped that the row_id_xxxx was just an increment and would be replaced but that's not the case, instead it's a unique id.

The form I am creating allows the user to save a form before they submit it completely and what happens is it will continue to create "new" rows once it is saved.

Any ideas on how to prevent this?

2 Answers 2

1

Here's my solution. It simply makes an additional request to the form to grab the matrix fields and reinitializes them. I had to trim this up so it may or may not work in it's entirety but you get the idea.

$(function () {

    // ajax form post
    $("button[type='submit']").bind('click', function (e) {

        // select your form
        var $form = $('#yourform');

        // submit the form
        $.ajax({
            type: "POST",
            dataType: "json",
            url: $form.attr('action'),
            data: $form.serializeArray();,
            success: function (data) {
                if (data.success) 
                {
                    reloadMatrices(); // here's the magic
                    if ($form.find('[name="action"]').val() == "submit") // your form will have multiple <button name="action"> tags with different values such as "submit" or "save"
                    { 
                        alert("Thank you for your submission! We will be contacting you shortly.");
                        window.location = "//" + window.location.hostname + "/confirmation"; // redirect to confirmation page
                    }
                }
            }
        });

    });
});

/**
 * function reloadMatrices()
 * 
 * Requests the same form and replaces all instances of a Matrix fieldtype with the new form from the request and reinitializes them.
 */
function reloadMatrices() {
    $.ajax({
        type: "GET",
        url: window.location,
        success: function (data) {
            var $data = $(data);

            // you might be able to use .load() here instead for more concise code
            $('.matrix-ee2').each(function () {
                var $this = $(this);
                $this.replaceWith($data.find("#" + $this.attr('id')));

                // reinitialize all of the matrices so they work as intended
                // IMPORTANT: requires an md5 jQuery plugin such as https://github.com/placemarker/jQuery-MD5
                window['initMatrix_' + $.md5($this.attr('id'))](); 
            });

        }
    });
}
0

This sounds pretty complicated on the account of unique row IDs.

How about a sneaky workaround, since you're using AJAX already - after saving the partial form data, including Matrix, do an AJAX request that would return a safecracker form with Matrix field rendered with {field:matrix_field} and then parse that HTML with Javascript for the row IDs that you need?

1
  • Thanks Andris! I didn't have time to post a solution yesterday but I did come up with one that does exactly as you stated. I'll post below because I did run into some weird issues. :) Aug 16, 2013 at 17:03

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

Not the answer you're looking for? Browse other questions tagged or ask your own question.