-
Notifications
You must be signed in to change notification settings - Fork 5
/
BindingsTools.java
101 lines (85 loc) · 3.08 KB
/
BindingsTools.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
package org.genericsystem.defaults.tools;
import java.util.ArrayList;
import java.util.List;
import java.util.function.Function;
import java.util.function.Supplier;
import javafx.beans.InvalidationListener;
import javafx.beans.Observable;
import javafx.beans.WeakInvalidationListener;
import javafx.beans.binding.Binding;
import javafx.beans.binding.Bindings;
import javafx.beans.binding.ListBinding;
import javafx.beans.binding.ObjectBinding;
import javafx.beans.value.ObservableValue;
import javafx.collections.FXCollections;
import javafx.collections.ListChangeListener;
import javafx.collections.ObservableList;
import javafx.collections.WeakListChangeListener;
/**
* @author Nicolas Feybesse
*
*/
public class BindingsTools {
public static <U extends Binding<V>, V> U transmitSuccessiveInvalidations(U binding) {
binding.addListener((o, v, nv) -> {
});
return binding;
}
public static <T> Observable create(Observable... observables) {
return transmitSuccessiveInvalidations(Bindings.createObjectBinding(() -> "", observables));
}
public static <T> Observable createTransitive(ObservableValue<T> master, Function<T, Observable[]> slavesFromValue) {
return transmitSuccessiveInvalidations(new ObjectBinding<Object>() {
private Observable[] slaves;
private InvalidationListener onMasterInvalidion = (c) -> onMasterInvalidation();
{
master.addListener(new WeakInvalidationListener(onMasterInvalidion));
onMasterInvalidation();
}
private void onMasterInvalidation() {
unbind(slaves);
invalidate();
bind(slaves = slavesFromValue.apply(master.getValue()));
}
@Override
protected Object computeValue() {
return "";
}
});
}
public static <E> ObservableList<E> createMinimalUnitaryChangesBinding(ObservableList<E> source) {
return new ListBinding<E>() {
private ObservableList<E> internal = FXCollections.observableArrayList();
private ListChangeListener<E> onSrcInvalidation = (c) -> MinimalUnitaryChanges.doMinimalChanges(source, internal);
{
source.addListener(new WeakListChangeListener<>(onSrcInvalidation));
MinimalUnitaryChanges.doMinimalChanges(source, internal);
}
@Override
protected ObservableList<E> computeValue() {
return internal;
}
};
}
public static <E> ObservableList<E> createMinimalUnitaryChangesBinding(ObservableList<E> source, Supplier<List<E>> subElements, Function<E, Observable> slaveSupplier) {
return createMinimalUnitaryChangesBinding(new ListBinding<E>() {
private List<Observable> slaveInvalidators = new ArrayList<>();
private ListChangeListener<E> onSrcInvalidation = (c) -> onSrcInvalidation();
{
source.addListener(new WeakListChangeListener<>(onSrcInvalidation));
onSrcInvalidation();
}
@Override
protected ObservableList<E> computeValue() {
return FXCollections.observableList(subElements.get());
}
void onSrcInvalidation() {
slaveInvalidators.forEach(this::unbind);
slaveInvalidators.clear();
invalidate();
source.forEach(e -> slaveInvalidators.add(slaveSupplier.apply(e)));
slaveInvalidators.forEach(this::bind);
}
});
}
}