Select2: добавить и выбрать ручные значения при использовании источника данных ajax
Я хочу добиться следующего сценария с select2(4.0.0) и jquery(2.1.4):
- У меня есть поле выбора, которое берет данные из внешнего источника (конечная точка на сервере приложений Java)
- Пользователь может выбрать одно из возвращаемых значений или придумать собственное значение
- Теперь, когда пользователь отправляет форму и проверка на стороне сервера завершается неудачей, я хотел бы отобразить форму со всеми значениями, предоставленными ранее пользователем, поэтому в поле выбора должно быть значение, отправленное на сервер.
Чтобы достичь этого
- Я использую Ajax от выбора для запроса данных с сервера
- Я использую createTag, чтобы позволить пользователю создавать свои собственные значения
- Я хотел использовать initSelection, чтобы предварительно заполнить selectbox значением, ранее добавленным пользователем.
Мой код выглядит так:
$("select[name='serie']").select2({
ajax: {
url: "http://javaendpoit/serie/filter",
dataType: 'json',
delay: 250,
data: function (params) {
return {
name: params.term,
page: params.page
};
},
processResults: function (data, page) {
return {
results: $.map(data, function (item) {
return {
text: item.name,
name: item.name,
id: item.name
}
})
};
},
cache: true
},
escapeMarkup: function (markup) { return markup; },
minimumInputLength: 2,
templateResult: formatRepo,
templateSelection: formatRepoSelection,
tags: true,
createTag: function (tag) {
return {
id: tag.term,
text: tag.term,
name: tag.term,
isNew : true
};
},
/* below part is rendered by jsp so that it has the value from previous form submission; if it is initial form render the below part is not included */
initSelection : function (element, callback) {
callback({id:"Name",name:"Name","text":"Name"});
}
});
function formatRepo (serie) {
if (serie.loading) return serie.text;
var markup = '<div class="clearfix">' +
'<div clas="col-sm-10">' +
'<div class="clearfix">' +
'<div class="col-xs-12">' + serie.name + '</div>' +
'</div>';
markup += '</div></div>';
return markup;
}
function formatRepoSelection (serie) {
return serie.name;
}
Это работает просто отлично. Это означает, что после отправки я вижу значение Имя в поле выбора и это выбранное значение. Тем не менее, если я попытаюсь отправить эту форму еще раз, значение отсутствует в запросе.
Как предложено в числе тем здесь, я добавил следующую строку (см. Последнюю строку).
/* [...] */
initSelection : function (element, callback) {
callback({id:"Name",name:"Name","text":"Name"});
}
}).select2("val","Name");
Но после добавления этого значения имя даже не отображается в поле select2.
Я пытался исправить это в течение нескольких часов, но почему-то не могу найти правильное решение. Могу поспорить, что мне не хватает некоторых базовых вещей. Пожалуйста, помогите!
--- [РЕДАКТИРОВАТЬ]
После добавления данных я могу видеть значение Name даже при установке значения с помощью val, тем не менее, если я повторно отправляю форму, это значение все еще отсутствует в запросе.
.select2('data',{id:"Name",name:"Name","text":"Name"})
.select2('val', "Name")
--- [РЕДАКТИРОВАТЬ 2]
В html я использую select для создания этого элемента.
<select class="form-control" name="serie"></select>
2 ответа
Благодаря Кевину я смог разгадать загадку. Так что в конечном итоге я отказался от использования initSelection. Вместо этого я просто заполнил тег выбора параметрами, которые следует выбрать.
<select class="form-control" id="author" name="author" multiple="multiple">
<option value="name" selected="selected">name</option>
</select>
Удален initSelection из определения select2
$("select[name='author']").select2({
ajax: {
url: "http://javaendpoit/serie/filter",
dataType: 'json',
delay: 250,
data: function (params) {
return {
name: params.term,
page: params.page
};
},
processResults: function (data, page) {
return {
results: $.map(data, function (item) {
return {
text: item.name,
name: item.name,
id: item.name
}
})
};
},
cache: true
},
escapeMarkup: function (markup) {
return markup;
},
minimumInputLength: 1,
templateResult: formatRepo,
templateSelection: formatRepoSelection,
tags: true,
createTag: function (tag) {
return {
id: tag.term,
text: tag.term,
name: tag.term,
isNew: true
};
}
});
И изменил formatRepoSelection для работы со значениями без атрибута name.
function formatRepoSelection(serie) {
if (serie.name === undefined) {
return serie.text;
} else {
return serie.name;
}
}
Я думаю, что я не мог использовать атрибут имени в formatRepo и мог удалить предложение if для formatRepoSelection. Но это только незначительное исправление.
Мне удается сделать это с Select2 версии 4.0.2, как это:
$("select[name='serie']").data('select2')
.dataAdapter.select({
id:"Name",
name:"Name",
"text":"Name"
});