Search code examples
javascriptdrop-down-menusvelteshuffle

Svelte - How can I randomly shuffle my select options with a button?


I am trying to create a button that would shuffle the options of my select dropdown elements, with Svelte.

The idea, in the end, would be to have several list of dropdown menus, and to let user choose which one they want to fill manually, and which one they just want to shuffle without intervening.

So far I've got this, that doesn't work:

<script>
    let chifumi_1 = [
        { id: 1, text: 'Paper' },
        { id: 2, text: 'Rock' },
        { id: 3, text: 'Scissor' }
    ];
    let chifumi_2 = [
        { id: 1, text: `Paper` },
        { id: 2, text: `Rock` },
        { id: 3, text: `Scissor` }
    ];
    let chifumi_3 = [
        { id: 1, text: `Paper` },
        { id: 2, text: `Rock` },
        { id: 3, text: `Scissor` }
    ];

    function shuffle(a) {
    var j, x, i;
    for (i = a.length - 1; i > 0; i--) {
        j = Math.floor(Math.random() * (i + 1));
        x = a[i];
        a[i] = a[j];
        a[j] = x;
    }
    return a;
    }
</script>

<form class="pl-2">
    <select bind:value={chifumi_1}>
        {#each chifumi_1 as chifumi_1}
        <option value={chifumi_1}>
            {chifumi_1.text}
        </option>
        {/each}
    </select>
    <select bind:value={chifumi_2}>
        {#each chifumi_2 as chifumi_2}
        <option value={chifumi_2}>
            {chifumi_2.text}
        </option>
        {/each}
    </select>
    <select bind:value={chifumi_3}>
        {#each chifumi_3 as chifumi_3}
        <option value={chifumi_3}>
            {chifumi_3.text}
        </option>
        {/each}
    </select>
</form>

<button 
    style="border: 1px solid;"
    on:click={shuffle(chifumi_1)}
    on:click={shuffle(chifumi_2)}
    on:click={shuffle(chifumi_3)}>
        Chifumi Randomizer
</button>

For the shuffle function, I used the first answer of this query

Can anyone help me, please?


Solution

  • You lose reactivity because you modify an object without using an assignment. The function already returns the array again, so you could probably fix this by adding an assignment in the handler:

    on:click={() => chifumi_1 = shuffle(chifumi_1)}