icon hasdatepicker example ejemplos calendarios jquery-ui knockout.js

jquery-ui - hasdatepicker - jquery datepicker



Usar js knockout con controles deslizantes jquery ui (4)

Estoy tratando de averiguar si el knockout js funcionaría bien para el siguiente problema:

Tengo varios controles deslizantes que quiero vincular a cuadros de texto.

Cuando se cambia el cuadro de texto, el control deslizante correspondiente debe actualizarse al nuevo valor y viceversa.

Al cambiar el valor del control deslizante o el cuadro de texto, se debe invocar una función que utiliza la entrada de todos los cuadros de texto para calcular un resultado.

Tengo mi solución jQuery rápida y sucia aquí .

¿Sería fácil lograr el mismo resultado de una manera más elegante usando knockout js?

Supongo que necesitaría crear un controlador de enlace personalizado como está hecho en jQuery UI datepicker change event no detectado por KnockoutJS


Aquí hay un ejemplo: http://jsfiddle.net/jearles/Dt7Ka/

Utilizo un enlace personalizado para integrar el control deslizante jquery-ui y uso Knockout para capturar las entradas y calcular la cantidad neta.

-

UI

<h2>Slider Demo</h2> Savings: <input data-bind="value: savings, valueUpdate: ''afterkeydown''" /> <div style="margin: 10px" data-bind="slider: savings, sliderOptions: {min: 0, max: 100, range: ''min'', step: 1}"></div> Spent: <input data-bind="value: spent, valueUpdate: ''afterkeydown''" /> <div style="margin: 10px" data-bind="slider: spent, sliderOptions: {min: 0, max: 100, range: ''min'', step: 1}"></div> Net: <span data-bind="text: net"></span>

Ver modelo

ko.bindingHandlers.slider = { init: function (element, valueAccessor, allBindingsAccessor) { var options = allBindingsAccessor().sliderOptions || {}; $(element).slider(options); ko.utils.registerEventHandler(element, "slidechange", function (event, ui) { var observable = valueAccessor(); observable(ui.value); }); ko.utils.domNodeDisposal.addDisposeCallback(element, function () { $(element).slider("destroy"); }); ko.utils.registerEventHandler(element, "slide", function (event, ui) { var observable = valueAccessor(); observable(ui.value); }); }, update: function (element, valueAccessor) { var value = ko.utils.unwrapObservable(valueAccessor()); if (isNaN(value)) value = 0; $(element).slider("value", value); } }; var ViewModel = function() { var self = this; self.savings = ko.observable(10); self.spent = ko.observable(5); self.net = ko.computed(function() { return self.savings() - self.spent(); }); } ko.applyBindings(new ViewModel());


@John Earles y @Michael Kire Hansen: ¡gracias por sus maravillosas soluciones!

Usé el código avanzado de Michael Kire Hansen. Ate la opción "max:" del control deslizante a un ko.observable y resultó que el control deslizante no actualiza correctamente el valor en este caso. Ejemplo: Digamos que el control deslizante está en el valor 25 de máximo 25 y cambia el valor máximo a 100, el control deslizante permanece en la posición más correcta, indicando que está en el valor máximo (pero el valor sigue siendo 25, no 100). Tan pronto como deslice un punto hacia la izquierda, obtendrá el valor actualizado a 99.

Solución: en la parte "actualizar:" simplemente cambie las últimas dos líneas a:

$(element).slider("option", allBindingsAccessor().sliderOptions); $(element).slider("value", value);

Esto cambia las opciones primero, luego el valor y funciona como un amuleto.


Sé que es hace algunos días pero hice algunos ajustes al código de John Earles:

ko.bindingHandlers.slider = { init: function (element, valueAccessor, allBindingsAccessor) { var options = allBindingsAccessor().sliderOptions || {}; $(element).slider(options); ko.utils.registerEventHandler(element, "slidechange", function (event, ui) { var observable = valueAccessor(); observable(ui.value); }); ko.utils.domNodeDisposal.addDisposeCallback(element, function () { $(element).slider("destroy"); }); ko.utils.registerEventHandler(element, "slide", function (event, ui) { var observable = valueAccessor(); observable(ui.value); }); }, update: function (element, valueAccessor, allBindingsAccessor) { var value = ko.utils.unwrapObservable(valueAccessor()); if (isNaN(value)) value = 0; $(element).slider("option", allBindingsAccessor().sliderOptions); $(element).slider("value", value); } };

La razón de esto es que si usa opciones que cambian (fx otra observable), entonces no afectará el control deslizante aunque lo desee.


Muchas gracias por la ayuda, necesitaba usar un control deslizante de rango en mi escenario, así que aquí hay una extensión de @John Earles y @Michael Kire Hansen

ko.bindingHandlers.sliderRange = { init: function (element, valueAccessor, allBindingsAccessor) { var options = allBindingsAccessor().sliderOptions || {}; $(element).slider(options); ko.utils.registerEventHandler(element, "slidechange", function (event, ui) { var observable = valueAccessor(); observable.Min(ui.values[0]); observable.Max(ui.values[1]); }); ko.utils.domNodeDisposal.addDisposeCallback(element, function () { $(element).slider("destroy"); }); ko.utils.registerEventHandler(element, "slide", function (event, ui) { var observable = valueAccessor(); observable.Min(ui.values[0]); observable.Max(ui.values[1]); }); }, update: function (element, valueAccessor, allBindingsAccessor) { var value = ko.utils.unwrapObservable(valueAccessor()); if (isNaN(value.Min())) value.Min(0); if (isNaN(value.Max())) value.Max(0); $(element).slider("option", allBindingsAccessor().sliderOptions); $(element).slider("values", 0, value.Min()); $(element).slider("values", 1, value.Max()); } };

y luego el HTML para acompañarlo

<div id="slider-range" data-bind="sliderRange: { Min: 0, Max: 100 }, sliderOptions: { range: true, min: 0, max: 100, step: 10, values: [0, 100] }"></div>