Skip to content

Commit

Permalink
Add method to combine filter specs
Browse files Browse the repository at this point in the history
  • Loading branch information
minnerbe committed Dec 6, 2024
1 parent e271569 commit e7903c0
Show file tree
Hide file tree
Showing 3 changed files with 58 additions and 3 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -19,15 +19,14 @@ public class CompositeFilter implements Filter {
// empty constructor required to create instances from specifications
@SuppressWarnings("unused")
public CompositeFilter() {
this((List<Filter>) null);
}

public CompositeFilter(final Filter... filters) {
this(List.of(filters));
}

public CompositeFilter(final List<Filter> filters) {
this.filters = filters;
this.filters = new ArrayList<>(filters);
}

@Override
Expand All @@ -50,7 +49,7 @@ public Map<String, String> toParametersMap() {
return map;
}

private static String filterKey(final int i) {
static String filterKey(final int i) {
return "filter" + i;
}

Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package org.janelia.alignment.filter;

import java.io.Serializable;
import java.util.HashMap;
import java.util.Map;

import org.janelia.alignment.json.JsonUtils;
Expand Down Expand Up @@ -96,6 +97,33 @@ public static FilterSpec forFilter(final Filter filter) {
return new FilterSpec(filter.getClass().getName(), filter.toParametersMap());
}

public static FilterSpec combine(final FilterSpec first, final FilterSpec second) {
if (first == null || second == null) {
return first == null ? second : first;
}

final FilterSpec firstAsComposite = asCompositeSpec(first);
final FilterSpec secondAsComposite = asCompositeSpec(second);

// both are guaranteed to be composite filters -> unpack both, append, and repack
final Map<String, String> parameters = new HashMap<>(firstAsComposite.parameters);
final int shift = firstAsComposite.parameters.size();
for (int i = 0; i < secondAsComposite.parameters.size(); i++) {
final String key = CompositeFilter.filterKey(i + shift);
final String value = secondAsComposite.parameters.get(CompositeFilter.filterKey(i));
parameters.put(key, value);
}
return new FilterSpec(CompositeFilter.class.getName(), parameters);
}

private static FilterSpec asCompositeSpec(final FilterSpec filterSpec) {
if (filterSpec.className.equals(CompositeFilter.class.getName())) {
return filterSpec;
}
return new FilterSpec(CompositeFilter.class.getName(),
Map.of(CompositeFilter.filterKey(0), filterSpec.toJson()));
}

private Class<?> getClazz() throws IllegalArgumentException {
if (clazz == null) {
if (className == null) {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package org.janelia.alignment.filter;

import org.janelia.alignment.filter.emshading.QuadraticShading;
import org.junit.Assert;
import org.junit.Test;

Expand Down Expand Up @@ -75,4 +76,31 @@ private static Filter parseAndBuildFilter(final FilterSpec filterSpec) {
return parsedSpec.buildInstance();
}

@SuppressWarnings("DataFlowIssue")
@Test
public void compositeFilterSpecBuildsCorrectly() {
FilterSpec first = getTestFilterSpec(1);
FilterSpec second = getTestFilterSpec(2);

// combine filters in all possible ways
first = FilterSpec.combine(first, null);
second = FilterSpec.combine(null, second);

FilterSpec accumulate = FilterSpec.combine(first, second);

accumulate = FilterSpec.combine(first, accumulate);
accumulate = FilterSpec.combine(accumulate, second);

accumulate = FilterSpec.combine(accumulate, accumulate);

// check if it can be built and has the correct number of parameters
final Filter recoveredFilter = accumulate.buildInstance();
Assert.assertEquals(8, recoveredFilter.toParametersMap().size());
}

private static FilterSpec getTestFilterSpec(final int i) {
final QuadraticShading quadraticShading = new QuadraticShading(new double[]{i, 0, 0, 0, 0, 0});
final Filter filter = new ShadingCorrectionFilter(quadraticShading);
return FilterSpec.forFilter(filter);
}
}

0 comments on commit e7903c0

Please sign in to comment.