3

I've been using OpenCV 2.4 in Python to match features between two images, but I want to change one of the parameters of the "ORB" detector (the number of features it extracts "nfeatures") and there seems to be no way to do so in Python.

For C++ you can load a parameter yml/xml file by the 'read' (or 'load' for java?) methods of FeatureDetector/DescriptorExtractor. However the Python binding is missing this function/method.

It's also missing the binding to create an ORB object directly, so I can't pass the parameters there (Python binding seems to requires you to use cv2.DescriptorExtractor_create by string name -- which will segfault if you pass a bad string name or the parameters along with it... Additionally that function cannot take any other arguments it seems to pass onto the constructor.

My only hope seemed to be loading the complete object from xml with cv2.cv.Load(filename), but that seems to expect an object instance and not an Algorithm definition, for which I can't find any Python bindings in new or old syntax. I tried several variations on the file loading step, including mimicking the style of saved xml files from OpenCV with no luck.

Has anyone has success in one of the steps I tried above to pass parameters onto a detector (SURF or ORB, or any generic algorithm) in OpenCV?

Here is the code I am using to extract features:

def findFeatures(greyimg, detector="ORB", descriptor="ORB"):
    nfeatures = 2000 # No way to pass to detector...?
    detector = cv2.FeatureDetector_create(detector)
    descriptorExtractor = cv2.DescriptorExtractor_create(descriptor)
    keypoints = detector.detect(greyimg)
    (keypoints, descriptors) = descriptorExtractor.compute(greyimg, keypoints)
    return keypoints, descriptors

EDIT

Changing detector settings seems to only segfault on windows implementation -- waiting for a patch or fix to appear on OpenCV's site.

1 Answer 1

5
import cv2

# to see all ORB parameters and their values
detector = cv2.FeatureDetector_create("ORB")    
print "ORB parameters (dict):", detector.getParams()
for param in detector.getParams():
    ptype = detector.paramType(param)
    if ptype == 0:
        print param, "=", detector.getInt(param)
    elif ptype == 2:
        print param, "=", detector.getDouble(param)

# to set the nFeatures
print "nFeatures before:", detector.getInt("nFeatures")
detector.setInt("nFeatures", 1000)
print "nFeatures after:", detector.getInt("nFeatures")

with output:

ORB parameters (dict): ['WTA_K', 'edgeThreshold', 'firstLevel', 'nFeatures', 'nLevels', 'patchSize', 'scaleFactor', 'scoreType']
WTA_K = 2
edgeThreshold = 31
firstLevel = 0
nFeatures = 500
nLevels = 8
patchSize = 31
scaleFactor = 1.20000004768
scoreType = 0
nFeatures before: 500
nFeatures after: 1000

EDIT: To do the same with OpenCV 3.0 is now easier

import cv2

detector = cv2.ORB_create()
for attribute in dir(new_detector):
    if not attribute.startswith("get"):
        continue
    param = attribute.replace("get", "")
    get_param = getattr(new_backend, attribute)
    val = get_param()
    print param, '=', val

and analogically with a setter.

Sign up to request clarification or add additional context in comments.

4 Comments

I had tried this earlier before I posted the question. Under OpenCV 2.4 on Windows 7 64 bit running 32 bit Python and Windows Vista 32 bit running 32 bit Python this Segfaults on detector.getParams() with no stacktrace, no exception to catch, and no error message from OpenCV. What setup were you using where this did not Segfault immediately?
With me it crashes only on DescriptorMatcher's getParams() but the detector works. I am using Fedora 17 64bit, OpenCV 2.4.3., Python 2.7.3 64bit.
The detector works, but I can't set or get any of the parameters on the detector, which makes it unusable as the default values do not match all vision problems (I used a different detector as a result). If it crashes on getParams, how did you print the above output? I might try a fedora vm and see if the same calls crash on my machine.
You are completely right, adjustable parameters are critical for any computer vision problem. The code above works entirely in my setup (the one I mentioned above) and gets me that same output. I don't know what the problem with Windows might be but I suggest you try similar setup or check code.opencv.org/projects/opencv/issues for known bugs with Windows.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.