开发者

How to fill form with JSON?

开发者 https://www.devze.com 2023-03-25 22:57 出处:网络
I get ajax response as JSON and need to fill a form with it. How to do that in jQuery or something else ? Is something better than using $(json).each() ?

I get ajax response as JSON and need to fill a form with it. How to do that in jQuery or something else ? Is something better than using $(json).each() ?

JSON:

{ 
  "id" : 12,
  "name": "Jack",
  "description": "Description"
}

Form to fill

<form>
  <input type="text" name="id"/>
  <input type="text开发者_JS百科" name="name"/>
  <input type="text" name="description"/>
</form>


var json={ 
  "id" : 12,
  "name": "Jack",
  "description": "Description"
};
for(key in json)
{
  if(json.hasOwnProperty(key))
    $('input[name='+key+']').val(json[key]);
}

srry i thought it was the id property that was set.

here: http://jsfiddle.net/anilkamath87/XspdN/


Came here searching for a solution that didn't involve jQuery or a brunch of DOM scaning, but didn't find one... so here is my vanilla js solution brought to you other guys that probably ditched jQuery long ago.

const data = { 
  "id" : 12,
  "name": "Jack",
  "description": "Description",
  "nonExisting": "works too"
}

const { elements } = document.querySelector('form')

for (const [ key, value ] of Object.entries(data) ) {
  const field = elements.namedItem(key)
  field && (field.value = value)
}
<form>
  <input type="text" name="id"/>
  <input type="text" name="name"/>
  <input type="text" name="description"/>
</form>


Assuming data is the JSON object, you could use this inside the $.getJSON callback:

var $inputs = $('form input');
$.each(data, function(key, value) {
  $inputs.filter(function() {
    return key == this.name;
  }).val(value);
});


Pretty simple in pure JavaScript:

https://jsfiddle.net/ryanpcmcquen/u8v47hy9/

var data = {
  foo: 1,
  bar: 2
};
var inputs = Array.prototype.slice.call(document.querySelectorAll('form input'));

Object.keys(data).map(function (dataItem) {
  inputs.map(function (inputItem) {
    return (inputItem.name === dataItem) ? (inputItem.value = data[dataItem]) : false;
  });
});
<form>
  <input name="foo">
  <input name="bar">
</form>

Edit: This also works with other inputs such as select, simply by replacing document.querySelectorAll('form input') with document.querySelectorAll('form input, form select').

This also gets around the global leak in this answer: https://stackoverflow.com/a/6937576/2662028


jQuery Populate plugin and code proposed by @Mathias inspired me to make my own plugin:

Here my myPopulate plugin code. It use attr parameter as name of elements attribute on to use for identifying them.

(function($) {
    $.fn.myPopulate = function(json, attr) {
        var form = $(this);
        $.each(json, function(key, value) {
            form.children('[' + attr + '="' + key + '"]').val(value);
        });
    };
})(jQuery);

Using:

{ 
  "id" : 12,
  "name": "Jack",
  "description": "Description"
}

form1 (matching by name attribute):

<form>
    <input type="text" name="name" />
    <input type="text" name="id" />
    <textarea type="text" name="description" />
</form>
$('#form1').myPopulate(json, 'name');

form2 (matching by alt attribute):

<form id="form2">
    <input type="text" name="nick" alt="name" />
    <input type="text" name="identifier" alt="id" />
    <textarea type="text" name="desc" alt="description" />
</form>
$('#form2').myPopulate(json, 'alt');


I'm using this method with iCheck elements. This method can work native check and radio inputs.

populateForm(frm, data) {
    console.log(data);

    $.each(data, function(key, value) {
        var ctrl = $("[name=" + key + "]", frm);
        switch (ctrl.prop("type")) {
            case "radio":
                if (
                    ctrl.parent().hasClass("icheck-primary") ||
                    ctrl.parent().hasClass("icheck-danger") ||
                    ctrl.parent().hasClass("icheck-success")
                ) {
                    // raido kutularında aynı isimden birden fazla denetçi olduğu için bunları döngüyle almak lazım
                    // multiple radio boxes has same name and has different id. for this we must look to each html element
                    $.each(ctrl, function(ctrlKey, radioElem) {
                        radioElem = $(radioElem);
                        console.log(radioElem);
                        console.log(radioElem.attr("value"));

                        if (radioElem.attr("value") == value) {
                            radioElem.iCheck("check");
                        } else {
                            radioElem.iCheck("uncheck");
                        }
                    });
                } else {
                    $.each(ctrl, function(ctrlKey, radioElem) {
                        radioElem = $(radioElem);
                        console.log(radioElem);
                        console.log(radioElem.attr("value"));

                        if (radioElem.attr("value") == value) {
                            radioElem.attr("checked", value);
                        } else {
                            radioElem.attr("checked", value);
                        }
                    });
                }
                break;

            case "checkbox":
                if (
                    ctrl.parent().hasClass("icheck-primary") ||
                    ctrl.parent().hasClass("icheck-danger") ||
                    ctrl.parent().hasClass("icheck-success")
                ) {
                    if (ctrl.attr("value") == value) {
                        ctrl.iCheck("check");
                    } else {
                        ctrl.iCheck("uncheck");
                    }
                } else {
                    ctrl.removeAttr("checked");
                    ctrl.each(function() {
                        if (value === null) value = "";
                        if ($(this).attr("value") == value) {
                            $(this).attr("checked", value);
                        }
                    });
                }
                break;
            default:
                ctrl.val(value);
        }
    });
}

Example form:

<form id="form1">
    <div className="form-group row">
        <label className="col-sm-3 col-form-label">
            {window.app.translate(
                "iCheck Radio Example 1"
            )}
        </label>
        <div className="col-sm-9">
            <div className="icheck-primary">
                <input
                    type="radio"
                    id="radio1_0"
                    name="radio1"
                    value="0"
                />
                <label for="radio1_0">
                    {window.app.translate(
                        "Radio 1 0"
                    )}
                </label>
            </div>
            <div className="icheck-primary">
                <input
                    type="radio"
                    id="radio1_1"
                    name="radio1"
                    value="1"
                />
                <label for="radio1_1">
                    {window.app.translate(
                        "Radio 1 1"
                    )}
                </label>
            </div>
            <div className="icheck-primary">
                <input
                    type="radio"
                    id="radio1_2"
                    name="radio1"
                    value="2"
                />
                <label for="radio1_2">
                    {window.app.translate(
                        "Radio 1 2"
                    )}
                </label>
            </div>
        </div>
    </div>

    <div className="form-group row">
        <label className="col-sm-3 col-form-label">
            {window.app.translate(
                "iCheck Radio Example 2"
            )}
        </label>
        <div className="col-sm-9">
            <div className="icheck-primary">
                <input
                    type="radio"
                    id="radio2_0"
                    name="radio2"
                    value="0"
                />
                <label for="radio2_0">
                    {window.app.translate(
                        "Radio 2 0"
                    )}
                </label>
            </div>
            <div className="icheck-primary">
                <input
                    type="radio"
                    id="radio2_1"
                    name="radio2"
                    value="1"
                />
                <label for="radio2_1">
                    {window.app.translate(
                        "Radio 2 1"
                    )}
                </label>
            </div>
            <div className="icheck-primary">
                <input
                    type="radio"
                    id="radio2_2"
                    name="radio2"
                    value="2"
                />
                <label for="radio2_2">
                    {window.app.translate(
                        "Radio 2 2"
                    )}
                </label>
            </div>
        </div>
    </div>


    <div className="form-group row">
        <label
            htmlFor="ssl"
            className="col-sm-3 col-form-label"
        >
            {window.app.translate("SSL")}
        </label>
        <div className="col-sm-9">
            <div className="form-group row">
                <div className="col-sm-12">
                    <div className="icheck-primary d-inline">
                        <input
                            type="checkbox"
                            id="ssl"
                            name="ssl"
                            value="1"
                        />
                        <label for="ssl" />
                    </div>
                </div>
            </div>
        </div>
    </div>


</form>

Example json data:

{
    "radio1": "3",
    "radio2": "1",
    "ssl": "0"
}

Edit: I tried populate plugin but it doesn't working with iCheck and other things for example select2, chosen, etc...


You might want to take a look at the jQuery Populate plugin.

Although if this is the only use case you have, you might as well do it manually.


Just use a JSON plugin for jQuery - such as jquery-json.


You might also consider usage of jQuery templates for that purpose:

http://api.jquery.com/jQuery.template/


First you need to parse the JSON string so that you get an object that you can use:

var o = $.parseJSON(json);

(Note: You can also specify the data type 'json' in the AJAX call, then it will be parsed into an object already when you get the result.)

Then you can loop throught the properties in the object:

$.each(o, function(key, value){
  $('form [name=' + key + ']').val(value);
});


I haven't seen a solution that accounts for a form with nested properties. Here it is.

//pass in the parent object name, if there is one
let parentName = 'optional';
SyncJsonToForm(data, parentName);

function SyncJsonToForm(obj, path = '') {
     let subpath = path === '' ? path : path + '.';
     $.each(obj, function (key, value) {
          let jsonPath = subpath + key;

          // to debug a particular field (or multiple fields), replace the following JsonPath(s) with the desired property(ies)
          if ([''].includes(jsonPath)) {
               console.log(jsonPath);
               debugger;
          }

          // update the value for the jsonPath
          $(`[name="${jsonPath}"]`).val(value);

          if (typeof value === "object") {
               SyncJsonToForm(value, jsonPath);
          }
     });
}
0

精彩评论

暂无评论...
验证码 换一张
取 消