Decir que tengo un juego de 3 botones de radio:KnockoutJS: Fundido de entrada después de desvanecimiento algo más
<div>
<label>
<input type="radio" name="Who" value="Myself"
checked="@isMyselfChecked" data-bind="checked: who" />
Mine
</label>
<label>
<input type="radio" name="Who" value="MemberId"
checked="@isMemberIdChecked" data-bind="checked: who" />
I know the member's ID
</label>
<label>
<input type="radio" name="Who" value="MemberUrl"
checked="@isMemberUrlChecked" data-bind="checked: who" />
I know the member's URL
</label>
</div>
Cuando el usuario selecciona el primer botón (Mine/yo), no se requiere ninguna entrada adicional. Sin embargo, al seleccionar la segunda o tercera, de entrada adicional de es necesario:
<div>
<input type="text" name="MemberId" placeholder="Enter Member ID"
data-bind="toggleWho: who()" style="display: none" />
<input type="text" name="MemberUrl" placeholder="Enter Member URL"
data-bind="toggleWho: who()" style="display: none; width: 450px;" />
</div>
Es bastante fácil tener sólo data-bind="visible: who() === '[MemberId|MemberUrl]'"
en los cuadros de texto dependientes. Sin embargo, ¿qué sucede si quiero agregar transiciones de fundido de entrada/salida?
Probé el ejemplo personalizado fadeVisible
bindingHandler
del sitio de eliminación directa, y entiendo cómo funciona. Sin embargo, esto se desvanecerá y se desvanecerá en los cuadros de texto al mismo tiempo. Si se selecciona la radio 'MemberId'
, y el usuario selecciona 'MemberUrl'
de radio, quiero que el cuadro de MemberId
texto alcanza el volumen mínimo antes la caja MemberUrl
texto se desvanece en.
A continuación se muestra lo que tengo ahora, y funciona, pero yo no' Creo que es óptimo. ¿De qué otra manera se le puede decir a un novato que no realice el fundido de entrada hasta que se haya desvanecido un elemento anterior? ¿Necesito otro ko.observale
, o posiblemente un ko.computed
?
var viewModel = {
fadeSpeed: 150,
who: ko.observable($('input[type=radio][name=Who]:checked').val())
};
ko.bindingHandlers.toggleWho = {
init: function (element, valueAccessor) {
var value = valueAccessor();
var unwrapped = ko.utils.unwrapObservable(value);
if (unwrapped === element.name)
$(element).show();
},
update: function (element, valueAccessor) {
var value = valueAccessor();
var unwrapped = ko.utils.unwrapObservable(value);
// when selected value is myself, fade out the visible one, if any
if (unwrapped === 'Myself') {
$('input[type=text][name=MemberId]:visible')
.fadeOut(viewModel.fadeSpeed);
$('input[type=text][name=MemberUrl]:visible')
.fadeOut(viewModel.fadeSpeed);
}
// when selected value is memberid, may need to fade out url first
else if (unwrapped === 'MemberId') {
if ($('input[type=text][name=MemberUrl]:visible').length > 0) {
$('input[type=text][name=MemberUrl]:visible')
.fadeOut(viewModel.fadeSpeed, function() {
$('input[type=text][name=MemberId]')
.fadeIn(viewModel.fadeSpeed);
});
} else {
$('input[type=text][name=MemberId]')
.fadeIn(viewModel.fadeSpeed);
}
}
// when selected value is memberurl, may need to fade out id first
else if (unwrapped === 'MemberUrl') {
if ($('input[type=text][name=MemberId]:visible').length > 0) {
$('input[type=text][name=MemberId]:visible')
.fadeOut(viewModel.fadeSpeed, function() {
$('input[type=text][name=MemberUrl]')
.fadeIn(viewModel.fadeSpeed);
});
} else {
$('input[type=text][name=MemberUrl]')
.fadeIn(viewModel.fadeSpeed);
}
}
}
};
ko.applyBindings(viewModel);
Glad I could help. Es posible que desee considerar una solución más orientada a modelos. Las cosas tenderán a ser más simples con KO si sigues el patrón de MVVM. – Tyrsius
@Tyrsius, por "solución orientada a modelos", ¿quiere decir usar un foreach para procesar las radios desde la vm en lugar de emitirlas explícitamente en HTML? – danludwig
Sí, entre otras cosas. La idea en el patrón MVVM es que la vista no contiene ningún dato, solo sabe cómo mostrar su modelo. Todos los datos deben estar en el modelo. Esto permite que tanto la vista como el modelo sean utilizados por cualquier dato. – Tyrsius