Files
kreios/backoffice/app/Filament/Resources/ModelloResource/RelationManagers/ListinoRelationManager.php
T

135 lines
5.6 KiB
PHP

<?php
namespace App\Filament\Resources\ModelloResource\RelationManagers;
use App\Models\ListinoPrezzo;
use Filament\Forms;
use Filament\Forms\Form;
use Filament\Notifications\Notification;
use Filament\Resources\RelationManagers\RelationManager;
use Filament\Tables;
use Filament\Tables\Table;
use Illuminate\Database\Eloquent\Builder;
use Illuminate\Validation\Rules\Unique;
class ListinoRelationManager extends RelationManager
{
protected static string $relationship = 'listino';
protected static ?string $title = 'Listino';
protected static ?string $modelLabel = 'prezzo';
protected static ?string $pluralModelLabel = 'prezzi';
public function form(Form $form): Form
{
return $form->columns(3)->schema([
Forms\Components\TextInput::make('larghezza')
->label('Larghezza (mm)')
->integer()
->minValue(1)
->required()
->unique(
ignoreRecord: true,
modifyRuleUsing: fn (Unique $rule, Forms\Get $get) => $rule
->where('modello_id', $this->getOwnerRecord()->getKey())
->where('altezza', $get('altezza')),
)
->validationMessages(['unique' => 'Esiste già un prezzo per questa misura.']),
Forms\Components\TextInput::make('altezza')
->label('Altezza (mm)')
->integer()
->minValue(1)
->required(),
Forms\Components\TextInput::make('prezzo')
->label('Prezzo')
->numeric()
->minValue(0)
->prefix('€')
->required(),
]);
}
public function table(Table $table): Table
{
$misure = fn (string $colonna) => fn () => ListinoPrezzo::query()
->where('modello_id', $this->getOwnerRecord()->getKey())
->orderBy($colonna)
->distinct()
->pluck($colonna)
->mapWithKeys(fn ($v) => [$v => $this->mm($v)])
->all();
return $table
->description(fn () => ($data = $this->getOwnerRecord()->listino_aggiornato_at)
? 'Ultimo aggiornamento: '.$data->format('d/m/Y H:i').'. Il configuratore usa la prima misura del listino uguale o superiore a quella richiesta.'
: 'Nessun listino caricato: importalo dalla lista Sistemi o aggiungi i prezzi a mano.')
->modifyQueryUsing(fn (Builder $query) => $query->orderBy('altezza')->orderBy('larghezza'))
->defaultPaginationPageOption(25)
->columns([
Tables\Columns\TextColumn::make('altezza')
->label('Altezza')
->formatStateUsing(fn ($state) => $this->mm($state))
->sortable(),
Tables\Columns\TextColumn::make('larghezza')
->label('Larghezza')
->formatStateUsing(fn ($state) => $this->mm($state))
->sortable(),
Tables\Columns\TextInputColumn::make('prezzo')
->label('Prezzo (€)')
->type('number')
->step('0.01')
->rules(['required', 'numeric', 'min:0'])
->sortable(),
Tables\Columns\IconColumn::make('personalizzato')
->label('Personalizzato')
->icon(fn (bool $state) => $state ? 'heroicon-o-pencil-square' : null)
->color('warning')
->tooltip(fn (ListinoPrezzo $record) => $record->personalizzato ? 'Aggiunto a mano: può essere preservato alla prossima importazione' : null),
])
->filters([
Tables\Filters\SelectFilter::make('altezza')->label('Altezza')->options($misure('altezza')),
Tables\Filters\SelectFilter::make('larghezza')->label('Larghezza')->options($misure('larghezza')),
Tables\Filters\TernaryFilter::make('personalizzato')->label('Personalizzato'),
])
->headerActions([
Tables\Actions\CreateAction::make()
->mutateFormDataUsing(fn (array $data) => $data + ['personalizzato' => true]),
Tables\Actions\Action::make('svuota')
->label('Svuota listino')
->icon('heroicon-o-trash')
->color('danger')
->requiresConfirmation()
->modalDescription('Verranno eliminati tutti i prezzi del modello. Il configuratore non potrà calcolare il prezzo finché non sarà caricato un nuovo listino.')
->visible(fn () => $this->getOwnerRecord()->listino()->exists())
->action(function () {
$modello = $this->getOwnerRecord();
$modello->listino()->delete();
$modello->update(['listino_aggiornato_at' => null]);
Notification::make()->title('Listino svuotato')->success()->send();
}),
])
->actions([
Tables\Actions\EditAction::make(),
Tables\Actions\DeleteAction::make(),
])
->bulkActions([
Tables\Actions\BulkActionGroup::make([
Tables\Actions\DeleteBulkAction::make(),
]),
]);
}
public function isReadOnly(): bool
{
return false;
}
private function mm(mixed $valore): string
{
return number_format((int) $valore, 0, ',', '.').' mm';
}
}