Convert string to boolean for checkbox - javascript

I use v-model to display checked/unchecked checkboxes:
<template v-for="(item, index) in myFields">
<v-checkbox
v-model="myArray[item.code]"
:label="item.name"
/>
</template>
It works fine when I get true or false values from API. But now I get strings: "true" or "false" and my checkbox is always checked.
If I change the code on:
v-model="Boolean(myArray[item.code])"
I got the error:
'v-model' directives require the attribute value which is valid as LHS
How can I solve this problem?

Trying Boolean(myArray[item.code]) won’t work anyway because the string 'false' is true. So Boolean('false') return true.
Instead you should do myArray[item.code] !== 'false'
'false' will return false and every other string than false will return true
EDIT: You need to change myArray to an array of boolean like so
myArray.map((element) => element !== 'false')
Then this code will work
<template v-for="(item, index) in myFields">
<v-checkbox
v-model="myArray[item.code]"
:label="item.name"
/>
</template>

Related

null value in dynamic v-for with functional template refs

Situation
I am building a custom filtering component. This allows the user to apply n filters that are displayed with a v-for in the template. The user can update any value in the input fields or remove any of the filters afterwards.
Problem
After removing one of the filters, my array itemRefs got a null value as the last item.
Code (simplified)
<script setup>
const filtersScope = $ref([])
const itemRefs = $ref([])
function addFilter () {
filtersScope.push({ value: '' })
}
function removeFilter (idx) {
filtersScope.splice(idx, 1)
itemRefs.pop() // <- necessary? has no effect
// validate and emit stuff
console.log(itemRefs)
// itemRefs got at least one null item
// itemRefs = [null]
}
// assign the values from the input fields to work with it later on
function updateValue() {
itemRefs.forEach((input, idx) => filtersScope[idx].value = input.value)
}
</script>
<template>
<div v-for="(filter, idx) in filtersScope" :key="filter.id">
<input
type="text"
#keyup="updateValue"
:ref="(input) => { itemRefs[idx] = input }"
:value="filter.value"
>
<button #click="removeFilter(idx)" v-text="'x'" />
</div>
<button #click="addFilter()" v-text="'add filter +'" />
</template>
>>> Working demo
to reproduce:
add two filters
itemRefs got now the template refs as a reference, like: [input, input]
remove one filter, itemRefs now looks: [input, null]
remove the last filter, itemRefs now looks like: [null]
Question
Without the itemRefs.pop() I got the following error, after removing and applying new filters:
Uncaught TypeError: input is null
With the pop() method I prevent a console error, but the null-value in itemRefs still remains.
How do I clean my template refs cleanly?
I don't know what's up with using $refs inside $refs but it's clearly not working as one would expect.
However, you should never need nested $refs. When mutating data, mutate the outer $refs. Use $computed to get a simplified/focused angle/slice of that data.
Here's a working example.
<script setup>
const filtersScope = $ref([])
const values = $computed(() => filtersScope.map(e => e.value))
function addFilter() {
filtersScope.push({ value: '' })
}
function removeFilter(idx) {
filtersScope.splice(idx, 1);
console.log(values)
}
</script>
<template>
<div v-for="(filter, idx) in filtersScope" :key="idx">
<input type="text"
v-model="filtersScope[idx].value">
<button #click="removeFilter(idx)" v-text="'x'" />
</div>
<button #click="addFilter()" v-text="'add filter +'" />
</template>

Warning on render : Received `true` for a non-boolean attribute `className`

GEtting the following error for the div.container and span.text:
Warning: Received true for a non-boolean attribute className.
If you want to write it to the DOM, pass a string instead: className="true" or className={value.toString()}.
return (
Array.isArray(contactDetails) &&
contactDetails.map((item, index) => {
return item.type === DIVIDER ? (
<div key={index}>
<Divider variant={"middle"} className={classes.divider} />
<div className={classes.dividerText}>{item.text}</div>
</div>
) : (
item.text && (
<div className={classes.container} key={index}>
<div className={classes.icon}>{item.icon}</div>
<span className={classes.text}>{item.text}</span>
</div>
)
One of your classes-props is a boolean. You cannot push a boolean (true/false) to className.
You could console.log(classes), then you will see, which prop causes the warning.
It means at least one of the className values is boolean instead of string. we can not say anything more with this piece of code.
I got the same error when i didn't give a value to className attribute like below, probably one of your variable is null or boolean etc.
<img className src={...} .../>

Is there a way to pass vue model values into method function?

I recently started using Vue Js and I am stuck at this point where I cant pass vue model values to method function.
<div v-for="(post, index) in posts" :key="post.customerName">
<input type="text" v-model="post.customerName" /> /** successfully print customerName inside this field**/
<b-button block pill variant="outline-info" v-on:click="bookerName()">
{{post.customerName}}
</b-button>
</div>
Method Function
bookerName(){
console.log(this.post.customerName); /** prints out UNDEFINED **/
}
VUE data return
posts:{
customerName:{ 'David','John','Sam'},
},
bookerName: ''
Pass the index from v-for to the method, and get the value by index:
<b-button v-on:click="bookerName(index)">
...
bookerName (index){
console.log(this.posts[index])
}
Also, in your example you have bookerName: ''. Is it a property inside data()? If so, you cannot have method with the same name bookerName

Get Element from dynamic class name in Vue js

<v-data-table
:headers="menuheaders"
//this menus from api response
:items="menus"
item-key="usersmenu_menuid"
items-per-page="1000"
hide-default-footer=""
class="elevation-1"
>
<template v-slot:item.usersmenu_read="{ item }">
<v-checkbox :class="`read${item.usersmenu_read}`" :value="item.usersmenu_read === 1 ? true : false "></v-checkbox>
</template>
<template v-slot:item.usersmenu_edit="{ item }">
<v-checkbox :class="`edit${item.usersmenu_edit}`" :value="item.usersmenu_edit === 1 ? true : false "></v-checkbox>
</template>
<template v-slot:item.usersmenu_add="{ item }">
<v-checkbox :class="`add${item.usersmenu_add}`" :value="item.usersmenu_add === 1 ? true : false "></v-checkbox>
</template>
<template v-slot:item.usersmenu_delete="{ item }">
<v-checkbox :class="`delete${item.usersmenu_delete}`" :value="item.usersmenu_delete === 1 ? true : false "></v-checkbox>
</template>
</v-data-table>
Hi all, i have problem with this code, i want to getElementByClassName
let read = document.getElementsByClassName('read${usersmenu_read}')
But i dont know what i must fill in the flag.
let read = document.getElementsByClassName(In this flag, What should i fill ?)
Please give me some explanation. Thanks for you all
Did you try to use $refs in VueJS instead of using getElementsByClassName. Follow this: https://v2.vuejs.org/v2/api/#ref
<v-checkbox :class="`read${item.usersmenu_read}`" ref="readCheckbox" :value="item.usersmenu_read === 1 ? true : false "></v-checkbox>
// and use it in the component
this.$refs.readCheckbox
Update: for multiple checkbox
You can assign a ref to v-data-table instead directly in v-checkbox, and get all check box in DOM by use Vue $refs same above.
If you want to use getElementsByClass, you can give the checkboxes with a same name that not depend on menus data, say it's "menu-checkbox". Your checkbox will be:
<v-checkbox class="menu-checkbox" :class="`read${item.usersmenu_read}`" :value="item.usersmenu_read === 1 ? true : false "></v-checkbox>
// same for edit/add/delete
Now you can retrieve all checkboxes by:
document.getElementsByClassName('menu-checkbox')

Polymer 2.0 dom-if rendering template even though if condition is false

I am having trouble figuring out why my inner <dom-if" if="{{_isShowCategory(category.name)}}> template is rendering even though the condition is false. I print out the boolean result and the if condition correctly evaluates to false when category.name is 'account', but still, the template renders.
<dom-if if="[[_shouldRenderDrawer]]">
<template>
<!-- Two-way bind `drawerOpened` since app-drawer can update `opened` itself. -->
<app-drawer opened="{{drawerOpened}}" swipe-open tabindex="0">
<a name="account" href="/account">ACCOUNT</a>
<iron-selector role="navigation" class="drawer-list" selected="[[categoryName]]" attr-for-selected="name">
<dom-repeat items="[[categories]]" as="category" initial-count="4">
<!-- NOTE: I've also tried <dom-if if="{{_isShowCategory(category.name)}}> but I get the same result -->
<template is="dom-if" if="{{_isShowCategory(category.name)}}">
<span style="color:black">{{_isShowCategory(category.name)}}</span>
<a name="[[category.name]]" href="/[[category.name]]">[[category.title]]</a>
</template>
</dom-repeat>
</iron-selector>
</app-drawer>
</template>
</dom-if>
_isShowCategory(categoryName){
return !Boolean(categoryName === "account");
// I've also tried return !(categoryName==='account'), which returns the same result as the above
}
just change the IF statement in
return (categoryName !== "account");
The "!" symbol is the logical NOT operator, that means that whatever is true will became false and videversa, in your case is even trickier because you have:
IN THE CASE THE CONDITION IS TRUE
-- (categoryName === "account") = TRUE
-- -- Boolean(categoryName === "account") = TRUE
-- -- -- !Boolean(categoryName === "account") = FALSE, because of NOT symbol "!"
IN THE CASE THE CONDITION IS FALSE
-- (categoryName === "account") = FALSE
-- -- Boolean(categoryName === "account") = TRUE, because Boolean("anythingWithAValidValue") converts anything different then
null/undefined in TRUE otherwise FALSE
-- -- !Boolean(categoryName === "account") = FALSE, because of NOT symbol "!" as I mentioned before.
Btw this is not a Polymer Issue, please change the tag of your question, JS/JAVASCRIPT is more appropriated.

Categories

Resources