Skip to main content
Question

Implementing image thresholding (Otsu's method) with PythonCaller

  • December 14, 2022
  • 1 reply
  • 85 views

Hello!  I'm trying to implement Otsu's method of image thresholding on an incoming raster, using the PythonCaller transformer.  I  have the following code block in the PythonCaller parameters, although my Python isn't great, so there may well be issues with it:

import fme
import fmeobjects
import numpy as np
class OtsuThreshold(object):
    def __init__(self):
        pass
    def input(self, feature):
        #implement Otsu thresholding in native Python with numpy
        #get the image from the feature
        image = feature.getAttribute('image')
        #compute the histogram of the image, then find the peak of the histogram
 
        hist = np.histogram(image, bins=256, range=(0256))
        
        maxVal = np.max(hist[0])
        maxLoc = np.argmax(hist[0])
        #perform Otsu thresholding
        T = maxLoc
        thresh = np.where(image > T, 2550)
        #set the attribute value
        feature.setAttribute('image', thresh)
        #pass the feature on to the next transformer
        self.pyoutput(feature)

I am getting this error, seemingly within histograms.py within numpy itself:

Python Exception <TypeError>: '>=' not supported between instances of 'NoneType' and 'int'

A little digging hints that this may indicate that the raster is being read as None values, which I can seemingly confirm by inserting the following before the "hist" array:

        if image is None or len(image) == 0:
            # handle empty image
            # for example, you could return an empty feature
            return

This is where I hit a dead end though. 

Ideally I would like to return the actual Otsu threshold pixel value itself as an attribute, although I don't think my script it currently capable of that.

Thank you!

 

1 reply

dustin
Influencer
Forum|alt.badge.img+30
  • Influencer
  • December 14, 2022

I don't have any experience working with raster data in python, so take this with a grain of salt....

 

It appears your raster is stored on an attribute, so it's possible that you are attempting the raster calculations on binary data instead of the actual raster. I would consider using a RasterReplacer prior to the PythonCaller to extract the raster from the attribute as the feature geometry, and then perform the Otsu processing on that.  


Cookie policy

We use cookies to enhance and personalize your experience. If you accept you agree to our full cookie policy. Learn more about our cookies.

 
Cookie settings