Select Component Lazy Loading though API

I use external API as the source of options for my select component. Is there anyway to make it support the pagination of the api? which means load more data once the user scrolled to the end of shown records? either by auto calling the api and pass param page=1/2/3.. or the user click on show more button or smth' similar? My current code: here is how i use the component: Select::make('general_topic_id') ->label('General topic') ->searchable() ->options(fn ($get) => $this->getGeneralTopicOptions($get, null)) ->getSearchResultsUsing(fn ($get, string $search) => $this->getGeneralTopicOptions($get, $search)) ->disabled(fn ($get) => !$get('org_library_access_authorization_id')) ->reactive() ->placeholder('Select a general topic'), and here is my getGeneralTopicOptions method: private function getGeneralTopicOptions($get, $search): array { $orgLibraryAccessAuthorizationId = $get('org_library_access_authorization_id'); if (empty($orgLibraryAccessAuthorizationId)) { return []; } $generalTopics = ReferenceCurriculumService::getGeneralTopics($orgLibraryAccessAuthorizationId, $this->course->subject_code, $search); return collect($generalTopics)->mapWithKeys(function ($topic) { return [$topic['id'] => $topic['name']]; })->toArray(); }
18 Replies
LeandroFerreira
LeandroFerreira4mo ago
Custom component I think
Mohammed Ouda
Mohammed OudaOP4mo ago
Hi Leandro, entirly custom? or based on a suggestion?
LeandroFerreira
LeandroFerreira4mo ago
entirely
Mohammed Ouda
Mohammed OudaOP4mo ago
actually i am facing much troubles with the official docs in this regard, it's not really explaining how custom components can be structured. can you provide me with sufficient resources in this regard please?
Mohammed Ouda
Mohammed OudaOP4mo ago
Thanks for sharing Leandro, I was trying to keep the functionality of the current Select component and extend it. I'll try to give it another try with building a custom field. if you have any thoughts in regard to the extend methodology will be appreciated. Hi @Leandro Ferreira, I created this Test custom Field: <?php namespace App\Forms\Components; use Filament\Forms\Components\Field; use Filament\Forms\Components\Concerns; class Test extends Field { use Concerns\HasPlaceholder; use Concerns\HasOptions; protected string $view = 'forms.components.test'; public function loadMoreOptions() { \Log::info("got called!!"); } } and here is my forms.components.test blade file code: @php $statePath = $getStatePath(); $isDisabled = $isDisabled(); $placeholder = $getPlaceholder(); $options = $getOptions(); @endphp <x-dynamic-component :component="$getFieldWrapperView()" :field="$field" :inline-label-vertical-alignment="\Filament\Support\Enums\VerticalAlignment::Center" > <x-filament::input.wrapper :disabled="$isDisabled"> <div class="hidden" x-data="{ isDisabled: @js($isDisabled), init: function () { const container = $el.nextElementSibling container.dispatchEvent( new CustomEvent('set-select-property', { detail: { isDisabled: this.isDisabled }, }), ) console.log(this.isDisabled); }, }" ></div> <div> <select x-ref="input" wire:model="state.{{ $statePath }}" style="border: none; height: 36px; line-height: 36px; border-radius: .5rem; padding-top: 0; padding-bottom: 0; width: 100%; font-size: 14px;" {{ $isDisabled ? 'disabled' : '' }} > <option value="" disabled selected>{{ $placeholder }}</option> @foreach ($options as $key => $option) <option value="{{ $key }}">{{ $option }}</option> @endforeach </select> <button type="button" wire:click="loadMoreOptions()">Load More Options</button> </div> </x-filament::input.wrapper> </x-dynamic-component> the wire:click="loadMoreOptions()" returns Unable to call component method. Public method [loadMoreOptions] not found on component is there a proper way to call the method? I couldn't find a suitable result while I am searching in this regard.
LeandroFerreira
LeandroFerreira4mo ago
CreatePage, EditPage, etc are the livewire components. So you should add this method in your pages
Mohammed Ouda
Mohammed OudaOP4mo ago
Hi @Leandro Ferreira, I created my custom component. all looks good, but i have a small issue here.
Mohammed Ouda
Mohammed OudaOP4mo ago
here is my form schema:
Mohammed Ouda
Mohammed OudaOP4mo ago
when i click 'add Unit' from the repeater, this part of the code, which loads my component is causing an issue: $this->record ? View::make('filament.import-lesson-material') ->viewData(['course' => $this->record]) ->columnSpan('full') : null,
Mohammed Ouda
Mohammed OudaOP4mo ago
i get in the broswer console:
No description
Mohammed Ouda
Mohammed OudaOP4mo ago
and the repeater loses its binding to the rest of the form, so when i click submit it do net see all of the rest fields in the other repeater forms. its like corrupt everything. the content of the filament.import-lesson-material is: @if($course && isset($getState()['id'])) @livewire('import-lesson-material', ['course' => $course, 'lesson' => $getState()]) @endif Can you tell what part of this work breaks the flow?
LeandroFerreira
LeandroFerreira4mo ago
Please open new topics for any issues you’re encountering. Regarding this specific issue, I suggest reducing some of the code to better focus on the problem. Did you follow the instructions in https://filamentphp.com/docs/3.x/forms/adding-a-form-to-a-livewire-component#adding-the-form when creating your component?
Mohammed Ouda
Mohammed OudaOP4mo ago
yes, but it looks using it inside a repeater duplicates the main component div id which causes the issue.
Mohammed Ouda
Mohammed OudaOP4mo ago
No description
Mohammed Ouda
Mohammed OudaOP4mo ago
No description
Mohammed Ouda
Mohammed OudaOP4mo ago
@Leandro Ferreira, my structure is in an EditRecord page > has a Repeater > uses ImportLessonMaterial extends Filament\Forms\Components\Component > in its view > I call liveware component which is a button that opens a modal. does this structure has an issue? my issue currently, is a dubplicated IDs as i see from the console
Want results from more Discord servers?
Add your server