2016-08-23 36 views
1

我需要從form獲得價值,將其格式化爲JSON並通過AJAX發佈。這是我想達到的格式爲:jQuery表單 - 序列化成多維數組?

{ 
    items: [ 
    { id: 7, name: 'Book', price: 5.7 }, 
    { id: 5, name: 'Pencil', price: 2.5 } 
    ] 
} 

這裏的HTML:

(function($){ 
 
    
 
    var $form = $('form'); 
 
    
 
    // serializeArray format is way off from what I need 
 
    var rawData = $form.serializeArray(); 
 
    console.log(rawData) 
 
    
 
})(jQuery);
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script> 
 
<form> 
 
    <fieldset> 
 
    <h2>Product 1</h2> 
 
    <input type="hidden" name="items[0][id]" value="7"> 
 
    <input type="text" name="items[0][name]" value="Book"> 
 
    <input type="number" name="items[0][price]" value="5.7"> 
 
    </fieldset> 
 
    
 
    <fieldset> 
 
    <h2>Product 2</h2> 
 
    <input type="hidden" name="items[1][id]" value="5"> 
 
    <input type="text" name="items[1][name]" value="Pencil"> 
 
    <input type="number" name="items[1][price]" value="2.5"> 
 
    </fieldset> 
 
</form>

我應該環路,並使用正則表達式來解析name?還是有內置的方式?

如果需要,我可以更改<form>格式。

+0

無,我的意思是我想從輸入中獲取所有數據以形成該JSON。我需要通過Ajax發佈。我將編輯該問題以使其更清晰 – hrsetyono

+0

序列化在這裏不起作用,您需要手動執行 –

回答

1

請看一看這種方法。我們不能只使用$.serializeArray(),但我們也需要一些自定義代碼,如下所示。實際上,我們需要遍歷所有<fieldset>得到JSON因爲我們需要:

(function($) { 
 

 
    var $form = $('form'); 
 
    var fieldSets = $form.find("fieldset"); 
 
    var result = { 
 
    items: [] 
 
    }; 
 
    fieldSets.each(function() { 
 
    var fields = {}; 
 
    $.each($(this).serializeArray(), function() { 
 
     fields[this.name] = this.value; 
 
    }); 
 
    result.items.push(fields); 
 
    }); 
 

 
    console.log(result); 
 
})(jQuery);
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script> 
 
<form> 
 
    <fieldset> 
 
    <h2>Product 1</h2> 
 
    <input type="hidden" name="id" value="7"> 
 
    <input type="text" name="name" value="Book"> 
 
    <input type="number" name="price" value="5.7"> 
 
    </fieldset> 
 

 
    <fieldset> 
 
    <h2>Product 2</h2> 
 
    <input type="hidden" name="id" value="5"> 
 
    <input type="text" name="name" value="Pencil"> 
 
    <input type="number" name="price" value="2.5"> 
 
    </fieldset> 
 
</form>

注:修改了一下作爲代替name="items[0][id]"我已經給了HTML作爲name="id"

+0

謝謝,這似乎是更簡單的解決方案。 – hrsetyono

+0

歡迎@DarcCode ...':)'! – vijayP

1

是的,你需要自己解析name這個字段。沒有自動分析自定義字段的方法。當然有多種方法。

注意:我假設您的name="items[0][id]"字段指定它必須是結果數組中的第0項,並且這樣的<input>字段集不一定按照DOM中的item#的升序排列。換句話說,item[N]應該控制在<form>中的第Q <fieldset>

你可以使用serializeArray(),然後處理這些數據:

(function($){ 
 
    
 
    var $form = $('form'); 
 
    var data = $form.serializeArray(); 
 
    var result = {items:[]}; 
 
    data.forEach(function(input){ 
 
    nameArray = input.name.split(/[[\]]/); 
 
    item = nameArray[1]; 
 
    prop = nameArray[3]; 
 
    if(typeof result.items[item] !== 'object'){ 
 
     result.items[item]={}; 
 
    } 
 
    if(typeof result.items[item][prop] !== 'undefined'){ 
 
     //Consistency check the name attribute 
 
     console.log('Warning duplicate "name" property =' + input.name); 
 
    } 
 
    result.items[item][prop]=input.value; 
 
    }); 
 
    console.log(result); 
 
})(jQuery);
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script> 
 
<form> 
 
    <fieldset> 
 
    <h2>Product 1</h2> 
 
    <input type="hidden" name="items[0][id]" value="7"> 
 
    <input type="text" name="items[0][name]" value="Book"> 
 
    <input type="number" name="items[0][price]" value="5.7"> 
 
    </fieldset> 
 
    
 
    <fieldset> 
 
    <h2>Product 2</h2> 
 
    <input type="hidden" name="items[1][id]" value="5"> 
 
    <input type="text" name="items[1][name]" value="Pencil"> 
 
    <input type="number" name="items[1][price]" value="2.5"> 
 
    </fieldset> 
 
</form>

或者,你可以直接從DOM處理它:

(function($){ 
 

 
    var result = {items:[]}; 
 
    
 
    $('form fieldset input').each(function(){ 
 
    nameArray = this.name.split(/[[\]]/); 
 
    item = nameArray[1]; 
 
    prop = nameArray[3]; 
 
    if(typeof result.items[item] !== 'object'){ 
 
     result.items[item]={}; 
 
    } 
 
    if(typeof result.items[item][prop] !== 'undefined'){ 
 
     //Consistency check the name attribute 
 
     console.log('Warning duplicate "name" property =' + this.name); 
 
    } 
 
    result.items[item][prop]=this.value; 
 
    }); 
 
    console.log(result); 
 
})(jQuery);
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script> 
 
<form> 
 
    <fieldset> 
 
    <h2>Product 1</h2> 
 
    <input type="hidden" name="items[0][id]" value="7"> 
 
    <input type="text" name="items[0][name]" value="Book"> 
 
    <input type="number" name="items[0][price]" value="5.7"> 
 
    </fieldset> 
 
    
 
    <fieldset> 
 
    <h2>Product 2</h2> 
 
    <input type="hidden" name="items[1][id]" value="5"> 
 
    <input type="text" name="items[1][name]" value="Pencil"> 
 
    <input type="number" name="items[1][price]" value="2.5"> 
 
    </fieldset> 
 
</form>

+0

爲什麼您認爲這個解決方案將幫助OP? – vijayP

+0

感謝您的回答。 'items [0]'只是爲了避免重名的例子。我想可以使用重複名稱,如'id'或'name'就像vijayP的答案 – hrsetyono

+0

@DarcCode,謝謝。通常'name'屬性是很方便的(它可以用來對元素進行分組)(例如'getElementsByName()')。另一次,請在問題中提及HTML可以更改。當我讀到這個問題時,我假設你正在嘗試使用JavaScript來獲取基於HTML格式的所需JSON。考慮到它的寫法,這個假設和vijayP的假設(HTML可以方便地改變)都是有效的。在這個問題中指出將幫助人們爲你提供更好的答案。 – Makyen

1

這裏不能使用默認的序列,而不是你可以做一個手動系列化像

(function($) { 
 

 
    var $fieldsets = $('form fieldset'); 
 

 
    var items = $fieldsets.map(function(i, fs) { 
 
    var obj = {}; 
 
    $(fs).find('input').each(function() { 
 
     obj[this.name.match(/\[([^\[]*)\]$/)[1]] = this.value; 
 
    }); 
 
    return obj; 
 
    }).get(); 
 

 
    var rawData = { 
 
    items: items 
 
    }; 
 
    console.log(rawData) 
 

 
})(jQuery);
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script> 
 
<form> 
 
    <fieldset> 
 
    <h2>Product 1</h2> 
 
    <input type="hidden" name="items[0][id]" value="7"> 
 
    <input type="text" name="items[0][name]" value="Book"> 
 
    <input type="number" name="items[0][price]" value="5.7"> 
 
    </fieldset> 
 

 
    <fieldset> 
 
    <h2>Product 2</h2> 
 
    <input type="hidden" name="items[1][id]" value="5"> 
 
    <input type="text" name="items[1][name]" value="Pencil"> 
 
    <input type="number" name="items[1][price]" value="2.5"> 
 
    </fieldset> 
 
</form>