loadData(); } public function loadData(): void { $this->resetErrorBag(); // Reload data $this->plugin = $this->plugin->fresh(); $this->configuration_template = $this->plugin->configuration_template ?? []; $this->configuration = is_array($this->plugin->configuration) ? $this->plugin->configuration : []; // Initialize multiValues by exploding the CSV strings from the DB foreach ($this->configuration_template['custom_fields'] ?? [] as $field) { if (($field['field_type'] ?? null) === 'multi_string') { $fieldKey = $field['keyname']; $rawValue = $this->configuration[$fieldKey] ?? ($field['default'] ?? ''); $currentValue = is_array($rawValue) ? '' : (string)$rawValue; $this->multiValues[$fieldKey] = $currentValue !== '' ? array_values(array_filter(explode(',', $currentValue))) : ['']; } } } /** * Triggered by @close on the modal to discard any typed but unsaved changes */ public int $resetIndex = 0; // Add this property public function resetForm(): void { $this->loadData(); $this->resetIndex++; // Increment to force DOM refresh } public function saveConfiguration() { abort_unless(auth()->user()->plugins->contains($this->plugin), 403); // final validation layer $this->validate([ 'multiValues.*.*' => ['nullable', 'string', 'regex:/^[^,]*$/'], ], [ 'multiValues.*.*.regex' => 'Items cannot contain commas.', ]); // Prepare config copy to send to db $finalValues = $this->configuration; foreach ($this->configuration_template['custom_fields'] ?? [] as $field) { $fieldKey = $field['keyname']; // Handle multi_string: Join array back to CSV string if ($field['field_type'] === 'multi_string' && isset($this->multiValues[$fieldKey])) { $finalValues[$fieldKey] = implode(',', array_filter(array_map('trim', $this->multiValues[$fieldKey]))); } // Handle code fields: Try to JSON decode if necessary (standard TRMNL behavior) if ($field['field_type'] === 'code' && isset($finalValues[$fieldKey]) && is_string($finalValues[$fieldKey])) { $decoded = json_decode($finalValues[$fieldKey], true); if (json_last_error() === JSON_ERROR_NONE && (is_array($decoded) || is_object($decoded))) { $finalValues[$fieldKey] = $decoded; } } } // send to db $this->plugin->update(['configuration' => $finalValues]); $this->configuration = $finalValues; // update local state $this->dispatch('config-updated'); // notifies listeners Flux::modal('configuration-modal')->close(); } // ------------------------------------This section contains helper functions for interacting with the form------------------------------------------------ public function addMultiItem(string $fieldKey): void { $this->multiValues[$fieldKey][] = ''; } public function removeMultiItem(string $fieldKey, int $index): void { unset($this->multiValues[$fieldKey][$index]); $this->multiValues[$fieldKey] = array_values($this->multiValues[$fieldKey]); if (empty($this->multiValues[$fieldKey])) { $this->multiValues[$fieldKey][] = ''; } } // Livewire magic method to validate MultiValue input boxes // Runs on every debounce public function updatedMultiValues($value, $key) { $this->validate([ 'multiValues.*.*' => ['nullable', 'string', 'regex:/^[^,]*$/'], ], [ 'multiValues.*.*.regex' => 'Items cannot contain commas.', ]); } public function loadXhrSelectOptions(string $fieldKey, string $endpoint, ?string $query = null): void { abort_unless(auth()->user()->plugins->contains($this->plugin), 403); try { $requestData = []; if ($query !== null) { $requestData = [ 'function' => $fieldKey, 'query' => $query ]; } $response = $query !== null ? Http::post($endpoint, $requestData) : Http::post($endpoint); if ($response->successful()) { $this->xhrSelectOptions[$fieldKey] = $response->json(); } else { $this->xhrSelectOptions[$fieldKey] = []; } } catch (\Exception $e) { $this->xhrSelectOptions[$fieldKey] = []; } } public function searchXhrSelect(string $fieldKey, string $endpoint): void { $query = $this->searchQueries[$fieldKey] ?? ''; if (!empty($query)) { $this->loadXhrSelectOptions($fieldKey, $endpoint, $query); } } };?>
Configuration Configure your plugin settings
@if(isset($configuration_template['custom_fields']) && is_array($configuration_template['custom_fields'])) @foreach($configuration_template['custom_fields'] as $field) @php $fieldKey = $field['keyname'] ?? $field['key'] ?? $field['name']; $rawValue = $configuration[$fieldKey] ?? ($field['default'] ?? ''); # These are sanitized at Model/Plugin level, safe to render HTML $safeDescription = $field['description'] ?? ''; $safeHelp = $field['help_text'] ?? ''; // For code fields, if the value is an array, JSON encode it if ($field['field_type'] === 'code' && is_array($rawValue)) { $currentValue = json_encode($rawValue, JSON_PRETTY_PRINT | JSON_UNESCAPED_SLASHES); } else { $currentValue = is_array($rawValue) ? '' : (string) $rawValue; } @endphp
@if($field['field_type'] === 'author_bio') @continue @endif @if($field['field_type'] === 'copyable_webhook_url') @continue @endif @if($field['field_type'] === 'string' || $field['field_type'] === 'url') {{ $field['name'] }} {!! $safeDescription !!} {!! $safeHelp !!} @elseif($field['field_type'] === 'text') {{ $field['name'] }} {!! $safeDescription !!} {!! $safeHelp !!} @elseif($field['field_type'] === 'code') {{ $field['name'] }} {!! $safeDescription !!} {!! $safeHelp !!} @elseif($field['field_type'] === 'password') {{ $field['name'] }} {!! $safeDescription !!} {!! $safeHelp !!} @elseif($field['field_type'] === 'copyable') {{ $field['name'] }} {!! $safeDescription !!} {!! $safeHelp !!} @elseif($field['field_type'] === 'time_zone') {{ $field['name'] }} {!! $safeDescription !!} @foreach(timezone_identifiers_list() as $timezone) @endforeach {!! $safeHelp !!} @elseif($field['field_type'] === 'number') {{ $field['name'] }} {!! $safeDescription !!} {!! $safeHelp !!} @elseif($field['field_type'] === 'boolean') {{ $field['name'] }} {!! $safeDescription !!} {!! $safeHelp !!} @elseif($field['field_type'] === 'date') {{ $field['name'] }} {!! $safeDescription !!} {!! $safeHelp !!} @elseif($field['field_type'] === 'time') {{ $field['name'] }} {!! $safeDescription !!} {!! $safeHelp !!} @elseif($field['field_type'] === 'select') @if(isset($field['multiple']) && $field['multiple'] === true) {{ $field['name'] }} {!! $safeDescription !!} @if(isset($field['options']) && is_array($field['options'])) @foreach($field['options'] as $option) @if(is_array($option)) @foreach($option as $label => $value) @endforeach @else @php $key = mb_strtolower(str_replace(' ', '_', $option)); @endphp @endif @endforeach @endif {!! $safeHelp !!} @else {{ $field['name'] }} {!! $safeDescription !!} @if(isset($field['options']) && is_array($field['options'])) @foreach($field['options'] as $option) @if(is_array($option)) @foreach($option as $label => $value) @endforeach @else @php $key = mb_strtolower(str_replace(' ', '_', $option)); @endphp @endif @endforeach @endif {!! $safeHelp !!} @endif @elseif($field['field_type'] === 'xhrSelect') {{ $field['name'] }} {!! $safeDescription !!} @if(isset($xhrSelectOptions[$fieldKey]) && is_array($xhrSelectOptions[$fieldKey])) @foreach($xhrSelectOptions[$fieldKey] as $option) @if(is_array($option)) @if(isset($option['id']) && isset($option['name'])) {{-- xhrSelectSearch format: { 'id' => 'db-456', 'name' => 'Team Goals' } --}} @else {{-- xhrSelect format: { 'Braves' => 123 } --}} @foreach($option as $label => $value) @endforeach @endif @else @endif @endforeach @endif {!! $safeHelp !!} @elseif($field['field_type'] === 'xhrSelectSearch')
{{ $field['name'] }} {!! $safeDescription !!} {!! $safeHelp !!} @if((isset($xhrSelectOptions[$fieldKey]) && is_array($xhrSelectOptions[$fieldKey]) && count($xhrSelectOptions[$fieldKey]) > 0) || !empty($currentValue)) @if(isset($xhrSelectOptions[$fieldKey]) && is_array($xhrSelectOptions[$fieldKey])) @foreach($xhrSelectOptions[$fieldKey] as $option) @if(is_array($option)) @if(isset($option['id']) && isset($option['name'])) {{-- xhrSelectSearch format: { 'id' => 'db-456', 'name' => 'Team Goals' } --}} @else {{-- xhrSelect format: { 'Braves' => 123 } --}} @foreach($option as $label => $value) @endforeach @endif @else @endif @endforeach @endif @if(!empty($currentValue) && (!isset($xhrSelectOptions[$fieldKey]) || empty($xhrSelectOptions[$fieldKey]))) {{-- Show current value even if no options are loaded --}} @endif @endif
@elseif($field['field_type'] === 'multi_string') {{ $field['name'] }} {!! $safeDescription !!}
@foreach($multiValues[$fieldKey] as $index => $item)
@if(count($multiValues[$fieldKey]) > 1) @endif
@error("multiValues.{$fieldKey}.{$index}")
{{-- $message comes from thrown error --}} {{ $message }}
@enderror @endforeach Add Item
{!! $safeHelp !!}
@else Field type "{{ $field['field_type'] }}" not yet supported @endif
@endforeach @endif
Save Configuration @if($errors->any())
Fix errors before saving.
@endif