Do you want to use OpenCV v4+ in AutoIt v3 ?
If yes, then this udf might be for you.
- Download and extract libemgucv-windesktop-4.5.3.4721.zip into a folder
- Download and extract emgucv-autoit-bindings-v1.0.0-rc.0.zip into a folder
#Region ;**** Directives created by AutoIt3Wrapper_GUI ****
#AutoIt3Wrapper_UseX64=y
#EndRegion ;**** Directives created by AutoIt3Wrapper_GUI ****
Opt("MustDeclareVars", 1)
#include "emgucv-autoit-bindings\cve_extra.au3"
; Open the library
_OpenCV_DLLOpen("libemgucv-windesktop-4.5.3.4721\libs\x64\cvextern.dll")
Local $img = _cveImreadAndCheck("data\lena.jpg")
_cveImshowMat("Image", $img)
_cveWaitKey()
; always release resources to avoid memory leaks on long running processes
_cveMatRelease($img)
_cveDestroyAllWindows()
; Close the library
_Opencv_DLLClose()
# get the source files
git clone https://github.com/smbape/node-emgucv-autoit-generator
cd node-emgucv-autoit-generator
# download libemgucv-windesktop-4.5.3.4721
curl -L 'https://github.com/emgucv/emgucv/releases/download/4.5.3/libemgucv-windesktop-4.5.3.4721.zip' -o libemgucv-windesktop-4.5.3.4721.zip
unzip libemgucv-windesktop-4.5.3.4721.zip -d libemgucv-windesktop-4.5.3.4721
Now you can run any file in the samples\tutorial_code folder.
This shows how to put performance critical tasks in c++ functions, export those functions in a dll and then use them in autoit.
Look at samples\tutorial_code\Histograms_Matching\calcHist_Demo.au3 for an example of usage.
- Install CMAKE >= 3.5
- Install visual studio >= 10
Run build.bat script located in the autoit-addon folder.
- Finding the functions/constants names.
- Transform the parameter types according to the UDF parameter. This step might involve looking at the opencv documentation.
- Adjust the return type and variable. This step might involve looking at the opencv documentation.
For a function named foo or Foo, there is usually a function named _cveFoo
For a constant FOO, there is usually a Global Const ending with _FOO and starting with $CV_
For cv::Point, cv::Range, cv::Rect, cv::Scalar and cv::Size types,
there are _cvPoint, _cvRange, _cvRect, _cvScalar and _cvSize functions to convert parameters.
For cv::ScalarAll, there is _cvScalarAll function.
Types which are *Array like cv::_InputArray, are harder to translate because there is no automatic convertion in AutoIt like in c++.
For this reason, for functions which take those type of parameters, there will be 2 additionnal functions.
_cveFooTyped where you specified the type of the Array parameter and
_cveFooMat where you specified the type of all the Array parameter are Mat.
For vectors, there are functions starting with _VectorOf that allows to managed them.
As examples, for std::vector<int>*, there is
_VectorOfInt_VectorOfIntCreateSize_VectorOfIntGetSize_VectorOfIntPush_VectorOfIntPushMulti_VectorOfIntPushVector_VectorOfIntClear_VectorOfIntRelease_VectorOfIntCopyData_VectorOfIntGetStartAddress_VectorOfIntGetEndAddress_VectorOfIntGetItem_VectorOfIntGetItemPtr_VectorOfIntSizeOfItemInBytes
As examples, for std::vector<std::vector<cv::Point>>*, there is
_VectorOfVectorOfPoint_VectorOfVectorOfPointCreateSize_VectorOfVectorOfPointGetSize_VectorOfVectorOfPointPush_VectorOfVectorOfPointPushMulti_VectorOfVectorOfPointPushVector_VectorOfVectorOfPointClear_VectorOfVectorOfPointRelease_VectorOfVectorOfPointCopyData_VectorOfVectorOfPointGetStartAddress_VectorOfVectorOfPointGetEndAddress_VectorOfVectorOfPointGetItem_VectorOfVectorOfPointGetItemPtr_VectorOfVectorOfPointSizeOfItemInBytes
Let's translate the following python code
blurred = cv2.GaussianBlur(image, (3, 3), 0)
T, thresh_img = cv2.threshold(blurred, 215, 255, cv2.THRESH_BINARY)
cnts, _ = cv2.findContours(thresh_img,
cv2.RETR_EXTERNAL,
cv2.CHAIN_APPROX_SIMPLE)blurred = cv2.GaussianBlur(image, (3, 3), 0)The UDF function of GaussianBlur is
Func _cveGaussianBlur($src, $dst, $ksize, $sigmaX, $sigmaY = 0, $borderType = $CV_BORDER_DEFAULT)
; CVAPI(void) cveGaussianBlur(cv::_InputArray* src, cv::_OutputArray* dst, CvSize* ksize, double sigmaX, double sigmaY, int borderType);The GaussianBlur documentation gives the following information
void cv::GaussianBlur ( InputArray src,
OutputArray dst,
Size ksize,
double sigmaX,
double sigmaY = 0,
int borderType = BORDER_DEFAULT
)
Python:
cv.GaussianBlur( src, ksize, sigmaX[, dst[, sigmaY[, borderType]]] ) -> dst
src input image;
dst output image;In python, the returned value dst, is the OutputArray dst parameter of the c++ function, hence the UDF function.
src and dst are images, that means of type Mat
Because there are Array parameters, we have to use the Typed version of the UDF.
It allows to specify the type the Array parameters.
The python code will therefore become
$blurred = _cveMatCreate()
_cveGaussianBlurTyped("Mat", $image, "Mat", $blurred, _cvSize(3, 3), 0)And because all the Array types are Mat, it is equivalent to
$blurred = _cveMatCreate()
_cveGaussianBlurMat($image, $blurred, _cvSize(3, 3), 0)T, thresh_img = cv2.threshold(blurred, 215, 255, cv2.THRESH_BINARY)Applying the same steps leads to
$thresh_img = _cveMatCreate()
$T = _cveThresholdMat($blurred, $thresh_img, 215, 255, $CV_THRESH_BINARY)cnts, _ = cv2.findContours(thresh_img,
cv2.RETR_EXTERNAL,
cv2.CHAIN_APPROX_SIMPLE)Accoroding to findContours documentation
countours is a std::vector<std::vector<cv::Point>>
hierarchy Optional output vector (e.g. std::vector<cv::Vec4i>):
hierarchy is harder to translate. cv::Vec4i is a Matrix. A vector of Mattrix is also a Matrix.
The python code will become
$cnts = _VectorOfVectorOfPointCreate()
$_ = _cveMatCreate()
_cveFindContoursTyped("Mat", $thresh_img, "VectorOfVectorOfPoint", $cnts, "Mat", $_, $CV_RETR_EXTERNAL, $CV_CHAIN_APPROX_SIMPLE)Python
blurred = cv2.GaussianBlur(image, (3, 3), 0)
T, thresh_img = cv2.threshold(blurred, 215, 255, cv2.THRESH_BINARY)
cnts, _ = cv2.findContours(thresh_img,
cv2.RETR_EXTERNAL,
cv2.CHAIN_APPROX_SIMPLE)AutoIt
$blurred = _cveMatCreate()
_cveGaussianBlurTyped("Mat", $image, "Mat", $blurred, _cvSize(3, 3), 0)
$thresh_img = _cveMatCreate()
$T = _cveThresholdMat($blurred, $thresh_img, 215, 255, $CV_THRESH_BINARY)
$cnts = _VectorOfVectorOfPointCreate()
$_ = _cveMatCreate()
_cveFindContoursTyped("Mat", $thresh_img, "VectorOfVectorOfPoint", $cnts, "Mat", $_, $CV_RETR_EXTERNAL, $CV_CHAIN_APPROX_SIMPLE)- Install CMAKE >= 3.5
- Install visual studio >= 2017
- Install Git for Windows
- Install nodejs
In Git BASH, excute the following commands
# get the source files
git clone https://github.com/smbape/node-emgucv-autoit-generator
cd node-emgucv-autoit-generator
# Install nodejs dependencies
npm ci
# Install submodules
git submodule update --init --recursive
# Build emgucv cvextern.dll
git apply -v emgucv.patch --directory emgucv
find emgucv/ -type f -name '*.bat' -exec unix2dos '{}' \;
(cd $(realpath emgucv)/platforms/windows; CMAKE_BUILD_TYPE=Release ADDITIONAL_BUILD_TARGET=opencv_modules cmd.exe //c Build_Binary_x86.bat 64 nogpu vc no-openni "" "" build)node generate.jsI wanted to use OpenCV v4+ in AutoIt v3.
I found the Opencv UDF on the forum.
However it was for OpenCV v2 and there was a question for OpenCV v4+ without any anwser.
Therefore, there was no other option than trying find an answer myself.
AutoIt v3 is a freeware BASIC-like scripting language designed for automating the Windows GUI and general scripting.
AutoIt v3 can use dynamic libraries (dll).
However, since v3, OpenCV does not expose all the needed functions for image processing.
It is now focused on c++ project integration.
That means, if you want to use OpenCV in AutoIt v3,
you will need to write your own dll and export as many functions as you need.
It can be tedious.
I supposed that other languages will have the same problem.
AutoIt v3 is focused on windows and .Net is, at least in the past, focused on windows.
There was a high chance that an OpenCV binding to .Net will involve dlls.
Therefore, I looked for OpenCV in .Net and I found emgucv.
emgucv is a cross platform .Net wrapper to the OpenCV image processing library.
The project has exported almost all the OpenCV functions in a dll, making their dll suitable to be used with AutoIt v3