[javascript] VueJS conditionally add an attribute for an element

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?

This question is related to javascript vue.js vuejs2

The answer is


In html use

<input :required="condition" />

And define in data property like

data () {
   return {
      condition: false
   }
}

Simplest form:

<input :required="test">   // if true
<input :required="!test">  // if false
<input :required="!!test"> // test ? true : false

Try:

<input :required="test ? true : false">

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>

<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">


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.


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 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.


Examples related to javascript

need to add a class to an element How to make a variable accessible outside a function? Hide Signs that Meteor.js was Used How to create a showdown.js markdown extension Please help me convert this script to a simple image slider Highlight Anchor Links when user manually scrolls? Summing radio input values How to execute an action before close metro app WinJS javascript, for loop defines a dynamic variable name Getting all files in directory with ajax

Examples related to vue.js

How to fix 'Unchecked runtime.lastError: The message port closed before a response was received' chrome issue? Center content vertically on Vuetify Vue.js get selected option on @change Using Environment Variables with Vue.js did you register the component correctly? For recursive components, make sure to provide the "name" option Vue 'export default' vs 'new Vue' How can I go back/route-back on vue-router? Change the default base url for axios How to reference static assets within vue javascript How to change port number in vue-cli project

Examples related to vuejs2

How can I go back/route-back on vue-router? Change the default base url for axios How to change port number in vue-cli project How to solve 'Redirect has been blocked by CORS policy: No 'Access-Control-Allow-Origin' header'? vuetify center items into v-flex Vuejs: Event on route change Vuex - Computed property "name" was assigned to but it has no setter Vuex - passing multiple parameters to mutation How to listen to the window scroll event in a VueJS component? How to acces external json file objects in vue.js app