def __init__(self, *args, **kwargs):
        super(OpNansheGenerateDictionaryCached, self).__init__(*args, **kwargs)

        self.opDictionary = OpNansheGenerateDictionary(parent=self)

        self.opDictionary.K.connect(self.K)
        self.opDictionary.Gamma1.connect(self.Gamma1)
        self.opDictionary.Gamma2.connect(self.Gamma2)
        self.opDictionary.NumThreads.connect(self.NumThreads)
        self.opDictionary.Batchsize.connect(self.Batchsize)
        self.opDictionary.NumIter.connect(self.NumIter)
        self.opDictionary.Lambda1.connect(self.Lambda1)
        self.opDictionary.Lambda2.connect(self.Lambda2)
        self.opDictionary.PosAlpha.connect(self.PosAlpha)
        self.opDictionary.PosD.connect(self.PosD)
        self.opDictionary.Clean.connect(self.Clean)
        self.opDictionary.Mode.connect(self.Mode)
        self.opDictionary.ModeD.connect(self.ModeD)

        self.opCache = OpArrayCache(parent=self)
        self.opCache.fixAtCurrent.setValue(False)

        self.opDictionary.Input.connect(self.Input)
        self.opCache.Input.connect(self.opDictionary.Output)
        self.CleanBlocks.connect(self.opCache.CleanBlocks)
        self.Output.connect(self.opCache.Output)
Esempio n. 2
0
    def test(self):
        """
        Test use-case from https://github.com/ilastik/lazyflow/issues/111
        """
        data = numpy.zeros((20, 20))
        data = numpy.ma.masked_array(data,
                                     mask=numpy.ma.getmaskarray(data),
                                     fill_value=numpy.nan,
                                     shrink=False)
        data[...] = numpy.ma.masked
        op = OpArrayCache(graph=Graph())
        op.Input.meta.axistags = vigra.defaultAxistags('xy')
        op.Input.meta.has_mask = True
        op.Input.setValue(data)

        result_before = op.Output[0:20, 0:20].wait()

        assert result_before.astype(bool).filled(True).all()
        assert (result_before.mask == True).all()
        assert numpy.isnan(result_before.fill_value)

        # Should not crash...
        new_data = numpy.ones((20, 20))
        new_data = numpy.ma.masked_array(new_data,
                                         mask=numpy.ma.getmaskarray(new_data),
                                         fill_value=0,
                                         shrink=False)
        op.Input[0:20, 0:20] = new_data

        result_after = op.Output[0:20, 0:20].wait()

        assert (result_after == 1).all()
        assert (result_after.mask == False).all()
        assert (result_after.fill_value == 0).all()
    def __init__(self, *args, **kwargs):
        super(OpNanshePostprocessDataCached, self).__init__(*args, **kwargs)

        self.opPostprocessing = OpNanshePostprocessData(parent=self)

        self.opPostprocessing.SignificanceThreshold.connect(
            self.SignificanceThreshold)
        self.opPostprocessing.WaveletTransformScale.connect(
            self.WaveletTransformScale)
        self.opPostprocessing.NoiseThreshold.connect(self.NoiseThreshold)
        self.opPostprocessing.AcceptedRegionShapeConstraints_MajorAxisLength_Min.connect(
            self.AcceptedRegionShapeConstraints_MajorAxisLength_Min)
        self.opPostprocessing.AcceptedRegionShapeConstraints_MajorAxisLength_Min_Enabled.connect(
            self.AcceptedRegionShapeConstraints_MajorAxisLength_Min_Enabled)
        self.opPostprocessing.AcceptedRegionShapeConstraints_MajorAxisLength_Max.connect(
            self.AcceptedRegionShapeConstraints_MajorAxisLength_Max)
        self.opPostprocessing.AcceptedRegionShapeConstraints_MajorAxisLength_Max_Enabled.connect(
            self.AcceptedRegionShapeConstraints_MajorAxisLength_Max_Enabled)
        self.opPostprocessing.PercentagePixelsBelowMax.connect(
            self.PercentagePixelsBelowMax)
        self.opPostprocessing.MinLocalMaxDistance.connect(
            self.MinLocalMaxDistance)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Area_Min.connect(
            self.AcceptedNeuronShapeConstraints_Area_Min)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Area_Min_Enabled.connect(
            self.AcceptedNeuronShapeConstraints_Area_Min_Enabled)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Area_Max.connect(
            self.AcceptedNeuronShapeConstraints_Area_Max)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Area_Max_Enabled.connect(
            self.AcceptedNeuronShapeConstraints_Area_Max_Enabled)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Eccentricity_Min.connect(
            self.AcceptedNeuronShapeConstraints_Eccentricity_Min)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Eccentricity_Min_Enabled.connect(
            self.AcceptedNeuronShapeConstraints_Eccentricity_Min_Enabled)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Eccentricity_Max.connect(
            self.AcceptedNeuronShapeConstraints_Eccentricity_Max)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Eccentricity_Max_Enabled.connect(
            self.AcceptedNeuronShapeConstraints_Eccentricity_Max_Enabled)
        self.opPostprocessing.AlignmentMinThreshold.connect(
            self.AlignmentMinThreshold)
        self.opPostprocessing.OverlapMinThreshold.connect(
            self.OverlapMinThreshold)
        self.opPostprocessing.Fuse_FractionMeanNeuronMaxThreshold.connect(
            self.Fuse_FractionMeanNeuronMaxThreshold)

        self.opCache = OpArrayCache(parent=self)
        self.opCache.fixAtCurrent.setValue(False)
        self.CleanBlocks.connect(self.opCache.CleanBlocks)

        self.opPostprocessing.Input.connect(self.Input)
        self.opCache.Input.connect(self.opPostprocessing.Output)
        self.Output.connect(self.opCache.Output)

        self.opColorizeLabelImage = OpColorizeLabelImage(parent=self)
        self.opColorizeLabelImage.Input.connect(self.Output)
        self.ColorizedOutput.connect(self.opColorizeLabelImage.Output)
Esempio n. 4
0
    def __init__(self, block_roi, halo_padding, *args, **kwargs):
        super(self.__class__, self).__init__(*args, **kwargs)

        self.block_roi = block_roi  # In global coordinates
        self._halo_padding = halo_padding

        self._opBinarySubRegion = OpSubRegion(parent=self)
        self._opBinarySubRegion.Input.connect(self.BinaryImage)

        self._opRawSubRegion = OpSubRegion(parent=self)
        self._opRawSubRegion.Input.connect(self.RawImage)

        self._opExtract = OpObjectExtraction(parent=self)
        self._opExtract.BinaryImage.connect(self._opBinarySubRegion.Output)
        self._opExtract.RawImage.connect(self._opRawSubRegion.Output)
        self._opExtract.Features.connect(self.SelectedFeatures)
        self.BlockwiseRegionFeatures.connect(
            self._opExtract.BlockwiseRegionFeatures)

        self._opExtract._opRegFeats._opCache.name = "blockwise-regionfeats-cache"

        self._opPredict = OpObjectPredict(parent=self)
        self._opPredict.Features.connect(self._opExtract.RegionFeatures)
        self._opPredict.SelectedFeatures.connect(self.SelectedFeatures)
        self._opPredict.Classifier.connect(self.Classifier)
        self._opPredict.LabelsCount.connect(self.LabelsCount)
        self.ObjectwisePredictions.connect(self._opPredict.Predictions)

        self._opPredictionImage = OpRelabelSegmentation(parent=self)
        self._opPredictionImage.Image.connect(self._opExtract.LabelImage)
        self._opPredictionImage.Features.connect(
            self._opExtract.RegionFeatures)
        self._opPredictionImage.ObjectMap.connect(self._opPredict.Predictions)

        self._opPredictionCache = OpArrayCache(parent=self)
        self._opPredictionCache.Input.connect(self._opPredictionImage.Output)

        self._opProbabilityChannelsToImage = OpMultiRelabelSegmentation(
            parent=self)
        self._opProbabilityChannelsToImage.Image.connect(
            self._opExtract.LabelImage)
        self._opProbabilityChannelsToImage.ObjectMaps.connect(
            self._opPredict.ProbabilityChannels)
        self._opProbabilityChannelsToImage.Features.connect(
            self._opExtract.RegionFeatures)

        self._opProbabilityChannelStacker = OpMultiArrayStacker(parent=self)
        self._opProbabilityChannelStacker.Images.connect(
            self._opProbabilityChannelsToImage.Output)
        self._opProbabilityChannelStacker.AxisFlag.setValue('c')

        self._opProbabilityCache = OpArrayCache(parent=self)
        self._opProbabilityCache.Input.connect(
            self._opProbabilityChannelStacker.Output)
Esempio n. 5
0
    def __init__(self, *args, **kwargs):
        super(OpMaskedWatershed, self).__init__(*args, **kwargs)

        # Use an internal operator to prepare the data,
        #  for easy caching/parallelization.
        self._opPrepInput = _OpPrepWatershedInput(parent=self)
        self._opPrepInput.Input.connect(self.Input)
        self._opPrepInput.Mask.connect(self.Mask)

        self._opPreppedInputCache = OpArrayCache(parent=self)
        self._opPreppedInputCache.Input.connect(self._opPrepInput.Output)
Esempio n. 6
0
 def test(self):
     """
     Test use-case from https://github.com/ilastik/lazyflow/issues/111
     """
     data = numpy.zeros((20,20))
     data = vigra.taggedView(data, 'xy')
     op = OpArrayCache(graph=Graph())
     op.Input.setValue(data)
     
     # Should not crash...
     op.Input[0:20,0:20] = numpy.ones((20,20))
Esempio n. 7
0
    def test(self):
        """
        Test use-case from https://github.com/ilastik/lazyflow/issues/111
        """
        data = numpy.zeros((20, 20))
        data = vigra.taggedView(data, 'xy')
        op = OpArrayCache(graph=Graph())
        op.Input.setValue(data)

        # Should not crash...
        op.Input[0:20, 0:20] = numpy.ones((20, 20))
Esempio n. 8
0
    def __init__(self, *args, **kwargs):
        super(OpPreprocessing, self).__init__(*args, **kwargs)
        self._prepData = [None]
        self.applet = self.parent.parent.preprocessingApplet

        self._unsavedData = False  # set to True if data is not yet saved
        self._dirty = False  # set to True if any Input is dirty

        self.initialSigma = None  # save settings of last preprocess
        self.initialFilter = None  # applied to gui by pressing reset

        self._opFilter = OpFilter(parent=self)
        self._opFilter.Input.connect(self.InputData)
        self._opFilter.Sigma.connect(self.Sigma)
        self._opFilter.Filter.connect(self.Filter)

        self._opFilterNormalize = OpNormalize255(parent=self)
        self._opFilterNormalize.Input.connect(self._opFilter.Output)

        self._opFilterCache = OpArrayCache(parent=self)

        self._opWatershed = OpSimpleWatershed(parent=self)

        self._opWatershedCache = OpArrayCache(parent=self)

        self._opOverlayFilter = OpFilter(parent=self)
        self._opOverlayFilter.Input.connect(self.OverlayData)
        self._opOverlayFilter.Sigma.connect(self.Sigma)

        self._opOverlayNormalize = OpNormalize255(parent=self)
        self._opOverlayNormalize.Input.connect(self._opOverlayFilter.Output)

        self._opInputFilter = OpFilter(parent=self)
        self._opInputFilter.Input.connect(self.InputData)
        self._opInputFilter.Sigma.connect(self.Sigma)

        self._opInputNormalize = OpNormalize255(parent=self)
        self._opInputNormalize.Input.connect(self._opInputFilter.Output)

        self._opMstProvider = OpMstSegmentorProvider(self.applet, parent=self)
        self._opMstProvider.Image.connect(self._opFilterCache.Output)
        self._opMstProvider.LabelImage.connect(self._opWatershedCache.Output)

        self._opWatershedSourceCache = OpArrayCache(parent=self)

        #self.PreprocessedData.connect( self._opMstProvider.MST )

        # Display slots
        self.FilteredImage.connect(self._opFilterCache.Output)
        self.WatershedImage.connect(self._opWatershedCache.Output)

        self.InputData.notifyReady(self._checkConstraints)
Esempio n. 9
0
    def testCleanup(self):
        try:
            ArrayCacheMemoryMgr.instance.pause()
            op = OpArrayCache(graph=self.opProvider.graph)
            op.Input.connect(self.opProvider.Output)
            x = op.Output[...].wait()
            op.Input.disconnect()
            op.cleanUp()

            r = weakref.ref(op)
            del op
            gc.collect()
            assert r() is None, "OpArrayCache was not cleaned up correctly"
        finally:
            ArrayCacheMemoryMgr.instance.unpause()
Esempio n. 10
0
    def test(self):
        class SpecialNumber(object):
            def __init__(self, x):
                self.n = x

        data = numpy.ndarray(shape=(2, 3), dtype=object)
        data = numpy.ma.masked_array(data,
                                     mask=numpy.ma.getmaskarray(data),
                                     fill_value=None,
                                     shrink=False)
        for i in range(2):
            for j in range(3):
                data[i, j] = SpecialNumber(i * j)
        data[1, 1] = numpy.ma.masked

        graph = Graph()
        op = OpArrayCache(graph=graph)
        op.Input.meta.axistags = vigra.defaultAxistags('tc')
        op.Input.meta.has_mask = True
        op.Input.setValue(data)
        op.blockShape.setValue((1, 3))
        assert op.Output.meta.shape == (2, 3)
        assert op.Output.meta.has_mask == True
        outputData = op.Output[...].wait()
        outputData2 = numpy.ma.masked_array(data,
                                            mask=numpy.ma.getmaskarray(data),
                                            fill_value=None,
                                            shrink=False)
        op.Output[...].writeInto(outputData2).wait()

        assert (outputData == data).all()
        assert (outputData.mask == data.mask).all()
        assert (outputData.fill_value == data.fill_value)
    def __init__(self, *args, **kwargs):
        super( OpNanshePreprocessDataCached, self ).__init__( *args, **kwargs )

        self.opConvertType = OpConvertTypeCached(parent=self)
        self.opConvertType.Dtype.setValue(numpy.float32)

        self.opNansheRemoveZeroedLines = OpNansheRemoveZeroedLinesCached(parent=self)
        self.opNansheRemoveZeroedLines.ErosionShape.connect(self.ErosionShape)
        self.opNansheRemoveZeroedLines.DilationShape.connect(self.DilationShape)

        self.opNansheExtractF0 = OpNansheExtractF0Cached(parent=self)
        self.opNansheExtractF0.HalfWindowSize.connect(self.HalfWindowSize)
        self.opNansheExtractF0.WhichQuantile.connect(self.WhichQuantile)
        self.opNansheExtractF0.TemporalSmoothingGaussianFilterStdev.connect(self.TemporalSmoothingGaussianFilterStdev)
        self.opNansheExtractF0.SpatialSmoothingGaussianFilterStdev.connect(self.SpatialSmoothingGaussianFilterStdev)
        self.opNansheExtractF0.TemporalSmoothingGaussianFilterWindowSize.connect(self.TemporalSmoothingGaussianFilterWindowSize)
        self.opNansheExtractF0.SpatialSmoothingGaussianFilterWindowSize.connect(self.SpatialSmoothingGaussianFilterWindowSize)
        self.opNansheExtractF0.BiasEnabled.connect(self.BiasEnabled)
        self.opNansheExtractF0.Bias.connect(self.Bias)

        self.opNansheWaveletTransform = OpNansheWaveletTransformCached(parent=self)
        self.opNansheWaveletTransform.Scale.connect(self.Scale)


        self.OpNansheRemoveZeroedLinesOutput.connect(self.opNansheRemoveZeroedLines.Output)
        self.OpNansheExtractF0_dF_F_Output.connect(self.opNansheExtractF0.dF_F)
        self.OpNansheExtractF0_F0_Output.connect(self.opNansheExtractF0.F0)
        self.OpNansheWaveletTransformOutput.connect(self.opNansheWaveletTransform.Output)

        self.opCache = OpArrayCache(parent=self)
        self.opCache.fixAtCurrent.setValue(False)
        self.CleanBlocks.connect(self.opCache.CleanBlocks)

        self.CacheOutput.connect(self.opCache.Output)
    def __init__(self, *args, **kwargs):
        super( OpNansheGenerateDictionaryCached, self ).__init__( *args, **kwargs )

        self.opDictionary = OpNansheGenerateDictionary(parent=self)

        self.opDictionary.K.connect(self.K)
        self.opDictionary.Gamma1.connect(self.Gamma1)
        self.opDictionary.Gamma2.connect(self.Gamma2)
        self.opDictionary.NumThreads.connect(self.NumThreads)
        self.opDictionary.Batchsize.connect(self.Batchsize)
        self.opDictionary.NumIter.connect(self.NumIter)
        self.opDictionary.Lambda1.connect(self.Lambda1)
        self.opDictionary.Lambda2.connect(self.Lambda2)
        self.opDictionary.PosAlpha.connect(self.PosAlpha)
        self.opDictionary.PosD.connect(self.PosD)
        self.opDictionary.Clean.connect(self.Clean)
        self.opDictionary.Mode.connect(self.Mode)
        self.opDictionary.ModeD.connect(self.ModeD)


        self.opCache = OpArrayCache(parent=self)
        self.opCache.fixAtCurrent.setValue(False)

        self.opDictionary.Input.connect( self.Input )
        self.opCache.Input.connect( self.opDictionary.Output )
        self.CleanBlocks.connect( self.opCache.CleanBlocks )
        self.Output.connect( self.opCache.Output )
Esempio n. 13
0
    def __init__(self, *args, **kwargs):
        super(OpPredictionPipeline, self).__init__(*args, **kwargs)

        # Random forest prediction using CACHED features.
        self.predict = OpPredictCounter(parent=self)
        self.predict.name = "OpPredictCounter"
        self.predict.inputs['Classifier'].connect(self.Classifier)
        self.predict.inputs['Image'].connect(self.CachedFeatureImages)
        self.predict.inputs['LabelsCount'].connect(self.MaxLabel)
        self.PredictionProbabilities.connect(self.predict.PMaps)

        # Prediction cache for the GUI
        self.prediction_cache_gui = OpArrayCache(parent=self)
        self.prediction_cache_gui.name = "prediction_cache_gui"
        self.prediction_cache_gui.inputs["fixAtCurrent"].connect(
            self.FreezePredictions)
        self.prediction_cache_gui.inputs["Input"].connect(self.predict.PMaps)
        self.prediction_cache_gui.blockShape.setValue(128)

        ## Also provide each prediction channel as a separate layer (for the GUI)
        self.opUncertaintyEstimator = OpEnsembleMargin(parent=self)
        self.opUncertaintyEstimator.Input.connect(
            self.prediction_cache_gui.Output)

        ## Cache the uncertainty so we get zeros for uncomputed points
        self.opUncertaintyCache = OpArrayCache(parent=self)
        self.opUncertaintyCache.name = "opUncertaintyCache"
        self.opUncertaintyCache.blockShape.setValue(128)
        self.opUncertaintyCache.Input.connect(
            self.opUncertaintyEstimator.Output)
        self.opUncertaintyCache.fixAtCurrent.connect(self.FreezePredictions)
        self.UncertaintyEstimate.connect(self.opUncertaintyCache.Output)

        self.meaner = OpMean(parent=self)
        self.meaner.Input.connect(self.prediction_cache_gui.Output)

        self.precomputed_predictions_gui = OpPrecomputedInput(
            ignore_dirty_input=False, parent=self)
        self.precomputed_predictions_gui.name = "precomputed_predictions_gui"
        self.precomputed_predictions_gui.SlowInput.connect(self.meaner.Output)
        self.precomputed_predictions_gui.PrecomputedInput.connect(
            self.PredictionsFromDisk)
        self.CachedPredictionProbabilities.connect(
            self.precomputed_predictions_gui.Output)
    def __init__(self, *args, **kwargs):
        super(OpNanshePreprocessDataCached, self).__init__(*args, **kwargs)

        self.opConvertType = OpConvertTypeCached(parent=self)
        self.opConvertType.Dtype.setValue(numpy.float32)

        self.opNansheRemoveZeroedLines = OpNansheRemoveZeroedLinesCached(
            parent=self)
        self.opNansheRemoveZeroedLines.ErosionShape.connect(self.ErosionShape)
        self.opNansheRemoveZeroedLines.DilationShape.connect(
            self.DilationShape)

        self.opNansheExtractF0 = OpNansheExtractF0Cached(parent=self)
        self.opNansheExtractF0.HalfWindowSize.connect(self.HalfWindowSize)
        self.opNansheExtractF0.WhichQuantile.connect(self.WhichQuantile)
        self.opNansheExtractF0.TemporalSmoothingGaussianFilterStdev.connect(
            self.TemporalSmoothingGaussianFilterStdev)
        self.opNansheExtractF0.SpatialSmoothingGaussianFilterStdev.connect(
            self.SpatialSmoothingGaussianFilterStdev)
        self.opNansheExtractF0.TemporalSmoothingGaussianFilterWindowSize.connect(
            self.TemporalSmoothingGaussianFilterWindowSize)
        self.opNansheExtractF0.SpatialSmoothingGaussianFilterWindowSize.connect(
            self.SpatialSmoothingGaussianFilterWindowSize)
        self.opNansheExtractF0.BiasEnabled.connect(self.BiasEnabled)
        self.opNansheExtractF0.Bias.connect(self.Bias)

        self.opNansheWaveletTransform = OpNansheWaveletTransformCached(
            parent=self)
        self.opNansheWaveletTransform.Scale.connect(self.Scale)

        self.OpNansheRemoveZeroedLinesOutput.connect(
            self.opNansheRemoveZeroedLines.Output)
        self.OpNansheExtractF0_dF_F_Output.connect(self.opNansheExtractF0.dF_F)
        self.OpNansheExtractF0_F0_Output.connect(self.opNansheExtractF0.F0)
        self.OpNansheWaveletTransformOutput.connect(
            self.opNansheWaveletTransform.Output)

        self.opCache = OpArrayCache(parent=self)
        self.opCache.fixAtCurrent.setValue(False)
        self.CleanBlocks.connect(self.opCache.CleanBlocks)

        self.CacheOutput.connect(self.opCache.Output)
Esempio n. 15
0
    def test(self):
        """
        Test use-case from https://github.com/ilastik/lazyflow/issues/111
        """
        data = numpy.zeros((20,20))
        data = numpy.ma.masked_array(data,
                                     mask=numpy.ma.getmaskarray(data),
                                     fill_value=numpy.nan,
                                     shrink=False
        )
        data[...] = numpy.ma.masked
        op = OpArrayCache(graph=Graph())
        op.Input.meta.axistags = vigra.defaultAxistags('xy')
        op.Input.meta.has_mask = True
        op.Input.setValue(data)

        result_before = op.Output[0:20,0:20].wait()

        assert result_before.astype(bool).filled(True).all()
        assert (result_before.mask == True).all()
        assert numpy.isnan(result_before.fill_value)


        # Should not crash...
        new_data = numpy.ones((20,20))
        new_data = numpy.ma.masked_array(
            new_data, mask=numpy.ma.getmaskarray(new_data),
            fill_value=0,
            shrink=False
        )
        op.Input[0:20,0:20] = new_data

        result_after = op.Output[0:20,0:20].wait()

        assert (result_after == 1).all()
        assert (result_after.mask == False).all()
        assert (result_after.fill_value == 0).all()
Esempio n. 16
0
    def setUp(self):
        self.dataShape = (1, 100, 100, 10, 1)
        self.data = (numpy.random.random(self.dataShape) * 100).astype(int)
        self.data = self.data.view(vigra.VigraArray)
        self.data.axistags = vigra.defaultAxistags('txyzc')

        graph = Graph()
        opProvider = OpArrayPiperWithAccessCount(graph=graph)
        opProvider.Input.setValue(self.data)
        self.opProvider = opProvider

        opCache = OpArrayCache(graph=graph)
        opCache.Input.connect(opProvider.Output)
        opCache.blockShape.setValue((10, 10, 10, 10, 10))
        opCache.fixAtCurrent.setValue(False)
        self.opCache = opCache
    def __init__(self, *args, **kwargs):
        super(OpCachedRegionFeatures, self).__init__(*args, **kwargs)

        # Hook up the labeler
        self._opRegionFeatures = OpRegionFeatures(parent=self)
        self._opRegionFeatures.RawImage.connect(self.RawImage)
        self._opRegionFeatures.LabelImage.connect(self.LabelImage)
        self._opRegionFeatures.Features.connect(self.Features)

        # Hook up the cache.
        self._opCache = OpArrayCache(parent=self)
        self._opCache.Input.connect(self._opRegionFeatures.Output)

        # Hook up our output slots
        self.Output.connect(self._opCache.Output)
        self.CleanBlocks.connect(self._opCache.CleanBlocks)
Esempio n. 18
0
    def __init__(self, *args, **kwargs):
        super(OpCachedDivisionFeatures, self).__init__(*args, **kwargs)

        # Hook up the labeler
        self._opDivisionFeatures = OpDivisionFeatures(parent=self)        
        self._opDivisionFeatures.LabelVolume.connect(self.LabelImage)
        self._opDivisionFeatures.DivisionFeatureNames.connect(self.DivisionFeatureNames)
        self._opDivisionFeatures.RegionFeaturesVigra.connect(self.RegionFeaturesVigra)

        # Hook up the cache.
        self._opCache = OpArrayCache(parent=self)
        self._opCache.name = "OpCachedDivisionFeatures._opCache"
        self._opCache.Input.connect(self._opDivisionFeatures.BlockwiseDivisionFeatures)

        # Hook up our output slots
        self.Output.connect(self._opCache.Output)
        self.CleanBlocks.connect(self._opCache.CleanBlocks)
Esempio n. 19
0
    def test(self):
        class SpecialNumber(object):
            def __init__(self, x):
                self.n = x

        data = numpy.ndarray(shape=(2, 3), dtype=object)
        data = data.view(vigra.VigraArray)
        data.axistags = vigra.defaultAxistags('tc')
        for i in range(2):
            for j in range(3):
                data[i, j] = SpecialNumber(i * j)

        graph = Graph()
        op = OpArrayCache(graph=graph)
        op.Input.setValue(data)
        op.blockShape.setValue((1, 3))
        assert op.Output.meta.shape == (2, 3)
        outputData = op.Output[:].wait()

        # Can't use (outputData == data).all() here because vigra doesn't do the right thing if dtype is object.
        for x, y in zip(outputData.flat, data.flat):
            assert x == y
Esempio n. 20
0
    def setUp(self):
        self.dataShape = (1, 100, 100, 10, 1)
        self.data = (numpy.random.random(self.dataShape) * 100).astype(int)
        self.data = numpy.ma.masked_array(self.data,
                                          mask=numpy.ma.getmaskarray(
                                              self.data),
                                          fill_value=numpy.iinfo(int).max,
                                          shrink=False)
        self.data[:, 0] = numpy.ma.masked

        graph = Graph()
        opProvider = OpArrayPiperWithAccessCount(graph=graph)
        opProvider.Input.meta.axistags = vigra.defaultAxistags('txyzc')
        opProvider.Input.meta.has_mask = True
        opProvider.Input.setValue(self.data)
        self.opProvider = opProvider

        opCache = OpArrayCache(graph=graph)
        opCache.Input.connect(opProvider.Output)
        opCache.blockShape.setValue((10, 10, 10, 10, 10))
        opCache.fixAtCurrent.setValue(False)
        self.opCache = opCache
    def __init__(self, *args, **kwargs):
        super( OpNanshePostprocessDataCached, self ).__init__( *args, **kwargs )

        self.opPostprocessing = OpNanshePostprocessData(parent=self)

        self.opPostprocessing.SignificanceThreshold.connect(self.SignificanceThreshold)
        self.opPostprocessing.WaveletTransformScale.connect(self.WaveletTransformScale)
        self.opPostprocessing.NoiseThreshold.connect(self.NoiseThreshold)
        self.opPostprocessing.AcceptedRegionShapeConstraints_MajorAxisLength_Min.connect(self.AcceptedRegionShapeConstraints_MajorAxisLength_Min)
        self.opPostprocessing.AcceptedRegionShapeConstraints_MajorAxisLength_Min_Enabled.connect(self.AcceptedRegionShapeConstraints_MajorAxisLength_Min_Enabled)
        self.opPostprocessing.AcceptedRegionShapeConstraints_MajorAxisLength_Max.connect(self.AcceptedRegionShapeConstraints_MajorAxisLength_Max)
        self.opPostprocessing.AcceptedRegionShapeConstraints_MajorAxisLength_Max_Enabled.connect(self.AcceptedRegionShapeConstraints_MajorAxisLength_Max_Enabled)
        self.opPostprocessing.PercentagePixelsBelowMax.connect(self.PercentagePixelsBelowMax)
        self.opPostprocessing.MinLocalMaxDistance.connect(self.MinLocalMaxDistance)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Area_Min.connect(self.AcceptedNeuronShapeConstraints_Area_Min)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Area_Min_Enabled.connect(self.AcceptedNeuronShapeConstraints_Area_Min_Enabled)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Area_Max.connect(self.AcceptedNeuronShapeConstraints_Area_Max)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Area_Max_Enabled.connect(self.AcceptedNeuronShapeConstraints_Area_Max_Enabled)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Eccentricity_Min.connect(self.AcceptedNeuronShapeConstraints_Eccentricity_Min)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Eccentricity_Min_Enabled.connect(self.AcceptedNeuronShapeConstraints_Eccentricity_Min_Enabled)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Eccentricity_Max.connect(self.AcceptedNeuronShapeConstraints_Eccentricity_Max)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Eccentricity_Max_Enabled.connect(self.AcceptedNeuronShapeConstraints_Eccentricity_Max_Enabled)
        self.opPostprocessing.AlignmentMinThreshold.connect(self.AlignmentMinThreshold)
        self.opPostprocessing.OverlapMinThreshold.connect(self.OverlapMinThreshold)
        self.opPostprocessing.Fuse_FractionMeanNeuronMaxThreshold.connect(self.Fuse_FractionMeanNeuronMaxThreshold)


        self.opCache = OpArrayCache(parent=self)
        self.opCache.fixAtCurrent.setValue(False)
        self.CleanBlocks.connect( self.opCache.CleanBlocks )

        self.opPostprocessing.Input.connect( self.Input )
        self.opCache.Input.connect( self.opPostprocessing.Output )
        self.Output.connect( self.opCache.Output )

        self.opColorizeLabelImage = OpColorizeLabelImage(parent=self)
        self.opColorizeLabelImage.Input.connect(self.Output)
        self.ColorizedOutput.connect(self.opColorizeLabelImage.Output)
class OpNanshePreprocessDataCached(Operator):
    """
    Given an input image and max/min bounds,
    masks out (i.e. sets to zero) all pixels that fall outside the bounds.
    """
    name = "OpNanshePreprocessDataCached"
    category = "Pointwise"


    Input = InputSlot()
    CacheInput = InputSlot(optional=True)


    ToRemoveZeroedLines = InputSlot(value=True)
    ErosionShape = InputSlot(value=[21, 1])
    DilationShape = InputSlot(value=[1, 3])

    ToExtractF0 = InputSlot(value=True)
    HalfWindowSize = InputSlot(value=400, stype='int')
    WhichQuantile = InputSlot(value=0.15, stype='float')
    TemporalSmoothingGaussianFilterStdev = InputSlot(value=5.0, stype='float')
    SpatialSmoothingGaussianFilterStdev = InputSlot(value=5.0, stype='float')
    TemporalSmoothingGaussianFilterWindowSize = InputSlot(value=5.0, stype='float')
    SpatialSmoothingGaussianFilterWindowSize = InputSlot(value=5.0, stype='float')
    BiasEnabled = InputSlot(value=False, stype='bool')
    Bias = InputSlot(value=0.0, stype='float')

    ToWaveletTransform = InputSlot(value=True)
    Scale = InputSlot(value=4)


    OpNansheRemoveZeroedLinesOutput = OutputSlot()
    OpNansheExtractF0_dF_F_Output = OutputSlot()
    OpNansheExtractF0_F0_Output = OutputSlot()
    OpNansheWaveletTransformOutput = OutputSlot()

    CleanBlocks = OutputSlot()
    CacheOutput = OutputSlot()
    Output = OutputSlot()

    def __init__(self, *args, **kwargs):
        super( OpNanshePreprocessDataCached, self ).__init__( *args, **kwargs )

        self.opConvertType = OpConvertTypeCached(parent=self)
        self.opConvertType.Dtype.setValue(numpy.float32)

        self.opNansheRemoveZeroedLines = OpNansheRemoveZeroedLinesCached(parent=self)
        self.opNansheRemoveZeroedLines.ErosionShape.connect(self.ErosionShape)
        self.opNansheRemoveZeroedLines.DilationShape.connect(self.DilationShape)

        self.opNansheExtractF0 = OpNansheExtractF0Cached(parent=self)
        self.opNansheExtractF0.HalfWindowSize.connect(self.HalfWindowSize)
        self.opNansheExtractF0.WhichQuantile.connect(self.WhichQuantile)
        self.opNansheExtractF0.TemporalSmoothingGaussianFilterStdev.connect(self.TemporalSmoothingGaussianFilterStdev)
        self.opNansheExtractF0.SpatialSmoothingGaussianFilterStdev.connect(self.SpatialSmoothingGaussianFilterStdev)
        self.opNansheExtractF0.TemporalSmoothingGaussianFilterWindowSize.connect(self.TemporalSmoothingGaussianFilterWindowSize)
        self.opNansheExtractF0.SpatialSmoothingGaussianFilterWindowSize.connect(self.SpatialSmoothingGaussianFilterWindowSize)
        self.opNansheExtractF0.BiasEnabled.connect(self.BiasEnabled)
        self.opNansheExtractF0.Bias.connect(self.Bias)

        self.opNansheWaveletTransform = OpNansheWaveletTransformCached(parent=self)
        self.opNansheWaveletTransform.Scale.connect(self.Scale)


        self.OpNansheRemoveZeroedLinesOutput.connect(self.opNansheRemoveZeroedLines.Output)
        self.OpNansheExtractF0_dF_F_Output.connect(self.opNansheExtractF0.dF_F)
        self.OpNansheExtractF0_F0_Output.connect(self.opNansheExtractF0.F0)
        self.OpNansheWaveletTransformOutput.connect(self.opNansheWaveletTransform.Output)

        self.opCache = OpArrayCache(parent=self)
        self.opCache.fixAtCurrent.setValue(False)
        self.CleanBlocks.connect(self.opCache.CleanBlocks)

        self.CacheOutput.connect(self.opCache.Output)

    def setupOutputs(self):
        self.opNansheRemoveZeroedLines.Input.disconnect()
        self.opNansheExtractF0.Input.disconnect()
        self.opNansheWaveletTransform.Input.disconnect()
        self.opCache.Input.disconnect()

        next_output = self.Input

        self.opConvertType.Input.connect(next_output)
        next_output = self.opConvertType.Output

        if self.ToRemoveZeroedLines.value:
            self.opNansheRemoveZeroedLines.Input.connect(next_output)
            next_output = self.opNansheRemoveZeroedLines.Output

        if self.ToExtractF0.value:
            self.opNansheExtractF0.Input.connect(next_output)
            next_output = self.opNansheExtractF0.dF_F

        if self.ToWaveletTransform.value:
            self.opNansheWaveletTransform.Input.connect(next_output)
            next_output = self.opNansheWaveletTransform.Output

        self.Output.connect(next_output)
        self.opCache.Input.connect(next_output)

        self.opCache.blockShape.setValue( self.opCache.Output.meta.shape )

    # Don't need execute as the output will be drawn through the Output slot.

    def setInSlot(self, slot, subindex, key, value):
        assert slot == self.CacheInput

        self.opCache.setInSlot(self.opCache.Input, subindex, key, value)

    def propagateDirty(self, slot, subindex, roi):
        if slot.name == "ToRemoveZeroedLines":
            if slot.value:
                self.opNansheRemoveZeroedLines.Output.setDirty( slice(None) )
            else:
                if self.ToExtractF0.value:
                    self.opNansheExtractF0.Input.setDirty( slice(None) )
                elif self.ToWaveletTransform.value:
                    self.opNansheWaveletTransform.Input.setDirty( slice(None) )
                else:
                    self.opCache.Input.setDirty( slice(None) )
        elif slot.name == "ToExtractF0":
            if slot.value:
                self.opNansheExtractF0.dF_F.setDirty( slice(None) )
                self.opNansheExtractF0.F0.setDirty( slice(None) )
            else:
                if self.ToWaveletTransform.value:
                    self.opNansheWaveletTransform.Input.setDirty( slice(None) )
                else:
                    self.opCache.Input.setDirty( slice(None) )
        elif slot.name == "ToWaveletTransform":
            if slot.value:
                self.opNansheWaveletTransform.Output.setDirty( slice(None) )
            else:
                self.opCache.Input.setDirty( slice(None) )
class OpNansheGenerateDictionaryCached(Operator):
    """
    Given an input image and max/min bounds,
    masks out (i.e. sets to zero) all pixels that fall outside the bounds.
    """
    name = "OpNansheGenerateDictionaryCached"
    category = "Pointwise"


    Input = InputSlot()
    CacheInput = InputSlot(optional=True)

    K = InputSlot(value=100, stype="int")
    Gamma1 = InputSlot(value=0.0)
    Gamma2 = InputSlot(value=0.0)
    NumThreads = InputSlot(value=1)
    Batchsize = InputSlot(value=256)
    NumIter = InputSlot(value=100, stype="int")
    Lambda1 = InputSlot(value=0.2)
    Lambda2 = InputSlot(value=0.0)
    PosAlpha = InputSlot(value=True)
    PosD = InputSlot(value=True)
    Clean = InputSlot(value=True)
    Mode = InputSlot(value=2, stype="int")
    ModeD = InputSlot(value=0, stype="int")

    CleanBlocks = OutputSlot()
    Output = OutputSlot()

    def __init__(self, *args, **kwargs):
        super( OpNansheGenerateDictionaryCached, self ).__init__( *args, **kwargs )

        self.opDictionary = OpNansheGenerateDictionary(parent=self)

        self.opDictionary.K.connect(self.K)
        self.opDictionary.Gamma1.connect(self.Gamma1)
        self.opDictionary.Gamma2.connect(self.Gamma2)
        self.opDictionary.NumThreads.connect(self.NumThreads)
        self.opDictionary.Batchsize.connect(self.Batchsize)
        self.opDictionary.NumIter.connect(self.NumIter)
        self.opDictionary.Lambda1.connect(self.Lambda1)
        self.opDictionary.Lambda2.connect(self.Lambda2)
        self.opDictionary.PosAlpha.connect(self.PosAlpha)
        self.opDictionary.PosD.connect(self.PosD)
        self.opDictionary.Clean.connect(self.Clean)
        self.opDictionary.Mode.connect(self.Mode)
        self.opDictionary.ModeD.connect(self.ModeD)


        self.opCache = OpArrayCache(parent=self)
        self.opCache.fixAtCurrent.setValue(False)

        self.opDictionary.Input.connect( self.Input )
        self.opCache.Input.connect( self.opDictionary.Output )
        self.CleanBlocks.connect( self.opCache.CleanBlocks )
        self.Output.connect( self.opCache.Output )

    def setupOutputs(self):
        self.opCache.blockShape.setValue( self.opCache.Output.meta.shape )

    def setInSlot(self, slot, subindex, key, value):
        assert slot == self.CacheInput

        self.opCache.setInSlot(self.opCache.Input, subindex, key, value)

    def propagateDirty(self, slot, subindex, roi):
        pass
class OpNanshePostprocessDataCached(Operator):
    """
    Given an input image and max/min bounds,
    masks out (i.e. sets to zero) all pixels that fall outside the bounds.
    """
    name = "OpNanshePostprocessDataCached"
    category = "Pointwise"


    Input = InputSlot()
    CacheInput = InputSlot(optional=True)

    SignificanceThreshold = InputSlot(value=3.0, stype="float")
    WaveletTransformScale = InputSlot(value=4, stype="int")
    NoiseThreshold = InputSlot(value=4.0, stype="float")
    AcceptedRegionShapeConstraints_MajorAxisLength_Min = InputSlot(value=0.0, stype="float")
    AcceptedRegionShapeConstraints_MajorAxisLength_Min_Enabled = InputSlot(value=True, stype="bool")
    AcceptedRegionShapeConstraints_MajorAxisLength_Max = InputSlot(value=25.0, stype="float")
    AcceptedRegionShapeConstraints_MajorAxisLength_Max_Enabled = InputSlot(value=True, stype="bool")

    PercentagePixelsBelowMax = InputSlot(value=0.8, stype="float")
    MinLocalMaxDistance = InputSlot(value=20.0, stype="float")

    AcceptedNeuronShapeConstraints_Area_Min = InputSlot(value=45, stype="int")
    AcceptedNeuronShapeConstraints_Area_Min_Enabled = InputSlot(value=True, stype="bool")
    AcceptedNeuronShapeConstraints_Area_Max = InputSlot(value=600, stype="int")
    AcceptedNeuronShapeConstraints_Area_Max_Enabled = InputSlot(value=True, stype="bool")

    AcceptedNeuronShapeConstraints_Eccentricity_Min = InputSlot(value=0.0, stype="float")
    AcceptedNeuronShapeConstraints_Eccentricity_Min_Enabled = InputSlot(value=True, stype="bool")
    AcceptedNeuronShapeConstraints_Eccentricity_Max = InputSlot(value=0.9, stype="float")
    AcceptedNeuronShapeConstraints_Eccentricity_Max_Enabled = InputSlot(value=True, stype="bool")

    AlignmentMinThreshold = InputSlot(value=0.6, stype="float")
    OverlapMinThreshold = InputSlot(value=0.6, stype="float")

    Fuse_FractionMeanNeuronMaxThreshold = InputSlot(value=0.01, stype="float")

    CleanBlocks = OutputSlot()
    Output = OutputSlot()
    ColorizedOutput = OutputSlot()

    def __init__(self, *args, **kwargs):
        super( OpNanshePostprocessDataCached, self ).__init__( *args, **kwargs )

        self.opPostprocessing = OpNanshePostprocessData(parent=self)

        self.opPostprocessing.SignificanceThreshold.connect(self.SignificanceThreshold)
        self.opPostprocessing.WaveletTransformScale.connect(self.WaveletTransformScale)
        self.opPostprocessing.NoiseThreshold.connect(self.NoiseThreshold)
        self.opPostprocessing.AcceptedRegionShapeConstraints_MajorAxisLength_Min.connect(self.AcceptedRegionShapeConstraints_MajorAxisLength_Min)
        self.opPostprocessing.AcceptedRegionShapeConstraints_MajorAxisLength_Min_Enabled.connect(self.AcceptedRegionShapeConstraints_MajorAxisLength_Min_Enabled)
        self.opPostprocessing.AcceptedRegionShapeConstraints_MajorAxisLength_Max.connect(self.AcceptedRegionShapeConstraints_MajorAxisLength_Max)
        self.opPostprocessing.AcceptedRegionShapeConstraints_MajorAxisLength_Max_Enabled.connect(self.AcceptedRegionShapeConstraints_MajorAxisLength_Max_Enabled)
        self.opPostprocessing.PercentagePixelsBelowMax.connect(self.PercentagePixelsBelowMax)
        self.opPostprocessing.MinLocalMaxDistance.connect(self.MinLocalMaxDistance)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Area_Min.connect(self.AcceptedNeuronShapeConstraints_Area_Min)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Area_Min_Enabled.connect(self.AcceptedNeuronShapeConstraints_Area_Min_Enabled)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Area_Max.connect(self.AcceptedNeuronShapeConstraints_Area_Max)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Area_Max_Enabled.connect(self.AcceptedNeuronShapeConstraints_Area_Max_Enabled)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Eccentricity_Min.connect(self.AcceptedNeuronShapeConstraints_Eccentricity_Min)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Eccentricity_Min_Enabled.connect(self.AcceptedNeuronShapeConstraints_Eccentricity_Min_Enabled)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Eccentricity_Max.connect(self.AcceptedNeuronShapeConstraints_Eccentricity_Max)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Eccentricity_Max_Enabled.connect(self.AcceptedNeuronShapeConstraints_Eccentricity_Max_Enabled)
        self.opPostprocessing.AlignmentMinThreshold.connect(self.AlignmentMinThreshold)
        self.opPostprocessing.OverlapMinThreshold.connect(self.OverlapMinThreshold)
        self.opPostprocessing.Fuse_FractionMeanNeuronMaxThreshold.connect(self.Fuse_FractionMeanNeuronMaxThreshold)


        self.opCache = OpArrayCache(parent=self)
        self.opCache.fixAtCurrent.setValue(False)
        self.CleanBlocks.connect( self.opCache.CleanBlocks )

        self.opPostprocessing.Input.connect( self.Input )
        self.opCache.Input.connect( self.opPostprocessing.Output )
        self.Output.connect( self.opCache.Output )

        self.opColorizeLabelImage = OpColorizeLabelImage(parent=self)
        self.opColorizeLabelImage.Input.connect(self.Output)
        self.ColorizedOutput.connect(self.opColorizeLabelImage.Output)

    def setupOutputs(self):
        self.opCache.blockShape.setValue( self.opPostprocessing.Output.meta.shape )

        self.Output.meta.assignFrom( self.opCache.Output.meta )

    def setInSlot(self, slot, subindex, key, value):
        assert slot == self.CacheInput

        self.opCache.setInSlot(self.opCache.Input, subindex, key, value)

    def propagateDirty(self, slot, subindex, roi):
        pass
class OpNanshePreprocessDataCached(Operator):
    """
    Given an input image and max/min bounds,
    masks out (i.e. sets to zero) all pixels that fall outside the bounds.
    """
    name = "OpNanshePreprocessDataCached"
    category = "Pointwise"

    Input = InputSlot()
    CacheInput = InputSlot(optional=True)

    ToRemoveZeroedLines = InputSlot(value=True)
    ErosionShape = InputSlot(value=[21, 1])
    DilationShape = InputSlot(value=[1, 3])

    ToExtractF0 = InputSlot(value=True)
    HalfWindowSize = InputSlot(value=400, stype='int')
    WhichQuantile = InputSlot(value=0.15, stype='float')
    TemporalSmoothingGaussianFilterStdev = InputSlot(value=5.0, stype='float')
    SpatialSmoothingGaussianFilterStdev = InputSlot(value=5.0, stype='float')
    TemporalSmoothingGaussianFilterWindowSize = InputSlot(value=5.0,
                                                          stype='float')
    SpatialSmoothingGaussianFilterWindowSize = InputSlot(value=5.0,
                                                         stype='float')
    BiasEnabled = InputSlot(value=False, stype='bool')
    Bias = InputSlot(value=0.0, stype='float')

    ToWaveletTransform = InputSlot(value=True)
    Scale = InputSlot(value=4)

    OpNansheRemoveZeroedLinesOutput = OutputSlot()
    OpNansheExtractF0_dF_F_Output = OutputSlot()
    OpNansheExtractF0_F0_Output = OutputSlot()
    OpNansheWaveletTransformOutput = OutputSlot()

    CleanBlocks = OutputSlot()
    CacheOutput = OutputSlot()
    Output = OutputSlot()

    def __init__(self, *args, **kwargs):
        super(OpNanshePreprocessDataCached, self).__init__(*args, **kwargs)

        self.opConvertType = OpConvertTypeCached(parent=self)
        self.opConvertType.Dtype.setValue(numpy.float32)

        self.opNansheRemoveZeroedLines = OpNansheRemoveZeroedLinesCached(
            parent=self)
        self.opNansheRemoveZeroedLines.ErosionShape.connect(self.ErosionShape)
        self.opNansheRemoveZeroedLines.DilationShape.connect(
            self.DilationShape)

        self.opNansheExtractF0 = OpNansheExtractF0Cached(parent=self)
        self.opNansheExtractF0.HalfWindowSize.connect(self.HalfWindowSize)
        self.opNansheExtractF0.WhichQuantile.connect(self.WhichQuantile)
        self.opNansheExtractF0.TemporalSmoothingGaussianFilterStdev.connect(
            self.TemporalSmoothingGaussianFilterStdev)
        self.opNansheExtractF0.SpatialSmoothingGaussianFilterStdev.connect(
            self.SpatialSmoothingGaussianFilterStdev)
        self.opNansheExtractF0.TemporalSmoothingGaussianFilterWindowSize.connect(
            self.TemporalSmoothingGaussianFilterWindowSize)
        self.opNansheExtractF0.SpatialSmoothingGaussianFilterWindowSize.connect(
            self.SpatialSmoothingGaussianFilterWindowSize)
        self.opNansheExtractF0.BiasEnabled.connect(self.BiasEnabled)
        self.opNansheExtractF0.Bias.connect(self.Bias)

        self.opNansheWaveletTransform = OpNansheWaveletTransformCached(
            parent=self)
        self.opNansheWaveletTransform.Scale.connect(self.Scale)

        self.OpNansheRemoveZeroedLinesOutput.connect(
            self.opNansheRemoveZeroedLines.Output)
        self.OpNansheExtractF0_dF_F_Output.connect(self.opNansheExtractF0.dF_F)
        self.OpNansheExtractF0_F0_Output.connect(self.opNansheExtractF0.F0)
        self.OpNansheWaveletTransformOutput.connect(
            self.opNansheWaveletTransform.Output)

        self.opCache = OpArrayCache(parent=self)
        self.opCache.fixAtCurrent.setValue(False)
        self.CleanBlocks.connect(self.opCache.CleanBlocks)

        self.CacheOutput.connect(self.opCache.Output)

    def setupOutputs(self):
        self.opNansheRemoveZeroedLines.Input.disconnect()
        self.opNansheExtractF0.Input.disconnect()
        self.opNansheWaveletTransform.Input.disconnect()
        self.opCache.Input.disconnect()

        next_output = self.Input

        self.opConvertType.Input.connect(next_output)
        next_output = self.opConvertType.Output

        if self.ToRemoveZeroedLines.value:
            self.opNansheRemoveZeroedLines.Input.connect(next_output)
            next_output = self.opNansheRemoveZeroedLines.Output

        if self.ToExtractF0.value:
            self.opNansheExtractF0.Input.connect(next_output)
            next_output = self.opNansheExtractF0.dF_F

        if self.ToWaveletTransform.value:
            self.opNansheWaveletTransform.Input.connect(next_output)
            next_output = self.opNansheWaveletTransform.Output

        self.Output.connect(next_output)
        self.opCache.Input.connect(next_output)

        self.opCache.blockShape.setValue(self.opCache.Output.meta.shape)

    # Don't need execute as the output will be drawn through the Output slot.

    def setInSlot(self, slot, subindex, key, value):
        assert slot == self.CacheInput

        self.opCache.setInSlot(self.opCache.Input, subindex, key, value)

    def propagateDirty(self, slot, subindex, roi):
        if slot.name == "ToRemoveZeroedLines":
            if slot.value:
                self.opNansheRemoveZeroedLines.Output.setDirty(slice(None))
            else:
                if self.ToExtractF0.value:
                    self.opNansheExtractF0.Input.setDirty(slice(None))
                elif self.ToWaveletTransform.value:
                    self.opNansheWaveletTransform.Input.setDirty(slice(None))
                else:
                    self.opCache.Input.setDirty(slice(None))
        elif slot.name == "ToExtractF0":
            if slot.value:
                self.opNansheExtractF0.dF_F.setDirty(slice(None))
                self.opNansheExtractF0.F0.setDirty(slice(None))
            else:
                if self.ToWaveletTransform.value:
                    self.opNansheWaveletTransform.Input.setDirty(slice(None))
                else:
                    self.opCache.Input.setDirty(slice(None))
        elif slot.name == "ToWaveletTransform":
            if slot.value:
                self.opNansheWaveletTransform.Output.setDirty(slice(None))
            else:
                self.opCache.Input.setDirty(slice(None))
Esempio n. 26
0
class OpMaskedWatershed(Operator):
    """
    Performs a seeded watershed within a masked region.
    The masking is achieved using using vigra's terminate=StopAtThreshold feature.
    """
    Input = InputSlot(
        optional=True
    )  # If no input is given, output is voronoi within the masked region.
    Mask = InputSlot(
    )  # Watershed will only be computed for pixels where mask=True
    Seeds = InputSlot()

    Output = OutputSlot()

    def __init__(self, *args, **kwargs):
        super(OpMaskedWatershed, self).__init__(*args, **kwargs)

        # Use an internal operator to prepare the data,
        #  for easy caching/parallelization.
        self._opPrepInput = _OpPrepWatershedInput(parent=self)
        self._opPrepInput.Input.connect(self.Input)
        self._opPrepInput.Mask.connect(self.Mask)

        self._opPreppedInputCache = OpArrayCache(parent=self)
        self._opPreppedInputCache.Input.connect(self._opPrepInput.Output)

    def setupOutputs(self):
        if self.Input.ready():
            assert self.Input.meta.drange is not None, "Masked watershed requires input drange to be specified"

        # Cache the prepared input in 8 blocks
        blockshape = numpy.array(self._opPrepInput.Output.meta.shape) / 2
        blockshape = numpy.maximum(1, blockshape)
        self._opPreppedInputCache.blockShape.setValue(tuple(blockshape))

        self.Output.meta.assignFrom(self.Mask.meta)
        self.Output.meta.dtype = numpy.uint32

    def execute(self, slot, subindex, roi, result):
        # The input preparation involves converting to uint8 and combining
        #  the mask so we can use the StopAtThreshold mechanism
        with Timer() as prep_timer:
            input_data = self._opPreppedInputCache.Output(roi.start,
                                                          roi.stop).wait()
        logger.debug("Input prep took {} seconds".format(prep_timer.seconds()))

        input_axistags = self._opPrepInput.Output.meta.axistags
        max_input_value = self._opPrepInput.Output.meta.drange[1]

        seeds = self.Seeds(roi.start, roi.stop).wait()

        # The input_data has max value outside the mask area.
        # Discard seeds outside the mask
        seeds[input_data == max_input_value] = 0

        # Reduce to 3-D (keep order of xyz axes)
        tags = input_axistags
        axes3d = "".join([tag.key for tag in tags if tag.key in 'xyz'])

        input_view = vigra.taggedView(input_data, input_axistags)
        input_view = input_view.withAxes(*axes3d)
        input_view = vigra.taggedView(input_view, axes3d)

        seeds_view = vigra.taggedView(seeds, self.Seeds.meta.axistags)
        seeds_view = seeds_view.withAxes(*axes3d)
        seeds_view = seeds_view.astype(numpy.uint32)

        result_view = vigra.taggedView(result, self.Output.meta.axistags)
        result_view = result_view.withAxes(*axes3d)
        result_view = vigra.taggedView(result_view, axes3d)

        with Timer() as watershed_timer:
            # The 'watershedsNew' function is faster and supports StopAtThreshold even in turbo mode
            _, maxLabel = vigra.analysis.watershedsNew(
                input_view,
                seeds=seeds_view,
                out=result_view,
                method='turbo',
                terminate=vigra.analysis.SRGType.StopAtThreshold,
                max_cost=max_input_value - 1)

        logger.debug("vigra.watershedsNew() took {} seconds ({} seeds)".format(
            watershed_timer.seconds(), maxLabel))
        return result

    def propagateDirty(self, slot, subindex, roi):
        self.Output.setDirty()
Esempio n. 27
0
class OpSingleBlockObjectPrediction(Operator):
    RawImage = InputSlot()
    BinaryImage = InputSlot()

    SelectedFeatures = InputSlot(rtype=List, stype=Opaque)

    Classifier = InputSlot()
    LabelsCount = InputSlot()

    ObjectwisePredictions = OutputSlot(stype=Opaque, rtype=List)
    PredictionImage = OutputSlot()
    ProbabilityChannelImage = OutputSlot()
    BlockwiseRegionFeatures = OutputSlot()  # Indexed by (t,c)

    # Schematic:
    #
    # RawImage -----> opRawSubRegion ------                        _______________________
    #                                      \                      /                       \
    # BinaryImage --> opBinarySubRegion --> opExtract --(features)--> opPredict --(map)--> opPredictionImage --via execute()--> PredictionImage
    #                                      /         \               /                    /
    #                 SelectedFeatures-----           \   Classifier                     /
    #                                                  \                                /
    #                                                   (labels)---------------------------> opProbabilityChannelsToImage

    # +----------------------------------------------------------------+
    # | input_shape = RawImage.meta.shape                              |
    # |                                                                |
    # |                                                                |
    # |                                                                |
    # |                                                                |
    # |                                                                |
    # |                                                                |
    # |                    halo_shape = blockshape + 2*halo_padding    |
    # |                    +------------------------+                  |
    # |                    | halo_roi               |                  |
    # |                    | (for internal pipeline)|                  |
    # |                    |                        |                  |
    # |                    |  +------------------+  |                  |
    # |                    |  | block_roi        |  |                  |
    # |                    |  | (output shape)   |  |                  |
    # |                    |  |                  |  |                  |
    # |                    |  |                  |  |                  |
    # |                    |  |                  |  |                  |
    # |                    |  +------------------+  |                  |
    # |                    |                        |                  |
    # |                    |                        |                  |
    # |                    |                        |                  |
    # |                    +------------------------+                  |
    # |                                                                |
    # |                                                                |
    # |                                                                |
    # |                                                                |
    # |                                                                |
    # |                                                                |
    # |                                                                |
    # +----------------------------------------------------------------+

    def __init__(self, block_roi, halo_padding, *args, **kwargs):
        super(self.__class__, self).__init__(*args, **kwargs)

        self.block_roi = block_roi  # In global coordinates
        self._halo_padding = halo_padding

        self._opBinarySubRegion = OpSubRegion(parent=self)
        self._opBinarySubRegion.Input.connect(self.BinaryImage)

        self._opRawSubRegion = OpSubRegion(parent=self)
        self._opRawSubRegion.Input.connect(self.RawImage)

        self._opExtract = OpObjectExtraction(parent=self)
        self._opExtract.BinaryImage.connect(self._opBinarySubRegion.Output)
        self._opExtract.RawImage.connect(self._opRawSubRegion.Output)
        self._opExtract.Features.connect(self.SelectedFeatures)
        self.BlockwiseRegionFeatures.connect(
            self._opExtract.BlockwiseRegionFeatures)

        self._opExtract._opRegFeats._opCache.name = "blockwise-regionfeats-cache"

        self._opPredict = OpObjectPredict(parent=self)
        self._opPredict.Features.connect(self._opExtract.RegionFeatures)
        self._opPredict.SelectedFeatures.connect(self.SelectedFeatures)
        self._opPredict.Classifier.connect(self.Classifier)
        self._opPredict.LabelsCount.connect(self.LabelsCount)
        self.ObjectwisePredictions.connect(self._opPredict.Predictions)

        self._opPredictionImage = OpRelabelSegmentation(parent=self)
        self._opPredictionImage.Image.connect(self._opExtract.LabelImage)
        self._opPredictionImage.Features.connect(
            self._opExtract.RegionFeatures)
        self._opPredictionImage.ObjectMap.connect(self._opPredict.Predictions)

        self._opPredictionCache = OpArrayCache(parent=self)
        self._opPredictionCache.Input.connect(self._opPredictionImage.Output)

        self._opProbabilityChannelsToImage = OpMultiRelabelSegmentation(
            parent=self)
        self._opProbabilityChannelsToImage.Image.connect(
            self._opExtract.LabelImage)
        self._opProbabilityChannelsToImage.ObjectMaps.connect(
            self._opPredict.ProbabilityChannels)
        self._opProbabilityChannelsToImage.Features.connect(
            self._opExtract.RegionFeatures)

        self._opProbabilityChannelStacker = OpMultiArrayStacker(parent=self)
        self._opProbabilityChannelStacker.Images.connect(
            self._opProbabilityChannelsToImage.Output)
        self._opProbabilityChannelStacker.AxisFlag.setValue('c')

        self._opProbabilityCache = OpArrayCache(parent=self)
        self._opProbabilityCache.Input.connect(
            self._opProbabilityChannelStacker.Output)

    def setupOutputs(self):
        tagged_input_shape = self.RawImage.meta.getTaggedShape()
        self._halo_roi = self.computeHaloRoi(
            tagged_input_shape, self._halo_padding,
            self.block_roi)  # In global coordinates

        # Output roi in our own coordinates (i.e. relative to the halo start)
        self._output_roi = self.block_roi - self._halo_roi[0]

        halo_start, halo_stop = map(tuple, self._halo_roi)

        self._opRawSubRegion.Roi.setValue((halo_start, halo_stop))

        # Binary image has only 1 channel.  Adjust halo subregion.
        assert self.BinaryImage.meta.getTaggedShape()['c'] == 1
        c_index = self.BinaryImage.meta.axistags.channelIndex
        binary_halo_roi = numpy.array(self._halo_roi)
        binary_halo_roi[:, c_index] = (0, 1)  # Binary has only 1 channel.
        binary_halo_start, binary_halo_stop = map(tuple, binary_halo_roi)

        self._opBinarySubRegion.Roi.setValue(
            (binary_halo_start, binary_halo_stop))

        self.PredictionImage.meta.assignFrom(
            self._opPredictionImage.Output.meta)
        self.PredictionImage.meta.shape = tuple(
            numpy.subtract(self.block_roi[1], self.block_roi[0]))

        self.ProbabilityChannelImage.meta.assignFrom(
            self._opProbabilityChannelStacker.Output.meta)
        probability_shape = numpy.subtract(self.block_roi[1],
                                           self.block_roi[0])
        probability_shape[
            -1] = self._opProbabilityChannelStacker.Output.meta.shape[-1]
        self.ProbabilityChannelImage.meta.shape = tuple(probability_shape)

        # Cache the entire block
        self._opPredictionCache.blockShape.setValue(
            self._opPredictionCache.Input.meta.shape)
        self._opProbabilityCache.blockShape.setValue(
            self._opProbabilityCache.Input.meta.shape)

        # Forward dirty regions to our own output
        self._opPredictionImage.Output.notifyDirty(self._handleDirtyPrediction)

    def execute(self, slot, subindex, roi, destination):
        assert slot is self.PredictionImage or slot is self.ProbabilityChannelImage, "Unknown input slot"
        assert (numpy.array(roi.stop) <=
                slot.meta.shape).all(), "Roi is out-of-bounds"

        # Extract from the output (discard halo)
        halo_offset = numpy.subtract(self.block_roi[0], self._halo_roi[0])
        adjusted_roi = (halo_offset + roi.start, halo_offset + roi.stop)
        if slot is self.PredictionImage:
            return self._opPredictionCache.Output(
                *adjusted_roi).writeInto(destination).wait()
        elif slot is self.ProbabilityChannelImage:
            return self._opProbabilityCache.Output(
                *adjusted_roi).writeInto(destination).wait()

    def propagateDirty(self, slot, subindex, roi):
        """
        Nothing to do here because dirty notifications are propagated 
        through our internal pipeline and forwarded to our output via 
        our notifyDirty handler.
        """
        pass

    def _handleDirtyPrediction(self, slot, roi):
        """
        Foward dirty notifications from our internal output slot to the external one,
        but first discard the halo and offset the roi to compensate for the halo.
        """
        # Discard halo.  dirtyRoi is in internal coordinates (i.e. relative to halo start)
        dirtyRoi = getIntersection((roi.start, roi.stop),
                                   self._output_roi,
                                   assertIntersect=False)
        if dirtyRoi is not None:
            halo_offset = numpy.subtract(self.block_roi[0], self._halo_roi[0])
            adjusted_roi = dirtyRoi - halo_offset  # adjusted_roi is in output coordinates (relative to output block start)
            self.PredictionImage.setDirty(*adjusted_roi)

            # Expand to all channels and set channel image dirty
            adjusted_roi[:,
                         -1] = (0, self.ProbabilityChannelImage.meta.shape[-1])
            self.ProbabilityChannelImage.setDirty(*adjusted_roi)

    @classmethod
    def computeHaloRoi(cls, tagged_dataset_shape, halo_padding, block_roi):
        block_roi = numpy.array(block_roi)
        block_start, block_stop = block_roi

        channel_index = tagged_dataset_shape.keys().index('c')
        block_start[channel_index] = 0
        block_stop[channel_index] = tagged_dataset_shape['c']

        # Compute halo and clip to dataset bounds
        halo_start = block_start - halo_padding
        halo_start = numpy.maximum(halo_start, (0, ) * len(halo_start))

        halo_stop = block_stop + halo_padding
        halo_stop = numpy.minimum(halo_stop, tagged_dataset_shape.values())

        halo_roi = (halo_start, halo_stop)
        return halo_roi
class OpNanshePostprocessDataCached(Operator):
    """
    Given an input image and max/min bounds,
    masks out (i.e. sets to zero) all pixels that fall outside the bounds.
    """
    name = "OpNanshePostprocessDataCached"
    category = "Pointwise"

    Input = InputSlot()
    CacheInput = InputSlot(optional=True)

    SignificanceThreshold = InputSlot(value=3.0, stype="float")
    WaveletTransformScale = InputSlot(value=4, stype="int")
    NoiseThreshold = InputSlot(value=4.0, stype="float")
    AcceptedRegionShapeConstraints_MajorAxisLength_Min = InputSlot(
        value=0.0, stype="float")
    AcceptedRegionShapeConstraints_MajorAxisLength_Min_Enabled = InputSlot(
        value=True, stype="bool")
    AcceptedRegionShapeConstraints_MajorAxisLength_Max = InputSlot(
        value=25.0, stype="float")
    AcceptedRegionShapeConstraints_MajorAxisLength_Max_Enabled = InputSlot(
        value=True, stype="bool")

    PercentagePixelsBelowMax = InputSlot(value=0.8, stype="float")
    MinLocalMaxDistance = InputSlot(value=20.0, stype="float")

    AcceptedNeuronShapeConstraints_Area_Min = InputSlot(value=45, stype="int")
    AcceptedNeuronShapeConstraints_Area_Min_Enabled = InputSlot(value=True,
                                                                stype="bool")
    AcceptedNeuronShapeConstraints_Area_Max = InputSlot(value=600, stype="int")
    AcceptedNeuronShapeConstraints_Area_Max_Enabled = InputSlot(value=True,
                                                                stype="bool")

    AcceptedNeuronShapeConstraints_Eccentricity_Min = InputSlot(value=0.0,
                                                                stype="float")
    AcceptedNeuronShapeConstraints_Eccentricity_Min_Enabled = InputSlot(
        value=True, stype="bool")
    AcceptedNeuronShapeConstraints_Eccentricity_Max = InputSlot(value=0.9,
                                                                stype="float")
    AcceptedNeuronShapeConstraints_Eccentricity_Max_Enabled = InputSlot(
        value=True, stype="bool")

    AlignmentMinThreshold = InputSlot(value=0.6, stype="float")
    OverlapMinThreshold = InputSlot(value=0.6, stype="float")

    Fuse_FractionMeanNeuronMaxThreshold = InputSlot(value=0.01, stype="float")

    CleanBlocks = OutputSlot()
    Output = OutputSlot()
    ColorizedOutput = OutputSlot()

    def __init__(self, *args, **kwargs):
        super(OpNanshePostprocessDataCached, self).__init__(*args, **kwargs)

        self.opPostprocessing = OpNanshePostprocessData(parent=self)

        self.opPostprocessing.SignificanceThreshold.connect(
            self.SignificanceThreshold)
        self.opPostprocessing.WaveletTransformScale.connect(
            self.WaveletTransformScale)
        self.opPostprocessing.NoiseThreshold.connect(self.NoiseThreshold)
        self.opPostprocessing.AcceptedRegionShapeConstraints_MajorAxisLength_Min.connect(
            self.AcceptedRegionShapeConstraints_MajorAxisLength_Min)
        self.opPostprocessing.AcceptedRegionShapeConstraints_MajorAxisLength_Min_Enabled.connect(
            self.AcceptedRegionShapeConstraints_MajorAxisLength_Min_Enabled)
        self.opPostprocessing.AcceptedRegionShapeConstraints_MajorAxisLength_Max.connect(
            self.AcceptedRegionShapeConstraints_MajorAxisLength_Max)
        self.opPostprocessing.AcceptedRegionShapeConstraints_MajorAxisLength_Max_Enabled.connect(
            self.AcceptedRegionShapeConstraints_MajorAxisLength_Max_Enabled)
        self.opPostprocessing.PercentagePixelsBelowMax.connect(
            self.PercentagePixelsBelowMax)
        self.opPostprocessing.MinLocalMaxDistance.connect(
            self.MinLocalMaxDistance)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Area_Min.connect(
            self.AcceptedNeuronShapeConstraints_Area_Min)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Area_Min_Enabled.connect(
            self.AcceptedNeuronShapeConstraints_Area_Min_Enabled)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Area_Max.connect(
            self.AcceptedNeuronShapeConstraints_Area_Max)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Area_Max_Enabled.connect(
            self.AcceptedNeuronShapeConstraints_Area_Max_Enabled)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Eccentricity_Min.connect(
            self.AcceptedNeuronShapeConstraints_Eccentricity_Min)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Eccentricity_Min_Enabled.connect(
            self.AcceptedNeuronShapeConstraints_Eccentricity_Min_Enabled)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Eccentricity_Max.connect(
            self.AcceptedNeuronShapeConstraints_Eccentricity_Max)
        self.opPostprocessing.AcceptedNeuronShapeConstraints_Eccentricity_Max_Enabled.connect(
            self.AcceptedNeuronShapeConstraints_Eccentricity_Max_Enabled)
        self.opPostprocessing.AlignmentMinThreshold.connect(
            self.AlignmentMinThreshold)
        self.opPostprocessing.OverlapMinThreshold.connect(
            self.OverlapMinThreshold)
        self.opPostprocessing.Fuse_FractionMeanNeuronMaxThreshold.connect(
            self.Fuse_FractionMeanNeuronMaxThreshold)

        self.opCache = OpArrayCache(parent=self)
        self.opCache.fixAtCurrent.setValue(False)
        self.CleanBlocks.connect(self.opCache.CleanBlocks)

        self.opPostprocessing.Input.connect(self.Input)
        self.opCache.Input.connect(self.opPostprocessing.Output)
        self.Output.connect(self.opCache.Output)

        self.opColorizeLabelImage = OpColorizeLabelImage(parent=self)
        self.opColorizeLabelImage.Input.connect(self.Output)
        self.ColorizedOutput.connect(self.opColorizeLabelImage.Output)

    def setupOutputs(self):
        self.opCache.blockShape.setValue(
            self.opPostprocessing.Output.meta.shape)

        self.Output.meta.assignFrom(self.opCache.Output.meta)

    def setInSlot(self, slot, subindex, key, value):
        assert slot == self.CacheInput

        self.opCache.setInSlot(self.opCache.Input, subindex, key, value)

    def propagateDirty(self, slot, subindex, roi):
        pass
Esempio n. 29
0
            shape = tuple(self._slot.meta.shape)
            axes = "".join(self._slot.meta.getAxisKeys())
            dtype = self._slot.meta.dtype.__name__
        else:
            shape = axes = dtype = ""

        if not sip.isdeleted(self.shapeEdit):
            self.shapeEdit.setText(str(shape))
            self.axisOrderEdit.setText(axes)
            self.dtypeEdit.setText(dtype)


if __name__ == "__main__":
    import numpy
    import vigra
    from PyQt4.QtGui import QApplication
    from lazyflow.graph import Graph
    from lazyflow.operators import OpArrayCache

    data = numpy.zeros((10, 20, 30, 3), dtype=numpy.float32)
    data = vigra.taggedView(data, 'zyxc')

    op = OpArrayCache(graph=Graph())
    op.Input.setValue(data)

    app = QApplication([])
    w = SlotMetaInfoDisplayWidget(None)
    w.initSlot(op.Output)
    w.show()
    app.exec_()
class OpNansheGenerateDictionaryCached(Operator):
    """
    Given an input image and max/min bounds,
    masks out (i.e. sets to zero) all pixels that fall outside the bounds.
    """
    name = "OpNansheGenerateDictionaryCached"
    category = "Pointwise"

    Input = InputSlot()
    CacheInput = InputSlot(optional=True)

    K = InputSlot(value=100, stype="int")
    Gamma1 = InputSlot(value=0.0)
    Gamma2 = InputSlot(value=0.0)
    NumThreads = InputSlot(value=1)
    Batchsize = InputSlot(value=256)
    NumIter = InputSlot(value=100, stype="int")
    Lambda1 = InputSlot(value=0.2)
    Lambda2 = InputSlot(value=0.0)
    PosAlpha = InputSlot(value=True)
    PosD = InputSlot(value=True)
    Clean = InputSlot(value=True)
    Mode = InputSlot(value=2, stype="int")
    ModeD = InputSlot(value=0, stype="int")

    CleanBlocks = OutputSlot()
    Output = OutputSlot()

    def __init__(self, *args, **kwargs):
        super(OpNansheGenerateDictionaryCached, self).__init__(*args, **kwargs)

        self.opDictionary = OpNansheGenerateDictionary(parent=self)

        self.opDictionary.K.connect(self.K)
        self.opDictionary.Gamma1.connect(self.Gamma1)
        self.opDictionary.Gamma2.connect(self.Gamma2)
        self.opDictionary.NumThreads.connect(self.NumThreads)
        self.opDictionary.Batchsize.connect(self.Batchsize)
        self.opDictionary.NumIter.connect(self.NumIter)
        self.opDictionary.Lambda1.connect(self.Lambda1)
        self.opDictionary.Lambda2.connect(self.Lambda2)
        self.opDictionary.PosAlpha.connect(self.PosAlpha)
        self.opDictionary.PosD.connect(self.PosD)
        self.opDictionary.Clean.connect(self.Clean)
        self.opDictionary.Mode.connect(self.Mode)
        self.opDictionary.ModeD.connect(self.ModeD)

        self.opCache = OpArrayCache(parent=self)
        self.opCache.fixAtCurrent.setValue(False)

        self.opDictionary.Input.connect(self.Input)
        self.opCache.Input.connect(self.opDictionary.Output)
        self.CleanBlocks.connect(self.opCache.CleanBlocks)
        self.Output.connect(self.opCache.Output)

    def setupOutputs(self):
        self.opCache.blockShape.setValue(self.opCache.Output.meta.shape)

    def setInSlot(self, slot, subindex, key, value):
        assert slot == self.CacheInput

        self.opCache.setInSlot(self.opCache.Input, subindex, key, value)

    def propagateDirty(self, slot, subindex, roi):
        pass