Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add Custom FIlter Input Attributes, Cleanup Filter Tests #2131

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
46 changes: 46 additions & 0 deletions docs/filter-types/filters-number.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,27 @@ weight: 9

Number filters are just HTML number inputs.

```php
public function filters(): array
{
return [
NumberFilter::make('Amount')
->filter(function(Builder $builder, string $value) {
$builder->where('amount', '<', $value);
}),
];
}
```

Historically, min/max/placeholders were set using the "config" option, which is still available. However, it is strongly recommended to use the new setInputAttributes for enhanced customisation.

## Old Behaviour
The following would:
- Set a min of 0
- Set a max of 100
- Add a placeholder
- Keep the default colors & styling

```php
public function filters(): array
{
Expand All @@ -21,3 +42,28 @@ public function filters(): array
];
}
```

## New Behaviour
The following would:
- Set a min of 5
- Set a max of 20
- Set steps to be 0.5
- Add a placeholder
- Keep the default colors & styling

```php
public function filters(): array
{
return [
NumberFilter::make('Age')
->setInputAttributes([
'min' => '5', // Minimum Value Accepted
'max' => '20', // Maximum Value Accepted
'step' => '0.5', // Set step
'placeholder' => 'Enter Number 0 - 100', // A placeholder value
'default-colors' => true,
'default-styling' => true,
]),
];
}
```
52 changes: 52 additions & 0 deletions docs/filters/available-filter-methods.md
Original file line number Diff line number Diff line change
Expand Up @@ -208,6 +208,58 @@ TextFilter::make('Name')
),
```

## setInputAttributes
Allows for customising the attributes that will apply to the input field for the filter.

By default, this replaces the default classes on the Filter Input, if you would like to keep them, set the default-styling and/or default-colors flags to true.

### TextFilter Example
The following would:
- Set a maxlength of 75
- Set a placeholder of "Enter a Name"
- Replace the default colors
- Retain the default styling (e.g. rounding/shadow)

```php
public function filters(): array
{
return [
TextFilter::make('Name')
->setInputAttributes([
'maxlength' => '75',
'placeholder' => 'Enter a Name',
'class' => 'text-white bg-red-500 dark:bg-red-500',
'default-colors' => false,
'default-styling' => true,
]),
];
}
```

### NumberFilter Example
The following would:
- Set a min of 5
- Set a max of 20
- Set steps to be 0.5
- Keep the default colors & styling

```php
public function filters(): array
{
return [
NumberFilter::make('Age')
->setInputAttributes([
'min' => '5',
'max' => '20',
'step' => '0.5',
'default-colors' => true,
'default-styling' => true,
]),
];
}
```


## setCustomView
Use a fully custom view for a filter. This will utilise solely your view when rendering this filter. Note that the following methods will no longer apply to a filter using this:
- setCustomFilterLabel
Expand Down
17 changes: 9 additions & 8 deletions resources/views/components/tools/filters/boolean.blade.php
Original file line number Diff line number Diff line change
Expand Up @@ -7,14 +7,15 @@
<x-livewire-tables::tools.filter-label :$filter :$filterLayout :$tableName :$isTailwind :$isBootstrap4 :$isBootstrap5 :$isBootstrap />
<input id="thisId" type="checkbox" name="switch" class="hidden" :checked="value" />

<button id="{{ $tableName }}-filter-{{ $filter->getKey() }}"
x-ref="switchButton"
type="button"
@click="toggleStatusWithUpdate"
:class="(value == 1 || value == true) ? 'bg-blue-600' : 'bg-neutral-200'"
class="relative inline-flex h-6 py-0.5 ml-4 focus:outline-none rounded-full w-10"
x-cloak>
<span :class="(value == 1 || value == true) ? 'translate-x-[18px]' : 'translate-x-0.5'" class="w-5 h-5 duration-200 ease-in-out bg-white rounded-full shadow-md"></span>
<button x-cloak {{ $filterInputAttributes->merge([
":class" => "(value == 1 || value == true) ? '".$filterInputAttributes['activeColor']."' : '".$filterInputAttributes['inactiveColor']."'",
])
->class([
'relative inline-flex h-6 py-0.5 ml-4 focus:outline-none rounded-full w-10' => ($filterInputAttributes['default-styling'] ?? true)
])
->except(['default-styling','default-colors','activeColor','inactiveColor','blobColor'])
}}>
<span :class="(value == 1 || value == true) ? 'translate-x-[18px]' : 'translate-x-0.5'" class="w-5 h-5 duration-200 ease-in-out rounded-full shadow-md {{ $filterInputAttributes['blobColor'] }}"></span>
</button>
<template x-if="(value == 1 || value == true)">
<button @click="toggleStatusWithReset" type="button"
Expand Down
21 changes: 9 additions & 12 deletions resources/views/components/tools/filters/date.blade.php
Original file line number Diff line number Diff line change
Expand Up @@ -4,17 +4,14 @@
'rounded-md shadow-sm' => $isTailwind,
'mb-3 mb-md-0 input-group' => $isBootstrap,
])>
<input {{ $filter->getWireMethod('filterComponents.'.$filter->getKey()) }}
wire:key="{{ $filter->generateWireKey($tableName, 'date') }}"
id="{{ $tableName }}-filter-{{ $filter->getKey() }}@if($filter->hasCustomPosition())-{{ $filter->getCustomPosition() }}@endif"
type="date"
@if($filter->hasConfig('min')) min="{{ $filter->getConfig('min') }}" @endif
@if($filter->hasConfig('max')) max="{{ $filter->getConfig('max') }}" @endif
@if($filter->hasConfig('placeholder')) placeholder="{{ $filter->getConfig('placeholder') }}" @endif
@class([
'block w-full border-gray-300 rounded-md shadow-sm transition duration-150 ease-in-out focus:border-indigo-300 focus:ring focus:ring-indigo-200 focus:ring-opacity-50 dark:bg-gray-800 dark:text-white dark:border-gray-600' => $isTailwind,
'form-control' => $isBootstrap,
])
/>
<input {!! $filter->getWireMethod('filterComponents.'.$filter->getKey()) !!} {{
$filterInputAttributes->merge()
->class([
'block w-full rounded-md shadow-sm transition duration-150 ease-in-out focus:ring focus:ring-opacity-50' => $isTailwind && ($filterInputAttributes['default-styling'] ?? true),
'border-gray-300 focus:border-indigo-300 focus:ring-indigo-200 dark:bg-gray-800 dark:text-white dark:border-gray-600' => $isTailwind && ($filterInputAttributes['default-colors'] ?? true),
'form-control' => $isBootstrap,
])
->except(['default-styling','default-colors'])
}} />
</div>
</div>
21 changes: 9 additions & 12 deletions resources/views/components/tools/filters/datetime.blade.php
Original file line number Diff line number Diff line change
Expand Up @@ -5,17 +5,14 @@
'rounded-md shadow-sm' => $isTailwind,
'mb-3 mb-md-0 input-group' => $isBootstrap,
])>
<input {{ $filter->getWireMethod('filterComponents.'.$filter->getKey()) }}
wire:key="{{ $filter->generateWireKey($tableName, 'datetime') }}"
id="{{ $tableName }}-filter-{{ $filter->getKey() }}@if($filter->hasCustomPosition())-{{ $filter->getCustomPosition() }}@endif"
type="datetime-local"
@if($filter->hasConfig('min')) min="{{ $filter->getConfig('min') }}" @endif
@if($filter->hasConfig('max')) max="{{ $filter->getConfig('max') }}" @endif
@if($filter->hasConfig('placeholder')) placeholder="{{ $filter->getConfig('placeholder') }}" @endif
@class([
'block w-full border-gray-300 rounded-md shadow-sm transition duration-150 ease-in-out focus:border-indigo-300 focus:ring focus:ring-indigo-200 focus:ring-opacity-50 dark:bg-gray-800 dark:text-white dark:border-gray-600' => $isTailwind,
'form-control' => $isBootstrap,
])
/>
<input {!! $filter->getWireMethod('filterComponents.'.$filter->getKey()) !!} {{
$filterInputAttributes->merge()
->class([
'block w-full rounded-md shadow-sm transition duration-150 ease-in-out focus:ring focus:ring-opacity-50' => $isTailwind && ($filterInputAttributes['default-styling'] ?? true),
'border-gray-300 focus:border-indigo-300 focus:ring-indigo-200 dark:bg-gray-800 dark:text-white dark:border-gray-600' => $isTailwind && ($filterInputAttributes['default-colors'] ?? true),
'form-control' => $isBootstrap,
])
->except(['default-styling','default-colors'])
}} />
</div>
</div>
Original file line number Diff line number Diff line change
Expand Up @@ -2,37 +2,22 @@
<x-livewire-tables::tools.filter-label :$filter :$filterLayout :$tableName :$isTailwind :$isBootstrap4 :$isBootstrap5 :$isBootstrap />

@if ($isTailwind)
<div class="rounded-md shadow-sm">
<select multiple
{{ $filter->getWireMethod('filterComponents.'.$filter->getKey()) }}
wire:key="{{ $filter->generateWireKey($tableName, 'multiselectdropdown') }}"
id="{{ $tableName }}-filter-{{ $filter->getKey() }}@if($filter->hasCustomPosition())-{{ $filter->getCustomPosition() }}@endif"
class="block w-full transition duration-150 ease-in-out border-gray-300 rounded-md shadow-sm focus:border-indigo-300 focus:ring focus:ring-indigo-200 focus:ring-opacity-50 dark:bg-gray-800 dark:text-white dark:border-gray-600"
>
@if ($filter->getFirstOption() !== '')
<option @if($filter->isEmpty($this)) selected @endif value="all">{{ $filter->getFirstOption()}}</option>
@endif
@foreach($filter->getOptions() as $key => $value)
@if (is_iterable($value))
<optgroup label="{{ $key }}">
@foreach ($value as $optionKey => $optionValue)
<option value="{{ $optionKey }}">{{ $optionValue }}</option>
@endforeach
</optgroup>
@else
<option value="{{ $key }}">{{ $value }}</option>
@endif
@endforeach
</select>
</div>
@elseif ($isBootstrap)
<div class="rounded-md shadow-sm">
@endif
<select multiple
{{ $filter->getWireMethod("filterComponents.".$filter->getKey()) }}
wire:key="{{ $filter->generateWireKey($tableName, 'multiselectdropdown') }}"
id="{{ $tableName }}-filter-{{ $filter->getKey() }}@if($filter->hasCustomPosition())-{{ $filter->getCustomPosition() }}@endif"
class="{{ $isBootstrap4 ? 'form-control' : 'form-select' }}"
>
@if ($filter->getFirstOption() != "")
{!! $filter->getWireMethod('filterComponents.'.$filter->getKey()) !!} {{
$filterInputAttributes->merge([
'wire:key' => $filter->generateWireKey($tableName, 'multiselectdropdown'),
])
->class([
'block w-full transition duration-150 ease-in-out rounded-md shadow-sm focus:ring focus:ring-opacity-50' => $isTailwind && ($filterInputAttributes['default-styling'] ?? true),
'border-gray-300 focus:border-indigo-300 focus:ring-indigo-200 dark:bg-gray-800 dark:text-white dark:border-gray-600' => $isTailwind && ($filterInputAttributes['default-colors'] ?? true),
'form-control' => $isBootstrap4 && ($filterInputAttributes['default-styling'] ?? true),
'form-select' => $isBootstrap5 && ($filterInputAttributes['default-styling'] ?? true),
])
->except(['default-styling','default-colors'])
}}>
@if ($filter->getFirstOption() !== '')
<option @if($filter->isEmpty($this)) selected @endif value="all">{{ $filter->getFirstOption()}}</option>
@endif
@foreach($filter->getOptions() as $key => $value)
Expand All @@ -47,5 +32,7 @@ class="{{ $isBootstrap4 ? 'form-control' : 'form-select' }}"
@endif
@endforeach
</select>
@if ($isTailwind)
</div>
@endif
</div>
88 changes: 42 additions & 46 deletions resources/views/components/tools/filters/multi-select.blade.php
Original file line number Diff line number Diff line change
Expand Up @@ -2,61 +2,57 @@
<x-livewire-tables::tools.filter-label :$filter :$filterLayout :$tableName :$isTailwind :$isBootstrap4 :$isBootstrap5 :$isBootstrap />

@if ($isTailwind)
<div class="rounded-md shadow-sm">
<div>
<input
type="checkbox"
id="{{ $tableName }}-filter-{{ $filter->getKey() }}-select-all-@if($filter->hasCustomPosition()){{ $filter->getCustomPosition() }}@endif"
wire:input="selectAllFilterOptions('{{ $filter->getKey() }}')"
class="text-indigo-600 rounded border-gray-300 shadow-sm transition duration-150 ease-in-out focus:border-indigo-300 focus:ring focus:ring-indigo-200 focus:ring-opacity-50 dark:bg-gray-900 dark:text-white dark:border-gray-600 dark:hover:bg-gray-600 dark:focus:bg-gray-600 disabled:opacity-50 disabled:cursor-wait"
>
<label for="{{ $tableName }}-filter-{{ $filter->getKey() }}-select-all-@if($filter->hasCustomPosition()){{ $filter->getCustomPosition() }}@endif" class="dark:text-white">
<div class="rounded-md shadow-sm">
@endif
<div @class(['form-check' => $isBootstrap])>
<input id="{{ $tableName }}-filter-{{ $filter->getKey() }}-select-all{{ $filter->hasCustomPosition() ? '-'.$filter->getCustomPosition() : null }}" wire:input="selectAllFilterOptions('{{ $filter->getKey() }}')" {{
$filterInputAttributes->merge([
'type' => 'checkbox'
])
->class([
'rounded shadow-sm transition duration-150 ease-in-out focus:ring focus:ring-opacity-50 disabled:opacity-50 disabled:cursor-wait' => $isTailwind && ($filterInputAttributes['default-styling'] ?? true),
'text-indigo-600 border-gray-300 focus:border-indigo-300 focus:ring-indigo-200 dark:bg-gray-900 dark:text-white dark:border-gray-600 dark:hover:bg-gray-600 dark:focus:bg-gray-600 ' => $isTailwind && ($filterInputAttributes['default-colors'] ?? true),
'form-check-input' => $isBootstrap && ($filterInputAttributes['default-styling'] ?? true),
])
->except(['id','wire:key','value','default-styling','default-colors'])
}}>
<label for="{{ $tableName }}-filter-{{ $filter->getKey() }}-select-all{{ $filter->hasCustomPosition() ? '-'.$filter->getCustomPosition() : null }}" @class([
'dark:text-white' => $isTailwind,
'form-check-label' => $isBootstrap,
])>
@if ($filter->getFirstOption() !== '')
{{ $filter->getFirstOption() }}
@else
{{ __($localisationPath.'All') }}
@endif
</label>
</div>

@foreach($filter->getOptions() as $key => $value)
<div wire:key="{{ $tableName }}-filter-{{ $filter->getKey() }}-multiselect-{{ $key }}-@if($filter->hasCustomPosition()){{ $filter->getCustomPosition() }}@endif">
<input
type="checkbox"
id="{{ $tableName }}-filter-{{ $filter->getKey() }}-{{ $loop->index }}-@if($filter->hasCustomPosition()){{ $filter->getCustomPosition() }}@endif"
value="{{ $key }}"
wire:key="{{ $tableName }}-filter-{{ $filter->getKey() }}-{{ $loop->index }}-@if($filter->hasCustomPosition()){{ $filter->getCustomPosition() }}@endif"
{{ $filter->getWireMethod('filterComponents.'.$filter->getKey()) }}
class="text-indigo-600 rounded border-gray-300 shadow-sm transition duration-150 ease-in-out focus:border-indigo-300 focus:ring focus:ring-indigo-200 focus:ring-opacity-50 dark:bg-gray-900 dark:text-white dark:border-gray-600 dark:hover:bg-gray-600 dark:focus:bg-gray-600 disabled:opacity-50 disabled:cursor-wait"
>
<label for="{{ $tableName }}-filter-{{ $filter->getKey() }}-{{ $loop->index }}-@if($filter->hasCustomPosition()){{ $filter->getCustomPosition() }}@endif" class="dark:text-white">{{ $value }}</label>
</div>
@endforeach
</div>
@elseif ($isBootstrap)
<div class="form-check">
<input
type="checkbox"
id="{{ $tableName }}-filter-{{ $filter->getKey() }}-select-all-@if($filter->hasCustomPosition()){{ $filter->getCustomPosition() }}@endif"
wire:input="selectAllFilterOptions('{{ $filter->getKey() }}')"
class="form-check-input"
>
<label class="form-check-label" for="{{ $tableName }}-filter-{{ $filter->getKey() }}-@if($filter->hasCustomPosition()){{ $filter->getCustomPosition() }}@endif-select-all">{{ __($localisationPath.'All') }}</label>
</label>
</div>

@foreach($filter->getOptions() as $key => $value)
<div class="form-check" wire:key="{{ $tableName }}-filter-{{ $filter->getKey() }}-multiselect-{{ $key }}-@if($filter->hasCustomPosition()){{ $filter->getCustomPosition() }}@endif">
<input
class="form-check-input"
type="checkbox"
id="{{ $tableName }}-filter-{{ $filter->getKey() }}-{{ $loop->index }}-@if($filter->hasCustomPosition()){{ $filter->getCustomPosition() }}@endif"
value="{{ $key }}"
wire:key="{{ $tableName }}-filter-{{ $filter->getKey() }}-{{ $loop->index }}-@if($filter->hasCustomPosition()){{ $filter->getCustomPosition() }}@endif"
{{ $filter->getWireMethod('filterComponents.'.$filter->getKey()) }}

>
<label class="form-check-label" for="{{ $tableName }}-filter-{{ $filter->getKey() }}-{{ $loop->index }}-@if($filter->hasCustomPosition()){{ $filter->getCustomPosition() }}@endif">{{ $value }}</label>
<div @class([
'form-check' => $isBootstrap,
]) wire:key="{{ $tableName }}-filter-{{ $filter->getKey() }}-multiselect-{{ $key }}{{ $filter->hasCustomPosition() ? '-'.$filter->getCustomPosition() : null }}">
<input {!! $filter->getWireMethod('filterComponents.'.$filter->getKey()) !!}
id="{{ $tableName }}-filter-{{ $filter->getKey() }}-{{ $loop->index }}{{ $filter->hasCustomPosition() ? '-'.$filter->getCustomPosition() : null }}"

wire:key="{{ $tableName }}-filter-{{ $filter->getKey() }}-{{ $loop->index }}{{ $filter->hasCustomPosition() ? '-'.$filter->getCustomPosition() : null }}" value="{{ $key }}" {{
$filterInputAttributes->merge([
'type' => 'checkbox'
])
->class([
'rounded shadow-sm transition duration-150 ease-in-out focus:ring focus:ring-opacity-50 disabled:opacity-50 disabled:cursor-wait' => $isTailwind && ($filterInputAttributes['default-styling'] ?? true),
'text-indigo-600 border-gray-300 focus:border-indigo-300 focus:ring-indigo-200 dark:bg-gray-900 dark:text-white dark:border-gray-600 dark:hover:bg-gray-600 dark:focus:bg-gray-600 ' => $isTailwind && ($filterInputAttributes['default-colors'] ?? true),
'form-check-input' => $isBootstrap && ($filterInputAttributes['default-styling'] ?? true),
])
->except(['id','wire:key','value','default-styling','default-colors'])
}}>
<label for="{{ $tableName }}-filter-{{ $filter->getKey() }}-{{ $loop->index }}{{ $filter->hasCustomPosition() ? '-'.$filter->getCustomPosition() : null }}" @class([
'dark:text-white' => $isTailwind,
'form-check-label' => $isBootstrap,
])>{{ $value }}</label>
</div>
@endforeach
@if ($isTailwind)
</div>
@endif
</div>
Loading
Loading