In VueJS we can add or remove a DOM element using v-if:
<button v-if="isRequired">Important Button</button>
but is there a way to add / remove attributes of a dom element eg for the following conditionally set the required attribute:
Username: <input type="text" name="username" required>
by something similar to:
Username: <input type="text" name="username" v-if="name.required" required>
Any ideas?
null
, undefined
, or false
”, which is different from a JS script evaluating to false. This means an empty string is falsy in JavaScript, but would still add the attribute to DOM. To prevent that you could try v-bind:name="name || false"
false
to child component via a prop? 'false'
. In other cases when you need to control presence of non-boolean html attribute on the element you can use conditional rendering with v-if
as suggested here: github.com/vuejs/vue/issues/7552#issuecomment-361395234 attribute
but NOT prop
. We can safely pass explicit false
via a component property but NOT attribute (which is not recognised as a property). Am I correct? <input :required="condition">
You don't need <input :required="test ? true : false">
because if test is truthy you'll already get the required
attribute, and if test is falsy you won't get the attribute. The true : false
part is redundant, much like this...
if (condition) {
return true;
} else {
return false;
}
// or this...
return condition ? true : false;
// can *always* be replaced by...
return (condition); // parentheses generally not needed
The simplest way of doing this binding, then, is <input :required="condition">
Only if the test (or condition) can be misinterpreted would you need to do something else; in that case Syed's use of !!
does the trick.
<input :required="!!condition">
use v-bind
v-bind="{ ...(type && { variant: type })
Simplest form:
<input :required="test"> // if true
<input :required="!test"> // if false
<input :required="!!test"> // test ? true : false
String
value that by setting it to false
you will get type check
error. So set it to undefined
instead of false. docs !!
I've never seen that syntax before yesterday and during a code review I came across this: -- <input :required="!!!recipe.checked" v-model="recipe.pieType"><select :required="!!!recipe.checked" v-model="recipe.ingredients" :options="ingredients"></select>
Would you know what !!!
(3) mean for a :required
value? Thanks. It's notable to understand that if you'd like to conditionally add attributes you can also add a dynamic declaration:
<input v-bind="attrs" />
where attrs is declared as an object:
data() {
return {
attrs: {
required: true,
type: "text"
}
}
}
Which will result in:
<input required type="text"/>
Ideal in cases with multiple attributes.
Conditional rendering of attributes changed in Vue 3. To omit an attribute use null
or undefined
.
Vue 2:
<div :attr="false">
Result: <div>
<div :attr="null">
Result: <div>
Vue 3:
<div :attr="false">
Result: <div attr="false">
<div :attr="null">
Result: <div>
Try:
<input :required="test ? true : false">
Update: It has changed in Vue 3, see this answer https://stackoverflow.com/a/64598898
<input v-bind:required="test ? true : false">
anythingAtAll : ? true : false
(or if (condition) { return true; } else { return false; }
) in any language is ... unseemly. Just use return (condition)
or, in this case, <input :required="test">
test
is boolean
, you can just use :required="test"
String
value that by setting it to false
you will get type check
error. So set it to undefined
instead of false. docs :required="required"
where required
is a Boolean component property results in <el required="required"> for me <el required>
required="required"
in your markup is completely normal and standard. You can test this by creating a sample HTML file with a simple required
attribute. Your browser will fill up the blanks by itself. <input :required="test === 'somestring'">
You can pass boolean
by coercing it, put !!
before the variable.
let isRequired = '' || null || undefined
<input :required="!!isRequired"> // it will coerce value to respective boolean
But I would like to pull your attention for the following case where the receiving component has defined type
for props. In that case, if isRequired
has defined type to be string
then passing boolean
make it type check fails and you will get Vue warning. To fix that you may want to avoid passing that prop, so just put undefined
fallback and the prop will not sent to component
let isValue = false
<any-component
:my-prop="isValue ? 'Hey I am when the value exist' : undefined"
/>
Explanation
I have been through the same problem, and tried above solutions !!
Yes, I don't see the prop
but that actually does not fulfils what required here.
My problem -
let isValid = false
<any-component
:my-prop="isValue ? 'Hey I am when the value exist': false"
/>
In the above case, what I expected is not having my-prop
get passed to the child component - <any-conponent/>
I don't see the prop
in DOM
but In my <any-component/>
component, an error pops out of prop type check failure. As in the child component, I am expecting my-prop
to be a String
but it is boolean
.
myProp : {
type: String,
required: false,
default: ''
}
Which means that child component did receive the prop even if it is false
. Tweak here is to let the child component to take the default-value
and also skip the check. Passed undefined
works though!
<any-component
:my-prop="isValue ? 'Hey I am when the value exist' : undefined"
/>
This works and my child prop is having the default value.
You can use computed too
<input :required="isRequired" />
Computed:
computed: {
isRequired () {
return someLogic //Boolean, true or false
}
You can add colon before attribute (also can use conditions) like
<div :class="current? 'active': '' " >
<button :disabled="InvalidForm? true : false " >
If you want to set a dynamic value like props then you also can use colon before attribute name like :
<Child :data="userList" />
You could write something like this:
<input type="text" name="username" :required="condition ? true : false">
In html use
<input :required="condition" />
And define in data property like
data () {
return {
condition: false
}
}