Vue JS Option element "selected" is only attribute, need it as property - javascript

Trying to get an option to be selected by default if selected is present on the option object
This is what i have:
<template>
<select v-model="model" :placeholder="placeholder">
<option v-for="option in options" :value="option.value" :selected="option.selected">{{option.label}}</option>
</select>
</template>
<script>
export default {
props: {
model: {
default: null
},
placeholder: {
default: null
},
options: {
default: null
}
}
};
</script>
This sets selected attribute correctly, i can see it in element explorer
This doesnt seem to work, since its only an attribute, if i check the element, the "selected" property on it is false!
How do i set selected property of the option element?

You just need to set the originally selected value to the value of the v-model, i.e.
new Vue({
el: '#app',
data: {
options: [
{
value: 'foo',
label: 'foo label',
},
{
value: 'bar',
label: 'bar label',
},
{
value: 'baz',
label: 'baz label',
},
],
selected: 'bar',
}
})
<script src="https://unpkg.com/vue/dist/vue.js"></script>
<div id="app">
<select v-model="selected">
<option v-for="option in options" :value="option.value">{{option.label}}</option>
</select>
</div>

Found the issue, the "data" property for my component was coming from somewhere else.
So i needed to find where it was coming from.

Related

How can I use multiple b-form-radio-group avoiding visual interference among them?

I'm new using Vue and specifically Bootstrap Vue and I'm trying to build a form with multiple radio groups.
My problem is that when I change the value in one of them the others don't change their values (this was checked with Vue DevTools) but visually it looks like none of the values are selected
I don't know what is wrong with my approach
I post here a simplified version of the code looking for some help, thanks in advance:
<template>
<div>
<b-form-group label="Radio group 1" v-slot="{ ariaDescribedby }">
<b-form-radio-group
id="radio-group-1"
v-model="selected1"
:options="options1"
:aria-describedby="ariaDescribedby"
name="radio-options"
></b-form-radio-group>
</b-form-group>
<b-form-group label="Radio Group 2" v-slot="{ ariaDescribedby }">
<b-form-radio-group
id="radio-group-2"
v-model="selected2"
:options="options2"
:aria-describedby="ariaDescribedby"
name="radio-options"
></b-form-radio-group>
</b-form-group>
</div>
</template>
<script>
export default {
data() {
return {
selected1: 'first',
options1: [
{ text: 'First', value: 'first' },
{ text: 'Second', value: 'second' },
],
selected2: 'one',
options2: [
{ text: 'One', value: 'one' },
{ text: 'Two', value: 'two' },
]
}
}
}
</script>
Since both <b-form-radio-group> elements have the same name, "radio-options", visually they are treated like one group. The different v-model would still function correctly but this isn't what you want visually. Give the second group a different name:
<b-form-radio-group
id="radio-group-2"
v-model="selected2"
:options="options2"
:aria-describedby="ariaDescribedby"
name="radio-options2"
></b-form-radio-group>
Here I changed it to radio-options2.

How to check if selected dynamic form input meets some criteria

I'm still relatively new to Angular and the logic of this nested JSON is getting the better of me, so I apologize.
I am looking to create a dynamic form and used this tutorial as a starting point.
I am trying to build out conditional fields that will only display if the user selects a certain option. I would like it to work so that if any of my options has children defined in an array, a subsequent input with those children as options appears. I still have a ton of things to consider, but right now I'm trying to get it so that when a user selects Option 2, Option 2A and Option 2B automatically appear in another dropdown underneath.
How can I create an ngIf* statement that says "if the currently selected option has children, add them to another input"?
Here is my code in a sandbox
I have tried checking that the array length of "children" is longer than zero, and also created a boolean called "hasChildren" and manually assigning a true/false value to check against (though I don't prefer this solution because the finished app will have many nested options and it would be easier to just check if the array is empty or not).
I also tried this solution but must have had a syntax error, because it didn't work for me.
HTML:
<ng-template [ngSwitchCase]="'select'">
<div class="form-group">
<label [for]="input.controlName"> {{input.controlName}}</label>
<select [formControlName]="input.controlName" [name]="input.controlName" [id]="input.controlName"
[required]="input.validators.required">
<option value="">{{input.placeholder}}</option>
<option *ngFor="let option of input.options" [value]="option.value">{{option.optionName}}</option>
</select>
</div>
<div *ngIf="this.input.options.children > 0" class="form-group">
<label [for]="input.options.optionName">{{input.options.optionName}}</label>
<select [formOptionName]="input.options.children.childName" [name]="input.options.children.childName" [id]="input.options.children.childName">
<option *ngFor="let children of input.options.children" [value]="children.value">{{children.childName}}</option>
</select>
</div>
</ng-template>
form-data.ts
export interface FormData {
controlName: string;
controlType: string;
valueType?: string;
currentValue?: string;
placeholder?: string;
options?: Array<{
optionName: string;
value: string;
hasChildren: boolean;
children: Array<{
childName: string;
childValue: string;
}>
}>;
validators?: {
required?: boolean;
minlength?: number;
maxlength?: number;
};
}
mock-form.ts
import { FormData } from './../interface/form-data';
export const MockForm: FormData[] = [
{
controlName: 'Options',
placeholder: 'Choose an option',
controlType: 'select',
options: [{
optionName: 'Option 1',
value: 'option 1',
hasChildren: false,
children: []
},
{
optionName: 'Option 2',
value: 'option 2',
hasChildren: true,
children: [{
childName: 'Option 2A',
childValue: 'option 2a',
},
{
childName: 'Option 2B',
childValue: 'option 2b'
}],
}],
validators: {
required: true
}
}
]
I expect to get an output of a second dropdown containing options "Option 2A" and "Option 2B" when the user selects "Option 2," but I get a parsing error.
Many thanks in advance!
I have modified your code please check:
Your updated code sandbox code
check this demo
I think you are looking for cascading dropdown. The above solution may help you check it.

AngularJS - ng-select not working as expected

I have a filter drop down for some tabular data that reads data from a local storage item, the select tag is shown below, and below that is the code to add items to the select tag and the model for the filter.
The issue is that whilst the data filtered is correct when you refresh the page, the selected item only shows the correct value if the local storage value is true.
No matter what value the local storage item is selected="selected" is always added to the "Excluded from Search" option.
Can't for the life of me work out why, any help advice appreciated.
<select class="form-control form-control-sm" ng-model="filterSearch" ng-change="setFilterS()" id="theFilterS" >
<option ng-selected="{{option.value == filterSearch}}" ng-repeat="option in filterSearchOptions" value="{{option.value}}" >{{option.DisplayName}}</option>
</select>
$scope.filterSearch = localStorage.getItem("FilterSearch");
$scope.filterSearchOptions = [{
value: '',
DisplayName: 'All',
}, {
value: 'false',
DisplayName: 'Included in Search',
}, {
value: 'true',
DisplayName: 'Excluded from Search',
}];
You should try with the ng-options directive which IMO gives a simpler approach then ng-repeat
angular.module('app',[]).controller('testCtrl',function($scope){
$scope.filterSearch = 'true';
$scope.filterSearchOptions = [{
value: '',
DisplayName: 'All',
}, {
value: 'false',
DisplayName: 'Included in Search',
}, {
value: 'true',
DisplayName: 'Excluded from Search',
}];
});
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<div ng-app="app" ng-controller="testCtrl">
<select
class="form-control form-control-sm"
ng-model="filterSearch"
ng-change="setFilterS()"
id="theFilterS"
ng-options="option.value as option.DisplayName for option in filterSearchOptions">
</select>
{{filterSearch}}
</div>

How to create a list such that each option is a list in AngularJS?

I want to create a list in which each option is a list itself, but when I try this, the select tag ends it prematurely. Can this be done at all in AngularJS 1.3?
<body ng-app="">
<select placeHolder="This">
<option>A place-holder!</option>
<option>
<select>
<option>A place-holder!</option>
</select>
</option>
<option>Greetings!</option>
</select>
</body>
Something like this, using optgroup creates a sub-group of option rather than a new list.
It's not a standard HTML component. You'll need a JS library that implements it. One I could find is selectivity.js but you would have to write a directive to integrate it with your angular app.
$('#select-with-sublist').selectivity({
allowClear: true,
items: [{
id: 'a',
text: 'A',
submenu: {
items: [
{ id: 'a1', text: 'A1' },
{ id: 'a2', text: 'A2' },
{ id: 'a3', text: 'A3' }
]
}
}, {
id: 'b',
text: 'B',
submenu: {
items: [
{ id: 'b1', text: 'B1' },
{ id: 'b2', text: 'B2' }
]
}
}],
placeholder: 'Select',
showSearchInputInDropdown: false
});
Working example: https://jsfiddle.net/LukaszWiktor/ge64o2ym/
Use <optgroup> instead of the inner select.
<body ng-app="">
<select placeHolder="This">
<option>A place-holder!</option>
<optgroup label="Inner list">
<option>A place-holder!</option>
<option>A place-holder!</option>
</optgroup>
<option>Greetings!</option>
</select>
</body>
This can be done using this example, its a Multi level drop-down menu in Bootstrap 3. Its better to use this since its more flexible. not restricted to two levels only.

Update the value of a selected object in Vue

I wand to select an option from a multiple select field and update the prozent value of the selected objects:
<div id="assistenzen">
<form>
<select v-model="assistenz" multiple>
<option v-for="option in options" v-bind:value="option">
{{ option.text }}
</option>
</select>
<ul>
<li v-for="(assi, prozent) in assistenz">{{assi.text}}
<input v-model="assistenz" v-bind:value="prozent">
{{assi.prozent}}
</li>
</ul>
</form>
</div>
<script>
var assistenz = new Vue({
el: '#assistenzen',
data: {
assistenz: 'keine Assistenz',
options: [
{ text: 'One', value: 'A', prozent: '0' },
{ text: 'Two', value: 'B', prozent: '0' },
{ text: 'Three', value: 'C', prozent: '0' }
]
},
});
assistenz.config.devtools = true
</script>
This code creates an input for each selected option but, the whole option text is stored in the input as value. Also it does not update the property of the object.
currently i prefer 'watch':
watch: {
multiselect: function(indexes) {
for(var i = 0; i < this.options.length; i++)
this.options[i].show = indexes.indexOf(i) > -1;
}
}
full example:
https://jsfiddle.net/4xq3mj9o/
To update the value of the choosen objects I had reverenze the Item iterated in the for loop and bind the input model to the items value:
<div id="assistenzen">
<form>
<select v-model="assistenz" multiple>
<option v-for="option in options" v-bind:value="option">
{{ option.text }}
</option>
</select>
<ul>
<li v-for="assi in assistenz">{{assi.text}}
<input v-model="assi.prozent">
{{assi.prozent}}
</li>
</ul>
</form>
</div>
<script>
var assistenz = new Vue({
el: '#assistenzen',
data: {
assistenz: 'keine Assistenz',
options: [
{ text: 'One', value: 'A', prozent: '0' },
{ text: 'Two', value: 'B', prozent: '0' },
{ text: 'Three', value: 'C', prozent: '0' }
]
},
});
assistenz.config.devtools = true
</script>
Use vue-multiselect
Just use something like this
<Multiselect :options="Options" :value="Values" :multiple="true" #update="updateMultiValue"> </Multiselect>

Categories

Resources