Я новичок в веб-приложениях и наткнулся на проблему в Meteor, для которой я не нашел хорошего решения (пожалуйста, дайте мне знать, если ответ уже существует на https://stackoverflow.com/).
У меня есть страница шаблона profileEdit
, которую я хочу обновить значениями по умолчанию из коллекции Meteor.users
по мере ее отображения. Это прекрасно работает с помощью помощников по шаблонам для <input type="text">
, но для:
<select class="form-control" name="profileNamePrefix" id="profileNamePrefix">
а также
<label><input type="radio" name="profileGender">Male</label>
Мне пришлось использовать манипуляции с DOM jQuery, чтобы заставить его работать (это может быть моей настоящей проблемой):
JS
// GLOBAL FUNCTIONS
updateSelectedOption = function() {
var currentUserId = Meteor.userId();
var currentUser = Meteor.users.findOne(currentUserId);
var profileTitleOptions = $('#profileNamePrefix').children();
var status = false;
for (var i = 0; i < profileTitleOptions.length; i++) {
if (currentUser && currentUser.profile &&
currentUser.profile.title === profileTitleOptions[i].value) {
profileTitleOptions[i].selected = true;
statue = true;
break;
};
};
return status;
};
updateCheckedRadio = function() {
var currentUserId = Meteor.userId();
var currentUser = Meteor.users.findOne(currentUserId);
var profileGenderRadios = $('input:radio[name="profileGender"]');
var status = false;
for (var i = 0; i < profileGenderRadios.length; i++) {
if (currentUser && currentUser.profile &&
currentUser.profile.gender === $(profileGenderRadios[i].closest('label'))[0].innerText) {
$(profileGenderRadios[i]).attr("checked", "checked");
status = true;
break;
};
};
return status;
};
Эти функции работают, но я не знаю, где разместить вызовы функций. Поскольку они получают данные из Meteor.users
Collection , их следует вызывать как помощники (как обсуждалось здесь):
JS
Template.profileEdit.helpers({
'selectOptionIfTitleIs': function() {
return updateSelectedOption();
},
'checkRadioIfGenderIs': function() {
return updateCheckedRadio();
});
HTML
<template name="profileEdit">
<form role="form">
<div class="row">
<div class="col-sm-2">
<div class="form-group">
<label>Title</label>
<select class="form-control" name="profileNamePrefix" id="profileNamePrefix">
<option value="Mr">Mr.</option>
<option value="Ms">Ms.</option>
<option value="Mrs">Mrs.</option>
<option value="Dr">Dr.</option>
<option value="Prof">Prof.</option>
<option value="Sir">Sir</option>
</select>
{{#if selectOptionIfTitleIs}}
{{/if}}
</div>
</div><!-- /.col-sm-2 -->
<div class="col-sm-2">
<div class="radio">
<label><input type="radio" name="profileGender">Male</label>
</div>
<div class="radio">
<label><input type="radio" name="profileGender">Female</label>
</div>
</div><!-- /.col-sm-2 -->
{{#if checkRadioIfGenderIs}}
{{/if}}
</div>
</form>
</template>
Это работает, когда страница обновляется, но когда она перенаправляется с панели навигации через Router.go('profileEdit');
, она не обновляет выбранные/отмеченные значения, потому что вызовы jQuery пусты (я подозреваю, что это потому, что они выполняются до того, как HTML будет правильно вынесено). Добавление вызовов функций в onRendered()
решает эту проблему, но не работает при обновлении страницы.
JS
Template.profileEdit.onRendered(function() {
updateSelectedOption();
updateCheckedRadio();
});
Есть ли способ объединить эти два вызова функций и обновлять форму, когда страница перенаправляется, а также обновляется? Любые советы о том, как лучше реализовать функциональность обновления в Meteor, также приветствуются.
Отредактировано
После небольшого размышления и некоторой помощи от решения Питера я решил эту проблему, используя вместо этого только помощники пробелов и шаблонов:
HTML
<form role="form">
<div class="col-sm-2">
<div class="form-group">
<label>Title</label>
<select class="form-control" name="profileNamePrefix" id="profileNamePrefix">
{{#each namePrefixes}}
<option value="{{value}}" selected="{{prefixIsSelected}}">{{name}}</option>
{{/each}}
</select>
</div>
</div><!-- /.col-sm-2 -->
<div class="col-sm-2">
{{#each genders}}
<div class="radio">
<label><input type="radio" name="profileGender" checked="{{genderIsChecked}}">{{name}}</label>
</div>
{{/each}}
</div><!-- /.col-sm-2 -->
</form>
JS
Template.profileEdit.helpers({
namePrefixes: [{
name: "Mr.",
value: "Mr"
},
{
name: "Ms.",
value: "Ms"
},
{
name: "Mrs.",
value: "Mrs"
},
{
name: "Dr.",
value: "Dr"
},
{
name: "Prof.",
value: "Prof"
},
{
name: "Sir",
value: "Sir"
}
],
genders: [{name: "Male"},
{name: "Female"}
],
'prefixIsSelected': function() {
var currentUserId = Meteor.userId();
var currentUser = Meteor.users.findOne(currentUserId);
return currentUser && currentUser.profile && currentUser.profile.title === this.value;
},
'genderIsChecked': function() {
var currentUserId = Meteor.userId();
var currentUser = Meteor.users.findOne(currentUserId);
return currentUser && currentUser.profile && currentUser.profile.gender === this.name;
}
});
Таким образом, форма правильно обновляется при перенаправлении или обновлении. Остается только один вопрос: если мне придется обновлять что-то через jQuery, основанное на коллекции данных, откуда можно будет вызывать этот код? Или всегда можно найти «метеоритный путь» с помощью пробелов?
Заранее спасибо,