Skip to content

Commit be8a6f5

Browse files
When the last condition of a filter component is removed, a component event is now fired, telling other filter components that they should add their filter back to the grid.
1 parent 1435036 commit be8a6f5

File tree

1 file changed

+91
-26
lines changed

1 file changed

+91
-26
lines changed

vaadin-simple-grid-filter/src/main/java/software/xdev/vaadin/FilterComponent.java

Lines changed: 91 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,11 @@
4747
import java.util.stream.IntStream;
4848
import java.util.stream.Stream;
4949

50+
import com.vaadin.flow.component.AttachEvent;
51+
import com.vaadin.flow.component.ComponentEvent;
52+
import com.vaadin.flow.component.ComponentUtil;
5053
import com.vaadin.flow.component.Composite;
54+
import com.vaadin.flow.component.DetachEvent;
5155
import com.vaadin.flow.component.ItemLabelGenerator;
5256
import com.vaadin.flow.component.Key;
5357
import com.vaadin.flow.component.UI;
@@ -65,6 +69,7 @@
6569
import com.vaadin.flow.router.BeforeEnterEvent;
6670
import com.vaadin.flow.router.BeforeEnterObserver;
6771
import com.vaadin.flow.router.QueryParameters;
72+
import com.vaadin.flow.shared.Registration;
6873

6974
import software.xdev.vaadin.builder.CustomizableFilterBuilder;
7075
import software.xdev.vaadin.comparators.ContainsComparator;
@@ -369,6 +374,7 @@ private void onAcceptFilter()
369374
final boolean editable;
370375

371376
// Check if it's an initial condition
377+
// Set editable/deletable and the customization degree
372378
if(this.editingBadgeId != null && !this.editingBadgeId.equals(NO_BADGE_ID_STRING))
373379
{
374380
deletable = this.deletingBadgeEnabled;
@@ -396,6 +402,7 @@ private void onAcceptFilter()
396402
editable,
397403
customizationDegree);
398404

405+
// Query parameter
399406
if(!this.identifier.isBlank())
400407
{
401408
if(this.editingBadgeId != null && !this.editingBadgeId.equals(NO_BADGE_ID_STRING))
@@ -478,7 +485,7 @@ private void onAcceptFilter()
478485
});
479486
}
480487

481-
this.deactivateDeleteButtonFromChipComponents(deletableCondition, badge);
488+
this.setBtnDeleteClickListenerWhenConditionShouldBeDeletable(deletableCondition, badge);
482489

483490
// Format chip badge text if it contains LocalDate/LocalDateTime
484491
if(TemporalAccessor.class.isAssignableFrom(badge.getItem().getItem().getType())
@@ -490,12 +497,12 @@ private void onAcceptFilter()
490497
this.chipBadges.add(badge);
491498
this.hlChipBadges.add(badge);
492499

493-
this.updateGridFilter();
500+
this.addFilterConditionToGrid(badge);
494501

495502
return badge;
496503
}
497504

498-
private void deactivateDeleteButtonFromChipComponents(
505+
private void setBtnDeleteClickListenerWhenConditionShouldBeDeletable(
499506
final boolean conditionDeletable,
500507
final ChipBadgeExtension<FilterCondition<T, ?>> badge)
501508
{
@@ -812,32 +819,18 @@ else if(type.isAssignableFrom(Enum.class) || type.isAssignableFrom(Boolean.class
812819
}
813820
}
814821

815-
private void updateGridFilter()
822+
private void addFilterConditionToGrid(final ChipBadgeExtension<FilterCondition<T, ?>> chipBadge)
816823
{
817-
if(this.chipBadges.isEmpty())
818-
{
819-
this.dataGrid.getListDataView().removeFilters();
820-
return;
821-
}
824+
Objects.requireNonNull(chipBadge);
822825

823-
this.dataGrid.getListDataView().setFilter(item ->
826+
this.dataGrid.getListDataView().addFilter(item ->
824827
{
825-
final List<Predicate<T>> predicates = new ArrayList<>();
828+
final FilterCondition<T, ?> item1 = chipBadge.getItem();
829+
final String inputValue = item1.getInputValue();
830+
final Predicate<T> predicate =
831+
item1.getSelectedCondition().compare(item1.getItem().getValueProvider(), inputValue);
826832

827-
for(final ChipBadge<FilterCondition<T, ?>> chipBadge : this.chipBadges)
828-
{
829-
final FilterCondition<T, ?> item1 = chipBadge.getItem();
830-
final String inputValue = item1.getInputValue();
831-
832-
predicates.add(
833-
834-
item1.getSelectedCondition().compare(
835-
item1.getItem().getValueProvider(),
836-
inputValue)
837-
);
838-
}
839-
840-
return predicates.stream().map(p -> p.test(item)).reduce(Boolean::logicalAnd).orElseThrow();
833+
return predicate.test(item);
841834
});
842835
}
843836

@@ -938,10 +931,21 @@ private void removeChipBadgeCondition(final ChipBadgeExtension<FilterCondition<T
938931
{
939932
this.chipBadges.remove(chip);
940933
this.hlChipBadges.remove(chip);
934+
// Have to set all filter when removing a condition again because we cannot remove just one filter from the
935+
// grid
941936
this.updateGridFilter();
942937
this.removeQueryParameter(chip);
943938
}
944939

940+
private void updateGridFilter()
941+
{
942+
// Remove all filters from the grid
943+
this.dataGrid.getListDataView().removeFilters();
944+
// Fire grid removed all filters event
945+
// Every filter component in the current ui should add his filter back again to the grid
946+
ComponentUtil.fireEvent(UI.getCurrent(), new FilterComponentResetGridFilterEvent(this, false));
947+
}
948+
945949
/**
946950
* Sets the internationalization properties for the datePicker.
947951
*
@@ -1289,7 +1293,7 @@ private String createMultipleQueryParameterString()
12891293
/**
12901294
* Method for adding a specific filter condition as query parameter.
12911295
*
1292-
* @param filterCondition The condition which should be converted to query parameter.
1296+
* @param chipBadge The condition which should be converted to query parameter.
12931297
*/
12941298
private void addQueryParameter(final ChipBadgeExtension<FilterCondition<T, ?>> chipBadge)
12951299
{
@@ -1500,4 +1504,65 @@ public FilterComponent<T> withInitialFilter(
15001504

15011505
return filterComponent;
15021506
}
1507+
1508+
// Needed for interacting with other filter components on the same ui
1509+
private Registration registration;
1510+
1511+
@Override
1512+
protected void onAttach(final AttachEvent attachEvent)
1513+
{
1514+
super.onAttach(attachEvent);
1515+
// Register to events from the event bus
1516+
this.registration = ComponentUtil.addListener(
1517+
attachEvent.getUI(),
1518+
FilterComponentResetGridFilterEvent.class,
1519+
event ->
1520+
{
1521+
if(this.chipBadges.isEmpty())
1522+
{
1523+
return;
1524+
}
1525+
1526+
// Get all conditions from filter component and add them to the grid
1527+
this.dataGrid.getListDataView().addFilter(item -> this.isItemMatchingFilter(item, this.chipBadges));
1528+
}
1529+
);
1530+
}
1531+
1532+
private boolean isItemMatchingFilter(
1533+
final T item,
1534+
final List<ChipBadgeExtension<FilterCondition<T, ?>>> chipBadges)
1535+
{
1536+
final List<Predicate<T>> predicates = new ArrayList<>();
1537+
1538+
for(final ChipBadge<FilterCondition<T, ?>> chipBadge : chipBadges)
1539+
{
1540+
final FilterCondition<T, ?> item1 = chipBadge.getItem();
1541+
final String inputValue = item1.getInputValue();
1542+
1543+
predicates.add(
1544+
item1.getSelectedCondition().compare(
1545+
item1.getItem().getValueProvider(),
1546+
inputValue)
1547+
);
1548+
}
1549+
1550+
return predicates.stream().map(p -> p.test(item)).reduce(Boolean::logicalAnd).orElseThrow();
1551+
}
1552+
1553+
@Override
1554+
protected void onDetach(final DetachEvent detachEvent)
1555+
{
1556+
super.onDetach(detachEvent);
1557+
// Unregister from the event bus
1558+
this.registration.remove();
1559+
}
1560+
1561+
private static class FilterComponentResetGridFilterEvent extends ComponentEvent<FilterComponent>
1562+
{
1563+
public FilterComponentResetGridFilterEvent(final FilterComponent source, final boolean fromClient)
1564+
{
1565+
super(source, fromClient);
1566+
}
1567+
}
15031568
}

0 commit comments

Comments
 (0)