苗条、奇怪的反应性问题

时间:2021-06-20 10:48:43

标签: svelte

提供代码,这将有助于在 Svelte REPL 上重新创建我的问题。

<script>
    import { onMount } from "svelte";
    import { object_without_properties } from "svelte/internal";
    import { writable } from "svelte/store";

    class MyClass {}

    var myObjects = writable(null);
    let myObj1, myObj2, myObj3;
    onMount(async () => {
        $myObjects = [];
        var o1 = {
            myId: 1,
            myString: "String 1",
        };
        $myObjects = [...$myObjects, o1];
        var o2 = {
            myId: 2,
            myString: "String 2",
        };
        $myObjects = [...$myObjects, o2];
        var o3 = {
            myId: 3,
            myString: "String 3",
        };
        $myObjects = [...$myObjects, o3];
        myObj1 = $myObjects[0];
        myObj2 = $myObjects[1];
        myObj3 = $myObjects[2];
    });
    function dummy() {
        $myObjects = $myObjects;
    }
</script>

{#if $myObjects}
    <b>1. Values via myObj1, myObj2 and myObj3</b><br />
    <input type="text" bind:value={myObj1.myString} />
    <input type="text" bind:value={myObj2.myString} />
    <input type="text" bind:value={myObj3.myString} /><br />
    - NOTE! This doesn't get updated when you update the first items in below list. And vice versa.
    <br />
    Update above value and then click <button on:click={dummy}>dummyreset</button>! Then the values below
    are updated below. However, if you update the values below, the values above are <b>not</b> updated.
    <hr />
    <b>2. All values via each</b><br />
    {#each $myObjects as o}
        <input type="text" bind:value={o.myString} />
    {/each}
    <hr />
    <b>3. All values via three hard-coded inputs</b><br />
    <input type="text" bind:value={$myObjects[0].myString} />
    <input type="text" bind:value={$myObjects[1].myString} />
    <input type="text" bind:value={$myObjects[2].myString} />
{/if}

在我的实际应用程序(使用 Typescript)中,我有一个不同的场景,但我认为这可以解决问题。

我有一个包含三个项目的列表 ($myObjects)(每个项目都是一个带有 myId 和 myString 的对象)。我分配 input-text 来操作每个对象中的 myString 属性。

我创建了三种不同的方法来做到这一点:

  1. 通过三个专门创建的对象(myObj1、myObj2 和 myObj3),基本上就是 myObj1 = $myObjects[0] 等等。
  2. 通过使用 {#each} 循环遍历所有项目
  3. 通过 $myObjects[0]、$myObjects[1] 和 $myObjects[2] 对三个输入进行硬编码

查看 2 和 3 - 一切都按预期工作。如果我在第 2 行更改一个值,相应的值会立即在第 3 行更新 - 反之亦然。

然而,第一行永远不会更新。如果我更新第 1 行的值,然后单击虚拟按钮,我基本上会强制更新 2 和 3 列表,然后它就可以工作了。但并非如预期的那样。

另外,可以提到的是,如果我使用商店或只是普通实例,它没有任何区别。这是同样的问题。

有谁知道为什么 Svelte 会这样?我怎样才能让它按我的意愿工作?

0 个答案:

没有答案