Reputation: 21
Using Alpine.js how do you get the value of select1
or select2
in the main form()
function?
I can do it if I don't use x-data
on the Selects, but then you have to do funky things with the open
variable so it is unique for each Select (if you don't, then all the Selects open at once).
Notes:
x-for
to iterate the Select Option inputs because for performance reasons I'm pre-rendering those in HTML. They have icons and there is over 250 of them.@click="$dispatch('input', 'option1Key')"
technique the best way to set the value of the selected option, since not using an actual select input and x-for?<div x-data="form()">
<!-- snip other fields like regular inputs -->
<label for="select-1">Select 1</label>
<div x-data="{ select1: '', open: false }">
<div>Selected: <span x-text="select1"></span></div>
<button @click="open=true">Select ...</button>
<ul x-show="open" @click.away="open=false" x-model="select1" style="display: none;">
<li @click="$dispatch('input', 'option1Key')"><i class="icon"></i> Option1</li>
<li @click="$dispatch('input', 'option2Key')"><i class="icon"></i> Option2</li>
</ul>
</div>
<label for="select-2">Select 2</label>
<div x-data="{ select2: '', open: false }">
<div>Selected: <span x-text="select2"></span></div>
<button @click="open=true">Select ...</button>
<ul x-show="open" @click.away="open=false" x-model="select2" style="display: none;">
<li @click="$dispatch('input', 'option1Key')"><i class="icon"></i> Option1</li>
<li @click="$dispatch('input', 'option2Key')"><i class="icon"></i> Option2</li>
</ul>
</div>
<button class="search" type="submit" :disabled="loading" @click="search()">Search</button>
</div>
<script>
function form() {
return {
select1: '',
select2: '',
search() {
console.log(select1); // undefined
console.log(select2); // undefined
},
};
};
Upvotes: 2
Views: 6847
Reputation: 3888
For posterity, we discussed this through another channel but the way to fix this issue is to have a single Alpine component (x-data)
<div x-data="f()">
<!-- snip other fields like regular inputs -->
<div class="select">
<label for="select-1">Select 1 Label</label>
<div>
<div class="output">x-text "select1": <span x-text="select1"></span></div>
<button @click="open='select1'">Click to Select1 ...</button>
<ul x-show="open === 'select1'" @click.away="open=null" x-model="select1">
<li @click="$dispatch('input', 'option1Key')"><i class="icon"></i> Option1</li>
<li @click="$dispatch('input', 'option2Key')"><i class="icon"></i> Option2</li>
</ul>
</div>
</div>
<div class="select">
<label for="select-2">Select 2 Label</label>
<div>
<div class="output">x-text "select2": <span x-text="select2"></span></div>
<button @click="open='select2'">Click to Select2 ...</button>
<ul x-show="open === 'select2'" @click.away="open=null" x-model="select2">
<li @click="$dispatch('input', 'option1Key')"><i class="icon"></i> Option1</li>
<li @click="$dispatch('input', 'option2Key')"><i class="icon"></i> Option2</li>
</ul>
</div>
</div>
<button class="search" type="submit" :disabled="loading" @click="search()">Search</button>
</div>
Script
function f() {
return {
open: null,
loading: false,
select1: '',
select2: '',
search() {
console.log('select1 value: ' + "'" + this.select1 + "'"); // ''
console.log('select2 value: ' + "'" + this.select2 + "'"); // ''
},
};
}
The fills working fiddle is at https://jsfiddle.net/w7hg341m/9/
Upvotes: 1