Closed JosephSilber closed 9 years ago
It was briefly mentioned in the guide but I think two-way filters are what you're looking for: http://vuejs.org/guide/custom-filter.html#Two-way_Filters
They're not exactly the same thing: http://jsfiddle.net/6jjuoypf/
The two-way filters don't allow you to type anything you want into the input. Unless you use lazy
, which is not what I want in this context.
Play with that fiddle. It's messed up on so many fronts:
$0.00
, since it keeps on formatting it.$294.32
. Hitting backspace once will change it to $294.30
. From there you can press backspace as many times as you want, but nothing will change.Maybe all this can be fixed by only triggering the "read" lazily?
Well, they are the same thing, it's just formatting user input is itself a very tricky thing. I don't think you'd get what you expect with Angular formatters/parsers either.
Think about what you are trying to do: it's impossible to have a 1:1 transform relationship between the user input value and the underlying model value: both $123.
and $123.00
gets converted to the same number, there's no way to know what text we should format 123
back into.
So yeah, what we actually want is "persist as the user types, but format only when the user blurs". Two-way filters are not created for this use case. Or, more generally, two-way binding just doesn't make sense in this case. You have to have two separate piece of state to store the underlying value and the display value, and handle input
and blur
events separately: http://jsfiddle.net/yyx990803/6jjuoypf/1/
Closing because formatters/parsers won't solve this issue.
@yyx990803 formatters in angular are only invoked if the model changes through a source other than the form element. This prevents all the issues outlined above.
See this example: http://jsfiddle.net/3yn8hoyp/
If you type 3.5
into the input field, it'll stay that way. But if you set the value through the button, the input field will be set to $3.50
.
Now, they don't call the formatter on blur - which I think they should - but that's a different point. The most important thing is that the formatters are not called as you type!
@JosephSilber ah, that makes sense. This would make two-way filters easier to use.
@yyx990803 I'm not sure I understand you. Are you saying you think it'll be a good idea to have this be the default behavior for two-way filters? And if so, what do you think of calling the "read" on blur?
@JosephSilber yes, the current two-way filter behavior is confusing and hard to use. I think the angular formatter behavior simplifies the issue. We just need to prevent triggering model->view updates when the user is typing.
Can you please re-open this issue then?
Beautiful! Thank you so very much!
:sunglasses:
How to do that in vuejs 2.0? The possibility to use an object as filter with read and write functions does not work anymore
to me it didnt work , when I try to use filter inside the input it gives an error . It dont aloud me to use a filter like this v-model="price | currency" like in this example - https://vuejs.org/v2/guide/migration.html#Two-Way-Filters-replaced
I am using vue - 2.1.8 , does some one knows whats is wrong ?
Is there any way to accomplish in Vue what Formatters and Parsers do in Angular?
If not, would that be a reasonable request?
For a single value you could maybe use a computed property, but that's a single non-reusable transformation. If you want to run the value through a pipeline, well... you can't.
Also, if your value is in a
v-repeat
, you can't use a computed property anymore; you'll have to create a component for your repeater...None of that is ideal.
Here's my current use-case: I'm trying to convert this simple online invoice creator from jQuery-spaghetti to Vue. As you can see, the values in the input elements are/should all be formatted as currency, but the underlying model value has to be a number so that you can run your math on them.