Comments (13)
这种情况确实存在,因为vue会通过hasChanged
函数判断新旧两个值是否相同来决定是否执行trigger
,但由于你事先将input
元素的值发生了修改,然后将修改后的值传递给ref
,导致hasChanged
函数判断为false
,所以dom
无法及时更新,如果你确实需要对input
的value
属性做出修改后再传递给ref
,那么请你对updateText
函数作出这样的修改:
const updateText = (e) => {
const value = e.target.value;
text.value = value;
text.value = text.value.toLowerCase();
};
先将input
元素的原始值传递给ref
,让hasChanged
函数判断为true
,这样vue就会把effect
放入执行队列中,然后再将text.value
的值修改为你想要的值,这样就可以正确的响应式。且由于vue对effect
做了去重处理,所以你不必担心dom
更新两次。
希望对你有些帮助。
from core.
@NathanAP 由于您给的信息较少,我按照你的言论所述无法复刻你当时的环境,如果可以的话,请给出完整示例。vue.js版本号3.4.19
from core.
I can't reproduce the behavior of the video in the linked playground on either Chrome, Safari or Firefox.
Please provide more detail and a reproduction that acutally reproduces the issue. also test your reproduction in different browsers, with extensions disabled etc.
from core.
I can't reproduce the behavior of the video in the linked playground on either Chrome, Safari or Firefox.
Please provide more detail and a reproduction that acutally reproduces the issue. also test your reproduction in different browsers, with extensions disabled etc.
It can be reproduced when change the value of the input from aaa
to aaA
. Because the text.value
is both aaa
((hasChanged(value, oldValue) === false
), so it won't execute trigger
.
from core.
- Type
aaaaa
into the input field. - Select the middle
a
(using the Shift key or the mouse) and replace it with an uppercaseA
. Observe that the input field showsaaAaa
, but the ref variable does not update. - Now, replace an
a
with a different letter, likeB
, and notice both the displayed value and the ref variable value change accordingly.
from core.
@zh-lx So, it turns out that if I want to reliably synchronize a ref variable with an input, I should always use v-model
with @input
and never rely on :value
? Otherwise, discrepancies between the reactive variable and the input's internal value might occur.
from core.
It appears that the source of truth for an <input>
with the :value
prop and @input
handler becomes not the prop itself, but the user's input. Is this architecture intentional and considered desirable behavior?
It seems that developers must "catch up" with the new value, as noted by @YiMo1, through double assignment. This looks odd. For instance, in React (sorry), achieving the same goals does not require extra manipulation:
const [text, setText] = React.useState('');
const handleSetText = (e) => {
const value = e.target.value;
if (/^[a-z]*$/.test(value)) setText(value);
};
<input value={text} onChange={handleSetText} />
My question: Is the current approach in Vue considered optimal for handling user input, and are there plans to simplify this aspect to make the behavior more intuitive?
P.S. Here is also a real-life example illustrating the consequences of non-obvious behavior, which leads to different solutions, like this one:
<input v-model="model" @keydown="onKeydown" />
const onKeydown = (e: KeyboardEvent) => {
if (
regexpPattern.value &&
!regexpPattern.value.test(e.key)
// and many other extra keydown checks
) {
e.preventDefault();
}
};
Here, I omitted the logic with handling the Backspace key, cutting through Cmd+X/Ctrl+X, but it also needs to be additionally described.
All of this could be avoided if the <input>
simply looked at the value from the :value
prop, and user input did not affect anything other than sending input
events and others.
Perhaps there is a more elegant solution; I would appreciate a tip!
from core.
This is expected behavior IMO, as when you are assigning text.value = value.toLowerCase()
, the old text.value
and the new text.value
is exactly the same. To Vue this means nothing has changed state-wise, so no updates will happen.
Avoiding updates when no state change has happened is fundamental to performance, so this is not something that can or will be changed.
You can use either the workaround by @YiMo1 or use v-model
with a watcher.
from core.
Appreciating the prompt response, @yyx990803.
Noting a nuance: the <input>
in Vue appears to favor user input over the :value
prop. Wondering if this is intentional and if there's a thought about bringing it in line with the prop's role as the main source? This seems to be a central quirk in the issue.
from core.
The central issue here is that there is no update is happening because no reactive state has changed.
from core.
Not sure if this fits here, but I have a situation here:
My list is a defineModel
and is being updated by list.value.push(new Item({ ... })
but it won't update on my others components
This image represents the list result:
This image is console.log(list.value.length)
right when I update it:
edit:
This is my structure:
- Main with
const list = ref([])
; - Component 1 created in Main with
const list = defineModel('list')
and further in I havelist.value = response.data
- Component 2 created in Main with
const list = defineModel('list')
and further in I havelist.value.push(new Item({ ... })
A watch in main component triggers both changes, but I cannot see it change in the screen.
from core.
@NathanAP 由于您给的信息较少,我按照你的言论所述无法复刻你当时的环境,如果可以的话,请给出完整示例。vue.js版本号3.4.19
I ended up doing it with Pinia yesterday because I would need to do it anyway 🙃
Anyway, I believe that might be something else I was doing wrong in my logic to make it not update my screen data. I'll edit and mark my comment as not relevant for the discussion.
from core.
I stumbled upon this RFC that might shed some light on the discussion about input behavior in Vue, particularly regarding the concept of input's props as properties or like attributes. It resonates deeply with the issues we're encountering here, especially when it comes to the one-way data flow and the role of props as the source of truth.
from core.
Related Issues (20)
- bug:子组件传参如果是个函数返回的对象,在父组件回调函数中对ref/reactive声明的变量赋值,如果该变量也在模版中使用,则会导致子组件所有接收的props每次都被重置 HOT 2
- Vue TSC & computed-refs HOT 3
- using symbol as a prop type throw error HOT 3
- Inconsistent behaviour in `Transition` component and lifecycle hooks like `onBeforeUnmount` and `onUnmounted` HOT 1
- toggle event throws error on details element HOT 1
- Radio input element's checked value not synced with props checked. HOT 2
- When using vue3, main.js automatically adds printing appz
- When using vue3, when main.js is running, the automatic addition of printing appz appears. HOT 1
- jsx 三元运算非预期 HOT 2
- vue webcomponent 里使用vue组件,组件内部样式丢失 HOT 3
- Failed to resolve import source when using PNPM
- scoped css [data="xyz"] is applied to wrong element HOT 2
- watchEffect 没触发 HOT 2
- Unintentional $event value setting on customized event HOT 2
- Blank screen when scaffolding project with ts (related to Vue Router) HOT 1
- Custom elements not able to associate with form
- Cannot determine prop from mapped type
- vue-component-meta: Invalid component prop types when using options api + a prop with a default function HOT 2
- Computed re render is inconsistent. HOT 2
- `watch` a ref props object not take effect HOT 2
Recommend Projects
-
React
A declarative, efficient, and flexible JavaScript library for building user interfaces.
-
Vue.js
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
-
Typescript
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
-
TensorFlow
An Open Source Machine Learning Framework for Everyone
-
Django
The Web framework for perfectionists with deadlines.
-
Laravel
A PHP framework for web artisans
-
D3
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
-
Recommend Topics
-
javascript
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
-
web
Some thing interesting about web. New door for the world.
-
server
A server is a program made to process requests and deliver data to clients.
-
Machine learning
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
-
Visualization
Some thing interesting about visualization, use data art
-
Game
Some thing interesting about game, make everyone happy.
Recommend Org
-
Facebook
We are working to build community through open source technology. NB: members must have two-factor auth.
-
Microsoft
Open source projects and samples from Microsoft.
-
Google
Google ❤️ Open Source for everyone.
-
Alibaba
Alibaba Open Source for everyone
-
D3
Data-Driven Documents codes.
-
Tencent
China tencent open source team.
from core.