Search code examples
javascriptknockout.jsradio-buttonwizardknockout-templating

How do I get the value of radio button option in my Knockout.js wizard?


To simplify things, here is the fiddle: http://jsfiddle.net/FyuSD/157/

<script id="choiceTmpl" type="text/html">
            <label><input type="radio" value="boughtBefore" data-bind="checked: radioSelectedOptionValue" />Purchase products I have bought before</label>
            <br />
            <label><input type="radio" value="searchProduct" data-bind="checked: radioSelectedOptionValue" />Search for a product I haven't purchased before</label>
            <br />

I guess I have a couple questions. I am building a wizard and need different execution steps depending on which option the user selects. The question I want to know is, how do I get the value of radio button that they select?

Like on step two, if they select "purchase products I have bought before" how can I redirect it to another question: create order from guide or create order from previous order (using radio buttons again)?

I can't figure out how to get the value of what they select. Furthermore, how would I skip steps depending on the option they choose? (fore example, go from step 2 to step 4 if they select "want to search for a product" in step 2)

Lastly, is there an easy way to change the radio-button text to match the questions without create a new template for each?

Sorry if this is too many questions, and thanks for the help...


Solution

    1. The value of the radio button they check is passed to the function (typically an observable, setting its value) by the checked binding. See the radio example in the documentation.
    2. Set up a computed as a state machine, and then have its value determine which wizard page is visible.
    3. Label text could also be bound to model properties, but I didn't do that in my example.

    I've written a simplistic example Fiddle: http://jsfiddle.net/rqt46qw1/ Note that although my example uses only the radio selection to determine the page to show, your computed can involve as many variables as you need it to.

    <div data-bind="visible:wizPage() == '1'">
        <h1>Welcome</h1>
        <label>Page 2</label><input type="radio" value="p2" data-bind="checked:radioSelected" />
        <label>Page 3</label><input type="radio" value="p3" data-bind="checked:radioSelected" />
    </div>
    <div data-bind="visible:wizPage() == '2'">
        <h1>Some Option</h1>
        <label>Page 3</label><input type="radio" value="p3" data-bind="checked:radioSelected" />
        <label>Start Over</label><input type="radio" value="p1" data-bind="checked:radioSelected" />
    </div>
    <div data-bind="visible:wizPage() == '3'">
        <h1>Another Option</h1>
        <label>Page 2</label><input type="radio" value="p2" data-bind="checked:radioSelected" />
        <label>Start Over</label><input type="radio" value="p1" data-bind="checked:radioSelected" />
    </div>
    

    Javascript:

    var viewModel = (function () {
        var radioSelected = ko.observable();
        var wizPage = ko.computed(function () {
            if (radioSelected() == 'p2') {
                return '2';
            }
            else if (radioSelected() == 'p3') {
                return '3';
            }
            else {
                return '1';
            }
        });
        return {
            wizPage: wizPage,
            radioSelected:radioSelected
        };
    }());
    
    console.debug("ViewModel:", viewModel);
    ko.applyBindings(viewModel);