Skip to content

Commit 52418c5

Browse files
gselzerctrueden
authored andcommitted
WIP: port threshold namespace
1 parent b5e442b commit 52418c5

11 files changed

Lines changed: 1734 additions & 0 deletions
Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,54 @@
1+
/*
2+
* #%L
3+
* ImageJ software for multidimensional image processing and analysis.
4+
* %%
5+
* Copyright (C) 2014 - 2018 ImageJ developers.
6+
* %%
7+
* Redistribution and use in source and binary forms, with or without
8+
* modification, are permitted provided that the following conditions are met:
9+
*
10+
* 1. Redistributions of source code must retain the above copyright notice,
11+
* this list of conditions and the following disclaimer.
12+
* 2. Redistributions in binary form must reproduce the above copyright notice,
13+
* this list of conditions and the following disclaimer in the documentation
14+
* and/or other materials provided with the distribution.
15+
*
16+
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
17+
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18+
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19+
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS BE
20+
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
21+
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
22+
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
23+
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
24+
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
25+
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
26+
* POSSIBILITY OF SUCH DAMAGE.
27+
* #L%
28+
*/
29+
30+
package net.imagej.ops.threshold;
31+
32+
import net.imglib2.histogram.Histogram1d;
33+
import net.imglib2.type.numeric.RealType;
34+
35+
import org.scijava.ops.core.computer.Computer;
36+
37+
/**
38+
* Abstract superclass of {@link ComputeThresholdHistogram} implementations.
39+
*
40+
* @author Curtis Rueden
41+
*/
42+
public abstract class AbstractComputeThresholdHistogram<T extends RealType<T>>
43+
implements Computer<Histogram1d<T>, T>
44+
{
45+
@Override
46+
public void compute(final Histogram1d<T> input, final T output) {
47+
final long binPos = computeBin(input);
48+
49+
// convert bin number to corresponding gray level
50+
input.getCenterValue(binPos, output);
51+
}
52+
53+
abstract protected long computeBin(final Histogram1d<T> input);
54+
}
Lines changed: 84 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,84 @@
1+
///*
2+
// * #%L
3+
// * ImageJ software for multidimensional image processing and analysis.
4+
// * %%
5+
// * Copyright (C) 2014 - 2018 ImageJ developers.
6+
// * %%
7+
// * Redistribution and use in source and binary forms, with or without
8+
// * modification, are permitted provided that the following conditions are met:
9+
// *
10+
// * 1. Redistributions of source code must retain the above copyright notice,
11+
// * this list of conditions and the following disclaimer.
12+
// * 2. Redistributions in binary form must reproduce the above copyright notice,
13+
// * this list of conditions and the following disclaimer in the documentation
14+
// * and/or other materials provided with the distribution.
15+
// *
16+
// * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
17+
// * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18+
// * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19+
// * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS BE
20+
// * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
21+
// * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
22+
// * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
23+
// * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
24+
// * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
25+
// * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
26+
// * POSSIBILITY OF SUCH DAMAGE.
27+
// * #L%
28+
// */
29+
//
30+
//package net.imagej.ops.threshold;
31+
//
32+
//import net.imagej.ops.Ops;
33+
//import net.imagej.ops.map.neighborhood.AbstractCenterAwareComputerOp;
34+
//import net.imagej.ops.special.computer.BinaryComputerOp;
35+
//import net.imagej.ops.special.computer.UnaryComputerOp;
36+
//import net.imagej.ops.special.function.UnaryFunctionOp;
37+
//import net.imagej.ops.threshold.apply.LocalThreshold;
38+
//import net.imglib2.histogram.Histogram1d;
39+
//import net.imglib2.type.BooleanType;
40+
//import net.imglib2.type.numeric.RealType;
41+
//
42+
///**
43+
// * {@link AbstractCenterAwareComputerOp} for use in {@link LocalThreshold}s.
44+
// *
45+
// * @author Stefan Helfrich (University of Konstanz)
46+
// */
47+
//@Plugin(type = Op.class, name = "threshold.local")
48+
//public abstract class LocalThresholdMethodHistogram<T extends RealType<T>, O extends BooleanType<O>>
49+
// extends AbstractCenterAwareComputerOp<T, O> {
50+
//
51+
// protected UnaryFunctionOp<Iterable<T>, Histogram1d<T>> histCreator;
52+
// protected UnaryComputerOp<Histogram1d<T>, T> thresholdComputer;
53+
// protected BinaryComputerOp<T, T, O> applyThreshold;
54+
//
55+
// @SuppressWarnings({ "unchecked", "rawtypes" })
56+
// @Override
57+
// public void initialize() {
58+
// histCreator = (UnaryFunctionOp) Functions.unary(ops(), Histogram.class, Histogram1d.class,
59+
// in1() == null ? Iterable.class : in1());
60+
//
61+
// thresholdComputer = getThresholdComputer();
62+
// }
63+
//
64+
// @Override
65+
// public void compute(final Iterable<T> neighborhood, final T center, final O output) {
66+
// // TODO Move to initialize when NIL objects are available
67+
// if (applyThreshold == null) {
68+
// applyThreshold = Computers.binary(ops(), Ops.Threshold.Apply.class, output, center, center);
69+
// }
70+
//
71+
// // Compute histogram for neighborhood
72+
// final Histogram1d<T> hist = histCreator.calculate(neighborhood);
73+
//
74+
// // Compute threshold
75+
// final T computedThreshold = center.createVariable();
76+
// thresholdComputer.compute(hist, computedThreshold);
77+
//
78+
// // Apply threshold
79+
// applyThreshold.compute(center, computedThreshold, output);
80+
// }
81+
//
82+
// protected abstract UnaryComputerOp<Histogram1d<T>, T> getThresholdComputer();
83+
//
84+
//}
Lines changed: 108 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,108 @@
1+
/*
2+
* #%L
3+
* ImageJ software for multidimensional image processing and analysis.
4+
* %%
5+
* Copyright (C) 2014 - 2018 ImageJ developers.
6+
* %%
7+
* Redistribution and use in source and binary forms, with or without
8+
* modification, are permitted provided that the following conditions are met:
9+
*
10+
* 1. Redistributions of source code must retain the above copyright notice,
11+
* this list of conditions and the following disclaimer.
12+
* 2. Redistributions in binary form must reproduce the above copyright notice,
13+
* this list of conditions and the following disclaimer in the documentation
14+
* and/or other materials provided with the distribution.
15+
*
16+
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
17+
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18+
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19+
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS BE
20+
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
21+
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
22+
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
23+
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
24+
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
25+
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
26+
* POSSIBILITY OF SUCH DAMAGE.
27+
* #L%
28+
*/
29+
30+
package net.imagej.ops.threshold;
31+
32+
// Ported from Antti Niemisto's HistThresh Matlab toolbox
33+
// Relicensed BSD 2-12-13
34+
35+
/**
36+
* Utility methods used by the various threshold methods.
37+
*
38+
* @author Barry DeZonia
39+
* @author Gabriel Landini
40+
*/
41+
public final class Thresholds {
42+
43+
private Thresholds() {
44+
// NB: Prevent instantiation of utility class.
45+
}
46+
47+
public static boolean bimodalTest(double[] y) {
48+
int len = y.length;
49+
int modes = 0;
50+
51+
for (int k = 1; k < len - 1; k++) {
52+
if (y[k - 1] < y[k] && y[k + 1] < y[k]) {
53+
modes++;
54+
if (modes > 2)
55+
return false;
56+
}
57+
}
58+
return (modes == 2);
59+
}
60+
61+
/**
62+
* The partial sum A from C. A. Glasbey, "An analysis of histogram-based
63+
* thresholding algorithms," CVGIP: Graphical Models and Image Processing,
64+
* vol. 55, pp. 532-537, 1993.
65+
*/
66+
public static double A(long[] y, int j) {
67+
double x = 0;
68+
for (int i = 0; i <= j; i++)
69+
x += y[i];
70+
return x;
71+
}
72+
73+
/**
74+
* The partial sum B from C. A. Glasbey, "An analysis of histogram-based
75+
* thresholding algorithms," CVGIP: Graphical Models and Image Processing,
76+
* vol. 55, pp. 532-537, 1993.
77+
*/
78+
public static double B(long[] y, int j) {
79+
double x = 0;
80+
for (int i = 0; i <= j; i++)
81+
x += y[i] * i;
82+
return x;
83+
}
84+
85+
/**
86+
* The partial sum C from C. A. Glasbey, "An analysis of histogram-based
87+
* thresholding algorithms," CVGIP: Graphical Models and Image Processing,
88+
* vol. 55, pp. 532-537, 1993.
89+
*/
90+
public static double C(long[] y, int j) {
91+
double x = 0;
92+
for (int i = 0; i <= j; i++)
93+
x += y[i] * i * i;
94+
return x;
95+
}
96+
97+
/**
98+
* The partial sum D from C. A. Glasbey, "An analysis of histogram-based
99+
* thresholding algorithms," CVGIP: Graphical Models and Image Processing,
100+
* vol. 55, pp. 532-537, 1993.
101+
*/
102+
public static double D(long[] y, int j) {
103+
double x = 0;
104+
for (int i = 0; i <= j; i++)
105+
x += y[i] * i * i * i;
106+
return x;
107+
}
108+
}
Lines changed: 98 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,98 @@
1+
/*
2+
* #%L
3+
* ImageJ software for multidimensional image processing and analysis.
4+
* %%
5+
* Copyright (C) 2014 - 2018 ImageJ developers.
6+
* %%
7+
* Redistribution and use in source and binary forms, with or without
8+
* modification, are permitted provided that the following conditions are met:
9+
*
10+
* 1. Redistributions of source code must retain the above copyright notice,
11+
* this list of conditions and the following disclaimer.
12+
* 2. Redistributions in binary form must reproduce the above copyright notice,
13+
* this list of conditions and the following disclaimer in the documentation
14+
* and/or other materials provided with the distribution.
15+
*
16+
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
17+
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18+
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19+
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS BE
20+
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
21+
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
22+
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
23+
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
24+
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
25+
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
26+
* POSSIBILITY OF SUCH DAMAGE.
27+
* #L%
28+
*/
29+
30+
package net.imagej.ops.threshold.apply;
31+
32+
import java.util.Comparator;
33+
34+
import net.imglib2.type.logic.BitType;
35+
import net.imglib2.type.numeric.RealType;
36+
37+
import org.scijava.ops.OpDependency;
38+
import org.scijava.ops.core.Op;
39+
import org.scijava.ops.core.computer.BiComputer;
40+
import org.scijava.ops.core.computer.Computer;
41+
import org.scijava.ops.core.computer.Computer3;
42+
import org.scijava.ops.util.Adapt;
43+
import org.scijava.ops.util.Maps;
44+
import org.scijava.param.Parameter;
45+
import org.scijava.plugin.Plugin;
46+
import org.scijava.struct.ItemIO;
47+
48+
/**
49+
* Applies the given threshold value to every element along the given
50+
* {@link Iterable} input.
51+
*
52+
* @author Martin Horn (University of Konstanz)
53+
* @author Christian Dietz (University of Konstanz)
54+
*/
55+
@Plugin(type = Op.class, name = "threshold.apply")
56+
@Parameter(key = "input")
57+
@Parameter(key = "threshold")
58+
@Parameter(key = "comparator")
59+
@Parameter(key = "output", type = ItemIO.BOTH)
60+
public class ApplyConstantThreshold<T extends RealType<T>>
61+
implements Computer3<Iterable<T>, T, Comparator<T>, Iterable<BitType>> {
62+
63+
@OpDependency(name = "threshold.apply")
64+
Computer3<T, T, Comparator<? super T>, BitType> applyThreshold;
65+
66+
// TODO can/should the Comparator be of <? super T> instead of just <T>?
67+
@Override
68+
public void compute(final Iterable<T> input1, final T input2, final Comparator<T> comparator,
69+
final Iterable<BitType> output) {
70+
Computer<T, BitType> thresholdComputer = Adapt.Computers.asComputer(applyThreshold, input2, comparator);
71+
Computer<Iterable<T>, Iterable<BitType>> liftedThreshold = Maps.Computers.Iterables.liftBoth(thresholdComputer);
72+
liftedThreshold.accept(input1, output);
73+
}
74+
75+
}
76+
77+
// -- CONVENIENCE OPS -- //
78+
79+
// If people don't want to / don't know how to make a comparator, they can just
80+
// use this Op. The default comparator just returns true if the input is greater
81+
// than the threshold.
82+
@Plugin(type = Op.class, name = "threshold.apply")
83+
@Parameter(key = "input")
84+
@Parameter(key = "threshold")
85+
@Parameter(key = "output", type = ItemIO.BOTH)
86+
class ApplyConstantThresholdSimple<T extends RealType<T>> implements BiComputer<Iterable<T>, T, Iterable<BitType>> {
87+
88+
@OpDependency(name = "threshold.apply")
89+
Computer3<Iterable<T>, T, Comparator<T>, Iterable<BitType>> applyThreshold;
90+
91+
// TODO can/should the Comparator be of <? super T> instead of just <T>?
92+
@Override
93+
public void compute(final Iterable<T> input1, final T input2, final Iterable<BitType> output) {
94+
95+
applyThreshold.compute(input1, input2, (in1, in2) -> in1.compareTo(in2), output);
96+
}
97+
98+
}

0 commit comments

Comments
 (0)