Use $get to find repeater value

Hello - I am using a repeater on a form. Within the repeater, I want the user to select an option from a list. If a new section is added to the repeater, I do not want the category that has already been selected above to be an option. I am trying to use $get to find the repeater but nothing seems to work. I've tried $get('selections') and $get('../selections') but nothing has worked. What am I missing?
Repeater::make('selections')
->columns(4)
->disableItemMovement()
->maxWidth('max-w-7xl')
->minItems(1)
->createItemButtonLabel('Add Category')
->collapsible()
->reactive()
->schema([
Select::make('menu_category')
->label('Category')
->required()
->options(function(callable $get) {
$repeater = $get('../selections');
$idsAlreadyUsed = [];
if(isset($repeater[0])) {
foreach($repeater as $section) {
if(in_array($section['menu_category'], $idsAlreadyUsed) === false) {
$idsAlreadyUsed[] = $section['menu_category'];
}
}
}
return MenuCategory::whereNotIn('id', $idsAlreadyUsed)->pluck('name', 'id')->toArray();
}),
Repeater::make('selections')
->columns(4)
->disableItemMovement()
->maxWidth('max-w-7xl')
->minItems(1)
->createItemButtonLabel('Add Category')
->collapsible()
->reactive()
->schema([
Select::make('menu_category')
->label('Category')
->required()
->options(function(callable $get) {
$repeater = $get('../selections');
$idsAlreadyUsed = [];
if(isset($repeater[0])) {
foreach($repeater as $section) {
if(in_array($section['menu_category'], $idsAlreadyUsed) === false) {
$idsAlreadyUsed[] = $section['menu_category'];
}
}
}
return MenuCategory::whereNotIn('id', $idsAlreadyUsed)->pluck('name', 'id')->toArray();
}),
13 Replies
Unknown User
Unknown User2y ago
Message Not Public
Sign In & Join Server To View
bwurtz999
bwurtz999OP2y ago
I found this yesterday. I'm pretty sure I tried getState and got an error. But I'll try it again When I try this:
Repeater::make('selections')
->columns(4)
->disableItemMovement()
->maxWidth('max-w-7xl')
->minItems(1)
->createItemButtonLabel('Add Category')
->collapsible()
->reactive()
->schema([
Select::make('menu_category')
->label('Category')
->required()
->reactive()
->options(function(RelationManager $livewire) {
Log::debug($livewire->getState());
return MenuCategory::pluck('name', 'id')->toArray();
}),
Repeater::make('selections')
->columns(4)
->disableItemMovement()
->maxWidth('max-w-7xl')
->minItems(1)
->createItemButtonLabel('Add Category')
->collapsible()
->reactive()
->schema([
Select::make('menu_category')
->label('Category')
->required()
->reactive()
->options(function(RelationManager $livewire) {
Log::debug($livewire->getState());
return MenuCategory::pluck('name', 'id')->toArray();
}),
I get an error saying Method App\Filament\Resources\OrderResource\RelationManagers\SelectionsRelationManager::getState does not exist.
Spârky
Spârky2y ago
Hello! Sorry for digging up the thread, did you find a way to make it work ? @bwurtz999
bwurtz999
bwurtz999OP2y ago
@sparkyyy_ yes I did. I wasn't going up enough levels $get('../../selections') solved it for me
Spârky
Spârky2y ago
I'll try this tomorrow! Thanks for the quick response 🙂 Good morning 🙂 I tried to adapt your code to my problem but it seems like the condition
if(isset($repeater[0]))
if(isset($repeater[0]))
is never fulfilled so I still have all the options. Are you sure this is all the code you have?
Dan Harrin
Dan Harrin2y ago
0 is not necessarily a repeater index usually they are uuids
Spârky
Spârky2y ago
Yes I noticed that, when I var_dump my repeater, I get a uuid but it changes every refresh Any idea?
Dan Harrin
Dan Harrin2y ago
Arr::first($repeater) ?
Spârky
Spârky2y ago
Ok, I almost made it work Now when I pick an option, this option is not available for other instances but it also removes it from the input 😦 Here is the code :
Forms\Components\Repeater::make('product_menu')
->label("Produits du menu")
->schema([
Forms\Components\Select::make('product_id')
->label('Produit')
->required()
->options(function (callable $get){
$repeater = $get('../../product_menu');
$idIsAlreadyUsed = [];
$repeater_uuid = array_key_first($repeater);
if (isset($repeater[$repeater_uuid])){
foreach ($repeater as $section){
if (in_array($section['product_id'], $idIsAlreadyUsed) === false){
$idIsAlreadyUsed[] = $section['product_id'];
}
}
}
return Product::whereNotIn('id', array_filter($idIsAlreadyUsed, fn ($value) => !is_null($value)))->pluck('name','id')->toArray();
}),
Forms\Components\Repeater::make('product_menu')
->label("Produits du menu")
->schema([
Forms\Components\Select::make('product_id')
->label('Produit')
->required()
->options(function (callable $get){
$repeater = $get('../../product_menu');
$idIsAlreadyUsed = [];
$repeater_uuid = array_key_first($repeater);
if (isset($repeater[$repeater_uuid])){
foreach ($repeater as $section){
if (in_array($section['product_id'], $idIsAlreadyUsed) === false){
$idIsAlreadyUsed[] = $section['product_id'];
}
}
}
return Product::whereNotIn('id', array_filter($idIsAlreadyUsed, fn ($value) => !is_null($value)))->pluck('name','id')->toArray();
}),
Dan Harrin
Dan Harrin2y ago
you could use $state to get the current value and make sure its present in this set of options
bwurtz999
bwurtz999OP2y ago
@sparkyyy_ I think you're missing something in the if statement. It wasn't in the original I posted in this thread, but here is what I use that now works:
->options(function($livewire, callable $get) {
$info = $get('../../selections');
$thisMenuCategory = $get('menu_category');
$idsAlreadyUsed = [];
foreach($info as $repeater) {
if(in_array($repeater['menu_category'], $idsAlreadyUsed) === false
&& $repeater['menu_category'] !== null
&& $repeater['menu_category'] != $thisMenuCategory) {
$idsAlreadyUsed[] = $repeater['menu_category'];
}
}
return MenuCategory::whereNotIn('id', $idsAlreadyUsed)->pluck('name', 'id')->toArray();
}),
->options(function($livewire, callable $get) {
$info = $get('../../selections');
$thisMenuCategory = $get('menu_category');
$idsAlreadyUsed = [];
foreach($info as $repeater) {
if(in_array($repeater['menu_category'], $idsAlreadyUsed) === false
&& $repeater['menu_category'] !== null
&& $repeater['menu_category'] != $thisMenuCategory) {
$idsAlreadyUsed[] = $repeater['menu_category'];
}
}
return MenuCategory::whereNotIn('id', $idsAlreadyUsed)->pluck('name', 'id')->toArray();
}),
I think because you don't have && $repeater['menu_category'] != $thisMenuCategory is why it keeps being removed
Spârky
Spârky2y ago
Oh okay, I tried to do something with the state but couldn't make it work I'll be on a vacation until Monday but I'll keep you updated. Thanks anyway! 🙂 Hello! I hope you are doing well 🙂 Thank you so much, this is exactly what I was looking for and it is working 🥲
Want results from more Discord servers?
Add your server