2.4.2
https://jsbin.com/qejofexedo/edit?html , js, output
veja o link de reprodução.
Quando eu clico em Expand is True
, então expand
para se tornar false
. E apenas countA
mudou.
Quando clico em Expand is Ture
, nada aconteceu.
countA
e countB
mudaram.
Acho que quando eu clico, expand
mudou para false
, mas imediatamente o evento de clique foi acionado. Ele executa outro evento de clique do vnode. Em seguida, a expansão mudou para true
.
p
, section
, nenhum erro ocorrerá.i
para a tag pai div
no primeiro div, nenhum erro ocorrerá
parece normal
Sua reprodução está funcionando conforme o esperado ...
@Kingwl @ yyx990803 Desculpe por isso. Eu testei outros casos e esqueci de mudar de volta.
O código importante é
<div class="header" v-if="expand"> // block 1
<i @click="expand = false, countA++">Expand is True</i> // element 1
</div>
<div class="expand" v-if="!expand" @click="expand = true, countB++"> // block 2
<i>Expand is False</i> // element 2
</div>
Existem quatro casos:
block 1
e block2
, funciona bemelement 1
e element 2
, funciona bemblock 1
e element 2
, altere expand
para verdadeiro está ok. Mas não pode mudar de volta.element 1
e block 2
, não pode alterar expand
para falso. Mas pode alterar expand
para verdadeiro.Então, isso acontece porque:
<i>
dispara, acionando uma primeira atualização em nextTick (microtarefa)Isso é bastante complicado na correção, e outras libs que utilizam microtarefas para enfileiramento de atualizações também apresentam esse problema (por exemplo, Preact). O React não parece ter esse problema porque usa um sistema de eventos sintético (provavelmente devido a casos extremos como este).
Para contornar isso, você pode simplesmente dar às duas divs externas chaves diferentes para forçá-las a serem substituídas durante as atualizações. Isso evitaria que o evento bubbled fosse captado:
<div class="header" v-if="expand" key="1"> // block 1
<i @click="expand = false, countA++">Expand is True</i> // element 1
</div>
<div class="expand" v-if="!expand" @click="expand = true, countB++" key="2"> // block 2
<i>Expand is False</i> // element 2
</div>
Comentários muito úteis
Então, isso acontece porque:
<i>
dispara, acionando uma primeira atualização em nextTick (microtarefa)Isso é bastante complicado na correção, e outras libs que utilizam microtarefas para enfileiramento de atualizações também apresentam esse problema (por exemplo, Preact). O React não parece ter esse problema porque usa um sistema de eventos sintético (provavelmente devido a casos extremos como este).
Para contornar isso, você pode simplesmente dar às duas divs externas chaves diferentes para forçá-las a serem substituídas durante as atualizações. Isso evitaria que o evento bubbled fosse captado: