diff --git a/.gitignore b/.gitignore
index 3f5e0f7..f1d9cb4 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1,6 +1,7 @@
etc/
build_*/
-binaries/
+dataset_*/
+binaries*/
java_gui/dist/
java_gui/build/
java_gui/bgslibrary.exe
@@ -9,4 +10,5 @@ qt_gui/
fet/etc/
*.exe
*.pdb
-*.suo
\ No newline at end of file
+*.suo
+*.dll
diff --git a/CMakeLists.txt b/CMakeLists.txt
index d8e60da..6a01cce 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -2,24 +2,44 @@ cmake_minimum_required(VERSION 2.8)
project(bgslibrary)
-set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=gnu++0x")
+# cmake -D BGS_PYTHON_SUPPORT=ON ..
+if(NOT DEFINED BGS_PYTHON_SUPPORT)
+ set(BGS_PYTHON_SUPPORT OFF)
+elseif()
+ # add_definitions(-DBGS_PYTHON_SUPPORT)
+endif()
+message(STATUS "BGSLIBRARY WITH PYTHON SUPPORT: ${BGS_PYTHON_SUPPORT}")
+
+if(UNIX)
+ set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=gnu++0x")
+endif(UNIX)
+
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -std=c99")
#set(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} ${CMAKE_CURRENT_SOURCE_DIR}/cmake-modules)
-set( bgs_out_dir "." )
+# compilation mode setup
+set(CMAKE_BUILD_TYPE Release)
+#set(CMAKE_BUILD_TYPE Debug)
+
+if(WIN32)
+ set(CMAKE_CXX_FLAGS_RELEASE "${CMAKE_CXX_FLAGS_RELEASE} /MT")
+ set(CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS_DEBUG} /MTd")
+endif(WIN32)
+
+set(bgs_out_dir ".")
# First for the generic no-config case (e.g. with mingw)
-set( CMAKE_RUNTIME_OUTPUT_DIRECTORY ${bgs_out_dir} )
-set( CMAKE_LIBRARY_OUTPUT_DIRECTORY ${bgs_out_dir} )
-set( CMAKE_ARCHIVE_OUTPUT_DIRECTORY ${bgs_out_dir} )
+set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${bgs_out_dir})
+set(CMAKE_LIBRARY_OUTPUT_DIRECTORY ${bgs_out_dir})
+set(CMAKE_ARCHIVE_OUTPUT_DIRECTORY ${bgs_out_dir})
# Second, for multi-config builds (e.g. msvc)
-foreach( OUTPUTCONFIG ${CMAKE_CONFIGURATION_TYPES} )
- string( TOUPPER ${OUTPUTCONFIG} OUTPUTCONFIG )
- set( CMAKE_RUNTIME_OUTPUT_DIRECTORY_${OUTPUTCONFIG} ${bgs_out_dir} )
- set( CMAKE_LIBRARY_OUTPUT_DIRECTORY_${OUTPUTCONFIG} ${bgs_out_dir} )
- set( CMAKE_ARCHIVE_OUTPUT_DIRECTORY_${OUTPUTCONFIG} ${bgs_out_dir} )
-endforeach( OUTPUTCONFIG CMAKE_CONFIGURATION_TYPES )
-
-IF(UNIX)
+foreach(OUTPUTCONFIG ${CMAKE_CONFIGURATION_TYPES})
+ string(TOUPPER ${OUTPUTCONFIG} OUTPUTCONFIG)
+ set(CMAKE_RUNTIME_OUTPUT_DIRECTORY_${OUTPUTCONFIG} ${bgs_out_dir})
+ set(CMAKE_LIBRARY_OUTPUT_DIRECTORY_${OUTPUTCONFIG} ${bgs_out_dir})
+ set(CMAKE_ARCHIVE_OUTPUT_DIRECTORY_${OUTPUTCONFIG} ${bgs_out_dir})
+endforeach(OUTPUTCONFIG CMAKE_CONFIGURATION_TYPES)
+
+if(UNIX)
# add some standard warnings
ADD_DEFINITIONS(-Wno-variadic-macros -Wno-long-long -Wall -Wextra -Winit-self -Woverloaded-virtual -Wsign-promo -Wno-unused-parameter -pedantic -Woverloaded-virtual -Wno-unknown-pragmas)
@@ -30,6 +50,7 @@ IF(UNIX)
#ADD_DEFINITIONS(-Wconversion -Wfloat-equal)
endif(UNIX)
+set(OpenCV_STATIC OFF)
find_package(OpenCV REQUIRED)
message(STATUS "OpenCV library status:")
@@ -37,24 +58,50 @@ message(STATUS " version: ${OpenCV_VERSION}")
message(STATUS " libraries: ${OpenCV_LIBS}")
message(STATUS " include path: ${OpenCV_INCLUDE_DIRS}")
-if(${OpenCV_VERSION} VERSION_EQUAL 3 OR ${OpenCV_VERSION} VERSION_GREATER 3)
- message(FATAL_ERROR "OpenCV version is not compatible: ${OpenCV_VERSION}")
-endif()
+# if(${OpenCV_VERSION} VERSION_EQUAL 3 OR ${OpenCV_VERSION} VERSION_GREATER 3)
+# message(FATAL_ERROR "OpenCV version is not compatible: ${OpenCV_VERSION}")
+# endif()
if(${OpenCV_VERSION} VERSION_LESS 2.3.1)
message(FATAL_ERROR "OpenCV version is not compatible: ${OpenCV_VERSION}")
endif()
-file(GLOB sources FrameProcessor.cpp PreProcessor.cpp VideoAnalysis.cpp VideoCapture.cpp)
-file(GLOB main Main.cpp)
+if(BGS_PYTHON_SUPPORT)
+ set(Boost_USE_STATIC_LIBS OFF)
+ set(Boost_USE_MULTITHREADED ON)
+ set(Boost_USE_STATIC_RUNTIME OFF)
+
+ find_package(Boost REQUIRED COMPONENTS python)
+ find_package(PythonLibs REQUIRED)
+
+ message(STATUS "Boost library status:")
+ message(STATUS " version: ${Boost_VERSION}")
+ message(STATUS " libraries: ${Boost_LIBRARIES}")
+ message(STATUS " include path: ${Boost_INCLUDE_DIRS}")
+
+ message(STATUS "Python library status:")
+ message(STATUS " version: ${PYTHON_VERSION}")
+ message(STATUS " libraries: ${PYTHON_LIBRARIES}")
+ message(STATUS " include path: ${PYTHON_INCLUDE_DIRS}")
+endif()
+
+#file(GLOB sources FrameProcessor.cpp PreProcessor.cpp VideoAnalysis.cpp VideoCapture.cpp)
+file(GLOB main Main.cpp FrameProcessor.cpp PreProcessor.cpp VideoAnalysis.cpp VideoCapture.cpp)
file(GLOB demo Demo.cpp)
file(GLOB demo2 Demo2.cpp)
# list(REMOVE_ITEM sources ${demo} ${demo2})
file(GLOB_RECURSE analysis_src package_analysis/*.cpp)
-file(GLOB_RECURSE bgs_src package_bgs/*.cpp package_bgs/*.c)
-file(GLOB_RECURSE bgs_include package_bgs/*.h)
+if(BGS_PYTHON_SUPPORT)
+ file(GLOB_RECURSE bgs_src package_bgs/*.cpp package_bgs/*.c wrapper_python/*.cpp)
+ file(GLOB_RECURSE bgs_include package_bgs/*.h wrapper_python/*.h)
+ include_directories(${CMAKE_SOURCE_DIR} ${OpenCV_INCLUDE_DIRS} ${Boost_INCLUDE_DIRS} ${PYTHON_INCLUDE_DIRS})
+else()
+ file(GLOB_RECURSE bgs_src package_bgs/*.cpp package_bgs/*.c)
+ file(GLOB_RECURSE bgs_include package_bgs/*.h)
+ include_directories(${CMAKE_SOURCE_DIR} ${OpenCV_INCLUDE_DIRS})
+endif()
# GMG is not available in older OpenCV versions
if(${OpenCV_VERSION} VERSION_LESS 2.4.3)
@@ -62,10 +109,16 @@ if(${OpenCV_VERSION} VERSION_LESS 2.4.3)
list(REMOVE_ITEM bgs_src ${gmg})
endif()
-include_directories(${CMAKE_SOURCE_DIR})
-
-add_library(libbgs STATIC ${sources} ${bgs_src} ${analysis_src})
-target_link_libraries(libbgs ${OpenCV_LIBS})
+if(BGS_PYTHON_SUPPORT)
+ #add_library(libbgs SHARED ${sources} ${bgs_src} ${analysis_src})
+ add_library(libbgs SHARED ${bgs_src} ${analysis_src})
+ target_link_libraries(libbgs ${OpenCV_LIBS} ${Boost_LIBRARIES} ${PYTHON_LIBRARIES})
+ target_compile_definitions(libbgs PRIVATE BGS_PYTHON_SUPPORT=1)
+else()
+ #add_library(libbgs STATIC ${sources} ${bgs_src} ${analysis_src})
+ add_library(libbgs STATIC ${bgs_src} ${analysis_src})
+ target_link_libraries(libbgs ${OpenCV_LIBS})
+endif()
set_property(TARGET libbgs PROPERTY PUBLIC_HEADER ${bgs_include})
if(WIN32)
# set_property(TARGET libbgs PROPERTY SUFFIX ".lib")
@@ -83,7 +136,7 @@ target_link_libraries(bgs_demo ${OpenCV_LIBS} libbgs)
add_executable(bgs_demo2 ${demo2})
target_link_libraries(bgs_demo2 ${OpenCV_LIBS} libbgs)
-INSTALL(TARGETS libbgs
+install(TARGETS libbgs
bgslibrary
RUNTIME DESTINATION bin COMPONENT app
LIBRARY DESTINATION lib COMPONENT runtime
diff --git a/Demo.cpp b/Demo.cpp
index 61561be..fec54d8 100644
--- a/Demo.cpp
+++ b/Demo.cpp
@@ -17,178 +17,98 @@ along with BGSLibrary. If not, see .
#include
#include
-
-#include "package_bgs/FrameDifferenceBGS.h"
-#include "package_bgs/StaticFrameDifferenceBGS.h"
-#include "package_bgs/WeightedMovingMeanBGS.h"
-#include "package_bgs/WeightedMovingVarianceBGS.h"
-#include "package_bgs/MixtureOfGaussianV1BGS.h"
-#include "package_bgs/MixtureOfGaussianV2BGS.h"
-#include "package_bgs/AdaptiveBackgroundLearning.h"
-#include "package_bgs/AdaptiveSelectiveBackgroundLearning.h"
-
-#if CV_MAJOR_VERSION >= 2 && CV_MINOR_VERSION >= 4 && CV_SUBMINOR_VERSION >= 3
-#include "package_bgs/GMG.h"
-#endif
-
-#include "package_bgs/dp/DPAdaptiveMedianBGS.h"
-#include "package_bgs/dp/DPGrimsonGMMBGS.h"
-#include "package_bgs/dp/DPZivkovicAGMMBGS.h"
-#include "package_bgs/dp/DPMeanBGS.h"
-#include "package_bgs/dp/DPWrenGABGS.h"
-#include "package_bgs/dp/DPPratiMediodBGS.h"
-#include "package_bgs/dp/DPEigenbackgroundBGS.h"
-#include "package_bgs/dp/DPTextureBGS.h"
-
-#include "package_bgs/tb/T2FGMM_UM.h"
-#include "package_bgs/tb/T2FGMM_UV.h"
-#include "package_bgs/tb/T2FMRF_UM.h"
-#include "package_bgs/tb/T2FMRF_UV.h"
-#include "package_bgs/tb/FuzzySugenoIntegral.h"
-#include "package_bgs/tb/FuzzyChoquetIntegral.h"
-
-#include "package_bgs/lb/LBSimpleGaussian.h"
-#include "package_bgs/lb/LBFuzzyGaussian.h"
-#include "package_bgs/lb/LBMixtureOfGaussians.h"
-#include "package_bgs/lb/LBAdaptiveSOM.h"
-#include "package_bgs/lb/LBFuzzyAdaptiveSOM.h"
-
-#include "package_bgs/ck/LbpMrf.h"
-#include "package_bgs/jmo/MultiLayerBGS.h"
-// The PBAS algorithm was removed from BGSLibrary because it is
-// based on patented algorithm ViBE
-// http://www2.ulg.ac.be/telecom/research/vibe/
-//#include "package_bgs/pt/PixelBasedAdaptiveSegmenter.h"
-#include "package_bgs/av/VuMeter.h"
-#include "package_bgs/ae/KDE.h"
-#include "package_bgs/db/IndependentMultimodalBGS.h"
-#include "package_bgs/sjn/SJN_MultiCueBGS.h"
-#include "package_bgs/bl/SigmaDeltaBGS.h"
-
-#include "package_bgs/pl/SuBSENSE.h"
-#include "package_bgs/pl/LOBSTER.h"
+#include "package_bgs/bgslibrary.h"
int main(int argc, char **argv)
{
std::cout << "Using OpenCV " << CV_MAJOR_VERSION << "." << CV_MINOR_VERSION << "." << CV_SUBMINOR_VERSION << std::endl;
- CvCapture *capture = 0;
- int resize_factor = 100;
+ VideoCapture capture;
- if(argc > 1)
+ if (argc > 1)
{
std::cout << "Openning: " << argv[1] << std::endl;
- capture = cvCaptureFromAVI(argv[1]);
+ capture.open(argv[1]);
}
else
- {
- capture = cvCaptureFromCAM(0);
- resize_factor = 50; // set size = 50% of original image
- }
+ capture.open(0);
- if(!capture)
+ if (!capture.isOpened())
{
std::cerr << "Cannot initialize video!" << std::endl;
return -1;
}
-
- IplImage *frame_aux = cvQueryFrame(capture);
- IplImage *frame = cvCreateImage(cvSize((int)((frame_aux->width*resize_factor)/100) , (int)((frame_aux->height*resize_factor)/100)), frame_aux->depth, frame_aux->nChannels);
- cvResize(frame_aux, frame);
/* Background Subtraction Methods */
IBGS *bgs;
- /*** Default Package ***/
- bgs = new FrameDifferenceBGS;
- //bgs = new StaticFrameDifferenceBGS;
- //bgs = new WeightedMovingMeanBGS;
- //bgs = new WeightedMovingVarianceBGS;
- //bgs = new MixtureOfGaussianV1BGS;
- //bgs = new MixtureOfGaussianV2BGS;
+ bgs = new FrameDifference;
+ //bgs = new StaticFrameDifference;
+ //bgs = new WeightedMovingMean;
+ //bgs = new WeightedMovingVariance;
+ //bgs = new MixtureOfGaussianV1; // only on OpenCV 2.x
+ //bgs = new MixtureOfGaussianV2;
//bgs = new AdaptiveBackgroundLearning;
//bgs = new AdaptiveSelectiveBackgroundLearning;
- //bgs = new GMG;
-
- /*** DP Package (thanks to Donovan Parks) ***/
- //bgs = new DPAdaptiveMedianBGS;
- //bgs = new DPGrimsonGMMBGS;
- //bgs = new DPZivkovicAGMMBGS;
- //bgs = new DPMeanBGS;
- //bgs = new DPWrenGABGS;
- //bgs = new DPPratiMediodBGS;
- //bgs = new DPEigenbackgroundBGS;
- //bgs = new DPTextureBGS;
-
- /*** TB Package (thanks to Thierry Bouwmans, Fida EL BAF and Zhenjie Zhao) ***/
+ //bgs = new GMG; // only on OpenCV 2.x
+ //bgs = new KNN; // only on OpenCV 3.x
+ //bgs = new DPAdaptiveMedian;
+ //bgs = new DPGrimsonGMM;
+ //bgs = new DPZivkovicAGMM;
+ //bgs = new DPMean;
+ //bgs = new DPWrenGA;
+ //bgs = new DPPratiMediod;
+ //bgs = new DPEigenbackground;
+ //bgs = new DPTexture;
//bgs = new T2FGMM_UM;
//bgs = new T2FGMM_UV;
//bgs = new T2FMRF_UM;
//bgs = new T2FMRF_UV;
//bgs = new FuzzySugenoIntegral;
//bgs = new FuzzyChoquetIntegral;
-
- /*** JMO Package (thanks to Jean-Marc Odobez) ***/
- //bgs = new MultiLayerBGS;
-
- /*** PT Package (thanks to Martin Hofmann, Philipp Tiefenbacher and Gerhard Rigoll) ***/
+ //bgs = new MultiLayer;
//bgs = new PixelBasedAdaptiveSegmenter;
-
- /*** LB Package (thanks to Laurence Bender) ***/
//bgs = new LBSimpleGaussian;
//bgs = new LBFuzzyGaussian;
//bgs = new LBMixtureOfGaussians;
//bgs = new LBAdaptiveSOM;
//bgs = new LBFuzzyAdaptiveSOM;
-
- /*** LBP-MRF Package (thanks to Csaba Kertész) ***/
- //bgs = new LbpMrf;
-
- /*** AV Package (thanks to Lionel Robinault and Antoine Vacavant) ***/
+ //bgs = new LBP_MRF;
//bgs = new VuMeter;
-
- /*** EG Package (thanks to Ahmed Elgammal) ***/
//bgs = new KDE;
-
- /*** DB Package (thanks to Domenico Daniele Bloisi) ***/
- //bgs = new IndependentMultimodalBGS;
-
- /*** SJN Package (thanks to SeungJong Noh) ***/
- //bgs = new SJN_MultiCueBGS;
-
- /*** BL Package (thanks to Benjamin Laugraud) ***/
- //bgs = new SigmaDeltaBGS;
-
- /*** PL Package (thanks to Pierre-Luc) ***/
- //bgs = new SuBSENSEBGS();
- //bgs = new LOBSTERBGS();
+ //bgs = new IndependentMultimodal;
+ //bgs = new MultiCue;
+ //bgs = new SigmaDelta;
+ //bgs = new SuBSENSE;
+ //bgs = new LOBSTER;
+ //bgs = new PAWCS;
+ //bgs = new TwoPoints;
+ //bgs = new ViBe;
int key = 0;
- while(key != 'q')
+ cv::Mat img_input;
+ while (key != 'q')
{
- frame_aux = cvQueryFrame(capture);
- if(!frame_aux) break;
+ capture >> img_input;
+ if (img_input.empty()) break;
- cvResize(frame_aux, frame);
-
- cv::Mat img_input(frame);
cv::imshow("input", img_input);
cv::Mat img_mask;
cv::Mat img_bkgmodel;
bgs->process(img_input, img_mask, img_bkgmodel); // by default, it shows automatically the foreground mask image
-
+
//if(!img_mask.empty())
// cv::imshow("Foreground", img_mask);
// do something
-
+
key = cvWaitKey(33);
}
delete bgs;
+ capture.release();
cvDestroyAllWindows();
- cvReleaseCapture(&capture);
return 0;
}
diff --git a/Demo.py b/Demo.py
new file mode 100644
index 0000000..71bc352
--- /dev/null
+++ b/Demo.py
@@ -0,0 +1,84 @@
+import numpy as np
+import cv2
+import libbgs
+
+## BGS Library algorithms
+bgs = libbgs.FrameDifference()
+#bgs = libbgs.StaticFrameDifference()
+#bgs = libbgs.AdaptiveBackgroundLearning()
+#bgs = libbgs.AdaptiveSelectiveBackgroundLearning()
+#bgs = libbgs.DPAdaptiveMedian()
+#bgs = libbgs.DPEigenbackground()
+#bgs = libbgs.DPGrimsonGMM()
+#bgs = libbgs.DPMean()
+#bgs = libbgs.DPPratiMediod()
+#bgs = libbgs.DPTexture()
+#bgs = libbgs.DPWrenGA()
+#bgs = libbgs.DPZivkovicAGMM()
+#bgs = libbgs.FuzzyChoquetIntegral()
+#bgs = libbgs.FuzzySugenoIntegral()
+#bgs = libbgs.GMG() # if opencv 2.x
+#bgs = libbgs.IndependentMultimodal()
+#bgs = libbgs.KDE()
+#bgs = libbgs.KNN() # if opencv 3.x
+#bgs = libbgs.LBAdaptiveSOM()
+#bgs = libbgs.LBFuzzyAdaptiveSOM()
+#bgs = libbgs.LBFuzzyGaussian()
+#bgs = libbgs.LBMixtureOfGaussians()
+#bgs = libbgs.LBSimpleGaussian()
+#bgs = libbgs.LBP_MRF()
+#bgs = libbgs.LOBSTER()
+#bgs = libbgs.MixtureOfGaussianV1() # if opencv 2.x
+#bgs = libbgs.MixtureOfGaussianV2()
+#bgs = libbgs.MultiCue()
+#bgs = libbgs.MultiLayer()
+#bgs = libbgs.PAWCS()
+#bgs = libbgs.PixelBasedAdaptiveSegmenter()
+#bgs = libbgs.SigmaDelta()
+#bgs = libbgs.SuBSENSE()
+#bgs = libbgs.T2FGMM_UM()
+#bgs = libbgs.T2FGMM_UV()
+#bgs = libbgs.T2FMRF_UM()
+#bgs = libbgs.T2FMRF_UV()
+#bgs = libbgs.VuMeter()
+#bgs = libbgs.WeightedMovingMean()
+#bgs = libbgs.WeightedMovingVariance()
+#bgs = libbgs.TwoPoints()
+#bgs = libbgs.ViBe()
+
+video_file = "dataset/video.avi"
+
+capture = cv2.VideoCapture(video_file)
+while not capture.isOpened():
+ capture = cv2.VideoCapture(video_file)
+ cv2.waitKey(1000)
+ print "Wait for the header"
+
+pos_frame = capture.get(cv2.cv.CV_CAP_PROP_POS_FRAMES)
+while True:
+ flag, frame = capture.read()
+
+ if flag:
+ cv2.imshow('video', frame)
+ pos_frame = capture.get(cv2.cv.CV_CAP_PROP_POS_FRAMES)
+ #print str(pos_frame)+" frames"
+
+ img_output = bgs.apply(frame)
+ img_bgmodel = bgs.getBackgroundModel();
+
+ cv2.imshow('img_output', img_output)
+ cv2.imshow('img_bgmodel', img_bgmodel)
+
+ else:
+ capture.set(cv2.cv.CV_CAP_PROP_POS_FRAMES, pos_frame-1)
+ print "frame is not ready"
+ cv2.waitKey(1000)
+ # break
+
+ if 0xFF & cv2.waitKey(10) == 27:
+ break
+
+ if capture.get(cv2.cv.CV_CAP_PROP_POS_FRAMES) == capture.get(cv2.cv.CV_CAP_PROP_FRAME_COUNT):
+ break
+
+cv2.destroyAllWindows()
diff --git a/Demo2.cpp b/Demo2.cpp
index fe95c52..22c6ffc 100644
--- a/Demo2.cpp
+++ b/Demo2.cpp
@@ -17,56 +17,7 @@ along with BGSLibrary. If not, see .
#include
#include
-
-#include "package_bgs/FrameDifferenceBGS.h"
-#include "package_bgs/StaticFrameDifferenceBGS.h"
-#include "package_bgs/WeightedMovingMeanBGS.h"
-#include "package_bgs/WeightedMovingVarianceBGS.h"
-#include "package_bgs/MixtureOfGaussianV1BGS.h"
-#include "package_bgs/MixtureOfGaussianV2BGS.h"
-#include "package_bgs/AdaptiveBackgroundLearning.h"
-#include "package_bgs/AdaptiveSelectiveBackgroundLearning.h"
-
-#if CV_MAJOR_VERSION >= 2 && CV_MINOR_VERSION >= 4 && CV_SUBMINOR_VERSION >= 3
-#include "package_bgs/GMG.h"
-#endif
-
-#include "package_bgs/dp/DPAdaptiveMedianBGS.h"
-#include "package_bgs/dp/DPGrimsonGMMBGS.h"
-#include "package_bgs/dp/DPZivkovicAGMMBGS.h"
-#include "package_bgs/dp/DPMeanBGS.h"
-#include "package_bgs/dp/DPWrenGABGS.h"
-#include "package_bgs/dp/DPPratiMediodBGS.h"
-#include "package_bgs/dp/DPEigenbackgroundBGS.h"
-#include "package_bgs/dp/DPTextureBGS.h"
-
-#include "package_bgs/tb/T2FGMM_UM.h"
-#include "package_bgs/tb/T2FGMM_UV.h"
-#include "package_bgs/tb/T2FMRF_UM.h"
-#include "package_bgs/tb/T2FMRF_UV.h"
-#include "package_bgs/tb/FuzzySugenoIntegral.h"
-#include "package_bgs/tb/FuzzyChoquetIntegral.h"
-
-#include "package_bgs/lb/LBSimpleGaussian.h"
-#include "package_bgs/lb/LBFuzzyGaussian.h"
-#include "package_bgs/lb/LBMixtureOfGaussians.h"
-#include "package_bgs/lb/LBAdaptiveSOM.h"
-#include "package_bgs/lb/LBFuzzyAdaptiveSOM.h"
-
-#include "package_bgs/ck/LbpMrf.h"
-#include "package_bgs/jmo/MultiLayerBGS.h"
-// The PBAS algorithm was removed from BGSLibrary because it is
-// based on patented algorithm ViBE
-// http://www2.ulg.ac.be/telecom/research/vibe/
-//#include "package_bgs/pt/PixelBasedAdaptiveSegmenter.h"
-#include "package_bgs/av/VuMeter.h"
-#include "package_bgs/ae/KDE.h"
-#include "package_bgs/db/IndependentMultimodalBGS.h"
-#include "package_bgs/sjn/SJN_MultiCueBGS.h"
-#include "package_bgs/bl/SigmaDeltaBGS.h"
-
-#include "package_bgs/pl/SuBSENSE.h"
-#include "package_bgs/pl/LOBSTER.h"
+#include "package_bgs/bgslibrary.h"
int main(int argc, char **argv)
{
@@ -75,81 +26,60 @@ int main(int argc, char **argv)
/* Background Subtraction Methods */
IBGS *bgs;
- /*** Default Package ***/
- bgs = new FrameDifferenceBGS;
- //bgs = new StaticFrameDifferenceBGS;
- //bgs = new WeightedMovingMeanBGS;
- //bgs = new WeightedMovingVarianceBGS;
- //bgs = new MixtureOfGaussianV1BGS;
- //bgs = new MixtureOfGaussianV2BGS;
+ bgs = new FrameDifference;
+ //bgs = new StaticFrameDifference;
+ //bgs = new WeightedMovingMean;
+ //bgs = new WeightedMovingVariance;
+ //bgs = new MixtureOfGaussianV1; // only on OpenCV 2.x
+ //bgs = new MixtureOfGaussianV2;
//bgs = new AdaptiveBackgroundLearning;
//bgs = new AdaptiveSelectiveBackgroundLearning;
- //bgs = new GMG;
-
- /*** DP Package (thanks to Donovan Parks) ***/
- //bgs = new DPAdaptiveMedianBGS;
- //bgs = new DPGrimsonGMMBGS;
- //bgs = new DPZivkovicAGMMBGS;
- //bgs = new DPMeanBGS;
- //bgs = new DPWrenGABGS;
- //bgs = new DPPratiMediodBGS;
- //bgs = new DPEigenbackgroundBGS;
- //bgs = new DPTextureBGS;
-
- /*** TB Package (thanks to Thierry Bouwmans, Fida EL BAF and Zhenjie Zhao) ***/
+ //bgs = new GMG; // only on OpenCV 2.x
+ //bgs = new KNN; // only on OpenCV 3.x
+ //bgs = new DPAdaptiveMedian;
+ //bgs = new DPGrimsonGMM;
+ //bgs = new DPZivkovicAGMM;
+ //bgs = new DPMean;
+ //bgs = new DPWrenGA;
+ //bgs = new DPPratiMediod;
+ //bgs = new DPEigenbackground;
+ //bgs = new DPTexture;
//bgs = new T2FGMM_UM;
//bgs = new T2FGMM_UV;
//bgs = new T2FMRF_UM;
//bgs = new T2FMRF_UV;
//bgs = new FuzzySugenoIntegral;
//bgs = new FuzzyChoquetIntegral;
-
- /*** JMO Package (thanks to Jean-Marc Odobez) ***/
- //bgs = new MultiLayerBGS;
-
- /*** PT Package (thanks to Martin Hofmann, Philipp Tiefenbacher and Gerhard Rigoll) ***/
+ //bgs = new MultiLayer;
//bgs = new PixelBasedAdaptiveSegmenter;
-
- /*** LB Package (thanks to Laurence Bender) ***/
//bgs = new LBSimpleGaussian;
//bgs = new LBFuzzyGaussian;
//bgs = new LBMixtureOfGaussians;
//bgs = new LBAdaptiveSOM;
//bgs = new LBFuzzyAdaptiveSOM;
-
- /*** LBP-MRF Package (thanks to Csaba Kertész) ***/
- //bgs = new LbpMrf;
-
- /*** AV Package (thanks to Lionel Robinault and Antoine Vacavant) ***/
+ //bgs = new LBP_MRF;
//bgs = new VuMeter;
-
- /*** EG Package (thanks to Ahmed Elgammal) ***/
//bgs = new KDE;
-
- /*** DB Package (thanks to Domenico Daniele Bloisi) ***/
- //bgs = new IndependentMultimodalBGS;
-
- /*** SJN Package (thanks to SeungJong Noh) ***/
- //bgs = new SJN_MultiCueBGS;
-
- /*** BL Package (thanks to Benjamin Laugraud) ***/
- //bgs = new SigmaDeltaBGS;
-
- /*** PL Package (thanks to Pierre-Luc) ***/
- //bgs = new SuBSENSEBGS();
- //bgs = new LOBSTERBGS();
+ //bgs = new IndependentMultimodal;
+ //bgs = new MultiCue;
+ //bgs = new SigmaDelta;
+ //bgs = new SuBSENSE;
+ //bgs = new LOBSTER;
+ //bgs = new PAWCS;
+ //bgs = new TwoPoints;
+ //bgs = new ViBe;
int frameNumber = 1;
int key = 0;
- while(key != 'q')
+ while (key != 'q')
{
std::stringstream ss;
ss << frameNumber;
- std::string fileName = "frames/" + ss.str() + ".png";
+ std::string fileName = "dataset/frames/" + ss.str() + ".png";
std::cout << "reading " << fileName << std::endl;
cv::Mat img_input = cv::imread(fileName, CV_LOAD_IMAGE_COLOR);
-
+
if (img_input.empty())
break;
@@ -157,18 +87,19 @@ int main(int argc, char **argv)
cv::Mat img_mask;
cv::Mat img_bkgmodel;
- bgs->process(img_input, img_mask, img_bkgmodel); // by default, it shows automatically the foreground mask image
-
+ bgs->process(img_input, img_mask, img_bkgmodel);
+ // by default, "bgs->process(.)" automatically shows the foreground mask image
+ // or set "bgs->setShowOutput(false)" to disable
+
//if(!img_mask.empty())
// cv::imshow("Foreground", img_mask);
// do something
-
+
key = cvWaitKey(33);
frameNumber++;
}
cvWaitKey(0);
delete bgs;
-
cvDestroyAllWindows();
return 0;
diff --git a/FrameProcessor.cpp b/FrameProcessor.cpp
index 0cce652..5088121 100644
--- a/FrameProcessor.cpp
+++ b/FrameProcessor.cpp
@@ -37,23 +37,25 @@ namespace bgslibrary
if (enablePreProcessor)
preProcessor = new PreProcessor;
- if (enableFrameDifferenceBGS)
- frameDifference = new FrameDifferenceBGS;
+ if (enableFrameDifference)
+ frameDifference = new FrameDifference;
- if (enableStaticFrameDifferenceBGS)
- staticFrameDifference = new StaticFrameDifferenceBGS;
+ if (enableStaticFrameDifference)
+ staticFrameDifference = new StaticFrameDifference;
- if (enableWeightedMovingMeanBGS)
- weightedMovingMean = new WeightedMovingMeanBGS;
+ if (enableWeightedMovingMean)
+ weightedMovingMean = new WeightedMovingMean;
- if (enableWeightedMovingVarianceBGS)
- weightedMovingVariance = new WeightedMovingVarianceBGS;
+ if (enableWeightedMovingVariance)
+ weightedMovingVariance = new WeightedMovingVariance;
- if (enableMixtureOfGaussianV1BGS)
- mixtureOfGaussianV1BGS = new MixtureOfGaussianV1BGS;
+#if CV_MAJOR_VERSION == 2
+ if (enableMixtureOfGaussianV1)
+ mixtureOfGaussianV1 = new MixtureOfGaussianV1;
+#endif
- if (enableMixtureOfGaussianV2BGS)
- mixtureOfGaussianV2BGS = new MixtureOfGaussianV2BGS;
+ if (enableMixtureOfGaussianV2)
+ mixtureOfGaussianV2 = new MixtureOfGaussianV2;
if (enableAdaptiveBackgroundLearning)
adaptiveBackgroundLearning = new AdaptiveBackgroundLearning;
@@ -63,29 +65,29 @@ namespace bgslibrary
gmg = new GMG;
#endif
- if (enableDPAdaptiveMedianBGS)
- adaptiveMedian = new DPAdaptiveMedianBGS;
+ if (enableDPAdaptiveMedian)
+ dpAdaptiveMedian = new DPAdaptiveMedian;
- if (enableDPGrimsonGMMBGS)
- grimsonGMM = new DPGrimsonGMMBGS;
+ if (enableDPGrimsonGMM)
+ dpGrimsonGMM = new DPGrimsonGMM;
- if (enableDPZivkovicAGMMBGS)
- zivkovicAGMM = new DPZivkovicAGMMBGS;
+ if (enableDPZivkovicAGMM)
+ dpZivkovicAGMM = new DPZivkovicAGMM;
- if (enableDPMeanBGS)
- temporalMean = new DPMeanBGS;
+ if (enableDPMean)
+ dpTemporalMean = new DPMean;
- if (enableDPWrenGABGS)
- wrenGA = new DPWrenGABGS;
+ if (enableDPWrenGA)
+ dpWrenGA = new DPWrenGA;
- if (enableDPPratiMediodBGS)
- pratiMediod = new DPPratiMediodBGS;
+ if (enableDPPratiMediod)
+ dpPratiMediod = new DPPratiMediod;
- if (enableDPEigenbackgroundBGS)
- eigenBackground = new DPEigenbackgroundBGS;
+ if (enableDPEigenbackground)
+ dpEigenBackground = new DPEigenbackground;
- if (enableDPTextureBGS)
- textureBGS = new DPTextureBGS;
+ if (enableDPTexture)
+ dpTexture = new DPTexture;
if (enableT2FGMM_UM)
type2FuzzyGMM_UM = new T2FGMM_UM;
@@ -121,13 +123,15 @@ namespace bgslibrary
lbFuzzyAdaptiveSOM = new LBFuzzyAdaptiveSOM;
if (enableLbpMrf)
- lbpMrf = new LbpMrf;
+ lbpMrf = new LBP_MRF;
- if(enableMultiLayerBGS)
- multiLayerBGS = new MultiLayerBGS;
+#if CV_MAJOR_VERSION == 2
+ if (enableMultiLayer)
+ multiLayer = new MultiLayer;
+#endif
- //if(enablePBAS)
- // pixelBasedAdaptiveSegmenter = new PixelBasedAdaptiveSegmenter;
+ if (enablePBAS)
+ pixelBasedAdaptiveSegmenter = new PixelBasedAdaptiveSegmenter;
if (enableVuMeter)
vuMeter = new VuMeter;
@@ -136,19 +140,19 @@ namespace bgslibrary
kde = new KDE;
if (enableIMBS)
- imbs = new IndependentMultimodalBGS;
+ imbs = new IndependentMultimodal;
- if (enableMultiCueBGS)
- mcbgs = new SJN_MultiCueBGS;
+ if (enableMultiCue)
+ multiCue = new MultiCue;
- if (enableSigmaDeltaBGS)
- sdbgs = new SigmaDeltaBGS;
+ if (enableSigmaDelta)
+ sigmaDelta = new SigmaDelta;
- if (enableSuBSENSEBGS)
- ssbgs = new SuBSENSEBGS;
+ if (enableSuBSENSE)
+ subSENSE = new SuBSENSE;
- if (enableLOBSTERBGS)
- lobgs = new LOBSTERBGS;
+ if (enableLOBSTER)
+ lobster = new LOBSTER;
if (enableForegroundMaskAnalysis)
foregroundMaskAnalysis = new ForegroundMaskAnalysis;
@@ -171,169 +175,177 @@ namespace bgslibrary
frameNumber++;
if (enablePreProcessor)
- preProcessor->process(img_input, img_prep);
+ preProcessor->process(img_input, img_preProcessor);
- if (enableFrameDifferenceBGS)
- process("FrameDifferenceBGS", frameDifference, img_prep, img_framediff);
+ if (enableFrameDifference)
+ process("FrameDifference", frameDifference, img_preProcessor, img_frameDifference);
- if (enableStaticFrameDifferenceBGS)
- process("StaticFrameDifferenceBGS", staticFrameDifference, img_prep, img_staticfdiff);
+ if (enableStaticFrameDifference)
+ process("StaticFrameDifference", staticFrameDifference, img_preProcessor, img_staticFrameDifference);
- if (enableWeightedMovingMeanBGS)
- process("WeightedMovingMeanBGS", weightedMovingMean, img_prep, img_wmovmean);
+ if (enableWeightedMovingMean)
+ process("WeightedMovingMean", weightedMovingMean, img_preProcessor, img_weightedMovingMean);
- if (enableWeightedMovingVarianceBGS)
- process("WeightedMovingVarianceBGS", weightedMovingVariance, img_prep, img_movvar);
+ if (enableWeightedMovingVariance)
+ process("WeightedMovingVariance", weightedMovingVariance, img_preProcessor, img_weightedMovingVariance);
- if (enableMixtureOfGaussianV1BGS)
- process("MixtureOfGaussianV1BGS", mixtureOfGaussianV1BGS, img_prep, img_mog1);
+#if CV_MAJOR_VERSION == 2
+ if (enableMixtureOfGaussianV1)
+ process("MixtureOfGaussianV1", mixtureOfGaussianV1, img_preProcessor, img_mixtureOfGaussianV1);
+#endif
- if (enableMixtureOfGaussianV2BGS)
- process("MixtureOfGaussianV2BGS", mixtureOfGaussianV2BGS, img_prep, img_mog2);
+ if (enableMixtureOfGaussianV2)
+ process("MixtureOfGaussianV2", mixtureOfGaussianV2, img_preProcessor, img_mixtureOfGaussianV2);
if (enableAdaptiveBackgroundLearning)
- process("AdaptiveBackgroundLearning", adaptiveBackgroundLearning, img_prep, img_bkgl_fgmask);
+ process("AdaptiveBackgroundLearning", adaptiveBackgroundLearning, img_preProcessor, img_adaptiveBackgroundLearning);
#if CV_MAJOR_VERSION >= 2 && CV_MINOR_VERSION >= 4 && CV_SUBMINOR_VERSION >= 3
if (enableGMG)
- process("GMG", gmg, img_prep, img_gmg);
+ process("GMG", gmg, img_preProcessor, img_gmg);
#endif
- if (enableDPAdaptiveMedianBGS)
- process("DPAdaptiveMedianBGS", adaptiveMedian, img_prep, img_adpmed);
+ if (enableDPAdaptiveMedian)
+ process("DPAdaptiveMedian", dpAdaptiveMedian, img_preProcessor, img_dpAdaptiveMedian);
- if (enableDPGrimsonGMMBGS)
- process("DPGrimsonGMMBGS", grimsonGMM, img_prep, img_grigmm);
+ if (enableDPGrimsonGMM)
+ process("DPGrimsonGMM", dpGrimsonGMM, img_preProcessor, img_dpGrimsonGMM);
- if (enableDPZivkovicAGMMBGS)
- process("DPZivkovicAGMMBGS", zivkovicAGMM, img_prep, img_zivgmm);
+ if (enableDPZivkovicAGMM)
+ process("DPZivkovicAGMM", dpZivkovicAGMM, img_preProcessor, img_dpZivkovicAGMM);
- if (enableDPMeanBGS)
- process("DPMeanBGS", temporalMean, img_prep, img_tmpmean);
+ if (enableDPMean)
+ process("DPMean", dpTemporalMean, img_preProcessor, img_dpTemporalMean);
- if (enableDPWrenGABGS)
- process("DPWrenGABGS", wrenGA, img_prep, img_wrenga);
+ if (enableDPWrenGA)
+ process("DPWrenGA", dpWrenGA, img_preProcessor, img_dpWrenGA);
- if (enableDPPratiMediodBGS)
- process("DPPratiMediodBGS", pratiMediod, img_prep, img_pramed);
+ if (enableDPPratiMediod)
+ process("DPPratiMediod", dpPratiMediod, img_preProcessor, img_dpPratiMediod);
- if (enableDPEigenbackgroundBGS)
- process("DPEigenbackgroundBGS", eigenBackground, img_prep, img_eigbkg);
+ if (enableDPEigenbackground)
+ process("DPEigenbackground", dpEigenBackground, img_preProcessor, img_dpEigenBackground);
- if (enableDPTextureBGS)
- process("DPTextureBGS", textureBGS, img_prep, img_texbgs);
+ if (enableDPTexture)
+ process("DPTexture", dpTexture, img_preProcessor, img_dpTexture);
if (enableT2FGMM_UM)
- process("T2FGMM_UM", type2FuzzyGMM_UM, img_prep, img_t2fgmm_um);
+ process("T2FGMM_UM", type2FuzzyGMM_UM, img_preProcessor, img_type2FuzzyGMM_UM);
if (enableT2FGMM_UV)
- process("T2FGMM_UV", type2FuzzyGMM_UV, img_prep, img_t2fgmm_uv);
+ process("T2FGMM_UV", type2FuzzyGMM_UV, img_preProcessor, img_type2FuzzyGMM_UV);
if (enableT2FMRF_UM)
- process("T2FMRF_UM", type2FuzzyMRF_UM, img_prep, img_t2fmrf_um);
+ process("T2FMRF_UM", type2FuzzyMRF_UM, img_preProcessor, img_type2FuzzyMRF_UM);
if (enableT2FMRF_UV)
- process("T2FMRF_UV", type2FuzzyMRF_UV, img_prep, img_t2fmrf_uv);
+ process("T2FMRF_UV", type2FuzzyMRF_UV, img_preProcessor, img_type2FuzzyMRF_UV);
if (enableFuzzySugenoIntegral)
- process("FuzzySugenoIntegral", fuzzySugenoIntegral, img_prep, img_fsi);
+ process("FuzzySugenoIntegral", fuzzySugenoIntegral, img_preProcessor, img_fuzzySugenoIntegral);
if (enableFuzzyChoquetIntegral)
- process("FuzzyChoquetIntegral", fuzzyChoquetIntegral, img_prep, img_fci);
+ process("FuzzyChoquetIntegral", fuzzyChoquetIntegral, img_preProcessor, img_fuzzyChoquetIntegral);
if (enableLBSimpleGaussian)
- process("LBSimpleGaussian", lbSimpleGaussian, img_prep, img_lb_sg);
+ process("LBSimpleGaussian", lbSimpleGaussian, img_preProcessor, img_lbSimpleGaussian);
if (enableLBFuzzyGaussian)
- process("LBFuzzyGaussian", lbFuzzyGaussian, img_prep, img_lb_fg);
+ process("LBFuzzyGaussian", lbFuzzyGaussian, img_preProcessor, img_lbFuzzyGaussian);
if (enableLBMixtureOfGaussians)
- process("LBMixtureOfGaussians", lbMixtureOfGaussians, img_prep, img_lb_mog);
+ process("LBMixtureOfGaussians", lbMixtureOfGaussians, img_preProcessor, img_lbMixtureOfGaussians);
if (enableLBAdaptiveSOM)
- process("LBAdaptiveSOM", lbAdaptiveSOM, img_prep, img_lb_som);
+ process("LBAdaptiveSOM", lbAdaptiveSOM, img_preProcessor, img_lbAdaptiveSOM);
if (enableLBFuzzyAdaptiveSOM)
- process("LBFuzzyAdaptiveSOM", lbFuzzyAdaptiveSOM, img_prep, img_lb_fsom);
+ process("LBFuzzyAdaptiveSOM", lbFuzzyAdaptiveSOM, img_preProcessor, img_lbFuzzyAdaptiveSOM);
if (enableLbpMrf)
- process("LbpMrf", lbpMrf, img_prep, img_lbp_mrf);
+ process("LbpMrf", lbpMrf, img_preProcessor, img_lbpMrf);
- if(enableMultiLayerBGS)
+#if CV_MAJOR_VERSION == 2
+ if (enableMultiLayer)
{
- multiLayerBGS->setStatus(MultiLayerBGS::MLBGS_LEARN);
- //multiLayerBGS->setStatus(MultiLayerBGS::MLBGS_DETECT);
- process("MultiLayerBGS", multiLayerBGS, img_prep, img_mlbgs);
+ multiLayer->setStatus(MultiLayer::MLBGS_LEARN);
+ //multiLayer->setStatus(MultiLayer::MLBGS_DETECT);
+ process("MultiLayer", multiLayer, img_preProcessor, img_multiLayer);
}
+#endif
- //if(enablePBAS)
- // process("PBAS", pixelBasedAdaptiveSegmenter, img_prep, img_pt_pbas);
+ if (enablePBAS)
+ process("PBAS", pixelBasedAdaptiveSegmenter, img_preProcessor, img_pixelBasedAdaptiveSegmenter);
if (enableVuMeter)
- process("VuMeter", vuMeter, img_prep, img_vumeter);
+ process("VuMeter", vuMeter, img_preProcessor, img_vumeter);
if (enableKDE)
- process("KDE", kde, img_prep, img_kde);
+ process("KDE", kde, img_preProcessor, img_kde);
if (enableIMBS)
- process("IMBS", imbs, img_prep, img_imbs);
+ process("IMBS", imbs, img_preProcessor, img_imbs);
- if (enableMultiCueBGS)
- process("MultiCueBGS", mcbgs, img_prep, img_mcbgs);
+ if (enableMultiCue)
+ process("MultiCue", multiCue, img_preProcessor, img_multiCue);
- if (enableSigmaDeltaBGS)
- process("SigmaDeltaBGS", sdbgs, img_prep, img_sdbgs);
+ if (enableSigmaDelta)
+ process("SigmaDelta", sigmaDelta, img_preProcessor, img_sigmaDelta);
- if (enableSuBSENSEBGS)
- process("SuBSENSEBGS", ssbgs, img_prep, img_ssbgs);
+ if (enableSuBSENSE)
+ process("SuBSENSE", subSENSE, img_preProcessor, img_subSENSE);
- if (enableLOBSTERBGS)
- process("LOBSTERBGS", lobgs, img_prep, img_lobgs);
+ if (enableLOBSTER)
+ process("LOBSTER", lobster, img_preProcessor, img_lobster);
if (enableForegroundMaskAnalysis)
{
foregroundMaskAnalysis->stopAt = frameToStop;
foregroundMaskAnalysis->img_ref_path = imgref;
- foregroundMaskAnalysis->process(frameNumber, "FrameDifferenceBGS", img_framediff);
- foregroundMaskAnalysis->process(frameNumber, "StaticFrameDifferenceBGS", img_staticfdiff);
- foregroundMaskAnalysis->process(frameNumber, "WeightedMovingMeanBGS", img_wmovmean);
- foregroundMaskAnalysis->process(frameNumber, "WeightedMovingVarianceBGS", img_movvar);
- foregroundMaskAnalysis->process(frameNumber, "MixtureOfGaussianV1BGS", img_mog1);
- foregroundMaskAnalysis->process(frameNumber, "MixtureOfGaussianV2BGS", img_mog2);
- foregroundMaskAnalysis->process(frameNumber, "AdaptiveBackgroundLearning", img_bkgl_fgmask);
+ foregroundMaskAnalysis->process(frameNumber, "FrameDifference", img_frameDifference);
+ foregroundMaskAnalysis->process(frameNumber, "StaticFrameDifference", img_staticFrameDifference);
+ foregroundMaskAnalysis->process(frameNumber, "WeightedMovingMean", img_weightedMovingMean);
+ foregroundMaskAnalysis->process(frameNumber, "WeightedMovingVariance", img_weightedMovingVariance);
+#if CV_MAJOR_VERSION == 2
+ foregroundMaskAnalysis->process(frameNumber, "MixtureOfGaussianV1", img_mixtureOfGaussianV1);
+#endif
+ foregroundMaskAnalysis->process(frameNumber, "MixtureOfGaussianV2", img_mixtureOfGaussianV2);
+ foregroundMaskAnalysis->process(frameNumber, "AdaptiveBackgroundLearning", img_adaptiveBackgroundLearning);
#if CV_MAJOR_VERSION >= 2 && CV_MINOR_VERSION >= 4 && CV_SUBMINOR_VERSION >= 3
foregroundMaskAnalysis->process(frameNumber, "GMG", img_gmg);
#endif
- foregroundMaskAnalysis->process(frameNumber, "DPAdaptiveMedianBGS", img_adpmed);
- foregroundMaskAnalysis->process(frameNumber, "DPGrimsonGMMBGS", img_grigmm);
- foregroundMaskAnalysis->process(frameNumber, "DPZivkovicAGMMBGS", img_zivgmm);
- foregroundMaskAnalysis->process(frameNumber, "DPMeanBGS", img_tmpmean);
- foregroundMaskAnalysis->process(frameNumber, "DPWrenGABGS", img_wrenga);
- foregroundMaskAnalysis->process(frameNumber, "DPPratiMediodBGS", img_pramed);
- foregroundMaskAnalysis->process(frameNumber, "DPEigenbackgroundBGS", img_eigbkg);
- foregroundMaskAnalysis->process(frameNumber, "DPTextureBGS", img_texbgs);
- foregroundMaskAnalysis->process(frameNumber, "T2FGMM_UM", img_t2fgmm_um);
- foregroundMaskAnalysis->process(frameNumber, "T2FGMM_UV", img_t2fgmm_uv);
- foregroundMaskAnalysis->process(frameNumber, "T2FMRF_UM", img_t2fmrf_um);
- foregroundMaskAnalysis->process(frameNumber, "T2FMRF_UV", img_t2fmrf_uv);
- foregroundMaskAnalysis->process(frameNumber, "FuzzySugenoIntegral", img_fsi);
- foregroundMaskAnalysis->process(frameNumber, "FuzzyChoquetIntegral", img_fci);
- foregroundMaskAnalysis->process(frameNumber, "LBSimpleGaussian", img_lb_sg);
- foregroundMaskAnalysis->process(frameNumber, "LBFuzzyGaussian", img_lb_fg);
- foregroundMaskAnalysis->process(frameNumber, "LBMixtureOfGaussians", img_lb_mog);
- foregroundMaskAnalysis->process(frameNumber, "LBAdaptiveSOM", img_lb_som);
- foregroundMaskAnalysis->process(frameNumber, "LBFuzzyAdaptiveSOM", img_lb_fsom);
- foregroundMaskAnalysis->process(frameNumber, "LbpMrf", img_lbp_mrf);
- foregroundMaskAnalysis->process(frameNumber, "MultiLayerBGS", img_mlbgs);
- //foregroundMaskAnalysis->process(frameNumber, "PBAS", img_pt_pbas);
+ foregroundMaskAnalysis->process(frameNumber, "DPAdaptiveMedian", img_dpAdaptiveMedian);
+ foregroundMaskAnalysis->process(frameNumber, "DPGrimsonGMM", img_dpGrimsonGMM);
+ foregroundMaskAnalysis->process(frameNumber, "DPZivkovicAGMM", img_dpZivkovicAGMM);
+ foregroundMaskAnalysis->process(frameNumber, "DPMean", img_dpTemporalMean);
+ foregroundMaskAnalysis->process(frameNumber, "DPWrenGA", img_dpWrenGA);
+ foregroundMaskAnalysis->process(frameNumber, "DPPratiMediod", img_dpPratiMediod);
+ foregroundMaskAnalysis->process(frameNumber, "DPEigenbackground", img_dpEigenBackground);
+ foregroundMaskAnalysis->process(frameNumber, "DPTexture", img_dpTexture);
+ foregroundMaskAnalysis->process(frameNumber, "T2FGMM_UM", img_type2FuzzyGMM_UM);
+ foregroundMaskAnalysis->process(frameNumber, "T2FGMM_UV", img_type2FuzzyGMM_UV);
+ foregroundMaskAnalysis->process(frameNumber, "T2FMRF_UM", img_type2FuzzyMRF_UM);
+ foregroundMaskAnalysis->process(frameNumber, "T2FMRF_UV", img_type2FuzzyMRF_UV);
+ foregroundMaskAnalysis->process(frameNumber, "FuzzySugenoIntegral", img_fuzzySugenoIntegral);
+ foregroundMaskAnalysis->process(frameNumber, "FuzzyChoquetIntegral", img_fuzzyChoquetIntegral);
+ foregroundMaskAnalysis->process(frameNumber, "LBSimpleGaussian", img_lbSimpleGaussian);
+ foregroundMaskAnalysis->process(frameNumber, "LBFuzzyGaussian", img_lbFuzzyGaussian);
+ foregroundMaskAnalysis->process(frameNumber, "LBMixtureOfGaussians", img_lbMixtureOfGaussians);
+ foregroundMaskAnalysis->process(frameNumber, "LBAdaptiveSOM", img_lbAdaptiveSOM);
+ foregroundMaskAnalysis->process(frameNumber, "LBFuzzyAdaptiveSOM", img_lbFuzzyAdaptiveSOM);
+ foregroundMaskAnalysis->process(frameNumber, "LbpMrf", img_lbpMrf);
+#if CV_MAJOR_VERSION == 2
+ foregroundMaskAnalysis->process(frameNumber, "MultiLayer", img_multiLayer);
+#endif
+ foregroundMaskAnalysis->process(frameNumber, "PBAS", img_pixelBasedAdaptiveSegmenter);
foregroundMaskAnalysis->process(frameNumber, "VuMeter", img_vumeter);
foregroundMaskAnalysis->process(frameNumber, "KDE", img_kde);
foregroundMaskAnalysis->process(frameNumber, "IMBS", img_imbs);
- foregroundMaskAnalysis->process(frameNumber, "MultiCueBGS", img_mcbgs);
- foregroundMaskAnalysis->process(frameNumber, "SigmaDeltaBGS", img_sdbgs);
- foregroundMaskAnalysis->process(frameNumber, "SuBSENSEBGS", img_ssbgs);
- foregroundMaskAnalysis->process(frameNumber, "LOBSTERBGS", img_lobgs);
+ foregroundMaskAnalysis->process(frameNumber, "MultiCue", img_multiCue);
+ foregroundMaskAnalysis->process(frameNumber, "SigmaDelta", img_sigmaDelta);
+ foregroundMaskAnalysis->process(frameNumber, "SuBSENSE", img_subSENSE);
+ foregroundMaskAnalysis->process(frameNumber, "LOBSTER", img_lobster);
}
firstTime = false;
@@ -341,8 +353,8 @@ namespace bgslibrary
void FrameProcessor::finish(void)
{
- /*if(enableMultiLayerBGS)
- multiLayerBGS->finish();
+ /*if(enableMultiLayer)
+ multiLayer->finish();
if(enableLBSimpleGaussian)
lbSimpleGaussian->finish();
@@ -362,17 +374,17 @@ namespace bgslibrary
if (enableForegroundMaskAnalysis)
delete foregroundMaskAnalysis;
- if (enableLOBSTERBGS)
- delete lobgs;
+ if (enableLOBSTER)
+ delete lobster;
- if (enableSuBSENSEBGS)
- delete ssbgs;
+ if (enableSuBSENSE)
+ delete subSENSE;
- if (enableSigmaDeltaBGS)
- delete sdbgs;
+ if (enableSigmaDelta)
+ delete sigmaDelta;
- if (enableMultiCueBGS)
- delete mcbgs;
+ if (enableMultiCue)
+ delete multiCue;
if (enableIMBS)
delete imbs;
@@ -383,11 +395,13 @@ namespace bgslibrary
if (enableVuMeter)
delete vuMeter;
- //if(enablePBAS)
- // delete pixelBasedAdaptiveSegmenter;
+ if (enablePBAS)
+ delete pixelBasedAdaptiveSegmenter;
- if (enableMultiLayerBGS)
- delete multiLayerBGS;
+#if CV_MAJOR_VERSION == 2
+ if (enableMultiLayer)
+ delete multiLayer;
+#endif
if (enableLBFuzzyAdaptiveSOM)
delete lbFuzzyAdaptiveSOM;
@@ -409,7 +423,7 @@ namespace bgslibrary
delete lbpMrf;
#endif
- if(enableFuzzyChoquetIntegral)
+ if (enableFuzzyChoquetIntegral)
delete fuzzyChoquetIntegral;
if (enableFuzzySugenoIntegral)
@@ -427,29 +441,29 @@ namespace bgslibrary
if (enableT2FGMM_UM)
delete type2FuzzyGMM_UM;
- if (enableDPTextureBGS)
- delete textureBGS;
+ if (enableDPTexture)
+ delete dpTexture;
- if (enableDPEigenbackgroundBGS)
- delete eigenBackground;
+ if (enableDPEigenbackground)
+ delete dpEigenBackground;
- if (enableDPPratiMediodBGS)
- delete pratiMediod;
+ if (enableDPPratiMediod)
+ delete dpPratiMediod;
- if (enableDPWrenGABGS)
- delete wrenGA;
+ if (enableDPWrenGA)
+ delete dpWrenGA;
- if (enableDPMeanBGS)
- delete temporalMean;
+ if (enableDPMean)
+ delete dpTemporalMean;
- if (enableDPZivkovicAGMMBGS)
- delete zivkovicAGMM;
+ if (enableDPZivkovicAGMM)
+ delete dpZivkovicAGMM;
- if (enableDPGrimsonGMMBGS)
- delete grimsonGMM;
+ if (enableDPGrimsonGMM)
+ delete dpGrimsonGMM;
- if (enableDPAdaptiveMedianBGS)
- delete adaptiveMedian;
+ if (enableDPAdaptiveMedian)
+ delete dpAdaptiveMedian;
#if CV_MAJOR_VERSION >= 2 && CV_MINOR_VERSION >= 4 && CV_SUBMINOR_VERSION >= 3
if (enableGMG)
@@ -459,22 +473,24 @@ namespace bgslibrary
if (enableAdaptiveBackgroundLearning)
delete adaptiveBackgroundLearning;
- if (enableMixtureOfGaussianV2BGS)
- delete mixtureOfGaussianV2BGS;
+ if (enableMixtureOfGaussianV2)
+ delete mixtureOfGaussianV2;
- if (enableMixtureOfGaussianV1BGS)
- delete mixtureOfGaussianV1BGS;
+#if CV_MAJOR_VERSION == 2
+ if (enableMixtureOfGaussianV1)
+ delete mixtureOfGaussianV1;
+#endif
- if (enableWeightedMovingVarianceBGS)
+ if (enableWeightedMovingVariance)
delete weightedMovingVariance;
- if (enableWeightedMovingMeanBGS)
+ if (enableWeightedMovingMean)
delete weightedMovingMean;
- if (enableStaticFrameDifferenceBGS)
+ if (enableStaticFrameDifference)
delete staticFrameDifference;
- if (enableFrameDifferenceBGS)
+ if (enableFrameDifference)
delete frameDifference;
if (enablePreProcessor)
@@ -503,25 +519,27 @@ namespace bgslibrary
cvWriteInt(fs, "enableForegroundMaskAnalysis", enableForegroundMaskAnalysis);
- cvWriteInt(fs, "enableFrameDifferenceBGS", enableFrameDifferenceBGS);
- cvWriteInt(fs, "enableStaticFrameDifferenceBGS", enableStaticFrameDifferenceBGS);
- cvWriteInt(fs, "enableWeightedMovingMeanBGS", enableWeightedMovingMeanBGS);
- cvWriteInt(fs, "enableWeightedMovingVarianceBGS", enableWeightedMovingVarianceBGS);
- cvWriteInt(fs, "enableMixtureOfGaussianV1BGS", enableMixtureOfGaussianV1BGS);
- cvWriteInt(fs, "enableMixtureOfGaussianV2BGS", enableMixtureOfGaussianV2BGS);
+ cvWriteInt(fs, "enableFrameDifference", enableFrameDifference);
+ cvWriteInt(fs, "enableStaticFrameDifference", enableStaticFrameDifference);
+ cvWriteInt(fs, "enableWeightedMovingMean", enableWeightedMovingMean);
+ cvWriteInt(fs, "enableWeightedMovingVariance", enableWeightedMovingVariance);
+#if CV_MAJOR_VERSION == 2
+ cvWriteInt(fs, "enableMixtureOfGaussianV1", enableMixtureOfGaussianV1);
+#endif
+ cvWriteInt(fs, "enableMixtureOfGaussianV2", enableMixtureOfGaussianV2);
cvWriteInt(fs, "enableAdaptiveBackgroundLearning", enableAdaptiveBackgroundLearning);
#if CV_MAJOR_VERSION >= 2 && CV_MINOR_VERSION >= 4 && CV_SUBMINOR_VERSION >= 3
cvWriteInt(fs, "enableGMG", enableGMG);
#endif
- cvWriteInt(fs, "enableDPAdaptiveMedianBGS", enableDPAdaptiveMedianBGS);
- cvWriteInt(fs, "enableDPGrimsonGMMBGS", enableDPGrimsonGMMBGS);
- cvWriteInt(fs, "enableDPZivkovicAGMMBGS", enableDPZivkovicAGMMBGS);
- cvWriteInt(fs, "enableDPMeanBGS", enableDPMeanBGS);
- cvWriteInt(fs, "enableDPWrenGABGS", enableDPWrenGABGS);
- cvWriteInt(fs, "enableDPPratiMediodBGS", enableDPPratiMediodBGS);
- cvWriteInt(fs, "enableDPEigenbackgroundBGS", enableDPEigenbackgroundBGS);
- cvWriteInt(fs, "enableDPTextureBGS", enableDPTextureBGS);
+ cvWriteInt(fs, "enableDPAdaptiveMedian", enableDPAdaptiveMedian);
+ cvWriteInt(fs, "enableDPGrimsonGMM", enableDPGrimsonGMM);
+ cvWriteInt(fs, "enableDPZivkovicAGMM", enableDPZivkovicAGMM);
+ cvWriteInt(fs, "enableDPMean", enableDPMean);
+ cvWriteInt(fs, "enableDPWrenGA", enableDPWrenGA);
+ cvWriteInt(fs, "enableDPPratiMediod", enableDPPratiMediod);
+ cvWriteInt(fs, "enableDPEigenbackground", enableDPEigenbackground);
+ cvWriteInt(fs, "enableDPTexture", enableDPTexture);
cvWriteInt(fs, "enableT2FGMM_UM", enableT2FGMM_UM);
cvWriteInt(fs, "enableT2FGMM_UV", enableT2FGMM_UV);
@@ -538,15 +556,17 @@ namespace bgslibrary
cvWriteInt(fs, "enableLbpMrf", enableLbpMrf);
- cvWriteInt(fs, "enableMultiLayerBGS", enableMultiLayerBGS);
- //cvWriteInt(fs, "enablePBAS", enablePBAS);
+#if CV_MAJOR_VERSION == 2
+ cvWriteInt(fs, "enableMultiLayer", enableMultiLayer);
+#endif
+ cvWriteInt(fs, "enablePBAS", enablePBAS);
cvWriteInt(fs, "enableVuMeter", enableVuMeter);
cvWriteInt(fs, "enableKDE", enableKDE);
cvWriteInt(fs, "enableIMBS", enableIMBS);
- cvWriteInt(fs, "enableMultiCueBGS", enableMultiCueBGS);
- cvWriteInt(fs, "enableSigmaDeltaBGS", enableSigmaDeltaBGS);
- cvWriteInt(fs, "enableSuBSENSEBGS", enableSuBSENSEBGS);
- cvWriteInt(fs, "enableLOBSTERBGS", enableLOBSTERBGS);
+ cvWriteInt(fs, "enableMultiCue", enableMultiCue);
+ cvWriteInt(fs, "enableSigmaDelta", enableSigmaDelta);
+ cvWriteInt(fs, "enableSuBSENSE", enableSuBSENSE);
+ cvWriteInt(fs, "enableLOBSTER", enableLOBSTER);
cvReleaseFileStorage(&fs);
}
@@ -561,25 +581,27 @@ namespace bgslibrary
enableForegroundMaskAnalysis = cvReadIntByName(fs, 0, "enableForegroundMaskAnalysis", false);
- enableFrameDifferenceBGS = cvReadIntByName(fs, 0, "enableFrameDifferenceBGS", false);
- enableStaticFrameDifferenceBGS = cvReadIntByName(fs, 0, "enableStaticFrameDifferenceBGS", false);
- enableWeightedMovingMeanBGS = cvReadIntByName(fs, 0, "enableWeightedMovingMeanBGS", false);
- enableWeightedMovingVarianceBGS = cvReadIntByName(fs, 0, "enableWeightedMovingVarianceBGS", false);
- enableMixtureOfGaussianV1BGS = cvReadIntByName(fs, 0, "enableMixtureOfGaussianV1BGS", false);
- enableMixtureOfGaussianV2BGS = cvReadIntByName(fs, 0, "enableMixtureOfGaussianV2BGS", false);
+ enableFrameDifference = cvReadIntByName(fs, 0, "enableFrameDifference", false);
+ enableStaticFrameDifference = cvReadIntByName(fs, 0, "enableStaticFrameDifference", false);
+ enableWeightedMovingMean = cvReadIntByName(fs, 0, "enableWeightedMovingMean", false);
+ enableWeightedMovingVariance = cvReadIntByName(fs, 0, "enableWeightedMovingVariance", false);
+#if CV_MAJOR_VERSION == 2
+ enableMixtureOfGaussianV1 = cvReadIntByName(fs, 0, "enableMixtureOfGaussianV1", false);
+#endif
+ enableMixtureOfGaussianV2 = cvReadIntByName(fs, 0, "enableMixtureOfGaussianV2", false);
enableAdaptiveBackgroundLearning = cvReadIntByName(fs, 0, "enableAdaptiveBackgroundLearning", false);
#if CV_MAJOR_VERSION >= 2 && CV_MINOR_VERSION >= 4 && CV_SUBMINOR_VERSION >= 3
enableGMG = cvReadIntByName(fs, 0, "enableGMG", false);
#endif
- enableDPAdaptiveMedianBGS = cvReadIntByName(fs, 0, "enableDPAdaptiveMedianBGS", false);
- enableDPGrimsonGMMBGS = cvReadIntByName(fs, 0, "enableDPGrimsonGMMBGS", false);
- enableDPZivkovicAGMMBGS = cvReadIntByName(fs, 0, "enableDPZivkovicAGMMBGS", false);
- enableDPMeanBGS = cvReadIntByName(fs, 0, "enableDPMeanBGS", false);
- enableDPWrenGABGS = cvReadIntByName(fs, 0, "enableDPWrenGABGS", false);
- enableDPPratiMediodBGS = cvReadIntByName(fs, 0, "enableDPPratiMediodBGS", false);
- enableDPEigenbackgroundBGS = cvReadIntByName(fs, 0, "enableDPEigenbackgroundBGS", false);
- enableDPTextureBGS = cvReadIntByName(fs, 0, "enableDPTextureBGS", false);
+ enableDPAdaptiveMedian = cvReadIntByName(fs, 0, "enableDPAdaptiveMedian", false);
+ enableDPGrimsonGMM = cvReadIntByName(fs, 0, "enableDPGrimsonGMM", false);
+ enableDPZivkovicAGMM = cvReadIntByName(fs, 0, "enableDPZivkovicAGMM", false);
+ enableDPMean = cvReadIntByName(fs, 0, "enableDPMean", false);
+ enableDPWrenGA = cvReadIntByName(fs, 0, "enableDPWrenGA", false);
+ enableDPPratiMediod = cvReadIntByName(fs, 0, "enableDPPratiMediod", false);
+ enableDPEigenbackground = cvReadIntByName(fs, 0, "enableDPEigenbackground", false);
+ enableDPTexture = cvReadIntByName(fs, 0, "enableDPTexture", false);
enableT2FGMM_UM = cvReadIntByName(fs, 0, "enableT2FGMM_UM", false);
enableT2FGMM_UV = cvReadIntByName(fs, 0, "enableT2FGMM_UV", false);
@@ -596,15 +618,17 @@ namespace bgslibrary
enableLbpMrf = cvReadIntByName(fs, 0, "enableLbpMrf", false);
- enableMultiLayerBGS = cvReadIntByName(fs, 0, "enableMultiLayerBGS", false);
- //enablePBAS = cvReadIntByName(fs, 0, "enablePBAS", false);
+#if CV_MAJOR_VERSION == 2
+ enableMultiLayer = cvReadIntByName(fs, 0, "enableMultiLayer", false);
+#endif
+ enablePBAS = cvReadIntByName(fs, 0, "enablePBAS", false);
enableVuMeter = cvReadIntByName(fs, 0, "enableVuMeter", false);
enableKDE = cvReadIntByName(fs, 0, "enableKDE", false);
enableIMBS = cvReadIntByName(fs, 0, "enableIMBS", false);
- enableMultiCueBGS = cvReadIntByName(fs, 0, "enableMultiCueBGS", false);
- enableSigmaDeltaBGS = cvReadIntByName(fs, 0, "enableSigmaDeltaBGS", false);
- enableSuBSENSEBGS = cvReadIntByName(fs, 0, "enableSuBSENSEBGS", false);
- enableLOBSTERBGS = cvReadIntByName(fs, 0, "enableLOBSTERBGS", false);
+ enableMultiCue = cvReadIntByName(fs, 0, "enableMultiCue", false);
+ enableSigmaDelta = cvReadIntByName(fs, 0, "enableSigmaDelta", false);
+ enableSuBSENSE = cvReadIntByName(fs, 0, "enableSuBSENSE", false);
+ enableLOBSTER = cvReadIntByName(fs, 0, "enableLOBSTER", false);
cvReleaseFileStorage(&fs);
}
diff --git a/FrameProcessor.h b/FrameProcessor.h
index 0bb854e..228fa4c 100644
--- a/FrameProcessor.h
+++ b/FrameProcessor.h
@@ -21,56 +21,7 @@ along with BGSLibrary. If not, see .
#include "PreProcessor.h"
#include "package_bgs/IBGS.h"
-
-#include "package_bgs/FrameDifferenceBGS.h"
-#include "package_bgs/StaticFrameDifferenceBGS.h"
-#include "package_bgs/WeightedMovingMeanBGS.h"
-#include "package_bgs/WeightedMovingVarianceBGS.h"
-#include "package_bgs/MixtureOfGaussianV1BGS.h"
-#include "package_bgs/MixtureOfGaussianV2BGS.h"
-#include "package_bgs/AdaptiveBackgroundLearning.h"
-#if CV_MAJOR_VERSION >= 2 && CV_MINOR_VERSION >= 4 && CV_SUBMINOR_VERSION >= 3
-#include "package_bgs/GMG.h"
-#endif
-
-#include "package_bgs/dp/DPAdaptiveMedianBGS.h"
-#include "package_bgs/dp/DPGrimsonGMMBGS.h"
-#include "package_bgs/dp/DPZivkovicAGMMBGS.h"
-#include "package_bgs/dp/DPMeanBGS.h"
-#include "package_bgs/dp/DPWrenGABGS.h"
-#include "package_bgs/dp/DPPratiMediodBGS.h"
-#include "package_bgs/dp/DPEigenbackgroundBGS.h"
-#include "package_bgs/dp/DPTextureBGS.h"
-
-#include "package_bgs/tb/T2FGMM_UM.h"
-#include "package_bgs/tb/T2FGMM_UV.h"
-#include "package_bgs/tb/T2FMRF_UM.h"
-#include "package_bgs/tb/T2FMRF_UV.h"
-#include "package_bgs/tb/FuzzySugenoIntegral.h"
-#include "package_bgs/tb/FuzzyChoquetIntegral.h"
-
-#include "package_bgs/lb/LBSimpleGaussian.h"
-#include "package_bgs/lb/LBFuzzyGaussian.h"
-#include "package_bgs/lb/LBMixtureOfGaussians.h"
-#include "package_bgs/lb/LBAdaptiveSOM.h"
-#include "package_bgs/lb/LBFuzzyAdaptiveSOM.h"
-
-#include "package_bgs/ck/LbpMrf.h"
-
-#include "package_bgs/jmo/MultiLayerBGS.h"
-// The PBAS algorithm was removed from BGSLibrary because it is
-// based on patented algorithm ViBE
-// http://www2.ulg.ac.be/telecom/research/vibe/
-//#include "package_bgs/pt/PixelBasedAdaptiveSegmenter.h"
-#include "package_bgs/av/VuMeter.h"
-#include "package_bgs/ae/KDE.h"
-#include "package_bgs/db/IndependentMultimodalBGS.h"
-#include "package_bgs/sjn/SJN_MultiCueBGS.h"
-#include "package_bgs/bl/SigmaDeltaBGS.h"
-
-#include "package_bgs/pl/SuBSENSE.h"
-#include "package_bgs/pl/LOBSTER.h"
-
+#include "package_bgs/bgslibrary.h"
#include "package_analysis/ForegroundMaskAnalysis.h"
namespace bgslibrary
@@ -84,35 +35,37 @@ namespace bgslibrary
double duration;
std::string tictoc;
- cv::Mat img_prep;
+ cv::Mat img_preProcessor;
PreProcessor* preProcessor;
bool enablePreProcessor;
- cv::Mat img_framediff;
- FrameDifferenceBGS* frameDifference;
- bool enableFrameDifferenceBGS;
+ cv::Mat img_frameDifference;
+ FrameDifference* frameDifference;
+ bool enableFrameDifference;
- cv::Mat img_staticfdiff;
- StaticFrameDifferenceBGS* staticFrameDifference;
- bool enableStaticFrameDifferenceBGS;
+ cv::Mat img_staticFrameDifference;
+ StaticFrameDifference* staticFrameDifference;
+ bool enableStaticFrameDifference;
- cv::Mat img_wmovmean;
- WeightedMovingMeanBGS* weightedMovingMean;
- bool enableWeightedMovingMeanBGS;
+ cv::Mat img_weightedMovingMean;
+ WeightedMovingMean* weightedMovingMean;
+ bool enableWeightedMovingMean;
- cv::Mat img_movvar;
- WeightedMovingVarianceBGS* weightedMovingVariance;
- bool enableWeightedMovingVarianceBGS;
+ cv::Mat img_weightedMovingVariance;
+ WeightedMovingVariance* weightedMovingVariance;
+ bool enableWeightedMovingVariance;
- cv::Mat img_mog1;
- MixtureOfGaussianV1BGS* mixtureOfGaussianV1BGS;
- bool enableMixtureOfGaussianV1BGS;
+#if CV_MAJOR_VERSION == 2
+ cv::Mat img_mixtureOfGaussianV1;
+ MixtureOfGaussianV1* mixtureOfGaussianV1;
+ bool enableMixtureOfGaussianV1;
+#endif
- cv::Mat img_mog2;
- MixtureOfGaussianV2BGS* mixtureOfGaussianV2BGS;
- bool enableMixtureOfGaussianV2BGS;
+ cv::Mat img_mixtureOfGaussianV2;
+ MixtureOfGaussianV2* mixtureOfGaussianV2;
+ bool enableMixtureOfGaussianV2;
- cv::Mat img_bkgl_fgmask;
+ cv::Mat img_adaptiveBackgroundLearning;
AdaptiveBackgroundLearning* adaptiveBackgroundLearning;
bool enableAdaptiveBackgroundLearning;
@@ -122,93 +75,95 @@ namespace bgslibrary
bool enableGMG;
#endif
- cv::Mat img_adpmed;
- DPAdaptiveMedianBGS* adaptiveMedian;
- bool enableDPAdaptiveMedianBGS;
+ cv::Mat img_dpAdaptiveMedian;
+ DPAdaptiveMedian* dpAdaptiveMedian;
+ bool enableDPAdaptiveMedian;
- cv::Mat img_grigmm;
- DPGrimsonGMMBGS* grimsonGMM;
- bool enableDPGrimsonGMMBGS;
+ cv::Mat img_dpGrimsonGMM;
+ DPGrimsonGMM* dpGrimsonGMM;
+ bool enableDPGrimsonGMM;
- cv::Mat img_zivgmm;
- DPZivkovicAGMMBGS* zivkovicAGMM;
- bool enableDPZivkovicAGMMBGS;
+ cv::Mat img_dpZivkovicAGMM;
+ DPZivkovicAGMM* dpZivkovicAGMM;
+ bool enableDPZivkovicAGMM;
- cv::Mat img_tmpmean;
- DPMeanBGS* temporalMean;
- bool enableDPMeanBGS;
+ cv::Mat img_dpTemporalMean;
+ DPMean* dpTemporalMean;
+ bool enableDPMean;
- cv::Mat img_wrenga;
- DPWrenGABGS* wrenGA;
- bool enableDPWrenGABGS;
+ cv::Mat img_dpWrenGA;
+ DPWrenGA* dpWrenGA;
+ bool enableDPWrenGA;
- cv::Mat img_pramed;
- DPPratiMediodBGS* pratiMediod;
- bool enableDPPratiMediodBGS;
+ cv::Mat img_dpPratiMediod;
+ DPPratiMediod* dpPratiMediod;
+ bool enableDPPratiMediod;
- cv::Mat img_eigbkg;
- DPEigenbackgroundBGS* eigenBackground;
- bool enableDPEigenbackgroundBGS;
+ cv::Mat img_dpEigenBackground;
+ DPEigenbackground* dpEigenBackground;
+ bool enableDPEigenbackground;
- cv::Mat img_texbgs;
- DPTextureBGS* textureBGS;
- bool enableDPTextureBGS;
+ cv::Mat img_dpTexture;
+ DPTexture* dpTexture;
+ bool enableDPTexture;
- cv::Mat img_t2fgmm_um;
+ cv::Mat img_type2FuzzyGMM_UM;
T2FGMM_UM* type2FuzzyGMM_UM;
bool enableT2FGMM_UM;
- cv::Mat img_t2fgmm_uv;
+ cv::Mat img_type2FuzzyGMM_UV;
T2FGMM_UV* type2FuzzyGMM_UV;
bool enableT2FGMM_UV;
- cv::Mat img_t2fmrf_um;
+ cv::Mat img_type2FuzzyMRF_UM;
T2FMRF_UM* type2FuzzyMRF_UM;
bool enableT2FMRF_UM;
- cv::Mat img_t2fmrf_uv;
+ cv::Mat img_type2FuzzyMRF_UV;
T2FMRF_UV* type2FuzzyMRF_UV;
bool enableT2FMRF_UV;
- cv::Mat img_fsi;
+ cv::Mat img_fuzzySugenoIntegral;
FuzzySugenoIntegral* fuzzySugenoIntegral;
bool enableFuzzySugenoIntegral;
- cv::Mat img_fci;
+ cv::Mat img_fuzzyChoquetIntegral;
FuzzyChoquetIntegral* fuzzyChoquetIntegral;
bool enableFuzzyChoquetIntegral;
- cv::Mat img_lb_sg;
+ cv::Mat img_lbSimpleGaussian;
LBSimpleGaussian* lbSimpleGaussian;
bool enableLBSimpleGaussian;
- cv::Mat img_lb_fg;
+ cv::Mat img_lbFuzzyGaussian;
LBFuzzyGaussian* lbFuzzyGaussian;
bool enableLBFuzzyGaussian;
- cv::Mat img_lb_mog;
+ cv::Mat img_lbMixtureOfGaussians;
LBMixtureOfGaussians* lbMixtureOfGaussians;
bool enableLBMixtureOfGaussians;
- cv::Mat img_lb_som;
+ cv::Mat img_lbAdaptiveSOM;
LBAdaptiveSOM* lbAdaptiveSOM;
bool enableLBAdaptiveSOM;
- cv::Mat img_lb_fsom;
+ cv::Mat img_lbFuzzyAdaptiveSOM;
LBFuzzyAdaptiveSOM* lbFuzzyAdaptiveSOM;
bool enableLBFuzzyAdaptiveSOM;
- cv::Mat img_lbp_mrf;
- LbpMrf* lbpMrf;
+ cv::Mat img_lbpMrf;
+ LBP_MRF* lbpMrf;
bool enableLbpMrf;
- cv::Mat img_mlbgs;
- MultiLayerBGS* multiLayerBGS;
- bool enableMultiLayerBGS;
+#if CV_MAJOR_VERSION == 2
+ cv::Mat img_multiLayer;
+ MultiLayer* multiLayer;
+ bool enableMultiLayer;
+#endif
- //cv::Mat img_pt_pbas;
- //PixelBasedAdaptiveSegmenter* pixelBasedAdaptiveSegmenter;
- //bool enablePBAS;
+ cv::Mat img_pixelBasedAdaptiveSegmenter;
+ PixelBasedAdaptiveSegmenter* pixelBasedAdaptiveSegmenter;
+ bool enablePBAS;
cv::Mat img_vumeter;
VuMeter* vuMeter;
@@ -219,24 +174,24 @@ namespace bgslibrary
bool enableKDE;
cv::Mat img_imbs;
- IndependentMultimodalBGS* imbs;
+ IndependentMultimodal* imbs;
bool enableIMBS;
- cv::Mat img_mcbgs;
- SJN_MultiCueBGS* mcbgs;
- bool enableMultiCueBGS;
+ cv::Mat img_multiCue;
+ MultiCue* multiCue;
+ bool enableMultiCue;
- cv::Mat img_sdbgs;
- SigmaDeltaBGS* sdbgs;
- bool enableSigmaDeltaBGS;
+ cv::Mat img_sigmaDelta;
+ SigmaDelta* sigmaDelta;
+ bool enableSigmaDelta;
- cv::Mat img_ssbgs;
- SuBSENSEBGS* ssbgs;
- bool enableSuBSENSEBGS;
+ cv::Mat img_subSENSE;
+ SuBSENSE* subSENSE;
+ bool enableSuBSENSE;
- cv::Mat img_lobgs;
- LOBSTERBGS* lobgs;
- bool enableLOBSTERBGS;
+ cv::Mat img_lobster;
+ LOBSTER* lobster;
+ bool enableLOBSTER;
ForegroundMaskAnalysis* foregroundMaskAnalysis;
bool enableForegroundMaskAnalysis;
diff --git a/Main.cpp b/Main.cpp
index 1d170ad..7a406d9 100644
--- a/Main.cpp
+++ b/Main.cpp
@@ -29,7 +29,7 @@ namespace bgslibrary
static void start(int argc, const char **argv)
{
std::cout << "-----------------------------------------" << std::endl;
- std::cout << "Background Subtraction Library v1.9.2 " << std::endl;
+ std::cout << "Background Subtraction Library v2.0.0 " << std::endl;
std::cout << "http://code.google.com/p/bgslibrary " << std::endl;
std::cout << "by: " << std::endl;
std::cout << "Andrews Sobral (andrewssobral@gmail.com) " << std::endl;
diff --git a/PreProcessor.cpp b/PreProcessor.cpp
index 6f4ebbe..4c13f7e 100644
--- a/PreProcessor.cpp
+++ b/PreProcessor.cpp
@@ -95,7 +95,7 @@ namespace bgslibrary
cv2DRotationMatrix(center, angle, 1.0, mapMatrix);
cvWarpAffine(image, rotatedImage, mapMatrix, CV_INTER_LINEAR + CV_WARP_FILL_OUTLIERS, cvScalarAll(0));
- cv::Mat img_rot(rotatedImage);
+ cv::Mat img_rot = cv::cvarrToMat(rotatedImage);
img_rot.copyTo(img_output);
cvReleaseImage(&image);
diff --git a/PreProcessor.h b/PreProcessor.h
index da46cce..2e6e61c 100644
--- a/PreProcessor.h
+++ b/PreProcessor.h
@@ -19,7 +19,6 @@ along with BGSLibrary. If not, see .
#include
#include
-
namespace bgslibrary
{
class PreProcessor
diff --git a/README.md b/README.md
index a35389a..3b8a3cb 100644
--- a/README.md
+++ b/README.md
@@ -4,13 +4,13 @@ A Background Subtraction Library
[](https://youtu.be/_UbERwuQ0OU)
-Last Page Update: **12/03/2017**
+Last Page Update: **18/03/2017**
-Latest Library Version: **1.9.2** (see [Release Notes](https://github.com/andrewssobral/bgslibrary/wiki/Release-notes) for more info)
+Latest Library Version: **2.0.0** (see [Release Notes](https://github.com/andrewssobral/bgslibrary/wiki/Release-notes) for more info)
-The **BGSLibrary** was developed by [Andrews Sobral](http://andrewssobral.wixsite.com/home) and provides an easy-to-use C++ framework based on [OpenCV](http://www.opencv.org/) to perform foreground-background separation in videos. The bgslibrary compiles under Windows, Linux, and Mac OS X. Currently the library contains **37** algorithms. The source code is available under [GNU GPLv3 license](https://www.gnu.org/licenses/gpl-3.0.en.html), the library is free and open source for academic purposes.
+The **BGSLibrary** was developed by [Andrews Sobral](http://andrewssobral.wixsite.com/home) and provides an easy-to-use C++ framework based on [OpenCV](http://www.opencv.org/) to perform foreground-background separation in videos. The bgslibrary is compatible with OpenCV 2.x and 3.x, and compiles under Windows, Linux, and Mac OS X. Currently the library contains **40** algorithms. The source code is available under [GNU GPLv3 license](https://www.gnu.org/licenses/gpl-3.0.en.html), the library is free and open source for academic purposes.
-Note: the BGSLibrary is based on OpenCV 2.X, if you want to use with OpenCV 3.x please check-out our [opencv3](https://github.com/andrewssobral/bgslibrary/tree/opencv3) branch.
+***Note: The [opencv3](https://github.com/andrewssobral/bgslibrary/tree/opencv3) branch will be deprecated.***
* [List of available algorithms](https://github.com/andrewssobral/bgslibrary/wiki/List-of-available-algorithms)
* [Algorithms benchmark](https://github.com/andrewssobral/bgslibrary/wiki/Algorithms-benchmark)
@@ -77,6 +77,7 @@ Some algorithms of the BGSLibrary were used successfully in the following papers
* (2013) Sobral, Andrews; Oliveira, Luciano; Schnitman, Leizer; Souza, Felippe. (**Best Paper Award**) Highway Traffic Congestion Classification Using Holistic Properties. In International Conference on Signal Processing, Pattern Recognition and Applications (SPPRA'2013), Innsbruck, Austria, Feb 2013. ([Online](http://dx.doi.org/10.2316/P.2013.798-105)) ([PDF](http://www.researchgate.net/publication/233427564_HIGHWAY_TRAFFIC_CONGESTION_CLASSIFICATION_USING_HOLISTIC_PROPERTIES))
+
Videos
------
diff --git a/VideoAnalysis.cpp b/VideoAnalysis.cpp
index 1e46542..9c8020a 100644
--- a/VideoAnalysis.cpp
+++ b/VideoAnalysis.cpp
@@ -18,7 +18,9 @@ along with BGSLibrary. If not, see .
namespace bgslibrary
{
- VideoAnalysis::VideoAnalysis() : use_file(false), use_camera(false), cameraIndex(0), use_comp(false), frameToStop(0)
+ VideoAnalysis::VideoAnalysis() :
+ use_file(false), use_camera(false), cameraIndex(0),
+ use_comp(false), frameToStop(0)
{
std::cout << "VideoAnalysis()" << std::endl;
}
@@ -32,8 +34,9 @@ namespace bgslibrary
{
bool flag = false;
+#if CV_MAJOR_VERSION == 2
const char* keys =
- "{hp|help|false|Print help message}"
+ "{hp|help|false|Print this message}"
"{uf|use_file|false|Use video file}"
"{fn|filename||Specify video file}"
"{uc|use_cam|false|Use camera}"
@@ -42,21 +45,63 @@ namespace bgslibrary
"{st|stopAt|0|Frame number to stop}"
"{im|imgref||Specify image file}"
;
+#elif CV_MAJOR_VERSION == 3
+ const std::string keys =
+ "{h help ? | | Print this message }"
+ "{uf use_file |false| Use a video file }"
+ "{fn filename | | Specify a video file }"
+ "{uc use_cam |false| Use a webcamera }"
+ "{ca camera | 0 | Specify camera index }"
+ "{co use_comp |false| Use mask comparator }"
+ "{st stopAt | 0 | Frame number to stop }"
+ "{im imgref | | Specify a image file }"
+ ;
+#endif
+
cv::CommandLineParser cmd(argc, argv, keys);
+#if CV_MAJOR_VERSION == 2
if (argc <= 1 || cmd.get("help") == true)
{
std::cout << "Usage: " << argv[0] << " [options]" << std::endl;
- std::cout << "Avaible options:" << std::endl;
+ std::cout << "Available options:" << std::endl;
cmd.printParams();
return false;
}
+#elif CV_MAJOR_VERSION == 3
+ if (argc <= 1 || cmd.has("help"))
+ {
+ std::cout << "Usage: " << argv[0] << " [options]" << std::endl;
+ std::cout << "Available options:" << std::endl;
+ cmd.printMessage();
+ return false;
+ }
+ if (!cmd.check())
+ {
+ cmd.printErrors();
+ return false;
+ }
+#endif
+
+ use_file = cmd.get("uf"); //use_file
+ filename = cmd.get("fn"); //filename
+ use_camera = cmd.get("uc"); //use_cam
+ cameraIndex = cmd.get("ca"); //camera
+ use_comp = cmd.get("co"); //use_comp
+ frameToStop = cmd.get("st"); //stopAt
+ imgref = cmd.get("im"); //imgref
+
+ std::cout << "use_file: " << use_file << std::endl;
+ std::cout << "filename: " << filename << std::endl;
+ std::cout << "use_camera: " << use_camera << std::endl;
+ std::cout << "cameraIndex: " << cameraIndex << std::endl;
+ std::cout << "use_comp: " << use_comp << std::endl;
+ std::cout << "frameToStop: " << frameToStop << std::endl;
+ std::cout << "imgref: " << imgref << std::endl;
+ //return false;
- use_file = cmd.get("use_file");
if (use_file)
{
- filename = cmd.get("filename");
-
if (filename.empty())
{
std::cout << "Specify filename" << std::endl;
@@ -66,26 +111,15 @@ namespace bgslibrary
flag = true;
}
- use_camera = cmd.get("use_cam");
if (use_camera)
- {
- cameraIndex = cmd.get("camera");
flag = true;
- }
- if (flag == true)
+ if (flag && use_comp)
{
- use_comp = cmd.get("use_comp");
- if (use_comp)
+ if (imgref.empty())
{
- frameToStop = cmd.get("stopAt");
- imgref = cmd.get("imgref");
-
- if (imgref.empty())
- {
- std::cout << "Specify image reference" << std::endl;
- return false;
- }
+ std::cout << "Specify image reference" << std::endl;
+ return false;
}
}
diff --git a/VideoCapture.cpp b/VideoCapture.cpp
index 4de5b90..b302a3f 100644
--- a/VideoCapture.cpp
+++ b/VideoCapture.cpp
@@ -15,6 +15,7 @@ You should have received a copy of the GNU General Public License
along with BGSLibrary. If not, see .
*/
#include "VideoCapture.h"
+#include
namespace bgslibrary
{
@@ -74,8 +75,11 @@ namespace bgslibrary
}
}
- VideoCapture::VideoCapture() : key(0), start_time(0), delta_time(0), freq(0), fps(0), frameNumber(0), stopAt(0),
- useCamera(false), useVideo(false), input_resize_percent(100), showOutput(true), enableFlip(false)
+ VideoCapture::VideoCapture() :
+ key(0), start_time(0), delta_time(0), freq(0),
+ fps(0), frameNumber(0), stopAt(0), useCamera(false),
+ useVideo(false), input_resize_percent(100), showOutput(true),
+ enableFlip(false), cameraIndex(0)
{
std::cout << "VideoCapture()" << std::endl;
}
@@ -101,10 +105,10 @@ namespace bgslibrary
void VideoCapture::setUpCamera()
{
std::cout << "Camera index:" << cameraIndex << std::endl;
- capture = cvCaptureFromCAM(cameraIndex);
+ capture.open(cameraIndex);
- if (!capture)
- std::cerr << "Cannot open initialize webcam!\n" << std::endl;
+ if (!capture.isOpened())
+ std::cerr << "Cannot initialize webcam!\n" << std::endl;
}
void VideoCapture::setVideo(std::string filename)
@@ -117,10 +121,13 @@ namespace bgslibrary
void VideoCapture::setUpVideo()
{
- capture = cvCaptureFromFile(videoFileName.c_str());
+ std::cout << "Openning: " << videoFileName << std::endl;
+ capture.open(videoFileName.c_str());
- if (!capture)
+ if (!capture.isOpened())
std::cerr << "Cannot open video file " << videoFileName << std::endl;
+ else
+ std::cout << "OK" << std::endl;
}
void VideoCapture::start()
@@ -129,17 +136,21 @@ namespace bgslibrary
if (useCamera) setUpCamera();
if (useVideo) setUpVideo();
- if (!capture) std::cerr << "Capture error..." << std::endl;
+ //if (!capture) std::cerr << "Capture error..." << std::endl;
- int input_fps = cvGetCaptureProperty(capture, CV_CAP_PROP_FPS);
+ int input_fps = capture.get(CV_CAP_PROP_FPS);
std::cout << "input->fps:" << input_fps << std::endl;
+ /*
IplImage* frame1 = cvQueryFrame(capture);
- frame = cvCreateImage(cvSize((int)((frame1->width*input_resize_percent) / 100), (int)((frame1->height*input_resize_percent) / 100)), frame1->depth, frame1->nChannels);
+ frame = cvCreateImage(cvSize(
+ (int)((frame1->width*input_resize_percent) / 100),
+ (int)((frame1->height*input_resize_percent) / 100)), frame1->depth, frame1->nChannels);
//cvCreateImage(cvSize(frame1->width/input_resize_factor, frame1->height/input_resize_factor), frame1->depth, frame1->nChannels);
std::cout << "input->resize_percent:" << input_resize_percent << std::endl;
std::cout << "input->width:" << frame->width << std::endl;
std::cout << "input->height:" << frame->height << std::endl;
+ */
double loopDelay = 33.333;
if (input_fps > 0)
@@ -152,13 +163,14 @@ namespace bgslibrary
{
frameNumber++;
- frame1 = cvQueryFrame(capture);
- if (!frame1) break;
+ cv::Mat frame;
+ capture >> frame;
+ if (frame.empty()) break;
- cvResize(frame1, frame);
+ //cvResize(frame1, frame);
- if (enableFlip)
- cvFlip(frame, frame, 0);
+ //if (enableFlip)
+ // cvFlip(frame, frame, 0);
if (VC_ROI::use_roi == true && VC_ROI::roi_defined == false && firstTime == true)
{
@@ -166,7 +178,9 @@ namespace bgslibrary
do
{
- cv::Mat img_input(frame);
+ //cv::Mat img_input = cv::cvarrToMat(frame);
+ cv::Mat img_input;
+ frame.copyTo(img_input);
if (showOutput)
{
@@ -202,11 +216,13 @@ namespace bgslibrary
if (VC_ROI::use_roi == true && VC_ROI::roi_defined == true)
{
- CvRect rect = cvRect(VC_ROI::roi_x0, VC_ROI::roi_y0, VC_ROI::roi_x1 - VC_ROI::roi_x0, VC_ROI::roi_y1 - VC_ROI::roi_y0);
- cvSetImageROI(frame, rect);
+ cv::Rect roi(VC_ROI::roi_x0, VC_ROI::roi_y0, VC_ROI::roi_x1 - VC_ROI::roi_x0, VC_ROI::roi_y1 - VC_ROI::roi_y0);
+ frame = frame(roi);
}
- cv::Mat img_input(frame);
+ //cv::Mat img_input = cv::cvarrToMat(frame);
+ cv::Mat img_input;
+ frame.copyTo(img_input);
if (showOutput)
cv::imshow("Input", img_input);
@@ -221,7 +237,7 @@ namespace bgslibrary
fps = freq / delta_time;
//std::cout << "FPS: " << fps << std::endl;
- cvResetImageROI(frame);
+ //cvResetImageROI(frame);
key = cvWaitKey(loopDelay);
//std::cout << "key: " << key << std::endl;
@@ -238,7 +254,7 @@ namespace bgslibrary
firstTime = false;
} while (1);
- cvReleaseCapture(&capture);
+ capture.release();
}
void VideoCapture::saveConfig()
diff --git a/VideoCapture.h b/VideoCapture.h
index a8ba2ff..0e88c87 100644
--- a/VideoCapture.h
+++ b/VideoCapture.h
@@ -18,7 +18,8 @@ along with BGSLibrary. If not, see .
#include
#include
-
+#include
+#include
#include "Config.h"
#include "IFrameProcessor.h"
@@ -29,7 +30,7 @@ namespace bgslibrary
{
private:
IFrameProcessor* frameProcessor;
- CvCapture* capture;
+ cv::VideoCapture capture;
IplImage* frame;
int key;
int64 start_time;
diff --git a/config/FrameProcessor.xml b/config/FrameProcessor.xml
index 5155bbf..3cf398c 100644
--- a/config/FrameProcessor.xml
+++ b/config/FrameProcessor.xml
@@ -3,22 +3,22 @@
""
1
0
-1
-0
-0
-0
-0
-0
+1
+0
+0
+0
+0
+0
0
0
-0
-0
-0
-0
-0
-0
-0
-0
+0
+0
+0
+0
+0
+0
+0
+0
0
0
0
@@ -31,12 +31,13 @@
0
0
0
-0
+0
+0
0
0
0
-0
-0
-0
-0
+0
+0
+0
+0
diff --git a/dataset/demo.avi b/dataset/demo.avi
new file mode 100644
index 0000000..df20707
Binary files /dev/null and b/dataset/demo.avi differ
diff --git a/frames/1.png b/dataset/frames/1.png
similarity index 100%
rename from frames/1.png
rename to dataset/frames/1.png
diff --git a/frames/10.png b/dataset/frames/10.png
similarity index 100%
rename from frames/10.png
rename to dataset/frames/10.png
diff --git a/frames/11.png b/dataset/frames/11.png
similarity index 100%
rename from frames/11.png
rename to dataset/frames/11.png
diff --git a/frames/12.png b/dataset/frames/12.png
similarity index 100%
rename from frames/12.png
rename to dataset/frames/12.png
diff --git a/frames/13.png b/dataset/frames/13.png
similarity index 100%
rename from frames/13.png
rename to dataset/frames/13.png
diff --git a/frames/14.png b/dataset/frames/14.png
similarity index 100%
rename from frames/14.png
rename to dataset/frames/14.png
diff --git a/frames/15.png b/dataset/frames/15.png
similarity index 100%
rename from frames/15.png
rename to dataset/frames/15.png
diff --git a/frames/16.png b/dataset/frames/16.png
similarity index 100%
rename from frames/16.png
rename to dataset/frames/16.png
diff --git a/frames/17.png b/dataset/frames/17.png
similarity index 100%
rename from frames/17.png
rename to dataset/frames/17.png
diff --git a/frames/18.png b/dataset/frames/18.png
similarity index 100%
rename from frames/18.png
rename to dataset/frames/18.png
diff --git a/frames/19.png b/dataset/frames/19.png
similarity index 100%
rename from frames/19.png
rename to dataset/frames/19.png
diff --git a/frames/2.png b/dataset/frames/2.png
similarity index 100%
rename from frames/2.png
rename to dataset/frames/2.png
diff --git a/frames/20.png b/dataset/frames/20.png
similarity index 100%
rename from frames/20.png
rename to dataset/frames/20.png
diff --git a/frames/21.png b/dataset/frames/21.png
similarity index 100%
rename from frames/21.png
rename to dataset/frames/21.png
diff --git a/frames/22.png b/dataset/frames/22.png
similarity index 100%
rename from frames/22.png
rename to dataset/frames/22.png
diff --git a/frames/23.png b/dataset/frames/23.png
similarity index 100%
rename from frames/23.png
rename to dataset/frames/23.png
diff --git a/frames/24.png b/dataset/frames/24.png
similarity index 100%
rename from frames/24.png
rename to dataset/frames/24.png
diff --git a/frames/25.png b/dataset/frames/25.png
similarity index 100%
rename from frames/25.png
rename to dataset/frames/25.png
diff --git a/frames/26.png b/dataset/frames/26.png
similarity index 100%
rename from frames/26.png
rename to dataset/frames/26.png
diff --git a/frames/27.png b/dataset/frames/27.png
similarity index 100%
rename from frames/27.png
rename to dataset/frames/27.png
diff --git a/frames/28.png b/dataset/frames/28.png
similarity index 100%
rename from frames/28.png
rename to dataset/frames/28.png
diff --git a/frames/29.png b/dataset/frames/29.png
similarity index 100%
rename from frames/29.png
rename to dataset/frames/29.png
diff --git a/frames/3.png b/dataset/frames/3.png
similarity index 100%
rename from frames/3.png
rename to dataset/frames/3.png
diff --git a/frames/30.png b/dataset/frames/30.png
similarity index 100%
rename from frames/30.png
rename to dataset/frames/30.png
diff --git a/frames/31.png b/dataset/frames/31.png
similarity index 100%
rename from frames/31.png
rename to dataset/frames/31.png
diff --git a/frames/32.png b/dataset/frames/32.png
similarity index 100%
rename from frames/32.png
rename to dataset/frames/32.png
diff --git a/frames/33.png b/dataset/frames/33.png
similarity index 100%
rename from frames/33.png
rename to dataset/frames/33.png
diff --git a/frames/34.png b/dataset/frames/34.png
similarity index 100%
rename from frames/34.png
rename to dataset/frames/34.png
diff --git a/frames/35.png b/dataset/frames/35.png
similarity index 100%
rename from frames/35.png
rename to dataset/frames/35.png
diff --git a/frames/36.png b/dataset/frames/36.png
similarity index 100%
rename from frames/36.png
rename to dataset/frames/36.png
diff --git a/frames/37.png b/dataset/frames/37.png
similarity index 100%
rename from frames/37.png
rename to dataset/frames/37.png
diff --git a/frames/38.png b/dataset/frames/38.png
similarity index 100%
rename from frames/38.png
rename to dataset/frames/38.png
diff --git a/frames/39.png b/dataset/frames/39.png
similarity index 100%
rename from frames/39.png
rename to dataset/frames/39.png
diff --git a/frames/4.png b/dataset/frames/4.png
similarity index 100%
rename from frames/4.png
rename to dataset/frames/4.png
diff --git a/frames/40.png b/dataset/frames/40.png
similarity index 100%
rename from frames/40.png
rename to dataset/frames/40.png
diff --git a/frames/41.png b/dataset/frames/41.png
similarity index 100%
rename from frames/41.png
rename to dataset/frames/41.png
diff --git a/frames/42.png b/dataset/frames/42.png
similarity index 100%
rename from frames/42.png
rename to dataset/frames/42.png
diff --git a/frames/43.png b/dataset/frames/43.png
similarity index 100%
rename from frames/43.png
rename to dataset/frames/43.png
diff --git a/frames/44.png b/dataset/frames/44.png
similarity index 100%
rename from frames/44.png
rename to dataset/frames/44.png
diff --git a/frames/45.png b/dataset/frames/45.png
similarity index 100%
rename from frames/45.png
rename to dataset/frames/45.png
diff --git a/frames/46.png b/dataset/frames/46.png
similarity index 100%
rename from frames/46.png
rename to dataset/frames/46.png
diff --git a/frames/47.png b/dataset/frames/47.png
similarity index 100%
rename from frames/47.png
rename to dataset/frames/47.png
diff --git a/frames/48.png b/dataset/frames/48.png
similarity index 100%
rename from frames/48.png
rename to dataset/frames/48.png
diff --git a/frames/49.png b/dataset/frames/49.png
similarity index 100%
rename from frames/49.png
rename to dataset/frames/49.png
diff --git a/frames/5.png b/dataset/frames/5.png
similarity index 100%
rename from frames/5.png
rename to dataset/frames/5.png
diff --git a/frames/50.png b/dataset/frames/50.png
similarity index 100%
rename from frames/50.png
rename to dataset/frames/50.png
diff --git a/frames/51.png b/dataset/frames/51.png
similarity index 100%
rename from frames/51.png
rename to dataset/frames/51.png
diff --git a/frames/6.png b/dataset/frames/6.png
similarity index 100%
rename from frames/6.png
rename to dataset/frames/6.png
diff --git a/frames/7.png b/dataset/frames/7.png
similarity index 100%
rename from frames/7.png
rename to dataset/frames/7.png
diff --git a/frames/8.png b/dataset/frames/8.png
similarity index 100%
rename from frames/8.png
rename to dataset/frames/8.png
diff --git a/frames/9.png b/dataset/frames/9.png
similarity index 100%
rename from frames/9.png
rename to dataset/frames/9.png
diff --git a/demos/DemoFrameDifferenceBGS.cpp b/demos/DemoFrameDifferenceBGS.cpp
deleted file mode 100644
index 5a449e2..0000000
--- a/demos/DemoFrameDifferenceBGS.cpp
+++ /dev/null
@@ -1,49 +0,0 @@
-#include
-#include
-
-
-#include "package_bgs/FrameDifferenceBGS.h"
-
-int main(int argc, char **argv)
-{
- CvCapture *capture = 0;
-
- capture = cvCaptureFromCAM(0);
- //capture = cvCaptureFromAVI("video.avi");
-
- if(!capture){
- std::cerr << "Cannot open initialize webcam!" << std::endl;
- return 1;
- }
-
- IplImage *frame = cvQueryFrame(capture);
-
- FrameDifferenceBGS* bgs = new FrameDifferenceBGS;
-
- int key = 0;
- while(key != 'q')
- {
- frame = cvQueryFrame(capture);
-
- if(!frame) break;
-
- cv::Mat img_input(frame,true);
- cv::resize(img_input,img_input,cv::Size(320,240));
- cv::imshow("input", img_input);
-
- cv::Mat img_mask;
- bgs->process(img_input, img_mask); // automatically shows the foreground mask image
-
- //if(!img_mask.empty())
- // do something
-
- key = cvWaitKey(1);
- }
-
- delete bgs;
-
- cvDestroyAllWindows();
- cvReleaseCapture(&capture);
-
- return 0;
-}
diff --git a/demos/DemoMultiLayerBGS.cpp b/demos/DemoMultiLayerBGS.cpp
deleted file mode 100644
index 08abe30..0000000
--- a/demos/DemoMultiLayerBGS.cpp
+++ /dev/null
@@ -1,49 +0,0 @@
-#include
-#include
-
-
-#include "package_bgs/jmo/MultiLayerBGS.h"
-
-int main(int argc, char **argv)
-{
- CvCapture *capture = 0;
-
- capture = cvCaptureFromCAM(0);
- //capture = cvCaptureFromAVI("video.avi");
-
- if(!capture){
- std::cerr << "Cannot open initialize webcam!" << std::endl;
- return 1;
- }
-
- IplImage *frame = cvQueryFrame(capture);
-
- MultiLayerBGS* bgs = new MultiLayerBGS;
-
- int key = 0;
- while(key != 'q')
- {
- frame = cvQueryFrame(capture);
-
- if(!frame) break;
-
- cv::Mat img_input(frame,true);
- cv::resize(img_input,img_input,cv::Size(320,240));
- cv::imshow("input", img_input);
-
- cv::Mat img_mask;
- bgs->process(img_input, img_mask); // automatically shows the foreground mask image
-
- //if(!img_mask.empty())
- // do something
-
- key = cvWaitKey(1);
- }
-
- delete bgs;
-
- cvDestroyAllWindows();
- cvReleaseCapture(&capture);
-
- return 0;
-}
diff --git a/demos/linux_ubuntu/.gitignore b/demos/linux_ubuntu/.gitignore
new file mode 100644
index 0000000..46d4288
--- /dev/null
+++ b/demos/linux_ubuntu/.gitignore
@@ -0,0 +1,8 @@
+# Ignore everything in this directory
+*
+# Except these files
+!.gitignore
+!CMakeLists.txt
+!FrameDifferenceTest.cpp
+!README.txt
+!config/
diff --git a/example_linux/CMakeLists.txt b/demos/linux_ubuntu/CMakeLists.txt
similarity index 66%
rename from example_linux/CMakeLists.txt
rename to demos/linux_ubuntu/CMakeLists.txt
index 9317e55..8cc38e8 100644
--- a/example_linux/CMakeLists.txt
+++ b/demos/linux_ubuntu/CMakeLists.txt
@@ -9,15 +9,14 @@ find_package(OpenCV REQUIRED)
file(GLOB source FrameDifferenceTest.cpp)
-file(GLOB_RECURSE bgs_src ../package_bgs/*.cpp ../package_bgs/*.c)
-file(GLOB_RECURSE bgs_include ../package_bgs/*.h)
+file(GLOB_RECURSE bgs_src ../../package_bgs/*.cpp ../../package_bgs/*.c ../../package_analysis/*.cpp)
+file(GLOB_RECURSE bgs_inc ../../package_bgs/*.h ../../package_analysis/*.h)
include_directories(${CMAKE_SOURCE_DIR})
add_library(bgs SHARED ${bgs_src})
target_link_libraries(bgs ${OpenCV_LIBS})
-set_property(TARGET bgs PROPERTY PUBLIC_HEADER ${bgs_include})
+set_property(TARGET bgs PROPERTY PUBLIC_HEADER ${bgs_inc})
add_executable(FrameDifferenceTest ${source})
target_link_libraries(FrameDifferenceTest ${OpenCV_LIBS} bgs)
-
diff --git a/example_macosx/FrameDifferenceTest.cpp b/demos/linux_ubuntu/FrameDifferenceTest.cpp
similarity index 87%
rename from example_macosx/FrameDifferenceTest.cpp
rename to demos/linux_ubuntu/FrameDifferenceTest.cpp
index 56f1e7c..7ebe8b1 100644
--- a/example_macosx/FrameDifferenceTest.cpp
+++ b/demos/linux_ubuntu/FrameDifferenceTest.cpp
@@ -2,7 +2,9 @@
#include
#include
-#include "../package_bgs/FrameDifferenceBGS.h"
+#include "../../package_bgs/FrameDifference.h"
+
+using namespace bgslibrary::algorithms;
int main(int argc, char **argv)
{
@@ -15,7 +17,7 @@ int main(int argc, char **argv)
}
IBGS *bgs;
- bgs = new FrameDifferenceBGS;
+ bgs = new FrameDifference;
IplImage *frame;
while(1)
diff --git a/example_linux/README.txt b/demos/linux_ubuntu/README.txt
similarity index 100%
rename from example_linux/README.txt
rename to demos/linux_ubuntu/README.txt
diff --git a/demos/linux_ubuntu/config/.gitignore b/demos/linux_ubuntu/config/.gitignore
new file mode 100644
index 0000000..8ee04a0
--- /dev/null
+++ b/demos/linux_ubuntu/config/.gitignore
@@ -0,0 +1,4 @@
+# Ignore everything in this directory
+*
+# Except these files
+!.gitignore
\ No newline at end of file
diff --git a/demos/macosx/.gitignore b/demos/macosx/.gitignore
new file mode 100644
index 0000000..46d4288
--- /dev/null
+++ b/demos/macosx/.gitignore
@@ -0,0 +1,8 @@
+# Ignore everything in this directory
+*
+# Except these files
+!.gitignore
+!CMakeLists.txt
+!FrameDifferenceTest.cpp
+!README.txt
+!config/
diff --git a/example_macosx/CMakeLists.txt b/demos/macosx/CMakeLists.txt
similarity index 79%
rename from example_macosx/CMakeLists.txt
rename to demos/macosx/CMakeLists.txt
index 107303f..a9775d8 100644
--- a/example_macosx/CMakeLists.txt
+++ b/demos/macosx/CMakeLists.txt
@@ -20,15 +20,14 @@ find_package(OpenCV REQUIRED)
file(GLOB source FrameDifferenceTest.cpp)
-file(GLOB_RECURSE bgs_src ../package_bgs/*.cpp ../package_bgs/*.c)
-file(GLOB_RECURSE bgs_include ../package_bgs/*.h)
+file(GLOB_RECURSE bgs_src ../../package_bgs/*.cpp ../../package_bgs/*.c ../../package_analysis/*.cpp)
+file(GLOB_RECURSE bgs_inc ../../package_bgs/*.h ../../package_analysis/*.h)
include_directories(${CMAKE_SOURCE_DIR})
add_library(bgs SHARED ${bgs_src})
target_link_libraries(bgs ${OpenCV_LIBS})
-set_property(TARGET bgs PROPERTY PUBLIC_HEADER ${bgs_include})
+set_property(TARGET bgs PROPERTY PUBLIC_HEADER ${bgs_inc})
add_executable(FrameDifferenceTest ${source})
target_link_libraries(FrameDifferenceTest ${OpenCV_LIBS} bgs)
-
diff --git a/example_linux/FrameDifferenceTest.cpp b/demos/macosx/FrameDifferenceTest.cpp
similarity index 87%
rename from example_linux/FrameDifferenceTest.cpp
rename to demos/macosx/FrameDifferenceTest.cpp
index 56f1e7c..7ebe8b1 100644
--- a/example_linux/FrameDifferenceTest.cpp
+++ b/demos/macosx/FrameDifferenceTest.cpp
@@ -2,7 +2,9 @@
#include
#include
-#include "../package_bgs/FrameDifferenceBGS.h"
+#include "../../package_bgs/FrameDifference.h"
+
+using namespace bgslibrary::algorithms;
int main(int argc, char **argv)
{
@@ -15,7 +17,7 @@ int main(int argc, char **argv)
}
IBGS *bgs;
- bgs = new FrameDifferenceBGS;
+ bgs = new FrameDifference;
IplImage *frame;
while(1)
diff --git a/example_macosx/README.txt b/demos/macosx/README.txt
similarity index 100%
rename from example_macosx/README.txt
rename to demos/macosx/README.txt
diff --git a/demos/macosx/config/.gitignore b/demos/macosx/config/.gitignore
new file mode 100644
index 0000000..8ee04a0
--- /dev/null
+++ b/demos/macosx/config/.gitignore
@@ -0,0 +1,4 @@
+# Ignore everything in this directory
+*
+# Except these files
+!.gitignore
\ No newline at end of file
diff --git a/README_CMAKE_USERS.txt b/docs/README_CMAKE_USERS_OPENCV2.txt
similarity index 70%
rename from README_CMAKE_USERS.txt
rename to docs/README_CMAKE_USERS_OPENCV2.txt
index 974e941..26c6997 100644
--- a/README_CMAKE_USERS.txt
+++ b/docs/README_CMAKE_USERS_OPENCV2.txt
@@ -15,18 +15,17 @@ Please follow the instructions below:
1) Go to Windows console.
2) Clone BGSLibrary git repository:
-e.g.: git clone https://github.com/andrewssobral/bgslibrary.git
+git clone https://github.com/andrewssobral/bgslibrary.git
3) Go to bgslibrary/build folder.
-e.g.: C:\bgslibrary\build>_
-2) Set your OpenCV PATH:
-e.g.:
-\> setlocal
-\> set OpenCV_DIR=C:\OpenCV2.4.10\build
-\> cmake -DOpenCV_DIR=%OpenCV_DIR% -G "Visual Studio 12" ..
-or:
-\> cmake -DOpenCV_DIR=%OpenCV_DIR% -G "Visual Studio 12 Win64" ..
+4) Set your OpenCV PATH:
+setlocal
+set OpenCV_DIR=C:\OpenCV2.4.10\build
+
+5) Launch CMAKE:
+(For Windows x86 32bits) cmake -DOpenCV_DIR=%OpenCV_DIR% -G "Visual Studio 12" ..
+(For Windows x64 64bits) cmake -DOpenCV_DIR=%OpenCV_DIR% -G "Visual Studio 12 Win64" ..
Now, you will see something like (for win64):
-------------------------------------------------
@@ -52,27 +51,25 @@ Now, you will see something like (for win64):
-- Build files have been written to: C:/bgslibrary/build
-------------------------------------------------
-3) Include OpenCV binaries in the system path:
-\> set PATH=%PATH%;%OpenCV_DIR%\x86\vc12\bin
-or:
-\> set PATH=%PATH%;%OpenCV_DIR%\x64\vc12\bin
+6) Include OpenCV binaries in the system path:
+(For Windows x86 32bits) set PATH=%PATH%;%OpenCV_DIR%\x86\vc12\bin
+(For Windows x64 64bits) set PATH=%PATH%;%OpenCV_DIR%\x64\vc12\bin
-4) Open 'bgs.sln' in Visual Studio and switch to 'RELEASE' mode
-4.1) Note if you are using a Visual Studio version superior than 2013, you will need to CANCEL the project wizard update. However, you can go to step (2) and change the Visual Studio version, e.g.: -G "Visual Studio XX", where XX is your Visual Studio version.
+7) Open 'bgs.sln' in Visual Studio and switch to 'RELEASE' mode
+7.1) Note if you are using a Visual Studio version superior than 2013, you will need to CANCEL the project wizard update. However, you can go to step (5) and change the Visual Studio version, e.g.: -G "Visual Studio XX", where XX is your Visual Studio version.
-5) Click on 'ALL_BUILD' project and build!
+8) Click on 'ALL_BUILD' project and build!
-6) If everything goes well, you can run bgslibrary in the Windows console as follows:
+9) If everything goes well, you can run bgslibrary in the Windows console as follows:
-6.1) Running BGSLibrary with a webcamera:
+9.1) Running BGSLibrary with a webcamera:
C:\bgslibrary> build\bgslibrary.exe --use_cam --camera=0
-6.2) Running demo code:
+9.2) Running demo code:
C:\bgslibrary> build\bgs_demo.exe dataset/video.avi
-6.3) Running demo2 code:
+9.3) Running demo2 code:
C:\bgslibrary> build\bgs_demo2.exe
Additional information:
* Note that bgslibrary requires a 'config' folder in the working directory.
-e.g.: C:\bgslibrary\config
diff --git a/docs/README_CMAKE_USERS_OPENCV3.txt b/docs/README_CMAKE_USERS_OPENCV3.txt
new file mode 100644
index 0000000..543fd86
--- /dev/null
+++ b/docs/README_CMAKE_USERS_OPENCV3.txt
@@ -0,0 +1,77 @@
+-------------------------------------------------
+-------------- WINDOWS CMAKE USERS --------------
+
+How to build BGSLibrary with OpenCV 3.2.0 and Visual Studio 2015 from CMAKE.
+
+For Linux users, please see the instruction in README_LINUX_USERS.txt file.
+
+Dependencies:
+* GIT (tested with git version 2.7.2.windows.1).
+* CMAKE for Windows (tested with cmake version 3.1.1).
+* Microsoft Visual Studio (tested with VS2015).
+
+Please follow the instructions below:
+
+1) Go to Windows console.
+
+2) Clone BGSLibrary git repository:
+git clone https://github.com/andrewssobral/bgslibrary.git
+
+3) Go to bgslibrary/build folder.
+
+4) Set your OpenCV PATH:
+setlocal
+set OpenCV_DIR=C:\OpenCV3.2.0\build
+
+5) Launch CMAKE:
+cmake -DOpenCV_DIR=%OpenCV_DIR% -G "Visual Studio 14 Win64" ..
+
+Now, you will see something like:
+-------------------------------------------------
+-- The C compiler identification is MSVC 19.0.24215.1
+-- The CXX compiler identification is MSVC 19.0.24215.1
+-- Check for working C compiler using: Visual Studio 14 2015 Win64
+-- Check for working C compiler using: Visual Studio 14 2015 Win64 -- works
+-- Detecting C compiler ABI info
+-- Detecting C compiler ABI info - done
+-- Check for working CXX compiler using: Visual Studio 14 2015 Win64
+-- Check for working CXX compiler using: Visual Studio 14 2015 Win64 -- works
+-- Detecting CXX compiler ABI info
+-- Detecting CXX compiler ABI info - done
+-- Detecting CXX compile features
+-- Detecting CXX compile features - done
+-- OpenCV ARCH: x64
+-- OpenCV RUNTIME: vc14
+-- OpenCV STATIC: ON
+-- Found OpenCV 3.2.0 in C:/OpenCV3.2.0/build/x64/vc14/lib
+-- You might need to add C:\OpenCV3.2.0\build\x64\vc14\bin to your PATH to be able to run your applications.
+-- OpenCV library status:
+-- version: 3.2.0
+-- libraries: opencv_world;opencv_videostab;opencv_videoio;opencv_video;opencv_superres;opencv_stitching;opencv_shape;opencv_photo;opencv_objdetect;opencv_ml;opencv_imgproc;opencv_imgcodecs;opencv_highgui;opencv_flann;opencv_features2d;opencv_core;opencv_calib3d
+-- include path: C:/OpenCV3.2.0/build/include;C:/OpenCV3.2.0/build/include/opencv
+-- Configuring done
+-- Generating done
+-- Build files have been written to: C:/bgslibrary/build
+-------------------------------------------------
+
+6) Include OpenCV binaries in the system path:
+set PATH=%PATH%;%OpenCV_DIR%\x64\vc14\bin
+
+7) Open 'bgs.sln' in Visual Studio and switch to 'RELEASE' mode
+7.1) Note if you are using a Visual Studio version superior than 2015, you will need to CANCEL the project wizard update. However, you can go to step (2) and change the Visual Studio version, e.g.: -G "Visual Studio XX", where XX is your Visual Studio version.
+
+8) Click on 'ALL_BUILD' project and build!
+
+9) If everything goes well, you can run bgslibrary in the Windows console as follows:
+
+9.1) Running BGSLibrary with a webcamera:
+C:\bgslibrary> build\bgslibrary.exe --use_cam --camera=0
+
+9.2) Running demo code:
+C:\bgslibrary> build\bgs_demo.exe dataset/video.avi
+
+9.3) Running demo2 code:
+C:\bgslibrary> build\bgs_demo2.exe
+
+Additional information:
+* Note that bgslibrary requires a 'config' folder in the working directory.
diff --git a/README_LINUX_USERS.txt b/docs/README_LINUX_USERS.txt
similarity index 85%
rename from README_LINUX_USERS.txt
rename to docs/README_LINUX_USERS.txt
index 5a2611f..9482f33 100644
--- a/README_LINUX_USERS.txt
+++ b/docs/README_LINUX_USERS.txt
@@ -4,6 +4,8 @@
# Requirements:
# cmake >= 2.8
# opencv >= 2.3.1
+#
+# Tested with: Ubuntu 14.04 and Ubuntu 16.04
cd build
cmake ..
@@ -17,7 +19,8 @@ export LD_LIBRARY_PATH
# Now you can run bgslibrary by: bgs -i video.avi
########################
cd ..
-chmod +x run_video.sh run_camera.sh run_demo.sh
+chmod +x *.sh
./run_video.sh
./run_camera.sh
./run_demo.sh
+./run_demo2.sh
diff --git a/README_VISUAL_STUDIO_USERS.txt b/docs/README_VS2010_OPENCV2.txt
similarity index 81%
rename from README_VISUAL_STUDIO_USERS.txt
rename to docs/README_VS2010_OPENCV2.txt
index ee9fe12..66ee0f4 100644
--- a/README_VISUAL_STUDIO_USERS.txt
+++ b/docs/README_VS2010_OPENCV2.txt
@@ -1,16 +1,13 @@
---------------------------------------------------
BGSLibrary with Visual Studio 2010 and Opencv 2.4.x
---------------------------------------------------
-
-1) Clone our VS2010 example project at [vs2010] folder
-https://github.com/andrewssobral/bgslibrary/tree/master/vs2010
-
-Or configure manually by:
+--- Tutorial for Windows x86 32 bits ---
+----------------------------------------
1) Install OpenCV
1.a) Download OpenCV 2.4.x from http://opencv.org/
-2.b) Install in: C:\OpenCV2.4.x
-2.c) Add OpenCV binaries in your Path
+1.b) Install in: C:\OpenCV2.4.x
+1.c) Add OpenCV binaries in your Path
C:\OpenCV2.4.x\build\x86\vc10\bin
2) Download BGSLibrary
@@ -22,7 +19,7 @@ C:\OpenCV2.4.x\build\x86\vc10\bin
3.c) Set project location: C:\bgslibrary
3.d) Set project name: bgslibrary
3.e) Set Empty project
-3.f) Add Demo.cpp in [Source Files]
+3.f) Add Main.cpp in [Source Files]
3.g) Add content of c:\bgslibrary\package_bgs\*.* in [Header Files]
3.h) Add content of c:\bgslibrary\package_analysis\*.* in [Header Files]
3.i) Change to [Release] [Win32] mode
diff --git a/example_linux/config/KEEP_THIS_FOLDER b/example_linux/config/KEEP_THIS_FOLDER
deleted file mode 100644
index 24353bc..0000000
--- a/example_linux/config/KEEP_THIS_FOLDER
+++ /dev/null
@@ -1 +0,0 @@
-bgslibrary uses this folder to store the configuration files
\ No newline at end of file
diff --git a/example_macosx/config/KEEP_THIS_FOLDER b/example_macosx/config/KEEP_THIS_FOLDER
deleted file mode 100644
index 24353bc..0000000
--- a/example_macosx/config/KEEP_THIS_FOLDER
+++ /dev/null
@@ -1 +0,0 @@
-bgslibrary uses this folder to store the configuration files
\ No newline at end of file
diff --git a/java_gui/README.txt b/gui_java/README.txt
similarity index 100%
rename from java_gui/README.txt
rename to gui_java/README.txt
diff --git a/java_gui/_COPY_bgslibrary.exe_HERE_ b/gui_java/_COPY_bgslibrary.exe_HERE_
similarity index 100%
rename from java_gui/_COPY_bgslibrary.exe_HERE_
rename to gui_java/_COPY_bgslibrary.exe_HERE_
diff --git a/java_gui/bgslibrary_gui.jar b/gui_java/bgslibrary_gui.jar
similarity index 100%
rename from java_gui/bgslibrary_gui.jar
rename to gui_java/bgslibrary_gui.jar
diff --git a/java_gui/bgslibrary_gui.properties b/gui_java/bgslibrary_gui.properties
similarity index 100%
rename from java_gui/bgslibrary_gui.properties
rename to gui_java/bgslibrary_gui.properties
diff --git a/java_gui/build.xml b/gui_java/build.xml
similarity index 100%
rename from java_gui/build.xml
rename to gui_java/build.xml
diff --git a/java_gui/config/.gitignore b/gui_java/config/.gitignore
similarity index 100%
rename from java_gui/config/.gitignore
rename to gui_java/config/.gitignore
diff --git a/java_gui/config/FrameProcessor.xml b/gui_java/config/FrameProcessor.xml
similarity index 100%
rename from java_gui/config/FrameProcessor.xml
rename to gui_java/config/FrameProcessor.xml
diff --git a/java_gui/config/PreProcessor.xml b/gui_java/config/PreProcessor.xml
similarity index 100%
rename from java_gui/config/PreProcessor.xml
rename to gui_java/config/PreProcessor.xml
diff --git a/java_gui/config/VideoCapture.xml b/gui_java/config/VideoCapture.xml
similarity index 100%
rename from java_gui/config/VideoCapture.xml
rename to gui_java/config/VideoCapture.xml
diff --git a/java_gui/images/bgslibrary_gui_screen01.png b/gui_java/images/bgslibrary_gui_screen01.png
similarity index 100%
rename from java_gui/images/bgslibrary_gui_screen01.png
rename to gui_java/images/bgslibrary_gui_screen01.png
diff --git a/java_gui/images/bgslibrary_gui_screen02.png b/gui_java/images/bgslibrary_gui_screen02.png
similarity index 100%
rename from java_gui/images/bgslibrary_gui_screen02.png
rename to gui_java/images/bgslibrary_gui_screen02.png
diff --git a/java_gui/images/bgslibrary_gui_screen03.png b/gui_java/images/bgslibrary_gui_screen03.png
similarity index 100%
rename from java_gui/images/bgslibrary_gui_screen03.png
rename to gui_java/images/bgslibrary_gui_screen03.png
diff --git a/java_gui/images/bgslibrary_gui_screen04.png b/gui_java/images/bgslibrary_gui_screen04.png
similarity index 100%
rename from java_gui/images/bgslibrary_gui_screen04.png
rename to gui_java/images/bgslibrary_gui_screen04.png
diff --git a/java_gui/images/logo.jpg b/gui_java/images/logo.jpg
similarity index 100%
rename from java_gui/images/logo.jpg
rename to gui_java/images/logo.jpg
diff --git a/java_gui/lib/commons-configuration-1.8.jar b/gui_java/lib/commons-configuration-1.8.jar
similarity index 100%
rename from java_gui/lib/commons-configuration-1.8.jar
rename to gui_java/lib/commons-configuration-1.8.jar
diff --git a/java_gui/lib/commons-io-2.3.jar b/gui_java/lib/commons-io-2.3.jar
similarity index 100%
rename from java_gui/lib/commons-io-2.3.jar
rename to gui_java/lib/commons-io-2.3.jar
diff --git a/java_gui/lib/commons-lang-2.6.jar b/gui_java/lib/commons-lang-2.6.jar
similarity index 100%
rename from java_gui/lib/commons-lang-2.6.jar
rename to gui_java/lib/commons-lang-2.6.jar
diff --git a/java_gui/lib/commons-logging-1.1.1.jar b/gui_java/lib/commons-logging-1.1.1.jar
similarity index 100%
rename from java_gui/lib/commons-logging-1.1.1.jar
rename to gui_java/lib/commons-logging-1.1.1.jar
diff --git a/java_gui/lib/swingx-all-1.6.3.jar b/gui_java/lib/swingx-all-1.6.3.jar
similarity index 100%
rename from java_gui/lib/swingx-all-1.6.3.jar
rename to gui_java/lib/swingx-all-1.6.3.jar
diff --git a/java_gui/lib/swingx-beaninfo-1.6.3.jar b/gui_java/lib/swingx-beaninfo-1.6.3.jar
similarity index 100%
rename from java_gui/lib/swingx-beaninfo-1.6.3.jar
rename to gui_java/lib/swingx-beaninfo-1.6.3.jar
diff --git a/java_gui/manifest.mf b/gui_java/manifest.mf
similarity index 100%
rename from java_gui/manifest.mf
rename to gui_java/manifest.mf
diff --git a/java_gui/nbproject/build-impl.xml b/gui_java/nbproject/build-impl.xml
similarity index 100%
rename from java_gui/nbproject/build-impl.xml
rename to gui_java/nbproject/build-impl.xml
diff --git a/java_gui/nbproject/genfiles.properties b/gui_java/nbproject/genfiles.properties
similarity index 100%
rename from java_gui/nbproject/genfiles.properties
rename to gui_java/nbproject/genfiles.properties
diff --git a/java_gui/nbproject/private/config.properties b/gui_java/nbproject/private/config.properties
similarity index 100%
rename from java_gui/nbproject/private/config.properties
rename to gui_java/nbproject/private/config.properties
diff --git a/java_gui/nbproject/private/private.properties b/gui_java/nbproject/private/private.properties
similarity index 100%
rename from java_gui/nbproject/private/private.properties
rename to gui_java/nbproject/private/private.properties
diff --git a/java_gui/nbproject/private/private.xml b/gui_java/nbproject/private/private.xml
similarity index 100%
rename from java_gui/nbproject/private/private.xml
rename to gui_java/nbproject/private/private.xml
diff --git a/java_gui/nbproject/project.properties b/gui_java/nbproject/project.properties
similarity index 100%
rename from java_gui/nbproject/project.properties
rename to gui_java/nbproject/project.properties
diff --git a/java_gui/nbproject/project.xml b/gui_java/nbproject/project.xml
similarity index 100%
rename from java_gui/nbproject/project.xml
rename to gui_java/nbproject/project.xml
diff --git a/java_gui/run_camera.bat b/gui_java/run_camera.bat
similarity index 100%
rename from java_gui/run_camera.bat
rename to gui_java/run_camera.bat
diff --git a/java_gui/run_java_gui.bat b/gui_java/run_java_gui.bat
similarity index 100%
rename from java_gui/run_java_gui.bat
rename to gui_java/run_java_gui.bat
diff --git a/java_gui/run_java_gui_with_console.bat b/gui_java/run_java_gui_with_console.bat
similarity index 100%
rename from java_gui/run_java_gui_with_console.bat
rename to gui_java/run_java_gui_with_console.bat
diff --git a/java_gui/run_video.bat b/gui_java/run_video.bat
similarity index 100%
rename from java_gui/run_video.bat
rename to gui_java/run_video.bat
diff --git a/java_gui/src/br/com/bgslibrary/Main.java b/gui_java/src/br/com/bgslibrary/Main.java
similarity index 100%
rename from java_gui/src/br/com/bgslibrary/Main.java
rename to gui_java/src/br/com/bgslibrary/Main.java
diff --git a/java_gui/src/br/com/bgslibrary/entity/Command.java b/gui_java/src/br/com/bgslibrary/entity/Command.java
similarity index 100%
rename from java_gui/src/br/com/bgslibrary/entity/Command.java
rename to gui_java/src/br/com/bgslibrary/entity/Command.java
diff --git a/java_gui/src/br/com/bgslibrary/entity/Configuration.java b/gui_java/src/br/com/bgslibrary/entity/Configuration.java
similarity index 100%
rename from java_gui/src/br/com/bgslibrary/entity/Configuration.java
rename to gui_java/src/br/com/bgslibrary/entity/Configuration.java
diff --git a/java_gui/src/br/com/bgslibrary/gui/AboutDialog.form b/gui_java/src/br/com/bgslibrary/gui/AboutDialog.form
similarity index 100%
rename from java_gui/src/br/com/bgslibrary/gui/AboutDialog.form
rename to gui_java/src/br/com/bgslibrary/gui/AboutDialog.form
diff --git a/java_gui/src/br/com/bgslibrary/gui/AboutDialog.java b/gui_java/src/br/com/bgslibrary/gui/AboutDialog.java
similarity index 100%
rename from java_gui/src/br/com/bgslibrary/gui/AboutDialog.java
rename to gui_java/src/br/com/bgslibrary/gui/AboutDialog.java
diff --git a/java_gui/src/br/com/bgslibrary/gui/MainFrame.form b/gui_java/src/br/com/bgslibrary/gui/MainFrame.form
similarity index 100%
rename from java_gui/src/br/com/bgslibrary/gui/MainFrame.form
rename to gui_java/src/br/com/bgslibrary/gui/MainFrame.form
diff --git a/java_gui/src/br/com/bgslibrary/gui/MainFrame.java b/gui_java/src/br/com/bgslibrary/gui/MainFrame.java
similarity index 100%
rename from java_gui/src/br/com/bgslibrary/gui/MainFrame.java
rename to gui_java/src/br/com/bgslibrary/gui/MainFrame.java
diff --git a/java_gui/src/br/com/bgslibrary/resources/logo.jpg b/gui_java/src/br/com/bgslibrary/resources/logo.jpg
similarity index 100%
rename from java_gui/src/br/com/bgslibrary/resources/logo.jpg
rename to gui_java/src/br/com/bgslibrary/resources/logo.jpg
diff --git a/vs2010mfc/.gitignore b/gui_mfc/.gitignore
similarity index 100%
rename from vs2010mfc/.gitignore
rename to gui_mfc/.gitignore
diff --git a/vs2013mfc/ReadMe.txt b/gui_mfc/ReadMe.txt
similarity index 100%
rename from vs2013mfc/ReadMe.txt
rename to gui_mfc/ReadMe.txt
diff --git a/vs2010mfc/config/AdaptiveBackgroundLearning.xml b/gui_mfc/config/AdaptiveBackgroundLearning.xml
similarity index 100%
rename from vs2010mfc/config/AdaptiveBackgroundLearning.xml
rename to gui_mfc/config/AdaptiveBackgroundLearning.xml
diff --git a/vs2010mfc/config/AdaptiveSelectiveBackgroundLearning.xml b/gui_mfc/config/AdaptiveSelectiveBackgroundLearning.xml
similarity index 100%
rename from vs2010mfc/config/AdaptiveSelectiveBackgroundLearning.xml
rename to gui_mfc/config/AdaptiveSelectiveBackgroundLearning.xml
diff --git a/vs2010mfc/config/DPAdaptiveMedianBGS.xml b/gui_mfc/config/DPAdaptiveMedianBGS.xml
similarity index 100%
rename from vs2010mfc/config/DPAdaptiveMedianBGS.xml
rename to gui_mfc/config/DPAdaptiveMedianBGS.xml
diff --git a/vs2010mfc/config/DPEigenbackgroundBGS.xml b/gui_mfc/config/DPEigenbackgroundBGS.xml
similarity index 100%
rename from vs2010mfc/config/DPEigenbackgroundBGS.xml
rename to gui_mfc/config/DPEigenbackgroundBGS.xml
diff --git a/vs2010mfc/config/DPGrimsonGMMBGS.xml b/gui_mfc/config/DPGrimsonGMMBGS.xml
similarity index 100%
rename from vs2010mfc/config/DPGrimsonGMMBGS.xml
rename to gui_mfc/config/DPGrimsonGMMBGS.xml
diff --git a/vs2010mfc/config/DPMeanBGS.xml b/gui_mfc/config/DPMeanBGS.xml
similarity index 100%
rename from vs2010mfc/config/DPMeanBGS.xml
rename to gui_mfc/config/DPMeanBGS.xml
diff --git a/vs2010mfc/config/DPPratiMediodBGS.xml b/gui_mfc/config/DPPratiMediodBGS.xml
similarity index 100%
rename from vs2010mfc/config/DPPratiMediodBGS.xml
rename to gui_mfc/config/DPPratiMediodBGS.xml
diff --git a/vs2010mfc/config/DPTextureBGS.xml b/gui_mfc/config/DPTextureBGS.xml
similarity index 100%
rename from vs2010mfc/config/DPTextureBGS.xml
rename to gui_mfc/config/DPTextureBGS.xml
diff --git a/vs2010mfc/config/DPWrenGABGS.xml b/gui_mfc/config/DPWrenGABGS.xml
similarity index 100%
rename from vs2010mfc/config/DPWrenGABGS.xml
rename to gui_mfc/config/DPWrenGABGS.xml
diff --git a/vs2010mfc/config/DPZivkovicAGMMBGS.xml b/gui_mfc/config/DPZivkovicAGMMBGS.xml
similarity index 100%
rename from vs2010mfc/config/DPZivkovicAGMMBGS.xml
rename to gui_mfc/config/DPZivkovicAGMMBGS.xml
diff --git a/vs2010mfc/config/FrameDifferenceBGS.xml b/gui_mfc/config/FrameDifferenceBGS.xml
similarity index 100%
rename from vs2010mfc/config/FrameDifferenceBGS.xml
rename to gui_mfc/config/FrameDifferenceBGS.xml
diff --git a/vs2010mfc/config/FuzzyChoquetIntegral.xml b/gui_mfc/config/FuzzyChoquetIntegral.xml
similarity index 100%
rename from vs2010mfc/config/FuzzyChoquetIntegral.xml
rename to gui_mfc/config/FuzzyChoquetIntegral.xml
diff --git a/vs2010mfc/config/FuzzySugenoIntegral.xml b/gui_mfc/config/FuzzySugenoIntegral.xml
similarity index 100%
rename from vs2010mfc/config/FuzzySugenoIntegral.xml
rename to gui_mfc/config/FuzzySugenoIntegral.xml
diff --git a/vs2010mfc/config/GMG.xml b/gui_mfc/config/GMG.xml
similarity index 100%
rename from vs2010mfc/config/GMG.xml
rename to gui_mfc/config/GMG.xml
diff --git a/vs2010mfc/config/IndependentMultimodalBGS.xml b/gui_mfc/config/IndependentMultimodalBGS.xml
similarity index 100%
rename from vs2010mfc/config/IndependentMultimodalBGS.xml
rename to gui_mfc/config/IndependentMultimodalBGS.xml
diff --git a/vs2010mfc/config/KDE.xml b/gui_mfc/config/KDE.xml
similarity index 100%
rename from vs2010mfc/config/KDE.xml
rename to gui_mfc/config/KDE.xml
diff --git a/vs2010mfc/config/LBAdaptiveSOM.xml b/gui_mfc/config/LBAdaptiveSOM.xml
similarity index 100%
rename from vs2010mfc/config/LBAdaptiveSOM.xml
rename to gui_mfc/config/LBAdaptiveSOM.xml
diff --git a/vs2010mfc/config/LBFuzzyAdaptiveSOM.xml b/gui_mfc/config/LBFuzzyAdaptiveSOM.xml
similarity index 100%
rename from vs2010mfc/config/LBFuzzyAdaptiveSOM.xml
rename to gui_mfc/config/LBFuzzyAdaptiveSOM.xml
diff --git a/vs2010mfc/config/LBFuzzyGaussian.xml b/gui_mfc/config/LBFuzzyGaussian.xml
similarity index 100%
rename from vs2010mfc/config/LBFuzzyGaussian.xml
rename to gui_mfc/config/LBFuzzyGaussian.xml
diff --git a/vs2010mfc/config/LBMixtureOfGaussians.xml b/gui_mfc/config/LBMixtureOfGaussians.xml
similarity index 100%
rename from vs2010mfc/config/LBMixtureOfGaussians.xml
rename to gui_mfc/config/LBMixtureOfGaussians.xml
diff --git a/vs2010mfc/config/LBSimpleGaussian.xml b/gui_mfc/config/LBSimpleGaussian.xml
similarity index 100%
rename from vs2010mfc/config/LBSimpleGaussian.xml
rename to gui_mfc/config/LBSimpleGaussian.xml
diff --git a/vs2010mfc/config/LOBSTERBGS.xml b/gui_mfc/config/LOBSTERBGS.xml
similarity index 100%
rename from vs2010mfc/config/LOBSTERBGS.xml
rename to gui_mfc/config/LOBSTERBGS.xml
diff --git a/vs2010mfc/config/MixtureOfGaussianV1BGS.xml b/gui_mfc/config/MixtureOfGaussianV1BGS.xml
similarity index 100%
rename from vs2010mfc/config/MixtureOfGaussianV1BGS.xml
rename to gui_mfc/config/MixtureOfGaussianV1BGS.xml
diff --git a/vs2010mfc/config/MixtureOfGaussianV2BGS.xml b/gui_mfc/config/MixtureOfGaussianV2BGS.xml
similarity index 100%
rename from vs2010mfc/config/MixtureOfGaussianV2BGS.xml
rename to gui_mfc/config/MixtureOfGaussianV2BGS.xml
diff --git a/vs2010mfc/config/MultiCueBGS.xml b/gui_mfc/config/MultiCueBGS.xml
similarity index 100%
rename from vs2010mfc/config/MultiCueBGS.xml
rename to gui_mfc/config/MultiCueBGS.xml
diff --git a/vs2010mfc/config/MultiLayerBGS.xml b/gui_mfc/config/MultiLayerBGS.xml
similarity index 100%
rename from vs2010mfc/config/MultiLayerBGS.xml
rename to gui_mfc/config/MultiLayerBGS.xml
diff --git a/vs2010mfc/config/SigmaDeltaBGS.xml b/gui_mfc/config/SigmaDeltaBGS.xml
similarity index 100%
rename from vs2010mfc/config/SigmaDeltaBGS.xml
rename to gui_mfc/config/SigmaDeltaBGS.xml
diff --git a/vs2010mfc/config/StaticFrameDifferenceBGS.xml b/gui_mfc/config/StaticFrameDifferenceBGS.xml
similarity index 100%
rename from vs2010mfc/config/StaticFrameDifferenceBGS.xml
rename to gui_mfc/config/StaticFrameDifferenceBGS.xml
diff --git a/vs2010mfc/config/SuBSENSEBGS.xml b/gui_mfc/config/SuBSENSEBGS.xml
similarity index 100%
rename from vs2010mfc/config/SuBSENSEBGS.xml
rename to gui_mfc/config/SuBSENSEBGS.xml
diff --git a/vs2010mfc/config/T2FGMM_UM.xml b/gui_mfc/config/T2FGMM_UM.xml
similarity index 100%
rename from vs2010mfc/config/T2FGMM_UM.xml
rename to gui_mfc/config/T2FGMM_UM.xml
diff --git a/vs2010mfc/config/T2FGMM_UV.xml b/gui_mfc/config/T2FGMM_UV.xml
similarity index 100%
rename from vs2010mfc/config/T2FGMM_UV.xml
rename to gui_mfc/config/T2FGMM_UV.xml
diff --git a/vs2010mfc/config/T2FMRF_UM.xml b/gui_mfc/config/T2FMRF_UM.xml
similarity index 100%
rename from vs2010mfc/config/T2FMRF_UM.xml
rename to gui_mfc/config/T2FMRF_UM.xml
diff --git a/vs2010mfc/config/T2FMRF_UV.xml b/gui_mfc/config/T2FMRF_UV.xml
similarity index 100%
rename from vs2010mfc/config/T2FMRF_UV.xml
rename to gui_mfc/config/T2FMRF_UV.xml
diff --git a/vs2010mfc/config/VuMeter.xml b/gui_mfc/config/VuMeter.xml
similarity index 100%
rename from vs2010mfc/config/VuMeter.xml
rename to gui_mfc/config/VuMeter.xml
diff --git a/vs2010mfc/config/WeightedMovingMeanBGS.xml b/gui_mfc/config/WeightedMovingMeanBGS.xml
similarity index 100%
rename from vs2010mfc/config/WeightedMovingMeanBGS.xml
rename to gui_mfc/config/WeightedMovingMeanBGS.xml
diff --git a/vs2010mfc/config/WeightedMovingVarianceBGS.xml b/gui_mfc/config/WeightedMovingVarianceBGS.xml
similarity index 100%
rename from vs2010mfc/config/WeightedMovingVarianceBGS.xml
rename to gui_mfc/config/WeightedMovingVarianceBGS.xml
diff --git a/vs2010mfc/dataset/video.avi b/gui_mfc/dataset/video.avi
similarity index 100%
rename from vs2010mfc/dataset/video.avi
rename to gui_mfc/dataset/video.avi
diff --git a/vs2013mfc/outputs/background/.gitignore b/gui_mfc/outputs/background/.gitignore
similarity index 100%
rename from vs2013mfc/outputs/background/.gitignore
rename to gui_mfc/outputs/background/.gitignore
diff --git a/vs2013mfc/outputs/foreground/.gitignore b/gui_mfc/outputs/foreground/.gitignore
similarity index 100%
rename from vs2013mfc/outputs/foreground/.gitignore
rename to gui_mfc/outputs/foreground/.gitignore
diff --git a/vs2013mfc/outputs/input/.gitignore b/gui_mfc/outputs/input/.gitignore
similarity index 100%
rename from vs2013mfc/outputs/input/.gitignore
rename to gui_mfc/outputs/input/.gitignore
diff --git a/vs2010mfc/src/.gitignore b/gui_mfc/src/.gitignore
similarity index 100%
rename from vs2010mfc/src/.gitignore
rename to gui_mfc/src/.gitignore
diff --git a/vs2010mfc/src/App.cpp b/gui_mfc/src/App.cpp
similarity index 100%
rename from vs2010mfc/src/App.cpp
rename to gui_mfc/src/App.cpp
diff --git a/vs2010mfc/src/App.h b/gui_mfc/src/App.h
similarity index 100%
rename from vs2010mfc/src/App.h
rename to gui_mfc/src/App.h
diff --git a/vs2010mfc/src/Dlg.cpp b/gui_mfc/src/Dlg.cpp
similarity index 100%
rename from vs2010mfc/src/Dlg.cpp
rename to gui_mfc/src/Dlg.cpp
diff --git a/vs2010mfc/src/Dlg.h b/gui_mfc/src/Dlg.h
similarity index 100%
rename from vs2010mfc/src/Dlg.h
rename to gui_mfc/src/Dlg.h
diff --git a/vs2013mfc/src/ReadMe.txt b/gui_mfc/src/ReadMe.txt
similarity index 100%
rename from vs2013mfc/src/ReadMe.txt
rename to gui_mfc/src/ReadMe.txt
diff --git a/vs2013mfc/src/bgslibrary_vs2013_mfc.rc b/gui_mfc/src/bgslibrary_vs2013_mfc.rc
similarity index 100%
rename from vs2013mfc/src/bgslibrary_vs2013_mfc.rc
rename to gui_mfc/src/bgslibrary_vs2013_mfc.rc
diff --git a/vs2013mfc/src/bgslibrary_vs2013_mfc.sln b/gui_mfc/src/bgslibrary_vs2013_mfc.sln
similarity index 100%
rename from vs2013mfc/src/bgslibrary_vs2013_mfc.sln
rename to gui_mfc/src/bgslibrary_vs2013_mfc.sln
diff --git a/vs2013mfc/src/bgslibrary_vs2013_mfc.vcxproj b/gui_mfc/src/bgslibrary_vs2013_mfc.vcxproj
similarity index 100%
rename from vs2013mfc/src/bgslibrary_vs2013_mfc.vcxproj
rename to gui_mfc/src/bgslibrary_vs2013_mfc.vcxproj
diff --git a/vs2013mfc/src/bgslibrary_vs2013_mfc.vcxproj.filters b/gui_mfc/src/bgslibrary_vs2013_mfc.vcxproj.filters
similarity index 100%
rename from vs2013mfc/src/bgslibrary_vs2013_mfc.vcxproj.filters
rename to gui_mfc/src/bgslibrary_vs2013_mfc.vcxproj.filters
diff --git a/vs2013mfc/src/bgslibrary_vs2013_mfc.vcxproj.user b/gui_mfc/src/bgslibrary_vs2013_mfc.vcxproj.user
similarity index 100%
rename from vs2013mfc/src/bgslibrary_vs2013_mfc.vcxproj.user
rename to gui_mfc/src/bgslibrary_vs2013_mfc.vcxproj.user
diff --git a/vs2013mfc/src/res/bgslibrary_vs2013_mfc.ico b/gui_mfc/src/res/bgslibrary_vs2013_mfc.ico
similarity index 100%
rename from vs2013mfc/src/res/bgslibrary_vs2013_mfc.ico
rename to gui_mfc/src/res/bgslibrary_vs2013_mfc.ico
diff --git a/vs2013mfc/src/res/bgslibrary_vs2013_mfc.rc2 b/gui_mfc/src/res/bgslibrary_vs2013_mfc.rc2
similarity index 100%
rename from vs2013mfc/src/res/bgslibrary_vs2013_mfc.rc2
rename to gui_mfc/src/res/bgslibrary_vs2013_mfc.rc2
diff --git a/vs2010mfc/src/resource.h b/gui_mfc/src/resource.h
similarity index 100%
rename from vs2010mfc/src/resource.h
rename to gui_mfc/src/resource.h
diff --git a/vs2010mfc/src/stdafx.cpp b/gui_mfc/src/stdafx.cpp
similarity index 100%
rename from vs2010mfc/src/stdafx.cpp
rename to gui_mfc/src/stdafx.cpp
diff --git a/vs2010mfc/src/stdafx.h b/gui_mfc/src/stdafx.h
similarity index 100%
rename from vs2010mfc/src/stdafx.h
rename to gui_mfc/src/stdafx.h
diff --git a/vs2010mfc/src/targetver.h b/gui_mfc/src/targetver.h
similarity index 100%
rename from vs2010mfc/src/targetver.h
rename to gui_mfc/src/targetver.h
diff --git a/gui_qt/.gitignore b/gui_qt/.gitignore
new file mode 100644
index 0000000..9c28032
--- /dev/null
+++ b/gui_qt/.gitignore
@@ -0,0 +1,9 @@
+_*/
+debug/
+release/
+build_*/
+dataset*/
+binaries*/
+Makefile*
+*.exe
+*.dll
diff --git a/gui_qt/CMakeLists.txt b/gui_qt/CMakeLists.txt
new file mode 100644
index 0000000..83c8920
--- /dev/null
+++ b/gui_qt/CMakeLists.txt
@@ -0,0 +1,52 @@
+cmake_minimum_required(VERSION 2.8.11)
+
+project(bgslibrary_gui)
+
+# Find includes in corresponding build directories
+set(CMAKE_INCLUDE_CURRENT_DIR ON)
+
+# Instruct CMake to run moc automatically when needed.
+set(CMAKE_AUTOMOC ON)
+
+# Handle the Qt uic code generator automatically
+set(CMAKE_AUTOUIC ON)
+
+# Find the Qt5Widgets library
+find_package(Qt5Widgets)
+
+SET(app_RESOURCES application.qrc)
+QT5_ADD_RESOURCES(app_RESOURCES_RCC ${app_RESOURCES})
+
+# Find the OpenCV library
+set(OpenCV_STATIC OFF)
+find_package(OpenCV REQUIRED)
+
+message(STATUS "OpenCV library status:")
+message(STATUS " version: ${OpenCV_VERSION}")
+message(STATUS " libraries: ${OpenCV_LIBS}")
+message(STATUS " include path: ${OpenCV_INCLUDE_DIRS}")
+
+file(GLOB main bgslibrary_gui.cpp mainwindow.cpp qt_utils.cpp texteditor.cpp)
+
+file(GLOB_RECURSE analysis_src ../package_analysis/*.cpp)
+file(GLOB_RECURSE analysis_inc ../package_analysis/*.h)
+file(GLOB_RECURSE bgs_src ../package_bgs/*.cpp ../package_bgs/*.c)
+file(GLOB_RECURSE bgs_inc ../package_bgs/*.h)
+
+include_directories(${CMAKE_SOURCE_DIR} ${OpenCV_INCLUDE_DIRS})
+
+add_library(libbgs STATIC ${bgs_src} ${analysis_src})
+target_link_libraries(libbgs ${OpenCV_LIBS})
+set_property(TARGET libbgs PROPERTY PUBLIC_HEADER ${bgs_inc} ${analysis_inc})
+
+if(WIN32)
+ # set_property(TARGET libbgs PROPERTY SUFFIX ".lib")
+else()
+ set_property(TARGET libbgs PROPERTY OUTPUT_NAME "bgs")
+endif()
+
+# Tell CMake to create the bgslibrary_gui executable
+add_executable(bgslibrary_gui ${main} ${app_RESOURCES_RCC})
+
+# Use the Widgets module from Qt 5.
+target_link_libraries(bgslibrary_gui Qt5::Widgets ${OpenCV_LIBS} libbgs)
diff --git a/gui_qt/README.txt b/gui_qt/README.txt
new file mode 100644
index 0000000..41a4cd2
--- /dev/null
+++ b/gui_qt/README.txt
@@ -0,0 +1,17 @@
+#-------------------------------------------------
+#
+# Project created with Qt 5.6.2
+#
+# Compiling BGSLibrary QT GUI with CMAKE
+#
+#-------------------------------------------------
+# Qt 5.x 64-bit for Desktop (MSVC 2015)
+#-------------------------------------------------
+
+mkdir build
+
+cd build
+
+set OpenCV_DIR=C:\OpenCV3.2.0\build
+
+cmake -DOpenCV_DIR=%OpenCV_DIR% -G "Visual Studio 14 Win64" ..
diff --git a/gui_qt/application.qrc b/gui_qt/application.qrc
new file mode 100644
index 0000000..3e8687f
--- /dev/null
+++ b/gui_qt/application.qrc
@@ -0,0 +1,10 @@
+
+
+ figs/copy.png
+ figs/cut.png
+ figs/new.png
+ figs/open.png
+ figs/paste.png
+ figs/save.png
+
+
\ No newline at end of file
diff --git a/gui_qt/bgslibrary_gui.cpp b/gui_qt/bgslibrary_gui.cpp
new file mode 100644
index 0000000..e886262
--- /dev/null
+++ b/gui_qt/bgslibrary_gui.cpp
@@ -0,0 +1,38 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+#include "mainwindow.h"
+
+int main(int argc, char *argv[])
+{
+ std::cout << "--------------------------------------------" << std::endl;
+ std::cout << "Background Subtraction Library v2.0.0 " << std::endl;
+ std::cout << "https://github.com/andrewssobral/bgslibrary " << std::endl;
+ std::cout << "by: " << std::endl;
+ std::cout << "Andrews Sobral (andrewssobral@gmail.com) " << std::endl;
+ std::cout << "--------------------------------------------" << std::endl;
+ std::cout << "Using OpenCV version " << CV_VERSION << std::endl;
+
+ QApplication a(argc, argv);
+
+ QCoreApplication::setApplicationName("BGSLibrary");
+ QCoreApplication::setApplicationVersion("2.0.0");
+
+ MainWindow w;
+ w.show();
+
+ return a.exec();
+}
diff --git a/gui_qt/bgslibrary_gui.pro b/gui_qt/bgslibrary_gui.pro
new file mode 100644
index 0000000..feedbf6
--- /dev/null
+++ b/gui_qt/bgslibrary_gui.pro
@@ -0,0 +1,248 @@
+#-------------------------------------------------
+#
+# Project created by QtCreator
+#
+#-------------------------------------------------
+
+QT += core gui
+
+greaterThan(QT_MAJOR_VERSION, 4): QT += widgets
+
+TARGET = bgslibrary_gui
+TEMPLATE = app
+
+# For Windows x64 + Visual Studio 2015 + OpenCV 3.1.0
+#INCLUDEPATH += C:/OpenCV3.1.0/build/include
+#LIBS += -LC:/OpenCV3.1.0/build/x64/vc14/lib -lopencv_world310
+
+# For Windows x64 + Visual Studio 2015 + OpenCV 3.2.0
+INCLUDEPATH += C:/OpenCV3.2.0/build/include
+LIBS += -LC:/OpenCV3.2.0/build/x64/vc14/lib -lopencv_world320
+
+# For Linux
+# INCLUDEPATH += /usr/local/include/opencv
+# LIBS += -L/usr/local/lib
+
+RESOURCES = application.qrc
+
+SOURCES += bgslibrary_gui.cpp\
+ mainwindow.cpp \
+ qt_utils.cpp \
+ texteditor.cpp \
+ ../package_analysis/ForegroundMaskAnalysis.cpp \
+ ../package_analysis/PerformanceUtils.cpp \
+ ../package_analysis/PixelUtils.cpp \
+ ../package_bgs/_template_/Amber.cpp \
+ ../package_bgs/_template_/MyBGS.cpp \
+ ../package_bgs/dp/AdaptiveMedianBGS.cpp \
+ ../package_bgs/dp/Eigenbackground.cpp \
+ ../package_bgs/dp/Error.cpp \
+ ../package_bgs/dp/GrimsonGMM.cpp \
+ ../package_bgs/dp/Image.cpp \
+ ../package_bgs/dp/MeanBGS.cpp \
+ ../package_bgs/dp/PratiMediodBGS.cpp \
+ ../package_bgs/dp/TextureBGS.cpp \
+ ../package_bgs/dp/WrenGA.cpp \
+ ../package_bgs/dp/ZivkovicAGMM.cpp \
+ ../package_bgs/IMBS/IMBS.cpp \
+ ../package_bgs/KDE/KernelTable.cpp \
+ ../package_bgs/KDE/NPBGmodel.cpp \
+ ../package_bgs/KDE/NPBGSubtractor.cpp \
+ ../package_bgs/lb/BGModel.cpp \
+ ../package_bgs/lb/BGModelFuzzyGauss.cpp \
+ ../package_bgs/lb/BGModelFuzzySom.cpp \
+ ../package_bgs/lb/BGModelGauss.cpp \
+ ../package_bgs/lb/BGModelMog.cpp \
+ ../package_bgs/lb/BGModelSom.cpp \
+ ../package_bgs/LBP_MRF/graph.cpp \
+ ../package_bgs/LBP_MRF/maxflow.cpp \
+ ../package_bgs/LBP_MRF/MEDefs.cpp \
+ ../package_bgs/LBP_MRF/MEHistogram.cpp \
+ ../package_bgs/LBP_MRF/MEImage.cpp \
+ ../package_bgs/LBP_MRF/MotionDetection.cpp \
+ ../package_bgs/LBSP/BackgroundSubtractorLBSP.cpp \
+ ../package_bgs/LBSP/BackgroundSubtractorLBSP_.cpp \
+ ../package_bgs/LBSP/BackgroundSubtractorLOBSTER.cpp \
+ ../package_bgs/LBSP/BackgroundSubtractorPAWCS.cpp \
+ ../package_bgs/LBSP/BackgroundSubtractorSuBSENSE.cpp \
+ ../package_bgs/LBSP/LBSP.cpp \
+ ../package_bgs/LBSP/LBSP_.cpp \
+ ../package_bgs/MultiLayer/blob.cpp \
+ ../package_bgs/MultiLayer/BlobExtraction.cpp \
+ ../package_bgs/MultiLayer/BlobResult.cpp \
+ ../package_bgs/MultiLayer/CMultiLayerBGS.cpp \
+ ../package_bgs/MultiLayer/LocalBinaryPattern.cpp \
+ ../package_bgs/PBAS/PBAS.cpp \
+ ../package_bgs/SigmaDelta/sdLaMa091.cpp \
+ ../package_bgs/T2F/FuzzyUtils.cpp \
+ ../package_bgs/T2F/MRF.cpp \
+ ../package_bgs/T2F/T2FGMM.cpp \
+ ../package_bgs/T2F/T2FMRF.cpp \
+ ../package_bgs/TwoPoints/two_points.cpp \
+ ../package_bgs/ViBe/vibe-background-sequential.cpp \
+ ../package_bgs/VuMeter/TBackground.cpp \
+ ../package_bgs/VuMeter/TBackgroundVuMeter.cpp \
+ ../package_bgs/AdaptiveBackgroundLearning.cpp \
+ ../package_bgs/AdaptiveSelectiveBackgroundLearning.cpp \
+ ../package_bgs/DPAdaptiveMedian.cpp \
+ ../package_bgs/DPEigenbackground.cpp \
+ ../package_bgs/DPGrimsonGMM.cpp \
+ ../package_bgs/DPMean.cpp \
+ ../package_bgs/DPPratiMediod.cpp \
+ ../package_bgs/DPTexture.cpp \
+ ../package_bgs/DPWrenGA.cpp \
+ ../package_bgs/DPZivkovicAGMM.cpp \
+ ../package_bgs/FrameDifference.cpp \
+ ../package_bgs/FuzzyChoquetIntegral.cpp \
+ ../package_bgs/FuzzySugenoIntegral.cpp \
+ ../package_bgs/GMG.cpp \
+ ../package_bgs/IndependentMultimodal.cpp \
+ ../package_bgs/KDE.cpp \
+ ../package_bgs/KNN.cpp \
+ ../package_bgs/LBAdaptiveSOM.cpp \
+ ../package_bgs/LBFuzzyAdaptiveSOM.cpp \
+ ../package_bgs/LBFuzzyGaussian.cpp \
+ ../package_bgs/LBMixtureOfGaussians.cpp \
+ ../package_bgs/LBP_MRF.cpp \
+ ../package_bgs/LBSimpleGaussian.cpp \
+ ../package_bgs/LOBSTER.cpp \
+ ../package_bgs/MixtureOfGaussianV1.cpp \
+ ../package_bgs/MixtureOfGaussianV2.cpp \
+ ../package_bgs/MultiCue.cpp \
+ ../package_bgs/MultiLayer.cpp \
+ ../package_bgs/PAWCS.cpp \
+ ../package_bgs/PixelBasedAdaptiveSegmenter.cpp \
+ ../package_bgs/SigmaDelta.cpp \
+ ../package_bgs/StaticFrameDifference.cpp \
+ ../package_bgs/SuBSENSE.cpp \
+ ../package_bgs/T2FGMM_UM.cpp \
+ ../package_bgs/T2FGMM_UV.cpp \
+ ../package_bgs/T2FMRF_UM.cpp \
+ ../package_bgs/T2FMRF_UV.cpp \
+ ../package_bgs/TwoPoints.cpp \
+ ../package_bgs/ViBe.cpp \
+ ../package_bgs/VuMeter.cpp \
+ ../package_bgs/WeightedMovingMean.cpp \
+ ../package_bgs/WeightedMovingVariance.cpp \
+ ../package_bgs/_template_/amber/amber.c
+
+HEADERS += mainwindow.h \
+ qt_utils.h \
+ texteditor.h \
+ ../package_analysis/ForegroundMaskAnalysis.h \
+ ../package_analysis/PerformanceUtils.h \
+ ../package_analysis/PixelUtils.h \
+ ../package_bgs/_template_/amber/amber.h \
+ ../package_bgs/_template_/Amber.h \
+ ../package_bgs/_template_/MyBGS.h \
+ ../package_bgs/dp/AdaptiveMedianBGS.h \
+ ../package_bgs/dp/Bgs.h \
+ ../package_bgs/dp/BgsParams.h \
+ ../package_bgs/dp/Eigenbackground.h \
+ ../package_bgs/dp/Error.h \
+ ../package_bgs/dp/GrimsonGMM.h \
+ ../package_bgs/dp/Image.h \
+ ../package_bgs/dp/MeanBGS.h \
+ ../package_bgs/dp/PratiMediodBGS.h \
+ ../package_bgs/dp/TextureBGS.h \
+ ../package_bgs/dp/WrenGA.h \
+ ../package_bgs/dp/ZivkovicAGMM.h \
+ ../package_bgs/IMBS/IMBS.hpp \
+ ../package_bgs/KDE/KernelTable.h \
+ ../package_bgs/KDE/NPBGmodel.h \
+ ../package_bgs/KDE/NPBGSubtractor.h \
+ ../package_bgs/lb/BGModel.h \
+ ../package_bgs/lb/BGModelFuzzyGauss.h \
+ ../package_bgs/lb/BGModelFuzzySom.h \
+ ../package_bgs/lb/BGModelGauss.h \
+ ../package_bgs/lb/BGModelMog.h \
+ ../package_bgs/lb/BGModelSom.h \
+ ../package_bgs/lb/Types.h \
+ ../package_bgs/LBP_MRF/block.h \
+ ../package_bgs/LBP_MRF/graph.h \
+ ../package_bgs/LBP_MRF/MEDefs.hpp \
+ ../package_bgs/LBP_MRF/MEHistogram.hpp \
+ ../package_bgs/LBP_MRF/MEImage.hpp \
+ ../package_bgs/LBP_MRF/MotionDetection.hpp \
+ ../package_bgs/LBSP/BackgroundSubtractorLBSP.h \
+ ../package_bgs/LBSP/BackgroundSubtractorLBSP_.h \
+ ../package_bgs/LBSP/BackgroundSubtractorLOBSTER.h \
+ ../package_bgs/LBSP/BackgroundSubtractorPAWCS.h \
+ ../package_bgs/LBSP/BackgroundSubtractorSuBSENSE.h \
+ ../package_bgs/LBSP/DistanceUtils.h \
+ ../package_bgs/LBSP/LBSP.h \
+ ../package_bgs/LBSP/LBSP_.h \
+ ../package_bgs/LBSP/RandUtils.h \
+ ../package_bgs/MultiLayer/BackgroundSubtractionAPI.h \
+ ../package_bgs/MultiLayer/BGS.h \
+ ../package_bgs/MultiLayer/blob.h \
+ ../package_bgs/MultiLayer/BlobExtraction.h \
+ ../package_bgs/MultiLayer/BlobLibraryConfiguration.h \
+ ../package_bgs/MultiLayer/BlobResult.h \
+ ../package_bgs/MultiLayer/CMultiLayerBGS.h \
+ ../package_bgs/MultiLayer/LocalBinaryPattern.h \
+ ../package_bgs/MultiLayer/OpenCvDataConversion.h \
+ ../package_bgs/MultiLayer/OpenCvLegacyIncludes.h \
+ ../package_bgs/PBAS/PBAS.h \
+ ../package_bgs/SigmaDelta/sdLaMa091.h \
+ ../package_bgs/T2F/FuzzyUtils.h \
+ ../package_bgs/T2F/MRF.h \
+ ../package_bgs/T2F/T2FGMM.h \
+ ../package_bgs/T2F/T2FMRF.h \
+ ../package_bgs/TwoPoints/two_points.h \
+ ../package_bgs/ViBe/vibe-background-sequential.h \
+ ../package_bgs/VuMeter/TBackground.h \
+ ../package_bgs/VuMeter/TBackgroundVuMeter.h \
+ ../package_bgs/AdaptiveBackgroundLearning.h \
+ ../package_bgs/AdaptiveSelectiveBackgroundLearning.h \
+ ../package_bgs/bgslibrary.h \
+ ../package_bgs/DPAdaptiveMedian.h \
+ ../package_bgs/DPEigenbackground.h \
+ ../package_bgs/DPGrimsonGMM.h \
+ ../package_bgs/DPMean.h \
+ ../package_bgs/DPPratiMediod.h \
+ ../package_bgs/DPTexture.h \
+ ../package_bgs/DPWrenGA.h \
+ ../package_bgs/DPZivkovicAGMM.h \
+ ../package_bgs/FrameDifference.h \
+ ../package_bgs/FuzzyChoquetIntegral.h \
+ ../package_bgs/FuzzySugenoIntegral.h \
+ ../package_bgs/GMG.h \
+ ../package_bgs/IBGS.h \
+ ../package_bgs/IndependentMultimodal.h \
+ ../package_bgs/KDE.h \
+ ../package_bgs/KNN.h \
+ ../package_bgs/LBAdaptiveSOM.h \
+ ../package_bgs/LBFuzzyAdaptiveSOM.h \
+ ../package_bgs/LBFuzzyGaussian.h \
+ ../package_bgs/LBMixtureOfGaussians.h \
+ ../package_bgs/LBP_MRF.h \
+ ../package_bgs/LBSimpleGaussian.h \
+ ../package_bgs/LOBSTER.h \
+ ../package_bgs/MixtureOfGaussianV1.h \
+ ../package_bgs/MixtureOfGaussianV2.h \
+ ../package_bgs/MultiCue.h \
+ ../package_bgs/MultiLayer.h \
+ ../package_bgs/PAWCS.h \
+ ../package_bgs/PixelBasedAdaptiveSegmenter.h \
+ ../package_bgs/SigmaDelta.h \
+ ../package_bgs/StaticFrameDifference.h \
+ ../package_bgs/SuBSENSE.h \
+ ../package_bgs/T2FGMM_UM.h \
+ ../package_bgs/T2FGMM_UV.h \
+ ../package_bgs/T2FMRF_UM.h \
+ ../package_bgs/T2FMRF_UV.h \
+ ../package_bgs/TwoPoints.h \
+ ../package_bgs/ViBe.h \
+ ../package_bgs/VuMeter.h \
+ ../package_bgs/WeightedMovingMean.h \
+ ../package_bgs/WeightedMovingVariance.h
+
+FORMS += mainwindow.ui
+
+DISTFILES += \
+ ../package_bgs/LBSP/LBSP_16bits_dbcross_1ch.i \
+ ../package_bgs/LBSP/LBSP_16bits_dbcross_3ch1t.i \
+ ../package_bgs/LBSP/LBSP_16bits_dbcross_3ch3t.i \
+ ../package_bgs/LBSP/LBSP_16bits_dbcross_s3ch.i \
+ ../package_bgs/ViBe/LICENSE
diff --git a/gui_qt/build/.gitignore b/gui_qt/build/.gitignore
new file mode 100644
index 0000000..4e2a98b
--- /dev/null
+++ b/gui_qt/build/.gitignore
@@ -0,0 +1,4 @@
+# Ignore everything in this directory
+*
+# Except these files
+!.gitignore
diff --git a/gui_qt/figs/copy.png b/gui_qt/figs/copy.png
new file mode 100644
index 0000000..2aeb282
Binary files /dev/null and b/gui_qt/figs/copy.png differ
diff --git a/gui_qt/figs/cut.png b/gui_qt/figs/cut.png
new file mode 100644
index 0000000..54638e9
Binary files /dev/null and b/gui_qt/figs/cut.png differ
diff --git a/gui_qt/figs/new.png b/gui_qt/figs/new.png
new file mode 100644
index 0000000..12131b0
Binary files /dev/null and b/gui_qt/figs/new.png differ
diff --git a/gui_qt/figs/open.png b/gui_qt/figs/open.png
new file mode 100644
index 0000000..45fa288
Binary files /dev/null and b/gui_qt/figs/open.png differ
diff --git a/gui_qt/figs/paste.png b/gui_qt/figs/paste.png
new file mode 100644
index 0000000..c14425c
Binary files /dev/null and b/gui_qt/figs/paste.png differ
diff --git a/gui_qt/figs/save.png b/gui_qt/figs/save.png
new file mode 100644
index 0000000..daba865
Binary files /dev/null and b/gui_qt/figs/save.png differ
diff --git a/gui_qt/mainwindow.cpp b/gui_qt/mainwindow.cpp
new file mode 100644
index 0000000..bb7eac8
--- /dev/null
+++ b/gui_qt/mainwindow.cpp
@@ -0,0 +1,571 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+#include "mainwindow.h"
+#include "ui_mainwindow.h"
+
+namespace bgslibrary
+{
+ //template IBGS* createInstance() { return new T; }
+ //typedef std::map map_ibgs;
+
+ IBGS* get_alg(std::string alg_name) {
+ map_ibgs map;
+ map["FrameDifference"] = &createInstance;
+ map["StaticFrameDifference"] = &createInstance;
+ map["WeightedMovingMean"] = &createInstance;
+ map["WeightedMovingVariance"] = &createInstance;
+#if CV_MAJOR_VERSION == 2
+ map["MixtureOfGaussianV1"] = &createInstance; // only for OpenCV 2.x
+#endif
+ map["MixtureOfGaussianV2"] = &createInstance;
+ map["AdaptiveBackgroundLearning"] = &createInstance;
+ map["AdaptiveSelectiveBackgroundLearning"] = &createInstance;
+#if CV_MAJOR_VERSION == 2 && CV_MINOR_VERSION >= 4 && CV_SUBMINOR_VERSION >= 3
+ map["GMG"] = &createInstance; // only for OpenCV >= 2.4.3
+#endif
+#if CV_MAJOR_VERSION == 3
+ map["KNN"] = &createInstance; // only on OpenCV 3.x
+#endif
+ map["DPAdaptiveMedian"] = &createInstance;
+ map["DPGrimsonGMM"] = &createInstance;
+ map["DPZivkovicAGMM"] = &createInstance;
+ map["DPMean"] = &createInstance;
+ map["DPWrenGA"] = &createInstance;
+ map["DPPratiMediod"] = &createInstance;
+ map["DPEigenbackground"] = &createInstance;
+ map["DPTexture"] = &createInstance;
+ map["T2FGMM_UM"] = &createInstance;
+ map["T2FGMM_UV"] = &createInstance;
+ map["T2FMRF_UM"] = &createInstance;
+ map["T2FMRF_UV"] = &createInstance;
+ map["FuzzySugenoIntegral"] = &createInstance;
+ map["FuzzyChoquetIntegral"] = &createInstance;
+ map["MultiLayer"] = &createInstance;
+ map["PixelBasedAdaptiveSegmenter"] = &createInstance;
+ map["LBSimpleGaussian"] = &createInstance;
+ map["LBFuzzyGaussian"] = &createInstance;
+ map["LBMixtureOfGaussians"] = &createInstance;
+ map["LBAdaptiveSOM"] = &createInstance;
+ map["LBFuzzyAdaptiveSOM"] = &createInstance;
+ map["LBP_MRF"] = &createInstance;
+ map["VuMeter"] = &createInstance;
+ map["KDE"] = &createInstance;
+ map["IndependentMultimodal"] = &createInstance;
+ map["MultiCue"] = &createInstance;
+ map["SigmaDelta"] = &createInstance;
+ map["SuBSENSE"] = &createInstance;
+ map["LOBSTER"] = &createInstance;
+ map["PAWCS"] = &createInstance;
+ map["TwoPoints"] = &createInstance;
+ map["ViBe"] = &createInstance;
+
+ return map[alg_name]();
+ }
+
+ QStringList get_algs_name()
+ {
+ QStringList stringList;
+ stringList.append("FrameDifference");
+ stringList.append("StaticFrameDifference");
+ stringList.append("WeightedMovingMean");
+ stringList.append("WeightedMovingVariance");
+#if CV_MAJOR_VERSION == 2
+ stringList.append("MixtureOfGaussianV1"); // only for OpenCV 2.x
+#endif
+ stringList.append("MixtureOfGaussianV2");
+ stringList.append("AdaptiveBackgroundLearning");
+ stringList.append("AdaptiveSelectiveBackgroundLearning");
+#if CV_MAJOR_VERSION == 2 && CV_MINOR_VERSION >= 4 && CV_SUBMINOR_VERSION >= 3
+ stringList.append("GMG"); // only for OpenCV >= 2.4.3
+#endif
+#if CV_MAJOR_VERSION == 3
+ stringList.append("KNN"); // only on OpenCV 3.x
+#endif
+ stringList.append("DPAdaptiveMedian");
+ stringList.append("DPGrimsonGMM");
+ stringList.append("DPZivkovicAGMM");
+ stringList.append("DPMean");
+ stringList.append("DPWrenGA");
+ stringList.append("DPPratiMediod");
+ stringList.append("DPEigenbackground");
+ stringList.append("DPTexture");
+ stringList.append("T2FGMM_UM");
+ stringList.append("T2FGMM_UV");
+ stringList.append("T2FMRF_UM");
+ stringList.append("T2FMRF_UV");
+ stringList.append("FuzzySugenoIntegral");
+ stringList.append("FuzzyChoquetIntegral");
+ stringList.append("MultiLayer");
+ stringList.append("PixelBasedAdaptiveSegmenter");
+ stringList.append("LBSimpleGaussian");
+ stringList.append("LBFuzzyGaussian");
+ stringList.append("LBMixtureOfGaussians");
+ stringList.append("LBAdaptiveSOM");
+ stringList.append("LBFuzzyAdaptiveSOM");
+ stringList.append("LBP_MRF");
+ stringList.append("VuMeter");
+ stringList.append("KDE");
+ stringList.append("IndependentMultimodal");
+ stringList.append("MultiCue");
+ stringList.append("SigmaDelta");
+ stringList.append("SuBSENSE");
+ stringList.append("LOBSTER");
+ stringList.append("PAWCS");
+ stringList.append("TwoPoints");
+ stringList.append("ViBe");
+ return stringList;
+ }
+}
+
+MainWindow::MainWindow(QWidget *parent) :
+ QMainWindow(parent),
+ ui(new Ui::MainWindow)
+{
+ ui->setupUi(this);
+ //QDir applicationPath(QCoreApplication::applicationDirPath());
+ fileName = QDir(".").filePath("dataset/video.avi");
+ //fileName = applicationPath.absolutePath() + "dataset";
+ ui->lineEdit_inputdata->setText(fileName);
+ //fileName = ui->lineEdit_inputdata->text();
+ timer = new QTimer(this); connect(timer, SIGNAL(timeout()), this, SLOT(startCapture()));
+ QStringListModel* listModel = new QStringListModel(bgslibrary::get_algs_name(), NULL);
+ listModel->sort(0);
+ ui->listView_algorithms->setModel(listModel);
+ QModelIndex index = listModel->index(0);
+ ui->listView_algorithms->selectionModel()->select(index, QItemSelectionModel::Select);
+}
+
+MainWindow::~MainWindow()
+{
+ delete ui;
+}
+
+void MainWindow::on_actionExit_triggered()
+{
+ this->close();
+}
+
+void MainWindow::on_pushButton_inputdata_clicked()
+{
+ QFileDialog dialog(this);
+
+ if (ui->checkBox_imageseq->isChecked())
+ dialog.setFileMode(QFileDialog::Directory);
+ else
+ dialog.setFileMode(QFileDialog::ExistingFile);
+ //dialog.setFileMode(QFileDialog::AnyFile);
+
+ dialog.exec();
+ QStringList list = dialog.selectedFiles();
+ /*
+ for(int index = 0; index < list.length(); index++)
+ std::cout << list.at(index).toStdString() << std::endl;
+ */
+ if (list.size() > 0)
+ {
+ fileName = list.at(0);
+ ui->lineEdit_inputdata->setText(fileName);
+ }
+}
+
+void MainWindow::on_pushButton_out_in_clicked()
+{
+ QFileDialog dialog(this);
+ dialog.setDirectory(".");
+ dialog.setFileMode(QFileDialog::Directory);
+ dialog.exec();
+ QStringList list = dialog.selectedFiles();
+ if (list.size() > 0)
+ {
+ fileName = list.at(0);
+ ui->lineEdit_out_in->setText(fileName);
+ }
+}
+
+void MainWindow::on_pushButton_out_fg_clicked()
+{
+ QFileDialog dialog(this);
+ dialog.setDirectory(".");
+ dialog.setFileMode(QFileDialog::Directory);
+ dialog.exec();
+ QStringList list = dialog.selectedFiles();
+ if (list.size() > 0)
+ {
+ fileName = list.at(0);
+ ui->lineEdit_out_fg->setText(fileName);
+ }
+}
+
+void MainWindow::on_pushButton_out_bg_clicked()
+{
+ QFileDialog dialog(this);
+ dialog.setDirectory(".");
+ dialog.setFileMode(QFileDialog::Directory);
+ dialog.exec();
+ QStringList list = dialog.selectedFiles();
+ if (list.size() > 0)
+ {
+ fileName = list.at(0);
+ ui->lineEdit_out_bg->setText(fileName);
+ }
+}
+
+void MainWindow::on_pushButton_start_clicked()
+{
+ useCamera = false;
+ useVideo = false;
+ useSequence = false;
+
+ if (ui->checkBox_webcamera->isChecked())
+ useCamera = true;
+ else
+ {
+ if (ui->checkBox_imageseq->isChecked())
+ useSequence = true;
+ else
+ useVideo = true;
+ }
+
+ if (!timer->isActive() && setUpCapture())
+ {
+ createBGS();
+ startTimer();
+ }
+}
+
+void MainWindow::on_pushButton_stop_clicked()
+{
+ stopTimer();
+}
+
+void MainWindow::createBGS()
+{
+ QString algorithm_name = getSelectedAlgorithmName();
+ bgs = bgslibrary::get_alg(algorithm_name.toStdString());
+ bgs->setShowOutput(false);
+}
+
+void MainWindow::destroyBGS()
+{
+ delete bgs;
+}
+
+void MainWindow::startTimer()
+{
+ std::cout << "startTimer()" << std::endl;
+
+ ui->progressBar->setValue(0);
+ setFrameNumber(0);
+ frameNumber_aux = 0;
+ timer->start(33);
+
+ // disable options
+}
+
+void MainWindow::stopTimer()
+{
+ if (!timer->isActive())
+ return;
+
+ std::cout << "stopTimer()" << std::endl;
+
+ timer->stop();
+ //setFrameNumber(0);
+ //ui->progressBar->setValue(0);
+
+ destroyBGS();
+
+ if (useCamera || useVideo)
+ capture.release();
+
+ // enable options
+}
+
+void MainWindow::setFrameNumber(long long _frameNumber)
+{
+ //std::cout << "setFrameNumber()" << std::endl;
+ frameNumber = _frameNumber;
+ QString txt_frameNumber = QString::fromStdString(its(frameNumber));
+ ui->label_framenumber_txt->setText(txt_frameNumber);
+}
+
+bool MainWindow::setUpCapture()
+{
+ capture_length = 0;
+
+ if (useCamera && !setUpCamera()) {
+ std::cout << "Cannot initialize webcamera!" << std::endl;
+ return false;
+ }
+
+ if (useVideo && !setUpVideo()) {
+ std::cout << "Cannot open video file " << fileName.toStdString() << std::endl;
+ return false;
+ }
+
+ if (useSequence && !setUpSequence()) {
+ std::cout << "Cannot process images at " << fileName.toStdString() << std::endl;
+ return false;
+ }
+
+ if (useCamera || useVideo) {
+ int capture_fps = capture.get(CV_CAP_PROP_FPS);
+ std::cout << "capture_fps: " << capture_fps << std::endl;
+ }
+
+ if (useVideo) {
+ capture_length = capture.get(CV_CAP_PROP_FRAME_COUNT);
+ std::cout << "capture_length: " << capture_length << std::endl;
+ }
+
+ std::cout << "OK!" << std::endl;
+ return true;
+}
+
+void MainWindow::startCapture()
+{
+ //std::cout << "startCapture()" << std::endl;
+ setFrameNumber(frameNumber + 1);
+ cv::Mat cv_frame;
+
+ if (useCamera || useVideo)
+ capture >> cv_frame;
+
+ if (useSequence && (frameNumber - 1) < entryList.length())
+ {
+ QString file = entryList.at(frameNumber - 1);
+ QString filePath = QDir(fileName).filePath(file);
+
+ std::cout << "Processing: " << filePath.toStdString() << std::endl;
+ if (fileExists(filePath))
+ cv_frame = cv::imread(filePath.toStdString());
+ }
+
+ if (cv_frame.empty())
+ {
+ stopTimer();
+ return;
+ }
+
+ if (frameNumber == 1)
+ {
+ int frame_width = cv_frame.size().width;
+ int frame_height = cv_frame.size().height;
+ ui->label_frameresw_txt->setText(QString::fromStdString(its(frame_width)));
+ ui->label_frameresh_txt->setText(QString::fromStdString(its(frame_height)));
+ }
+
+ if (useVideo && capture_length > 0)
+ {
+ double perc = (double(frameNumber) / double(capture_length)) * 100.0;
+ //std::cout << "perc: " << perc << std::endl;
+ ui->progressBar->setValue(perc);
+ }
+
+ int startAt = ui->spinBox_startat->value();
+ if (startAt > 0 && frameNumber < startAt)
+ {
+ timer->setInterval(1);
+ return;
+ }
+ else
+ timer->setInterval(33);
+
+ int stopAt = ui->spinBox_stopat->value();
+ if (stopAt > 0 && frameNumber >= stopAt)
+ {
+ stopTimer();
+ return;
+ }
+
+ cv::Mat cv_frame_small;
+ cv::resize(cv_frame, cv_frame_small, cv::Size(250, 250));
+
+ QImage qt_frame = cv2qimage(cv_frame_small);
+ ui->label_img_in->setPixmap(QPixmap::fromImage(qt_frame, Qt::MonoOnly));
+
+ processFrame(cv_frame);
+}
+
+QImage MainWindow::cv2qimage(const cv::Mat &cv_frame)
+{
+ if (cv_frame.channels() == 3)
+ return Mat2QImage(cv_frame);
+ else
+ return GrayMat2QImage(cv_frame);
+}
+
+void MainWindow::processFrame(const cv::Mat &cv_frame)
+{
+ cv::Mat cv_fg;
+ cv::Mat cv_bg;
+ tic();
+ bgs->process(cv_frame, cv_fg, cv_bg);
+ toc();
+ ui->label_fps_txt->setText(QString::fromStdString(its(fps())));
+
+ cv::Mat cv_fg_small;
+ cv::resize(cv_fg, cv_fg_small, cv::Size(250, 250));
+ QImage qt_fg = cv2qimage(cv_fg_small);
+ ui->label_img_fg->setPixmap(QPixmap::fromImage(qt_fg, Qt::MonoOnly));
+
+ cv::Mat cv_bg_small;
+ cv::resize(cv_bg, cv_bg_small, cv::Size(250, 250));
+ QImage qt_bg = cv2qimage(cv_bg_small);
+ ui->label_img_bg->setPixmap(QPixmap::fromImage(qt_bg, Qt::MonoOnly));
+
+ if (ui->checkBox_save_im->isChecked() || ui->checkBox_save_fg->isChecked() || ui->checkBox_save_bg->isChecked())
+ {
+ if (ui->checkBox_kfn->isChecked())
+ frameNumber_aux = frameNumber;
+ else
+ frameNumber_aux = frameNumber_aux + 1;
+ }
+ if (ui->checkBox_save_im->isChecked())
+ {
+ QString out_im_path = ui->lineEdit_out_in->text();
+ QString out_im_file = QDir(out_im_path).filePath(QString::number(frameNumber_aux) + ".png");
+ cv::imwrite(out_im_file.toStdString(), cv_frame);
+ }
+ if (ui->checkBox_save_fg->isChecked())
+ {
+ QString out_im_path = ui->lineEdit_out_fg->text();
+ QString out_im_file = QDir(out_im_path).filePath(QString::number(frameNumber_aux) + ".png");
+ cv::imwrite(out_im_file.toStdString(), cv_fg);
+ }
+ if (ui->checkBox_save_bg->isChecked())
+ {
+ QString out_im_path = ui->lineEdit_out_bg->text();
+ QString out_im_file = QDir(out_im_path).filePath(QString::number(frameNumber) + ".png");
+ cv::imwrite(out_im_file.toStdString(), cv_bg);
+ }
+}
+
+void MainWindow::tic()
+{
+ duration = static_cast(cv::getTickCount());
+}
+
+void MainWindow::toc()
+{
+ duration = (static_cast(cv::getTickCount()) - duration) / cv::getTickFrequency();
+ //std::cout << "time(sec):" << std::fixed << std::setprecision(6) << duration << std::endl;
+ //std::cout << duration << std::endl;
+}
+
+double MainWindow::fps()
+{
+ //double fps = frameNumber / duration;
+ double fps = 1 / duration;
+ //std::cout << "Estimated frames per second : " << fps << std::endl;
+ return fps;
+}
+
+bool MainWindow::setUpCamera()
+{
+ int cameraIndex = ui->spinBox_webcamera->value();
+ std::cout << "Camera index: " << cameraIndex << std::endl;
+
+ capture.open(cameraIndex);
+ return capture.isOpened();
+}
+
+bool MainWindow::setUpVideo()
+{
+ std::string videoFileName = fileName.toStdString();
+ std::cout << "Openning: " << videoFileName << std::endl;
+ capture.open(videoFileName.c_str());
+ return capture.isOpened();
+}
+
+bool MainWindow::setUpSequence()
+{
+ std::cout << "Directory path: " << fileName.toStdString() << std::endl;
+ if (QDir(fileName).exists())
+ {
+ QDir dir(fileName);
+ QStringList filters;
+ filters << "*.png" << "*.jpg" << "*.bmp" << "*.gif";
+ dir.setNameFilters(filters);
+ //entryList = dir.entryList(QDir::NoDotAndDotDot | QDir::System | QDir::Hidden | QDir::AllDirs | QDir::Files, QDir::DirsFirst);
+ //entryList = dir.entryList(QDir::Filter::Files, QDir::SortFlag::NoSort);
+ dir.setFilter(QDir::Files | QDir::NoSymLinks);
+ dir.setSorting(QDir::NoSort); // will sort manually with std::sort
+ //dir.setSorting(QDir::LocaleAware);
+ entryList = dir.entryList();
+
+ std::cout << entryList.length() << std::endl;
+ if (entryList.length() == 0)
+ {
+ QMessageBox::warning(this, "Warning", "No image found! (png, jpg, bmp, gif)");
+ return false;
+ }
+
+ QCollator collator;
+ collator.setNumericMode(true);
+ std::sort(
+ entryList.begin(),
+ entryList.end(),
+ [&collator](const QString &file1, const QString &file2)
+ {
+ return collator.compare(file1, file2) < 0;
+ });
+
+ // for(int i = 0; i < entryList.length(); i++)
+ // {
+ // QString file = entryList.at(i);
+ // std::cout << file.toStdString() << std::endl;
+ // }
+ return true;
+ }
+ else
+ {
+ QMessageBox::warning(this, "Warning", "Directory path doesn't exist!");
+ return false;
+ }
+}
+
+QString MainWindow::getSelectedAlgorithmName()
+{
+ QModelIndex index = ui->listView_algorithms->currentIndex();
+ QString algorithm_name = index.data(Qt::DisplayRole).toString();
+ return algorithm_name;
+}
+
+void MainWindow::on_listView_algorithms_doubleClicked(const QModelIndex &index)
+{
+ QString algorithm_name = index.data(Qt::DisplayRole).toString();
+ std::cout << "Selected algorithm: " << algorithm_name.toStdString() << std::endl;
+
+ // CodeEditor editor;
+ // editor.setWindowTitle(QObject::tr("Code Editor Example"));
+ // editor.show();
+
+ QString configFileName = QDir(".").filePath("config/" + algorithm_name + ".xml");
+ std::cout << "Looking for: " << configFileName.toStdString() << std::endl;
+
+ if (fileExists(configFileName))
+ {
+ textEditor.loadFile(configFileName);
+ textEditor.show();
+ }
+ else
+ {
+ QMessageBox::warning(this, "Warning", "XML configuration file not found!\nPlease run the algorithm first!");
+ return;
+ }
+}
diff --git a/gui_qt/mainwindow.h b/gui_qt/mainwindow.h
new file mode 100644
index 0000000..a834882
--- /dev/null
+++ b/gui_qt/mainwindow.h
@@ -0,0 +1,110 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+#pragma once
+
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+
+#include
+
+#include "qt_utils.h"
+#include "texteditor.h"
+#include "../package_bgs/bgslibrary.h"
+
+namespace bgslibrary
+{
+ template IBGS * createInstance() { return new T; }
+ typedef std::map map_ibgs;
+
+ IBGS* get_alg(std::string alg_name);
+ QStringList get_algs_name();
+}
+
+namespace Ui {
+ class MainWindow;
+}
+
+class MainWindow : public QMainWindow
+{
+ Q_OBJECT
+
+public:
+ explicit MainWindow(QWidget *parent = 0);
+ ~MainWindow();
+
+ private slots:
+ void on_actionExit_triggered();
+
+ void on_pushButton_inputdata_clicked();
+
+ void on_pushButton_start_clicked();
+
+ void on_pushButton_stop_clicked();
+
+ void on_pushButton_out_in_clicked();
+
+ void on_pushButton_out_fg_clicked();
+
+ void on_pushButton_out_bg_clicked();
+
+ void on_listView_algorithms_doubleClicked(const QModelIndex &index);
+
+private:
+ Ui::MainWindow *ui;
+ QString fileName;
+ cv::VideoCapture capture;
+ bool useCamera = false;
+ bool useVideo = false;
+ bool useSequence = false;
+ QStringList entryList;
+ long long frameNumber = 0;
+ long long frameNumber_aux = 0;
+ bool setUpCapture();
+ bool setUpCamera();
+ bool setUpVideo();
+ bool setUpSequence();
+ QString getSelectedAlgorithmName();
+ QTimer* timer;
+ void startTimer();
+ void stopTimer();
+ void setFrameNumber(long long frameNumber);
+ QImage cv2qimage(const cv::Mat &cv_frame);
+ void processFrame(const cv::Mat &cv_frame);
+ IBGS *bgs;
+ void createBGS();
+ void destroyBGS();
+ double duration = 0;
+ void tic();
+ void toc();
+ double fps();
+ int capture_length = 0;
+ TextEditor textEditor;
+
+ public slots:
+ void startCapture();
+};
diff --git a/gui_qt/mainwindow.ui b/gui_qt/mainwindow.ui
new file mode 100644
index 0000000..75e9e61
--- /dev/null
+++ b/gui_qt/mainwindow.ui
@@ -0,0 +1,631 @@
+
+
+ MainWindow
+
+
+
+ 0
+ 0
+ 1070
+ 559
+
+
+
+ BGSLibrary QT GUI
+
+
+
+
+
+ 10
+ 10
+ 251
+ 16
+
+
+
+ Algorithms
+
+
+
+
+
+ 10
+ 30
+ 256
+ 361
+
+
+
+ QAbstractItemView::NoEditTriggers
+
+
+
+
+
+ 280
+ 10
+ 601
+ 16
+
+
+
+ Input (specify a video file or a directory path containing the sequence of images)
+
+
+
+
+
+ 280
+ 30
+ 721
+ 22
+
+
+
+ ./dataset/video.avi
+
+
+
+
+
+ 1010
+ 30
+ 40
+ 21
+
+
+
+ ...
+
+
+
+
+
+ 280
+ 60
+ 131
+ 20
+
+
+
+ Use web camera
+
+
+
+
+
+ 410
+ 60
+ 42
+ 20
+
+
+
+
+
+
+ 470
+ 60
+ 151
+ 20
+
+
+
+ Sequence of images?
+
+
+
+
+
+ 945
+ 60
+ 55
+ 20
+
+
+
+ Start at:
+
+
+
+
+
+ 1000
+ 60
+ 50
+ 20
+
+
+
+ 9999
+
+
+
+
+
+ 945
+ 85
+ 55
+ 20
+
+
+
+ Stop at:
+
+
+
+
+
+ 1000
+ 85
+ 50
+ 20
+
+
+
+ 9999
+
+
+
+
+
+ 280
+ 120
+ 250
+ 16
+
+
+
+ Input
+
+
+ Qt::AlignCenter
+
+
+
+
+
+ 280
+ 140
+ 250
+ 250
+
+
+
+ QFrame::Box
+
+
+ IMG_INPUT
+
+
+ Qt::AlignCenter
+
+
+
+
+
+ 540
+ 140
+ 250
+ 250
+
+
+
+ QFrame::Box
+
+
+ IMG_FOREGROUND
+
+
+ Qt::AlignCenter
+
+
+
+
+
+ 800
+ 140
+ 250
+ 250
+
+
+
+ QFrame::Box
+
+
+ IMG_BACKGROUND
+
+
+ Qt::AlignCenter
+
+
+
+
+
+ 540
+ 120
+ 250
+ 16
+
+
+
+ Foreground mask
+
+
+ Qt::AlignCenter
+
+
+
+
+
+ 800
+ 120
+ 250
+ 16
+
+
+
+ Background model
+
+
+ Qt::AlignCenter
+
+
+
+
+
+ 280
+ 400
+ 52
+ 20
+
+
+
+ Save
+
+
+
+
+
+ 540
+ 400
+ 52
+ 20
+
+
+
+ Save
+
+
+
+
+
+ 800
+ 400
+ 52
+ 20
+
+
+
+ Save
+
+
+
+
+
+ 960
+ 470
+ 93
+ 23
+
+
+
+ Stop
+
+
+
+
+
+ 850
+ 470
+ 93
+ 23
+
+
+
+ Start
+
+
+
+
+
+ 280
+ 470
+ 550
+ 23
+
+
+
+ 0
+
+
+
+
+
+ 10
+ 400
+ 121
+ 16
+
+
+
+ Estimated FPS:
+
+
+
+
+
+ 210
+ 400
+ 55
+ 16
+
+
+
+ Qt::LeftToRight
+
+
+ QFrame::Box
+
+
+ 0
+
+
+ Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter
+
+
+
+
+
+ 10
+ 420
+ 121
+ 16
+
+
+
+ Frame number:
+
+
+
+
+
+ 210
+ 420
+ 55
+ 16
+
+
+
+ Qt::LeftToRight
+
+
+ QFrame::Box
+
+
+ 0
+
+
+ Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter
+
+
+
+
+
+ 209
+ 470
+ 61
+ 23
+
+
+
+ Progress:
+
+
+
+
+
+ 10
+ 440
+ 121
+ 16
+
+
+
+ Frame resolution:
+
+
+
+
+
+ 140
+ 440
+ 55
+ 16
+
+
+
+ Qt::LeftToRight
+
+
+ QFrame::Box
+
+
+ 0
+
+
+ Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter
+
+
+
+
+
+ 210
+ 440
+ 55
+ 16
+
+
+
+ Qt::LeftToRight
+
+
+ QFrame::Box
+
+
+ 0
+
+
+ Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter
+
+
+
+
+
+ 193
+ 440
+ 21
+ 16
+
+
+
+ x
+
+
+ Qt::AlignCenter
+
+
+
+
+
+ 348
+ 400
+ 140
+ 20
+
+
+
+ ./output/in/
+
+
+
+
+
+ 490
+ 400
+ 40
+ 20
+
+
+
+ ...
+
+
+
+
+
+ 608
+ 400
+ 140
+ 20
+
+
+
+ ./output/fg/
+
+
+
+
+
+ 750
+ 400
+ 40
+ 20
+
+
+
+ ...
+
+
+
+
+
+ 1010
+ 400
+ 40
+ 20
+
+
+
+ ...
+
+
+
+
+
+ 868
+ 400
+ 140
+ 20
+
+
+
+ ./output/bg/
+
+
+
+
+
+ 280
+ 420
+ 141
+ 20
+
+
+
+ Keep frame number
+
+
+ true
+
+
+
+
+
+
+
+ Exit
+
+
+
+
+
+
+
diff --git a/gui_qt/qt_utils.cpp b/gui_qt/qt_utils.cpp
new file mode 100644
index 0000000..2464d78
--- /dev/null
+++ b/gui_qt/qt_utils.cpp
@@ -0,0 +1,74 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+
+#include "qt_utils.h"
+
+QImage GrayMat2QImage(cv::Mat const& src) {
+ cv::Mat temp;
+ src.copyTo(temp);
+ QImage dest((const uchar *)temp.data, temp.cols, temp.rows, temp.step, QImage::Format_Indexed8);
+ dest.bits();
+ return dest;
+}
+QImage Mat2QImage(cv::Mat const& src) {
+ cv::Mat temp;
+ cvtColor(src, temp, CV_BGR2RGB);
+ QImage dest((const uchar *)temp.data, temp.cols, temp.rows, temp.step, QImage::Format_RGB888);
+ dest.bits();
+ return dest;
+}
+cv::Mat QImage2Mat(QImage const& src) {
+ cv::Mat tmp(src.height(), src.width(), CV_8UC3, (uchar*)src.bits(), src.bytesPerLine());
+ cv::Mat result;
+ cvtColor(tmp, result, CV_RGB2BGR);
+ return result;
+}
+
+QString base64_encode(const QString string) {
+ QByteArray ba;
+ ba.append(string);
+ return ba.toBase64();
+}
+QString base64_decode(const QString string) {
+ QByteArray ba;
+ ba.append(string);
+ return QByteArray::fromBase64(ba);
+}
+QString md5_encode(const QString string) {
+ QByteArray ba;
+ ba.append(string);
+ return QString(QCryptographicHash::hash((ba), QCryptographicHash::Md5).toHex());
+}
+
+int sti(const std::string &s) {
+ int i;
+ std::stringstream ss;
+ ss << s;
+ ss >> i;
+ return i;
+}
+std::string its(int i) {
+ std::stringstream ss;
+ ss << i;
+ return ss.str();
+}
+
+bool fileExists(QString path) {
+ QFileInfo check_file(path);
+ // check if file exists and if yes: Is it really a file and no directory?
+ return check_file.exists() && check_file.isFile();
+}
diff --git a/gui_qt/qt_utils.h b/gui_qt/qt_utils.h
new file mode 100644
index 0000000..84128c5
--- /dev/null
+++ b/gui_qt/qt_utils.h
@@ -0,0 +1,99 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+#pragma once
+
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+
+QImage GrayMat2QImage(cv::Mat const& src);
+QImage Mat2QImage(cv::Mat const& src);
+cv::Mat QImage2Mat(QImage const& src);
+
+QString base64_encode(const QString string);
+QString base64_decode(const QString string);
+QString md5_encode(const QString);
+
+int sti(const std::string &s);
+std::string its(int i);
+
+bool fileExists(QString path);
+
+/*
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+
+class FileDialog : public QFileDialog
+{
+ Q_OBJECT
+ public:
+ explicit FileDialog(QWidget *parent = Q_NULLPTR)
+ : QFileDialog(parent)
+ {
+ setOption(QFileDialog::DontUseNativeDialog);
+ setFileMode(QFileDialog::Directory);
+ //setFileMode(QFileDialog::ExistingFiles);
+ //setFileMode(QFileDialog::Directory|QFileDialog::ExistingFiles);
+ for (auto *pushButton : findChildren()) {
+ qDebug() << pushButton->text();
+ if (pushButton->text() == "&Open" || pushButton->text() == "&Choose") {
+ openButton = pushButton;
+ break;
+ }
+ }
+ disconnect(openButton, SIGNAL(clicked(bool)));
+ connect(openButton, &QPushButton::clicked, this, &FileDialog::openClicked);
+ treeView = findChild();
+ }
+
+ QStringList selected() const
+ {
+ return selectedFilePaths;
+ }
+
+ public slots:
+ void openClicked()
+ {
+ selectedFilePaths.clear();
+ qDebug() << treeView->selectionModel()->selection();
+ for (const auto& modelIndex : treeView->selectionModel()->selectedIndexes()) {
+ qDebug() << modelIndex.column();
+ if (modelIndex.column() == 0)
+ selectedFilePaths.append(directory().absolutePath() + modelIndex.data().toString());
+ }
+ emit filesSelected(selectedFilePaths);
+ hide();
+ qDebug() << selectedFilePaths;
+ }
+
+ private:
+ QTreeView *treeView;
+ QPushButton *openButton;
+ QStringList selectedFilePaths;
+};
+*/
diff --git a/gui_qt/texteditor.cpp b/gui_qt/texteditor.cpp
new file mode 100644
index 0000000..80f45e1
--- /dev/null
+++ b/gui_qt/texteditor.cpp
@@ -0,0 +1,320 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+
+#include
+
+#include "texteditor.h"
+
+TextEditor::TextEditor()
+ : textEdit(new QPlainTextEdit)
+{
+ setCentralWidget(textEdit);
+
+ createActions();
+ createStatusBar();
+
+ readSettings();
+
+ connect(textEdit->document(), &QTextDocument::contentsChanged,
+ this, &TextEditor::documentWasModified);
+
+#ifndef QT_NO_SESSIONMANAGER
+ QGuiApplication::setFallbackSessionManagementEnabled(false);
+ connect(qApp, &QGuiApplication::commitDataRequest,
+ this, &TextEditor::commitData);
+#endif
+
+ setCurrentFile(QString());
+ setUnifiedTitleAndToolBarOnMac(true);
+}
+
+void TextEditor::closeEvent(QCloseEvent *event)
+{
+ if (maybeSave()) {
+ writeSettings();
+ event->accept();
+ }
+ else {
+ event->ignore();
+ }
+}
+
+void TextEditor::newFile()
+{
+ if (maybeSave()) {
+ textEdit->clear();
+ setCurrentFile(QString());
+ }
+}
+
+void TextEditor::open()
+{
+ if (maybeSave()) {
+ QString fileName = QFileDialog::getOpenFileName(this);
+ if (!fileName.isEmpty())
+ loadFile(fileName);
+ }
+}
+
+bool TextEditor::save()
+{
+ if (curFile.isEmpty()) {
+ return saveAs();
+ }
+ else {
+ return saveFile(curFile);
+ }
+}
+
+bool TextEditor::saveAs()
+{
+ QFileDialog dialog(this);
+ dialog.setWindowModality(Qt::WindowModal);
+ dialog.setAcceptMode(QFileDialog::AcceptSave);
+ if (dialog.exec() != QDialog::Accepted)
+ return false;
+ return saveFile(dialog.selectedFiles().first());
+}
+
+void TextEditor::about()
+{
+ QMessageBox::about(this, tr("About BGSLibrary"),
+ tr("The BGSLibrary provides an easy-to-use framework "
+ "to perform foreground-background separation in videos."));
+}
+
+void TextEditor::documentWasModified()
+{
+ setWindowModified(textEdit->document()->isModified());
+}
+
+void TextEditor::createActions()
+{
+
+ QMenu *fileMenu = menuBar()->addMenu(tr("&File"));
+ QToolBar *fileToolBar = addToolBar(tr("File"));
+ const QIcon newIcon = QIcon::fromTheme("document-new", QIcon(":/figs/new.png"));
+ QAction *newAct = new QAction(newIcon, tr("&New"), this);
+ newAct->setShortcuts(QKeySequence::New);
+ newAct->setStatusTip(tr("Create a new file"));
+ connect(newAct, &QAction::triggered, this, &TextEditor::newFile);
+ fileMenu->addAction(newAct);
+ fileToolBar->addAction(newAct);
+
+ const QIcon openIcon = QIcon::fromTheme("document-open", QIcon(":/figs/open.png"));
+ QAction *openAct = new QAction(openIcon, tr("&Open..."), this);
+ openAct->setShortcuts(QKeySequence::Open);
+ openAct->setStatusTip(tr("Open an existing file"));
+ connect(openAct, &QAction::triggered, this, &TextEditor::open);
+ fileMenu->addAction(openAct);
+ fileToolBar->addAction(openAct);
+
+ const QIcon saveIcon = QIcon::fromTheme("document-save", QIcon(":/figs/save.png"));
+ QAction *saveAct = new QAction(saveIcon, tr("&Save"), this);
+ saveAct->setShortcuts(QKeySequence::Save);
+ saveAct->setStatusTip(tr("Save the document to disk"));
+ connect(saveAct, &QAction::triggered, this, &TextEditor::save);
+ fileMenu->addAction(saveAct);
+ fileToolBar->addAction(saveAct);
+
+ const QIcon saveAsIcon = QIcon::fromTheme("document-save-as");
+ QAction *saveAsAct = fileMenu->addAction(saveAsIcon, tr("Save &As..."), this, &TextEditor::saveAs);
+ saveAsAct->setShortcuts(QKeySequence::SaveAs);
+ saveAsAct->setStatusTip(tr("Save the document under a new name"));
+
+
+ fileMenu->addSeparator();
+
+ const QIcon exitIcon = QIcon::fromTheme("application-exit");
+ QAction *exitAct = fileMenu->addAction(exitIcon, tr("E&xit"), this, &QWidget::close);
+ exitAct->setShortcuts(QKeySequence::Quit);
+ exitAct->setStatusTip(tr("Exit the application"));
+
+ QMenu *editMenu = menuBar()->addMenu(tr("&Edit"));
+ QToolBar *editToolBar = addToolBar(tr("Edit"));
+#ifndef QT_NO_CLIPBOARD
+ const QIcon cutIcon = QIcon::fromTheme("edit-cut", QIcon(":/figs/cut.png"));
+ QAction *cutAct = new QAction(cutIcon, tr("Cu&t"), this);
+ cutAct->setShortcuts(QKeySequence::Cut);
+ cutAct->setStatusTip(tr("Cut the current selection's contents to the "
+ "clipboard"));
+ connect(cutAct, &QAction::triggered, textEdit, &QPlainTextEdit::cut);
+ editMenu->addAction(cutAct);
+ editToolBar->addAction(cutAct);
+
+ const QIcon copyIcon = QIcon::fromTheme("edit-copy", QIcon(":/figs/copy.png"));
+ QAction *copyAct = new QAction(copyIcon, tr("&Copy"), this);
+ copyAct->setShortcuts(QKeySequence::Copy);
+ copyAct->setStatusTip(tr("Copy the current selection's contents to the "
+ "clipboard"));
+ connect(copyAct, &QAction::triggered, textEdit, &QPlainTextEdit::copy);
+ editMenu->addAction(copyAct);
+ editToolBar->addAction(copyAct);
+
+ const QIcon pasteIcon = QIcon::fromTheme("edit-paste", QIcon(":/figs/paste.png"));
+ QAction *pasteAct = new QAction(pasteIcon, tr("&Paste"), this);
+ pasteAct->setShortcuts(QKeySequence::Paste);
+ pasteAct->setStatusTip(tr("Paste the clipboard's contents into the current "
+ "selection"));
+ connect(pasteAct, &QAction::triggered, textEdit, &QPlainTextEdit::paste);
+ editMenu->addAction(pasteAct);
+ editToolBar->addAction(pasteAct);
+
+ menuBar()->addSeparator();
+
+#endif // !QT_NO_CLIPBOARD
+
+ QMenu *helpMenu = menuBar()->addMenu(tr("&Help"));
+ QAction *aboutAct = helpMenu->addAction(tr("&About"), this, &TextEditor::about);
+ aboutAct->setStatusTip(tr("Show the application's About box"));
+
+
+ QAction *aboutQtAct = helpMenu->addAction(tr("About &Qt"), qApp, &QApplication::aboutQt);
+ aboutQtAct->setStatusTip(tr("Show the Qt library's About box"));
+
+#ifndef QT_NO_CLIPBOARD
+ cutAct->setEnabled(false);
+ copyAct->setEnabled(false);
+ connect(textEdit, &QPlainTextEdit::copyAvailable, cutAct, &QAction::setEnabled);
+ connect(textEdit, &QPlainTextEdit::copyAvailable, copyAct, &QAction::setEnabled);
+#endif // !QT_NO_CLIPBOARD
+}
+
+void TextEditor::createStatusBar()
+{
+ statusBar()->showMessage(tr("Ready"));
+}
+
+void TextEditor::readSettings()
+{
+ QSettings settings(QCoreApplication::organizationName(), QCoreApplication::applicationName());
+ const QByteArray geometry = settings.value("geometry", QByteArray()).toByteArray();
+ if (geometry.isEmpty()) {
+ const QRect availableGeometry = QApplication::desktop()->availableGeometry(this);
+ resize(availableGeometry.width() / 3, availableGeometry.height() / 2);
+ move((availableGeometry.width() - width()) / 2,
+ (availableGeometry.height() - height()) / 2);
+ }
+ else {
+ restoreGeometry(geometry);
+ }
+}
+
+void TextEditor::writeSettings()
+{
+ QSettings settings(QCoreApplication::organizationName(), QCoreApplication::applicationName());
+ settings.setValue("geometry", saveGeometry());
+}
+
+bool TextEditor::maybeSave()
+{
+ if (!textEdit->document()->isModified())
+ return true;
+ const QMessageBox::StandardButton ret
+ = QMessageBox::warning(this, tr("Application"),
+ tr("The document has been modified.\n"
+ "Do you want to save your changes?"),
+ QMessageBox::Save | QMessageBox::Discard | QMessageBox::Cancel);
+ switch (ret) {
+ case QMessageBox::Save:
+ return save();
+ case QMessageBox::Cancel:
+ return false;
+ default:
+ break;
+ }
+ return true;
+}
+
+void TextEditor::loadFile(const QString &fileName)
+{
+ QFile file(fileName);
+ if (!file.open(QFile::ReadOnly | QFile::Text)) {
+ QMessageBox::warning(this, tr("Application"),
+ tr("Cannot read file %1:\n%2.")
+ .arg(QDir::toNativeSeparators(fileName), file.errorString()));
+ return;
+ }
+
+ QTextStream in(&file);
+#ifndef QT_NO_CURSOR
+ QApplication::setOverrideCursor(Qt::WaitCursor);
+#endif
+ textEdit->setPlainText(in.readAll());
+#ifndef QT_NO_CURSOR
+ QApplication::restoreOverrideCursor();
+#endif
+
+ setCurrentFile(fileName);
+ statusBar()->showMessage(tr("File loaded"), 2000);
+}
+
+bool TextEditor::saveFile(const QString &fileName)
+{
+ QFile file(fileName);
+ if (!file.open(QFile::WriteOnly | QFile::Text)) {
+ QMessageBox::warning(this, tr("Application"),
+ tr("Cannot write file %1:\n%2.")
+ .arg(QDir::toNativeSeparators(fileName),
+ file.errorString()));
+ return false;
+ }
+
+ QTextStream out(&file);
+#ifndef QT_NO_CURSOR
+ QApplication::setOverrideCursor(Qt::WaitCursor);
+#endif
+ out << textEdit->toPlainText();
+#ifndef QT_NO_CURSOR
+ QApplication::restoreOverrideCursor();
+#endif
+
+ setCurrentFile(fileName);
+ statusBar()->showMessage(tr("File saved"), 2000);
+ return true;
+}
+
+void TextEditor::setCurrentFile(const QString &fileName)
+{
+ curFile = fileName;
+ textEdit->document()->setModified(false);
+ setWindowModified(false);
+
+ QString shownName = curFile;
+ if (curFile.isEmpty())
+ shownName = "untitled.txt";
+ setWindowFilePath(shownName);
+}
+
+QString TextEditor::strippedName(const QString &fullFileName)
+{
+ return QFileInfo(fullFileName).fileName();
+}
+#ifndef QT_NO_SESSIONMANAGER
+void TextEditor::commitData(QSessionManager &manager)
+{
+ if (manager.allowsInteraction()) {
+ if (!maybeSave())
+ manager.cancel();
+ }
+ else {
+ // Non-interactive: save without asking
+ if (textEdit->document()->isModified())
+ save();
+ }
+}
+#endif
diff --git a/gui_qt/texteditor.h b/gui_qt/texteditor.h
new file mode 100644
index 0000000..c0d5d8f
--- /dev/null
+++ b/gui_qt/texteditor.h
@@ -0,0 +1,64 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+#ifndef TEXTEDITOR_H
+#define TEXTEDITOR_H
+
+#include
+
+class QAction;
+class QMenu;
+class QPlainTextEdit;
+class QSessionManager;
+
+class TextEditor : public QMainWindow
+{
+ Q_OBJECT
+
+public:
+ TextEditor();
+
+ void loadFile(const QString &fileName);
+
+protected:
+ void closeEvent(QCloseEvent *event) override;
+
+ private slots:
+ void newFile();
+ void open();
+ bool save();
+ bool saveAs();
+ void about();
+ void documentWasModified();
+#ifndef QT_NO_SESSIONMANAGER
+ void commitData(QSessionManager &);
+#endif
+
+private:
+ void createActions();
+ void createStatusBar();
+ void readSettings();
+ void writeSettings();
+ bool maybeSave();
+ bool saveFile(const QString &fileName);
+ void setCurrentFile(const QString &fileName);
+ QString strippedName(const QString &fullFileName);
+
+ QPlainTextEdit *textEdit;
+ QString curFile;
+};
+
+#endif // TEXTEDITOR_H
diff --git a/gui_qt/ui_mainwindow.h b/gui_qt/ui_mainwindow.h
new file mode 100644
index 0000000..eb3f468
--- /dev/null
+++ b/gui_qt/ui_mainwindow.h
@@ -0,0 +1,306 @@
+/********************************************************************************
+** Form generated from reading UI file 'mainwindow.ui'
+**
+** Created by: Qt User Interface Compiler version 5.6.2
+**
+** WARNING! All changes made in this file will be lost when recompiling UI file!
+********************************************************************************/
+
+#ifndef UI_MAINWINDOW_H
+#define UI_MAINWINDOW_H
+
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+
+QT_BEGIN_NAMESPACE
+
+class Ui_MainWindow
+{
+public:
+ QAction *actionExit;
+ QWidget *centralWidget;
+ QLabel *label_algorithms;
+ QListView *listView_algorithms;
+ QLabel *label_inputdata;
+ QLineEdit *lineEdit_inputdata;
+ QPushButton *pushButton_inputdata;
+ QCheckBox *checkBox_webcamera;
+ QSpinBox *spinBox_webcamera;
+ QCheckBox *checkBox_imageseq;
+ QLabel *label_startat;
+ QSpinBox *spinBox_startat;
+ QLabel *label_stopat;
+ QSpinBox *spinBox_stopat;
+ QLabel *label_input;
+ QLabel *label_img_in;
+ QLabel *label_img_fg;
+ QLabel *label_img_bg;
+ QLabel *label_foreground;
+ QLabel *label_background;
+ QCheckBox *checkBox_save_im;
+ QCheckBox *checkBox_save_fg;
+ QCheckBox *checkBox_save_bg;
+ QPushButton *pushButton_stop;
+ QPushButton *pushButton_start;
+ QProgressBar *progressBar;
+ QLabel *label_exectime;
+ QLabel *label_fps_txt;
+ QLabel *label_framenumber;
+ QLabel *label_framenumber_txt;
+ QLabel *label_status;
+ QLabel *label_frameres;
+ QLabel *label_frameresw_txt;
+ QLabel *label_frameresh_txt;
+ QLabel *label_frameres_2;
+ QLineEdit *lineEdit_out_in;
+ QPushButton *pushButton_out_in;
+ QLineEdit *lineEdit_out_fg;
+ QPushButton *pushButton_out_fg;
+ QPushButton *pushButton_out_bg;
+ QLineEdit *lineEdit_out_bg;
+ QCheckBox *checkBox_kfn;
+ QMenuBar *menuBar;
+ QMenu *menuBGSLibrary;
+ QStatusBar *statusBar;
+
+ void setupUi(QMainWindow *MainWindow)
+ {
+ if (MainWindow->objectName().isEmpty())
+ MainWindow->setObjectName(QStringLiteral("MainWindow"));
+ MainWindow->resize(1070, 559);
+ actionExit = new QAction(MainWindow);
+ actionExit->setObjectName(QStringLiteral("actionExit"));
+ centralWidget = new QWidget(MainWindow);
+ centralWidget->setObjectName(QStringLiteral("centralWidget"));
+ label_algorithms = new QLabel(centralWidget);
+ label_algorithms->setObjectName(QStringLiteral("label_algorithms"));
+ label_algorithms->setGeometry(QRect(10, 10, 251, 16));
+ listView_algorithms = new QListView(centralWidget);
+ listView_algorithms->setObjectName(QStringLiteral("listView_algorithms"));
+ listView_algorithms->setGeometry(QRect(10, 30, 256, 361));
+ listView_algorithms->setEditTriggers(QAbstractItemView::NoEditTriggers);
+ label_inputdata = new QLabel(centralWidget);
+ label_inputdata->setObjectName(QStringLiteral("label_inputdata"));
+ label_inputdata->setGeometry(QRect(280, 10, 601, 16));
+ lineEdit_inputdata = new QLineEdit(centralWidget);
+ lineEdit_inputdata->setObjectName(QStringLiteral("lineEdit_inputdata"));
+ lineEdit_inputdata->setGeometry(QRect(280, 30, 721, 22));
+ pushButton_inputdata = new QPushButton(centralWidget);
+ pushButton_inputdata->setObjectName(QStringLiteral("pushButton_inputdata"));
+ pushButton_inputdata->setGeometry(QRect(1010, 30, 40, 21));
+ checkBox_webcamera = new QCheckBox(centralWidget);
+ checkBox_webcamera->setObjectName(QStringLiteral("checkBox_webcamera"));
+ checkBox_webcamera->setGeometry(QRect(280, 60, 131, 20));
+ spinBox_webcamera = new QSpinBox(centralWidget);
+ spinBox_webcamera->setObjectName(QStringLiteral("spinBox_webcamera"));
+ spinBox_webcamera->setGeometry(QRect(410, 60, 42, 20));
+ checkBox_imageseq = new QCheckBox(centralWidget);
+ checkBox_imageseq->setObjectName(QStringLiteral("checkBox_imageseq"));
+ checkBox_imageseq->setGeometry(QRect(470, 60, 151, 20));
+ label_startat = new QLabel(centralWidget);
+ label_startat->setObjectName(QStringLiteral("label_startat"));
+ label_startat->setGeometry(QRect(945, 60, 55, 20));
+ spinBox_startat = new QSpinBox(centralWidget);
+ spinBox_startat->setObjectName(QStringLiteral("spinBox_startat"));
+ spinBox_startat->setGeometry(QRect(1000, 60, 50, 20));
+ spinBox_startat->setMaximum(9999);
+ label_stopat = new QLabel(centralWidget);
+ label_stopat->setObjectName(QStringLiteral("label_stopat"));
+ label_stopat->setGeometry(QRect(945, 85, 55, 20));
+ spinBox_stopat = new QSpinBox(centralWidget);
+ spinBox_stopat->setObjectName(QStringLiteral("spinBox_stopat"));
+ spinBox_stopat->setGeometry(QRect(1000, 85, 50, 20));
+ spinBox_stopat->setMaximum(9999);
+ label_input = new QLabel(centralWidget);
+ label_input->setObjectName(QStringLiteral("label_input"));
+ label_input->setGeometry(QRect(280, 120, 250, 16));
+ label_input->setAlignment(Qt::AlignCenter);
+ label_img_in = new QLabel(centralWidget);
+ label_img_in->setObjectName(QStringLiteral("label_img_in"));
+ label_img_in->setGeometry(QRect(280, 140, 250, 250));
+ label_img_in->setFrameShape(QFrame::Box);
+ label_img_in->setAlignment(Qt::AlignCenter);
+ label_img_fg = new QLabel(centralWidget);
+ label_img_fg->setObjectName(QStringLiteral("label_img_fg"));
+ label_img_fg->setGeometry(QRect(540, 140, 250, 250));
+ label_img_fg->setFrameShape(QFrame::Box);
+ label_img_fg->setAlignment(Qt::AlignCenter);
+ label_img_bg = new QLabel(centralWidget);
+ label_img_bg->setObjectName(QStringLiteral("label_img_bg"));
+ label_img_bg->setGeometry(QRect(800, 140, 250, 250));
+ label_img_bg->setFrameShape(QFrame::Box);
+ label_img_bg->setAlignment(Qt::AlignCenter);
+ label_foreground = new QLabel(centralWidget);
+ label_foreground->setObjectName(QStringLiteral("label_foreground"));
+ label_foreground->setGeometry(QRect(540, 120, 250, 16));
+ label_foreground->setAlignment(Qt::AlignCenter);
+ label_background = new QLabel(centralWidget);
+ label_background->setObjectName(QStringLiteral("label_background"));
+ label_background->setGeometry(QRect(800, 120, 250, 16));
+ label_background->setAlignment(Qt::AlignCenter);
+ checkBox_save_im = new QCheckBox(centralWidget);
+ checkBox_save_im->setObjectName(QStringLiteral("checkBox_save_im"));
+ checkBox_save_im->setGeometry(QRect(280, 400, 52, 20));
+ checkBox_save_fg = new QCheckBox(centralWidget);
+ checkBox_save_fg->setObjectName(QStringLiteral("checkBox_save_fg"));
+ checkBox_save_fg->setGeometry(QRect(540, 400, 52, 20));
+ checkBox_save_bg = new QCheckBox(centralWidget);
+ checkBox_save_bg->setObjectName(QStringLiteral("checkBox_save_bg"));
+ checkBox_save_bg->setGeometry(QRect(800, 400, 52, 20));
+ pushButton_stop = new QPushButton(centralWidget);
+ pushButton_stop->setObjectName(QStringLiteral("pushButton_stop"));
+ pushButton_stop->setGeometry(QRect(960, 470, 93, 23));
+ pushButton_start = new QPushButton(centralWidget);
+ pushButton_start->setObjectName(QStringLiteral("pushButton_start"));
+ pushButton_start->setGeometry(QRect(850, 470, 93, 23));
+ progressBar = new QProgressBar(centralWidget);
+ progressBar->setObjectName(QStringLiteral("progressBar"));
+ progressBar->setGeometry(QRect(280, 470, 550, 23));
+ progressBar->setValue(0);
+ label_exectime = new QLabel(centralWidget);
+ label_exectime->setObjectName(QStringLiteral("label_exectime"));
+ label_exectime->setGeometry(QRect(10, 400, 121, 16));
+ label_fps_txt = new QLabel(centralWidget);
+ label_fps_txt->setObjectName(QStringLiteral("label_fps_txt"));
+ label_fps_txt->setGeometry(QRect(210, 400, 55, 16));
+ label_fps_txt->setLayoutDirection(Qt::LeftToRight);
+ label_fps_txt->setFrameShape(QFrame::Box);
+ label_fps_txt->setAlignment(Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter);
+ label_framenumber = new QLabel(centralWidget);
+ label_framenumber->setObjectName(QStringLiteral("label_framenumber"));
+ label_framenumber->setGeometry(QRect(10, 420, 121, 16));
+ label_framenumber_txt = new QLabel(centralWidget);
+ label_framenumber_txt->setObjectName(QStringLiteral("label_framenumber_txt"));
+ label_framenumber_txt->setGeometry(QRect(210, 420, 55, 16));
+ label_framenumber_txt->setLayoutDirection(Qt::LeftToRight);
+ label_framenumber_txt->setFrameShape(QFrame::Box);
+ label_framenumber_txt->setAlignment(Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter);
+ label_status = new QLabel(centralWidget);
+ label_status->setObjectName(QStringLiteral("label_status"));
+ label_status->setGeometry(QRect(209, 470, 61, 23));
+ label_frameres = new QLabel(centralWidget);
+ label_frameres->setObjectName(QStringLiteral("label_frameres"));
+ label_frameres->setGeometry(QRect(10, 440, 121, 16));
+ label_frameresw_txt = new QLabel(centralWidget);
+ label_frameresw_txt->setObjectName(QStringLiteral("label_frameresw_txt"));
+ label_frameresw_txt->setGeometry(QRect(140, 440, 55, 16));
+ label_frameresw_txt->setLayoutDirection(Qt::LeftToRight);
+ label_frameresw_txt->setFrameShape(QFrame::Box);
+ label_frameresw_txt->setAlignment(Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter);
+ label_frameresh_txt = new QLabel(centralWidget);
+ label_frameresh_txt->setObjectName(QStringLiteral("label_frameresh_txt"));
+ label_frameresh_txt->setGeometry(QRect(210, 440, 55, 16));
+ label_frameresh_txt->setLayoutDirection(Qt::LeftToRight);
+ label_frameresh_txt->setFrameShape(QFrame::Box);
+ label_frameresh_txt->setAlignment(Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter);
+ label_frameres_2 = new QLabel(centralWidget);
+ label_frameres_2->setObjectName(QStringLiteral("label_frameres_2"));
+ label_frameres_2->setGeometry(QRect(193, 440, 21, 16));
+ label_frameres_2->setAlignment(Qt::AlignCenter);
+ lineEdit_out_in = new QLineEdit(centralWidget);
+ lineEdit_out_in->setObjectName(QStringLiteral("lineEdit_out_in"));
+ lineEdit_out_in->setGeometry(QRect(348, 400, 140, 20));
+ pushButton_out_in = new QPushButton(centralWidget);
+ pushButton_out_in->setObjectName(QStringLiteral("pushButton_out_in"));
+ pushButton_out_in->setGeometry(QRect(490, 400, 40, 20));
+ lineEdit_out_fg = new QLineEdit(centralWidget);
+ lineEdit_out_fg->setObjectName(QStringLiteral("lineEdit_out_fg"));
+ lineEdit_out_fg->setGeometry(QRect(608, 400, 140, 20));
+ pushButton_out_fg = new QPushButton(centralWidget);
+ pushButton_out_fg->setObjectName(QStringLiteral("pushButton_out_fg"));
+ pushButton_out_fg->setGeometry(QRect(750, 400, 40, 20));
+ pushButton_out_bg = new QPushButton(centralWidget);
+ pushButton_out_bg->setObjectName(QStringLiteral("pushButton_out_bg"));
+ pushButton_out_bg->setGeometry(QRect(1010, 400, 40, 20));
+ lineEdit_out_bg = new QLineEdit(centralWidget);
+ lineEdit_out_bg->setObjectName(QStringLiteral("lineEdit_out_bg"));
+ lineEdit_out_bg->setGeometry(QRect(868, 400, 140, 20));
+ checkBox_kfn = new QCheckBox(centralWidget);
+ checkBox_kfn->setObjectName(QStringLiteral("checkBox_kfn"));
+ checkBox_kfn->setGeometry(QRect(280, 420, 141, 20));
+ checkBox_kfn->setChecked(true);
+ MainWindow->setCentralWidget(centralWidget);
+ menuBar = new QMenuBar(MainWindow);
+ menuBar->setObjectName(QStringLiteral("menuBar"));
+ menuBar->setGeometry(QRect(0, 0, 1070, 26));
+ menuBGSLibrary = new QMenu(menuBar);
+ menuBGSLibrary->setObjectName(QStringLiteral("menuBGSLibrary"));
+ MainWindow->setMenuBar(menuBar);
+ statusBar = new QStatusBar(MainWindow);
+ statusBar->setObjectName(QStringLiteral("statusBar"));
+ MainWindow->setStatusBar(statusBar);
+
+ menuBar->addAction(menuBGSLibrary->menuAction());
+ menuBGSLibrary->addAction(actionExit);
+
+ retranslateUi(MainWindow);
+
+ QMetaObject::connectSlotsByName(MainWindow);
+ } // setupUi
+
+ void retranslateUi(QMainWindow *MainWindow)
+ {
+ MainWindow->setWindowTitle(QApplication::translate("MainWindow", "BGSLibrary QT GUI", 0));
+ actionExit->setText(QApplication::translate("MainWindow", "Exit", 0));
+ label_algorithms->setText(QApplication::translate("MainWindow", "Algorithms", 0));
+ label_inputdata->setText(QApplication::translate("MainWindow", "Input (specify a video file or a directory path containing the sequence of images)", 0));
+ lineEdit_inputdata->setText(QApplication::translate("MainWindow", "./dataset/video.avi", 0));
+ pushButton_inputdata->setText(QApplication::translate("MainWindow", "...", 0));
+ checkBox_webcamera->setText(QApplication::translate("MainWindow", "Use web camera", 0));
+ checkBox_imageseq->setText(QApplication::translate("MainWindow", "Sequence of images?", 0));
+ label_startat->setText(QApplication::translate("MainWindow", "Start at:", 0));
+ label_stopat->setText(QApplication::translate("MainWindow", "Stop at:", 0));
+ label_input->setText(QApplication::translate("MainWindow", "Input", 0));
+ label_img_in->setText(QApplication::translate("MainWindow", "IMG_INPUT", 0));
+ label_img_fg->setText(QApplication::translate("MainWindow", "IMG_FOREGROUND", 0));
+ label_img_bg->setText(QApplication::translate("MainWindow", "IMG_BACKGROUND", 0));
+ label_foreground->setText(QApplication::translate("MainWindow", "Foreground mask", 0));
+ label_background->setText(QApplication::translate("MainWindow", "Background model", 0));
+ checkBox_save_im->setText(QApplication::translate("MainWindow", "Save", 0));
+ checkBox_save_fg->setText(QApplication::translate("MainWindow", "Save", 0));
+ checkBox_save_bg->setText(QApplication::translate("MainWindow", "Save", 0));
+ pushButton_stop->setText(QApplication::translate("MainWindow", "Stop", 0));
+ pushButton_start->setText(QApplication::translate("MainWindow", "Start", 0));
+ label_exectime->setText(QApplication::translate("MainWindow", "Estimated FPS:", 0));
+ label_fps_txt->setText(QApplication::translate("MainWindow", "0", 0));
+ label_framenumber->setText(QApplication::translate("MainWindow", "Frame number:", 0));
+ label_framenumber_txt->setText(QApplication::translate("MainWindow", "0", 0));
+ label_status->setText(QApplication::translate("MainWindow", "Progress:", 0));
+ label_frameres->setText(QApplication::translate("MainWindow", "Frame resolution:", 0));
+ label_frameresw_txt->setText(QApplication::translate("MainWindow", "0", 0));
+ label_frameresh_txt->setText(QApplication::translate("MainWindow", "0", 0));
+ label_frameres_2->setText(QApplication::translate("MainWindow", "x", 0));
+ lineEdit_out_in->setText(QApplication::translate("MainWindow", "./output/in/", 0));
+ pushButton_out_in->setText(QApplication::translate("MainWindow", "...", 0));
+ lineEdit_out_fg->setText(QApplication::translate("MainWindow", "./output/fg/", 0));
+ pushButton_out_fg->setText(QApplication::translate("MainWindow", "...", 0));
+ pushButton_out_bg->setText(QApplication::translate("MainWindow", "...", 0));
+ lineEdit_out_bg->setText(QApplication::translate("MainWindow", "./output/bg/", 0));
+ checkBox_kfn->setText(QApplication::translate("MainWindow", "Keep frame number", 0));
+ menuBGSLibrary->setTitle(QApplication::translate("MainWindow", "BGSLibrary", 0));
+ } // retranslateUi
+
+};
+
+namespace Ui {
+ class MainWindow: public Ui_MainWindow {};
+} // namespace Ui
+
+QT_END_NAMESPACE
+
+#endif // UI_MAINWINDOW_H
diff --git a/output/bg/.gitignore b/output/bg/.gitignore
new file mode 100644
index 0000000..4e2a98b
--- /dev/null
+++ b/output/bg/.gitignore
@@ -0,0 +1,4 @@
+# Ignore everything in this directory
+*
+# Except these files
+!.gitignore
diff --git a/output/fg/.gitignore b/output/fg/.gitignore
new file mode 100644
index 0000000..4e2a98b
--- /dev/null
+++ b/output/fg/.gitignore
@@ -0,0 +1,4 @@
+# Ignore everything in this directory
+*
+# Except these files
+!.gitignore
diff --git a/output/in/.gitignore b/output/in/.gitignore
new file mode 100644
index 0000000..4e2a98b
--- /dev/null
+++ b/output/in/.gitignore
@@ -0,0 +1,4 @@
+# Ignore everything in this directory
+*
+# Except these files
+!.gitignore
diff --git a/package_bgs/tb/PerformanceUtils.cpp b/package_analysis/PerformanceUtils.cpp
similarity index 59%
rename from package_bgs/tb/PerformanceUtils.cpp
rename to package_analysis/PerformanceUtils.cpp
index 0d7cf77..6ad5e5f 100644
--- a/package_bgs/tb/PerformanceUtils.cpp
+++ b/package_analysis/PerformanceUtils.cpp
@@ -15,15 +15,16 @@ You should have received a copy of the GNU General Public License
along with BGSLibrary. If not, see .
*/
#include "PerformanceUtils.h"
-#include
+//#include
+//#include
-PerformanceUtils::PerformanceUtils(void){}
+PerformanceUtils::PerformanceUtils(void) {}
-PerformanceUtils::~PerformanceUtils(void){}
+PerformanceUtils::~PerformanceUtils(void) {}
float PerformanceUtils::NrPixels(IplImage *image)
{
- return (float) (image->width * image->height);
+ return (float)(image->width * image->height);
}
float PerformanceUtils::NrAllDetectedPixNotNULL(IplImage *image, IplImage *ground_truth)
@@ -31,19 +32,19 @@ float PerformanceUtils::NrAllDetectedPixNotNULL(IplImage *image, IplImage *groun
//Nombre de tous les pixels non nuls dans Groundthruth et dans image
float Union12 = 0.0;
- unsigned char *pixelGT = (unsigned char*) malloc(1*sizeof(unsigned char));
- unsigned char *pixelI = (unsigned char*) malloc(1*sizeof(unsigned char));
+ unsigned char *pixelGT = (unsigned char*)malloc(1 * sizeof(unsigned char));
+ unsigned char *pixelI = (unsigned char*)malloc(1 * sizeof(unsigned char));
PixelUtils p;
- for(int y = 0; y < image->height; y++)
+ for (int y = 0; y < image->height; y++)
{
- for(int x = 0; x < image->width; x++)
- {
- p.GetGrayPixel(ground_truth,x,y,pixelGT);
- p.GetGrayPixel(image,x,y,pixelI);
+ for (int x = 0; x < image->width; x++)
+ {
+ p.GetGrayPixel(ground_truth, x, y, pixelGT);
+ p.GetGrayPixel(image, x, y, pixelI);
- if((pixelGT[0] != 0) || (pixelI[0] != 0))
+ if ((pixelGT[0] != 0) || (pixelI[0] != 0))
Union12++;
}
}
@@ -51,44 +52,44 @@ float PerformanceUtils::NrAllDetectedPixNotNULL(IplImage *image, IplImage *groun
free(pixelGT);
free(pixelI);
- return Union12;
+ return Union12;
}
float PerformanceUtils::NrTruePositives(IplImage *image, IplImage *ground_truth, bool debug)
{
float nTP = 0.0;
- unsigned char *pixelGT = (unsigned char*) malloc(1*sizeof(unsigned char));
- unsigned char *pixelI = (unsigned char*) malloc(1*sizeof(unsigned char));
+ unsigned char *pixelGT = (unsigned char*)malloc(1 * sizeof(unsigned char));
+ unsigned char *pixelI = (unsigned char*)malloc(1 * sizeof(unsigned char));
IplImage *TPimage = 0;
- if(debug)
+ if (debug)
{
- TPimage = cvCreateImage(cvSize(image->width,image->height),image->depth,image->nChannels);
- cvFillImage(TPimage,0.0);
+ TPimage = cvCreateImage(cvSize(image->width, image->height), image->depth, image->nChannels);
+ cvSetZero(TPimage);
}
PixelUtils p;
- for(int y = 0; y < image->height; y++)
+ for (int y = 0; y < image->height; y++)
{
- for(int x = 0; x < image->width; x++)
- {
- p.GetGrayPixel(ground_truth,x,y,pixelGT);
- p.GetGrayPixel(image,x,y,pixelI);
+ for (int x = 0; x < image->width; x++)
+ {
+ p.GetGrayPixel(ground_truth, x, y, pixelGT);
+ p.GetGrayPixel(image, x, y, pixelI);
- if((pixelGT[0] != 0) && (pixelI[0] != 0))
+ if ((pixelGT[0] != 0) && (pixelI[0] != 0))
{
- if(debug)
- p.PutGrayPixel(TPimage,x,y,*pixelI);
+ if (debug)
+ p.PutGrayPixel(TPimage, x, y, *pixelI);
nTP++;
}
}
}
- if(debug)
+ if (debug)
{
cvNamedWindow("TPImage", 0);
cvShowImage("TPImage", TPimage);
@@ -101,46 +102,46 @@ float PerformanceUtils::NrTruePositives(IplImage *image, IplImage *ground_truth,
free(pixelGT);
free(pixelI);
- return nTP;
+ return nTP;
}
float PerformanceUtils::NrTrueNegatives(IplImage* image, IplImage* ground_truth, bool debug)
{
float nTN = 0.0;
- unsigned char *pixelGT = (unsigned char *)malloc(1*sizeof(unsigned char));
- unsigned char *pixelI = (unsigned char *)malloc(1*sizeof(unsigned char));
+ unsigned char *pixelGT = (unsigned char *)malloc(1 * sizeof(unsigned char));
+ unsigned char *pixelI = (unsigned char *)malloc(1 * sizeof(unsigned char));
IplImage *TNimage = 0;
- if(debug)
+ if (debug)
{
- TNimage = cvCreateImage(cvSize(image->width,image->height),image->depth,image->nChannels);
- cvFillImage(TNimage, 0.0);
+ TNimage = cvCreateImage(cvSize(image->width, image->height), image->depth, image->nChannels);
+ cvSetZero(TNimage);
}
PixelUtils p;
- for(int y = 0; y < image->height; y++)
+ for (int y = 0; y < image->height; y++)
{
- for(int x = 0; x < image->width; x++)
+ for (int x = 0; x < image->width; x++)
{
- p.GetGrayPixel(ground_truth,x,y,pixelGT);
- p.GetGrayPixel(image,x,y,pixelI);
+ p.GetGrayPixel(ground_truth, x, y, pixelGT);
+ p.GetGrayPixel(image, x, y, pixelI);
- if((pixelGT[0] == 0) && (pixelI[0] == 0.0))
+ if ((pixelGT[0] == 0) && (pixelI[0] == 0.0))
{
*pixelI = 255;
- if(debug)
- p.PutGrayPixel(TNimage,x,y,*pixelI);
+ if (debug)
+ p.PutGrayPixel(TNimage, x, y, *pixelI);
nTN++;
- }
+ }
}
}
- if(debug)
+ if (debug)
{
cvNamedWindow("TNImage", 0);
cvShowImage("TNImage", TNimage);
@@ -156,41 +157,41 @@ float PerformanceUtils::NrTrueNegatives(IplImage* image, IplImage* ground_truth,
return nTN;
}
-float PerformanceUtils::NrFalsePositives(IplImage *image, IplImage *ground_truth,bool debug)
+float PerformanceUtils::NrFalsePositives(IplImage *image, IplImage *ground_truth, bool debug)
{
float nFP = 0.0;
- unsigned char *pixelGT = (unsigned char*) malloc(1*sizeof(unsigned char));
- unsigned char *pixelI = (unsigned char*) malloc(1*sizeof(unsigned char));
+ unsigned char *pixelGT = (unsigned char*)malloc(1 * sizeof(unsigned char));
+ unsigned char *pixelI = (unsigned char*)malloc(1 * sizeof(unsigned char));
IplImage *FPimage = 0;
- if(debug)
+ if (debug)
{
- FPimage = cvCreateImage(cvSize(image->width,image->height),image->depth,image->nChannels);
- cvFillImage(FPimage, 0.0);
+ FPimage = cvCreateImage(cvSize(image->width, image->height), image->depth, image->nChannels);
+ cvSetZero(FPimage);
}
PixelUtils p;
- for(int y = 0; y < image->height; y++)
+ for (int y = 0; y < image->height; y++)
{
- for(int x = 0; x < image->width; x++)
+ for (int x = 0; x < image->width; x++)
{
- p.GetGrayPixel(ground_truth,x,y,pixelGT);
- p.GetGrayPixel(image,x,y,pixelI);
+ p.GetGrayPixel(ground_truth, x, y, pixelGT);
+ p.GetGrayPixel(image, x, y, pixelI);
- if((pixelGT[0] == 0) && (pixelI[0] != 0))
+ if ((pixelGT[0] == 0) && (pixelI[0] != 0))
{
- if(debug)
- p.PutGrayPixel(FPimage,x,y,*pixelI);
+ if (debug)
+ p.PutGrayPixel(FPimage, x, y, *pixelI);
nFP++;
}
}
}
- if(debug)
+ if (debug)
{
cvNamedWindow("FPImage", 0);
cvShowImage("FPImage", FPimage);
@@ -203,44 +204,44 @@ float PerformanceUtils::NrFalsePositives(IplImage *image, IplImage *ground_truth
free(pixelGT);
free(pixelI);
- return nFP;
+ return nFP;
}
float PerformanceUtils::NrFalseNegatives(IplImage * image, IplImage *ground_truth, bool debug)
{
float nFN = 0.0;
- unsigned char *pixelGT = (unsigned char*) malloc(1*sizeof(unsigned char));
- unsigned char *pixelI = (unsigned char*) malloc(1*sizeof(unsigned char));
+ unsigned char *pixelGT = (unsigned char*)malloc(1 * sizeof(unsigned char));
+ unsigned char *pixelI = (unsigned char*)malloc(1 * sizeof(unsigned char));
IplImage *FNimage = 0;
- if(debug)
+ if (debug)
{
- FNimage = cvCreateImage(cvSize(image->width,image->height),image->depth,image->nChannels);
- cvFillImage(FNimage, 0.0);
+ FNimage = cvCreateImage(cvSize(image->width, image->height), image->depth, image->nChannels);
+ cvSetZero(FNimage);
}
PixelUtils p;
- for(int y = 0; y < image->height; y++)
+ for (int y = 0; y < image->height; y++)
{
- for(int x = 0; x < image->width; x++)
+ for (int x = 0; x < image->width; x++)
{
- p.GetGrayPixel(ground_truth,x,y,pixelGT);
- p.GetGrayPixel(image,x,y,pixelI);
+ p.GetGrayPixel(ground_truth, x, y, pixelGT);
+ p.GetGrayPixel(image, x, y, pixelI);
- if((pixelGT[0] != 0) && (pixelI[0] == 0))
+ if ((pixelGT[0] != 0) && (pixelI[0] == 0))
{
- if(debug)
- p.PutGrayPixel(FNimage,x,y,*pixelGT);
+ if (debug)
+ p.PutGrayPixel(FNimage, x, y, *pixelGT);
nFN++;
}
}
}
- if(debug)
+ if (debug)
{
cvNamedWindow("FNImage", 0);
cvShowImage("FNImage", FNimage);
@@ -253,19 +254,19 @@ float PerformanceUtils::NrFalseNegatives(IplImage * image, IplImage *ground_trut
free(pixelGT);
free(pixelI);
- return nFN;
+ return nFN;
}
float PerformanceUtils::SimilarityMeasure(IplImage *image, IplImage *ground_truth, bool debug)
{
- cv::Mat img_input(image,true);
- cv::Mat img_ref(ground_truth,true);
+ cv::Mat img_input = cv::cvarrToMat(image, true);
+ cv::Mat img_ref = cv::cvarrToMat(ground_truth, true);
int rn = cv::countNonZero(img_ref);
cv::Mat i;
cv::Mat u;
- if(rn > 0)
+ if (rn > 0)
{
i = img_input & img_ref;
u = img_input | img_ref;
@@ -278,16 +279,16 @@ float PerformanceUtils::SimilarityMeasure(IplImage *image, IplImage *ground_trut
int in = cv::countNonZero(i);
int un = cv::countNonZero(u);
-
+
double s = (((double)in) / ((double)un));
-
- if(debug)
+
+ if (debug)
{
cv::imshow("A^B", i);
cv::imshow("AvB", u);
//std::cout << "Similarity Measure: " << s << std::endl;
-
+
//<< " press ENTER to continue" << std::endl;
//cv::waitKey(0);
}
@@ -295,45 +296,45 @@ float PerformanceUtils::SimilarityMeasure(IplImage *image, IplImage *ground_trut
return s;
}
-void PerformanceUtils::ImageROC(IplImage *image, IplImage* ground_truth, bool saveResults, char* filename)
+void PerformanceUtils::ImageROC(IplImage *image, IplImage* ground_truth, bool saveResults, std::string filename)
{
- unsigned char *pixelGT = (unsigned char*) malloc(1*sizeof(unsigned char));
- unsigned char *pixelI = (unsigned char*) malloc(1*sizeof(unsigned char));
+ unsigned char *pixelGT = (unsigned char*)malloc(1 * sizeof(unsigned char));
+ unsigned char *pixelI = (unsigned char*)malloc(1 * sizeof(unsigned char));
- IplImage *ROCimage = cvCreateImage(cvSize(image->width,image->height),image->depth,image->nChannels);
- cvFillImage(ROCimage, 0.0);
+ IplImage *ROCimage = cvCreateImage(cvSize(image->width, image->height), image->depth, image->nChannels);
+ cvSetZero(ROCimage);
PixelUtils p;
- for(int y = 0; y < image->height; y++)
+ for (int y = 0; y < image->height; y++)
{
- for(int x = 0; x < image->width; x++)
+ for (int x = 0; x < image->width; x++)
{
- p.GetGrayPixel(ground_truth,x,y,pixelGT);
- p.GetGrayPixel(image,x,y,pixelI);
+ p.GetGrayPixel(ground_truth, x, y, pixelGT);
+ p.GetGrayPixel(image, x, y, pixelI);
- if((pixelGT[0] != 0) && (pixelI[0] != 0)) // TP
+ if ((pixelGT[0] != 0) && (pixelI[0] != 0)) // TP
{
*pixelI = 30;
- p.PutGrayPixel(ROCimage,x,y,*pixelI);
+ p.PutGrayPixel(ROCimage, x, y, *pixelI);
}
- if((pixelGT[0] == 0) && (pixelI[0] == 0.0)) // TN
+ if ((pixelGT[0] == 0) && (pixelI[0] == 0.0)) // TN
{
*pixelI = 0;
- p.PutGrayPixel(ROCimage,x,y,*pixelI);
- }
+ p.PutGrayPixel(ROCimage, x, y, *pixelI);
+ }
- if((pixelGT[0] == 0) && (pixelI[0] != 0)) // FP
+ if ((pixelGT[0] == 0) && (pixelI[0] != 0)) // FP
{
*pixelI = 255;
- p.PutGrayPixel(ROCimage,x,y,*pixelI);
+ p.PutGrayPixel(ROCimage, x, y, *pixelI);
}
- if((pixelGT[0] != 0) && (pixelI[0] == 0)) // FN
+ if ((pixelGT[0] != 0) && (pixelI[0] == 0)) // FN
{
*pixelI = 100;
- p.PutGrayPixel(ROCimage,x,y,*pixelI);
+ p.PutGrayPixel(ROCimage, x, y, *pixelI);
}
}
}
@@ -341,10 +342,10 @@ void PerformanceUtils::ImageROC(IplImage *image, IplImage* ground_truth, bool sa
cvNamedWindow("ROC image", 0);
cvShowImage("ROC image", ROCimage);
- if(saveResults)
+ if (saveResults)
{
- unsigned char *pixelOI = (unsigned char*) malloc(1*sizeof(unsigned char));
- unsigned char *pixelROC = (unsigned char*) malloc(1*sizeof(unsigned char));
+ unsigned char *pixelOI = (unsigned char*)malloc(1 * sizeof(unsigned char));
+ unsigned char *pixelROC = (unsigned char*)malloc(1 * sizeof(unsigned char));
float** freq;
float nTP = 0.0;
@@ -352,45 +353,45 @@ void PerformanceUtils::ImageROC(IplImage *image, IplImage* ground_truth, bool sa
float nFP = 0.0;
float nFN = 0.0;
- freq = (float**) malloc(256*(sizeof(float*)));
- for(int i = 0; i < 256; i++)
- freq[i] = (float*) malloc(7 * (sizeof(float)));
+ freq = (float**)malloc(256 * (sizeof(float*)));
+ for (int i = 0; i < 256; i++)
+ freq[i] = (float*)malloc(7 * (sizeof(float)));
- for(int i = 0; i < 256; i++)
- for(int j = 0; j < 6; j++)
+ for (int i = 0; i < 256; i++)
+ for (int j = 0; j < 6; j++)
freq[i][j] = 0.0;
- for(int y = 0; y < image->height; y++)
+ for (int y = 0; y < image->height; y++)
{
- for(int x = 0; x < image->width; x++)
+ for (int x = 0; x < image->width; x++)
{
- for(int i = 0; i < 256; i++)
+ for (int i = 0; i < 256; i++)
{
- p.GetGrayPixel(image,x,y,pixelOI);
- p.GetGrayPixel(ROCimage,x,y,pixelROC);
+ p.GetGrayPixel(image, x, y, pixelOI);
+ p.GetGrayPixel(ROCimage, x, y, pixelROC);
- if((pixelOI[0] == i) && (pixelROC[0] == 30.0)) // TP
+ if ((pixelOI[0] == i) && (pixelROC[0] == 30.0)) // TP
{
nTP++;
freq[i][0] = nTP;
break;
}
- if((pixelOI[0] == i) && (pixelROC[0] == 0.0)) // TN
+ if ((pixelOI[0] == i) && (pixelROC[0] == 0.0)) // TN
{
nTN++;
freq[i][1] = nTN;
break;
}
- if((pixelOI[0] == i) && (pixelROC[0] == 255.0)) // FP
+ if ((pixelOI[0] == i) && (pixelROC[0] == 255.0)) // FP
{
nFP++;
freq[i][2] = nFP;
break;
}
- if((pixelOI[0] == i) && (pixelROC[0] == 100)) // FN
+ if ((pixelOI[0] == i) && (pixelROC[0] == 100)) // FN
{
nFN++;
freq[i][3] = nFN;
@@ -409,17 +410,17 @@ void PerformanceUtils::ImageROC(IplImage *image, IplImage* ground_truth, bool sa
std::ofstream f(filename);
- if(!f.is_open())
+ if (!f.is_open())
std::cout << "Failed to open file " << filename << " for writing!" << std::endl;
else
{
f << " I TP TN FP FN FPR FNR DR \n" << std::endl;
-
- for(int i = 0; i < 256; i++)
+
+ for (int i = 0; i < 256; i++)
{
//printf("%4d - TP:%5.0f, TN:%5.0f, FP:%5.0f, FN:%5.0f,", i, freq[i][0], freq[i][1], freq[i][2], freq[i][3]);
- if((freq[i][3] + freq[i][0] != 0.0) && (freq[i][2] + freq[i][1] != 0.0))
+ if ((freq[i][3] + freq[i][0] != 0.0) && (freq[i][2] + freq[i][1] != 0.0))
{
freq[i][4] = freq[i][3] / (freq[i][3] + freq[i][0]); // FNR = FN / (TP + FN);
freq[i][5] = freq[i][2] / (freq[i][2] + freq[i][1]); // FPR = FP / (FP + TN);
@@ -429,12 +430,12 @@ void PerformanceUtils::ImageROC(IplImage *image, IplImage* ground_truth, bool sa
////fprintf(f," %4d %1.6f %1.6f\n",i,freq[i][5],freq[i][4]);
////fprintf(f," %1.6f %1.6f\n",freq[i][5],freq[i][4]);
char line[255];
- sprintf(line,"%3d %6.0f %6.0f %6.0f %6.0f %1.6f %1.6f %1.6f\n",
+ sprintf(line, "%3d %6.0f %6.0f %6.0f %6.0f %1.6f %1.6f %1.6f\n",
i, freq[i][0], freq[i][1], freq[i][2], freq[i][3], freq[i][5], freq[i][4], freq[i][6]);
f << line;
}
//else
- //printf("\n");
+ //printf("\n");
}
std::cout << "Results saved in " << filename << std::endl;
@@ -454,36 +455,36 @@ void PerformanceUtils::ImageROC(IplImage *image, IplImage* ground_truth, bool sa
free(pixelI);
}
-void PerformanceUtils::PerformanceEvaluation(IplImage *image, IplImage *ground_truth, bool saveResults, char* filename, bool debug)
+void PerformanceUtils::PerformanceEvaluation(IplImage *image, IplImage *ground_truth, bool saveResults, std::string filename, bool debug)
{
float N = 0;
N = NrPixels(image);
float U = 0;
U = NrAllDetectedPixNotNULL(image, ground_truth);
-
+
float TP = 0;
TP = NrTruePositives(image, ground_truth, debug);
-
+
float TN = 0;
TN = NrTrueNegatives(image, ground_truth, debug);
-
+
float FP = 0;
FP = NrFalsePositives(image, ground_truth, debug);
-
+
float FN = 0;
FN = NrFalseNegatives(image, ground_truth, debug);
-
+
float DetectionRate = TP / (TP + FN);
float Precision = TP / (TP + FP);
float Fmeasure = (2 * DetectionRate * Precision) / (DetectionRate + Precision);
float Accuracy = (TN + TP) / N;
float FalseNegativeRate = FN / (TP + FN);
-
+
float FalsePositiveRate = FP / (FP + TN);
float TruePositiveRate = TP / (TP + FN);
-
+
float SM = 0;
SM = SimilarityMeasure(image, ground_truth, debug);
@@ -506,11 +507,11 @@ void PerformanceUtils::PerformanceEvaluation(IplImage *image, IplImage *ground_t
std::string results = sstm.str();
std::cout << results;
- if(saveResults)
+ if (saveResults)
{
std::ofstream f(filename);
- if(!f.is_open())
+ if (!f.is_open())
std::cout << "Failed to open file " << filename << " for writing!" << std::endl;
else
{
diff --git a/package_bgs/tb/PerformanceUtils.h b/package_analysis/PerformanceUtils.h
similarity index 82%
rename from package_bgs/tb/PerformanceUtils.h
rename to package_analysis/PerformanceUtils.h
index 9257098..4be392f 100644
--- a/package_bgs/tb/PerformanceUtils.h
+++ b/package_analysis/PerformanceUtils.h
@@ -15,23 +15,11 @@ You should have received a copy of the GNU General Public License
along with BGSLibrary. If not, see .
*/
#pragma once
-/*
-Code provided by Thierry BOUWMANS
-
-Maitre de Conférences
-Laboratoire MIA
-Université de La Rochelle
-17000 La Rochelle
-France
-tbouwman@univ-lr.fr
-http://sites.google.com/site/thierrybouwmans/
-*/
#include
#include
#include
-
#include "PixelUtils.h"
class PerformanceUtils
@@ -48,7 +36,7 @@ class PerformanceUtils
float NrFalseNegatives(IplImage *image, IplImage *ground_truth, bool debug = false);
float SimilarityMeasure(IplImage *image, IplImage *ground_truth, bool debug = false);
- void ImageROC(IplImage *image, IplImage* ground_truth, bool saveResults = false, char* filename = "");
- void PerformanceEvaluation(IplImage *image, IplImage *ground_truth, bool saveResults = false, char* filename = "", bool debug = false);
+ void ImageROC(IplImage *image, IplImage* ground_truth, bool saveResults = false, std::string filename = "");
+ void PerformanceEvaluation(IplImage *image, IplImage *ground_truth, bool saveResults = false, std::string filename = "", bool debug = false);
};
diff --git a/package_analysis/PixelUtils.cpp b/package_analysis/PixelUtils.cpp
new file mode 100644
index 0000000..adce122
--- /dev/null
+++ b/package_analysis/PixelUtils.cpp
@@ -0,0 +1,351 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+#include "PixelUtils.h"
+
+PixelUtils::PixelUtils(void) {}
+PixelUtils::~PixelUtils(void) {}
+
+void PixelUtils::ColorConversion(IplImage* RGBImage, IplImage* ConvertedImage, int color_space)
+{
+ // Space Color RGB - Nothing to do!
+ if (color_space == 1)
+ cvCopy(RGBImage, ConvertedImage);
+
+ // Space Color Ohta
+ if (color_space == 2)
+ cvttoOTHA(RGBImage, ConvertedImage);
+
+ // Space Color HSV - V Intensity - (H,S) Chromaticity
+ if (color_space == 3)
+ cvCvtColor(RGBImage, ConvertedImage, CV_BGR2HSV);
+
+ // Space Color YCrCb - Y Intensity - (Cr,Cb) Chromaticity
+ if (color_space == 4)
+ cvCvtColor(RGBImage, ConvertedImage, CV_BGR2YCrCb);
+}
+
+void PixelUtils::cvttoOTHA(IplImage* RGBImage, IplImage* OthaImage)
+{
+ float* OhtaPixel = (float*)malloc(3 * (sizeof(float)));
+ float* RGBPixel = (float*)malloc(3 * (sizeof(float)));
+
+ for (int i = 0; i < RGBImage->width; i++)
+ {
+ for (int j = 0; j < RGBImage->height; j++)
+ {
+ GetPixel(RGBImage, i, j, RGBPixel);
+
+ // I1 = (R + G + B) / 3
+ *OhtaPixel = (*(RGBPixel)+(*(RGBPixel + 1)) + (*(RGBPixel + 2))) / 3.0;
+
+ // I2 = (R - B) / 2
+ *(OhtaPixel + 1) = (*RGBPixel - (*(RGBPixel + 2))) / 2.0;
+
+ // I3 = (2G - R - B) / 4
+ *(OhtaPixel + 2) = (2 * (*(RGBPixel + 1)) - (*RGBPixel) - (*(RGBPixel + 2))) / 4.0;
+
+ PutPixel(OthaImage, i, j, OhtaPixel);
+ }
+ }
+
+ free(OhtaPixel);
+ free(RGBPixel);
+}
+
+void PixelUtils::PostProcessing(IplImage *InputImage)
+{
+ IplImage *ResultImage = cvCreateImage(cvSize(InputImage->width, InputImage->height), IPL_DEPTH_32F, 3);
+
+ cvErode(InputImage, ResultImage, NULL, 1);
+ cvDilate(ResultImage, InputImage, NULL, 0);
+
+ cvReleaseImage(&ResultImage);
+}
+
+void PixelUtils::GetPixel(IplImage *image, int m, int n, unsigned char *pixelcourant)
+{
+ for (int k = 0; k < 3; k++)
+ pixelcourant[k] = ((unsigned char*)(image->imageData + image->widthStep*n))[m * 3 + k];
+}
+
+void PixelUtils::GetGrayPixel(IplImage *image, int m, int n, unsigned char *pixelcourant)
+{
+ *pixelcourant = ((unsigned char*)(image->imageData + image->widthStep*n))[m];
+}
+
+void PixelUtils::PutPixel(IplImage *image, int p, int q, unsigned char *pixelcourant)
+{
+ for (int r = 0; r < 3; r++)
+ ((unsigned char*)(image->imageData + image->widthStep*q))[p * 3 + r] = pixelcourant[r];
+}
+
+void PixelUtils::PutGrayPixel(IplImage *image, int p, int q, unsigned char pixelcourant)
+{
+ ((unsigned char*)(image->imageData + image->widthStep*q))[p] = pixelcourant;
+}
+
+void PixelUtils::GetPixel(IplImage *image, int m, int n, float *pixelcourant)
+{
+ for (int k = 0; k < 3; k++)
+ pixelcourant[k] = ((float*)(image->imageData + image->widthStep*n))[m * 3 + k];
+}
+
+void PixelUtils::GetGrayPixel(IplImage *image, int m, int n, float *pixelcourant)
+{
+ *pixelcourant = ((float*)(image->imageData + image->widthStep*n))[m];
+}
+
+void PixelUtils::PutPixel(IplImage *image, int p, int q, float *pixelcourant)
+{
+ for (int r = 0; r < 3; r++)
+ ((float*)(image->imageData + image->widthStep*q))[p * 3 + r] = pixelcourant[r];
+}
+
+void PixelUtils::PutGrayPixel(IplImage *image, int p, int q, float pixelcourant)
+{
+ ((float*)(image->imageData + image->widthStep*q))[p] = pixelcourant;
+}
+
+void PixelUtils::getNeighberhoodGrayPixel(IplImage* InputImage, int x, int y, float* neighberPixel)
+{
+ int i, j, k;
+
+ float* pixelCourant = (float*)malloc(1 * (sizeof(float)));
+
+ //le calcul de voisinage pour les 4 coins;
+ /* 1.*/
+ if (x == 0 && y == 0)
+ {
+ k = 0;
+ for (i = x; i < x + 2; i++)
+ for (j = y; j < y + 2; j++)
+ {
+ GetGrayPixel(InputImage, i, j, pixelCourant);
+ *(neighberPixel + k) = *pixelCourant;
+ k++;
+ }
+ }
+
+ /* 2.*/
+ if (x == 0 && y == InputImage->width)
+ {
+ k = 0;
+ for (i = x; i < x + 2; i++)
+ for (j = y - 1; j < y + 1; j++)
+ {
+ GetGrayPixel(InputImage, i, j, pixelCourant);
+ *(neighberPixel + k) = *pixelCourant;
+ k++;
+ }
+ }
+
+ /* 3.*/
+ if (x == InputImage->height && y == 0)
+ {
+ k = 0;
+ for (i = x - 1; i < x + 1; i++)
+ for (j = y; j < y + 2; j++)
+ {
+ GetGrayPixel(InputImage, i, j, pixelCourant);
+ *(neighberPixel + k) = *pixelCourant;
+ k++;
+ }
+ }
+
+ /* 4.*/
+ if (x == InputImage->height && y == InputImage->width)
+ {
+ k = 0;
+ for (i = x - 1; i < x + 1; i++)
+ for (j = y - 1; j < y + 1; j++)
+ {
+ GetGrayPixel(InputImage, i, j, pixelCourant);
+ *(neighberPixel + k) = *pixelCourant;
+ k++;
+ }
+ }
+
+ // Voisinage de la premiere ligne : L(0)
+ if (x == 0 && (y != 0 && y != InputImage->width))
+ {
+ k = 0;
+ for (i = x + 1; i >= x; i--)
+ for (j = y - 1; j < y + 2; j++)
+ {
+ GetGrayPixel(InputImage, i, j, pixelCourant);
+ *(neighberPixel + k) = *pixelCourant;
+ k++;
+ }
+ }
+
+ // Voisinage de la dernière colonne : C(w)
+ if ((x != 0 && x != InputImage->height) && y == InputImage->width)
+ {
+ k = 0;
+ for (i = x + 1; i > x - 2; i--)
+ for (j = y - 1; j < y + 1; j++)
+ {
+ GetGrayPixel(InputImage, i, j, pixelCourant);
+ *(neighberPixel + k) = *pixelCourant;
+ k++;
+ }
+ }
+
+ // Voisinage de la dernière ligne : L(h)
+ if (x == InputImage->height && (y != 0 && y != InputImage->width))
+ {
+ k = 0;
+ for (i = x; i > x - 2; i--)
+ for (j = y - 1; j < y + 2; j++)
+ {
+ GetGrayPixel(InputImage, i, j, pixelCourant);
+ *(neighberPixel + k) = *pixelCourant;
+ k++;
+ }
+ }
+
+ // Voisinage de la premiere colonne : C(0)
+ if ((x != 0 && x != InputImage->height) && y == 0)
+ {
+ k = 0;
+ for (i = x - 1; i < x + 2; i++)
+ for (j = y; j < y + 2; j++)
+ {
+ GetGrayPixel(InputImage, i, j, pixelCourant);
+ *(neighberPixel + k) = *pixelCourant;
+ k++;
+ }
+ }
+
+ //le calcul du voisinage pour le reste des elementes d'image
+ if ((x != 0 && x != InputImage->height) && (y != 0 && y != InputImage->width))
+ {
+ k = 0;
+ for (i = x + 1; i > x - 2; i--)
+ for (j = y - 1; j < y + 2; j++)
+ {
+ GetGrayPixel(InputImage, i, j, pixelCourant);
+ *(neighberPixel + k) = *pixelCourant;
+ k++;
+ }
+ }
+
+ free(pixelCourant);
+}
+
+void PixelUtils::ForegroundMinimum(IplImage *Foreground, float *Minimum, int n)
+{
+ int i, j, k;
+ float *pixelcourant;
+
+ pixelcourant = (float *)malloc(n * sizeof(float));
+
+ for (k = 0; k < n; k++)
+ *(Minimum + k) = 255;
+
+ for (i = 0; i < Foreground->width; i++)
+ for (j = 0; j < Foreground->height; j++)
+ {
+ if (n == 3)
+ {
+ GetPixel(Foreground, i, j, pixelcourant);
+
+ for (k = 0; k < n; k++)
+ if (*(pixelcourant + k) < *(Minimum + k))
+ *(Minimum + k) = *(pixelcourant + k);
+ }
+
+ if (n == 1)
+ {
+ GetGrayPixel(Foreground, i, j, pixelcourant);
+
+ if (*pixelcourant < *Minimum)
+ *Minimum = *pixelcourant;
+ }
+ }
+
+ free(pixelcourant);
+}
+
+void PixelUtils::ForegroundMaximum(IplImage *Foreground, float *Maximum, int n)
+{
+ int i, j, k;
+ float *pixelcourant;
+
+ pixelcourant = (float *)malloc(n * sizeof(float));
+
+ for (k = 0; k < n; k++)
+ *(Maximum + k) = 0;
+
+ for (i = 0; i < Foreground->width; i++)
+ for (j = 0; j < Foreground->height; j++)
+ {
+ if (n == 3)
+ {
+ GetPixel(Foreground, i, j, pixelcourant);
+
+ for (k = 0; k < n; k++)
+ if (*(pixelcourant + k) > *(Maximum + k))
+ *(Maximum + k) = *(pixelcourant + k);
+ }
+
+ if (n == 1)
+ {
+ GetGrayPixel(Foreground, i, j, pixelcourant);
+
+ if (*pixelcourant > *Maximum)
+ *Maximum = *pixelcourant;
+ }
+ }
+
+ free(pixelcourant);
+}
+
+void PixelUtils::ComplementaryAlphaImageCreation(IplImage *AlphaImage, IplImage *ComplementaryAlphaImage, int n)
+{
+ int i, j, k;
+ float *pixelcourant, *pixelcourant1;
+
+ pixelcourant = (float *)malloc(n * sizeof(float));
+ pixelcourant1 = (float *)malloc(n * sizeof(float));
+
+ for (i = 0; i < AlphaImage->width; i++)
+ for (j = 0; j < AlphaImage->height; j++)
+ {
+ if (n == 1)
+ {
+ GetGrayPixel(AlphaImage, i, j, pixelcourant);
+ *pixelcourant1 = 1 - *(pixelcourant);
+ PutGrayPixel(ComplementaryAlphaImage, i, j, *pixelcourant1);
+ }
+
+ if (n == 3)
+ {
+ GetPixel(AlphaImage, i, j, pixelcourant);
+ for (k = 0; k < 3; k++)
+ {
+ *pixelcourant1 = 1.0 - *(pixelcourant);
+ *(pixelcourant1 + 1) = 1.0 - *(pixelcourant + 1);
+ *(pixelcourant1 + 2) = 1.0 - *(pixelcourant + 2);
+ }
+ PutPixel(ComplementaryAlphaImage, i, j, pixelcourant1);
+ }
+ }
+
+ free(pixelcourant);
+ free(pixelcourant1);
+}
diff --git a/package_bgs/tb/PixelUtils.h b/package_analysis/PixelUtils.h
similarity index 90%
rename from package_bgs/tb/PixelUtils.h
rename to package_analysis/PixelUtils.h
index a2d3a4a..0e35c40 100644
--- a/package_bgs/tb/PixelUtils.h
+++ b/package_analysis/PixelUtils.h
@@ -15,22 +15,10 @@ You should have received a copy of the GNU General Public License
along with BGSLibrary. If not, see .
*/
#pragma once
-/*
-Code provided by Thierry BOUWMANS
-
-Maitre de Conférences
-Laboratoire MIA
-Université de La Rochelle
-17000 La Rochelle
-France
-tbouwman@univ-lr.fr
-http://sites.google.com/site/thierrybouwmans/
-*/
#include
#include
-
class PixelUtils
{
public:
@@ -39,9 +27,9 @@ class PixelUtils
void ColorConversion(IplImage* RGBImage, IplImage* ConvertedImage, int color_space);
void cvttoOTHA(IplImage* RGBImage, IplImage* OthaImage);
-
+
void PostProcessing(IplImage *InputImage);
-
+
void GetPixel(IplImage *image, int m, int n, unsigned char *pixelcourant);
void GetGrayPixel(IplImage *image, int m, int n, unsigned char *pixelcourant);
@@ -58,4 +46,4 @@ class PixelUtils
void ForegroundMaximum(IplImage *Foreground, float *Maximum, int n);
void ForegroundMinimum(IplImage *Foreground, float *Minimum, int n);
void ComplementaryAlphaImageCreation(IplImage *AlphaImage, IplImage *ComplementaryAlphaImage, int n);
-};
\ No newline at end of file
+};
diff --git a/package_bgs/AdaptiveBackgroundLearning.cpp b/package_bgs/AdaptiveBackgroundLearning.cpp
index b111e65..d2cb8a0 100644
--- a/package_bgs/AdaptiveBackgroundLearning.cpp
+++ b/package_bgs/AdaptiveBackgroundLearning.cpp
@@ -16,10 +16,14 @@ along with BGSLibrary. If not, see .
*/
#include "AdaptiveBackgroundLearning.h"
-AdaptiveBackgroundLearning::AdaptiveBackgroundLearning() : firstTime(true), alpha(0.05), limit(-1), counter(0), minVal(0.0), maxVal(1.0),
- enableThreshold(true), threshold(15), showForeground(true), showBackground(true)
+using namespace bgslibrary::algorithms;
+
+AdaptiveBackgroundLearning::AdaptiveBackgroundLearning() :
+ alpha(0.05), limit(-1), counter(0), minVal(0.0), maxVal(1.0),
+ enableThreshold(true), threshold(15)
{
std::cout << "AdaptiveBackgroundLearning()" << std::endl;
+ setup("./config/AdaptiveBackgroundLearning.xml");
}
AdaptiveBackgroundLearning::~AdaptiveBackgroundLearning()
@@ -29,52 +33,48 @@ AdaptiveBackgroundLearning::~AdaptiveBackgroundLearning()
void AdaptiveBackgroundLearning::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
{
- if(img_input.empty())
- return;
-
- loadConfig();
-
- if(firstTime)
- saveConfig();
+ init(img_input, img_output, img_bgmodel);
- if(img_background.empty())
+ if (img_background.empty())
img_input.copyTo(img_background);
cv::Mat img_input_f(img_input.size(), CV_32F);
- img_input.convertTo(img_input_f, CV_32F, 1./255.);
+ img_input.convertTo(img_input_f, CV_32F, 1. / 255.);
cv::Mat img_background_f(img_background.size(), CV_32F);
- img_background.convertTo(img_background_f, CV_32F, 1./255.);
+ img_background.convertTo(img_background_f, CV_32F, 1. / 255.);
cv::Mat img_diff_f(img_input.size(), CV_32F);
cv::absdiff(img_input_f, img_background_f, img_diff_f);
- if((limit > 0 && limit < counter) || limit == -1)
+ if ((limit > 0 && limit < counter) || limit == -1)
{
- img_background_f = alpha*img_input_f + (1-alpha)*img_background_f;
-
+ img_background_f = alpha*img_input_f + (1 - alpha)*img_background_f;
+
cv::Mat img_new_background(img_input.size(), CV_8U);
- img_background_f.convertTo(img_new_background, CV_8U, 255.0/(maxVal - minVal), -minVal);
+ img_background_f.convertTo(img_new_background, CV_8U, 255.0 / (maxVal - minVal), -minVal);
img_new_background.copyTo(img_background);
- if(limit > 0 && limit < counter)
+ if (limit > 0 && limit < counter)
counter++;
}
-
- cv::Mat img_foreground(img_input.size(), CV_8U);
- img_diff_f.convertTo(img_foreground, CV_8U, 255.0/(maxVal - minVal), -minVal);
- if(img_foreground.channels() == 3)
+ //cv::Mat img_foreground(img_input.size(), CV_8U);
+ img_diff_f.convertTo(img_foreground, CV_8UC1, 255.0 / (maxVal - minVal), -minVal);
+
+ if (img_foreground.channels() == 3)
cv::cvtColor(img_foreground, img_foreground, CV_BGR2GRAY);
- if(enableThreshold)
+ if (enableThreshold)
cv::threshold(img_foreground, img_foreground, threshold, 255, cv::THRESH_BINARY);
-
- if(showForeground)
- cv::imshow("A-Learning FG", img_foreground);
- if(showBackground)
+#ifndef MEX_COMPILE_FLAG
+ if (showOutput)
+ {
+ cv::imshow("A-Learning FG", img_foreground);
cv::imshow("A-Learning BG", img_background);
+ }
+#endif
img_foreground.copyTo(img_output);
img_background.copyTo(img_bgmodel);
@@ -84,28 +84,26 @@ void AdaptiveBackgroundLearning::process(const cv::Mat &img_input, cv::Mat &img_
void AdaptiveBackgroundLearning::saveConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/AdaptiveBackgroundLearning.xml", 0, CV_STORAGE_WRITE);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), 0, CV_STORAGE_WRITE);
cvWriteReal(fs, "alpha", alpha);
cvWriteInt(fs, "limit", limit);
cvWriteInt(fs, "enableThreshold", enableThreshold);
cvWriteInt(fs, "threshold", threshold);
- cvWriteInt(fs, "showForeground", showForeground);
- cvWriteInt(fs, "showBackground", showBackground);
+ cvWriteInt(fs, "showOutput", showOutput);
cvReleaseFileStorage(&fs);
}
void AdaptiveBackgroundLearning::loadConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/AdaptiveBackgroundLearning.xml", 0, CV_STORAGE_READ);
-
- alpha = cvReadRealByName(fs, 0, "alpha", 0.05);
- limit = cvReadIntByName(fs, 0, "limit", -1);
- enableThreshold = cvReadIntByName(fs, 0, "enableThreshold", true);
- threshold = cvReadIntByName(fs, 0, "threshold", 15);
- showForeground = cvReadIntByName(fs, 0, "showForeground", true);
- showBackground = cvReadIntByName(fs, 0, "showBackground", true);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_READ);
+
+ alpha = cvReadRealByName(fs, nullptr, "alpha", 0.05);
+ limit = cvReadIntByName(fs, nullptr, "limit", -1);
+ enableThreshold = cvReadIntByName(fs, nullptr, "enableThreshold", true);
+ threshold = cvReadIntByName(fs, nullptr, "threshold", 15);
+ showOutput = cvReadIntByName(fs, nullptr, "showOutput", true);
cvReleaseFileStorage(&fs);
}
diff --git a/package_bgs/AdaptiveBackgroundLearning.h b/package_bgs/AdaptiveBackgroundLearning.h
index 4bbac54..3cfc686 100644
--- a/package_bgs/AdaptiveBackgroundLearning.h
+++ b/package_bgs/AdaptiveBackgroundLearning.h
@@ -16,35 +16,32 @@ along with BGSLibrary. If not, see .
*/
#pragma once
-#include
-#include
-
-
#include "IBGS.h"
-class AdaptiveBackgroundLearning : public IBGS
+namespace bgslibrary
{
-private:
- bool firstTime;
- cv::Mat img_background;
- double alpha;
- long limit;
- long counter;
- double minVal;
- double maxVal;
- bool enableThreshold;
- int threshold;
- bool showForeground;
- bool showBackground;
-
-public:
- AdaptiveBackgroundLearning();
- ~AdaptiveBackgroundLearning();
-
- void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
-
-private:
- void saveConfig();
- void loadConfig();
-};
-
+ namespace algorithms
+ {
+ class AdaptiveBackgroundLearning : public IBGS
+ {
+ private:
+ double alpha;
+ long limit;
+ long counter;
+ double minVal;
+ double maxVal;
+ bool enableThreshold;
+ int threshold;
+
+ public:
+ AdaptiveBackgroundLearning();
+ ~AdaptiveBackgroundLearning();
+
+ void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
+
+ private:
+ void saveConfig();
+ void loadConfig();
+ };
+ }
+}
diff --git a/package_bgs/AdaptiveSelectiveBackgroundLearning.cpp b/package_bgs/AdaptiveSelectiveBackgroundLearning.cpp
index cd3e7d3..2f6f9fe 100644
--- a/package_bgs/AdaptiveSelectiveBackgroundLearning.cpp
+++ b/package_bgs/AdaptiveSelectiveBackgroundLearning.cpp
@@ -16,11 +16,14 @@ along with BGSLibrary. If not, see .
*/
#include "AdaptiveSelectiveBackgroundLearning.h"
-AdaptiveSelectiveBackgroundLearning::AdaptiveSelectiveBackgroundLearning() : firstTime(true),
-alphaLearn(0.05), alphaDetection(0.05), learningFrames(-1), counter(0), minVal(0.0), maxVal(1.0),
-threshold(15), showOutput(true)
+using namespace bgslibrary::algorithms;
+
+AdaptiveSelectiveBackgroundLearning::AdaptiveSelectiveBackgroundLearning() :
+ alphaLearn(0.05), alphaDetection(0.05), learningFrames(-1), counter(0), minVal(0.0), maxVal(1.0),
+ threshold(15)
{
std::cout << "AdaptiveSelectiveBackgroundLearning()" << std::endl;
+ setup("./config/AdaptiveSelectiveBackgroundLearning.xml");
}
AdaptiveSelectiveBackgroundLearning::~AdaptiveSelectiveBackgroundLearning()
@@ -30,8 +33,7 @@ AdaptiveSelectiveBackgroundLearning::~AdaptiveSelectiveBackgroundLearning()
void AdaptiveSelectiveBackgroundLearning::process(const cv::Mat &img_input_, cv::Mat &img_output, cv::Mat &img_bgmodel)
{
- if(img_input_.empty())
- return;
+ init(img_input_, img_output, img_bgmodel);
cv::Mat img_input;
if (img_input_.channels() == 3)
@@ -39,24 +41,19 @@ void AdaptiveSelectiveBackgroundLearning::process(const cv::Mat &img_input_, cv:
else
img_input_.copyTo(img_input);
- loadConfig();
-
- if(firstTime)
- saveConfig();
-
- if(img_background.empty())
+ if (img_background.empty())
img_input.copyTo(img_background);
cv::Mat img_input_f(img_input.size(), CV_32F);
- img_input.convertTo(img_input_f, CV_32F, 1./255.);
+ img_input.convertTo(img_input_f, CV_32F, 1. / 255.);
cv::Mat img_background_f(img_background.size(), CV_32F);
- img_background.convertTo(img_background_f, CV_32F, 1./255.);
+ img_background.convertTo(img_background_f, CV_32F, 1. / 255.);
cv::Mat img_diff_f(img_input.size(), CV_32F);
cv::absdiff(img_input_f, img_background_f, img_diff_f);
- cv::Mat img_foreground(img_input.size(), CV_8U);
+ //cv::Mat img_foreground(img_input.size(), CV_8U);
img_diff_f.convertTo(img_foreground, CV_8U, 255.0 / (maxVal - minVal), -minVal);
cv::threshold(img_foreground, img_foreground, threshold, 255, cv::THRESH_BINARY);
@@ -88,15 +85,17 @@ void AdaptiveSelectiveBackgroundLearning::process(const cv::Mat &img_input_, cv:
}
}
- cv::Mat img_new_background(img_input.size(), CV_8U);
- img_background_f.convertTo(img_new_background, CV_8U, 255.0 / (maxVal - minVal), -minVal);
- img_new_background.copyTo(img_background);
-
- if(showOutput)
+ //cv::Mat img_new_background(img_input.size(), CV_8U);
+ img_background_f.convertTo(img_background, CV_8UC1, 255.0 / (maxVal - minVal), -minVal);
+ //img_new_background.copyTo(img_background);
+
+#ifndef MEX_COMPILE_FLAG
+ if (showOutput)
{
cv::imshow("AS-Learning FG", img_foreground);
cv::imshow("AS-Learning BG", img_background);
}
+#endif
img_foreground.copyTo(img_output);
img_background.copyTo(img_bgmodel);
@@ -106,7 +105,7 @@ void AdaptiveSelectiveBackgroundLearning::process(const cv::Mat &img_input_, cv:
void AdaptiveSelectiveBackgroundLearning::saveConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/AdaptiveSelectiveBackgroundLearning.xml", 0, CV_STORAGE_WRITE);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_WRITE);
cvWriteInt(fs, "learningFrames", learningFrames);
cvWriteReal(fs, "alphaLearn", alphaLearn);
@@ -119,13 +118,13 @@ void AdaptiveSelectiveBackgroundLearning::saveConfig()
void AdaptiveSelectiveBackgroundLearning::loadConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/AdaptiveSelectiveBackgroundLearning.xml", 0, CV_STORAGE_READ);
-
- learningFrames = cvReadIntByName(fs, 0, "learningFrames", 90);
- alphaLearn = cvReadRealByName(fs, 0, "alphaLearn", 0.05);
- alphaDetection = cvReadRealByName(fs, 0, "alphaDetection", 0.05);
- threshold = cvReadIntByName(fs, 0, "threshold", 25);
- showOutput = cvReadIntByName(fs, 0, "showOutput", true);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), 0, CV_STORAGE_READ);
+
+ learningFrames = cvReadIntByName(fs, nullptr, "learningFrames", 90);
+ alphaLearn = cvReadRealByName(fs, nullptr, "alphaLearn", 0.05);
+ alphaDetection = cvReadRealByName(fs, nullptr, "alphaDetection", 0.05);
+ threshold = cvReadIntByName(fs, nullptr, "threshold", 25);
+ showOutput = cvReadIntByName(fs, nullptr, "showOutput", true);
cvReleaseFileStorage(&fs);
}
diff --git a/package_bgs/AdaptiveSelectiveBackgroundLearning.h b/package_bgs/AdaptiveSelectiveBackgroundLearning.h
index 2276747..24da44c 100644
--- a/package_bgs/AdaptiveSelectiveBackgroundLearning.h
+++ b/package_bgs/AdaptiveSelectiveBackgroundLearning.h
@@ -16,34 +16,32 @@ along with BGSLibrary. If not, see .
*/
#pragma once
-#include
-#include
-
-
#include "IBGS.h"
-class AdaptiveSelectiveBackgroundLearning : public IBGS
+namespace bgslibrary
{
-private:
- bool firstTime;
- cv::Mat img_background;
- double alphaLearn;
- double alphaDetection;
- long learningFrames;
- long counter;
- double minVal;
- double maxVal;
- int threshold;
- bool showOutput;
-
-public:
- AdaptiveSelectiveBackgroundLearning();
- ~AdaptiveSelectiveBackgroundLearning();
-
- void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
-
-private:
- void saveConfig();
- void loadConfig();
-};
-
+ namespace algorithms
+ {
+ class AdaptiveSelectiveBackgroundLearning : public IBGS
+ {
+ private:
+ double alphaLearn;
+ double alphaDetection;
+ long learningFrames;
+ long counter;
+ double minVal;
+ double maxVal;
+ int threshold;
+
+ public:
+ AdaptiveSelectiveBackgroundLearning();
+ ~AdaptiveSelectiveBackgroundLearning();
+
+ void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
+
+ private:
+ void saveConfig();
+ void loadConfig();
+ };
+ }
+}
diff --git a/package_bgs/DPAdaptiveMedian.cpp b/package_bgs/DPAdaptiveMedian.cpp
new file mode 100644
index 0000000..0885580
--- /dev/null
+++ b/package_bgs/DPAdaptiveMedian.cpp
@@ -0,0 +1,110 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+#include "DPAdaptiveMedian.h"
+
+using namespace bgslibrary::algorithms;
+
+DPAdaptiveMedian::DPAdaptiveMedian() :
+ frameNumber(0), threshold(40), samplingRate(7), learningFrames(30)
+{
+ std::cout << "DPAdaptiveMedian()" << std::endl;
+ setup("./config/DPAdaptiveMedian.xml");
+}
+
+DPAdaptiveMedian::~DPAdaptiveMedian()
+{
+ std::cout << "~DPAdaptiveMedian()" << std::endl;
+}
+
+void DPAdaptiveMedian::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
+{
+ init(img_input, img_output, img_bgmodel);
+
+ frame = new IplImage(img_input);
+
+ if (firstTime)
+ frame_data.ReleaseMemory(false);
+ frame_data = frame;
+
+ if (firstTime)
+ {
+ int width = img_input.size().width;
+ int height = img_input.size().height;
+
+ lowThresholdMask = cvCreateImage(cvSize(width, height), IPL_DEPTH_8U, 1);
+ lowThresholdMask.Ptr()->origin = IPL_ORIGIN_BL;
+
+ highThresholdMask = cvCreateImage(cvSize(width, height), IPL_DEPTH_8U, 1);
+ highThresholdMask.Ptr()->origin = IPL_ORIGIN_BL;
+
+ params.SetFrameSize(width, height);
+ params.LowThreshold() = threshold;
+ params.HighThreshold() = 2 * params.LowThreshold(); // Note: high threshold is used by post-processing
+ params.SamplingRate() = samplingRate;
+ params.LearningFrames() = learningFrames;
+
+ bgs.Initalize(params);
+ bgs.InitModel(frame_data);
+ }
+
+ bgs.Subtract(frameNumber, frame_data, lowThresholdMask, highThresholdMask);
+ lowThresholdMask.Clear();
+ bgs.Update(frameNumber, frame_data, lowThresholdMask);
+
+ img_foreground = cv::cvarrToMat(highThresholdMask.Ptr());
+ //bitwise_not(img_foreground, img_foreground);
+ img_background = cv::cvarrToMat(bgs.Background()->Ptr());
+
+#ifndef MEX_COMPILE_FLAG
+ if (showOutput)
+ {
+ cv::imshow("Adaptive Median FG (McFarlane&Schofield)", img_foreground);
+ cv::imshow("Adaptive Median BG (McFarlane&Schofield)", img_background);
+ }
+#endif
+
+ img_foreground.copyTo(img_output);
+ img_background.copyTo(img_bgmodel);
+
+ delete frame;
+ firstTime = false;
+ frameNumber++;
+}
+
+void DPAdaptiveMedian::saveConfig()
+{
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_WRITE);
+
+ cvWriteInt(fs, "threshold", threshold);
+ cvWriteInt(fs, "samplingRate", samplingRate);
+ cvWriteInt(fs, "learningFrames", learningFrames);
+ cvWriteInt(fs, "showOutput", showOutput);
+
+ cvReleaseFileStorage(&fs);
+}
+
+void DPAdaptiveMedian::loadConfig()
+{
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_READ);
+
+ threshold = cvReadIntByName(fs, nullptr, "threshold", 40);
+ samplingRate = cvReadIntByName(fs, nullptr, "samplingRate", 7);
+ learningFrames = cvReadIntByName(fs, nullptr, "learningFrames", 30);
+ showOutput = cvReadIntByName(fs, nullptr, "showOutput", true);
+
+ cvReleaseFileStorage(&fs);
+}
diff --git a/package_bgs/DPAdaptiveMedian.h b/package_bgs/DPAdaptiveMedian.h
new file mode 100644
index 0000000..7d2b7fa
--- /dev/null
+++ b/package_bgs/DPAdaptiveMedian.h
@@ -0,0 +1,53 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+#pragma once
+
+#include "IBGS.h"
+#include "dp/AdaptiveMedianBGS.h"
+
+using namespace Algorithms::BackgroundSubtraction;
+
+namespace bgslibrary
+{
+ namespace algorithms
+ {
+ class DPAdaptiveMedian : public IBGS
+ {
+ private:
+ long frameNumber;
+ IplImage* frame;
+ RgbImage frame_data;
+ AdaptiveMedianParams params;
+ AdaptiveMedianBGS bgs;
+ BwImage lowThresholdMask;
+ BwImage highThresholdMask;
+ int threshold;
+ int samplingRate;
+ int learningFrames;
+
+ public:
+ DPAdaptiveMedian();
+ ~DPAdaptiveMedian();
+
+ void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
+
+ private:
+ void saveConfig();
+ void loadConfig();
+ };
+ }
+}
diff --git a/package_bgs/dp/DPEigenbackgroundBGS.cpp b/package_bgs/DPEigenbackground.cpp
similarity index 53%
rename from package_bgs/dp/DPEigenbackgroundBGS.cpp
rename to package_bgs/DPEigenbackground.cpp
index 630d9cc..75763ce 100644
--- a/package_bgs/dp/DPEigenbackgroundBGS.cpp
+++ b/package_bgs/DPEigenbackground.cpp
@@ -14,37 +14,35 @@ GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with BGSLibrary. If not, see .
*/
-#include "DPEigenbackgroundBGS.h"
+#include "DPEigenbackground.h"
-DPEigenbackgroundBGS::DPEigenbackgroundBGS() : firstTime(true), frameNumber(0), threshold(225), historySize(20), embeddedDim(10), showOutput(true)
+using namespace bgslibrary::algorithms;
+
+DPEigenbackground::DPEigenbackground() :
+ frameNumber(0), threshold(225), historySize(20), embeddedDim(10)
{
- std::cout << "DPEigenbackgroundBGS()" << std::endl;
+ std::cout << "DPEigenbackground()" << std::endl;
+ setup("./config/DPEigenbackground.xml");
}
-DPEigenbackgroundBGS::~DPEigenbackgroundBGS()
+DPEigenbackground::~DPEigenbackground()
{
- std::cout << "~DPEigenbackgroundBGS()" << std::endl;
+ std::cout << "~DPEigenbackground()" << std::endl;
}
-void DPEigenbackgroundBGS::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
+void DPEigenbackground::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
{
- if(img_input.empty())
- return;
-
- loadConfig();
-
- if(firstTime)
- saveConfig();
+ init(img_input, img_output, img_bgmodel);
frame = new IplImage(img_input);
-
- if(firstTime)
+
+ if (firstTime)
frame_data.ReleaseMemory(false);
frame_data = frame;
- if(firstTime)
+ if (firstTime)
{
- int width = img_input.size().width;
+ int width = img_input.size().width;
int height = img_input.size().height;
lowThresholdMask = cvCreateImage(cvSize(width, height), IPL_DEPTH_8U, 1);
@@ -55,7 +53,7 @@ void DPEigenbackgroundBGS::process(const cv::Mat &img_input, cv::Mat &img_output
params.SetFrameSize(width, height);
params.LowThreshold() = threshold; //15*15;
- params.HighThreshold() = 2*params.LowThreshold(); // Note: high threshold is used by post-processing
+ params.HighThreshold() = 2 * params.LowThreshold(); // Note: high threshold is used by post-processing
//params.HistorySize() = 100;
params.HistorySize() = historySize;
//params.EmbeddedDim() = 20;
@@ -68,22 +66,27 @@ void DPEigenbackgroundBGS::process(const cv::Mat &img_input, cv::Mat &img_output
bgs.Subtract(frameNumber, frame_data, lowThresholdMask, highThresholdMask);
lowThresholdMask.Clear();
bgs.Update(frameNumber, frame_data, lowThresholdMask);
-
- cv::Mat foreground(highThresholdMask.Ptr());
- if(showOutput)
- cv::imshow("Eigenbackground (Oliver)", foreground);
+ img_foreground = cv::cvarrToMat(highThresholdMask.Ptr());
+ img_background = cv::cvarrToMat(bgs.Background()->Ptr());
+ //img_background = cv::Mat::zeros(img_input.size(), img_input.type());
+
+#ifndef MEX_COMPILE_FLAG
+ if (showOutput)
+ cv::imshow("Eigenbackground (Oliver)", img_foreground);
+#endif
- foreground.copyTo(img_output);
+ img_foreground.copyTo(img_output);
+ img_background.copyTo(img_bgmodel);
delete frame;
firstTime = false;
frameNumber++;
}
-void DPEigenbackgroundBGS::saveConfig()
+void DPEigenbackground::saveConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/DPEigenbackgroundBGS.xml", 0, CV_STORAGE_WRITE);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_WRITE);
cvWriteInt(fs, "threshold", threshold);
cvWriteInt(fs, "historySize", historySize);
@@ -93,14 +96,14 @@ void DPEigenbackgroundBGS::saveConfig()
cvReleaseFileStorage(&fs);
}
-void DPEigenbackgroundBGS::loadConfig()
+void DPEigenbackground::loadConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/DPEigenbackgroundBGS.xml", 0, CV_STORAGE_READ);
-
- threshold = cvReadIntByName(fs, 0, "threshold", 225);
- historySize = cvReadIntByName(fs, 0, "historySize", 20);
- embeddedDim = cvReadIntByName(fs, 0, "embeddedDim", 10);
- showOutput = cvReadIntByName(fs, 0, "showOutput", true);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_READ);
+
+ threshold = cvReadIntByName(fs, nullptr, "threshold", 225);
+ historySize = cvReadIntByName(fs, nullptr, "historySize", 20);
+ embeddedDim = cvReadIntByName(fs, nullptr, "embeddedDim", 10);
+ showOutput = cvReadIntByName(fs, nullptr, "showOutput", true);
cvReleaseFileStorage(&fs);
}
diff --git a/package_bgs/DPEigenbackground.h b/package_bgs/DPEigenbackground.h
new file mode 100644
index 0000000..f84fee7
--- /dev/null
+++ b/package_bgs/DPEigenbackground.h
@@ -0,0 +1,55 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+#pragma once
+
+#include "IBGS.h"
+#include "dp/Eigenbackground.h"
+
+using namespace Algorithms::BackgroundSubtraction;
+
+namespace bgslibrary
+{
+ namespace algorithms
+ {
+ class DPEigenbackground : public IBGS
+ {
+ private:
+ long frameNumber;
+ IplImage* frame;
+ RgbImage frame_data;
+
+ EigenbackgroundParams params;
+ Eigenbackground bgs;
+ BwImage lowThresholdMask;
+ BwImage highThresholdMask;
+
+ int threshold;
+ int historySize;
+ int embeddedDim;
+
+ public:
+ DPEigenbackground();
+ ~DPEigenbackground();
+
+ void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
+
+ private:
+ void saveConfig();
+ void loadConfig();
+ };
+ }
+}
diff --git a/package_bgs/dp/DPGrimsonGMMBGS.cpp b/package_bgs/DPGrimsonGMM.cpp
similarity index 54%
rename from package_bgs/dp/DPGrimsonGMMBGS.cpp
rename to package_bgs/DPGrimsonGMM.cpp
index ae54860..c72b4d2 100644
--- a/package_bgs/dp/DPGrimsonGMMBGS.cpp
+++ b/package_bgs/DPGrimsonGMM.cpp
@@ -14,37 +14,35 @@ GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with BGSLibrary. If not, see .
*/
-#include "DPGrimsonGMMBGS.h"
+#include "DPGrimsonGMM.h"
-DPGrimsonGMMBGS::DPGrimsonGMMBGS() : firstTime(true), frameNumber(0), threshold(9.0), alpha(0.01), gaussians(3), showOutput(true)
+using namespace bgslibrary::algorithms;
+
+DPGrimsonGMM::DPGrimsonGMM() :
+ frameNumber(0), threshold(9.0), alpha(0.01), gaussians(3)
{
- std::cout << "DPGrimsonGMMBGS()" << std::endl;
+ std::cout << "DPGrimsonGMM()" << std::endl;
+ setup("./config/DPGrimsonGMM.xml");
}
-DPGrimsonGMMBGS::~DPGrimsonGMMBGS()
+DPGrimsonGMM::~DPGrimsonGMM()
{
- std::cout << "~DPGrimsonGMMBGS()" << std::endl;
+ std::cout << "~DPGrimsonGMM()" << std::endl;
}
-void DPGrimsonGMMBGS::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
+void DPGrimsonGMM::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
{
- if(img_input.empty())
- return;
-
- loadConfig();
-
- if(firstTime)
- saveConfig();
+ init(img_input, img_output, img_bgmodel);
frame = new IplImage(img_input);
-
- if(firstTime)
+
+ if (firstTime)
frame_data.ReleaseMemory(false);
frame_data = frame;
- if(firstTime)
+ if (firstTime)
{
- int width = img_input.size().width;
+ int width = img_input.size().width;
int height = img_input.size().height;
lowThresholdMask = cvCreateImage(cvSize(width, height), IPL_DEPTH_8U, 1);
@@ -55,7 +53,7 @@ void DPGrimsonGMMBGS::process(const cv::Mat &img_input, cv::Mat &img_output, cv:
params.SetFrameSize(width, height);
params.LowThreshold() = threshold; //3.0f*3.0f;
- params.HighThreshold() = 2*params.LowThreshold(); // Note: high threshold is used by post-processing
+ params.HighThreshold() = 2 * params.LowThreshold(); // Note: high threshold is used by post-processing
//params.Alpha() = 0.001f;
params.Alpha() = alpha; //0.01f;
params.MaxModes() = gaussians; //3;
@@ -67,22 +65,27 @@ void DPGrimsonGMMBGS::process(const cv::Mat &img_input, cv::Mat &img_output, cv:
bgs.Subtract(frameNumber, frame_data, lowThresholdMask, highThresholdMask);
lowThresholdMask.Clear();
bgs.Update(frameNumber, frame_data, lowThresholdMask);
-
- cv::Mat foreground(highThresholdMask.Ptr());
- if(showOutput)
- cv::imshow("GMM (Grimson)", foreground);
-
- foreground.copyTo(img_output);
+ img_foreground = cv::cvarrToMat(highThresholdMask.Ptr());
+ img_background = cv::cvarrToMat(bgs.Background()->Ptr());
+ //img_background = cv::Mat::zeros(img_input.size(), img_input.type());
+
+#ifndef MEX_COMPILE_FLAG
+ if (showOutput)
+ cv::imshow("GMM (Grimson)", img_foreground);
+#endif
+
+ img_foreground.copyTo(img_output);
+ img_background.copyTo(img_bgmodel);
delete frame;
firstTime = false;
frameNumber++;
}
-void DPGrimsonGMMBGS::saveConfig()
+void DPGrimsonGMM::saveConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/DPGrimsonGMMBGS.xml", 0, CV_STORAGE_WRITE);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_WRITE);
cvWriteReal(fs, "threshold", threshold);
cvWriteReal(fs, "alpha", alpha);
@@ -92,14 +95,14 @@ void DPGrimsonGMMBGS::saveConfig()
cvReleaseFileStorage(&fs);
}
-void DPGrimsonGMMBGS::loadConfig()
+void DPGrimsonGMM::loadConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/DPGrimsonGMMBGS.xml", 0, CV_STORAGE_READ);
-
- threshold = cvReadRealByName(fs, 0, "threshold", 9.0);
- alpha = cvReadRealByName(fs, 0, "alpha", 0.01);
- gaussians = cvReadIntByName(fs, 0, "gaussians", 3);
- showOutput = cvReadIntByName(fs, 0, "showOutput", true);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_READ);
+
+ threshold = cvReadRealByName(fs, nullptr, "threshold", 9.0);
+ alpha = cvReadRealByName(fs, nullptr, "alpha", 0.01);
+ gaussians = cvReadIntByName(fs, nullptr, "gaussians", 3);
+ showOutput = cvReadIntByName(fs, nullptr, "showOutput", true);
cvReleaseFileStorage(&fs);
}
diff --git a/package_bgs/dp/DPEigenbackgroundBGS.h b/package_bgs/DPGrimsonGMM.h
similarity index 53%
rename from package_bgs/dp/DPEigenbackgroundBGS.h
rename to package_bgs/DPGrimsonGMM.h
index cd4e54c..dcc05eb 100644
--- a/package_bgs/dp/DPEigenbackgroundBGS.h
+++ b/package_bgs/DPGrimsonGMM.h
@@ -16,41 +16,40 @@ along with BGSLibrary. If not, see .
*/
#pragma once
-#include
-#include
-
-
-#include "../IBGS.h"
-#include "Eigenbackground.h"
+#include "IBGS.h"
+#include "dp/GrimsonGMM.h"
using namespace Algorithms::BackgroundSubtraction;
-class DPEigenbackgroundBGS : public IBGS
+namespace bgslibrary
{
-private:
- bool firstTime;
- long frameNumber;
- IplImage* frame;
- RgbImage frame_data;
-
- EigenbackgroundParams params;
- Eigenbackground bgs;
- BwImage lowThresholdMask;
- BwImage highThresholdMask;
-
- int threshold;
- int historySize;
- int embeddedDim;
- bool showOutput;
-
-public:
- DPEigenbackgroundBGS();
- ~DPEigenbackgroundBGS();
-
- void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
-
-private:
- void saveConfig();
- void loadConfig();
-};
-
+ namespace algorithms
+ {
+ class DPGrimsonGMM : public IBGS
+ {
+ private:
+ long frameNumber;
+ IplImage* frame;
+ RgbImage frame_data;
+
+ GrimsonParams params;
+ GrimsonGMM bgs;
+ BwImage lowThresholdMask;
+ BwImage highThresholdMask;
+
+ double threshold;
+ double alpha;
+ int gaussians;
+
+ public:
+ DPGrimsonGMM();
+ ~DPGrimsonGMM();
+
+ void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
+
+ private:
+ void saveConfig();
+ void loadConfig();
+ };
+ }
+}
diff --git a/package_bgs/dp/DPMeanBGS.cpp b/package_bgs/DPMean.cpp
similarity index 55%
rename from package_bgs/dp/DPMeanBGS.cpp
rename to package_bgs/DPMean.cpp
index 13260b4..3af1fb6 100644
--- a/package_bgs/dp/DPMeanBGS.cpp
+++ b/package_bgs/DPMean.cpp
@@ -14,37 +14,35 @@ GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with BGSLibrary. If not, see .
*/
-#include "DPMeanBGS.h"
+#include "DPMean.h"
-DPMeanBGS::DPMeanBGS() : firstTime(true), frameNumber(0), threshold(2700), alpha(1e-6f), learningFrames(30), showOutput(true)
+using namespace bgslibrary::algorithms;
+
+DPMean::DPMean() :
+ frameNumber(0), threshold(2700), alpha(1e-6f), learningFrames(30)
{
- std::cout << "DPMeanBGS()" << std::endl;
+ std::cout << "DPMean()" << std::endl;
+ setup("./config/DPMean.xml");
}
-DPMeanBGS::~DPMeanBGS()
+DPMean::~DPMean()
{
- std::cout << "~DPMeanBGS()" << std::endl;
+ std::cout << "~DPMean()" << std::endl;
}
-void DPMeanBGS::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
+void DPMean::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
{
- if(img_input.empty())
- return;
-
- loadConfig();
-
- if(firstTime)
- saveConfig();
+ init(img_input, img_output, img_bgmodel);
frame = new IplImage(img_input);
-
- if(firstTime)
+
+ if (firstTime)
frame_data.ReleaseMemory(false);
frame_data = frame;
- if(firstTime)
+ if (firstTime)
{
- int width = img_input.size().width;
+ int width = img_input.size().width;
int height = img_input.size().height;
lowThresholdMask = cvCreateImage(cvSize(width, height), IPL_DEPTH_8U, 1);
@@ -55,7 +53,7 @@ void DPMeanBGS::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &
params.SetFrameSize(width, height);
params.LowThreshold() = threshold; //3*30*30; // 2700
- params.HighThreshold() = 2*params.LowThreshold(); // Note: high threshold is used by post-processing
+ params.HighThreshold() = 2 * params.LowThreshold(); // Note: high threshold is used by post-processing
//params.Alpha() = 1e-6f;
params.Alpha() = alpha;
params.LearningFrames() = learningFrames;//30;
@@ -67,22 +65,27 @@ void DPMeanBGS::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &
bgs.Subtract(frameNumber, frame_data, lowThresholdMask, highThresholdMask);
lowThresholdMask.Clear();
bgs.Update(frameNumber, frame_data, lowThresholdMask);
-
- cv::Mat foreground(highThresholdMask.Ptr());
- if(showOutput)
- cv::imshow("Temporal Mean (Donovan Parks)", foreground);
+ img_foreground = cv::cvarrToMat(highThresholdMask.Ptr());
+ img_background = cv::cvarrToMat(bgs.Background()->Ptr());
+ //img_background = cv::Mat::zeros(img_input.size(), img_input.type());
+
+#ifndef MEX_COMPILE_FLAG
+ if (showOutput)
+ cv::imshow("Temporal Mean (Donovan Parks)", img_foreground);
+#endif
- foreground.copyTo(img_output);
+ img_foreground.copyTo(img_output);
+ img_background.copyTo(img_bgmodel);
delete frame;
firstTime = false;
frameNumber++;
}
-void DPMeanBGS::saveConfig()
+void DPMean::saveConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/DPMeanBGS.xml", 0, CV_STORAGE_WRITE);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_WRITE);
cvWriteInt(fs, "threshold", threshold);
cvWriteReal(fs, "alpha", alpha);
@@ -92,14 +95,14 @@ void DPMeanBGS::saveConfig()
cvReleaseFileStorage(&fs);
}
-void DPMeanBGS::loadConfig()
+void DPMean::loadConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/DPMeanBGS.xml", 0, CV_STORAGE_READ);
-
- threshold = cvReadIntByName(fs, 0, "threshold", 2700);
- alpha = cvReadRealByName(fs, 0, "alpha", 1e-6f);
- learningFrames = cvReadIntByName(fs, 0, "learningFrames", 30);
- showOutput = cvReadIntByName(fs, 0, "showOutput", true);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_READ);
+
+ threshold = cvReadIntByName(fs, nullptr, "threshold", 2700);
+ alpha = cvReadRealByName(fs, nullptr, "alpha", 1e-6f);
+ learningFrames = cvReadIntByName(fs, nullptr, "learningFrames", 30);
+ showOutput = cvReadIntByName(fs, nullptr, "showOutput", true);
cvReleaseFileStorage(&fs);
}
diff --git a/package_bgs/dp/DPZivkovicAGMMBGS.h b/package_bgs/DPMean.h
similarity index 56%
rename from package_bgs/dp/DPZivkovicAGMMBGS.h
rename to package_bgs/DPMean.h
index 775226a..6029968 100644
--- a/package_bgs/dp/DPZivkovicAGMMBGS.h
+++ b/package_bgs/DPMean.h
@@ -16,41 +16,40 @@ along with BGSLibrary. If not, see .
*/
#pragma once
-#include
-#include
-
-
-#include "../IBGS.h"
-#include "ZivkovicAGMM.h"
+#include "IBGS.h"
+#include "dp/MeanBGS.h"
using namespace Algorithms::BackgroundSubtraction;
-class DPZivkovicAGMMBGS : public IBGS
+namespace bgslibrary
{
-private:
- bool firstTime;
- long frameNumber;
- IplImage* frame;
- RgbImage frame_data;
-
- ZivkovicParams params;
- ZivkovicAGMM bgs;
- BwImage lowThresholdMask;
- BwImage highThresholdMask;
-
- double threshold;
- double alpha;
- int gaussians;
- bool showOutput;
-
-public:
- DPZivkovicAGMMBGS();
- ~DPZivkovicAGMMBGS();
-
- void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
-
-private:
- void saveConfig();
- void loadConfig();
-};
-
+ namespace algorithms
+ {
+ class DPMean : public IBGS
+ {
+ private:
+ long frameNumber;
+ IplImage* frame;
+ RgbImage frame_data;
+
+ MeanParams params;
+ MeanBGS bgs;
+ BwImage lowThresholdMask;
+ BwImage highThresholdMask;
+
+ int threshold;
+ double alpha;
+ int learningFrames;
+
+ public:
+ DPMean();
+ ~DPMean();
+
+ void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
+
+ private:
+ void saveConfig();
+ void loadConfig();
+ };
+ }
+}
diff --git a/package_bgs/dp/DPPratiMediodBGS.cpp b/package_bgs/DPPratiMediod.cpp
similarity index 53%
rename from package_bgs/dp/DPPratiMediodBGS.cpp
rename to package_bgs/DPPratiMediod.cpp
index ba1d6be..d1942c5 100644
--- a/package_bgs/dp/DPPratiMediodBGS.cpp
+++ b/package_bgs/DPPratiMediod.cpp
@@ -14,37 +14,35 @@ GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with BGSLibrary. If not, see .
*/
-#include "DPPratiMediodBGS.h"
+#include "DPPratiMediod.h"
-DPPratiMediodBGS::DPPratiMediodBGS() : firstTime(true), frameNumber(0), threshold(30), samplingRate(5), historySize(16), weight(5), showOutput(true)
+using namespace bgslibrary::algorithms;
+
+DPPratiMediod::DPPratiMediod() :
+ frameNumber(0), threshold(30), samplingRate(5), historySize(16), weight(5)
{
- std::cout << "DPPratiMediodBGS()" << std::endl;
+ std::cout << "DPPratiMediod()" << std::endl;
+ setup("./config/DPPratiMediod.xml");
}
-DPPratiMediodBGS::~DPPratiMediodBGS()
+DPPratiMediod::~DPPratiMediod()
{
- std::cout << "~DPPratiMediodBGS()" << std::endl;
+ std::cout << "~DPPratiMediod()" << std::endl;
}
-void DPPratiMediodBGS::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
+void DPPratiMediod::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
{
- if(img_input.empty())
- return;
-
- loadConfig();
-
- if(firstTime)
- saveConfig();
+ init(img_input, img_output, img_bgmodel);
frame = new IplImage(img_input);
-
- if(firstTime)
+
+ if (firstTime)
frame_data.ReleaseMemory(false);
frame_data = frame;
- if(firstTime)
+ if (firstTime)
{
- int width = img_input.size().width;
+ int width = img_input.size().width;
int height = img_input.size().height;
lowThresholdMask = cvCreateImage(cvSize(width, height), IPL_DEPTH_8U, 1);
@@ -55,7 +53,7 @@ void DPPratiMediodBGS::process(const cv::Mat &img_input, cv::Mat &img_output, cv
params.SetFrameSize(width, height);
params.LowThreshold() = threshold;
- params.HighThreshold() = 2*params.LowThreshold(); // Note: high threshold is used by post-processing
+ params.HighThreshold() = 2 * params.LowThreshold(); // Note: high threshold is used by post-processing
params.SamplingRate() = samplingRate;
params.HistorySize() = historySize;
params.Weight() = weight;
@@ -67,26 +65,29 @@ void DPPratiMediodBGS::process(const cv::Mat &img_input, cv::Mat &img_output, cv
bgs.Subtract(frameNumber, frame_data, lowThresholdMask, highThresholdMask);
lowThresholdMask.Clear();
bgs.Update(frameNumber, frame_data, lowThresholdMask);
-
- cv::Mat foreground(highThresholdMask.Ptr());
- cv::Mat background(bgs.Background()->Ptr());
- if(showOutput){
- cv::imshow("Temporal Median FG (Cucchiara&Calderara)", foreground);
- cv::imshow("Temporal Median BG (Cucchiara&Calderara)", background);
+ img_foreground = cv::cvarrToMat(highThresholdMask.Ptr());
+ img_background = cv::cvarrToMat(bgs.Background()->Ptr());
+
+#ifndef MEX_COMPILE_FLAG
+ if (showOutput)
+ {
+ cv::imshow("Temporal Median FG (Cucchiara&Calderara)", img_foreground);
+ cv::imshow("Temporal Median BG (Cucchiara&Calderara)", img_background);
}
+#endif
- foreground.copyTo(img_output);
- background.copyTo(img_bgmodel);
+ img_foreground.copyTo(img_output);
+ img_background.copyTo(img_bgmodel);
delete frame;
firstTime = false;
frameNumber++;
}
-void DPPratiMediodBGS::saveConfig()
+void DPPratiMediod::saveConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/DPPratiMediodBGS.xml", 0, CV_STORAGE_WRITE);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_WRITE);
cvWriteInt(fs, "threshold", threshold);
cvWriteInt(fs, "samplingRate", samplingRate);
@@ -97,15 +98,15 @@ void DPPratiMediodBGS::saveConfig()
cvReleaseFileStorage(&fs);
}
-void DPPratiMediodBGS::loadConfig()
+void DPPratiMediod::loadConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/DPPratiMediodBGS.xml", 0, CV_STORAGE_READ);
-
- threshold = cvReadIntByName(fs, 0, "threshold", 30);
- samplingRate = cvReadIntByName(fs, 0, "samplingRate", 5);
- historySize = cvReadIntByName(fs, 0, "historySize", 16);
- weight = cvReadIntByName(fs, 0, "weight", 5);
- showOutput = cvReadIntByName(fs, 0, "showOutput", true);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_READ);
+
+ threshold = cvReadIntByName(fs, nullptr, "threshold", 30);
+ samplingRate = cvReadIntByName(fs, nullptr, "samplingRate", 5);
+ historySize = cvReadIntByName(fs, nullptr, "historySize", 16);
+ weight = cvReadIntByName(fs, nullptr, "weight", 5);
+ showOutput = cvReadIntByName(fs, nullptr, "showOutput", true);
cvReleaseFileStorage(&fs);
-}
\ No newline at end of file
+}
diff --git a/package_bgs/dp/DPMeanBGS.h b/package_bgs/DPPratiMediod.h
similarity index 52%
rename from package_bgs/dp/DPMeanBGS.h
rename to package_bgs/DPPratiMediod.h
index 8829686..d37a77a 100644
--- a/package_bgs/dp/DPMeanBGS.h
+++ b/package_bgs/DPPratiMediod.h
@@ -16,41 +16,41 @@ along with BGSLibrary. If not, see .
*/
#pragma once
-#include
-#include
-
-
-#include "../IBGS.h"
-#include "MeanBGS.h"
+#include "IBGS.h"
+#include "dp/PratiMediodBGS.h"
using namespace Algorithms::BackgroundSubtraction;
-class DPMeanBGS : public IBGS
+namespace bgslibrary
{
-private:
- bool firstTime;
- long frameNumber;
- IplImage* frame;
- RgbImage frame_data;
-
- MeanParams params;
- MeanBGS bgs;
- BwImage lowThresholdMask;
- BwImage highThresholdMask;
-
- int threshold;
- double alpha;
- int learningFrames;
- bool showOutput;
-
-public:
- DPMeanBGS();
- ~DPMeanBGS();
-
- void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
-
-private:
- void saveConfig();
- void loadConfig();
-};
-
+ namespace algorithms
+ {
+ class DPPratiMediod : public IBGS
+ {
+ private:
+ long frameNumber;
+ IplImage* frame;
+ RgbImage frame_data;
+
+ PratiParams params;
+ PratiMediodBGS bgs;
+ BwImage lowThresholdMask;
+ BwImage highThresholdMask;
+
+ int threshold;
+ int samplingRate;
+ int historySize;
+ int weight;
+
+ public:
+ DPPratiMediod();
+ ~DPPratiMediod();
+
+ void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
+
+ private:
+ void saveConfig();
+ void loadConfig();
+ };
+ }
+}
diff --git a/package_bgs/dp/DPTextureBGS.cpp b/package_bgs/DPTexture.cpp
similarity index 65%
rename from package_bgs/dp/DPTextureBGS.cpp
rename to package_bgs/DPTexture.cpp
index 2d34342..3285ccf 100644
--- a/package_bgs/dp/DPTextureBGS.cpp
+++ b/package_bgs/DPTexture.cpp
@@ -14,15 +14,18 @@ GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with BGSLibrary. If not, see .
*/
-#include "DPTextureBGS.h"
+#include "DPTexture.h"
-DPTextureBGS::DPTextureBGS() : firstTime(true), showOutput(true)
- //, enableFiltering(true)
+using namespace bgslibrary::algorithms;
+
+DPTexture::DPTexture()
+// : enableFiltering(true)
{
- std::cout << "DPTextureBGS()" << std::endl;
+ std::cout << "DPTexture()" << std::endl;
+ setup("./config/DPTexture.xml");
}
-DPTextureBGS::~DPTextureBGS()
+DPTexture::~DPTexture()
{
delete[] bgModel; // ~10Kb (25.708-15.968)
delete[] modeArray;
@@ -33,34 +36,31 @@ DPTextureBGS::~DPTextureBGS()
fgMask.ReleaseImage();
tempMask.ReleaseImage();
texture.ReleaseImage();
- std::cout << "~DPTextureBGS()" << std::endl;
+ std::cout << "~DPTexture()" << std::endl;
}
-void DPTextureBGS::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
+void DPTexture::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
{
- if(img_input.empty())
- return;
-
- loadConfig();
+ init(img_input, img_output, img_bgmodel);
frame = new IplImage(img_input);
-
- if(firstTime)
+
+ if (firstTime)
{
- width = img_input.size().width;
+ width = img_input.size().width;
height = img_input.size().height;
size = width * height;
// input image
image = cvCreateImage(cvSize(width, height), 8, 3);
- cvCopy(frame, image.Ptr());
+ cvCopy(frame, image.Ptr());
// foreground masks
fgMask = cvCreateImage(cvSize(width, height), 8, 1);
tempMask = cvCreateImage(cvSize(width, height), 8, 1);
cvZero(fgMask.Ptr());
cvZero(tempMask.Ptr());
-
+
// create background model
bgModel = new TextureArray[size];
texture = cvCreateImage(cvSize(width, height), 8, 3);
@@ -71,16 +71,16 @@ void DPTextureBGS::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Ma
// initialize background model
bgs.LBP(image, texture);
bgs.Histogram(texture, curTextureHist);
- for(int y = REGION_R+TEXTURE_R; y < height-REGION_R-TEXTURE_R; ++y)
+ for (int y = REGION_R + TEXTURE_R; y < height - REGION_R - TEXTURE_R; ++y)
{
- for(int x = REGION_R+TEXTURE_R; x < width-REGION_R-TEXTURE_R; ++x)
+ for (int x = REGION_R + TEXTURE_R; x < width - REGION_R - TEXTURE_R; ++x)
{
- int index = x+y*width;
-
- for(int m = 0; m < NUM_MODES; ++m)
+ int index = x + y*width;
+
+ for (int m = 0; m < NUM_MODES; ++m)
{
- for(int i = 0; i < NUM_BINS; ++i)
- {
+ for (int i = 0; i < NUM_BINS; ++i)
+ {
bgModel[index].mode[m].r[i] = curTextureHist[index].r[i];
bgModel[index].mode[m].g[i] = curTextureHist[index].g[i];
bgModel[index].mode[m].b[i] = curTextureHist[index].b[i];
@@ -91,18 +91,16 @@ void DPTextureBGS::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Ma
//dilateElement = cvCreateStructuringElementEx(7, 7, 3, 3, CV_SHAPE_RECT);
//erodeElement = cvCreateStructuringElementEx(3, 3, 1, 1, CV_SHAPE_RECT);
-
- saveConfig();
firstTime = false;
}
-
- cvCopy(frame, image.Ptr());
+
+ cvCopy(frame, image.Ptr());
// perform background subtraction
bgs.LBP(image, texture);
bgs.Histogram(texture, curTextureHist);
bgs.BgsCompare(bgModel, curTextureHist, modeArray, THRESHOLD, fgMask);
-
+
//if(enableFiltering)
//{
// // size filtering
@@ -120,22 +118,27 @@ void DPTextureBGS::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Ma
// cvErode(fgMask.Ptr(), fgMask.Ptr(), erodeElement, 1);
//}
- cv::Mat foreground(fgMask.Ptr());
- if(!foreground.empty())
- foreground.copyTo(img_output);
-
- if(showOutput)
- cv::imshow("Texture BGS (Donovan Parks)", foreground);
+ img_foreground = cv::cvarrToMat(fgMask.Ptr());
+ //img_background = cv::cvarrToMat(bgs.Background()->Ptr());
+ img_background = cv::Mat::zeros(img_input.size(), img_input.type());
+
+#ifndef MEX_COMPILE_FLAG
+ if (showOutput)
+ cv::imshow("Texture BGS (Donovan Parks)", img_foreground);
+#endif
- // update background subtraction
+ img_foreground.copyTo(img_output);
+ img_background.copyTo(img_bgmodel);
+
+ // update background subtraction
bgs.UpdateModel(fgMask, bgModel, curTextureHist, modeArray);
-
+
delete frame;
}
-void DPTextureBGS::saveConfig()
+void DPTexture::saveConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/DPTextureBGS.xml", 0, CV_STORAGE_WRITE);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_WRITE);
//cvWriteReal(fs, "alpha", alpha);
//cvWriteInt(fs, "enableFiltering", enableFiltering);
@@ -144,13 +147,13 @@ void DPTextureBGS::saveConfig()
cvReleaseFileStorage(&fs);
}
-void DPTextureBGS::loadConfig()
+void DPTexture::loadConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/DPTextureBGS.xml", 0, CV_STORAGE_READ);
-
- //alpha = cvReadRealByName(fs, 0, "alpha", 1e-6f);
- //enableFiltering = cvReadIntByName(fs, 0, "enableFiltering", true);
- showOutput = cvReadIntByName(fs, 0, "showOutput", true);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_READ);
+
+ //alpha = cvReadRealByName(fs, nullptr, "alpha", 1e-6f);
+ //enableFiltering = cvReadIntByName(fs, nullptr, "enableFiltering", true);
+ showOutput = cvReadIntByName(fs, nullptr, "showOutput", true);
cvReleaseFileStorage(&fs);
}
diff --git a/package_bgs/DPTexture.h b/package_bgs/DPTexture.h
new file mode 100644
index 0000000..3cfdcea
--- /dev/null
+++ b/package_bgs/DPTexture.h
@@ -0,0 +1,59 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+#pragma once
+
+#include "IBGS.h"
+#include "dp/TextureBGS.h"
+//#include "ConnectedComponents.h"
+
+namespace bgslibrary
+{
+ namespace algorithms
+ {
+ class DPTexture : public IBGS
+ {
+ private:
+ int width;
+ int height;
+ int size;
+ TextureBGS bgs;
+ IplImage* frame;
+ RgbImage image;
+ BwImage fgMask;
+ BwImage tempMask;
+ TextureArray* bgModel;
+ RgbImage texture;
+ unsigned char* modeArray;
+ TextureHistogram* curTextureHist;
+ //ConnectedComponents cc;
+ //CBlobResult largeBlobs;
+ //IplConvKernel* dilateElement;
+ //IplConvKernel* erodeElement;
+ //bool enableFiltering;
+
+ public:
+ DPTexture();
+ ~DPTexture();
+
+ void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
+
+ private:
+ void saveConfig();
+ void loadConfig();
+ };
+ }
+}
diff --git a/package_bgs/dp/DPWrenGABGS.cpp b/package_bgs/DPWrenGA.cpp
similarity index 54%
rename from package_bgs/dp/DPWrenGABGS.cpp
rename to package_bgs/DPWrenGA.cpp
index d7241b1..7fc3313 100644
--- a/package_bgs/dp/DPWrenGABGS.cpp
+++ b/package_bgs/DPWrenGA.cpp
@@ -14,37 +14,35 @@ GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with BGSLibrary. If not, see .
*/
-#include "DPWrenGABGS.h"
+#include "DPWrenGA.h"
-DPWrenGABGS::DPWrenGABGS() : firstTime(true), frameNumber(0), threshold(12.25f), alpha(0.005f), learningFrames(30), showOutput(true)
+using namespace bgslibrary::algorithms;
+
+DPWrenGA::DPWrenGA() :
+ frameNumber(0), threshold(12.25f), alpha(0.005f), learningFrames(30)
{
- std::cout << "DPWrenGABGS()" << std::endl;
+ std::cout << "DPWrenGA()" << std::endl;
+ setup("./config/DPWrenGA.xml");
}
-DPWrenGABGS::~DPWrenGABGS()
+DPWrenGA::~DPWrenGA()
{
- std::cout << "~DPWrenGABGS()" << std::endl;
+ std::cout << "~DPWrenGA()" << std::endl;
}
-void DPWrenGABGS::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
+void DPWrenGA::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
{
- if(img_input.empty())
- return;
-
- loadConfig();
-
- if(firstTime)
- saveConfig();
+ init(img_input, img_output, img_bgmodel);
frame = new IplImage(img_input);
-
- if(firstTime)
+
+ if (firstTime)
frame_data.ReleaseMemory(false);
frame_data = frame;
- if(firstTime)
+ if (firstTime)
{
- int width = img_input.size().width;
+ int width = img_input.size().width;
int height = img_input.size().height;
lowThresholdMask = cvCreateImage(cvSize(width, height), IPL_DEPTH_8U, 1);
@@ -55,7 +53,7 @@ void DPWrenGABGS::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat
params.SetFrameSize(width, height);
params.LowThreshold() = threshold; //3.5f*3.5f;
- params.HighThreshold() = 2*params.LowThreshold(); // Note: high threshold is used by post-processing
+ params.HighThreshold() = 2 * params.LowThreshold(); // Note: high threshold is used by post-processing
params.Alpha() = alpha; //0.005f;
params.LearningFrames() = learningFrames; //30;
@@ -66,22 +64,27 @@ void DPWrenGABGS::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat
bgs.Subtract(frameNumber, frame_data, lowThresholdMask, highThresholdMask);
lowThresholdMask.Clear();
bgs.Update(frameNumber, frame_data, lowThresholdMask);
-
- cv::Mat foreground(highThresholdMask.Ptr());
- if(showOutput)
- cv::imshow("Gaussian Average (Wren)", foreground);
-
- foreground.copyTo(img_output);
+ img_foreground = cv::cvarrToMat(highThresholdMask.Ptr());
+ img_background = cv::cvarrToMat(bgs.Background()->Ptr());
+ //img_background = cv::Mat::zeros(img_input.size(), img_input.type());
+
+#ifndef MEX_COMPILE_FLAG
+ if (showOutput)
+ cv::imshow("Gaussian Average (Wren)", img_foreground);
+#endif
+
+ img_foreground.copyTo(img_output);
+ img_background.copyTo(img_bgmodel);
delete frame;
firstTime = false;
frameNumber++;
}
-void DPWrenGABGS::saveConfig()
+void DPWrenGA::saveConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/DPWrenGABGS.xml", 0, CV_STORAGE_WRITE);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_WRITE);
cvWriteReal(fs, "threshold", threshold);
cvWriteReal(fs, "alpha", alpha);
@@ -91,15 +94,14 @@ void DPWrenGABGS::saveConfig()
cvReleaseFileStorage(&fs);
}
-void DPWrenGABGS::loadConfig()
+void DPWrenGA::loadConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/DPWrenGABGS.xml", 0, CV_STORAGE_READ);
-
- threshold = cvReadRealByName(fs, 0, "threshold", 12.25f);
- alpha = cvReadRealByName(fs, 0, "alpha", 0.005f);
- learningFrames = cvReadIntByName(fs, 0, "learningFrames", 30);
- showOutput = cvReadIntByName(fs, 0, "showOutput", true);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_READ);
+
+ threshold = cvReadRealByName(fs, nullptr, "threshold", 12.25f);
+ alpha = cvReadRealByName(fs, nullptr, "alpha", 0.005f);
+ learningFrames = cvReadIntByName(fs, nullptr, "learningFrames", 30);
+ showOutput = cvReadIntByName(fs, nullptr, "showOutput", true);
cvReleaseFileStorage(&fs);
}
-
diff --git a/package_bgs/dp/DPWrenGABGS.h b/package_bgs/DPWrenGA.h
similarity index 54%
rename from package_bgs/dp/DPWrenGABGS.h
rename to package_bgs/DPWrenGA.h
index 30ab614..e4b0b5f 100644
--- a/package_bgs/dp/DPWrenGABGS.h
+++ b/package_bgs/DPWrenGA.h
@@ -16,41 +16,40 @@ along with BGSLibrary. If not, see .
*/
#pragma once
-#include
-#include
-
-
-#include "../IBGS.h"
-#include "WrenGA.h"
+#include "IBGS.h"
+#include "dp/WrenGA.h"
using namespace Algorithms::BackgroundSubtraction;
-class DPWrenGABGS : public IBGS
+namespace bgslibrary
{
-private:
- bool firstTime;
- long frameNumber;
- IplImage* frame;
- RgbImage frame_data;
-
- WrenParams params;
- WrenGA bgs;
- BwImage lowThresholdMask;
- BwImage highThresholdMask;
-
- double threshold;
- double alpha;
- int learningFrames;
- bool showOutput;
-
-public:
- DPWrenGABGS();
- ~DPWrenGABGS();
-
- void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
-
-private:
- void saveConfig();
- void loadConfig();
-};
-
+ namespace algorithms
+ {
+ class DPWrenGA : public IBGS
+ {
+ private:
+ long frameNumber;
+ IplImage* frame;
+ RgbImage frame_data;
+
+ WrenParams params;
+ WrenGA bgs;
+ BwImage lowThresholdMask;
+ BwImage highThresholdMask;
+
+ double threshold;
+ double alpha;
+ int learningFrames;
+
+ public:
+ DPWrenGA();
+ ~DPWrenGA();
+
+ void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
+
+ private:
+ void saveConfig();
+ void loadConfig();
+ };
+ }
+}
diff --git a/package_bgs/dp/DPZivkovicAGMMBGS.cpp b/package_bgs/DPZivkovicAGMM.cpp
similarity index 53%
rename from package_bgs/dp/DPZivkovicAGMMBGS.cpp
rename to package_bgs/DPZivkovicAGMM.cpp
index e8276f6..a5a9735 100644
--- a/package_bgs/dp/DPZivkovicAGMMBGS.cpp
+++ b/package_bgs/DPZivkovicAGMM.cpp
@@ -14,37 +14,35 @@ GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with BGSLibrary. If not, see .
*/
-#include "DPZivkovicAGMMBGS.h"
+#include "DPZivkovicAGMM.h"
-DPZivkovicAGMMBGS::DPZivkovicAGMMBGS() : firstTime(true), frameNumber(0), threshold(25.0f), alpha(0.001f), gaussians(3), showOutput(true)
+using namespace bgslibrary::algorithms;
+
+DPZivkovicAGMM::DPZivkovicAGMM() :
+ frameNumber(0), threshold(25.0f), alpha(0.001f), gaussians(3)
{
- std::cout << "DPZivkovicAGMMBGS()" << std::endl;
+ std::cout << "DPZivkovicAGMM()" << std::endl;
+ setup("./config/DPZivkovicAGMM.xml");
}
-DPZivkovicAGMMBGS::~DPZivkovicAGMMBGS()
+DPZivkovicAGMM::~DPZivkovicAGMM()
{
- std::cout << "~DPZivkovicAGMMBGS()" << std::endl;
+ std::cout << "~DPZivkovicAGMM()" << std::endl;
}
-void DPZivkovicAGMMBGS::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
+void DPZivkovicAGMM::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
{
- if(img_input.empty())
- return;
-
- loadConfig();
-
- if(firstTime)
- saveConfig();
+ init(img_input, img_output, img_bgmodel);
frame = new IplImage(img_input);
-
- if(firstTime)
+
+ if (firstTime)
frame_data.ReleaseMemory(false);
frame_data = frame;
- if(firstTime)
+ if (firstTime)
{
- int width = img_input.size().width;
+ int width = img_input.size().width;
int height = img_input.size().height;
lowThresholdMask = cvCreateImage(cvSize(width, height), IPL_DEPTH_8U, 1);
@@ -55,7 +53,7 @@ void DPZivkovicAGMMBGS::process(const cv::Mat &img_input, cv::Mat &img_output, c
params.SetFrameSize(width, height);
params.LowThreshold() = threshold; //5.0f*5.0f;
- params.HighThreshold() = 2*params.LowThreshold(); // Note: high threshold is used by post-processing
+ params.HighThreshold() = 2 * params.LowThreshold(); // Note: high threshold is used by post-processing
params.Alpha() = alpha; //0.001f;
params.MaxModes() = gaussians; //3;
@@ -66,22 +64,27 @@ void DPZivkovicAGMMBGS::process(const cv::Mat &img_input, cv::Mat &img_output, c
bgs.Subtract(frameNumber, frame_data, lowThresholdMask, highThresholdMask);
lowThresholdMask.Clear();
bgs.Update(frameNumber, frame_data, lowThresholdMask);
-
- cv::Mat foreground(highThresholdMask.Ptr());
- if(showOutput)
- cv::imshow("Gaussian Mixture Model (Zivkovic)", foreground);
-
- foreground.copyTo(img_output);
+ img_foreground = cv::cvarrToMat(highThresholdMask.Ptr());
+ img_background = cv::cvarrToMat(bgs.Background()->Ptr());
+ //img_background = cv::Mat::zeros(img_input.size(), img_input.type());
+
+#ifndef MEX_COMPILE_FLAG
+ if (showOutput)
+ cv::imshow("Gaussian Mixture Model (Zivkovic)", img_foreground);
+#endif
+
+ img_foreground.copyTo(img_output);
+ img_background.copyTo(img_bgmodel);
delete frame;
firstTime = false;
frameNumber++;
}
-void DPZivkovicAGMMBGS::saveConfig()
+void DPZivkovicAGMM::saveConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/DPZivkovicAGMMBGS.xml", 0, CV_STORAGE_WRITE);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_WRITE);
cvWriteReal(fs, "threshold", threshold);
cvWriteReal(fs, "alpha", alpha);
@@ -91,14 +94,14 @@ void DPZivkovicAGMMBGS::saveConfig()
cvReleaseFileStorage(&fs);
}
-void DPZivkovicAGMMBGS::loadConfig()
+void DPZivkovicAGMM::loadConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/DPZivkovicAGMMBGS.xml", 0, CV_STORAGE_READ);
-
- threshold = cvReadRealByName(fs, 0, "threshold", 25.0f);
- alpha = cvReadRealByName(fs, 0, "alpha", 0.001f);
- gaussians = cvReadIntByName(fs, 0, "gaussians", 3);
- showOutput = cvReadIntByName(fs, 0, "showOutput", true);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_READ);
+
+ threshold = cvReadRealByName(fs, nullptr, "threshold", 25.0f);
+ alpha = cvReadRealByName(fs, nullptr, "alpha", 0.001f);
+ gaussians = cvReadIntByName(fs, nullptr, "gaussians", 3);
+ showOutput = cvReadIntByName(fs, nullptr, "showOutput", true);
cvReleaseFileStorage(&fs);
}
diff --git a/package_bgs/dp/DPGrimsonGMMBGS.h b/package_bgs/DPZivkovicAGMM.h
similarity index 53%
rename from package_bgs/dp/DPGrimsonGMMBGS.h
rename to package_bgs/DPZivkovicAGMM.h
index 4f955b9..f35504b 100644
--- a/package_bgs/dp/DPGrimsonGMMBGS.h
+++ b/package_bgs/DPZivkovicAGMM.h
@@ -16,41 +16,40 @@ along with BGSLibrary. If not, see .
*/
#pragma once
-#include
-#include
-
-
-#include "../IBGS.h"
-#include "GrimsonGMM.h"
+#include "IBGS.h"
+#include "dp/ZivkovicAGMM.h"
using namespace Algorithms::BackgroundSubtraction;
-class DPGrimsonGMMBGS : public IBGS
+namespace bgslibrary
{
-private:
- bool firstTime;
- long frameNumber;
- IplImage* frame;
- RgbImage frame_data;
-
- GrimsonParams params;
- GrimsonGMM bgs;
- BwImage lowThresholdMask;
- BwImage highThresholdMask;
-
- double threshold;
- double alpha;
- int gaussians;
- bool showOutput;
-
-public:
- DPGrimsonGMMBGS();
- ~DPGrimsonGMMBGS();
-
- void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
-
-private:
- void saveConfig();
- void loadConfig();
-};
-
+ namespace algorithms
+ {
+ class DPZivkovicAGMM : public IBGS
+ {
+ private:
+ long frameNumber;
+ IplImage* frame;
+ RgbImage frame_data;
+
+ ZivkovicParams params;
+ ZivkovicAGMM bgs;
+ BwImage lowThresholdMask;
+ BwImage highThresholdMask;
+
+ double threshold;
+ double alpha;
+ int gaussians;
+
+ public:
+ DPZivkovicAGMM();
+ ~DPZivkovicAGMM();
+
+ void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
+
+ private:
+ void saveConfig();
+ void loadConfig();
+ };
+ }
+}
diff --git a/package_bgs/FrameDifference.cpp b/package_bgs/FrameDifference.cpp
new file mode 100644
index 0000000..4d5c076
--- /dev/null
+++ b/package_bgs/FrameDifference.cpp
@@ -0,0 +1,84 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+#include "FrameDifference.h"
+
+using namespace bgslibrary::algorithms;
+
+FrameDifference::FrameDifference() :
+ enableThreshold(true), threshold(15)
+{
+ std::cout << "FrameDifference()" << std::endl;
+ setup("./config/FrameDifference.xml");
+}
+
+FrameDifference::~FrameDifference()
+{
+ std::cout << "~FrameDifference()" << std::endl;
+}
+
+void FrameDifference::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
+{
+ init(img_input, img_output, img_bgmodel);
+
+ if (img_background.empty())
+ {
+ img_input.copyTo(img_background);
+ return;
+ }
+
+ cv::absdiff(img_background, img_input, img_foreground);
+
+ if (img_foreground.channels() == 3)
+ cv::cvtColor(img_foreground, img_foreground, CV_BGR2GRAY);
+
+ if (enableThreshold)
+ cv::threshold(img_foreground, img_foreground, threshold, 255, cv::THRESH_BINARY);
+
+#ifndef MEX_COMPILE_FLAG
+ if (showOutput)
+ cv::imshow("Frame Difference", img_foreground);
+#endif
+
+ img_foreground.copyTo(img_output);
+
+ img_input.copyTo(img_background);
+ img_background.copyTo(img_bgmodel);
+
+ firstTime = false;
+}
+
+void FrameDifference::saveConfig()
+{
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_WRITE);
+
+ cvWriteInt(fs, "enableThreshold", enableThreshold);
+ cvWriteInt(fs, "threshold", threshold);
+ cvWriteInt(fs, "showOutput", showOutput);
+
+ cvReleaseFileStorage(&fs);
+}
+
+void FrameDifference::loadConfig()
+{
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_READ);
+
+ enableThreshold = cvReadIntByName(fs, nullptr, "enableThreshold", true);
+ threshold = cvReadIntByName(fs, nullptr, "threshold", 15);
+ showOutput = cvReadIntByName(fs, nullptr, "showOutput", true);
+
+ cvReleaseFileStorage(&fs);
+}
diff --git a/package_bgs/FrameDifferenceBGS.h b/package_bgs/FrameDifference.h
similarity index 61%
rename from package_bgs/FrameDifferenceBGS.h
rename to package_bgs/FrameDifference.h
index 338979f..07bed8e 100644
--- a/package_bgs/FrameDifferenceBGS.h
+++ b/package_bgs/FrameDifference.h
@@ -16,29 +16,28 @@ along with BGSLibrary. If not, see .
*/
#pragma once
-#include
-#include
-
-
#include "IBGS.h"
-class FrameDifferenceBGS : public IBGS
+namespace bgslibrary
{
-private:
- bool firstTime;
- cv::Mat img_input_prev;
- cv::Mat img_foreground;
- bool enableThreshold;
- int threshold;
- bool showOutput;
-
-public:
- FrameDifferenceBGS();
- ~FrameDifferenceBGS();
-
- void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
-
-private:
- void saveConfig();
- void loadConfig();
-};
\ No newline at end of file
+ namespace algorithms
+ {
+ class FrameDifference : public IBGS
+ {
+ private:
+ bool enableThreshold;
+ int threshold;
+
+ public:
+ FrameDifference();
+ ~FrameDifference();
+
+ void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
+
+ private:
+ void saveConfig();
+ void loadConfig();
+ };
+ }
+}
+
diff --git a/package_bgs/FrameDifferenceBGS.cpp b/package_bgs/FrameDifferenceBGS.cpp
deleted file mode 100644
index e871651..0000000
--- a/package_bgs/FrameDifferenceBGS.cpp
+++ /dev/null
@@ -1,83 +0,0 @@
-/*
-This file is part of BGSLibrary.
-
-BGSLibrary is free software: you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 3 of the License, or
-(at your option) any later version.
-
-BGSLibrary is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with BGSLibrary. If not, see .
-*/
-#include "FrameDifferenceBGS.h"
-
-FrameDifferenceBGS::FrameDifferenceBGS() : firstTime(true), enableThreshold(true), threshold(15), showOutput(true)
-{
- std::cout << "FrameDifferenceBGS()" << std::endl;
-}
-
-FrameDifferenceBGS::~FrameDifferenceBGS()
-{
- std::cout << "~FrameDifferenceBGS()" << std::endl;
-}
-
-void FrameDifferenceBGS::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
-{
- if(img_input.empty())
- return;
-
- loadConfig();
-
- if(firstTime)
- saveConfig();
-
- if(img_input_prev.empty())
- {
- img_input.copyTo(img_input_prev);
- return;
- }
-
- cv::absdiff(img_input_prev, img_input, img_foreground);
-
- if(img_foreground.channels() == 3)
- cv::cvtColor(img_foreground, img_foreground, CV_BGR2GRAY);
-
- if(enableThreshold)
- cv::threshold(img_foreground, img_foreground, threshold, 255, cv::THRESH_BINARY);
-
- if(showOutput)
- cv::imshow("Frame Difference", img_foreground);
-
- img_foreground.copyTo(img_output);
-
- img_input.copyTo(img_input_prev);
-
- firstTime = false;
-}
-
-void FrameDifferenceBGS::saveConfig()
-{
- CvFileStorage* fs = cvOpenFileStorage("./config/FrameDifferenceBGS.xml", 0, CV_STORAGE_WRITE);
-
- cvWriteInt(fs, "enableThreshold", enableThreshold);
- cvWriteInt(fs, "threshold", threshold);
- cvWriteInt(fs, "showOutput", showOutput);
-
- cvReleaseFileStorage(&fs);
-}
-
-void FrameDifferenceBGS::loadConfig()
-{
- CvFileStorage* fs = cvOpenFileStorage("./config/FrameDifferenceBGS.xml", 0, CV_STORAGE_READ);
-
- enableThreshold = cvReadIntByName(fs, 0, "enableThreshold", true);
- threshold = cvReadIntByName(fs, 0, "threshold", 15);
- showOutput = cvReadIntByName(fs, 0, "showOutput", true);
-
- cvReleaseFileStorage(&fs);
-}
\ No newline at end of file
diff --git a/package_bgs/tb/FuzzyChoquetIntegral.cpp b/package_bgs/FuzzyChoquetIntegral.cpp
similarity index 62%
rename from package_bgs/tb/FuzzyChoquetIntegral.cpp
rename to package_bgs/FuzzyChoquetIntegral.cpp
index c97e174..3d24126 100644
--- a/package_bgs/tb/FuzzyChoquetIntegral.cpp
+++ b/package_bgs/FuzzyChoquetIntegral.cpp
@@ -15,12 +15,15 @@ You should have received a copy of the GNU General Public License
along with BGSLibrary. If not, see .
*/
#include "FuzzyChoquetIntegral.h"
-#include
-FuzzyChoquetIntegral::FuzzyChoquetIntegral() : firstTime(true), frameNumber(0), showOutput(true),
- framesToLearn(10), alphaLearn(0.1), alphaUpdate(0.01), colorSpace(1), option(2), smooth(true), threshold(0.67)
+using namespace bgslibrary::algorithms;
+
+FuzzyChoquetIntegral::FuzzyChoquetIntegral() :
+ frameNumber(0), framesToLearn(10), alphaLearn(0.1), alphaUpdate(0.01),
+ colorSpace(1), option(2), smooth(true), threshold(0.67)
{
std::cout << "FuzzyChoquetIntegral()" << std::endl;
+ setup("./config/FuzzyChoquetIntegral.xml");
}
FuzzyChoquetIntegral::~FuzzyChoquetIntegral()
@@ -30,48 +33,52 @@ FuzzyChoquetIntegral::~FuzzyChoquetIntegral()
void FuzzyChoquetIntegral::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
{
- if(img_input.empty())
- return;
+ init(img_input, img_output, img_bgmodel);
cv::Mat img_input_f3(img_input.size(), CV_32F);
- img_input.convertTo(img_input_f3, CV_32F, 1./255.);
-
- loadConfig();
+ img_input.convertTo(img_input_f3, CV_32F, 1. / 255.);
- if(firstTime)
+ if (firstTime)
{
std::cout << "FuzzyChoquetIntegral parameters:" << std::endl;
-
+
std::string colorSpaceName = "";
- switch(colorSpace)
+ switch (colorSpace)
{
- case 1: colorSpaceName = "RGB"; break;
- case 2: colorSpaceName = "OHTA"; break;
- case 3: colorSpaceName = "HSV"; break;
- case 4: colorSpaceName = "YCrCb"; break;
+ case 1: colorSpaceName = "RGB"; break;
+ case 2: colorSpaceName = "OHTA"; break;
+ case 3: colorSpaceName = "HSV"; break;
+ case 4: colorSpaceName = "YCrCb"; break;
}
std::cout << "Color space: " << colorSpaceName << std::endl;
- if(option == 1)
+ if (option == 1)
std::cout << "Fuzzing by 3 color components" << std::endl;
- if(option == 2)
+ if (option == 2)
std::cout << "Fuzzing by 2 color components + 1 texture component" << std::endl;
-
- saveConfig();
}
- if(frameNumber <= framesToLearn)
+ if (frameNumber <= framesToLearn)
{
- if(frameNumber == 0)
+ if (frameNumber == 0)
std::cout << "FuzzyChoquetIntegral initializing background model by adaptive learning..." << std::endl;
- if(img_background_f3.empty())
+ if (img_background_f3.empty())
img_input_f3.copyTo(img_background_f3);
else
- img_background_f3 = alphaLearn*img_input_f3 + (1-alphaLearn)*img_background_f3;
+ img_background_f3 = alphaLearn*img_input_f3 + (1 - alphaLearn)*img_background_f3;
+
+ double minVal = 0., maxVal = 1.;
+ img_background_f3.convertTo(img_background, CV_8U, 255.0 / (maxVal - minVal), -minVal);
+ img_background.copyTo(img_bgmodel);
+
+ img_foreground = cv::Mat::zeros(img_input.size(), img_input.type());
+ img_foreground.copyTo(img_output);
- if(showOutput)
- cv::imshow("CI BG Model", img_background_f3);
+#ifndef MEX_COMPILE_FLAG
+ if (showOutput)
+ cv::imshow("CI BG Model", img_background);
+#endif
}
else
{
@@ -87,72 +94,74 @@ void FuzzyChoquetIntegral::process(const cv::Mat &img_input, cv::Mat &img_output
IplImage* background_f1 = new IplImage(img_background_f1);
IplImage* lbp_input_f1 = cvCreateImage(cvSize(input_f1->width, input_f1->height), IPL_DEPTH_32F, 1);
- cvFillImage(lbp_input_f1, 0.0);
+ cvSetZero(lbp_input_f1);
fu.LBP(input_f1, lbp_input_f1);
- IplImage* lbp_background_f1 = cvCreateImage(cvSize(background_f1->width, background_f1->height), IPL_DEPTH_32F , 1);
- cvFillImage(lbp_background_f1, 0.0);
+ IplImage* lbp_background_f1 = cvCreateImage(cvSize(background_f1->width, background_f1->height), IPL_DEPTH_32F, 1);
+ cvSetZero(lbp_background_f1);
fu.LBP(background_f1, lbp_background_f1);
IplImage* sim_texture_f1 = cvCreateImage(cvSize(input_f1->width, input_f1->height), IPL_DEPTH_32F, 1);
fu.SimilarityDegreesImage(lbp_input_f1, lbp_background_f1, sim_texture_f1, 1, colorSpace);
IplImage* sim_color_f3 = cvCreateImage(cvSize(input_f3->width, input_f3->height), IPL_DEPTH_32F, 3);
- fu.SimilarityDegreesImage(input_f3, background_f3, sim_color_f3, 3, colorSpace);
+ fu.SimilarityDegreesImage(input_f3, background_f3, sim_color_f3, 3, colorSpace);
- float* measureG = (float*) malloc(3*(sizeof(float)));
+ float* measureG = (float*)malloc(3 * (sizeof(float)));
IplImage* integral_choquet_f1 = cvCreateImage(cvSize(input_f1->width, input_f1->height), IPL_DEPTH_32F, 1);
// 3 color components
- if(option == 1)
+ if (option == 1)
{
fu.FuzzyMeasureG(0.4f, 0.3f, 0.3f, measureG);
fu.getFuzzyIntegralChoquet(sim_texture_f1, sim_color_f3, option, measureG, integral_choquet_f1);
}
// 2 color components + 1 texture component
- if(option == 2)
+ if (option == 2)
{
fu.FuzzyMeasureG(0.6f, 0.3f, 0.1f, measureG);
fu.getFuzzyIntegralChoquet(sim_texture_f1, sim_color_f3, option, measureG, integral_choquet_f1);
}
free(measureG);
- cv::Mat img_integral_choquet_f1(integral_choquet_f1);
+ cv::Mat img_integral_choquet_f1 = cv::cvarrToMat(integral_choquet_f1);
- if(smooth)
+ if (smooth)
cv::medianBlur(img_integral_choquet_f1, img_integral_choquet_f1, 3);
cv::Mat img_foreground_f1(img_input.size(), CV_32F);
cv::threshold(img_integral_choquet_f1, img_foreground_f1, threshold, 255, cv::THRESH_BINARY_INV);
- cv::Mat img_foreground_u1(img_input.size(), CV_8U);
+ //cv::Mat img_foreground_u1(img_input.size(), CV_8U);
double minVal = 0., maxVal = 1.;
- img_foreground_f1.convertTo(img_foreground_u1, CV_8U, 255.0/(maxVal - minVal), -minVal);
- img_foreground_u1.copyTo(img_output);
+ img_foreground_f1.convertTo(img_foreground, CV_8U, 255.0 / (maxVal - minVal), -minVal);
+ img_foreground.copyTo(img_output);
- cv::Mat img_background_u3(img_input.size(), CV_8U);
+ //cv::Mat img_background_u3(img_input.size(), CV_8U);
//double minVal = 0., maxVal = 1.;
- img_background_f3.convertTo(img_background_u3, CV_8U, 255.0/(maxVal - minVal), -minVal);
- img_background_u3.copyTo(img_bgmodel);
+ img_background_f3.convertTo(img_background, CV_8U, 255.0 / (maxVal - minVal), -minVal);
+ img_background.copyTo(img_bgmodel);
- if(showOutput)
+#ifndef MEX_COMPILE_FLAG
+ if (showOutput)
{
cvShowImage("CI LBP Input", lbp_input_f1);
cvShowImage("CI LBP Background", lbp_background_f1);
cvShowImage("CI Prob FG Mask", integral_choquet_f1);
- cv::imshow("CI BG Model", img_background_f3);
- cv::imshow("CI FG Mask", img_foreground_u1);
+ cv::imshow("CI BG Model", img_background);
+ cv::imshow("CI FG Mask", img_foreground);
}
+#endif
- if(frameNumber == (framesToLearn + 1))
+ if (frameNumber == (framesToLearn + 1))
std::cout << "FuzzyChoquetIntegral updating background model by adaptive-selective learning..." << std::endl;
IplImage* updated_background_f3 = cvCreateImage(cvSize(input_f1->width, input_f1->height), IPL_DEPTH_32F, 3);
- cvFillImage(updated_background_f3, 0.0);
+ cvSetZero(updated_background_f3);
fu.AdaptativeSelectiveBackgroundModelUpdate(input_f3, background_f3, updated_background_f3, integral_choquet_f1, threshold, alphaUpdate);
- cv::Mat img_updated_background_f3(updated_background_f3);
+ cv::Mat img_updated_background_f3 = cv::cvarrToMat(updated_background_f3);
img_updated_background_f3.copyTo(img_background_f3);
cvReleaseImage(&lbp_input_f1);
@@ -161,7 +170,7 @@ void FuzzyChoquetIntegral::process(const cv::Mat &img_input, cv::Mat &img_output
cvReleaseImage(&sim_color_f3);
cvReleaseImage(&integral_choquet_f1);
cvReleaseImage(&updated_background_f3);
-
+
delete background_f1;
delete background_f3;
delete input_f1;
@@ -174,8 +183,8 @@ void FuzzyChoquetIntegral::process(const cv::Mat &img_input, cv::Mat &img_output
void FuzzyChoquetIntegral::saveConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/FuzzyChoquetIntegral.xml", 0, CV_STORAGE_WRITE);
-
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_WRITE);
+
cvWriteInt(fs, "showOutput", showOutput);
cvWriteInt(fs, "framesToLearn", framesToLearn);
cvWriteReal(fs, "alphaLearn", alphaLearn);
@@ -190,16 +199,16 @@ void FuzzyChoquetIntegral::saveConfig()
void FuzzyChoquetIntegral::loadConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/FuzzyChoquetIntegral.xml", 0, CV_STORAGE_READ);
-
- showOutput = cvReadIntByName(fs, 0, "showOutput", true);
- framesToLearn = cvReadIntByName(fs, 0, "framesToLearn", 10);
- alphaLearn = cvReadRealByName(fs, 0, "alphaLearn", 0.1);
- alphaUpdate = cvReadRealByName(fs, 0, "alphaUpdate", 0.01);
- colorSpace = cvReadIntByName(fs, 0, "colorSpace", 1);
- option = cvReadIntByName(fs, 0, "option", 2);
- smooth = cvReadIntByName(fs, 0, "smooth", true);
- threshold = cvReadRealByName(fs, 0, "threshold", 0.67);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_READ);
+
+ showOutput = cvReadIntByName(fs, nullptr, "showOutput", true);
+ framesToLearn = cvReadIntByName(fs, nullptr, "framesToLearn", 10);
+ alphaLearn = cvReadRealByName(fs, nullptr, "alphaLearn", 0.1);
+ alphaUpdate = cvReadRealByName(fs, nullptr, "alphaUpdate", 0.01);
+ colorSpace = cvReadIntByName(fs, nullptr, "colorSpace", 1);
+ option = cvReadIntByName(fs, nullptr, "option", 2);
+ smooth = cvReadIntByName(fs, nullptr, "smooth", true);
+ threshold = cvReadRealByName(fs, nullptr, "threshold", 0.67);
cvReleaseFileStorage(&fs);
}
diff --git a/package_bgs/FuzzyChoquetIntegral.h b/package_bgs/FuzzyChoquetIntegral.h
new file mode 100644
index 0000000..25681b0
--- /dev/null
+++ b/package_bgs/FuzzyChoquetIntegral.h
@@ -0,0 +1,53 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+#pragma once
+
+#include "IBGS.h"
+#include "T2F/FuzzyUtils.h"
+
+namespace bgslibrary
+{
+ namespace algorithms
+ {
+ class FuzzyChoquetIntegral : public IBGS
+ {
+ private:
+ long frameNumber;
+
+ int framesToLearn;
+ double alphaLearn;
+ double alphaUpdate;
+ int colorSpace;
+ int option;
+ bool smooth;
+ double threshold;
+
+ FuzzyUtils fu;
+ cv::Mat img_background_f3;
+
+ public:
+ FuzzyChoquetIntegral();
+ ~FuzzyChoquetIntegral();
+
+ void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
+
+ private:
+ void saveConfig();
+ void loadConfig();
+ };
+ }
+}
diff --git a/package_bgs/tb/FuzzySugenoIntegral.cpp b/package_bgs/FuzzySugenoIntegral.cpp
similarity index 62%
rename from package_bgs/tb/FuzzySugenoIntegral.cpp
rename to package_bgs/FuzzySugenoIntegral.cpp
index 859f14e..e62fa02 100644
--- a/package_bgs/tb/FuzzySugenoIntegral.cpp
+++ b/package_bgs/FuzzySugenoIntegral.cpp
@@ -15,12 +15,15 @@ You should have received a copy of the GNU General Public License
along with BGSLibrary. If not, see .
*/
#include "FuzzySugenoIntegral.h"
-#include
-FuzzySugenoIntegral::FuzzySugenoIntegral() : firstTime(true), frameNumber(0), showOutput(true),
- framesToLearn(10), alphaLearn(0.1), alphaUpdate(0.01), colorSpace(1), option(2), smooth(true), threshold(0.67)
+using namespace bgslibrary::algorithms;
+
+FuzzySugenoIntegral::FuzzySugenoIntegral() :
+ frameNumber(0), framesToLearn(10), alphaLearn(0.1), alphaUpdate(0.01),
+ colorSpace(1), option(2), smooth(true), threshold(0.67)
{
std::cout << "FuzzySugenoIntegral()" << std::endl;
+ setup("./config/FuzzySugenoIntegral.xml");
}
FuzzySugenoIntegral::~FuzzySugenoIntegral()
@@ -30,48 +33,52 @@ FuzzySugenoIntegral::~FuzzySugenoIntegral()
void FuzzySugenoIntegral::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
{
- if(img_input.empty())
- return;
+ init(img_input, img_output, img_bgmodel);
cv::Mat img_input_f3(img_input.size(), CV_32F);
- img_input.convertTo(img_input_f3, CV_32F, 1./255.);
-
- loadConfig();
+ img_input.convertTo(img_input_f3, CV_32F, 1. / 255.);
- if(firstTime)
+ if (firstTime)
{
std::cout << "FuzzySugenoIntegral parameters:" << std::endl;
-
+
std::string colorSpaceName = "";
- switch(colorSpace)
+ switch (colorSpace)
{
- case 1: colorSpaceName = "RGB"; break;
- case 2: colorSpaceName = "OHTA"; break;
- case 3: colorSpaceName = "HSV"; break;
- case 4: colorSpaceName = "YCrCb"; break;
+ case 1: colorSpaceName = "RGB"; break;
+ case 2: colorSpaceName = "OHTA"; break;
+ case 3: colorSpaceName = "HSV"; break;
+ case 4: colorSpaceName = "YCrCb"; break;
}
std::cout << "Color space: " << colorSpaceName << std::endl;
- if(option == 1)
+ if (option == 1)
std::cout << "Fuzzing by 3 color components" << std::endl;
- if(option == 2)
+ if (option == 2)
std::cout << "Fuzzing by 2 color components + 1 texture component" << std::endl;
-
- saveConfig();
}
- if(frameNumber <= framesToLearn)
+ if (frameNumber <= framesToLearn)
{
- if(frameNumber == 0)
+ if (frameNumber == 0)
std::cout << "FuzzySugenoIntegral initializing background model by adaptive learning..." << std::endl;
- if(img_background_f3.empty())
+ if (img_background_f3.empty())
img_input_f3.copyTo(img_background_f3);
else
- img_background_f3 = alphaLearn*img_input_f3 + (1-alphaLearn)*img_background_f3;
+ img_background_f3 = alphaLearn*img_input_f3 + (1 - alphaLearn)*img_background_f3;
+
+ double minVal = 0., maxVal = 1.;
+ img_background_f3.convertTo(img_background, CV_8U, 255.0 / (maxVal - minVal), -minVal);
+ img_background.copyTo(img_bgmodel);
+
+ img_foreground = cv::Mat::zeros(img_input.size(), img_input.type());
+ img_foreground.copyTo(img_output);
- if(showOutput)
- cv::imshow("SI BG Model", img_background_f3);
+#ifndef MEX_COMPILE_FLAG
+ if (showOutput)
+ cv::imshow("SI BG Model", img_background);
+#endif
}
else
{
@@ -87,72 +94,74 @@ void FuzzySugenoIntegral::process(const cv::Mat &img_input, cv::Mat &img_output,
IplImage* background_f1 = new IplImage(img_background_f1);
IplImage* lbp_input_f1 = cvCreateImage(cvSize(input_f1->width, input_f1->height), IPL_DEPTH_32F, 1);
- cvFillImage(lbp_input_f1, 0.0);
+ cvSetZero(lbp_input_f1);
fu.LBP(input_f1, lbp_input_f1);
- IplImage* lbp_background_f1 = cvCreateImage(cvSize(background_f1->width, background_f1->height), IPL_DEPTH_32F , 1);
- cvFillImage(lbp_background_f1, 0.0);
+ IplImage* lbp_background_f1 = cvCreateImage(cvSize(background_f1->width, background_f1->height), IPL_DEPTH_32F, 1);
+ cvSetZero(lbp_background_f1);
fu.LBP(background_f1, lbp_background_f1);
IplImage* sim_texture_f1 = cvCreateImage(cvSize(input_f1->width, input_f1->height), IPL_DEPTH_32F, 1);
fu.SimilarityDegreesImage(lbp_input_f1, lbp_background_f1, sim_texture_f1, 1, colorSpace);
IplImage* sim_color_f3 = cvCreateImage(cvSize(input_f3->width, input_f3->height), IPL_DEPTH_32F, 3);
- fu.SimilarityDegreesImage(input_f3, background_f3, sim_color_f3, 3, colorSpace);
+ fu.SimilarityDegreesImage(input_f3, background_f3, sim_color_f3, 3, colorSpace);
- float* measureG = (float*) malloc(3*(sizeof(float)));
+ float* measureG = (float*)malloc(3 * (sizeof(float)));
IplImage* integral_sugeno_f1 = cvCreateImage(cvSize(input_f1->width, input_f1->height), IPL_DEPTH_32F, 1);
// 3 color components
- if(option == 1)
+ if (option == 1)
{
fu.FuzzyMeasureG(0.4f, 0.3f, 0.3f, measureG);
fu.getFuzzyIntegralSugeno(sim_texture_f1, sim_color_f3, option, measureG, integral_sugeno_f1);
}
// 2 color components + 1 texture component
- if(option == 2)
+ if (option == 2)
{
fu.FuzzyMeasureG(0.6f, 0.3f, 0.1f, measureG);
fu.getFuzzyIntegralSugeno(sim_texture_f1, sim_color_f3, option, measureG, integral_sugeno_f1);
}
free(measureG);
- cv::Mat img_integral_sugeno_f1(integral_sugeno_f1);
+ cv::Mat img_integral_sugeno_f1 = cv::cvarrToMat(integral_sugeno_f1);
- if(smooth)
+ if (smooth)
cv::medianBlur(img_integral_sugeno_f1, img_integral_sugeno_f1, 3);
cv::Mat img_foreground_f1(img_input.size(), CV_32F);
cv::threshold(img_integral_sugeno_f1, img_foreground_f1, threshold, 255, cv::THRESH_BINARY_INV);
- cv::Mat img_foreground_u1(img_input.size(), CV_8U);
+ //cv::Mat img_foreground_u1(img_input.size(), CV_8U);
double minVal = 0., maxVal = 1.;
- img_foreground_f1.convertTo(img_foreground_u1, CV_8U, 255.0/(maxVal - minVal), -minVal);
- img_foreground_u1.copyTo(img_output);
-
- cv::Mat img_background_u3(img_input.size(), CV_8U);
+ img_foreground_f1.convertTo(img_foreground, CV_8U, 255.0 / (maxVal - minVal), -minVal);
+ img_foreground.copyTo(img_output);
+
+ //cv::Mat img_background_u3(img_input.size(), CV_8U);
//double minVal = 0., maxVal = 1.;
- img_background_f3.convertTo(img_background_u3, CV_8U, 255.0/(maxVal - minVal), -minVal);
- img_background_u3.copyTo(img_bgmodel);
+ img_background_f3.convertTo(img_background, CV_8U, 255.0 / (maxVal - minVal), -minVal);
+ img_background.copyTo(img_bgmodel);
- if(showOutput)
+#ifndef MEX_COMPILE_FLAG
+ if (showOutput)
{
cvShowImage("SI LBP Input", lbp_input_f1);
cvShowImage("SI LBP Background", lbp_background_f1);
cvShowImage("SI Prob FG Mask", integral_sugeno_f1);
- cv::imshow("SI BG Model", img_background_f3);
- cv::imshow("SI FG Mask", img_foreground_u1);
+ cv::imshow("SI BG Model", img_background);
+ cv::imshow("SI FG Mask", img_foreground);
}
+#endif
- if(frameNumber == (framesToLearn + 1))
+ if (frameNumber == (framesToLearn + 1))
std::cout << "FuzzySugenoIntegral updating background model by adaptive-selective learning..." << std::endl;
IplImage* updated_background_f3 = cvCreateImage(cvSize(input_f1->width, input_f1->height), IPL_DEPTH_32F, 3);
- cvFillImage(updated_background_f3, 0.0);
+ cvSetZero(updated_background_f3);
fu.AdaptativeSelectiveBackgroundModelUpdate(input_f3, background_f3, updated_background_f3, integral_sugeno_f1, threshold, alphaUpdate);
- cv::Mat img_updated_background_f3(updated_background_f3);
+ cv::Mat img_updated_background_f3 = cv::cvarrToMat(updated_background_f3);
img_updated_background_f3.copyTo(img_background_f3);
cvReleaseImage(&lbp_input_f1);
@@ -161,7 +170,7 @@ void FuzzySugenoIntegral::process(const cv::Mat &img_input, cv::Mat &img_output,
cvReleaseImage(&sim_color_f3);
cvReleaseImage(&integral_sugeno_f1);
cvReleaseImage(&updated_background_f3);
-
+
delete background_f1;
delete background_f3;
delete input_f1;
@@ -174,8 +183,8 @@ void FuzzySugenoIntegral::process(const cv::Mat &img_input, cv::Mat &img_output,
void FuzzySugenoIntegral::saveConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/FuzzySugenoIntegral.xml", 0, CV_STORAGE_WRITE);
-
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_WRITE);
+
cvWriteInt(fs, "showOutput", showOutput);
cvWriteInt(fs, "framesToLearn", framesToLearn);
cvWriteReal(fs, "alphaLearn", alphaLearn);
@@ -184,22 +193,22 @@ void FuzzySugenoIntegral::saveConfig()
cvWriteInt(fs, "option", option);
cvWriteInt(fs, "smooth", smooth);
cvWriteReal(fs, "threshold", threshold);
-
+
cvReleaseFileStorage(&fs);
}
void FuzzySugenoIntegral::loadConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/FuzzySugenoIntegral.xml", 0, CV_STORAGE_READ);
-
- showOutput = cvReadIntByName(fs, 0, "showOutput", true);
- framesToLearn = cvReadIntByName(fs, 0, "framesToLearn", 10);
- alphaLearn = cvReadRealByName(fs, 0, "alphaLearn", 0.1);
- alphaUpdate = cvReadRealByName(fs, 0, "alphaUpdate", 0.01);
- colorSpace = cvReadIntByName(fs, 0, "colorSpace", 1);
- option = cvReadIntByName(fs, 0, "option", 2);
- smooth = cvReadIntByName(fs, 0, "smooth", true);
- threshold = cvReadRealByName(fs, 0, "threshold", 0.67);
-
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_READ);
+
+ showOutput = cvReadIntByName(fs, nullptr, "showOutput", true);
+ framesToLearn = cvReadIntByName(fs, nullptr, "framesToLearn", 10);
+ alphaLearn = cvReadRealByName(fs, nullptr, "alphaLearn", 0.1);
+ alphaUpdate = cvReadRealByName(fs, nullptr, "alphaUpdate", 0.01);
+ colorSpace = cvReadIntByName(fs, nullptr, "colorSpace", 1);
+ option = cvReadIntByName(fs, nullptr, "option", 2);
+ smooth = cvReadIntByName(fs, nullptr, "smooth", true);
+ threshold = cvReadRealByName(fs, nullptr, "threshold", 0.67);
+
cvReleaseFileStorage(&fs);
}
diff --git a/package_bgs/FuzzySugenoIntegral.h b/package_bgs/FuzzySugenoIntegral.h
new file mode 100644
index 0000000..70bde15
--- /dev/null
+++ b/package_bgs/FuzzySugenoIntegral.h
@@ -0,0 +1,53 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+#pragma once
+
+#include "IBGS.h"
+#include "T2F/FuzzyUtils.h"
+
+namespace bgslibrary
+{
+ namespace algorithms
+ {
+ class FuzzySugenoIntegral : public IBGS
+ {
+ private:
+ long long frameNumber;
+
+ int framesToLearn;
+ double alphaLearn;
+ double alphaUpdate;
+ int colorSpace;
+ int option;
+ bool smooth;
+ double threshold;
+
+ FuzzyUtils fu;
+ cv::Mat img_background_f3;
+
+ public:
+ FuzzySugenoIntegral();
+ ~FuzzySugenoIntegral();
+
+ void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
+
+ private:
+ void saveConfig();
+ void loadConfig();
+ };
+ }
+}
diff --git a/package_bgs/GMG.cpp b/package_bgs/GMG.cpp
index 675b23c..19bd8ab 100644
--- a/package_bgs/GMG.cpp
+++ b/package_bgs/GMG.cpp
@@ -16,9 +16,14 @@ along with BGSLibrary. If not, see .
*/
#include "GMG.h"
-GMG::GMG() : firstTime(true), initializationFrames(20), decisionThreshold(0.7), showOutput(true)
+#if CV_MAJOR_VERSION == 2
+
+using namespace bgslibrary::algorithms;
+
+GMG::GMG() : initializationFrames(20), decisionThreshold(0.7)
{
std::cout << "GMG()" << std::endl;
+ setup("./config/GMG.xml");
cv::initModule_video();
cv::setUseOptimized(true);
@@ -34,41 +39,33 @@ GMG::~GMG()
void GMG::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
{
- if(img_input.empty())
- return;
+ init(img_input, img_output, img_bgmodel);
- loadConfig();
-
- if(firstTime)
+ if (firstTime)
{
fgbg->set("initializationFrames", initializationFrames);
fgbg->set("decisionThreshold", decisionThreshold);
-
- saveConfig();
}
-
- if(fgbg.empty())
+
+ if (fgbg.empty())
{
std::cerr << "Failed to create BackgroundSubtractor.GMG Algorithm." << std::endl;
return;
}
(*fgbg)(img_input, img_foreground);
-
- cv::Mat img_background;
(*fgbg).getBackgroundImage(img_background);
img_input.copyTo(img_segmentation);
cv::add(img_input, cv::Scalar(100, 100, 0), img_segmentation, img_foreground);
- if(showOutput)
+#ifndef MEX_COMPILE_FLAG
+ if (showOutput)
{
- if (!img_foreground.empty())
- cv::imshow("GMG FG (Godbehere-Matsukawa-Goldberg)", img_foreground);
-
- if (!img_background.empty())
- cv::imshow("GMG BG (Godbehere-Matsukawa-Goldberg)", img_background);
+ cv::imshow("GMG FG (Godbehere-Matsukawa-Goldberg)", img_foreground);
+ cv::imshow("GMG BG (Godbehere-Matsukawa-Goldberg)", img_background);
}
+#endif
img_foreground.copyTo(img_output);
img_background.copyTo(img_bgmodel);
@@ -78,7 +75,7 @@ void GMG::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bg
void GMG::saveConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/GMG.xml", 0, CV_STORAGE_WRITE);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_WRITE);
cvWriteInt(fs, "initializationFrames", initializationFrames);
cvWriteReal(fs, "decisionThreshold", decisionThreshold);
@@ -89,11 +86,13 @@ void GMG::saveConfig()
void GMG::loadConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/GMG.xml", 0, CV_STORAGE_READ);
-
- initializationFrames = cvReadIntByName(fs, 0, "initializationFrames", 20);
- decisionThreshold = cvReadRealByName(fs, 0, "decisionThreshold", 0.7);
- showOutput = cvReadIntByName(fs, 0, "showOutput", true);
-
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_READ);
+
+ initializationFrames = cvReadIntByName(fs, nullptr, "initializationFrames", 20);
+ decisionThreshold = cvReadRealByName(fs, nullptr, "decisionThreshold", 0.7);
+ showOutput = cvReadIntByName(fs, nullptr, "showOutput", true);
+
cvReleaseFileStorage(&fs);
}
+
+#endif
diff --git a/package_bgs/GMG.h b/package_bgs/GMG.h
index 9da28ad..1b4af30 100644
--- a/package_bgs/GMG.h
+++ b/package_bgs/GMG.h
@@ -16,30 +16,34 @@ along with BGSLibrary. If not, see .
*/
#pragma once
-#include
-#include
+#include "opencv2/core/version.hpp"
+#if CV_MAJOR_VERSION == 2
#include "IBGS.h"
-class GMG : public IBGS
+namespace bgslibrary
{
-private:
- bool firstTime;
- cv::Ptr fgbg;
- int initializationFrames;
- double decisionThreshold;
- cv::Mat img_foreground;
- cv::Mat img_segmentation;
- bool showOutput;
-
-public:
- GMG();
- ~GMG();
-
- void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
-
-private:
- void saveConfig();
- void loadConfig();
-};
-
+ namespace algorithms
+ {
+ class GMG : public IBGS
+ {
+ private:
+ cv::Ptr fgbg;
+ int initializationFrames;
+ double decisionThreshold;
+ cv::Mat img_segmentation;
+
+ public:
+ GMG();
+ ~GMG();
+
+ void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
+
+ private:
+ void saveConfig();
+ void loadConfig();
+ };
+ }
+}
+
+#endif
diff --git a/package_bgs/IBGS.h b/package_bgs/IBGS.h
index 073ce18..718bf51 100644
--- a/package_bgs/IBGS.h
+++ b/package_bgs/IBGS.h
@@ -16,18 +16,59 @@ along with BGSLibrary. If not, see .
*/
#pragma once
+#include
+#include
#include
-class IBGS
+namespace bgslibrary
{
-public:
- virtual void process(const cv::Mat &img_input, cv::Mat &img_foreground, cv::Mat &img_background) = 0;
- /*virtual void process(const cv::Mat &img_input, cv::Mat &img_foreground){
- process(img_input, img_foreground, cv::Mat());
- }*/
- virtual ~IBGS(){}
+ namespace algorithms
+ {
+ class IBGS
+ {
+ public:
+ void setShowOutput(const bool _showOutput) {
+ showOutput = _showOutput;
+ }
+ cv::Mat apply(const cv::Mat &img_input) {
+ setShowOutput(false);
+ cv::Mat _img_foreground;
+ cv::Mat _img_background;
+ process(img_input, _img_foreground, _img_background);
+ _img_background.copyTo(img_background);
+ return _img_foreground;
+ }
+ cv::Mat getBackgroundModel() {
+ return img_background;
+ }
+ virtual void process(const cv::Mat &img_input, cv::Mat &img_foreground, cv::Mat &img_background) = 0;
+ virtual ~IBGS() {}
-private:
- virtual void saveConfig() = 0;
- virtual void loadConfig() = 0;
-};
+ protected:
+ bool firstTime = true;
+ bool showOutput = true;
+ cv::Mat img_background;
+ cv::Mat img_foreground;
+ std::string config_xml;
+ void setup(const std::string _config_xml) {
+ config_xml = _config_xml;
+ if (!config_xml.empty()) {
+ if (!std::ifstream(config_xml))
+ saveConfig();
+ loadConfig();
+ }
+ }
+ void init(const cv::Mat &img_input, cv::Mat &img_outfg, cv::Mat &img_outbg) {
+ assert(img_input.empty() == false);
+ //img_outfg = cv::Mat::zeros(img_input.size(), img_input.type());
+ //img_outbg = cv::Mat::zeros(img_input.size(), img_input.type());
+ img_outfg = cv::Mat::zeros(img_input.size(), CV_8UC1);
+ img_outbg = cv::Mat::zeros(img_input.size(), CV_8UC3);
+ }
+
+ private:
+ virtual void saveConfig() = 0;
+ virtual void loadConfig() = 0;
+ };
+ }
+}
diff --git a/package_bgs/db/imbs.cpp b/package_bgs/IMBS/IMBS.cpp
similarity index 74%
rename from package_bgs/db/imbs.cpp
rename to package_bgs/IMBS/IMBS.cpp
index f5fc0d0..b1e177b 100644
--- a/package_bgs/db/imbs.cpp
+++ b/package_bgs/IMBS/IMBS.cpp
@@ -1,5 +1,21 @@
/*
-* IMBS Background Subtraction Library
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+/*
+* IMBS Background Subtraction Library
*
* This file imbs.hpp contains the C++ OpenCV based implementation for
* IMBS algorithm described in
@@ -8,8 +24,8 @@
* In Proc. of the Third Int. Conf. on Computational Modeling of Objects
* Presented in Images: Fundamentals, Methods and Applications, pp. 39-44, 2012.
* Please, cite the above paper if you use IMBS.
-*
-* This software is provided without any warranty about its usability.
+*
+* This software is provided without any warranty about its usability.
* It is for educational purposes and should be regarded as such.
*
* Written by Domenico D. Bloisi
@@ -19,7 +35,7 @@
*
*/
-#include "imbs.hpp"
+#include "IMBS.hpp"
using namespace std;
using namespace cv;
@@ -29,15 +45,15 @@ BackgroundSubtractorIMBS::BackgroundSubtractorIMBS()
fps = 0.;
fgThreshold = 15;
associationThreshold = 5;
- samplingPeriod = 250.;//500.ms
+ samplingPeriod = 250;//500.ms
minBinHeight = 2;
numSamples = 10; //30
alpha = 0.65f;
beta = 1.15f;
- tau_s = 60.;
- tau_h = 40.;
+ tau_s = 60;
+ tau_h = 40;
minArea = 30.;
- persistencePeriod = samplingPeriod*numSamples/3.;//ms
+ persistencePeriod = samplingPeriod*numSamples / 3.;//ms
initial_tick_count = (double)getTickCount();
@@ -63,7 +79,7 @@ BackgroundSubtractorIMBS::BackgroundSubtractorIMBS(
this->fps = fps;
this->fgThreshold = fgThreshold;
this->persistencePeriod = persistencePeriod;
- if(minBinHeight <= 1){
+ if (minBinHeight <= 1) {
this->minBinHeight = 1;
}
else {
@@ -79,7 +95,7 @@ BackgroundSubtractorIMBS::BackgroundSubtractorIMBS(
this->tau_h = tau_h;
this->minArea = minArea;
- if(fps == 0.)
+ if (fps == 0.)
initial_tick_count = (double)getTickCount();
else
initial_tick_count = 0;
@@ -106,7 +122,7 @@ void BackgroundSubtractorIMBS::initialize(Size frameSize, int frameType)
this->numPixels = frameSize.width*frameSize.height;
persistenceMap = new unsigned int[numPixels];
- for(unsigned int i = 0; i < numPixels; i++) {
+ for (unsigned int i = 0; i < numPixels; i++) {
persistenceMap[i] = 0;
}
@@ -134,20 +150,20 @@ void BackgroundSubtractorIMBS::initialize(Size frameSize, int frameType)
//initial message to be shown until the first fg mask is computed
initialMsgGray = Mat::zeros(frameSize, CV_8UC1);
- putText(initialMsgGray, "Creating", Point(10,20), FONT_HERSHEY_SIMPLEX, 0.4, CV_RGB(255, 255, 255));
- putText(initialMsgGray, "initial", Point(10,40), FONT_HERSHEY_SIMPLEX, 0.4, CV_RGB(255, 255, 255));
- putText(initialMsgGray, "background...", Point(10,60), FONT_HERSHEY_SIMPLEX, 0.4, CV_RGB(255, 255, 255));
+ putText(initialMsgGray, "Creating", Point(10, 20), FONT_HERSHEY_SIMPLEX, 0.4, CV_RGB(255, 255, 255));
+ putText(initialMsgGray, "initial", Point(10, 40), FONT_HERSHEY_SIMPLEX, 0.4, CV_RGB(255, 255, 255));
+ putText(initialMsgGray, "background...", Point(10, 60), FONT_HERSHEY_SIMPLEX, 0.4, CV_RGB(255, 255, 255));
initialMsgRGB = Mat::zeros(frameSize, CV_8UC3);
- putText(initialMsgRGB, "Creating", Point(10,20), FONT_HERSHEY_SIMPLEX, 0.4, CV_RGB(255, 255, 255));
- putText(initialMsgRGB, "initial", Point(10,40), FONT_HERSHEY_SIMPLEX, 0.4, CV_RGB(255, 255, 255));
- putText(initialMsgRGB, "background...", Point(10,60), FONT_HERSHEY_SIMPLEX, 0.4, CV_RGB(255, 255, 255));
+ putText(initialMsgRGB, "Creating", Point(10, 20), FONT_HERSHEY_SIMPLEX, 0.4, CV_RGB(255, 255, 255));
+ putText(initialMsgRGB, "initial", Point(10, 40), FONT_HERSHEY_SIMPLEX, 0.4, CV_RGB(255, 255, 255));
+ putText(initialMsgRGB, "background...", Point(10, 60), FONT_HERSHEY_SIMPLEX, 0.4, CV_RGB(255, 255, 255));
- if(minBinHeight <= 1){
+ if (minBinHeight <= 1) {
minBinHeight = 1;
}
- for(unsigned int p = 0; p < numPixels; ++p)
+ for (unsigned int p = 0; p < numPixels; ++p)
{
bgBins[p].binValues = new Vec3b[numSamples];
bgBins[p].binHeights = new uchar[numSamples];
@@ -169,7 +185,7 @@ void BackgroundSubtractorIMBS::apply(InputArray _frame, OutputArray _fgmask, dou
CV_Assert(frame.channels() == 3);
bool needToInitialize = nframes == 0 || frame.type() != frameType;
- if( needToInitialize ) {
+ if (needToInitialize) {
initialize(frame.size(), frame.type());
}
@@ -179,29 +195,29 @@ void BackgroundSubtractorIMBS::apply(InputArray _frame, OutputArray _fgmask, dou
//get current time
prev_timestamp = timestamp;
- if(fps == 0.) {
+ if (fps == 0.) {
timestamp = getTimestamp();//ms
}
else {
- timestamp += 1000./fps;//ms
+ timestamp += 1000. / fps;//ms
}
//check for global changes
- if(sudden_change) {
+ if (sudden_change) {
changeBg();
}
//wait for the first model to be generated
- if(bgModel[0].isValid[0]) {
- getFg();
+ if (bgModel[0].isValid[0]) {
+ getFg();
hsvSuppression();
filterFg();
- }
+ }
//update the bg model
updateBg();
//show an initial message if the first bg is not yet ready
- if(!bgModel[0].isValid[0]) {
+ if (!bgModel[0].isValid[0]) {
initialMsgGray.copyTo(fgmask);
initialMsgRGB.copyTo(bgImage);
}
@@ -209,23 +225,23 @@ void BackgroundSubtractorIMBS::apply(InputArray _frame, OutputArray _fgmask, dou
}
void BackgroundSubtractorIMBS::updateBg() {
- if(bg_reset) {
- if(bg_frame_counter > numSamples - 1) {
+ if (bg_reset) {
+ if (bg_frame_counter > numSamples - 1) {
bg_frame_counter = numSamples - 1;
}
}
- if(prev_bg_frame_time > timestamp) {
+ if (prev_bg_frame_time > timestamp) {
prev_bg_frame_time = timestamp;
}
- if(bg_frame_counter == numSamples - 1) {
+ if (bg_frame_counter == numSamples - 1) {
createBg(bg_frame_counter);
bg_frame_counter = 0;
}
else { //bg_frame_counter < (numSamples - 1)
- if((timestamp - prev_bg_frame_time) >= samplingPeriod)
+ if ((timestamp - prev_bg_frame_time) >= samplingPeriod)
{
//get a new sample for creating the bg model
prev_bg_frame_time = timestamp;
@@ -237,7 +253,7 @@ void BackgroundSubtractorIMBS::updateBg() {
}
double BackgroundSubtractorIMBS::getTimestamp() {
- return ((double)getTickCount() - initial_tick_count)*1000./getTickFrequency();
+ return ((double)getTickCount() - initial_tick_count)*1000. / getTickFrequency();
}
void BackgroundSubtractorIMBS::hsvSuppression() {
@@ -251,35 +267,35 @@ void BackgroundSubtractorIMBS::hsvSuppression() {
vector imHSV;
cv::split(convertImageRGBtoHSV(frame), imHSV);
- for(unsigned int p = 0; p < numPixels; ++p) {
- if(fgmask.data[p]) {
+ for (unsigned int p = 0; p < numPixels; ++p) {
+ if (fgmask.data[p]) {
h_i = imHSV[0].data[p];
s_i = imHSV[1].data[p];
v_i = imHSV[2].data[p];
- for(unsigned int n = 0; n < maxBgBins; ++n) {
- if(!bgModel[p].isValid[n]) {
+ for (unsigned int n = 0; n < maxBgBins; ++n) {
+ if (!bgModel[p].isValid[n]) {
break;
}
- if(bgModel[p].isFg[n]) {
+ if (bgModel[p].isFg[n]) {
continue;
}
- bgrPixel.at(0,0) = bgModel[p].values[n];
+ bgrPixel.at(0, 0) = bgModel[p].values[n];
cv::Mat hsvPixel = convertImageRGBtoHSV(bgrPixel);
- h_b = hsvPixel.at(0,0)[0];
- s_b = hsvPixel.at(0,0)[1];
- v_b = hsvPixel.at(0,0)[2];
+ h_b = hsvPixel.at(0, 0)[0];
+ s_b = hsvPixel.at(0, 0)[1];
+ v_b = hsvPixel.at(0, 0)[2];
v_ratio = (float)v_i / (float)v_b;
s_diff = std::abs(s_i - s_b);
- h_diff = std::min( std::abs(h_i - h_b), 255 - std::abs(h_i - h_b));
+ h_diff = std::min(std::abs(h_i - h_b), 255 - std::abs(h_i - h_b));
- if( h_diff <= tau_h &&
+ if (h_diff <= tau_h &&
s_diff <= tau_s &&
v_ratio >= alpha &&
v_ratio < beta)
@@ -293,7 +309,7 @@ void BackgroundSubtractorIMBS::hsvSuppression() {
}
void BackgroundSubtractorIMBS::createBg(unsigned int bg_sample_number) {
- if(!bgSample.data) {
+ if (!bgSample.data) {
//cerr << "createBg -- an error occurred: " <<
// " unable to retrieve frame no. " << bg_sample_number << endl;
@@ -305,18 +321,18 @@ void BackgroundSubtractorIMBS::createBg(unsigned int bg_sample_number) {
//split bgSample in channels
cv::split(bgSample, bgSampleBGR);
//create a statistical model for each pixel (a set of bins of variable size)
- for(unsigned int p = 0; p < numPixels; ++p) {
+ for (unsigned int p = 0; p < numPixels; ++p) {
//create an initial bin for each pixel from the first sample (bg_sample_number = 0)
- if(bg_sample_number == 0) {
- for(int k = 0; k < 3; ++k) {
+ if (bg_sample_number == 0) {
+ for (int k = 0; k < 3; ++k) {
bgBins[p].binValues[0][k] = bgSampleBGR[k].data[p];
}
bgBins[p].binHeights[0] = 1;
- for(unsigned int s = 1; s < numSamples; ++s) {
+ for (unsigned int s = 1; s < numSamples; ++s) {
bgBins[p].binHeights[s] = 0;
}
//if the sample pixel is from foreground keep track of that situation
- if(fgmask.data[p] == FOREGROUND_LABEL) {
+ if (fgmask.data[p] == FOREGROUND_LABEL) {
bgBins[p].isFg[0] = true;
}
else {
@@ -324,32 +340,32 @@ void BackgroundSubtractorIMBS::createBg(unsigned int bg_sample_number) {
}
}//if(bg_sample_number == 0)
else { //bg_sample_number > 0
- for(int k = 0; k < 3; ++k) {
+ for (int k = 0; k < 3; ++k) {
currentPixel[k] = bgSampleBGR[k].data[p];
}
int den = 0;
- for(unsigned int s = 0; s < bg_sample_number; ++s) {
+ for (unsigned int s = 0; s < bg_sample_number; ++s) {
//try to associate the current pixel values to an existing bin
- if( std::abs(currentPixel[2] - bgBins[p].binValues[s][2]) <= associationThreshold &&
+ if (std::abs(currentPixel[2] - bgBins[p].binValues[s][2]) <= associationThreshold &&
std::abs(currentPixel[1] - bgBins[p].binValues[s][1]) <= associationThreshold &&
- std::abs(currentPixel[0] - bgBins[p].binValues[s][0]) <= associationThreshold )
+ std::abs(currentPixel[0] - bgBins[p].binValues[s][0]) <= associationThreshold)
{
den = (bgBins[p].binHeights[s] + 1);
- for(int k = 0; k < 3; ++k) {
+ for (int k = 0; k < 3; ++k) {
bgBins[p].binValues[s][k] =
(bgBins[p].binValues[s][k] * bgBins[p].binHeights[s] + currentPixel[k]) / den;
}
bgBins[p].binHeights[s]++; //increment the height of the bin
- if(fgmask.data[p] == FOREGROUND_LABEL) {
+ if (fgmask.data[p] == FOREGROUND_LABEL) {
bgBins[p].isFg[s] = true;
}
break;
}
//if the association is not possible, create a new bin
- else if(bgBins[p].binHeights[s] == 0) {
+ else if (bgBins[p].binHeights[s] == 0) {
bgBins[p].binValues[s] = currentPixel;
bgBins[p].binHeights[s]++;
- if(fgmask.data[p] == FOREGROUND_LABEL) {
+ if (fgmask.data[p] == FOREGROUND_LABEL) {
bgBins[p].isFg[s] = true;
}
else {
@@ -362,44 +378,44 @@ void BackgroundSubtractorIMBS::createBg(unsigned int bg_sample_number) {
//if all samples have been processed
//it is time to compute the fg mask
- if(bg_sample_number == (numSamples - 1)) {
+ if (bg_sample_number == (numSamples - 1)) {
unsigned int index = 0;
int max_height = -1;
- for(unsigned int s = 0; s < numSamples; ++s){
- if(bgBins[p].binHeights[s] == 0) {
+ for (unsigned int s = 0; s < numSamples; ++s) {
+ if (bgBins[p].binHeights[s] == 0) {
bgModel[p].isValid[index] = false;
break;
}
- if(index == maxBgBins) {
+ if (index == maxBgBins) {
break;
}
- else if(bgBins[p].binHeights[s] >= minBinHeight) {
- if(fgmask.data[p] == PERSISTENCE_LABEL) {
- for(unsigned int n = 0; n < maxBgBins; n++) {
- if(!bgModel[p].isValid[n]) {
+ else if (bgBins[p].binHeights[s] >= minBinHeight) {
+ if (fgmask.data[p] == PERSISTENCE_LABEL) {
+ for (unsigned int n = 0; n < maxBgBins; n++) {
+ if (!bgModel[p].isValid[n]) {
break;
}
unsigned int d = std::max((int)std::abs(bgModel[p].values[n][0] - bgBins[p].binValues[s][0]),
- std::abs(bgModel[p].values[n][1] - bgBins[p].binValues[s][1]) );
- d = std::max((int)d, std::abs(bgModel[p].values[n][2] - bgBins[p].binValues[s][2]) );
- if(d < fgThreshold){
+ std::abs(bgModel[p].values[n][1] - bgBins[p].binValues[s][1]));
+ d = std::max((int)d, std::abs(bgModel[p].values[n][2] - bgBins[p].binValues[s][2]));
+ if (d < fgThreshold) {
bgModel[p].isFg[n] = false;
bgBins[p].isFg[s] = false;
}
}
}
- if(bgBins[p].binHeights[s] > max_height) {
+ if (bgBins[p].binHeights[s] > max_height) {
max_height = bgBins[p].binHeights[s];
- for(int k = 0; k < 3; ++k) {
+ for (int k = 0; k < 3; ++k) {
bgModel[p].values[index][k] = bgModel[p].values[0][k];
}
bgModel[p].isValid[index] = true;
bgModel[p].isFg[index] = bgModel[p].isFg[0];
bgModel[p].counter[index] = bgModel[p].counter[0];
- for(int k = 0; k < 3; ++k) {
+ for (int k = 0; k < 3; ++k) {
bgModel[p].values[0][k] = bgBins[p].binValues[s][k];
}
bgModel[p].isValid[0] = true;
@@ -407,7 +423,7 @@ void BackgroundSubtractorIMBS::createBg(unsigned int bg_sample_number) {
bgModel[p].counter[0] = bgBins[p].binHeights[s];
}
else {
- for(int k = 0; k < 3; ++k) {
+ for (int k = 0; k < 3; ++k) {
bgModel[p].values[index][k] = bgBins[p].binValues[s][k];
}
bgModel[p].isValid[index] = true;
@@ -421,25 +437,25 @@ void BackgroundSubtractorIMBS::createBg(unsigned int bg_sample_number) {
}//else --> if(frame_number == 0)
}//numPixels
- if(bg_sample_number == (numSamples - 1)) {
- //std::cout << "new bg created" << std::endl;
+ if (bg_sample_number == (numSamples - 1)) {
+ //std::cout << "new bg created" << std::endl;
persistenceImage = Scalar(0);
bg_reset = false;
- if(sudden_change) {
+ if (sudden_change) {
numSamples *= 3.;
samplingPeriod *= 2.;
sudden_change = false;
}
- for(unsigned int i = 0; i < numPixels; i++) {
+ for (unsigned int i = 0; i < numPixels; i++) {
persistenceMap[i] = 0;
}
unsigned int p = 0;
- for(int i = 0; i < bgImage.rows; ++i) {
- for(int j = 0; j < bgImage.cols; ++j, ++p) {
- bgImage.at(i,j) = bgModel[p].values[0];
+ for (int i = 0; i < bgImage.rows; ++i) {
+ for (int j = 0; j < bgImage.cols; ++j, ++p) {
+ bgImage.at(i, j) = bgModel[p].values[0];
}
}
}
@@ -452,13 +468,13 @@ void BackgroundSubtractorIMBS::getFg() {
bool isFg = true;
bool conditionalUpdated = false;
unsigned int d = 0;
- for(unsigned int p = 0; p < numPixels; ++p) {
+ for (unsigned int p = 0; p < numPixels; ++p) {
isFg = true;
conditionalUpdated = false;
d = 0;
- for(unsigned int n = 0; n < maxBgBins; ++n) {
- if(!bgModel[p].isValid[n]) {
- if(n == 0) {
+ for (unsigned int n = 0; n < maxBgBins; ++n) {
+ if (!bgModel[p].isValid[n]) {
+ if (n == 0) {
isFg = false;
}
break;
@@ -466,13 +482,13 @@ void BackgroundSubtractorIMBS::getFg() {
else { //the model is valid
d = std::max(
(int)std::abs(bgModel[p].values[n][0] - frameBGR[0].data[p]),
- std::abs(bgModel[p].values[n][1] - frameBGR[1].data[p]) );
+ std::abs(bgModel[p].values[n][1] - frameBGR[1].data[p]));
d = std::max(
- (int)d, std::abs(bgModel[p].values[n][2] - frameBGR[2].data[p]) );
- if(d < fgThreshold){
+ (int)d, std::abs(bgModel[p].values[n][2] - frameBGR[2].data[p]));
+ if (d < fgThreshold) {
//check if it is a potential background pixel
//from stationary object
- if(bgModel[p].isFg[n]) {
+ if (bgModel[p].isFg[n]) {
conditionalUpdated = true;
break;
}
@@ -483,13 +499,13 @@ void BackgroundSubtractorIMBS::getFg() {
}
}
}
- if(isFg) {
- if(conditionalUpdated) {
+ if (isFg) {
+ if (conditionalUpdated) {
fgmask.data[p] = PERSISTENCE_LABEL;
persistenceMap[p] += (timestamp - prev_timestamp);
- if(persistenceMap[p] > persistencePeriod) {
- for(unsigned int n = 0; n < maxBgBins; ++n) {
- if(!bgModel[p].isValid[n]) {
+ if (persistenceMap[p] > persistencePeriod) {
+ for (unsigned int n = 0; n < maxBgBins; ++n) {
+ if (!bgModel[p].isValid[n]) {
break;
}
bgModel[p].isFg[n] = false;
@@ -521,13 +537,13 @@ void BackgroundSubtractorIMBS::areaThresholding()
if (area < minArea || area >= maxArea)
continue;
else {
- drawContours( tmpBinaryImage, contours, contourIdx, Scalar(255), CV_FILLED );
+ drawContours(tmpBinaryImage, contours, contourIdx, Scalar(255), CV_FILLED);
}
- }
- for(int i = 0; i < fgfiltered.rows; ++i) {
- for(int j = 0; j < fgfiltered.cols; ++j) {
- if(!tmpBinaryImage.at(i,j)) {
- fgfiltered.at(i,j) = 0;
+ }
+ for (int i = 0; i < fgfiltered.rows; ++i) {
+ for (int j = 0; j < fgfiltered.cols; ++j) {
+ if (!tmpBinaryImage.at(i, j)) {
+ fgfiltered.at(i, j) = 0;
}
}
}
@@ -560,9 +576,9 @@ Mat BackgroundSubtractorIMBS::convertImageRGBtoHSV(const Mat& imageRGB)
for (int x = 0; x < w; ++x) {
// Get the RGB pixel components. NOTE that OpenCV stores RGB pixels in B,G,R order.
//uchar *pRGB = (uchar*)(imRGB + y*rowSizeRGB + x*3);
- int bB = imageRGB.at(y,x)[0]; //*(uchar*)(pRGB+0); // Blue component
- int bG = imageRGB.at(y,x)[1]; //*(uchar*)(pRGB+1); // Green component
- int bR = imageRGB.at(y,x)[2]; //*(uchar*)(pRGB+2); // Red component
+ int bB = imageRGB.at(y, x)[0]; //*(uchar*)(pRGB+0); // Blue component
+ int bG = imageRGB.at(y, x)[1]; //*(uchar*)(pRGB+1); // Green component
+ int bR = imageRGB.at(y, x)[2]; //*(uchar*)(pRGB+2); // Red component
// Convert from 8-bit integers to floats.
fR = bR * BYTE_TO_FLOAT;
@@ -619,10 +635,10 @@ Mat BackgroundSubtractorIMBS::convertImageRGBtoHSV(const Mat& imageRGB)
fH = (fG - fB) * ANGLE_TO_UNIT;
}
else if (iMax == bG) { // between cyan and yellow.
- fH = (2.0f/6.0f) + ( fB - fR ) * ANGLE_TO_UNIT;
+ fH = (2.0f / 6.0f) + (fB - fR) * ANGLE_TO_UNIT;
}
else { // between magenta and cyan.
- fH = (4.0f/6.0f) + ( fR - fG ) * ANGLE_TO_UNIT;
+ fH = (4.0f / 6.0f) + (fR - fG) * ANGLE_TO_UNIT;
}
// Wrap outlier Hues around the circle.
if (fH < 0.0f)
@@ -666,14 +682,14 @@ Mat BackgroundSubtractorIMBS::convertImageRGBtoHSV(const Mat& imageRGB)
void BackgroundSubtractorIMBS::getBackgroundImage(OutputArray backgroundImage) const
{
- bgImage.copyTo(backgroundImage);
+ bgImage.copyTo(backgroundImage);
}
void BackgroundSubtractorIMBS::filterFg() {
unsigned int cnt = 0;
- for(unsigned int p = 0; p < numPixels; ++p) {
- if(fgmask.data[p] == (uchar)255) {
+ for (unsigned int p = 0; p < numPixels; ++p) {
+ if (fgmask.data[p] == (uchar)255) {
fgfiltered.data[p] = 255;
cnt++;
}
@@ -682,23 +698,23 @@ void BackgroundSubtractorIMBS::filterFg() {
}
}
- if(cnt > numPixels*0.5) {
+ if (cnt > numPixels*0.5) {
sudden_change = true;
}
- if(morphologicalFiltering) {
- cv::Mat element3(3,3,CV_8U,cv::Scalar(1));
+ if (morphologicalFiltering) {
+ cv::Mat element3(3, 3, CV_8U, cv::Scalar(1));
cv::morphologyEx(fgfiltered, fgfiltered, cv::MORPH_OPEN, element3);
cv::morphologyEx(fgfiltered, fgfiltered, cv::MORPH_CLOSE, element3);
}
areaThresholding();
- for(unsigned int p = 0; p < numPixels; ++p) {
- if(fgmask.data[p] == PERSISTENCE_LABEL) {
+ for (unsigned int p = 0; p < numPixels; ++p) {
+ if (fgmask.data[p] == PERSISTENCE_LABEL) {
fgfiltered.data[p] = PERSISTENCE_LABEL;
}
- else if(fgmask.data[p] == SHADOW_LABEL) {
+ else if (fgmask.data[p] == SHADOW_LABEL) {
fgfiltered.data[p] = SHADOW_LABEL;
}
}
@@ -715,7 +731,7 @@ void BackgroundSubtractorIMBS::changeBg() {
//bg_reset = true;
//cout << "qua" << endl;
- if(!bg_reset) {
+ if (!bg_reset) {
numSamples /= 3.;
samplingPeriod /= 2.;
bg_frame_counter = 0;
@@ -724,19 +740,19 @@ void BackgroundSubtractorIMBS::changeBg() {
}
void BackgroundSubtractorIMBS::getBgModel(BgModel bgModel_copy[], int size) {
- if(size != numPixels) {
+ if (size != numPixels) {
return;
}
- for(unsigned int i = 0; i < numPixels; ++i){
+ for (unsigned int i = 0; i < numPixels; ++i) {
bgModel_copy[i].values = new Vec3b[maxBgBins];
bgModel_copy[i].isValid = new bool[maxBgBins];
bgModel_copy[i].isValid[0] = false;
bgModel_copy[i].isFg = new bool[maxBgBins];
bgModel_copy[i].counter = new uchar[maxBgBins];
}
- for(unsigned int p = 0; p < numPixels; ++p) {
- for(unsigned int n = 0; n < maxBgBins; ++n) {
- if(!bgModel[p].isValid[n]) {
+ for (unsigned int p = 0; p < numPixels; ++p) {
+ for (unsigned int n = 0; n < maxBgBins; ++n) {
+ if (!bgModel[p].isValid[n]) {
break;
}
bgModel_copy[p].values[n] = bgModel[p].values[n];
diff --git a/package_bgs/db/imbs.hpp b/package_bgs/IMBS/IMBS.hpp
similarity index 77%
rename from package_bgs/db/imbs.hpp
rename to package_bgs/IMBS/IMBS.hpp
index fd7faf1..383e0ae 100644
--- a/package_bgs/db/imbs.hpp
+++ b/package_bgs/IMBS/IMBS.hpp
@@ -1,5 +1,21 @@
/*
-* IMBS Background Subtraction Library
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+/*
+* IMBS Background Subtraction Library
*
* This file imbs.hpp contains the C++ OpenCV based implementation for
* IMBS algorithm described in
@@ -8,8 +24,8 @@
* In Proc. of the Third Int. Conf. on Computational Modeling of Objects
* Presented in Images: Fundamentals, Methods and Applications, pp. 39-44, 2012.
* Please, cite the above paper if you use IMBS.
-*
-* This software is provided without any warranty about its usability.
+*
+* This software is provided without any warranty about its usability.
* It is for educational purposes and should be regarded as such.
*
* Written by Domenico D. Bloisi
@@ -18,9 +34,7 @@
* domenico.bloisi@gmail.com
*
*/
-
-#ifndef __IMBS_HPP__
-#define __IMBS_HPP__
+#pragma once
//OPENCV
#include
@@ -41,23 +55,23 @@ class BackgroundSubtractorIMBS
BackgroundSubtractorIMBS();
//! the full constructor
BackgroundSubtractorIMBS(double fps,
- unsigned int fgThreshold=15,
- unsigned int associationThreshold=5,
- double samplingPeriod=500.,
- unsigned int minBinHeight=2,
- unsigned int numSamples=30,
- double alpha=0.65,
- double beta=1.15,
- double tau_s=60.,
- double tau_h=40.,
- double minArea=30.,
- double persistencePeriod=10000.,
- bool morphologicalFiltering=false
- );
+ unsigned int fgThreshold = 15,
+ unsigned int associationThreshold = 5,
+ double samplingPeriod = 500.,
+ unsigned int minBinHeight = 2,
+ unsigned int numSamples = 30,
+ double alpha = 0.65,
+ double beta = 1.15,
+ double tau_s = 60.,
+ double tau_h = 40.,
+ double minArea = 30.,
+ double persistencePeriod = 10000.,
+ bool morphologicalFiltering = false
+ );
//! the destructor
~BackgroundSubtractorIMBS();
//! the update operator
- void apply(InputArray image, OutputArray fgmask, double learningRate=-1.);
+ void apply(InputArray image, OutputArray fgmask, double learningRate = -1.);
//! computes a background image which shows only the highest bin for each pixel
void getBackgroundImage(OutputArray backgroundImage) const;
@@ -73,7 +87,7 @@ class BackgroundSubtractorIMBS
//method for computing the foreground mask
void getFg();
//method for suppressing shadows and highlights
- void hsvSuppression();
+ void hsvSuppression();
//method for refining foreground mask
void filterFg();
//method for filtering out blobs smaller than a given area
@@ -82,7 +96,7 @@ class BackgroundSubtractorIMBS
double getTimestamp();
//method for converting from RGB to HSV
Mat convertImageRGBtoHSV(const Mat& imageRGB);
- //method for changing the bg in case of sudden changes
+ //method for changing the bg in case of sudden changes
void changeBg();
//current input RGB frame
@@ -112,7 +126,7 @@ class BackgroundSubtractorIMBS
//previous time stamp in milliseconds (ms)
double prev_timestamp;
double initial_tick_count;
- //initial message to be shown until the first bg model is ready
+ //initial message to be shown until the first bg model is ready
Mat initialMsgGray;
Mat initialMsgRGB;
@@ -174,5 +188,3 @@ class BackgroundSubtractorIMBS
}
void getBgModel(BgModel bgModel_copy[], int size);
};
-
-#endif //__IMBS_HPP__
diff --git a/package_bgs/IndependentMultimodal.cpp b/package_bgs/IndependentMultimodal.cpp
new file mode 100644
index 0000000..7b4de4c
--- /dev/null
+++ b/package_bgs/IndependentMultimodal.cpp
@@ -0,0 +1,74 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+#include "IndependentMultimodal.h"
+
+using namespace bgslibrary::algorithms;
+
+IndependentMultimodal::IndependentMultimodal() : fps(10)
+{
+ std::cout << "IndependentMultimodal()" << std::endl;
+ pIMBS = new BackgroundSubtractorIMBS(fps);
+ setup("./config/IndependentMultimodal.xml");
+}
+
+IndependentMultimodal::~IndependentMultimodal()
+{
+ std::cout << "~IndependentMultimodal()" << std::endl;
+ delete pIMBS;
+}
+
+void IndependentMultimodal::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
+{
+ init(img_input, img_output, img_bgmodel);
+
+ //get the fgmask and update the background model
+ pIMBS->apply(img_input, img_foreground);
+
+ //get background image
+ pIMBS->getBackgroundImage(img_background);
+
+ img_foreground.copyTo(img_output);
+ img_background.copyTo(img_bgmodel);
+
+#ifndef MEX_COMPILE_FLAG
+ if (showOutput)
+ {
+ cv::imshow("IMBS FG", img_foreground);
+ cv::imshow("IMBS BG", img_background);
+ }
+#endif
+
+ firstTime = false;
+}
+
+void IndependentMultimodal::saveConfig()
+{
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_WRITE);
+
+ cvWriteInt(fs, "showOutput", showOutput);
+
+ cvReleaseFileStorage(&fs);
+}
+
+void IndependentMultimodal::loadConfig()
+{
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_READ);
+
+ showOutput = cvReadIntByName(fs, nullptr, "showOutput", true);
+
+ cvReleaseFileStorage(&fs);
+}
diff --git a/package_bgs/StaticFrameDifferenceBGS.h b/package_bgs/IndependentMultimodal.h
similarity index 60%
rename from package_bgs/StaticFrameDifferenceBGS.h
rename to package_bgs/IndependentMultimodal.h
index 55f7bf1..4e2e3a3 100644
--- a/package_bgs/StaticFrameDifferenceBGS.h
+++ b/package_bgs/IndependentMultimodal.h
@@ -16,30 +16,28 @@ along with BGSLibrary. If not, see .
*/
#pragma once
-#include
-#include
-
-
#include "IBGS.h"
+#include "IMBS/IMBS.hpp"
-class StaticFrameDifferenceBGS : public IBGS
+namespace bgslibrary
{
-private:
- bool firstTime;
- cv::Mat img_background;
- cv::Mat img_foreground;
- bool enableThreshold;
- int threshold;
- bool showOutput;
-
-public:
- StaticFrameDifferenceBGS();
- ~StaticFrameDifferenceBGS();
-
- void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
-
-private:
- void saveConfig();
- void loadConfig();
-};
-
+ namespace algorithms
+ {
+ class IndependentMultimodal : public IBGS
+ {
+ private:
+ BackgroundSubtractorIMBS* pIMBS;
+ int fps;
+
+ public:
+ IndependentMultimodal();
+ ~IndependentMultimodal();
+
+ void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
+
+ private:
+ void saveConfig();
+ void loadConfig();
+ };
+ }
+}
diff --git a/package_bgs/ae/KDE.cpp b/package_bgs/KDE.cpp
similarity index 56%
rename from package_bgs/ae/KDE.cpp
rename to package_bgs/KDE.cpp
index 2cbbd8c..28564a0 100644
--- a/package_bgs/ae/KDE.cpp
+++ b/package_bgs/KDE.cpp
@@ -16,11 +16,15 @@ along with BGSLibrary. If not, see .
*/
#include "KDE.h"
-KDE::KDE() : SequenceLength(50), TimeWindowSize(100), SDEstimationFlag(1), lUseColorRatiosFlag(1),
- th(10e-8), alpha(0.3), framesToLearn(10), frameNumber(0), firstTime(true), showOutput(true)
+using namespace bgslibrary::algorithms;
+
+KDE::KDE() :
+ SequenceLength(50), TimeWindowSize(100), SDEstimationFlag(1), lUseColorRatiosFlag(1),
+ th(10e-8), alpha(0.3), framesToLearn(10), frameNumber(0)
{
p = new NPBGSubtractor;
std::cout << "KDE()" << std::endl;
+ setup("./config/KDE.xml");
}
KDE::~KDE()
@@ -32,72 +36,73 @@ KDE::~KDE()
void KDE::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
{
- if(img_input.empty())
- return;
-
- loadConfig();
+ init(img_input, img_output, img_bgmodel);
- if(firstTime)
+ if (firstTime)
{
rows = img_input.size().height;
cols = img_input.size().width;
color_channels = img_input.channels();
// SequenceLength: number of samples for each pixel.
- // TimeWindowSize: Time window for sampling. for example in the call above, the bg will sample 50 points out of 100 frames.
+ // TimeWindowSize: Time window for sampling. for example in the call above, the bg will sample 50 points out of 100 frames.
// this rate will affect how fast the model adapt.
// SDEstimationFlag: True means to estimate suitable kernel bandwidth to each pixel, False uses a default value.
// lUseColorRatiosFlag: True means use normalized RGB for color (recommended.)
- p->Intialize(rows,cols,color_channels,SequenceLength,TimeWindowSize,SDEstimationFlag,lUseColorRatiosFlag);
+ p->Intialize(rows, cols, color_channels, SequenceLength, TimeWindowSize, SDEstimationFlag, lUseColorRatiosFlag);
// th: 0-1 is the probability threshold for a pixel to be a foregroud. typically make it small as 10e-8. the smaller the value the less false positive and more false negative.
// alpha: 0-1, for color. typically set to 0.3. this affect shadow suppression.
- p->SetThresholds(th,alpha);
+ p->SetThresholds(th, alpha);
FGImage = new unsigned char[rows*cols];
//FilteredFGImage = new unsigned char[rows*cols];
FilteredFGImage = 0;
DisplayBuffers = 0;
- img_foreground = cv::Mat::zeros(rows,cols,CV_8UC1);
+ img_foreground = cv::Mat::zeros(img_input.size(), CV_8UC1);
+ img_background = cv::Mat::zeros(img_input.size(), img_input.type());
frameNumber = 0;
- saveConfig();
firstTime = false;
}
// Stores the first N frames to build the background model
- if(frameNumber < framesToLearn)
+ if (frameNumber < framesToLearn)
{
p->AddFrame(img_input.data);
frameNumber++;
- return;
}
-
- // Build the background model with first 10 frames
- if(frameNumber == framesToLearn)
+ else
{
- p->Estimation();
- frameNumber++;
- }
+ // Build the background model with first 10 frames
+ if (frameNumber == framesToLearn)
+ {
+ p->Estimation();
+ frameNumber++;
+ }
+
+ // Now, we can subtract the background
+ ((NPBGSubtractor*)p)->NBBGSubtraction(img_input.data, FGImage, FilteredFGImage, DisplayBuffers);
- // Now, we can subtract the background
- ((NPBGSubtractor *)p)->NBBGSubtraction(img_input.data,FGImage,FilteredFGImage,DisplayBuffers);
-
- // At each frame also you can call the update function to adapt the bg
- // here you pass a mask where pixels with true value will be masked out of the update.
- ((NPBGSubtractor *)p)->Update(FGImage);
+ // At each frame also you can call the update function to adapt the bg
+ // here you pass a mask where pixels with true value will be masked out of the update.
+ ((NPBGSubtractor*)p)->Update(FGImage);
- img_foreground.data = FGImage;
+ img_foreground.data = FGImage;
+ }
- if(showOutput)
+#ifndef MEX_COMPILE_FLAG
+ if (showOutput)
cv::imshow("KDE", img_foreground);
+#endif
img_foreground.copyTo(img_output);
+ img_background.copyTo(img_bgmodel);
}
void KDE::saveConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/KDE.xml", 0, CV_STORAGE_WRITE);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_WRITE);
cvWriteInt(fs, "framesToLearn", framesToLearn);
cvWriteInt(fs, "SequenceLength", SequenceLength);
@@ -113,16 +118,16 @@ void KDE::saveConfig()
void KDE::loadConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/KDE.xml", 0, CV_STORAGE_READ);
-
- framesToLearn = cvReadIntByName(fs, 0, "framesToLearn", 10);
- SequenceLength = cvReadIntByName(fs, 0, "SequenceLength", 50);
- TimeWindowSize = cvReadIntByName(fs, 0, "TimeWindowSize", 100);
- SDEstimationFlag = cvReadIntByName(fs, 0, "SDEstimationFlag", 1);
- lUseColorRatiosFlag = cvReadIntByName(fs, 0, "lUseColorRatiosFlag", 1);
- th = cvReadRealByName(fs, 0, "th", 10e-8);
- alpha = cvReadRealByName(fs, 0, "alpha", 0.3);
- showOutput = cvReadIntByName(fs, 0, "showOutput", true);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_READ);
+
+ framesToLearn = cvReadIntByName(fs, nullptr, "framesToLearn", 10);
+ SequenceLength = cvReadIntByName(fs, nullptr, "SequenceLength", 50);
+ TimeWindowSize = cvReadIntByName(fs, nullptr, "TimeWindowSize", 100);
+ SDEstimationFlag = cvReadIntByName(fs, nullptr, "SDEstimationFlag", 1);
+ lUseColorRatiosFlag = cvReadIntByName(fs, nullptr, "lUseColorRatiosFlag", 1);
+ th = cvReadRealByName(fs, nullptr, "th", 10e-8);
+ alpha = cvReadRealByName(fs, nullptr, "alpha", 0.3);
+ showOutput = cvReadIntByName(fs, nullptr, "showOutput", true);
cvReleaseFileStorage(&fs);
}
diff --git a/package_bgs/KDE.h b/package_bgs/KDE.h
new file mode 100644
index 0000000..e77996f
--- /dev/null
+++ b/package_bgs/KDE.h
@@ -0,0 +1,57 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+#pragma once
+
+#include "IBGS.h"
+#include "KDE/NPBGSubtractor.h"
+
+namespace bgslibrary
+{
+ namespace algorithms
+ {
+ class KDE : public IBGS
+ {
+ private:
+ NPBGSubtractor *p;
+ int rows;
+ int cols;
+ int color_channels;
+ int SequenceLength;
+ int TimeWindowSize;
+ int SDEstimationFlag;
+ int lUseColorRatiosFlag;
+ double th;
+ double alpha;
+ int framesToLearn;
+ int frameNumber;
+
+ unsigned char *FGImage;
+ unsigned char *FilteredFGImage;
+ unsigned char **DisplayBuffers;
+
+ public:
+ KDE();
+ ~KDE();
+
+ void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
+
+ private:
+ void saveConfig();
+ void loadConfig();
+ };
+ }
+}
diff --git a/package_bgs/ae/KernelTable.cpp b/package_bgs/KDE/KernelTable.cpp
similarity index 75%
rename from package_bgs/ae/KernelTable.cpp
rename to package_bgs/KDE/KernelTable.cpp
index 9e20d7c..bd9c368 100644
--- a/package_bgs/ae/KernelTable.cpp
+++ b/package_bgs/KDE/KernelTable.cpp
@@ -26,21 +26,21 @@ along with BGSLibrary. If not, see .
* copyright notice must be included. For any other uses of this software,
* in original or modified form, including but not limited to distribution
* in whole or in part, specific prior permission must be obtained from
-* Author or UMIACS. These programs shall not be used, rewritten, or
-* adapted as the basis of a commercial software or hardware product
-* without first obtaining appropriate licenses from Author.
+* Author or UMIACS. These programs shall not be used, rewritten, or
+* adapted as the basis of a commercial software or hardware product
+* without first obtaining appropriate licenses from Author.
* Other than these cases, no part of this software may be used or
* distributed without written permission of the author.
*
-* Neither the author nor UMIACS make any representations about the
-* suitability of this software for any purpose. It is provided
+* Neither the author nor UMIACS make any representations about the
+* suitability of this software for any purpose. It is provided
* "as is" without express or implied warranty.
*
* Ahmed Elgammal
-*
+*
* University of Maryland at College Park
* UMIACS
-* A.V. Williams Bldg.
+* A.V. Williams Bldg.
* CollegePark, MD 20742
* E-mail: elgammal@umiacs.umd.edu
*
@@ -67,8 +67,8 @@ KernelLUTable::KernelLUTable(int KernelHalfWidth, double Segmamin, double Segmam
{
std::cout << "KernelLUTable()" << std::endl;
- double C1,C2,v,segma,sum;
- int bin,b;
+ double C1, C2, v, segma, sum;
+ int bin, b;
minsegma = Segmamin;
maxsegma = Segmamax;
@@ -78,27 +78,27 @@ KernelLUTable::KernelLUTable(int KernelHalfWidth, double Segmamin, double Segmam
// Generate the Kernel
// allocate memory for the Kernal Table
- kerneltable = new double[segmabins*(2*KernelHalfWidth+1)];
+ kerneltable = new double[segmabins*(2 * KernelHalfWidth + 1)];
kernelsums = new double[segmabins];
double segmastep = (maxsegma - minsegma) / segmabins;
double y;
- for(segma = minsegma, bin = 0; bin < segmabins; segma += segmastep, bin++)
+ for (segma = minsegma, bin = 0; bin < segmabins; segma += segmastep, bin++)
{
- C1 = 1/(sqrt(2*PI)*segma);
- C2 = -1/(2*segma*segma);
+ C1 = 1 / (sqrt(2 * PI)*segma);
+ C2 = -1 / (2 * segma*segma);
- b = (2*KernelHalfWidth+1)*bin;
+ b = (2 * KernelHalfWidth + 1)*bin;
sum = 0;
-
- for(int x = 0; x <= KernelHalfWidth; x++)
+
+ for (int x = 0; x <= KernelHalfWidth; x++)
{
- y = x/1.0;
+ y = x / 1.0;
v = C1*exp(C2*y*y);
- kerneltable[b+KernelHalfWidth+x]=v;
- kerneltable[b+KernelHalfWidth-x]=v;
- sum += 2*v;
+ kerneltable[b + KernelHalfWidth + x] = v;
+ kerneltable[b + KernelHalfWidth - x] = v;
+ sum += 2 * v;
}
sum -= C1;
@@ -106,11 +106,11 @@ KernelLUTable::KernelLUTable(int KernelHalfWidth, double Segmamin, double Segmam
kernelsums[bin] = sum;
// Normailization
- for(int x = 0; x <= KernelHalfWidth; x++)
+ for (int x = 0; x <= KernelHalfWidth; x++)
{
- v = kerneltable[b+KernelHalfWidth+x] / sum;
- kerneltable[b+KernelHalfWidth+x]=v;
- kerneltable[b+KernelHalfWidth-x]=v;
+ v = kerneltable[b + KernelHalfWidth + x] / sum;
+ kerneltable[b + KernelHalfWidth + x] = v;
+ kerneltable[b + KernelHalfWidth - x] = v;
}
}
}
diff --git a/package_bgs/ae/KernelTable.h b/package_bgs/KDE/KernelTable.h
similarity index 86%
rename from package_bgs/ae/KernelTable.h
rename to package_bgs/KDE/KernelTable.h
index bc37cc4..63a20dc 100644
--- a/package_bgs/ae/KernelTable.h
+++ b/package_bgs/KDE/KernelTable.h
@@ -26,28 +26,26 @@ along with BGSLibrary. If not, see .
* copyright notice must be included. For any other uses of this software,
* in original or modified form, including but not limited to distribution
* in whole or in part, specific prior permission must be obtained from
-* Author or UMIACS. These programs shall not be used, rewritten, or
-* adapted as the basis of a commercial software or hardware product
-* without first obtaining appropriate licenses from Author.
+* Author or UMIACS. These programs shall not be used, rewritten, or
+* adapted as the basis of a commercial software or hardware product
+* without first obtaining appropriate licenses from Author.
* Other than these cases, no part of this software may be used or
* distributed without written permission of the author.
*
-* Neither the author nor UMIACS make any representations about the
-* suitability of this software for any purpose. It is provided
+* Neither the author nor UMIACS make any representations about the
+* suitability of this software for any purpose. It is provided
* "as is" without express or implied warranty.
*
* Ahmed Elgammal
-*
+*
* University of Maryland at College Park
* UMIACS
-* A.V. Williams Bldg.
+* A.V. Williams Bldg.
* CollegePark, MD 20742
* E-mail: elgammal@umiacs.umd.edu
*
**/
-
-#ifndef __KERNEL_TABLE__
-#define __KERNEL_TABLE__
+#pragma once
#include
@@ -65,7 +63,5 @@ class KernelLUTable
KernelLUTable();
~KernelLUTable();
- KernelLUTable(int KernelHalfWidth,double Segmamin,double Segmamax,int Segmabins);
+ KernelLUTable(int KernelHalfWidth, double Segmamin, double Segmamax, int Segmabins);
};
-
-#endif
diff --git a/package_bgs/KDE/NPBGSubtractor.cpp b/package_bgs/KDE/NPBGSubtractor.cpp
new file mode 100644
index 0000000..5f004b9
--- /dev/null
+++ b/package_bgs/KDE/NPBGSubtractor.cpp
@@ -0,0 +1,1160 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+/*
+*
+* Copyright 2001 by Ahmed Elgammal All rights reserved.
+*
+* Permission to use, copy, or modify this software and its documentation
+* for educational and research purposes only and without fee is hereby
+* granted, provided that this copyright notice and the original authors's
+* name appear on all copies and supporting documentation. If individual
+* files are separated from this distribution directory structure, this
+* copyright notice must be included. For any other uses of this software,
+* in original or modified form, including but not limited to distribution
+* in whole or in part, specific prior permission must be obtained from
+* Author or UMIACS. These programs shall not be used, rewritten, or
+* adapted as the basis of a commercial software or hardware product
+* without first obtaining appropriate licenses from Author.
+* Other than these cases, no part of this software may be used or
+* distributed without written permission of the author.
+*
+* Neither the author nor UMIACS make any representations about the
+* suitability of this software for any purpose. It is provided
+* "as is" without express or implied warranty.
+*
+* Ahmed Elgammal
+*
+* University of Maryland at College Park
+* UMIACS
+* A.V. Williams Bldg.
+* CollegePark, MD 20742
+* E-mail: elgammal@umiacs.umd.edu
+*
+**/
+
+// NPBGSubtractor.cpp: implementation of the NPBGSubtractor class.
+//
+//////////////////////////////////////////////////////////////////////
+
+#include "NPBGSubtractor.h"
+#include
+#include
+#include
+
+//#ifdef _DEBUG
+//#undef THIS_FILE
+//static char THIS_FILE[]=__FILE__;
+//#define new DEBUG_NEW
+//#endif
+
+void BGR2SnGnRn(unsigned char * in_image,
+ unsigned char * out_image,
+ unsigned int rows,
+ unsigned int cols)
+{
+ unsigned int i;
+ unsigned int r2, r3;
+ unsigned int r, g, b;
+ double s;
+
+ for (i = 0; i < rows*cols * 3; i += 3)
+ {
+ b = in_image[i];
+ g = in_image[i + 1];
+ r = in_image[i + 2];
+
+ // calculate color ratios
+ s = (double)255 / (double)(b + g + r + 30);
+
+ r2 = (unsigned int)((g + 10) * s);
+ r3 = (unsigned int)((r + 10) * s);
+
+ out_image[i] = (unsigned char)(((unsigned int)b + g + r) / 3);
+ out_image[i + 1] = (unsigned char)(r2 > 255 ? 255 : r2);
+ out_image[i + 2] = (unsigned char)(r3 > 255 ? 255 : r3);
+ }
+}
+
+void UpdateDiffHist(unsigned char * image1, unsigned char * image2, DynamicMedianHistogram * pHist)
+{
+ unsigned int j;
+ int bin, diff;
+
+ unsigned int imagesize = pHist->imagesize;
+ unsigned char histbins = pHist->histbins;
+ unsigned char *pAbsDiffHist = pHist->Hist;
+
+ int histbins_1 = histbins - 1;
+
+ for (j = 0; j < imagesize; j++)
+ {
+ diff = (int)image1[j] - (int)image2[j];
+ diff = abs(diff);
+ // update histogram
+ bin = (diff < histbins ? diff : histbins_1);
+ pAbsDiffHist[j*histbins + bin]++;
+ }
+}
+
+void FindHistMedians(DynamicMedianHistogram * pAbsDiffHist)
+{
+ unsigned char * Hist = pAbsDiffHist->Hist;
+ unsigned char * MedianBins = pAbsDiffHist->MedianBins;
+ unsigned char * AccSum = pAbsDiffHist->AccSum;
+ unsigned char histsum = pAbsDiffHist->histsum;
+ unsigned char histbins = pAbsDiffHist->histbins;
+ unsigned int imagesize = pAbsDiffHist->imagesize;
+
+ int sum;
+ int bin;
+ unsigned int histindex;
+ unsigned char medianCount = histsum / 2;
+ unsigned int j;
+
+ // find medians
+ for (j = 0; j < imagesize; j++)
+ {
+ // find the median
+ bin = 0;
+ sum = 0;
+
+ histindex = j*histbins;
+
+ while (sum < medianCount)
+ {
+ sum += Hist[histindex + bin];
+ bin++;
+ }
+
+ bin--;
+
+ MedianBins[j] = bin;
+ AccSum[j] = sum;
+ }
+}
+
+DynamicMedianHistogram BuildAbsDiffHist(unsigned char * pSequence,
+ unsigned int rows,
+ unsigned int cols,
+ unsigned int color_channels,
+ unsigned int SequenceLength,
+ unsigned int histbins)
+{
+
+ unsigned int imagesize = rows*cols*color_channels;
+ unsigned int i;
+
+ DynamicMedianHistogram Hist;
+
+ unsigned char *pAbsDiffHist = new unsigned char[rows*cols*color_channels*histbins];
+ unsigned char *pMedianBins = new unsigned char[rows*cols*color_channels];
+ unsigned char *pMedianFreq = new unsigned char[rows*cols*color_channels];
+ unsigned char *pAccSum = new unsigned char[rows*cols*color_channels];
+
+ memset(pAbsDiffHist, 0, rows*cols*color_channels*histbins);
+
+ Hist.Hist = pAbsDiffHist;
+ Hist.MedianBins = pMedianBins;
+ Hist.MedianFreq = pMedianFreq;
+ Hist.AccSum = pAccSum;
+ Hist.histbins = histbins;
+ Hist.imagesize = rows*cols*color_channels;
+ Hist.histsum = SequenceLength - 1;
+
+ unsigned char *image1, *image2;
+ for (i = 1; i < SequenceLength; i++)
+ {
+ // find diff between frame i,i-1;
+ image1 = pSequence + (i - 1)*imagesize;
+ image2 = pSequence + (i)*imagesize;
+
+ UpdateDiffHist(image1, image2, &Hist);
+ }
+
+ FindHistMedians(&Hist);
+
+ return Hist;
+}
+
+void EstimateSDsFromAbsDiffHist(DynamicMedianHistogram * pAbsDiffHist,
+ unsigned char * pSDs,
+ unsigned int imagesize,
+ double MinSD,
+ double MaxSD,
+ unsigned int kernelbins)
+{
+ double v;
+ double kernelbinfactor = (kernelbins - 1) / (MaxSD - MinSD);
+ int medianCount;
+ int sum;
+ int bin;
+ unsigned int histindex;
+ unsigned int j;
+ unsigned int x1, x2;
+
+ unsigned char *Hist = pAbsDiffHist->Hist;
+ unsigned char *MedianBins = pAbsDiffHist->MedianBins;
+ unsigned char *AccSum = pAbsDiffHist->AccSum;
+ unsigned char histsum = pAbsDiffHist->histsum;
+ unsigned char histbins = pAbsDiffHist->histbins;
+
+ medianCount = (histsum) / 2;
+
+ for (j = 0; j < imagesize; j++)
+ {
+ histindex = j*histbins;
+
+ bin = MedianBins[j];
+ sum = AccSum[j];
+
+ x1 = sum - Hist[histindex + bin];
+ x2 = sum;
+
+ // interpolate to get the median
+ // x1 < 50 % < x2
+
+ v = 1.04 * ((double)bin - (double)(x2 - medianCount) / (double)(x2 - x1));
+ v = (v <= MinSD ? MinSD : v);
+
+ // convert sd to kernel table bin
+
+ bin = (int)(v >= MaxSD ? kernelbins - 1 : floor((v - MinSD)*kernelbinfactor + .5));
+
+ assert(bin >= 0 && bin < kernelbins);
+
+ pSDs[j] = bin;
+ }
+}
+
+//////////////////////////////////////////////////////////////////////
+// Construction/Destruction
+//////////////////////////////////////////////////////////////////////
+
+NPBGSubtractor::NPBGSubtractor() {}
+
+NPBGSubtractor::~NPBGSubtractor()
+{
+ delete AbsDiffHist.Hist;
+ delete AbsDiffHist.MedianBins;
+ delete AbsDiffHist.MedianFreq;
+ delete AbsDiffHist.AccSum;
+ delete KernelTable;
+ delete BGModel->SDbinsImage;
+ delete BGModel;
+ delete Pimage1;
+ delete Pimage2;
+ delete tempFrame;
+ delete imageindex->List;
+ delete imageindex;
+}
+
+int NPBGSubtractor::Intialize(unsigned int prows,
+ unsigned int pcols,
+ unsigned int pcolor_channels,
+ unsigned int SequenceLength,
+ unsigned int pTimeWindowSize,
+ unsigned char pSDEstimationFlag,
+ unsigned char pUseColorRatiosFlag)
+{
+
+ rows = prows;
+ cols = pcols;
+ color_channels = pcolor_channels;
+ imagesize = rows*cols*color_channels;
+ SdEstimateFlag = pSDEstimationFlag;
+ UseColorRatiosFlag = pUseColorRatiosFlag;
+ //SampleSize = SequenceLength;
+
+ AdaptBGFlag = FALSE;
+ //
+ SubsetFlag = TRUE;
+
+ UpdateSDRate = 0;
+
+ BGModel = new NPBGmodel(rows, cols, color_channels, SequenceLength, pTimeWindowSize, 500);
+
+ Pimage1 = new double[rows*cols];
+ Pimage2 = new double[rows*cols];
+
+ tempFrame = new unsigned char[rows*cols * 3];
+
+ imageindex = new ImageIndex;
+ imageindex->List = new unsigned int[rows*cols];
+
+ // error checking
+ if (BGModel == NULL)
+ return 0;
+
+ return 1;
+}
+
+void NPBGSubtractor::AddFrame(unsigned char *ImageBuffer)
+{
+ if (UseColorRatiosFlag && color_channels == 3)
+ BGR2SnGnRn(ImageBuffer, ImageBuffer, rows, cols);
+
+ BGModel->AddFrame(ImageBuffer);
+}
+
+void NPBGSubtractor::Estimation()
+{
+ int SampleSize = BGModel->SampleSize;
+
+ memset(BGModel->TemporalMask, 0, rows*cols*BGModel->TemporalBufferLength);
+
+ //BGModel->AccMask= new unsigned int [rows*cols];
+ memset(BGModel->AccMask, 0, rows*cols * sizeof(unsigned int));
+
+ unsigned char *pSDs = new unsigned char[rows*cols*color_channels];
+
+ //DynamicMedianHistogram AbsDiffHist;
+
+ int Abshistbins = 20;
+
+ TimeIndex = 0;
+
+ // estimate standard deviations
+
+ if (SdEstimateFlag)
+ {
+ AbsDiffHist = BuildAbsDiffHist(BGModel->Sequence, rows, cols, color_channels, SampleSize, Abshistbins);
+ EstimateSDsFromAbsDiffHist(&AbsDiffHist, pSDs, imagesize, SEGMAMIN, SEGMAMAX, SEGMABINS);
+ }
+ else
+ {
+ unsigned int bin;
+ bin = (unsigned int)floor(((DEFAULTSEGMA - SEGMAMIN)*SEGMABINS) / (SEGMAMAX - SEGMAMIN));
+ memset(pSDs, bin, rows*cols*color_channels * sizeof(unsigned char));
+ }
+
+ BGModel->SDbinsImage = pSDs;
+
+ // Generate the Kernel
+ KernelTable = new KernelLUTable(KERNELHALFWIDTH, SEGMAMIN, SEGMAMAX, SEGMABINS);
+}
+
+/*********************************************************************/
+
+void BuildImageIndex(unsigned char * Image,
+ ImageIndex * imageIndex,
+ unsigned int rows,
+ unsigned int cols)
+{
+ unsigned int i, j;
+ unsigned int r, c;
+ unsigned int * image_list;
+
+ j = cols + 1;
+ i = 0;
+ image_list = imageIndex->List;
+
+ for (r = 1; r < rows - 1; r++)
+ {
+ for (c = 1; c < cols - 1; c++)
+ {
+ if (Image[j])
+ image_list[i++] = j;
+
+ j++;
+ }
+ j += 2;
+ }
+
+ imageIndex->cnt = i;
+}
+
+/*********************************************************************/
+
+void HystExpandOperatorIndexed(unsigned char * inImage,
+ ImageIndex * inIndex,
+ double * Pimage,
+ double hyst_th,
+ unsigned char * outImage,
+ ImageIndex * outIndex,
+ unsigned int urows,
+ unsigned int ucols)
+{
+ unsigned int * in_list;
+ unsigned int in_cnt;
+ unsigned int * out_list;
+
+ int rows, cols;
+
+ int Nbr[9];
+ unsigned int i, j;
+ unsigned int k;
+ unsigned int idx;
+
+ rows = (int)urows;
+ cols = (int)ucols;
+
+ in_cnt = inIndex->cnt;
+ in_list = inIndex->List;
+
+ Nbr[0] = -cols - 1;
+ Nbr[1] = -cols;
+ Nbr[2] = -cols + 1;
+ Nbr[3] = -1;
+ Nbr[4] = 0;
+ Nbr[5] = 1;
+ Nbr[6] = cols - 1;
+ Nbr[7] = cols;
+ Nbr[8] = cols + 1;
+
+ memset(outImage, 0, rows*cols);
+
+ out_list = outIndex->List;
+ k = 0;
+
+ for (i = 0; i < in_cnt; i++)
+ {
+ for (j = 0; j < 9; j++)
+ {
+ idx = in_list[i] + Nbr[j];
+
+ if (Pimage[idx] < hyst_th)
+ outImage[idx] = 255;
+ }
+ }
+
+ // build index for out image
+ BuildImageIndex(outImage, outIndex, urows, ucols);
+}
+
+/*********************************************************************/
+
+void HystShrinkOperatorIndexed(unsigned char * inImage,
+ ImageIndex * inIndex,
+ double * Pimage,
+ double hyst_th,
+ unsigned char * outImage,
+ ImageIndex * outIndex,
+ unsigned int urows,
+ unsigned int ucols)
+{
+ unsigned int * in_list;
+ unsigned int in_cnt;
+ unsigned int * out_list;
+
+ int rows, cols;
+
+ int Nbr[9];
+ unsigned int i, j;
+ unsigned int k, idx;
+
+ rows = (int)urows;
+ cols = (int)ucols;
+
+ in_cnt = inIndex->cnt;
+ in_list = inIndex->List;
+
+ Nbr[0] = -cols - 1;
+ Nbr[1] = -cols;
+ Nbr[2] = -cols + 1;
+ Nbr[3] = -1;
+ Nbr[4] = 0;
+ Nbr[5] = 1;
+ Nbr[6] = cols - 1;
+ Nbr[7] = cols;
+ Nbr[8] = cols + 1;
+
+ memset(outImage, 0, rows*cols);
+
+ out_list = outIndex->List;
+ k = 0;
+
+ for (i = 0; i < in_cnt; i++)
+ {
+ idx = in_list[i];
+ j = 0;
+
+ while (j < 9 && inImage[idx + Nbr[j]])
+ j++;
+
+ if (j >= 9 || Pimage[idx] <= hyst_th)
+ outImage[idx] = 255;
+ }
+
+ BuildImageIndex(outImage, outIndex, rows, cols);
+}
+
+/*********************************************************************/
+
+void ExpandOperatorIndexed(unsigned char * inImage,
+ ImageIndex * inIndex,
+ unsigned char * outImage,
+ ImageIndex * outIndex,
+ unsigned int urows,
+ unsigned int ucols)
+{
+ unsigned int * in_list;
+ unsigned int in_cnt;
+ unsigned int * out_list;
+
+ int rows, cols;
+
+ int Nbr[9];
+ unsigned int i, j;
+ unsigned int k;
+ unsigned int idx;
+
+ rows = (int)urows;
+ cols = (int)ucols;
+
+ in_cnt = inIndex->cnt;
+ in_list = inIndex->List;
+
+ Nbr[0] = -cols - 1;
+ Nbr[1] = -cols;
+ Nbr[2] = -cols + 1;
+ Nbr[3] = -1;
+ Nbr[4] = 0;
+ Nbr[5] = 1;
+ Nbr[6] = cols - 1;
+ Nbr[7] = cols;
+ Nbr[8] = cols + 1;
+
+
+ memset(outImage, 0, rows*cols);
+
+
+ out_list = outIndex->List;
+ k = 0;
+ for (i = 0; i < in_cnt; i++)
+ for (j = 0; j < 9; j++) {
+ idx = in_list[i] + Nbr[j];
+ outImage[idx] = 255;
+ }
+
+
+ // build index for out image
+
+ BuildImageIndex(outImage, outIndex, rows, cols);
+
+}
+
+/*********************************************************************/
+
+void ShrinkOperatorIndexed(unsigned char * inImage,
+ ImageIndex * inIndex,
+ unsigned char * outImage,
+ ImageIndex * outIndex,
+ unsigned int urows,
+ unsigned int ucols)
+{
+
+ unsigned int * in_list;
+ unsigned int in_cnt;
+ unsigned int * out_list;
+
+ int rows, cols;
+
+ int Nbr[9];
+ unsigned int i, j;
+ unsigned int k, idx;
+
+ rows = (int)urows;
+ cols = (int)ucols;
+
+ in_cnt = inIndex->cnt;
+ in_list = inIndex->List;
+
+ Nbr[0] = -cols - 1;
+ Nbr[1] = -cols;
+ Nbr[2] = -cols + 1;
+ Nbr[3] = -1;
+ Nbr[4] = 0;
+ Nbr[5] = 1;
+ Nbr[6] = cols - 1;
+ Nbr[7] = cols;
+ Nbr[8] = cols + 1;
+
+
+ memset(outImage, 0, rows*cols);
+
+ out_list = outIndex->List;
+ k = 0;
+ for (i = 0; i < in_cnt; i++) {
+ idx = in_list[i];
+ j = 0;
+
+ while (j < 9 && inImage[idx + Nbr[j]]) {
+ j++;
+ }
+
+ if (j >= 9) {
+ outImage[idx] = 255;
+ }
+ }
+
+ BuildImageIndex(outImage, outIndex, rows, cols);
+}
+
+/*********************************************************************/
+
+void NoiseFilter_o(unsigned char * Image,
+ unsigned char * ResultIm,
+ int rows,
+ int cols,
+ unsigned char th)
+{
+ /* assuming input is 1 for on, 0 for off */
+
+
+ int r, c;
+ unsigned char *p, *n, *nw, *ne, *e, *w, *s, *sw, *se;
+ unsigned int v;
+ unsigned int TH;
+
+ unsigned char * ResultPtr;
+
+ TH = 255 * th;
+
+ memset(ResultIm, 0, rows*cols);
+
+ p = Image + cols + 1;
+ ResultPtr = ResultIm + cols + 1;
+
+ for (r = 1; r < rows - 1; r++)
+ {
+ for (c = 1; c < cols - 1; c++)
+ {
+ if (*p)
+ {
+ n = p - cols;
+ ne = n + 1;
+ nw = n - 1;
+ e = p + 1;
+ w = p - 1;
+ s = p + cols;
+ se = s + 1;
+ sw = s - 1;
+
+ v = (unsigned int)*nw + *n + *ne + *w + *e + *sw + *s + *se;
+
+ if (v >= TH)
+ *ResultPtr = 255;
+ else
+ *ResultPtr = 0;
+ }
+ p++;
+ ResultPtr++;
+ }
+ p += 2;
+ ResultPtr += 2;
+ }
+}
+
+/*********************************************************************/
+
+void NPBGSubtractor::SequenceBGUpdate_Pairs(unsigned char * image,
+ unsigned char * Mask)
+{
+ unsigned int i, ic;
+ unsigned char * pSequence = BGModel->Sequence;
+ unsigned char * PixelQTop = BGModel->PixelQTop;
+ unsigned int Top = BGModel->Top;
+ unsigned int rate;
+
+ int TemporalBufferTop = (int)BGModel->TemporalBufferTop;
+ unsigned char * pTemporalBuffer = BGModel->TemporalBuffer;
+ unsigned char * pTemporalMask = BGModel->TemporalMask;
+ int TemporalBufferLength = BGModel->TemporalBufferLength;
+
+ unsigned int * AccMask = BGModel->AccMask;
+ unsigned int ResetMaskTh = BGModel->ResetMaskTh;
+
+ unsigned char *pAbsDiffHist = AbsDiffHist.Hist;
+ unsigned char histbins = AbsDiffHist.histbins;
+ int histbins_1 = histbins - 1;
+
+ int TimeWindowSize = BGModel->TimeWindowSize;
+ int SampleSize = BGModel->SampleSize;
+
+ int TemporalBufferNext;
+
+ unsigned int imagebuffersize = rows*cols*color_channels;
+ unsigned int imagespatialsize = rows*cols;
+
+ unsigned char mask;
+
+ unsigned int histindex;
+ unsigned char diff;
+ unsigned char bin;
+
+ static int TBCount = 0;
+
+ unsigned char * pTBbase1, *pTBbase2;
+ unsigned char * pModelbase1, *pModelbase2;
+
+ rate = TimeWindowSize / SampleSize;
+ rate = (rate > 2) ? rate : 2;
+
+
+ TemporalBufferNext = (TemporalBufferTop + 1)
+ % TemporalBufferLength;
+
+ // pointers to Masks : Top and Next
+ unsigned char * pTMaskTop = pTemporalMask + TemporalBufferTop*imagespatialsize;
+ unsigned char * pTMaskNext = pTemporalMask + TemporalBufferNext*imagespatialsize;
+
+ // pointers to TB frames: Top and Next
+ unsigned char * pTBTop = pTemporalBuffer + TemporalBufferTop*imagebuffersize;
+ unsigned char * pTBNext = pTemporalBuffer + TemporalBufferNext*imagebuffersize;
+
+ if (((TimeIndex) % rate == 0) && TBCount >= TemporalBufferLength)
+ {
+ for (i = 0, ic = 0; i < imagespatialsize; i++, ic += color_channels)
+ {
+ mask = *(pTMaskTop + i) || *(pTMaskNext + i);
+
+ if (!mask)
+ {
+ // pointer to TB pixels to be added to the model
+ pTBbase1 = pTBTop + ic;
+ pTBbase2 = pTBNext + ic;
+
+ // pointers to Model pixels to be replaced
+ pModelbase1 = pSequence + PixelQTop[i] * imagebuffersize + ic;
+ pModelbase2 = pSequence + ((PixelQTop[i] + 1) % SampleSize)*imagebuffersize + ic;
+
+ // update Deviation Histogram
+ if (SdEstimateFlag)
+ {
+ if (color_channels == 1)
+ {
+ histindex = i*histbins;
+
+ // add new pair from temporal buffer
+ diff = (unsigned char)abs((int)*pTBbase1 - (int)*pTBbase2);
+ bin = (diff < histbins ? diff : histbins_1);
+ pAbsDiffHist[histindex + bin]++;
+
+
+ // remove old pair from the model
+ diff = (unsigned char)abs((int)*pModelbase1 - (int)*pModelbase2);
+ bin = (diff < histbins ? diff : histbins_1);
+ pAbsDiffHist[histindex + bin]--;
+ }
+ else
+ {
+ // color
+
+ // add new pair from temporal buffer
+ histindex = ic*histbins;
+ diff = abs(*pTBbase1 -
+ *pTBbase2);
+ bin = (diff < histbins ? diff : histbins_1);
+ pAbsDiffHist[histindex + bin]++;
+
+ histindex += histbins;
+ diff = abs(*(pTBbase1 + 1) -
+ *(pTBbase2 + 1));
+ bin = (diff < histbins ? diff : histbins_1);
+ pAbsDiffHist[histindex + bin]++;
+
+ histindex += histbins;
+ diff = abs(*(pTBbase1 + 2) -
+ *(pTBbase2 + 2));
+ bin = (diff < histbins ? diff : histbins_1);
+ pAbsDiffHist[histindex + bin]++;
+
+ // remove old pair from the model
+ histindex = ic*histbins;
+
+ diff = abs(*pModelbase1 -
+ *pModelbase2);
+ bin = (diff < histbins ? diff : histbins_1);
+ pAbsDiffHist[histindex + bin]--;
+
+ histindex += histbins;
+ diff = abs(*(pModelbase1 + 1) -
+ *(pModelbase2 + 1));
+ bin = (diff < histbins ? diff : histbins_1);
+ pAbsDiffHist[histindex + bin]--;
+
+ histindex += histbins;
+ diff = abs(*(pModelbase1 + 2) -
+ *(pModelbase2 + 2));
+ bin = (diff < histbins ? diff : histbins_1);
+ pAbsDiffHist[histindex + bin]--;
+ }
+ }
+
+ // add new pair into the model
+ memcpy(pModelbase1, pTBbase1, color_channels * sizeof(unsigned char));
+
+ memcpy(pModelbase2, pTBbase2, color_channels * sizeof(unsigned char));
+
+ PixelQTop[i] = (PixelQTop[i] + 2) % SampleSize;
+ }
+ }
+ } // end if (sampling event)
+
+ // update temporal buffer
+ // add new frame to Temporal buffer.
+ memcpy(pTBTop, image, imagebuffersize);
+
+ // update AccMask
+ // update new Mask with information in AccMask
+
+ for (i = 0; i < rows*cols; i++)
+ {
+ if (Mask[i])
+ AccMask[i]++;
+ else
+ AccMask[i] = 0;
+
+ if (AccMask[i] > ResetMaskTh)
+ Mask[i] = 0;
+ }
+
+ // add new mask
+ memcpy(pTMaskTop, Mask, imagespatialsize);
+
+ // advance Temporal buffer pointer
+ TemporalBufferTop = (TemporalBufferTop + 1) % TemporalBufferLength;
+
+ BGModel->TemporalBufferTop = TemporalBufferTop;
+
+ TBCount++;
+
+ // estimate SDs
+
+ if (SdEstimateFlag && UpdateSDRate && ((TimeIndex) % UpdateSDRate == 0))
+ {
+ double MaxSD = KernelTable->maxsegma;
+ double MinSD = KernelTable->minsegma;
+ int KernelBins = KernelTable->segmabins;
+
+ unsigned char * pSDs = BGModel->SDbinsImage;
+
+ FindHistMedians(&(AbsDiffHist));
+ EstimateSDsFromAbsDiffHist(&(AbsDiffHist), pSDs, imagebuffersize, MinSD, MaxSD, KernelBins);
+ }
+
+ TimeIndex++;
+}
+
+/*********************************************************************/
+
+void DisplayPropabilityImageWithThresholding(double * Pimage,
+ unsigned char * DisplayImage,
+ double Threshold,
+ unsigned int rows,
+ unsigned int cols)
+{
+ double p;
+
+ for (unsigned int i = 0; i < rows*cols; i++)
+ {
+ p = Pimage[i];
+
+ DisplayImage[i] = (p > Threshold) ? 0 : 255;
+ }
+}
+
+/*********************************************************************/
+
+void NPBGSubtractor::NPBGSubtraction_Subset_Kernel(
+ unsigned char * image,
+ unsigned char * FGImage,
+ unsigned char * FilteredFGImage)
+{
+ unsigned int i, j;
+ unsigned char *pSequence = BGModel->Sequence;
+
+ unsigned int SampleSize = BGModel->SampleSize;
+
+ double *kerneltable = KernelTable->kerneltable;
+ int KernelHalfWidth = KernelTable->tablehalfwidth;
+ double *KernelSum = KernelTable->kernelsums;
+ double KernelMaxSigma = KernelTable->maxsegma;
+ double KernelMinSigma = KernelTable->minsegma;
+ int KernelBins = KernelTable->segmabins;
+ unsigned char * SDbins = BGModel->SDbinsImage;
+
+ unsigned char * SaturationImage = FilteredFGImage;
+
+ // default sigmas .. to be removed.
+ double sigma1;
+ double sigma2;
+ double sigma3;
+
+ sigma1 = 2.25;
+ sigma2 = 2.25;
+ sigma3 = 2.25;
+
+ double p;
+ double th;
+
+ double alpha;
+
+ alpha = AlphaValue;
+
+ /* intialize FG image */
+
+ memset(FGImage, 0, rows*cols);
+
+ //Threshold=1;
+ th = Threshold * SampleSize;
+
+ double sum = 0, kernel1, kernel2, kernel3;
+ int k, g;
+
+
+ if (color_channels == 1)
+ {
+ // gray scale
+
+ int kernelbase;
+
+ for (i = 0; i < rows*cols; i++)
+ {
+ kernelbase = SDbins[i] * (2 * KernelHalfWidth + 1);
+ sum = 0;
+ j = 0;
+
+ while (j < SampleSize && sum < th)
+ {
+ g = pSequence[j*imagesize + i];
+ k = g - image[i] + KernelHalfWidth;
+ sum += kerneltable[kernelbase + k];
+ j++;
+ }
+
+ p = sum / j;
+ Pimage1[i] = p;
+ }
+ }
+ else if (UseColorRatiosFlag && SubsetFlag)
+ {
+ // color ratios
+
+ unsigned int ig;
+ int base;
+
+ int kernelbase1;
+ int kernelbase2;
+ int kernelbase3;
+
+ unsigned int kerneltablewidth = 2 * KernelHalfWidth + 1;
+
+ double beta = 3.0; // minimum bound on the range.
+ double betau = 100.0;
+
+ double beta_over_alpha = beta / alpha;
+ double betau_over_alpha = betau / alpha;
+
+
+ double brightness_lowerbound = 1 - alpha;
+ double brightness_upperbound = 1 + alpha;
+ int x1, x2;
+ unsigned int SubsampleCount;
+
+ for (i = 0, ig = 0; i < imagesize; i += 3, ig++)
+ {
+ kernelbase1 = SDbins[i] * kerneltablewidth;
+ kernelbase2 = SDbins[i + 1] * kerneltablewidth;
+ kernelbase3 = SDbins[i + 2] * kerneltablewidth;
+
+ sum = 0;
+ j = 0;
+ SubsampleCount = 0;
+
+ while (j < SampleSize && sum < th)
+ {
+ base = j*imagesize + i;
+ g = pSequence[base];
+
+ if (g < beta_over_alpha)
+ {
+ x1 = (int)(g - beta);
+ x2 = (int)(g + beta);
+ }
+ else if (g > betau_over_alpha)
+ {
+ x1 = (int)(g - betau);
+ x2 = (int)(g + betau);
+ }
+ else
+ {
+ x1 = (int)(g*brightness_lowerbound + 0.5);
+ x2 = (int)(g*brightness_upperbound + 0.5);
+ }
+
+ if (x1 < image[i] && image[i] < x2)
+ {
+ g = pSequence[base + 1];
+ k = (g - image[i + 1]) + KernelHalfWidth;
+ kernel2 = kerneltable[kernelbase2 + k];
+
+ g = pSequence[base + 2];
+ k = (g - image[i + 2]) + KernelHalfWidth;
+ kernel3 = kerneltable[kernelbase3 + k];
+
+ sum += kernel2*kernel3;
+
+ SubsampleCount++;
+ }
+ j++;
+ }
+
+ p = sum / j;
+ Pimage1[ig] = p;
+ }
+ }
+ else if (UseColorRatiosFlag && !SubsetFlag)
+ {
+ // color ratios
+
+ unsigned int ig;
+ int base;
+ int bin;
+
+ int kernelbase1;
+ int kernelbase2;
+ int kernelbase3;
+
+ unsigned int kerneltablewidth = 2 * KernelHalfWidth + 1;
+
+ int gmin, gmax;
+ double gfactor;
+
+ gmax = 200;
+ gmin = 10;
+
+ gfactor = (KernelMaxSigma - KernelMinSigma) / (double)(gmax - gmin);
+
+ for (i = 0, ig = 0; i < imagesize; i += 3, ig++)
+ {
+
+ bin = (int)floor(((alpha * 16 - KernelMinSigma)*KernelBins) / (KernelMaxSigma - KernelMinSigma));
+
+ kernelbase1 = bin*kerneltablewidth;
+ kernelbase2 = SDbins[i + 1] * kerneltablewidth;
+ kernelbase3 = SDbins[i + 2] * kerneltablewidth;
+
+ sum = 0;
+ j = 0;
+
+ while (j < SampleSize && sum < th)
+ {
+ base = j*imagesize + i;
+ g = pSequence[base];
+
+ if (g < gmin)
+ bin = 0;
+ else if (g > gmax)
+ bin = KernelBins - 1;
+ else
+ bin = (int)((g - gmin) * gfactor + 0.5);
+
+ kernelbase1 = bin*kerneltablewidth;
+
+ k = (g - image[i]) + KernelHalfWidth;
+ kernel1 = kerneltable[kernelbase1 + k];
+
+ g = pSequence[base + 1];
+ k = (g - image[i + 1]) + KernelHalfWidth;
+ kernel2 = kerneltable[kernelbase2 + k];
+
+ g = pSequence[base + 2];
+ k = (g - image[i + 2]) + KernelHalfWidth;
+ kernel3 = kerneltable[kernelbase3 + k];
+
+ sum += kernel1*kernel2*kernel3;
+ j++;
+ }
+
+ p = sum / j;
+ Pimage1[ig] = p;
+ }
+ }
+ else // RGB color
+ {
+ unsigned int ig;
+ int base;
+
+ int kernelbase1;
+ int kernelbase2;
+ int kernelbase3;
+ unsigned int kerneltablewidth = 2 * KernelHalfWidth + 1;
+
+ for (i = 0, ig = 0; i < imagesize; i += 3, ig++)
+ {
+ // used extimated kernel width to access the right kernel
+ kernelbase1 = SDbins[i] * kerneltablewidth;
+ kernelbase2 = SDbins[i + 1] * kerneltablewidth;
+ kernelbase3 = SDbins[i + 2] * kerneltablewidth;
+
+ sum = 0;
+ j = 0;
+ while (j < SampleSize && sum < th)
+ {
+ base = j*imagesize + i;
+ g = pSequence[base];
+ k = (g - image[i]) + KernelHalfWidth;
+ kernel1 = kerneltable[kernelbase1 + k];
+
+ g = pSequence[base + 1];
+ k = (g - image[i + 1]) + KernelHalfWidth;
+ kernel2 = kerneltable[kernelbase2 + k];
+
+ g = pSequence[base + 2];
+ k = (g - image[i + 2]) + KernelHalfWidth;
+ kernel3 = kerneltable[kernelbase3 + k];
+
+ sum += kernel1*kernel2*kernel3;
+ j++;
+ }
+
+ p = sum / j;
+ Pimage1[ig] = p;
+ }
+ }
+
+ DisplayPropabilityImageWithThresholding(Pimage1, FGImage, Threshold, rows, cols);
+}
+
+/*********************************************************************/
+
+void NPBGSubtractor::NBBGSubtraction(unsigned char * Frame,
+ unsigned char * FGImage,
+ unsigned char * FilteredFGImage,
+ unsigned char ** DisplayBuffers)
+{
+ if (UseColorRatiosFlag)
+ BGR2SnGnRn(Frame, tempFrame, rows, cols);
+ else
+ memcpy(tempFrame, Frame, rows*cols*color_channels);
+
+ NPBGSubtraction_Subset_Kernel(tempFrame, FGImage, FilteredFGImage);
+ /*NoiseFilter_o(FGImage,DisplayBuffers[3],rows,cols,4);
+ BuildImageIndex(DisplayBuffers[3],imageindex,rows,cols);
+
+ ExpandOperatorIndexed(DisplayBuffers[3],imageindex,DisplayBuffers[4],imageindex,rows,cols);
+ ShrinkOperatorIndexed(DisplayBuffers[4],imageindex,FilteredFGImage,imageindex,rows,cols);
+
+ memset(DisplayBuffers[3],0,rows*cols);*/
+}
+
+void NPBGSubtractor::Update(unsigned char * FGMask)
+{
+ if (UpdateBGFlag)
+ SequenceBGUpdate_Pairs(tempFrame, FGMask);
+}
diff --git a/package_bgs/ae/NPBGSubtractor.h b/package_bgs/KDE/NPBGSubtractor.h
similarity index 87%
rename from package_bgs/ae/NPBGSubtractor.h
rename to package_bgs/KDE/NPBGSubtractor.h
index e7f3795..ce4bffc 100644
--- a/package_bgs/ae/NPBGSubtractor.h
+++ b/package_bgs/KDE/NPBGSubtractor.h
@@ -26,21 +26,21 @@ along with BGSLibrary. If not, see .
* copyright notice must be included. For any other uses of this software,
* in original or modified form, including but not limited to distribution
* in whole or in part, specific prior permission must be obtained from
-* Author or UMIACS. These programs shall not be used, rewritten, or
-* adapted as the basis of a commercial software or hardware product
-* without first obtaining appropriate licenses from Author.
+* Author or UMIACS. These programs shall not be used, rewritten, or
+* adapted as the basis of a commercial software or hardware product
+* without first obtaining appropriate licenses from Author.
* Other than these cases, no part of this software may be used or
* distributed without written permission of the author.
*
-* Neither the author nor UMIACS make any representations about the
-* suitability of this software for any purpose. It is provided
+* Neither the author nor UMIACS make any representations about the
+* suitability of this software for any purpose. It is provided
* "as is" without express or implied warranty.
*
* Ahmed Elgammal
-*
+*
* University of Maryland at College Park
* UMIACS
-* A.V. Williams Bldg.
+* A.V. Williams Bldg.
* CollegePark, MD 20742
* E-mail: elgammal@umiacs.umd.edu
*
@@ -49,13 +49,7 @@ along with BGSLibrary. If not, see .
// NPBGSubtractor.h: interface for the NPBGSubtractor class.
//
//////////////////////////////////////////////////////////////////////
-
-#if !defined(AFX_NPBGSUBTRACTOR_H__84B0F51E_6E65_41E4_AC01_723B406363C4__INCLUDED_)
-#define AFX_NPBGSUBTRACTOR_H__84B0F51E_6E65_41E4_AC01_723B406363C4__INCLUDED_
-
-#if _MSC_VER > 1000
#pragma once
-#endif // _MSC_VER > 1000
#include "NPBGmodel.h"
#include "KernelTable.h"
@@ -87,7 +81,7 @@ typedef struct
unsigned int *List;
} ImageIndex;
-class NPBGSubtractor
+class NPBGSubtractor
{
private:
unsigned int rows;
@@ -146,9 +140,7 @@ class NPBGSubtractor
AlphaValue = alpha;
};
- void SetUpdateFlag(unsigned int bgflag){
+ void SetUpdateFlag(unsigned int bgflag) {
UpdateBGFlag = bgflag;
};
};
-
-#endif // !defined(AFX_NPBGSUBTRACTOR_H__84B0F51E_6E65_41E4_AC01_723B406363C4__INCLUDED_)
diff --git a/package_bgs/ae/NPBGmodel.cpp b/package_bgs/KDE/NPBGmodel.cpp
similarity index 78%
rename from package_bgs/ae/NPBGmodel.cpp
rename to package_bgs/KDE/NPBGmodel.cpp
index 2c8b074..a79a7b4 100644
--- a/package_bgs/ae/NPBGmodel.cpp
+++ b/package_bgs/KDE/NPBGmodel.cpp
@@ -26,21 +26,21 @@ along with BGSLibrary. If not, see .
* copyright notice must be included. For any other uses of this software,
* in original or modified form, including but not limited to distribution
* in whole or in part, specific prior permission must be obtained from
-* Author or UMIACS. These programs shall not be used, rewritten, or
-* adapted as the basis of a commercial software or hardware product
-* without first obtaining appropriate licenses from Author.
+* Author or UMIACS. These programs shall not be used, rewritten, or
+* adapted as the basis of a commercial software or hardware product
+* without first obtaining appropriate licenses from Author.
* Other than these cases, no part of this software may be used or
* distributed without written permission of the author.
*
-* Neither the author nor UMIACS make any representations about the
-* suitability of this software for any purpose. It is provided
+* Neither the author nor UMIACS make any representations about the
+* suitability of this software for any purpose. It is provided
* "as is" without express or implied warranty.
*
* Ahmed Elgammal
-*
+*
* University of Maryland at College Park
* UMIACS
-* A.V. Williams Bldg.
+* A.V. Williams Bldg.
* CollegePark, MD 20742
* E-mail: elgammal@umiacs.umd.edu
*
@@ -55,7 +55,7 @@ along with BGSLibrary. If not, see .
#ifdef _DEBUG
#undef THIS_FILE
-static char THIS_FILE[]=__FILE__;
+static char THIS_FILE[] = __FILE__;
//#define new DEBUG_NEW
#endif
@@ -80,11 +80,11 @@ NPBGmodel::~NPBGmodel()
}
NPBGmodel::NPBGmodel(unsigned int Rows,
- unsigned int Cols,
- unsigned int ColorChannels,
- unsigned int Length,
- unsigned int pTimeWindowSize,
- unsigned int bg_suppression_time)
+ unsigned int Cols,
+ unsigned int ColorChannels,
+ unsigned int Length,
+ unsigned int pTimeWindowSize,
+ unsigned int bg_suppression_time)
{
std::cout << "NPBGmodel()" << std::endl;
@@ -98,14 +98,14 @@ NPBGmodel::NPBGmodel(unsigned int Rows,
TimeWindowSize = pTimeWindowSize;
- Sequence = new unsigned char[imagesize*Length];
+ Sequence = new unsigned char[imagesize*Length];
Top = 0;
- memset(Sequence,0,imagesize*Length);
+ memset(Sequence, 0, imagesize*Length);
PixelQTop = new unsigned char[rows*cols];
// temporalBuffer
- TemporalBufferLength = (TimeWindowSize/Length > 2 ? TimeWindowSize/Length:2);
+ TemporalBufferLength = (TimeWindowSize / Length > 2 ? TimeWindowSize / Length : 2);
TemporalBuffer = new unsigned char[imagesize*TemporalBufferLength];
TemporalMask = new unsigned char[rows*cols*TemporalBufferLength];
@@ -116,12 +116,12 @@ NPBGmodel::NPBGmodel(unsigned int Rows,
ResetMaskTh = bg_suppression_time;
}
-void NPBGmodel::AddFrame(unsigned char *ImageBuffer)
+void NPBGmodel::AddFrame(unsigned char *ImageBuffer)
{
- memcpy(Sequence+Top*imagesize,ImageBuffer,imagesize);
- Top = (Top + 1) % SampleSize;
+ memcpy(Sequence + Top*imagesize, ImageBuffer, imagesize);
+ Top = (Top + 1) % SampleSize;
- memset(PixelQTop, (unsigned char) Top, rows*cols);
+ memset(PixelQTop, (unsigned char)Top, rows*cols);
- memcpy(TemporalBuffer,ImageBuffer,imagesize);
+ memcpy(TemporalBuffer, ImageBuffer, imagesize);
}
diff --git a/package_bgs/ae/NPBGmodel.h b/package_bgs/KDE/NPBGmodel.h
similarity index 84%
rename from package_bgs/ae/NPBGmodel.h
rename to package_bgs/KDE/NPBGmodel.h
index 9e28510..ba4a927 100644
--- a/package_bgs/ae/NPBGmodel.h
+++ b/package_bgs/KDE/NPBGmodel.h
@@ -26,21 +26,21 @@ along with BGSLibrary. If not, see .
* copyright notice must be included. For any other uses of this software,
* in original or modified form, including but not limited to distribution
* in whole or in part, specific prior permission must be obtained from
-* Author or UMIACS. These programs shall not be used, rewritten, or
-* adapted as the basis of a commercial software or hardware product
-* without first obtaining appropriate licenses from Author.
+* Author or UMIACS. These programs shall not be used, rewritten, or
+* adapted as the basis of a commercial software or hardware product
+* without first obtaining appropriate licenses from Author.
* Other than these cases, no part of this software may be used or
* distributed without written permission of the author.
*
-* Neither the author nor UMIACS make any representations about the
-* suitability of this software for any purpose. It is provided
+* Neither the author nor UMIACS make any representations about the
+* suitability of this software for any purpose. It is provided
* "as is" without express or implied warranty.
*
* Ahmed Elgammal
-*
+*
* University of Maryland at College Park
* UMIACS
-* A.V. Williams Bldg.
+* A.V. Williams Bldg.
* CollegePark, MD 20742
* E-mail: elgammal@umiacs.umd.edu
*
@@ -49,24 +49,18 @@ along with BGSLibrary. If not, see .
// NPBGmodel.h: interface for the NPBGmodel class.
//
//////////////////////////////////////////////////////////////////////
-
-#if !defined(AFX_NPBGMODEL_H__CCAF05D4_D06E_44C2_95D8_979E2249953A__INCLUDED_)
-#define AFX_NPBGMODEL_H__CCAF05D4_D06E_44C2_95D8_979E2249953A__INCLUDED_
-
-#if _MSC_VER > 1000
#pragma once
-#endif // _MSC_VER > 1000
#include
-class NPBGmodel
+class NPBGmodel
{
private:
unsigned char *Sequence;
unsigned int SampleSize;
unsigned int TimeWindowSize;
- unsigned int rows,cols,color_channels;
+ unsigned int rows, cols, color_channels;
unsigned int imagesize;
unsigned int Top;
@@ -74,7 +68,7 @@ class NPBGmodel
//unsigned int *PixelUpdateCounter;
- unsigned char *SDbinsImage;
+ unsigned char *SDbinsImage;
unsigned char *TemporalBuffer;
unsigned char TemporalBufferLength;
@@ -107,5 +101,3 @@ class NPBGmodel
friend class NPBGSubtractor;
};
-
-#endif // !defined(AFX_NPBGMODEL_H__CCAF05D4_D06E_44C2_95D8_979E2249953A__INCLUDED_)
diff --git a/package_bgs/KNN.cpp b/package_bgs/KNN.cpp
new file mode 100644
index 0000000..d2e1412
--- /dev/null
+++ b/package_bgs/KNN.cpp
@@ -0,0 +1,111 @@
+/*
+ This file is part of BGSLibrary.
+
+ BGSLibrary is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ BGSLibrary is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with BGSLibrary. If not, see .
+ */
+#include "KNN.h"
+
+#if CV_MAJOR_VERSION == 3
+
+using namespace bgslibrary::algorithms;
+
+KNN::KNN() :
+ history(500), nSamples(7), dist2Threshold(20.0f * 20.0f), knnSamples(0),
+ doShadowDetection(true), shadowValue(127), shadowThreshold(0.5f)
+{
+ std::cout << "KNN()" << std::endl;
+ setup("./config/KNN.xml");
+}
+
+KNN::~KNN()
+{
+ std::cout << "~KNN()" << std::endl;
+}
+
+void KNN::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
+{
+ init(img_input, img_output, img_bgmodel);
+
+ //------------------------------------------------------------------
+ // BackgroundSubtractorKNN
+ // http://docs.opencv.org/trunk/modules/video/doc/motion_analysis_and_object_tracking.html#backgroundsubtractorknn
+ //
+ // The class implements the K nearest neigbours algorithm from:
+ // "Efficient Adaptive Density Estimation per Image Pixel for the Task of Background Subtraction"
+ // Z.Zivkovic, F. van der Heijden
+ // Pattern Recognition Letters, vol. 27, no. 7, pages 773-780, 2006
+ // http: //www.zoranz.net/Publications/zivkovicPRL2006.pdf
+ //
+ // Fast for small foreground object. Results on the benchmark data is at http://www.changedetection.net.
+ //------------------------------------------------------------------
+
+ int prevNSamples = nSamples;
+ if (firstTime)
+ knn = cv::createBackgroundSubtractorKNN(history, dist2Threshold, doShadowDetection);
+
+ knn->setNSamples(nSamples);
+ knn->setkNNSamples(knnSamples);
+ knn->setShadowValue(shadowValue);
+ knn->setShadowThreshold(shadowThreshold);
+
+ knn->apply(img_input, img_foreground, prevNSamples != nSamples ? 0.f : 1.f);
+ knn->getBackgroundImage(img_background);
+
+#ifndef MEX_COMPILE_FLAG
+ if (showOutput)
+ {
+ cv::imshow("KNN FG", img_foreground);
+ cv::imshow("KNN BG", img_background);
+ }
+#endif
+
+ img_foreground.copyTo(img_output);
+ img_background.copyTo(img_bgmodel);
+
+ firstTime = false;
+}
+
+void KNN::saveConfig()
+{
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_WRITE);
+
+ cvWriteInt(fs, "history", history);
+ cvWriteInt(fs, "nSamples", nSamples);
+ cvWriteReal(fs, "dist2Threshold", dist2Threshold);
+ cvWriteInt(fs, "knnSamples", knnSamples);
+ cvWriteInt(fs, "doShadowDetection", doShadowDetection);
+ cvWriteInt(fs, "shadowValue", shadowValue);
+ cvWriteReal(fs, "shadowThreshold", shadowThreshold);
+ cvWriteInt(fs, "showOutput", showOutput);
+
+ cvReleaseFileStorage(&fs);
+}
+
+void KNN::loadConfig()
+{
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_READ);
+
+ history = cvReadIntByName(fs, nullptr, "history", 500);
+ nSamples = cvReadIntByName(fs, nullptr, "nSamples", 7);
+ dist2Threshold = cvReadRealByName(fs, nullptr, "dist2Threshold", 20.0f * 20.0f);
+ knnSamples = cvReadIntByName(fs, nullptr, "knnSamples", 0);
+ doShadowDetection = cvReadIntByName(fs, nullptr, "doShadowDetection", 1);
+ shadowValue = cvReadIntByName(fs, nullptr, "shadowValue", 127);
+ shadowThreshold = cvReadRealByName(fs, nullptr, "shadowThreshold", 0.5f);
+ showOutput = cvReadIntByName(fs, nullptr, "showOutput", true);
+
+ cvReleaseFileStorage(&fs);
+}
+
+#endif
diff --git a/package_bgs/KNN.h b/package_bgs/KNN.h
new file mode 100644
index 0000000..87f20b2
--- /dev/null
+++ b/package_bgs/KNN.h
@@ -0,0 +1,57 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+#pragma once
+
+#include "opencv2/core/version.hpp"
+#if CV_MAJOR_VERSION == 3
+
+#include
+#include
+#include
+
+#include "IBGS.h"
+
+namespace bgslibrary
+{
+ namespace algorithms
+ {
+ class KNN : public IBGS
+ {
+ private:
+ cv::Ptr knn;
+ int history;
+ int nSamples;
+ float dist2Threshold;
+ int knnSamples;
+ bool doShadowDetection;
+ int shadowValue;
+ float shadowThreshold;
+
+ public:
+ KNN();
+ ~KNN();
+
+ void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
+
+ private:
+ void saveConfig();
+ void loadConfig();
+ };
+ }
+}
+
+#endif
diff --git a/package_bgs/lb/LBAdaptiveSOM.cpp b/package_bgs/LBAdaptiveSOM.cpp
similarity index 61%
rename from package_bgs/lb/LBAdaptiveSOM.cpp
rename to package_bgs/LBAdaptiveSOM.cpp
index ce06433..188e11d 100644
--- a/package_bgs/lb/LBAdaptiveSOM.cpp
+++ b/package_bgs/LBAdaptiveSOM.cpp
@@ -16,10 +16,13 @@ along with BGSLibrary. If not, see .
*/
#include "LBAdaptiveSOM.h"
-LBAdaptiveSOM::LBAdaptiveSOM() : firstTime(true), showOutput(true),
+using namespace bgslibrary::algorithms;
+
+LBAdaptiveSOM::LBAdaptiveSOM() :
sensitivity(75), trainingSensitivity(245), learningRate(62), trainingLearningRate(255), trainingSteps(55)
{
std::cout << "LBAdaptiveSOM()" << std::endl;
+ setup("./config/LBAdaptiveSOM.xml");
}
LBAdaptiveSOM::~LBAdaptiveSOM()
@@ -30,64 +33,55 @@ LBAdaptiveSOM::~LBAdaptiveSOM()
void LBAdaptiveSOM::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
{
- if(img_input.empty())
- return;
+ init(img_input, img_output, img_bgmodel);
- loadConfig();
-
IplImage *frame = new IplImage(img_input);
-
- if(firstTime)
- {
- saveConfig();
+ if (firstTime)
+ {
int w = cvGetSize(frame).width;
int h = cvGetSize(frame).height;
- m_pBGModel = new BGModelSom(w,h);
+ m_pBGModel = new BGModelSom(w, h);
m_pBGModel->InitModel(frame);
}
-
- m_pBGModel->setBGModelParameter(0,sensitivity);
- m_pBGModel->setBGModelParameter(1,trainingSensitivity);
- m_pBGModel->setBGModelParameter(2,learningRate);
- m_pBGModel->setBGModelParameter(3,trainingLearningRate);
- m_pBGModel->setBGModelParameter(5,trainingSteps);
+
+ m_pBGModel->setBGModelParameter(0, sensitivity);
+ m_pBGModel->setBGModelParameter(1, trainingSensitivity);
+ m_pBGModel->setBGModelParameter(2, learningRate);
+ m_pBGModel->setBGModelParameter(3, trainingLearningRate);
+ m_pBGModel->setBGModelParameter(5, trainingSteps);
m_pBGModel->UpdateModel(frame);
- img_foreground = cv::Mat(m_pBGModel->GetFG());
- img_background = cv::Mat(m_pBGModel->GetBG());
-
- if(showOutput)
+ img_foreground = cv::cvarrToMat(m_pBGModel->GetFG());
+ img_background = cv::cvarrToMat(m_pBGModel->GetBG());
+
+#ifndef MEX_COMPILE_FLAG
+ if (showOutput)
{
cv::imshow("SOM Mask", img_foreground);
cv::imshow("SOM Model", img_background);
}
+#endif
img_foreground.copyTo(img_output);
img_background.copyTo(img_bgmodel);
-
+
delete frame;
-
+
firstTime = false;
}
-//void LBAdaptiveSOM::finish(void)
-//{
-// delete m_pBGModel;
-//}
-
void LBAdaptiveSOM::saveConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/LBAdaptiveSOM.xml", 0, CV_STORAGE_WRITE);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_WRITE);
cvWriteInt(fs, "sensitivity", sensitivity);
cvWriteInt(fs, "trainingSensitivity", trainingSensitivity);
cvWriteInt(fs, "learningRate", learningRate);
cvWriteInt(fs, "trainingLearningRate", trainingLearningRate);
cvWriteInt(fs, "trainingSteps", trainingSteps);
-
cvWriteInt(fs, "showOutput", showOutput);
cvReleaseFileStorage(&fs);
@@ -95,15 +89,14 @@ void LBAdaptiveSOM::saveConfig()
void LBAdaptiveSOM::loadConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/LBAdaptiveSOM.xml", 0, CV_STORAGE_READ);
-
- sensitivity = cvReadIntByName(fs, 0, "sensitivity", 75);
- trainingSensitivity = cvReadIntByName(fs, 0, "trainingSensitivity", 245);
- learningRate = cvReadIntByName(fs, 0, "learningRate", 62);
- trainingLearningRate = cvReadIntByName(fs, 0, "trainingLearningRate", 255);
- trainingSteps = cvReadIntByName(fs, 0, "trainingSteps", 55);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_READ);
+ sensitivity = cvReadIntByName(fs, nullptr, "sensitivity", 75);
+ trainingSensitivity = cvReadIntByName(fs, nullptr, "trainingSensitivity", 245);
+ learningRate = cvReadIntByName(fs, nullptr, "learningRate", 62);
+ trainingLearningRate = cvReadIntByName(fs, nullptr, "trainingLearningRate", 255);
+ trainingSteps = cvReadIntByName(fs, nullptr, "trainingSteps", 55);
showOutput = cvReadIntByName(fs, 0, "showOutput", true);
cvReleaseFileStorage(&fs);
-}
\ No newline at end of file
+}
diff --git a/package_bgs/lb/LBAdaptiveSOM.h b/package_bgs/LBAdaptiveSOM.h
similarity index 55%
rename from package_bgs/lb/LBAdaptiveSOM.h
rename to package_bgs/LBAdaptiveSOM.h
index beaf77b..7671ae1 100644
--- a/package_bgs/lb/LBAdaptiveSOM.h
+++ b/package_bgs/LBAdaptiveSOM.h
@@ -16,41 +16,35 @@ along with BGSLibrary. If not, see .
*/
#pragma once
-#include
-#include
-
-
-#include "BGModelSom.h"
-
-#include "../IBGS.h"
+#include "lb/BGModelSom.h"
+#include "IBGS.h"
using namespace lb_library;
using namespace lb_library::AdaptiveSOM;
-class LBAdaptiveSOM : public IBGS
+namespace bgslibrary
{
-private:
- bool firstTime;
- bool showOutput;
-
- BGModel* m_pBGModel;
- int sensitivity;
- int trainingSensitivity;
- int learningRate;
- int trainingLearningRate;
- int trainingSteps;
-
- cv::Mat img_foreground;
- cv::Mat img_background;
-
-public:
- LBAdaptiveSOM();
- ~LBAdaptiveSOM();
-
- void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
- //void finish(void);
-
-private:
- void saveConfig();
- void loadConfig();
-};
\ No newline at end of file
+ namespace algorithms
+ {
+ class LBAdaptiveSOM : public IBGS
+ {
+ private:
+ BGModel* m_pBGModel;
+ int sensitivity;
+ int trainingSensitivity;
+ int learningRate;
+ int trainingLearningRate;
+ int trainingSteps;
+
+ public:
+ LBAdaptiveSOM();
+ ~LBAdaptiveSOM();
+
+ void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
+
+ private:
+ void saveConfig();
+ void loadConfig();
+ };
+ }
+}
diff --git a/package_bgs/lb/LBFuzzyAdaptiveSOM.cpp b/package_bgs/LBFuzzyAdaptiveSOM.cpp
similarity index 59%
rename from package_bgs/lb/LBFuzzyAdaptiveSOM.cpp
rename to package_bgs/LBFuzzyAdaptiveSOM.cpp
index 4ef8560..73df1d7 100644
--- a/package_bgs/lb/LBFuzzyAdaptiveSOM.cpp
+++ b/package_bgs/LBFuzzyAdaptiveSOM.cpp
@@ -16,10 +16,13 @@ along with BGSLibrary. If not, see .
*/
#include "LBFuzzyAdaptiveSOM.h"
-LBFuzzyAdaptiveSOM::LBFuzzyAdaptiveSOM() : firstTime(true), showOutput(true),
+using namespace bgslibrary::algorithms;
+
+LBFuzzyAdaptiveSOM::LBFuzzyAdaptiveSOM() :
sensitivity(90), trainingSensitivity(240), learningRate(38), trainingLearningRate(255), trainingSteps(81)
{
std::cout << "LBFuzzyAdaptiveSOM()" << std::endl;
+ setup("./config/LBFuzzyAdaptiveSOM.xml");
}
LBFuzzyAdaptiveSOM::~LBFuzzyAdaptiveSOM()
@@ -30,64 +33,55 @@ LBFuzzyAdaptiveSOM::~LBFuzzyAdaptiveSOM()
void LBFuzzyAdaptiveSOM::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
{
- if(img_input.empty())
- return;
+ init(img_input, img_output, img_bgmodel);
- loadConfig();
-
IplImage *frame = new IplImage(img_input);
-
- if(firstTime)
- {
- saveConfig();
+ if (firstTime)
+ {
int w = cvGetSize(frame).width;
int h = cvGetSize(frame).height;
- m_pBGModel = new BGModelFuzzySom(w,h);
+ m_pBGModel = new BGModelFuzzySom(w, h);
m_pBGModel->InitModel(frame);
}
-
- m_pBGModel->setBGModelParameter(0,sensitivity);
- m_pBGModel->setBGModelParameter(1,trainingSensitivity);
- m_pBGModel->setBGModelParameter(2,learningRate);
- m_pBGModel->setBGModelParameter(3,trainingLearningRate);
- m_pBGModel->setBGModelParameter(5,trainingSteps);
+
+ m_pBGModel->setBGModelParameter(0, sensitivity);
+ m_pBGModel->setBGModelParameter(1, trainingSensitivity);
+ m_pBGModel->setBGModelParameter(2, learningRate);
+ m_pBGModel->setBGModelParameter(3, trainingLearningRate);
+ m_pBGModel->setBGModelParameter(5, trainingSteps);
m_pBGModel->UpdateModel(frame);
- img_foreground = cv::Mat(m_pBGModel->GetFG());
- img_background = cv::Mat(m_pBGModel->GetBG());
-
- if(showOutput)
+ img_foreground = cv::cvarrToMat(m_pBGModel->GetFG());
+ img_background = cv::cvarrToMat(m_pBGModel->GetBG());
+
+#ifndef MEX_COMPILE_FLAG
+ if (showOutput)
{
cv::imshow("FSOM Mask", img_foreground);
cv::imshow("FSOM Model", img_background);
}
+#endif
img_foreground.copyTo(img_output);
img_background.copyTo(img_bgmodel);
-
+
delete frame;
-
+
firstTime = false;
}
-//void LBFuzzyAdaptiveSOM::finish(void)
-//{
-// //delete m_pBGModel;
-//}
-
void LBFuzzyAdaptiveSOM::saveConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/LBFuzzyAdaptiveSOM.xml", 0, CV_STORAGE_WRITE);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_WRITE);
cvWriteInt(fs, "sensitivity", sensitivity);
cvWriteInt(fs, "trainingSensitivity", trainingSensitivity);
cvWriteInt(fs, "learningRate", learningRate);
cvWriteInt(fs, "trainingLearningRate", trainingLearningRate);
cvWriteInt(fs, "trainingSteps", trainingSteps);
-
cvWriteInt(fs, "showOutput", showOutput);
cvReleaseFileStorage(&fs);
@@ -95,15 +89,14 @@ void LBFuzzyAdaptiveSOM::saveConfig()
void LBFuzzyAdaptiveSOM::loadConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/LBFuzzyAdaptiveSOM.xml", 0, CV_STORAGE_READ);
-
- sensitivity = cvReadIntByName(fs, 0, "sensitivity", 90);
- trainingSensitivity = cvReadIntByName(fs, 0, "trainingSensitivity", 240);
- learningRate = cvReadIntByName(fs, 0, "learningRate", 38);
- trainingLearningRate = cvReadIntByName(fs, 0, "trainingLearningRate", 255);
- trainingSteps = cvReadIntByName(fs, 0, "trainingSteps", 81);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_READ);
- showOutput = cvReadIntByName(fs, 0, "showOutput", true);
+ sensitivity = cvReadIntByName(fs, nullptr, "sensitivity", 90);
+ trainingSensitivity = cvReadIntByName(fs, nullptr, "trainingSensitivity", 240);
+ learningRate = cvReadIntByName(fs, nullptr, "learningRate", 38);
+ trainingLearningRate = cvReadIntByName(fs, nullptr, "trainingLearningRate", 255);
+ trainingSteps = cvReadIntByName(fs, nullptr, "trainingSteps", 81);
+ showOutput = cvReadIntByName(fs, nullptr, "showOutput", true);
cvReleaseFileStorage(&fs);
-}
\ No newline at end of file
+}
diff --git a/package_bgs/lb/LBFuzzyAdaptiveSOM.h b/package_bgs/LBFuzzyAdaptiveSOM.h
similarity index 55%
rename from package_bgs/lb/LBFuzzyAdaptiveSOM.h
rename to package_bgs/LBFuzzyAdaptiveSOM.h
index 9c11d75..6a4a85c 100644
--- a/package_bgs/lb/LBFuzzyAdaptiveSOM.h
+++ b/package_bgs/LBFuzzyAdaptiveSOM.h
@@ -16,41 +16,35 @@ along with BGSLibrary. If not, see .
*/
#pragma once
-#include
-#include
-
-
-#include "BGModelFuzzySom.h"
-
-#include "../IBGS.h"
+#include "IBGS.h"
+#include "lb/BGModelFuzzySom.h"
using namespace lb_library;
using namespace lb_library::FuzzyAdaptiveSOM;
-class LBFuzzyAdaptiveSOM : public IBGS
+namespace bgslibrary
{
-private:
- bool firstTime;
- bool showOutput;
-
- BGModel* m_pBGModel;
- int sensitivity;
- int trainingSensitivity;
- int learningRate;
- int trainingLearningRate;
- int trainingSteps;
-
- cv::Mat img_foreground;
- cv::Mat img_background;
-
-public:
- LBFuzzyAdaptiveSOM();
- ~LBFuzzyAdaptiveSOM();
-
- void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
- //void finish(void);
-
-private:
- void saveConfig();
- void loadConfig();
-};
\ No newline at end of file
+ namespace algorithms
+ {
+ class LBFuzzyAdaptiveSOM : public IBGS
+ {
+ private:
+ BGModel* m_pBGModel;
+ int sensitivity;
+ int trainingSensitivity;
+ int learningRate;
+ int trainingLearningRate;
+ int trainingSteps;
+
+ public:
+ LBFuzzyAdaptiveSOM();
+ ~LBFuzzyAdaptiveSOM();
+
+ void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
+
+ private:
+ void saveConfig();
+ void loadConfig();
+ };
+ }
+}
diff --git a/package_bgs/lb/LBFuzzyGaussian.cpp b/package_bgs/LBFuzzyGaussian.cpp
similarity index 59%
rename from package_bgs/lb/LBFuzzyGaussian.cpp
rename to package_bgs/LBFuzzyGaussian.cpp
index dc257bf..b161026 100644
--- a/package_bgs/lb/LBFuzzyGaussian.cpp
+++ b/package_bgs/LBFuzzyGaussian.cpp
@@ -16,9 +16,13 @@ along with BGSLibrary. If not, see .
*/
#include "LBFuzzyGaussian.h"
-LBFuzzyGaussian::LBFuzzyGaussian() : firstTime(true), showOutput(true), sensitivity(72), bgThreshold(162), learningRate(49), noiseVariance(195)
+using namespace bgslibrary::algorithms;
+
+LBFuzzyGaussian::LBFuzzyGaussian() :
+ sensitivity(72), bgThreshold(162), learningRate(49), noiseVariance(195)
{
std::cout << "LBFuzzyGaussian()" << std::endl;
+ setup("./config/LBFuzzyGaussian.xml");
}
LBFuzzyGaussian::~LBFuzzyGaussian()
@@ -29,62 +33,53 @@ LBFuzzyGaussian::~LBFuzzyGaussian()
void LBFuzzyGaussian::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
{
- if(img_input.empty())
- return;
+ init(img_input, img_output, img_bgmodel);
- loadConfig();
-
IplImage *frame = new IplImage(img_input);
-
- if(firstTime)
- {
- saveConfig();
+ if (firstTime)
+ {
int w = cvGetSize(frame).width;
int h = cvGetSize(frame).height;
- m_pBGModel = new BGModelFuzzyGauss(w,h);
+ m_pBGModel = new BGModelFuzzyGauss(w, h);
m_pBGModel->InitModel(frame);
}
-
- m_pBGModel->setBGModelParameter(0,sensitivity);
- m_pBGModel->setBGModelParameter(1,bgThreshold);
- m_pBGModel->setBGModelParameter(2,learningRate);
- m_pBGModel->setBGModelParameter(3,noiseVariance);
+
+ m_pBGModel->setBGModelParameter(0, sensitivity);
+ m_pBGModel->setBGModelParameter(1, bgThreshold);
+ m_pBGModel->setBGModelParameter(2, learningRate);
+ m_pBGModel->setBGModelParameter(3, noiseVariance);
m_pBGModel->UpdateModel(frame);
- img_foreground = cv::Mat(m_pBGModel->GetFG());
- img_background = cv::Mat(m_pBGModel->GetBG());
-
- if(showOutput)
+ img_foreground = cv::cvarrToMat(m_pBGModel->GetFG());
+ img_background = cv::cvarrToMat(m_pBGModel->GetBG());
+
+#ifndef MEX_COMPILE_FLAG
+ if (showOutput)
{
cv::imshow("FG Mask", img_foreground);
cv::imshow("FG Model", img_background);
}
+#endif
img_foreground.copyTo(img_output);
img_background.copyTo(img_bgmodel);
-
+
delete frame;
-
+
firstTime = false;
}
-//void LBFuzzyGaussian::finish(void)
-//{
-// delete m_pBGModel;
-//}
-
void LBFuzzyGaussian::saveConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/LBFuzzyGaussian.xml", 0, CV_STORAGE_WRITE);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_WRITE);
cvWriteInt(fs, "sensitivity", sensitivity);
cvWriteInt(fs, "bgThreshold", bgThreshold);
cvWriteInt(fs, "learningRate", learningRate);
cvWriteInt(fs, "noiseVariance", noiseVariance);
-
cvWriteInt(fs, "showOutput", showOutput);
cvReleaseFileStorage(&fs);
@@ -92,14 +87,13 @@ void LBFuzzyGaussian::saveConfig()
void LBFuzzyGaussian::loadConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/LBFuzzyGaussian.xml", 0, CV_STORAGE_READ);
-
- sensitivity = cvReadIntByName(fs, 0, "sensitivity", 72);
- bgThreshold = cvReadIntByName(fs, 0, "bgThreshold", 162);
- learningRate = cvReadIntByName(fs, 0, "learningRate", 49);
- noiseVariance = cvReadIntByName(fs, 0, "noiseVariance", 195);
-
- showOutput = cvReadIntByName(fs, 0, "showOutput", true);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_READ);
+
+ sensitivity = cvReadIntByName(fs, nullptr, "sensitivity", 72);
+ bgThreshold = cvReadIntByName(fs, nullptr, "bgThreshold", 162);
+ learningRate = cvReadIntByName(fs, nullptr, "learningRate", 49);
+ noiseVariance = cvReadIntByName(fs, nullptr, "noiseVariance", 195);
+ showOutput = cvReadIntByName(fs, nullptr, "showOutput", true);
cvReleaseFileStorage(&fs);
}
diff --git a/package_bgs/lb/LBFuzzyGaussian.h b/package_bgs/LBFuzzyGaussian.h
similarity index 56%
rename from package_bgs/lb/LBFuzzyGaussian.h
rename to package_bgs/LBFuzzyGaussian.h
index f76156e..53c2667 100644
--- a/package_bgs/lb/LBFuzzyGaussian.h
+++ b/package_bgs/LBFuzzyGaussian.h
@@ -16,40 +16,34 @@ along with BGSLibrary. If not, see .
*/
#pragma once
-#include
-#include
-
-
-#include "BGModelFuzzyGauss.h"
-
-#include "../IBGS.h"
+#include "IBGS.h"
+#include "lb/BGModelFuzzyGauss.h"
using namespace lb_library;
using namespace lb_library::FuzzyGaussian;
-class LBFuzzyGaussian : public IBGS
+namespace bgslibrary
{
-private:
- bool firstTime;
- bool showOutput;
-
- BGModel* m_pBGModel;
- int sensitivity;
- int bgThreshold;
- int learningRate;
- int noiseVariance;
-
- cv::Mat img_foreground;
- cv::Mat img_background;
-
-public:
- LBFuzzyGaussian();
- ~LBFuzzyGaussian();
-
- void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
- //void finish(void);
-
-private:
- void saveConfig();
- void loadConfig();
-};
\ No newline at end of file
+ namespace algorithms
+ {
+ class LBFuzzyGaussian : public IBGS
+ {
+ private:
+ BGModel* m_pBGModel;
+ int sensitivity;
+ int bgThreshold;
+ int learningRate;
+ int noiseVariance;
+
+ public:
+ LBFuzzyGaussian();
+ ~LBFuzzyGaussian();
+
+ void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
+
+ private:
+ void saveConfig();
+ void loadConfig();
+ };
+ }
+}
diff --git a/package_bgs/lb/LBMixtureOfGaussians.cpp b/package_bgs/LBMixtureOfGaussians.cpp
similarity index 59%
rename from package_bgs/lb/LBMixtureOfGaussians.cpp
rename to package_bgs/LBMixtureOfGaussians.cpp
index 8d235c5..6cd9c91 100644
--- a/package_bgs/lb/LBMixtureOfGaussians.cpp
+++ b/package_bgs/LBMixtureOfGaussians.cpp
@@ -16,9 +16,13 @@ along with BGSLibrary. If not, see .
*/
#include "LBMixtureOfGaussians.h"
-LBMixtureOfGaussians::LBMixtureOfGaussians() : firstTime(true), showOutput(true), sensitivity(81), bgThreshold(83), learningRate(59), noiseVariance(206)
+using namespace bgslibrary::algorithms;
+
+LBMixtureOfGaussians::LBMixtureOfGaussians() :
+ sensitivity(81), bgThreshold(83), learningRate(59), noiseVariance(206)
{
std::cout << "LBMixtureOfGaussians()" << std::endl;
+ setup("./config/LBMixtureOfGaussians.xml");
}
LBMixtureOfGaussians::~LBMixtureOfGaussians()
@@ -29,62 +33,53 @@ LBMixtureOfGaussians::~LBMixtureOfGaussians()
void LBMixtureOfGaussians::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
{
- if(img_input.empty())
- return;
+ init(img_input, img_output, img_bgmodel);
- loadConfig();
-
IplImage *frame = new IplImage(img_input);
-
- if(firstTime)
- {
- saveConfig();
+ if (firstTime)
+ {
int w = cvGetSize(frame).width;
int h = cvGetSize(frame).height;
- m_pBGModel = new BGModelMog(w,h);
+ m_pBGModel = new BGModelMog(w, h);
m_pBGModel->InitModel(frame);
}
-
- m_pBGModel->setBGModelParameter(0,sensitivity);
- m_pBGModel->setBGModelParameter(1,bgThreshold);
- m_pBGModel->setBGModelParameter(2,learningRate);
- m_pBGModel->setBGModelParameter(3,noiseVariance);
+
+ m_pBGModel->setBGModelParameter(0, sensitivity);
+ m_pBGModel->setBGModelParameter(1, bgThreshold);
+ m_pBGModel->setBGModelParameter(2, learningRate);
+ m_pBGModel->setBGModelParameter(3, noiseVariance);
m_pBGModel->UpdateModel(frame);
- img_foreground = cv::Mat(m_pBGModel->GetFG());
- img_background = cv::Mat(m_pBGModel->GetBG());
-
- if(showOutput)
+ img_foreground = cv::cvarrToMat(m_pBGModel->GetFG());
+ img_background = cv::cvarrToMat(m_pBGModel->GetBG());
+
+#ifndef MEX_COMPILE_FLAG
+ if (showOutput)
{
cv::imshow("MOG Mask", img_foreground);
cv::imshow("MOG Model", img_background);
}
+#endif
img_foreground.copyTo(img_output);
img_background.copyTo(img_bgmodel);
-
+
delete frame;
-
+
firstTime = false;
}
-//void LBMixtureOfGaussians::finish(void)
-//{
-// delete m_pBGModel;
-//}
-
void LBMixtureOfGaussians::saveConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/LBMixtureOfGaussians.xml", 0, CV_STORAGE_WRITE);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_WRITE);
cvWriteInt(fs, "sensitivity", sensitivity);
cvWriteInt(fs, "bgThreshold", bgThreshold);
cvWriteInt(fs, "learningRate", learningRate);
cvWriteInt(fs, "noiseVariance", noiseVariance);
-
cvWriteInt(fs, "showOutput", showOutput);
cvReleaseFileStorage(&fs);
@@ -92,14 +87,13 @@ void LBMixtureOfGaussians::saveConfig()
void LBMixtureOfGaussians::loadConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/LBMixtureOfGaussians.xml", 0, CV_STORAGE_READ);
-
- sensitivity = cvReadIntByName(fs, 0, "sensitivity", 81);
- bgThreshold = cvReadIntByName(fs, 0, "bgThreshold", 83);
- learningRate = cvReadIntByName(fs, 0, "learningRate", 59);
- noiseVariance = cvReadIntByName(fs, 0, "noiseVariance", 206);
-
- showOutput = cvReadIntByName(fs, 0, "showOutput", true);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_READ);
+
+ sensitivity = cvReadIntByName(fs, nullptr, "sensitivity", 81);
+ bgThreshold = cvReadIntByName(fs, nullptr, "bgThreshold", 83);
+ learningRate = cvReadIntByName(fs, nullptr, "learningRate", 59);
+ noiseVariance = cvReadIntByName(fs, nullptr, "noiseVariance", 206);
+ showOutput = cvReadIntByName(fs, nullptr, "showOutput", true);
cvReleaseFileStorage(&fs);
-}
\ No newline at end of file
+}
diff --git a/package_bgs/lb/LBMixtureOfGaussians.h b/package_bgs/LBMixtureOfGaussians.h
similarity index 56%
rename from package_bgs/lb/LBMixtureOfGaussians.h
rename to package_bgs/LBMixtureOfGaussians.h
index 3b1a96d..8d4cb56 100644
--- a/package_bgs/lb/LBMixtureOfGaussians.h
+++ b/package_bgs/LBMixtureOfGaussians.h
@@ -16,40 +16,35 @@ along with BGSLibrary. If not, see .
*/
#pragma once
-#include
-#include
-
-
-#include "BGModelMog.h"
-
-#include "../IBGS.h"
+#include "IBGS.h"
+#include "lb/BGModelMog.h"
using namespace lb_library;
using namespace lb_library::MixtureOfGaussians;
-class LBMixtureOfGaussians : public IBGS
+namespace bgslibrary
{
-private:
- bool firstTime;
- bool showOutput;
-
- BGModel* m_pBGModel;
- int sensitivity;
- int bgThreshold;
- int learningRate;
- int noiseVariance;
-
- cv::Mat img_foreground;
- cv::Mat img_background;
-
-public:
- LBMixtureOfGaussians();
- ~LBMixtureOfGaussians();
-
- void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
- //void finish(void);
-
-private:
- void saveConfig();
- void loadConfig();
-};
\ No newline at end of file
+ namespace algorithms
+ {
+ class LBMixtureOfGaussians : public IBGS
+ {
+ private:
+ BGModel* m_pBGModel;
+ int sensitivity;
+ int bgThreshold;
+ int learningRate;
+ int noiseVariance;
+
+ public:
+ LBMixtureOfGaussians();
+ ~LBMixtureOfGaussians();
+
+ void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
+
+ private:
+ void saveConfig();
+ void loadConfig();
+ };
+ }
+}
+
diff --git a/package_bgs/ck/LbpMrf.cpp b/package_bgs/LBP_MRF.cpp
similarity index 57%
rename from package_bgs/ck/LbpMrf.cpp
rename to package_bgs/LBP_MRF.cpp
index f3d068c..b9e6bbe 100644
--- a/package_bgs/ck/LbpMrf.cpp
+++ b/package_bgs/LBP_MRF.cpp
@@ -18,35 +18,29 @@ Csaba, Kertész: Texture-Based Foreground Detection, International Journal of Si
Image Processing and Pattern Recognition (IJSIP), Vol. 4, No. 4, 2011.
*/
-#include "LbpMrf.h"
+#include "LBP_MRF.h"
-#include "MotionDetection.hpp"
+using namespace bgslibrary::algorithms;
-LbpMrf::LbpMrf() : firstTime(true), Detector(NULL), showOutput(true)
+LBP_MRF::LBP_MRF() :
+ Detector(nullptr)
{
- std::cout << "LbpMrf()" << std::endl;
+ std::cout << "LBP_MRF()" << std::endl;
+ setup("./config/LBP_MRF.xml");
Detector = new MotionDetection();
Detector->SetMode(MotionDetection::md_LBPHistograms);
}
-LbpMrf::~LbpMrf()
+LBP_MRF::~LBP_MRF()
{
- std::cout << "~LbpMrf()" << std::endl;
+ std::cout << "~LBP_MRF()" << std::endl;
delete Detector;
- Detector = NULL;
+ Detector = nullptr;
}
-void LbpMrf::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
+void LBP_MRF::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel)
{
- if(img_input.empty())
- return;
-
- loadConfig();
-
- if(firstTime)
- {
- saveConfig();
- }
+ init(img_input, img_output, img_bgmodel);
IplImage TempImage(img_input);
MEImage InputImage(img_input.cols, img_input.rows, img_input.channels());
@@ -56,32 +50,35 @@ void LbpMrf::process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img
Detector->DetectMotions(InputImage);
Detector->GetMotionsMask(OutputImage);
- img_output = (IplImage*)OutputImage.GetIplImage();
- bitwise_not(img_output, img_bgmodel);
+ img_foreground = cv::cvarrToMat((IplImage*)OutputImage.GetIplImage());
+ //bitwise_not(img_foreground, img_background);
+ img_background = cv::Mat::zeros(img_input.size(), img_input.type());
+
+#ifndef MEX_COMPILE_FLAG
+ if (showOutput)
+ cv::imshow("LBP-MRF FG", img_foreground);
+#endif
- if(showOutput)
- {
- cv::imshow("LBP-MRF FG", img_output);
- cv::imshow("LBP-MRF BG", img_bgmodel);
- }
+ img_foreground.copyTo(img_output);
+ img_background.copyTo(img_bgmodel);
firstTime = false;
}
-void LbpMrf::saveConfig()
+void LBP_MRF::saveConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/LbpMrf.xml", 0, CV_STORAGE_WRITE);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_WRITE);
cvWriteInt(fs, "showOutput", showOutput);
cvReleaseFileStorage(&fs);
}
-void LbpMrf::loadConfig()
+void LBP_MRF::loadConfig()
{
- CvFileStorage* fs = cvOpenFileStorage("./config/LbpMrf.xml", 0, CV_STORAGE_READ);
+ CvFileStorage* fs = cvOpenFileStorage(config_xml.c_str(), nullptr, CV_STORAGE_READ);
- showOutput = cvReadIntByName(fs, 0, "showOutput", true);
+ showOutput = cvReadIntByName(fs, nullptr, "showOutput", true);
cvReleaseFileStorage(&fs);
}
diff --git a/package_bgs/WeightedMovingMeanBGS.h b/package_bgs/LBP_MRF.h
similarity index 58%
rename from package_bgs/WeightedMovingMeanBGS.h
rename to package_bgs/LBP_MRF.h
index 6f72306..a6e5c05 100644
--- a/package_bgs/WeightedMovingMeanBGS.h
+++ b/package_bgs/LBP_MRF.h
@@ -16,32 +16,28 @@ along with BGSLibrary. If not, see .
*/
#pragma once
-#include
-#include
-
-
#include "IBGS.h"
+#include "LBP_MRF/MotionDetection.hpp"
-class WeightedMovingMeanBGS : public IBGS
+namespace bgslibrary
{
-private:
- bool firstTime;
- cv::Mat img_input_prev_1;
- cv::Mat img_input_prev_2;
- bool enableWeight;
- bool enableThreshold;
- int threshold;
- bool showOutput;
- bool showBackground;
-
-public:
- WeightedMovingMeanBGS();
- ~WeightedMovingMeanBGS();
-
- void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
-
-private:
- void saveConfig();
- void loadConfig();
-};
-
+ namespace algorithms
+ {
+ class LBP_MRF : public IBGS
+ {
+ private:
+ MotionDetection* Detector;
+ cv::Mat img_segmentation;
+
+ public:
+ LBP_MRF();
+ ~LBP_MRF();
+
+ void process(const cv::Mat &img_input, cv::Mat &img_output, cv::Mat &img_bgmodel);
+
+ private:
+ void saveConfig();
+ void loadConfig();
+ };
+ }
+}
diff --git a/package_bgs/LBP_MRF/MEDefs.cpp b/package_bgs/LBP_MRF/MEDefs.cpp
new file mode 100644
index 0000000..95b8033
--- /dev/null
+++ b/package_bgs/LBP_MRF/MEDefs.cpp
@@ -0,0 +1,57 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+/*
+ * This file is part of the AiBO+ project
+ *
+ * Copyright (C) 2005-2013 Csaba Kertész (csaba.kertesz@gmail.com)
+ *
+ * AiBO+ is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * AiBO+ is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Street #330, Boston, MA 02111-1307, USA.
+ *
+ */
+
+#include "MEDefs.hpp"
+
+#include
+
+float MERound(float number)
+{
+ double FracPart = 0.0;
+ double IntPart = 0.0;
+ float Ret = 0.0;
+
+ FracPart = modf((double)number, &IntPart);
+ if (number >= 0)
+ {
+ Ret = (float)(FracPart >= 0.5 ? IntPart + 1 : IntPart);
+ }
+ else {
+ Ret = (float)(FracPart <= -0.5 ? IntPart - 1 : IntPart);
+ }
+ return Ret;
+}
diff --git a/package_bgs/ck/MEDefs.hpp b/package_bgs/LBP_MRF/MEDefs.hpp
similarity index 73%
rename from package_bgs/ck/MEDefs.hpp
rename to package_bgs/LBP_MRF/MEDefs.hpp
index d5bc246..a886ee9 100644
--- a/package_bgs/ck/MEDefs.hpp
+++ b/package_bgs/LBP_MRF/MEDefs.hpp
@@ -1,4 +1,20 @@
/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+/*
* This file is part of the AiBO+ project
*
* Copyright (C) 2005-2013 Csaba Kertész (csaba.kertesz@gmail.com)
@@ -18,16 +34,9 @@
* Foundation, Inc., 59 Temple Street #330, Boston, MA 02111-1307, USA.
*
*/
+#pragma once
-#ifndef MEDefs_hpp
-#define MEDefs_hpp
-
-/**
- * @addtogroup mindeye
- * @{
- */
-
-/// Pi value
+ /// Pi value
#ifndef ME_PI_VALUE
#define ME_PI_VALUE 3.14159265
#endif
@@ -79,5 +88,3 @@ const T& MEBound(const T& min, const T& val, const T& max)
float MERound(float number);
/** @} */
-
-#endif
diff --git a/package_bgs/ck/MEHistogram.cpp b/package_bgs/LBP_MRF/MEHistogram.cpp
similarity index 54%
rename from package_bgs/ck/MEHistogram.cpp
rename to package_bgs/LBP_MRF/MEHistogram.cpp
index 09a9672..17c77fd 100644
--- a/package_bgs/ck/MEHistogram.cpp
+++ b/package_bgs/LBP_MRF/MEHistogram.cpp
@@ -1,4 +1,20 @@
/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+/*
* This file is part of the AiBO+ project
*
* Copyright (C) 2005-2013 Csaba Kertész (csaba.kertesz@gmail.com)
@@ -45,7 +61,7 @@ MEHistogram::~MEHistogram()
void MEHistogram::Clear()
{
- memset(&HistogramData, 0, 256*sizeof(int));
+ memset(&HistogramData, 0, 256 * sizeof(int));
}
@@ -77,11 +93,11 @@ void MEHistogram::Calculate(MEImage& image, int channel, HistogramType mode)
unsigned char *ImageData = image.GetImageData();
int rowStart = 0;
- for (int i = image.GetHeight()-1; i >= 0; i--)
+ for (int i = image.GetHeight() - 1; i >= 0; i--)
{
- for (int i1 = (image.GetWidth()-1)*image.GetLayers()+Channel-1; i1 >= Channel-1; i1 -= image.GetLayers())
+ for (int i1 = (image.GetWidth() - 1)*image.GetLayers() + Channel - 1; i1 >= Channel - 1; i1 -= image.GetLayers())
{
- HistogramData[ImageData[rowStart+i1]]++;
+ HistogramData[ImageData[rowStart + i1]]++;
}
rowStart += image.GetRowWidth();
}
@@ -99,11 +115,11 @@ void MEHistogram::Calculate(MEImage& image, HistogramType mode)
int RowStart = 0;
int RowWidth = image.GetRowWidth();
- for (int i = image.GetHeight()-1; i >= 0; i--)
+ for (int i = image.GetHeight() - 1; i >= 0; i--)
{
- for (int i1 = image.GetWidth()*image.GetLayers()-1; i1 >= 0; i1--)
+ for (int i1 = image.GetWidth()*image.GetLayers() - 1; i1 >= 0; i1--)
{
- HistogramData[ImageData[RowStart+i1]]++;
+ HistogramData[ImageData[RowStart + i1]]++;
}
RowStart += RowWidth;
}
@@ -126,16 +142,16 @@ void MEHistogram::Calculate(MEImage& image, int channel, int x0, int y0, int x1,
// Compute the correct region coordinates and check them
X0 = X0 < 0 ? 0 : X0;
Y0 = Y0 < 0 ? 0 : Y0;
- X1 = X1 > image.GetWidth()-1 ? image.GetWidth()-1 : X1;
- Y1 = Y1 > image.GetHeight()-1 ? image.GetHeight()-1 : Y1;
+ X1 = X1 > image.GetWidth() - 1 ? image.GetWidth() - 1 : X1;
+ Y1 = Y1 > image.GetHeight() - 1 ? image.GetHeight() - 1 : Y1;
RowStart = Y0*image.GetRowWidth();
for (int i = Y1; i >= Y0; --i)
{
- for (int i1 = X1*image.GetLayers()+Channel-1; i1 >= X0*image.GetLayers()+Channel-1;
- i1 -= image.GetLayers())
+ for (int i1 = X1*image.GetLayers() + Channel - 1; i1 >= X0*image.GetLayers() + Channel - 1;
+ i1 -= image.GetLayers())
{
- HistogramData[ImageData[RowStart+i1]]++;
+ HistogramData[ImageData[RowStart + i1]]++;
}
RowStart += RowWidth;
}
@@ -242,70 +258,70 @@ bool MEHistogram::Stretch(StretchType mode)
switch (mode)
{
- case s_OwnMode:
- Percent = 20;
+ case s_OwnMode:
+ Percent = 20;
+ MinIndex = GetLowestLimitIndex(Percent);
+ MaxIndex = GetHighestLimitIndex(Percent);
+
+ while ((abs(MaxIndex - MinIndex) < 52) && (Percent > 1))
+ {
+ Percent = Percent / 2;
MinIndex = GetLowestLimitIndex(Percent);
MaxIndex = GetHighestLimitIndex(Percent);
- while ((abs(MaxIndex-MinIndex) < 52) && (Percent > 1))
+ // The calculation gives wrong answer back
+ if (MinIndex == 0 && MaxIndex == 255)
{
- Percent = Percent / 2;
- MinIndex = GetLowestLimitIndex(Percent);
- MaxIndex = GetHighestLimitIndex(Percent);
-
- // The calculation gives wrong answer back
- if (MinIndex == 0 && MaxIndex == 255)
- {
- MinIndex = 128;
- MaxIndex = 128;
- Ret = false;
- }
+ MinIndex = 128;
+ MaxIndex = 128;
+ Ret = false;
}
- break;
+ }
+ break;
- case s_GimpMode:
- Count = GetPowerAmount(0, 255);
- NewCount = 0;
+ case s_GimpMode:
+ Count = GetPowerAmount(0, 255);
+ NewCount = 0;
- for (int i = 0; i < 255; i++)
- {
- double Value = 0.0;
- double NextValue = 0.0;
+ for (int i = 0; i < 255; i++)
+ {
+ double Value = 0.0;
+ double NextValue = 0.0;
- Value = HistogramData[i];
- NextValue = HistogramData[i+1];
- NewCount += Value;
- Percentage = NewCount / Count;
- NextPercentage = (NewCount+NextValue) / Count;
+ Value = HistogramData[i];
+ NextValue = HistogramData[i + 1];
+ NewCount += Value;
+ Percentage = NewCount / Count;
+ NextPercentage = (NewCount + NextValue) / Count;
- if (fabs(Percentage-0.006) < fabs(NextPercentage-0.006))
- {
- MinIndex = i+1;
- break;
- }
- }
- NewCount = 0.0;
- for (int i = 255; i > 0; i--)
+ if (fabs(Percentage - 0.006) < fabs(NextPercentage - 0.006))
{
- double Value = 0.0;
- double NextValue = 0.0;
+ MinIndex = i + 1;
+ break;
+ }
+ }
+ NewCount = 0.0;
+ for (int i = 255; i > 0; i--)
+ {
+ double Value = 0.0;
+ double NextValue = 0.0;
- Value = HistogramData[i];
- NextValue = HistogramData[i-1];
- NewCount += Value;
- Percentage = NewCount / Count;
- NextPercentage = (NewCount+NextValue) / Count;
+ Value = HistogramData[i];
+ NextValue = HistogramData[i - 1];
+ NewCount += Value;
+ Percentage = NewCount / Count;
+ NextPercentage = (NewCount + NextValue) / Count;
- if (fabs(Percentage-0.006) < fabs(NextPercentage-0.006))
- {
- MaxIndex = i-1;
- break;
- }
+ if (fabs(Percentage - 0.006) < fabs(NextPercentage - 0.006))
+ {
+ MaxIndex = i - 1;
+ break;
}
- break;
+ }
+ break;
- default:
- break;
+ default:
+ break;
}
if (MaxIndex <= MinIndex)
@@ -314,8 +330,8 @@ bool MEHistogram::Stretch(StretchType mode)
MaxIndex = 255;
Ret = false;
}
- if (MaxIndex-MinIndex <= 10 ||
- (MaxIndex-MinIndex <= 20 && (float)GetPowerAmount(MinIndex, MaxIndex) / GetPowerAmount(0, 255) < 0.20))
+ if (MaxIndex - MinIndex <= 10 ||
+ (MaxIndex - MinIndex <= 20 && (float)GetPowerAmount(MinIndex, MaxIndex) / GetPowerAmount(0, 255) < 0.20))
{
MinIndex = 0;
MaxIndex = 255;
@@ -327,7 +343,7 @@ bool MEHistogram::Stretch(StretchType mode)
for (int i = 0; i < 256; ++i)
{
- TransformedHistogram[i] = (unsigned char)MEBound(0, 255*(i-MinIndex) / (MaxIndex-MinIndex), 255);
+ TransformedHistogram[i] = (unsigned char)MEBound(0, 255 * (i - MinIndex) / (MaxIndex - MinIndex), 255);
}
for (int i = 0; i < 256; ++i)
{
@@ -371,7 +387,7 @@ void MEHistogramTransform::HistogramStretch(MEImage& image, TransformType time_m
for (int l = 1; l < image.GetLayers(); l++)
{
- RedChannel.Calculate(image, l+1, MEHistogram::h_Add);
+ RedChannel.Calculate(image, l + 1, MEHistogram::h_Add);
}
RedChannel.Stretch(StretchMode);
if (time_mode == t_Discrete && !DiscreteStretchingDone)
@@ -383,45 +399,46 @@ void MEHistogramTransform::HistogramStretch(MEImage& image, TransformType time_m
int RowStart = 0;
int RowWidth = image.GetRowWidth();
- for (int i = image.GetHeight()-1; i >= 0; i--)
+ for (int i = image.GetHeight() - 1; i >= 0; i--)
{
- for (int i1 = image.GetWidth()*image.GetLayers()-1; i1 >= 0; i1--)
+ for (int i1 = image.GetWidth()*image.GetLayers() - 1; i1 >= 0; i1--)
{
- ImageData[RowStart+i1] = RedChannel.HistogramData[ImageData[RowStart+i1]];
+ ImageData[RowStart + i1] = RedChannel.HistogramData[ImageData[RowStart + i1]];
}
RowStart += RowWidth;
}
- } else
- if (ChannelMode == p_SeparateChannels)
- {
- if (time_mode == t_Continuous || (time_mode == t_Discrete && !DiscreteStretchingDone))
+ }
+ else
+ if (ChannelMode == p_SeparateChannels)
{
- RedChannel.Calculate(image, 1, MEHistogram::h_Overwrite);
- GreenChannel.Calculate(image, 2, MEHistogram::h_Overwrite);
- BlueChannel.Calculate(image, 3, MEHistogram::h_Overwrite);
- RedChannel.Stretch(StretchMode);
- GreenChannel.Stretch(StretchMode);
- BlueChannel.Stretch(StretchMode);
- if (time_mode == t_Discrete && !DiscreteStretchingDone)
+ if (time_mode == t_Continuous || (time_mode == t_Discrete && !DiscreteStretchingDone))
{
- DiscreteStretchingDone = true;
+ RedChannel.Calculate(image, 1, MEHistogram::h_Overwrite);
+ GreenChannel.Calculate(image, 2, MEHistogram::h_Overwrite);
+ BlueChannel.Calculate(image, 3, MEHistogram::h_Overwrite);
+ RedChannel.Stretch(StretchMode);
+ GreenChannel.Stretch(StretchMode);
+ BlueChannel.Stretch(StretchMode);
+ if (time_mode == t_Discrete && !DiscreteStretchingDone)
+ {
+ DiscreteStretchingDone = true;
+ }
}
- }
- unsigned char *ImageData = image.GetImageData();
- int RowStart = 0;
- int RowWidth = image.GetRowWidth();
+ unsigned char *ImageData = image.GetImageData();
+ int RowStart = 0;
+ int RowWidth = image.GetRowWidth();
- for (int i = image.GetHeight()-1; i >= 0; i--)
- {
- for (int i1 = image.GetWidth()*image.GetLayers()-3; i1 >= 0; i1 -= 3)
+ for (int i = image.GetHeight() - 1; i >= 0; i--)
{
- ImageData[RowStart+i1] = RedChannel.HistogramData[ImageData[RowStart+i1]];
- ImageData[RowStart+i1+1] = GreenChannel.HistogramData[ImageData[RowStart+i1+1]];
- ImageData[RowStart+i1+2] = BlueChannel.HistogramData[ImageData[RowStart+i1+2]];
+ for (int i1 = image.GetWidth()*image.GetLayers() - 3; i1 >= 0; i1 -= 3)
+ {
+ ImageData[RowStart + i1] = RedChannel.HistogramData[ImageData[RowStart + i1]];
+ ImageData[RowStart + i1 + 1] = GreenChannel.HistogramData[ImageData[RowStart + i1 + 1]];
+ ImageData[RowStart + i1 + 2] = BlueChannel.HistogramData[ImageData[RowStart + i1 + 2]];
+ }
+ RowStart += RowWidth;
}
- RowStart += RowWidth;
}
- }
}
@@ -433,72 +450,72 @@ void MEHistogramTransform::HistogramEqualize(MEImage& image)
switch (image.GetLayers())
{
- case 1:
- // Grayscale image
- cvDest8bitImg = cvCreateImage(cvSize(image.GetWidth(), image.GetHeight()), 8, 1);
- cvEqualizeHist((IplImage*)image.GetIplImage(), cvDest8bitImg);
- image.SetIplImage((void*)cvDest8bitImg);
- cvReleaseImage(&cvDest8bitImg);
- break;
-
- case 3:
- // RGB image
- cvDestImg = cvCreateImage(cvSize(image.GetWidth(), image.GetHeight()), 8, 3);
- IplImage *cvR, *cvG, *cvB;
-
- cvR = cvCreateImage(cvSize(image.GetWidth(), image.GetHeight()), 8, 1);
- cvG = cvCreateImage(cvSize(image.GetWidth(), image.GetHeight()), 8, 1);
- cvB = cvCreateImage(cvSize(image.GetWidth(), image.GetHeight()), 8, 1);
-
- cvSplit((IplImage*)image.GetIplImage(), cvR, cvG, cvB, NULL);
- cvEqualizeHist(cvR, cvR);
- cvEqualizeHist(cvG, cvG);
- cvEqualizeHist(cvB, cvB);
- cvMerge(cvR, cvG, cvB, NULL, cvDestImg);
-
- image.SetIplImage((void*)cvDestImg);
- cvReleaseImage(&cvR);
- cvReleaseImage(&cvG);
- cvReleaseImage(&cvB);
- cvReleaseImage(&cvDestImg);
- break;
-
- default:
- break;
+ case 1:
+ // Grayscale image
+ cvDest8bitImg = cvCreateImage(cvSize(image.GetWidth(), image.GetHeight()), 8, 1);
+ cvEqualizeHist((IplImage*)image.GetIplImage(), cvDest8bitImg);
+ image.SetIplImage((void*)cvDest8bitImg);
+ cvReleaseImage(&cvDest8bitImg);
+ break;
+
+ case 3:
+ // RGB image
+ cvDestImg = cvCreateImage(cvSize(image.GetWidth(), image.GetHeight()), 8, 3);
+ IplImage *cvR, *cvG, *cvB;
+
+ cvR = cvCreateImage(cvSize(image.GetWidth(), image.GetHeight()), 8, 1);
+ cvG = cvCreateImage(cvSize(image.GetWidth(), image.GetHeight()), 8, 1);
+ cvB = cvCreateImage(cvSize(image.GetWidth(), image.GetHeight()), 8, 1);
+
+ cvSplit((IplImage*)image.GetIplImage(), cvR, cvG, cvB, NULL);
+ cvEqualizeHist(cvR, cvR);
+ cvEqualizeHist(cvG, cvG);
+ cvEqualizeHist(cvB, cvB);
+ cvMerge(cvR, cvG, cvB, NULL, cvDestImg);
+
+ image.SetIplImage((void*)cvDestImg);
+ cvReleaseImage(&cvR);
+ cvReleaseImage(&cvG);
+ cvReleaseImage(&cvB);
+ cvReleaseImage(&cvDestImg);
+ break;
+
+ default:
+ break;
}
}
void MEHistogramTransform::SetStretchProcessingMode(ProcessingType new_channel_mode,
- MEHistogram::StretchType new_stretch_mode)
+ MEHistogram::StretchType new_stretch_mode)
{
DiscreteStretchingDone = false;
- switch(new_channel_mode)
+ switch (new_channel_mode)
{
- case p_SeparateChannels:
- ChannelMode = new_channel_mode;
- break;
+ case p_SeparateChannels:
+ ChannelMode = new_channel_mode;
+ break;
- case p_Average:
- ChannelMode = new_channel_mode;
- break;
+ case p_Average:
+ ChannelMode = new_channel_mode;
+ break;
- default:
- break;
+ default:
+ break;
}
- switch(new_stretch_mode)
+ switch (new_stretch_mode)
{
- case MEHistogram::s_OwnMode:
- StretchMode = new_stretch_mode;
- break;
+ case MEHistogram::s_OwnMode:
+ StretchMode = new_stretch_mode;
+ break;
- case MEHistogram::s_GimpMode:
- StretchMode = new_stretch_mode;
- break;
+ case MEHistogram::s_GimpMode:
+ StretchMode = new_stretch_mode;
+ break;
- default:
- break;
+ default:
+ break;
}
}
diff --git a/package_bgs/ck/MEHistogram.hpp b/package_bgs/LBP_MRF/MEHistogram.hpp
similarity index 93%
rename from package_bgs/ck/MEHistogram.hpp
rename to package_bgs/LBP_MRF/MEHistogram.hpp
index 5b2b47f..0b2fb0d 100644
--- a/package_bgs/ck/MEHistogram.hpp
+++ b/package_bgs/LBP_MRF/MEHistogram.hpp
@@ -1,4 +1,20 @@
/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+/*
* This file is part of the AiBO+ project
*
* Copyright (C) 2005-2013 Csaba Kertész (csaba.kertesz@gmail.com)
@@ -18,14 +34,12 @@
* Foundation, Inc., 59 Temple Street #330, Boston, MA 02111-1307, USA.
*
*/
+#pragma once
-#ifndef MEHistogram_hpp
-#define MEHistogram_hpp
-
-/**
- * @addtogroup mindeye
- * @{
- */
+ /**
+ * @addtogroup mindeye
+ * @{
+ */
class MEImage;
@@ -344,5 +358,3 @@ class MEHistogramTransform
};
/** @} */
-
-#endif
diff --git a/package_bgs/ck/MEImage.cpp b/package_bgs/LBP_MRF/MEImage.cpp
similarity index 50%
rename from package_bgs/ck/MEImage.cpp
rename to package_bgs/LBP_MRF/MEImage.cpp
index 7373834..b01d494 100644
--- a/package_bgs/ck/MEImage.cpp
+++ b/package_bgs/LBP_MRF/MEImage.cpp
@@ -1,4 +1,20 @@
/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+/*
* This file is part of the AiBO+ project
*
* Copyright (C) 2005-2013 Csaba Kertész (csaba.kertesz@gmail.com)
@@ -30,17 +46,17 @@
cvReleaseImage((IplImage**)&image_ptr); \
image_ptr = NULL;
-// RGB to YUV transform
+ // RGB to YUV transform
const float RGBtoYUVMatrix[3][3] =
- {{ 0.299, 0.587, 0.114 },
- { -0.147, -0.289, 0.436 },
- { 0.615, -0.515, -0.100 }};
+{ { 0.299, 0.587, 0.114 },
+ { -0.147, -0.289, 0.436 },
+ { 0.615, -0.515, -0.100 } };
// RGB to YIQ transform
const float RGBtoYIQMatrix[3][3] =
- {{ 0.299, 0.587, 0.114 },
- { 0.596, -0.274, -0.322 },
- { 0.212, -0.523, 0.311 }};
+{ { 0.299, 0.587, 0.114 },
+ { 0.596, -0.274, -0.322 },
+ { 0.212, -0.523, 0.311 } };
MEImage::MEImage(int width, int height, int layers) : cvImg(NULL)
{
@@ -74,15 +90,15 @@ void MEImage::GetLayer(MEImage& new_layer, int layer_number) const
int LayerNumber = layer_number;
if ((new_layer.GetWidth() != ME_CAST_TO_IPLIMAGE(cvImg)->width) ||
- (new_layer.GetHeight() != ME_CAST_TO_IPLIMAGE(cvImg)->height) ||
- (new_layer.GetLayers() != 1))
+ (new_layer.GetHeight() != ME_CAST_TO_IPLIMAGE(cvImg)->height) ||
+ (new_layer.GetLayers() != 1))
{
new_layer.Realloc(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height, 1);
}
if (ME_CAST_TO_IPLIMAGE(cvImg)->nChannels < LayerNumber)
{
printf("The given layer number is too large (%d > %d)\n",
- LayerNumber, ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
+ LayerNumber, ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
LayerNumber = ME_CAST_TO_IPLIMAGE(cvImg)->nChannels;
}
@@ -103,17 +119,17 @@ void MEImage::SetLayer(MEImage& layer, int layer_number)
int LayerNumber = layer_number;
if (layer.GetWidth() != ME_CAST_TO_IPLIMAGE(cvImg)->width ||
- layer.GetHeight() != ME_CAST_TO_IPLIMAGE(cvImg)->height)
+ layer.GetHeight() != ME_CAST_TO_IPLIMAGE(cvImg)->height)
{
printf("The dimensions of the layer and "
- "destination image is different (%dx%d <> %dx%d)\n",
- layer.GetWidth(), layer.GetHeight(), ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height);
+ "destination image is different (%dx%d <> %dx%d)\n",
+ layer.GetWidth(), layer.GetHeight(), ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height);
return;
}
if (ME_CAST_TO_IPLIMAGE(cvImg)->nChannels < LayerNumber)
{
printf("The given layer number is too large (%d > %d)\n",
- LayerNumber, ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
+ LayerNumber, ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
LayerNumber = ME_CAST_TO_IPLIMAGE(cvImg)->nChannels;
}
if (LayerNumber <= 0)
@@ -124,7 +140,7 @@ void MEImage::SetLayer(MEImage& layer, int layer_number)
if (layer.GetLayers() != 1)
{
printf("The layer image has not one color channel (1 != %d)\n",
- layer.GetLayers());
+ layer.GetLayers());
return;
}
cvSetImageCOI(ME_CAST_TO_IPLIMAGE(cvImg), LayerNumber);
@@ -223,7 +239,7 @@ void MEImage::SetData(unsigned char* image_data, int width, int height, int chan
{
_Init(width, height, channels);
- for (int y = height-1; y >= 0; --y)
+ for (int y = height - 1; y >= 0; --y)
{
int Start = GetRowWidth()*y;
int Start2 = width*channels*y;
@@ -235,7 +251,7 @@ void MEImage::SetData(unsigned char* image_data, int width, int height, int chan
float MEImage::GetRatio() const
{
- return ME_CAST_TO_IPLIMAGE(cvImg) ? (float)ME_CAST_TO_IPLIMAGE(cvImg)->height/(float)ME_CAST_TO_IPLIMAGE(cvImg)->width : 0.0;
+ return ME_CAST_TO_IPLIMAGE(cvImg) ? (float)ME_CAST_TO_IPLIMAGE(cvImg)->height / (float)ME_CAST_TO_IPLIMAGE(cvImg)->width : 0.0;
}
@@ -289,7 +305,7 @@ void MEImage::ResizeScaleY(int new_height)
printf("Invalid new height: %d < 1\n", new_height);
return;
}
- Resize((int)((float)new_height*1/GetRatio()), new_height);
+ Resize((int)((float)new_height * 1 / GetRatio()), new_height);
}
@@ -322,19 +338,19 @@ void MEImage::Crop(int x1, int y1, int x2, int y2)
NewY2 = (NewY2 < 0) ? 0 : NewY2;
NewY2 = (NewY2 > ME_CAST_TO_IPLIMAGE(cvImg)->height) ? ME_CAST_TO_IPLIMAGE(cvImg)->height : NewY2;
- if ((NewX2-NewX1) <= 0)
+ if ((NewX2 - NewX1) <= 0)
{
- printf("Invalid new width: %d <= 0\n", NewX2-NewX1);
+ printf("Invalid new width: %d <= 0\n", NewX2 - NewX1);
return;
}
- if ((NewY2-NewY1) <= 0)
+ if ((NewY2 - NewY1) <= 0)
{
- printf("Invalid new height: %d <= 0\n", NewY2-NewY1);
+ printf("Invalid new height: %d <= 0\n", NewY2 - NewY1);
return;
}
- IplImage* TempImg = cvCreateImage(cvSize(NewX2-NewX1, NewY2-NewY1), 8, ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
+ IplImage* TempImg = cvCreateImage(cvSize(NewX2 - NewX1, NewY2 - NewY1), 8, ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
- cvSetImageROI(ME_CAST_TO_IPLIMAGE(cvImg), cvRect(NewX1, NewY1, NewX2-NewX1, NewY2-NewY1));
+ cvSetImageROI(ME_CAST_TO_IPLIMAGE(cvImg), cvRect(NewX1, NewY1, NewX2 - NewX1, NewY2 - NewY1));
cvCopy(ME_CAST_TO_IPLIMAGE(cvImg), TempImg);
ME_RELEASE_IPLIMAGE(cvImg);
cvImg = TempImg;
@@ -367,13 +383,13 @@ void MEImage::CopyImageInside(int x, int y, MEImage& source_image)
NewY = 0;
if (NewY > ME_CAST_TO_IPLIMAGE(cvImg)->height)
NewY = ME_CAST_TO_IPLIMAGE(cvImg)->height;
- if (NewX+PasteLengthX > ME_CAST_TO_IPLIMAGE(cvImg)->width)
- PasteLengthX = ME_CAST_TO_IPLIMAGE(cvImg)->width-NewX;
- if (NewY+PasteLengthY > ME_CAST_TO_IPLIMAGE(cvImg)->height)
- PasteLengthY = ME_CAST_TO_IPLIMAGE(cvImg)->height-NewY;
+ if (NewX + PasteLengthX > ME_CAST_TO_IPLIMAGE(cvImg)->width)
+ PasteLengthX = ME_CAST_TO_IPLIMAGE(cvImg)->width - NewX;
+ if (NewY + PasteLengthY > ME_CAST_TO_IPLIMAGE(cvImg)->height)
+ PasteLengthY = ME_CAST_TO_IPLIMAGE(cvImg)->height - NewY;
if (PasteLengthX != source_image.GetWidth() ||
- PasteLengthY != source_image.GetHeight())
+ PasteLengthY != source_image.GetHeight())
{
source_image.Resize(PasteLengthX, PasteLengthY);
}
@@ -386,8 +402,8 @@ void MEImage::CopyImageInside(int x, int y, MEImage& source_image)
void MEImage::Erode(int iterations)
{
IplImage* TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width,
- ME_CAST_TO_IPLIMAGE(cvImg)->height),
- 8, ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
+ ME_CAST_TO_IPLIMAGE(cvImg)->height),
+ 8, ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
cvErode(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, NULL, iterations);
ME_RELEASE_IPLIMAGE(cvImg);
@@ -398,8 +414,8 @@ void MEImage::Erode(int iterations)
void MEImage::Dilate(int iterations)
{
IplImage* TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width,
- ME_CAST_TO_IPLIMAGE(cvImg)->height),
- 8, ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
+ ME_CAST_TO_IPLIMAGE(cvImg)->height),
+ 8, ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
cvDilate(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, NULL, iterations);
ME_RELEASE_IPLIMAGE(cvImg);
@@ -416,22 +432,22 @@ void MEImage::Smooth()
void MEImage::SmoothAdvanced(SmoothType filtermode, int filtersize)
{
IplImage* TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
- ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
+ ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
switch (filtermode)
{
- case s_Blur:
- cvSmooth(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_BLUR, filtersize, filtersize, 0);
- break;
- case s_Median:
- cvSmooth(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_MEDIAN, filtersize, 0, 0);
- break;
- case s_Gaussian:
- cvSmooth(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_GAUSSIAN, filtersize, filtersize, 0);
- break;
- default:
- cvSmooth(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_MEDIAN, filtersize, 0, 0);
- break;
+ case s_Blur:
+ cvSmooth(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_BLUR, filtersize, filtersize, 0);
+ break;
+ case s_Median:
+ cvSmooth(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_MEDIAN, filtersize, 0, 0);
+ break;
+ case s_Gaussian:
+ cvSmooth(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_GAUSSIAN, filtersize, filtersize, 0);
+ break;
+ default:
+ cvSmooth(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_MEDIAN, filtersize, 0, 0);
+ break;
}
ME_RELEASE_IPLIMAGE(cvImg);
cvImg = TempImg;
@@ -446,7 +462,7 @@ void MEImage::Canny()
}
IplImage* TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
- ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
+ ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
cvCanny(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, 800, 1100, 5);
ME_RELEASE_IPLIMAGE(cvImg);
cvImg = TempImg;
@@ -460,8 +476,8 @@ void MEImage::Laplace()
ConvertToGrayscale(g_OpenCV);
}
IplImage* TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width,
- ME_CAST_TO_IPLIMAGE(cvImg)->height),
- IPL_DEPTH_16S, 1);
+ ME_CAST_TO_IPLIMAGE(cvImg)->height),
+ IPL_DEPTH_16S, 1);
cvLaplace(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, 3);
cvConvertScale(TempImg, ME_CAST_TO_IPLIMAGE(cvImg), 1, 0);
ME_RELEASE_IPLIMAGE(cvImg);
@@ -482,7 +498,7 @@ void MEImage::Quantize(int levels)
}
unsigned char* ImageData = (unsigned char*)ME_CAST_TO_IPLIMAGE(cvImg)->imageData;
- for (int i = ME_CAST_TO_IPLIMAGE(cvImg)->widthStep*ME_CAST_TO_IPLIMAGE(cvImg)->height-1; i >= 0; --i)
+ for (int i = ME_CAST_TO_IPLIMAGE(cvImg)->widthStep*ME_CAST_TO_IPLIMAGE(cvImg)->height - 1; i >= 0; --i)
{
ImageData[i] = ImageData[i] / (256 / levels)*(256 / levels);
}
@@ -503,7 +519,7 @@ void MEImage::Threshold(int threshold_limit)
}
unsigned char* ImageData = (unsigned char*)ME_CAST_TO_IPLIMAGE(cvImg)->imageData;
- for (int i = ME_CAST_TO_IPLIMAGE(cvImg)->widthStep*ME_CAST_TO_IPLIMAGE(cvImg)->height-1; i >= 0; --i)
+ for (int i = ME_CAST_TO_IPLIMAGE(cvImg)->widthStep*ME_CAST_TO_IPLIMAGE(cvImg)->height - 1; i >= 0; --i)
{
if (ImageData[i] < threshold_limit)
{
@@ -520,9 +536,9 @@ void MEImage::AdaptiveThreshold()
ConvertToGrayscale(g_OpenCV);
}
IplImage* TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
- ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
+ ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
cvAdaptiveThreshold(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, 25,
- CV_ADAPTIVE_THRESH_GAUSSIAN_C, CV_THRESH_BINARY, 7, -7);
+ CV_ADAPTIVE_THRESH_GAUSSIAN_C, CV_THRESH_BINARY, 7, -7);
ME_RELEASE_IPLIMAGE(cvImg);
cvImg = TempImg;
}
@@ -531,7 +547,7 @@ void MEImage::AdaptiveThreshold()
void MEImage::ThresholdByMask(MEImage& mask_image)
{
if (mask_image.GetWidth() != ME_CAST_TO_IPLIMAGE(cvImg)->width ||
- mask_image.GetHeight() != ME_CAST_TO_IPLIMAGE(cvImg)->height)
+ mask_image.GetHeight() != ME_CAST_TO_IPLIMAGE(cvImg)->height)
{
printf("Image properties are different\n");
return;
@@ -543,7 +559,7 @@ void MEImage::ThresholdByMask(MEImage& mask_image)
unsigned char* ImageData = (unsigned char*)ME_CAST_TO_IPLIMAGE(cvImg)->imageData;
unsigned char* MaskImageData = mask_image.GetImageData();
- for (int i = ME_CAST_TO_IPLIMAGE(cvImg)->widthStep*ME_CAST_TO_IPLIMAGE(cvImg)->height-1; i >= 0; --i)
+ for (int i = ME_CAST_TO_IPLIMAGE(cvImg)->widthStep*ME_CAST_TO_IPLIMAGE(cvImg)->height - 1; i >= 0; --i)
{
if (MaskImageData[i] == 0)
{
@@ -567,123 +583,123 @@ void MEImage::ColorSpace(ColorSpaceConvertType mode)
}
switch (mode)
{
- case csc_RGBtoXYZCIED65:
- TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width,
- ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
- ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
- cvCvtColor(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_RGB2XYZ);
- ME_RELEASE_IPLIMAGE(cvImg);
- cvImg = TempImg;
- break;
-
- case csc_XYZCIED65toRGB:
- TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width,
- ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
- ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
- cvCvtColor(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_XYZ2RGB);
- ME_RELEASE_IPLIMAGE(cvImg);
- cvImg = TempImg;
- break;
-
- case csc_RGBtoHSV:
- TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width,
- ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
- ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
- cvCvtColor(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_RGB2HSV);
- ME_RELEASE_IPLIMAGE(cvImg);
- cvImg = TempImg;
- break;
-
- case csc_HSVtoRGB:
- TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width,
- ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
- ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
- cvCvtColor(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_HSV2RGB);
- ME_RELEASE_IPLIMAGE(cvImg);
- cvImg = TempImg;
- break;
-
- case csc_RGBtoHLS:
- TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
- ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
- cvCvtColor(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_RGB2HLS);
- ME_RELEASE_IPLIMAGE(cvImg);
- cvImg = TempImg;
- break;
-
- case csc_HLStoRGB:
- TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
- ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
- cvCvtColor(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_HLS2RGB);
- ME_RELEASE_IPLIMAGE(cvImg);
- cvImg = TempImg;
- break;
-
- case csc_RGBtoCIELab:
- TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
- ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
- cvCvtColor(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_RGB2Lab);
- ME_RELEASE_IPLIMAGE(cvImg);
- cvImg = TempImg;
- break;
-
- case csc_CIELabtoRGB:
- TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
- ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
- cvCvtColor(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_Lab2RGB);
- ME_RELEASE_IPLIMAGE(cvImg);
- cvImg = TempImg;
- break;
-
- case csc_RGBtoCIELuv:
- TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
- ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
- cvCvtColor(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_RGB2Luv);
- ME_RELEASE_IPLIMAGE(cvImg);
- cvImg = TempImg;
- break;
-
- case csc_CIELuvtoRGB:
- TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
- ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
- cvCvtColor(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_Luv2RGB);
- ME_RELEASE_IPLIMAGE(cvImg);
- cvImg = TempImg;
- break;
-
- case csc_RGBtoYUV:
- ComputeColorSpace(csc_RGBtoYUV);
- break;
-
- case csc_RGBtoYIQ:
- ComputeColorSpace(csc_RGBtoYIQ);
- break;
-
- case csc_RGBtorgI:
- ImageData = (unsigned char*)ME_CAST_TO_IPLIMAGE(cvImg)->imageData;
- WidthStep = ME_CAST_TO_IPLIMAGE(cvImg)->widthStep;
- RowStart = 0;
- for (int y = ME_CAST_TO_IPLIMAGE(cvImg)->height-1; y >= 0; --y)
+ case csc_RGBtoXYZCIED65:
+ TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width,
+ ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
+ ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
+ cvCvtColor(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_RGB2XYZ);
+ ME_RELEASE_IPLIMAGE(cvImg);
+ cvImg = TempImg;
+ break;
+
+ case csc_XYZCIED65toRGB:
+ TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width,
+ ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
+ ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
+ cvCvtColor(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_XYZ2RGB);
+ ME_RELEASE_IPLIMAGE(cvImg);
+ cvImg = TempImg;
+ break;
+
+ case csc_RGBtoHSV:
+ TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width,
+ ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
+ ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
+ cvCvtColor(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_RGB2HSV);
+ ME_RELEASE_IPLIMAGE(cvImg);
+ cvImg = TempImg;
+ break;
+
+ case csc_HSVtoRGB:
+ TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width,
+ ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
+ ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
+ cvCvtColor(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_HSV2RGB);
+ ME_RELEASE_IPLIMAGE(cvImg);
+ cvImg = TempImg;
+ break;
+
+ case csc_RGBtoHLS:
+ TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
+ ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
+ cvCvtColor(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_RGB2HLS);
+ ME_RELEASE_IPLIMAGE(cvImg);
+ cvImg = TempImg;
+ break;
+
+ case csc_HLStoRGB:
+ TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
+ ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
+ cvCvtColor(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_HLS2RGB);
+ ME_RELEASE_IPLIMAGE(cvImg);
+ cvImg = TempImg;
+ break;
+
+ case csc_RGBtoCIELab:
+ TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
+ ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
+ cvCvtColor(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_RGB2Lab);
+ ME_RELEASE_IPLIMAGE(cvImg);
+ cvImg = TempImg;
+ break;
+
+ case csc_CIELabtoRGB:
+ TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
+ ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
+ cvCvtColor(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_Lab2RGB);
+ ME_RELEASE_IPLIMAGE(cvImg);
+ cvImg = TempImg;
+ break;
+
+ case csc_RGBtoCIELuv:
+ TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
+ ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
+ cvCvtColor(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_RGB2Luv);
+ ME_RELEASE_IPLIMAGE(cvImg);
+ cvImg = TempImg;
+ break;
+
+ case csc_CIELuvtoRGB:
+ TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
+ ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
+ cvCvtColor(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_Luv2RGB);
+ ME_RELEASE_IPLIMAGE(cvImg);
+ cvImg = TempImg;
+ break;
+
+ case csc_RGBtoYUV:
+ ComputeColorSpace(csc_RGBtoYUV);
+ break;
+
+ case csc_RGBtoYIQ:
+ ComputeColorSpace(csc_RGBtoYIQ);
+ break;
+
+ case csc_RGBtorgI:
+ ImageData = (unsigned char*)ME_CAST_TO_IPLIMAGE(cvImg)->imageData;
+ WidthStep = ME_CAST_TO_IPLIMAGE(cvImg)->widthStep;
+ RowStart = 0;
+ for (int y = ME_CAST_TO_IPLIMAGE(cvImg)->height - 1; y >= 0; --y)
+ {
+ for (int x = (ME_CAST_TO_IPLIMAGE(cvImg)->width - 1) * 3; x >= 0; x -= 3)
{
- for (int x = (ME_CAST_TO_IPLIMAGE(cvImg)->width-1)*3; x >= 0; x -= 3)
- {
- int r = 0;
- int g = 0;
- int I = 0;
-
- I = (int)ImageData[RowStart+x]+(int)ImageData[RowStart+x+1]+(int)ImageData[RowStart+x+2];
- r = (int)((float)ImageData[RowStart+x] / I*255);
- g = (int)((float)ImageData[RowStart+x+1] / I*255);
- ImageData[RowStart+x] = (unsigned char)r;
- ImageData[RowStart+x+1] = (unsigned char)g;
- ImageData[RowStart+x+2] = (unsigned char)(I / 3);
- }
- RowStart += WidthStep;
+ int r = 0;
+ int g = 0;
+ int I = 0;
+
+ I = (int)ImageData[RowStart + x] + (int)ImageData[RowStart + x + 1] + (int)ImageData[RowStart + x + 2];
+ r = (int)((float)ImageData[RowStart + x] / I * 255);
+ g = (int)((float)ImageData[RowStart + x + 1] / I * 255);
+ ImageData[RowStart + x] = (unsigned char)r;
+ ImageData[RowStart + x + 1] = (unsigned char)g;
+ ImageData[RowStart + x + 2] = (unsigned char)(I / 3);
}
- break;
+ RowStart += WidthStep;
+ }
+ break;
- default:
- break;
+ default:
+ break;
}
}
@@ -701,27 +717,27 @@ void MEImage::ConvertToGrayscale(GrayscaleType grayscale_mode)
switch (grayscale_mode)
{
- case g_Average:
- TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height), 8, 1);
- ImageData = (unsigned char*)TempImg->imageData;
+ case g_Average:
+ TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height), 8, 1);
+ ImageData = (unsigned char*)TempImg->imageData;
- for (int i = ME_CAST_TO_IPLIMAGE(cvImg)->widthStep*ME_CAST_TO_IPLIMAGE(cvImg)->height-3; i >= 0; i -= 3)
- {
- ImageData[i / 3] = (ImgData[i]+ImgData[i+1]+ImgData[i+2]) / 3;
- }
- ME_RELEASE_IPLIMAGE(cvImg);
- cvImg = TempImg;
- break;
+ for (int i = ME_CAST_TO_IPLIMAGE(cvImg)->widthStep*ME_CAST_TO_IPLIMAGE(cvImg)->height - 3; i >= 0; i -= 3)
+ {
+ ImageData[i / 3] = (ImgData[i] + ImgData[i + 1] + ImgData[i + 2]) / 3;
+ }
+ ME_RELEASE_IPLIMAGE(cvImg);
+ cvImg = TempImg;
+ break;
- case g_OpenCV:
- TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height), 8, 1);
- cvCvtColor(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_RGB2GRAY);
- ME_RELEASE_IPLIMAGE(cvImg);
- cvImg = TempImg;
- break;
+ case g_OpenCV:
+ TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height), 8, 1);
+ cvCvtColor(ME_CAST_TO_IPLIMAGE(cvImg), TempImg, CV_RGB2GRAY);
+ ME_RELEASE_IPLIMAGE(cvImg);
+ cvImg = TempImg;
+ break;
- default:
- break;
+ default:
+ break;
}
}
@@ -760,60 +776,60 @@ void MEImage::LBP(LBPType mode)
IplImage* TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height), 8, 1);
unsigned char* TempImgData = (unsigned char*)TempImg->imageData;
int WidthStep = ME_CAST_TO_IPLIMAGE(cvImg)->widthStep;
- int WidthStep_2 = ME_CAST_TO_IPLIMAGE(cvImg)->widthStep*2;
+ int WidthStep_2 = ME_CAST_TO_IPLIMAGE(cvImg)->widthStep * 2;
cvSetZero(TempImg);
switch (mode)
{
- case lbp_Normal:
- for (int i = ME_CAST_TO_IPLIMAGE(cvImg)->widthStep*(ME_CAST_TO_IPLIMAGE(cvImg)->height-2)-1; i >= ME_CAST_TO_IPLIMAGE(cvImg)->widthStep+1; --i)
- {
- TempImgData[i] =
- (ImageData[i] <= ImageData[i-ME_CAST_TO_IPLIMAGE(cvImg)->widthStep-1])+
- ((ImageData[i] <= ImageData[i-ME_CAST_TO_IPLIMAGE(cvImg)->widthStep])*2)+
- ((ImageData[i] <= ImageData[i-ME_CAST_TO_IPLIMAGE(cvImg)->widthStep+1])*4)+
- ((ImageData[i] <= ImageData[i-1])*8)+
- ((ImageData[i] <= ImageData[i+1])*16)+
- ((ImageData[i] <= ImageData[i+ME_CAST_TO_IPLIMAGE(cvImg)->widthStep-1])*32)+
- ((ImageData[i] <= ImageData[i+ME_CAST_TO_IPLIMAGE(cvImg)->widthStep])*64)+
- ((ImageData[i] <= ImageData[i+ME_CAST_TO_IPLIMAGE(cvImg)->widthStep+1])*128);
- }
- break;
+ case lbp_Normal:
+ for (int i = ME_CAST_TO_IPLIMAGE(cvImg)->widthStep*(ME_CAST_TO_IPLIMAGE(cvImg)->height - 2) - 1; i >= ME_CAST_TO_IPLIMAGE(cvImg)->widthStep + 1; --i)
+ {
+ TempImgData[i] =
+ (ImageData[i] <= ImageData[i - ME_CAST_TO_IPLIMAGE(cvImg)->widthStep - 1]) +
+ ((ImageData[i] <= ImageData[i - ME_CAST_TO_IPLIMAGE(cvImg)->widthStep]) * 2) +
+ ((ImageData[i] <= ImageData[i - ME_CAST_TO_IPLIMAGE(cvImg)->widthStep + 1]) * 4) +
+ ((ImageData[i] <= ImageData[i - 1]) * 8) +
+ ((ImageData[i] <= ImageData[i + 1]) * 16) +
+ ((ImageData[i] <= ImageData[i + ME_CAST_TO_IPLIMAGE(cvImg)->widthStep - 1]) * 32) +
+ ((ImageData[i] <= ImageData[i + ME_CAST_TO_IPLIMAGE(cvImg)->widthStep]) * 64) +
+ ((ImageData[i] <= ImageData[i + ME_CAST_TO_IPLIMAGE(cvImg)->widthStep + 1]) * 128);
+ }
+ break;
- case lbp_Special:
- for (int i = ME_CAST_TO_IPLIMAGE(cvImg)->widthStep*(ME_CAST_TO_IPLIMAGE(cvImg)->height-3)-2; i >= ME_CAST_TO_IPLIMAGE(cvImg)->widthStep*2+2; --i)
- {
- int CenterPixel = (ImageData[i+1]+ImageData[i-1]+
- ImageData[i-WidthStep]+ImageData[i+WidthStep]) / 4;
- TempImgData[i] = ((CenterPixel <= (ImageData[i-(WidthStep_2)-2]+
- ImageData[i-(WidthStep_2)-1]+
- ImageData[i-WidthStep-2]+
- ImageData[i-WidthStep-1]) / 4))+
- ((CenterPixel <= (ImageData[i-WidthStep]+
- ImageData[i-(WidthStep_2)]) / 2)*2)+
- ((CenterPixel <= ((ImageData[i-(WidthStep_2)+2]+
- ImageData[i-(WidthStep_2)+1]+
- ImageData[i-WidthStep+2]+
- ImageData[i-WidthStep+1]) / 4))*4)+
- ((CenterPixel <= (ImageData[i-1]+
- ImageData[i-2]) / 2)*8)+
- ((CenterPixel <= (ImageData[i+1]+
- ImageData[i+2]) / 2)*16)+
- ((CenterPixel <= ((ImageData[i+(WidthStep_2)-2]+
- ImageData[i+(WidthStep_2)-1]+
- ImageData[i+WidthStep-2]+
- ImageData[i+WidthStep-1]) / 4))*32)+
- ((CenterPixel <= (ImageData[i+WidthStep]+
- ImageData[i-WidthStep_2]) / 2)*64)+
- ((CenterPixel <= ((ImageData[i+(WidthStep_2)+2]+
- ImageData[i+(WidthStep_2)+1]+
- ImageData[i+WidthStep+2]+
- ImageData[i+WidthStep+1]) / 4))*128);
- }
- break;
+ case lbp_Special:
+ for (int i = ME_CAST_TO_IPLIMAGE(cvImg)->widthStep*(ME_CAST_TO_IPLIMAGE(cvImg)->height - 3) - 2; i >= ME_CAST_TO_IPLIMAGE(cvImg)->widthStep * 2 + 2; --i)
+ {
+ int CenterPixel = (ImageData[i + 1] + ImageData[i - 1] +
+ ImageData[i - WidthStep] + ImageData[i + WidthStep]) / 4;
+ TempImgData[i] = ((CenterPixel <= (ImageData[i - (WidthStep_2)-2] +
+ ImageData[i - (WidthStep_2)-1] +
+ ImageData[i - WidthStep - 2] +
+ ImageData[i - WidthStep - 1]) / 4)) +
+ ((CenterPixel <= (ImageData[i - WidthStep] +
+ ImageData[i - (WidthStep_2)]) / 2) * 2) +
+ ((CenterPixel <= ((ImageData[i - (WidthStep_2)+2] +
+ ImageData[i - (WidthStep_2)+1] +
+ ImageData[i - WidthStep + 2] +
+ ImageData[i - WidthStep + 1]) / 4)) * 4) +
+ ((CenterPixel <= (ImageData[i - 1] +
+ ImageData[i - 2]) / 2) * 8) +
+ ((CenterPixel <= (ImageData[i + 1] +
+ ImageData[i + 2]) / 2) * 16) +
+ ((CenterPixel <= ((ImageData[i + (WidthStep_2)-2] +
+ ImageData[i + (WidthStep_2)-1] +
+ ImageData[i + WidthStep - 2] +
+ ImageData[i + WidthStep - 1]) / 4)) * 32) +
+ ((CenterPixel <= (ImageData[i + WidthStep] +
+ ImageData[i - WidthStep_2]) / 2) * 64) +
+ ((CenterPixel <= ((ImageData[i + (WidthStep_2)+2] +
+ ImageData[i + (WidthStep_2)+1] +
+ ImageData[i + WidthStep + 2] +
+ ImageData[i + WidthStep + 1]) / 4)) * 128);
+ }
+ break;
- default:
- break;
+ default:
+ break;
}
ME_RELEASE_IPLIMAGE(cvImg);
cvImg = TempImg;
@@ -824,12 +840,13 @@ void MEImage::Binarize(int threshold)
{
unsigned char* ImageData = (unsigned char*)ME_CAST_TO_IPLIMAGE(cvImg)->imageData;
- for (int i = ME_CAST_TO_IPLIMAGE(cvImg)->height*ME_CAST_TO_IPLIMAGE(cvImg)->widthStep-1; i >= 0; --i)
+ for (int i = ME_CAST_TO_IPLIMAGE(cvImg)->height*ME_CAST_TO_IPLIMAGE(cvImg)->widthStep - 1; i >= 0; --i)
{
if (ImageData[i] >= threshold)
{
ImageData[i] = 255;
- } else {
+ }
+ else {
ImageData[i] = 0;
}
}
@@ -839,8 +856,8 @@ void MEImage::Binarize(int threshold)
void MEImage::Subtract(MEImage& source, SubtractModeType mode)
{
if (source.GetWidth() != ME_CAST_TO_IPLIMAGE(cvImg)->width ||
- source.GetHeight() != ME_CAST_TO_IPLIMAGE(cvImg)->height ||
- source.GetLayers() != ME_CAST_TO_IPLIMAGE(cvImg)->nChannels)
+ source.GetHeight() != ME_CAST_TO_IPLIMAGE(cvImg)->height ||
+ source.GetLayers() != ME_CAST_TO_IPLIMAGE(cvImg)->nChannels)
{
printf("Image properties are different.\n");
return;
@@ -852,42 +869,42 @@ void MEImage::Subtract(MEImage& source, SubtractModeType mode)
switch (mode)
{
- case sub_Normal:
- ImageData = (unsigned char*)ME_CAST_TO_IPLIMAGE(cvImg)->imageData;
- DstData = source.GetImageData();
- RowStart = 0;
+ case sub_Normal:
+ ImageData = (unsigned char*)ME_CAST_TO_IPLIMAGE(cvImg)->imageData;
+ DstData = source.GetImageData();
+ RowStart = 0;
- for (int y = ME_CAST_TO_IPLIMAGE(cvImg)->height-1; y >= 0; --y)
+ for (int y = ME_CAST_TO_IPLIMAGE(cvImg)->height - 1; y >= 0; --y)
+ {
+ for (int x = ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels - 1; x >= 0; --x)
{
- for (int x = ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels-1; x >= 0; --x)
- {
- ImageData[RowStart+x] =
- ImageData[RowStart+x]-DstData[RowStart+x] < 0 ? 0 :
- ImageData[RowStart+x]-DstData[RowStart+x];
- }
- RowStart += WidthStep;
+ ImageData[RowStart + x] =
+ ImageData[RowStart + x] - DstData[RowStart + x] < 0 ? 0 :
+ ImageData[RowStart + x] - DstData[RowStart + x];
}
- break;
+ RowStart += WidthStep;
+ }
+ break;
- case sub_Absolut:
- ImageData = (unsigned char*)ME_CAST_TO_IPLIMAGE(cvImg)->imageData;
- DstData = source.GetImageData();
- RowStart = 0;
+ case sub_Absolut:
+ ImageData = (unsigned char*)ME_CAST_TO_IPLIMAGE(cvImg)->imageData;
+ DstData = source.GetImageData();
+ RowStart = 0;
- for (int y = ME_CAST_TO_IPLIMAGE(cvImg)->height-1; y >= 0; --y)
+ for (int y = ME_CAST_TO_IPLIMAGE(cvImg)->height - 1; y >= 0; --y)
+ {
+ for (int x = ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels - 1; x >= 0; --x)
{
- for (int x = ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels-1; x >= 0; --x)
- {
- ImageData[RowStart+x] = ImageData[RowStart+x]-
- DstData[RowStart+x] < 0 ? -ImageData[RowStart+x]+
- DstData[RowStart+x] : ImageData[RowStart+x]-DstData[RowStart+x];
- }
- RowStart += WidthStep;
+ ImageData[RowStart + x] = ImageData[RowStart + x] -
+ DstData[RowStart + x] < 0 ? -ImageData[RowStart + x] +
+ DstData[RowStart + x] : ImageData[RowStart + x] - DstData[RowStart + x];
}
- break;
+ RowStart += WidthStep;
+ }
+ break;
- default:
- break;
+ default:
+ break;
}
}
@@ -895,8 +912,8 @@ void MEImage::Subtract(MEImage& source, SubtractModeType mode)
void MEImage::Multiple(MEImage& source, MultiplicationType mode)
{
if (source.GetWidth() != ME_CAST_TO_IPLIMAGE(cvImg)->width ||
- source.GetHeight() != ME_CAST_TO_IPLIMAGE(cvImg)->height ||
- source.GetLayers() != ME_CAST_TO_IPLIMAGE(cvImg)->nChannels)
+ source.GetHeight() != ME_CAST_TO_IPLIMAGE(cvImg)->height ||
+ source.GetLayers() != ME_CAST_TO_IPLIMAGE(cvImg)->nChannels)
{
printf("Image properties are different.\n");
return;
@@ -910,57 +927,59 @@ void MEImage::Multiple(MEImage& source, MultiplicationType mode)
switch (mode)
{
- case m_Normal:
- Result = 0;
- ImageData = (unsigned char*)ME_CAST_TO_IPLIMAGE(cvImg)->imageData;
- DstData = source.GetImageData();
+ case m_Normal:
+ Result = 0;
+ ImageData = (unsigned char*)ME_CAST_TO_IPLIMAGE(cvImg)->imageData;
+ DstData = source.GetImageData();
- for (int i = ME_CAST_TO_IPLIMAGE(cvImg)->height*ME_CAST_TO_IPLIMAGE(cvImg)->widthStep-1; i >= 0; --i)
+ for (int i = ME_CAST_TO_IPLIMAGE(cvImg)->height*ME_CAST_TO_IPLIMAGE(cvImg)->widthStep - 1; i >= 0; --i)
+ {
+ if ((ImageData[i] >= 128) && (DstData[i] >= 128))
{
- if ((ImageData[i] >= 128) && (DstData[i] >= 128))
- {
- Result = (float)ImageData[i]/128*(float)DstData[i]/128;
+ Result = (float)ImageData[i] / 128 * (float)DstData[i] / 128;
- if (Result >= 1)
- {
- ImageData[i] = 255;
- } else {
- ImageData[i] = 0;
- }
- } else {
+ if (Result >= 1)
+ {
+ ImageData[i] = 255;
+ }
+ else {
ImageData[i] = 0;
}
}
- break;
-
- case m_Neighbourhood:
- TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
- ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
- ImageData2 = (unsigned char*)ME_CAST_TO_IPLIMAGE(cvImg)->imageData;
- DstData = source.GetImageData();
- ImageData3 = (unsigned char*)TempImg->imageData;
-
- for (int y = ME_CAST_TO_IPLIMAGE(cvImg)->height-1; y >= 0; --y)
- for (int x = ME_CAST_TO_IPLIMAGE(cvImg)->width-1; x >= 0; --x)
- for (int l = ME_CAST_TO_IPLIMAGE(cvImg)->nChannels-1; l >= 0; --l)
- {
- if (((DstData[y*ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels+
- x*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels+l] == 255) ||
- (ImageData2[y*ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels+
- x*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels+l] == 255)) &&
- (NeighbourhoodCounter(x-2, y-2, n_5x5) > 3) &&
- (source.NeighbourhoodCounter(x-2, y-2, n_5x5) > 3))
+ else {
+ ImageData[i] = 0;
+ }
+ }
+ break;
+
+ case m_Neighbourhood:
+ TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
+ ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
+ ImageData2 = (unsigned char*)ME_CAST_TO_IPLIMAGE(cvImg)->imageData;
+ DstData = source.GetImageData();
+ ImageData3 = (unsigned char*)TempImg->imageData;
+
+ for (int y = ME_CAST_TO_IPLIMAGE(cvImg)->height - 1; y >= 0; --y)
+ for (int x = ME_CAST_TO_IPLIMAGE(cvImg)->width - 1; x >= 0; --x)
+ for (int l = ME_CAST_TO_IPLIMAGE(cvImg)->nChannels - 1; l >= 0; --l)
{
- ImageData3[y*ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels+
- x*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels+l] = 255;
+ if (((DstData[y*ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels +
+ x*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels + l] == 255) ||
+ (ImageData2[y*ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels +
+ x*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels + l] == 255)) &&
+ (NeighbourhoodCounter(x - 2, y - 2, n_5x5) > 3) &&
+ (source.NeighbourhoodCounter(x - 2, y - 2, n_5x5) > 3))
+ {
+ ImageData3[y*ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels +
+ x*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels + l] = 255;
+ }
}
- }
- ME_RELEASE_IPLIMAGE(cvImg);
- cvImg = TempImg;
- break;
+ ME_RELEASE_IPLIMAGE(cvImg);
+ cvImg = TempImg;
+ break;
- default:
- break;
+ default:
+ break;
}
}
@@ -968,8 +987,8 @@ void MEImage::Multiple(MEImage& source, MultiplicationType mode)
void MEImage::Addition(MEImage& source, AdditionType mode)
{
if (source.GetWidth() != ME_CAST_TO_IPLIMAGE(cvImg)->width ||
- source.GetHeight() != ME_CAST_TO_IPLIMAGE(cvImg)->height ||
- source.GetLayers() != ME_CAST_TO_IPLIMAGE(cvImg)->nChannels)
+ source.GetHeight() != ME_CAST_TO_IPLIMAGE(cvImg)->height ||
+ source.GetLayers() != ME_CAST_TO_IPLIMAGE(cvImg)->nChannels)
{
printf("Image properties are different.\n");
return;
@@ -979,25 +998,25 @@ void MEImage::Addition(MEImage& source, AdditionType mode)
switch (mode)
{
- case a_Average:
- for (int i = ME_CAST_TO_IPLIMAGE(cvImg)->height*ME_CAST_TO_IPLIMAGE(cvImg)->widthStep-1; i >= 0; --i)
- {
- ImageData[i] = (ImageData[i]+DstData[i]) / 2;
- }
- break;
+ case a_Average:
+ for (int i = ME_CAST_TO_IPLIMAGE(cvImg)->height*ME_CAST_TO_IPLIMAGE(cvImg)->widthStep - 1; i >= 0; --i)
+ {
+ ImageData[i] = (ImageData[i] + DstData[i]) / 2;
+ }
+ break;
- case a_Union:
- for (int i = ME_CAST_TO_IPLIMAGE(cvImg)->height*ME_CAST_TO_IPLIMAGE(cvImg)->widthStep-1; i >= 0; --i)
+ case a_Union:
+ for (int i = ME_CAST_TO_IPLIMAGE(cvImg)->height*ME_CAST_TO_IPLIMAGE(cvImg)->widthStep - 1; i >= 0; --i)
+ {
+ if (DstData[i] > ImageData[i])
{
- if (DstData[i] > ImageData[i])
- {
- ImageData[i] = DstData[i];
- }
+ ImageData[i] = DstData[i];
}
- break;
+ }
+ break;
- default:
- break;
+ default:
+ break;
}
}
@@ -1005,42 +1024,44 @@ void MEImage::Addition(MEImage& source, AdditionType mode)
void MEImage::EliminateSinglePixels()
{
IplImage* TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
- ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
+ ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
unsigned char* ImageData = (unsigned char*)ME_CAST_TO_IPLIMAGE(cvImg)->imageData;
unsigned char* DstData = (unsigned char*)TempImg->imageData;
int sum = 0;
int xy = 0;
int ywidth = ME_CAST_TO_IPLIMAGE(cvImg)->widthStep;
- for (int y = ME_CAST_TO_IPLIMAGE(cvImg)->height-1; y >= 0; --y)
- for (int x = ME_CAST_TO_IPLIMAGE(cvImg)->width-1; x >= 0; --x)
- {
- xy = y*ywidth+x*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels;
-
- for (int l = ME_CAST_TO_IPLIMAGE(cvImg)->nChannels-1; l >= 0; --l)
+ for (int y = ME_CAST_TO_IPLIMAGE(cvImg)->height - 1; y >= 0; --y)
+ for (int x = ME_CAST_TO_IPLIMAGE(cvImg)->width - 1; x >= 0; --x)
{
- if ((ImageData[xy+l] > 0) && (x > 0) && (y > 0) && (x < ME_CAST_TO_IPLIMAGE(cvImg)->width-1) && (y < ME_CAST_TO_IPLIMAGE(cvImg)->height-1))
+ xy = y*ywidth + x*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels;
+
+ for (int l = ME_CAST_TO_IPLIMAGE(cvImg)->nChannels - 1; l >= 0; --l)
{
- sum = (ImageData[xy-ywidth-ME_CAST_TO_IPLIMAGE(cvImg)->nChannels+l] > 0)+
- (ImageData[xy-ywidth+l] > 0)+
- (ImageData[xy-ywidth+ME_CAST_TO_IPLIMAGE(cvImg)->nChannels+l] > 0)+
- (ImageData[xy-ME_CAST_TO_IPLIMAGE(cvImg)->nChannels+l] > 0)+
- (ImageData[xy+ME_CAST_TO_IPLIMAGE(cvImg)->nChannels+l] > 0)+
- (ImageData[xy+ywidth-ME_CAST_TO_IPLIMAGE(cvImg)->nChannels+l] > 0)+
- (ImageData[xy+ywidth+l] > 0)+
- (ImageData[xy+ywidth+ME_CAST_TO_IPLIMAGE(cvImg)->nChannels+l] > 0);
-
- if (sum > 3)
+ if ((ImageData[xy + l] > 0) && (x > 0) && (y > 0) && (x < ME_CAST_TO_IPLIMAGE(cvImg)->width - 1) && (y < ME_CAST_TO_IPLIMAGE(cvImg)->height - 1))
{
- DstData[xy+l] = 255;
- } else {
- DstData[xy+l] = 0;
+ sum = (ImageData[xy - ywidth - ME_CAST_TO_IPLIMAGE(cvImg)->nChannels + l] > 0) +
+ (ImageData[xy - ywidth + l] > 0) +
+ (ImageData[xy - ywidth + ME_CAST_TO_IPLIMAGE(cvImg)->nChannels + l] > 0) +
+ (ImageData[xy - ME_CAST_TO_IPLIMAGE(cvImg)->nChannels + l] > 0) +
+ (ImageData[xy + ME_CAST_TO_IPLIMAGE(cvImg)->nChannels + l] > 0) +
+ (ImageData[xy + ywidth - ME_CAST_TO_IPLIMAGE(cvImg)->nChannels + l] > 0) +
+ (ImageData[xy + ywidth + l] > 0) +
+ (ImageData[xy + ywidth + ME_CAST_TO_IPLIMAGE(cvImg)->nChannels + l] > 0);
+
+ if (sum > 3)
+ {
+ DstData[xy + l] = 255;
+ }
+ else {
+ DstData[xy + l] = 0;
+ }
+ }
+ else {
+ DstData[xy + l] = 0;
}
- } else {
- DstData[xy+l] = 0;
}
}
- }
ME_RELEASE_IPLIMAGE(cvImg);
cvImg = TempImg;
}
@@ -1049,8 +1070,8 @@ void MEImage::EliminateSinglePixels()
float MEImage::DifferenceAreas(MEImage& reference, int difference) const
{
if (reference.GetWidth() != GetWidth() ||
- reference.GetHeight() != GetHeight() ||
- reference.GetLayers() != GetLayers())
+ reference.GetHeight() != GetHeight() ||
+ reference.GetLayers() != GetLayers())
{
printf("Image dimensions or channels are different\n");
return -1.0;
@@ -1062,16 +1083,16 @@ float MEImage::DifferenceAreas(MEImage& reference, int difference) const
int WidthStep = ME_CAST_TO_IPLIMAGE(cvImg)->widthStep;
int RowStart = 0;
- for (int y = ME_CAST_TO_IPLIMAGE(cvImg)->height-1; y >= 0; --y)
+ for (int y = ME_CAST_TO_IPLIMAGE(cvImg)->height - 1; y >= 0; --y)
{
- for (int x = ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels-1; x >= 0; --x)
+ for (int x = ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels - 1; x >= 0; --x)
{
- if (abs(OrigImgData[RowStart+x]-RefImgData[RowStart+x]) > difference)
+ if (abs(OrigImgData[RowStart + x] - RefImgData[RowStart + x]) > difference)
Pixels++;
}
RowStart += WidthStep;
}
- PixelDiff = (float)Pixels / (ME_CAST_TO_IPLIMAGE(cvImg)->height*ME_CAST_TO_IPLIMAGE(cvImg)->widthStep)*100;
+ PixelDiff = (float)Pixels / (ME_CAST_TO_IPLIMAGE(cvImg)->height*ME_CAST_TO_IPLIMAGE(cvImg)->widthStep) * 100;
return PixelDiff;
}
@@ -1079,8 +1100,8 @@ float MEImage::DifferenceAreas(MEImage& reference, int difference) const
int MEImage::AverageDifference(MEImage& reference) const
{
if (reference.GetWidth() != GetWidth() ||
- reference.GetHeight() != GetHeight() ||
- reference.GetLayers() != GetLayers())
+ reference.GetHeight() != GetHeight() ||
+ reference.GetLayers() != GetLayers())
{
printf("Image dimensions or channels are different\n");
return -1;
@@ -1091,11 +1112,11 @@ int MEImage::AverageDifference(MEImage& reference) const
int WidthStep = ME_CAST_TO_IPLIMAGE(cvImg)->widthStep;
int RowStart = 0;
- for (int y = ME_CAST_TO_IPLIMAGE(cvImg)->height-1; y >= 0; --y)
+ for (int y = ME_CAST_TO_IPLIMAGE(cvImg)->height - 1; y >= 0; --y)
{
- for (int x = ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels-1; x >= 0; --x)
+ for (int x = ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels - 1; x >= 0; --x)
{
- Difference += abs(OrigImgData[RowStart+x]-RefImgData[RowStart+x]);
+ Difference += abs(OrigImgData[RowStart + x] - RefImgData[RowStart + x]);
}
RowStart += WidthStep;
}
@@ -1107,8 +1128,8 @@ int MEImage::AverageDifference(MEImage& reference) const
void MEImage::Minimum(MEImage& image)
{
if (image.GetWidth() != ME_CAST_TO_IPLIMAGE(cvImg)->width ||
- image.GetHeight() != ME_CAST_TO_IPLIMAGE(cvImg)->height ||
- image.GetLayers() != ME_CAST_TO_IPLIMAGE(cvImg)->nChannels)
+ image.GetHeight() != ME_CAST_TO_IPLIMAGE(cvImg)->height ||
+ image.GetLayers() != ME_CAST_TO_IPLIMAGE(cvImg)->nChannels)
{
printf("Image properties are different\n");
return;
@@ -1118,12 +1139,12 @@ void MEImage::Minimum(MEImage& image)
int WidthStep = ME_CAST_TO_IPLIMAGE(cvImg)->widthStep;
int RowStart = 0;
- for (int y = ME_CAST_TO_IPLIMAGE(cvImg)->height-1; y >= 0; --y)
+ for (int y = ME_CAST_TO_IPLIMAGE(cvImg)->height - 1; y >= 0; --y)
{
- for (int x = ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels-1; x >= 0; --x)
+ for (int x = ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels - 1; x >= 0; --x)
{
- ImageData[RowStart+x] = ImageData[RowStart+x] > SecData[RowStart+x] ?
- SecData[RowStart+x] : ImageData[RowStart+x];
+ ImageData[RowStart + x] = ImageData[RowStart + x] > SecData[RowStart + x] ?
+ SecData[RowStart + x] : ImageData[RowStart + x];
}
RowStart += WidthStep;
}
@@ -1137,11 +1158,11 @@ float MEImage::AverageBrightnessLevel() const
int RowStart = 0;
int BrightnessLevel = 0;
- for (int y = ME_CAST_TO_IPLIMAGE(cvImg)->height-1; y >= 0; --y)
+ for (int y = ME_CAST_TO_IPLIMAGE(cvImg)->height - 1; y >= 0; --y)
{
- for (int x = ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels-1; x >= 0; --x)
+ for (int x = ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels - 1; x >= 0; --x)
{
- BrightnessLevel += (int)ImageData[RowStart+x];
+ BrightnessLevel += (int)ImageData[RowStart + x];
}
RowStart += WidthStep;
}
@@ -1160,8 +1181,8 @@ bool MEImage::Equal(const MEImage& reference, int maxabsdiff) const
bool Ret = true;
if (reference.GetWidth() != ME_CAST_TO_IPLIMAGE(cvImg)->width ||
- reference.GetHeight() != ME_CAST_TO_IPLIMAGE(cvImg)->height ||
- reference.GetLayers() != ME_CAST_TO_IPLIMAGE(cvImg)->nChannels)
+ reference.GetHeight() != ME_CAST_TO_IPLIMAGE(cvImg)->height ||
+ reference.GetLayers() != ME_CAST_TO_IPLIMAGE(cvImg)->nChannels)
{
printf("Image properties are different\n");
return false;
@@ -1171,11 +1192,11 @@ bool MEImage::Equal(const MEImage& reference, int maxabsdiff) const
int WidthStep = ME_CAST_TO_IPLIMAGE(cvImg)->widthStep;
int RowStart = 0;
- for (int y = ME_CAST_TO_IPLIMAGE(cvImg)->height-1; y >= 0; --y)
+ for (int y = ME_CAST_TO_IPLIMAGE(cvImg)->height - 1; y >= 0; --y)
{
- for (int x = ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels-1; x >= 0; --x)
+ for (int x = ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels - 1; x >= 0; --x)
{
- if (abs(ImageData[RowStart+x]-RefData[RowStart+x]) >= maxabsdiff)
+ if (abs(ImageData[RowStart + x] - RefData[RowStart + x]) >= maxabsdiff)
{
Ret = false;
return Ret;
@@ -1193,16 +1214,16 @@ unsigned char MEImage::GrayscalePixel(int x, int y) const
int NewY = y;
NewX = NewX < 0 ? 0 : NewX;
- NewX = NewX > ME_CAST_TO_IPLIMAGE(cvImg)->width-1 ? ME_CAST_TO_IPLIMAGE(cvImg)->width-1 : NewX;
+ NewX = NewX > ME_CAST_TO_IPLIMAGE(cvImg)->width - 1 ? ME_CAST_TO_IPLIMAGE(cvImg)->width - 1 : NewX;
NewY = NewY < 0 ? 0 : NewY;
- NewY = NewY > ME_CAST_TO_IPLIMAGE(cvImg)->height-1 ? ME_CAST_TO_IPLIMAGE(cvImg)->height-1 : NewY;
+ NewY = NewY > ME_CAST_TO_IPLIMAGE(cvImg)->height - 1 ? ME_CAST_TO_IPLIMAGE(cvImg)->height - 1 : NewY;
float Sum = 0;
unsigned char* ImageData = (unsigned char*)ME_CAST_TO_IPLIMAGE(cvImg)->imageData;
for (int l = 0; l < ME_CAST_TO_IPLIMAGE(cvImg)->nChannels; l++)
{
- Sum = Sum + (int)ImageData[NewY*ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels+NewX*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels+l];
+ Sum = Sum + (int)ImageData[NewY*ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels + NewX*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels + l];
}
Sum = Sum / ME_CAST_TO_IPLIMAGE(cvImg)->nChannels;
return (unsigned char)(Sum);
@@ -1210,7 +1231,7 @@ unsigned char MEImage::GrayscalePixel(int x, int y) const
int MEImage::NeighbourhoodCounter(int startx, int starty,
- NeighbourhoodType neighbourhood) const
+ NeighbourhoodType neighbourhood) const
{
int IterX = 0;
int IterY = 0;
@@ -1219,60 +1240,60 @@ int MEImage::NeighbourhoodCounter(int startx, int starty,
// Determine the iteration numbers
switch (neighbourhood)
{
- case n_2x2:
- IterX = 2;
- IterY = 2;
- break;
+ case n_2x2:
+ IterX = 2;
+ IterY = 2;
+ break;
- case n_3x3:
- IterX = 3;
- IterY = 3;
- break;
+ case n_3x3:
+ IterX = 3;
+ IterY = 3;
+ break;
- case n_3x2:
- IterX = 2;
- IterY = 3;
- break;
+ case n_3x2:
+ IterX = 2;
+ IterY = 3;
+ break;
- case n_5x5:
- IterX = 5;
- IterY = 5;
- break;
+ case n_5x5:
+ IterX = 5;
+ IterY = 5;
+ break;
- case n_7x7:
- IterX = 7;
- IterY = 7;
- break;
+ case n_7x7:
+ IterX = 7;
+ IterY = 7;
+ break;
- default:
- IterX = 3;
- IterY = 3;
- break;
+ default:
+ IterX = 3;
+ IterY = 3;
+ break;
}
- int NewStartX = startx ;
+ int NewStartX = startx;
int NewStartY = starty;
NewStartX = startx < 0 ? 0 : startx;
- NewStartX = startx >= ME_CAST_TO_IPLIMAGE(cvImg)->width-IterX ? ME_CAST_TO_IPLIMAGE(cvImg)->width-IterX-1 : startx;
+ NewStartX = startx >= ME_CAST_TO_IPLIMAGE(cvImg)->width - IterX ? ME_CAST_TO_IPLIMAGE(cvImg)->width - IterX - 1 : startx;
NewStartY = starty < 0 ? 0 : starty;
- NewStartY = starty >= ME_CAST_TO_IPLIMAGE(cvImg)->height-IterY ? ME_CAST_TO_IPLIMAGE(cvImg)->height-IterY-1 : starty;
+ NewStartY = starty >= ME_CAST_TO_IPLIMAGE(cvImg)->height - IterY ? ME_CAST_TO_IPLIMAGE(cvImg)->height - IterY - 1 : starty;
int Value = 0;
unsigned char* ImageData = (unsigned char*)ME_CAST_TO_IPLIMAGE(cvImg)->imageData;
- for (int x = NewStartX; x < NewStartX+IterX; x++)
- for (int y = NewStartY; y < NewStartY+IterY; y++)
- {
- Value = ((int)ImageData[y*ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels+x*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels]+
- (int)ImageData[y*ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels+x*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels+1]+
- (int)ImageData[y*ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels+x*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels+2]) / 3;
-
- if (Value == 255)
+ for (int x = NewStartX; x < NewStartX + IterX; x++)
+ for (int y = NewStartY; y < NewStartY + IterY; y++)
{
- Counter++;
+ Value = ((int)ImageData[y*ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels + x*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels] +
+ (int)ImageData[y*ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels + x*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels + 1] +
+ (int)ImageData[y*ME_CAST_TO_IPLIMAGE(cvImg)->width*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels + x*ME_CAST_TO_IPLIMAGE(cvImg)->nChannels + 2]) / 3;
+
+ if (Value == 255)
+ {
+ Counter++;
+ }
}
- }
return Counter;
}
@@ -1288,24 +1309,24 @@ void MEImage::GradientVector(bool smooth, int x, int y, int mask_size, int& resu
}
if (smooth)
{
- SmoothAdvanced(s_Gaussian, mask_size*3-(mask_size*3-1) % 2);
+ SmoothAdvanced(s_Gaussian, mask_size * 3 - (mask_size * 3 - 1) % 2);
}
- Results[0] = (int)GrayscalePixel(x,y)-(int)GrayscalePixel(x,y-mask_size);
- Results[1] = (int)GrayscalePixel(x,y)-(int)GrayscalePixel(x+DiagonalMaskSize,y-DiagonalMaskSize);
- Results[2] = (int)GrayscalePixel(x,y)-(int)GrayscalePixel(x+mask_size,y);
- Results[3] = (int)GrayscalePixel(x,y)-(int)GrayscalePixel(x+DiagonalMaskSize,y+DiagonalMaskSize);
- Results[4] = (int)GrayscalePixel(x,y)-(int)GrayscalePixel(x,y+mask_size);
- Results[5] = (int)GrayscalePixel(x,y)-(int)GrayscalePixel(x-DiagonalMaskSize,y+DiagonalMaskSize);
- Results[6] = (int)GrayscalePixel(x,y)-(int)GrayscalePixel(x-mask_size,y);
- Results[7] = (int)GrayscalePixel(x,y)-(int)GrayscalePixel(x+DiagonalMaskSize,y-DiagonalMaskSize);
+ Results[0] = (int)GrayscalePixel(x, y) - (int)GrayscalePixel(x, y - mask_size);
+ Results[1] = (int)GrayscalePixel(x, y) - (int)GrayscalePixel(x + DiagonalMaskSize, y - DiagonalMaskSize);
+ Results[2] = (int)GrayscalePixel(x, y) - (int)GrayscalePixel(x + mask_size, y);
+ Results[3] = (int)GrayscalePixel(x, y) - (int)GrayscalePixel(x + DiagonalMaskSize, y + DiagonalMaskSize);
+ Results[4] = (int)GrayscalePixel(x, y) - (int)GrayscalePixel(x, y + mask_size);
+ Results[5] = (int)GrayscalePixel(x, y) - (int)GrayscalePixel(x - DiagonalMaskSize, y + DiagonalMaskSize);
+ Results[6] = (int)GrayscalePixel(x, y) - (int)GrayscalePixel(x - mask_size, y);
+ Results[7] = (int)GrayscalePixel(x, y) - (int)GrayscalePixel(x + DiagonalMaskSize, y - DiagonalMaskSize);
- result_x = (DiagonalMaskSize*Results[1]+mask_size*Results[2]+
- DiagonalMaskSize*Results[3]-DiagonalMaskSize*Results[5]-
- mask_size*Results[6]+DiagonalMaskSize*Results[7]) / 256;
- result_y = (-mask_size*Results[0]-DiagonalMaskSize*Results[1]+
- DiagonalMaskSize*Results[3]+mask_size*Results[4]+
- DiagonalMaskSize*Results[5]-DiagonalMaskSize*Results[7]) / 256;
+ result_x = (DiagonalMaskSize*Results[1] + mask_size*Results[2] +
+ DiagonalMaskSize*Results[3] - DiagonalMaskSize*Results[5] -
+ mask_size*Results[6] + DiagonalMaskSize*Results[7]) / 256;
+ result_y = (-mask_size*Results[0] - DiagonalMaskSize*Results[1] +
+ DiagonalMaskSize*Results[3] + mask_size*Results[4] +
+ DiagonalMaskSize*Results[5] - DiagonalMaskSize*Results[7]) / 256;
}
@@ -1327,28 +1348,28 @@ void MEImage::GradientVisualize(int vector_x, int vector_y)
}
int masksize = (ME_CAST_TO_IPLIMAGE(cvImg)->width < ME_CAST_TO_IPLIMAGE(cvImg)->height) ?
- ME_CAST_TO_IPLIMAGE(cvImg)->width / (vector_x+1) :
- ME_CAST_TO_IPLIMAGE(cvImg)->height / (vector_y+1);
+ ME_CAST_TO_IPLIMAGE(cvImg)->width / (vector_x + 1) :
+ ME_CAST_TO_IPLIMAGE(cvImg)->height / (vector_y + 1);
- SmoothAdvanced(s_Gaussian, masksize*2-1);
+ SmoothAdvanced(s_Gaussian, masksize * 2 - 1);
for (int i = 1; i < vector_x; i++)
for (int i1 = 1; i1 < vector_y; i1++)
- {
- int Resultx = 0, Resulty = 0;
- int x = (int)(((float)ME_CAST_TO_IPLIMAGE(cvImg)->width*i / (vector_x)));
- int y = (int)(((float)ME_CAST_TO_IPLIMAGE(cvImg)->height*i1 / (vector_y)));
+ {
+ int Resultx = 0, Resulty = 0;
+ int x = (int)(((float)ME_CAST_TO_IPLIMAGE(cvImg)->width*i / (vector_x)));
+ int y = (int)(((float)ME_CAST_TO_IPLIMAGE(cvImg)->height*i1 / (vector_y)));
- GradientVector(false, x, y, (int)(0.707*masksize), Resultx, Resulty);
+ GradientVector(false, x, y, (int)(0.707*masksize), Resultx, Resulty);
- CvPoint Point1;
- CvPoint Point2;
+ CvPoint Point1;
+ CvPoint Point2;
- Point1.x = x-Resultx / 2;
- Point1.y = y-Resulty / 2;
- Point2.x = x+Resultx / 2;
- Point2.y = y+Resulty / 2;
- cvLine(ME_CAST_TO_IPLIMAGE(cvImg), Point1, Point2, CV_RGB(255, 255, 255), 1, 8);
- }
+ Point1.x = x - Resultx / 2;
+ Point1.y = y - Resulty / 2;
+ Point2.x = x + Resultx / 2;
+ Point2.y = y + Resulty / 2;
+ cvLine(ME_CAST_TO_IPLIMAGE(cvImg), Point1, Point2, CV_RGB(255, 255, 255), 1, 8);
+ }
}
@@ -1400,16 +1421,16 @@ void MEImage::ComputeColorSpace(ColorSpaceConvertType mode)
return;
}
IplImage* TempImg = cvCreateImage(cvSize(ME_CAST_TO_IPLIMAGE(cvImg)->width, ME_CAST_TO_IPLIMAGE(cvImg)->height), 8,
- ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
+ ME_CAST_TO_IPLIMAGE(cvImg)->nChannels);
for (int i = 0; i < 3; i++)
for (int i1 = 0; i1 < 3; i1++)
- {
- if (mode == csc_RGBtoYUV)
- TransformMatrix[i][i1] = RGBtoYUVMatrix[i][i1];
- if (mode == csc_RGBtoYIQ)
- TransformMatrix[i][i1] = RGBtoYIQMatrix[i][i1];
- }
+ {
+ if (mode == csc_RGBtoYUV)
+ TransformMatrix[i][i1] = RGBtoYUVMatrix[i][i1];
+ if (mode == csc_RGBtoYIQ)
+ TransformMatrix[i][i1] = RGBtoYIQMatrix[i][i1];
+ }
float x = 0.0;
float y = 0.0;
float z = 0.0;
@@ -1441,25 +1462,25 @@ void MEImage::ComputeColorSpace(ColorSpaceConvertType mode)
unsigned char* SrcData = (unsigned char*)ME_CAST_TO_IPLIMAGE(cvImg)->imageData;
unsigned char* DstData = (unsigned char*)TempImg->imageData;
- for (int i = ME_CAST_TO_IPLIMAGE(cvImg)->widthStep*ME_CAST_TO_IPLIMAGE(cvImg)->height-1; i >= 0; i-=3)
+ for (int i = ME_CAST_TO_IPLIMAGE(cvImg)->widthStep*ME_CAST_TO_IPLIMAGE(cvImg)->height - 1; i >= 0; i -= 3)
{
- x = (float)SrcData[i]*TransformMatrix[0][0]+
- (float)SrcData[i+1]*TransformMatrix[0][1]+
- (float)SrcData[i+2]*TransformMatrix[0][2];
- y = (float)SrcData[i]*TransformMatrix[1][0]+
- (float)SrcData[i+1]*TransformMatrix[1][1]+
- (float)SrcData[i+2]*TransformMatrix[1][2];
- z = (float)SrcData[i]*TransformMatrix[2][0]+
- (float)SrcData[i+1]*TransformMatrix[2][1]+
- (float)SrcData[i+2]*TransformMatrix[2][2];
+ x = (float)SrcData[i] * TransformMatrix[0][0] +
+ (float)SrcData[i + 1] * TransformMatrix[0][1] +
+ (float)SrcData[i + 2] * TransformMatrix[0][2];
+ y = (float)SrcData[i] * TransformMatrix[1][0] +
+ (float)SrcData[i + 1] * TransformMatrix[1][1] +
+ (float)SrcData[i + 2] * TransformMatrix[1][2];
+ z = (float)SrcData[i] * TransformMatrix[2][0] +
+ (float)SrcData[i + 1] * TransformMatrix[2][1] +
+ (float)SrcData[i + 2] * TransformMatrix[2][2];
- x = xmax-xmin != 0.0 ? 255.0 : (x-xmin) / (xmax-xmin)*255.0;
- y = ymax-ymin != 0.0 ? 255.0 : (y-xmin) / (ymax-ymin)*255.0;
- z = zmax-zmin != 0.0 ? 255.0 : (z-xmin) / (zmax-zmin)*255.0;
+ x = xmax - xmin != 0.0 ? 255.0 : (x - xmin) / (xmax - xmin)*255.0;
+ y = ymax - ymin != 0.0 ? 255.0 : (y - xmin) / (ymax - ymin)*255.0;
+ z = zmax - zmin != 0.0 ? 255.0 : (z - xmin) / (zmax - zmin)*255.0;
DstData[i] = (unsigned char)MEBound(0, (int)x, 255);
- DstData[i+1] = (unsigned char)MEBound(0, (int)y, 255);
- DstData[i+2] = (unsigned char)MEBound(0, (int)z, 255);
+ DstData[i + 1] = (unsigned char)MEBound(0, (int)y, 255);
+ DstData[i + 2] = (unsigned char)MEBound(0, (int)z, 255);
}
ME_RELEASE_IPLIMAGE(cvImg);
cvImg = TempImg;
diff --git a/package_bgs/ck/MEImage.hpp b/package_bgs/LBP_MRF/MEImage.hpp
similarity index 97%
rename from package_bgs/ck/MEImage.hpp
rename to package_bgs/LBP_MRF/MEImage.hpp
index 41ada3b..3a52a77 100644
--- a/package_bgs/ck/MEImage.hpp
+++ b/package_bgs/LBP_MRF/MEImage.hpp
@@ -1,4 +1,20 @@
/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+/*
* This file is part of the AiBO+ project
*
* Copyright (C) 2005-2013 Csaba Kertész (csaba.kertesz@gmail.com)
@@ -18,19 +34,17 @@
* Foundation, Inc., 59 Temple Street #330, Boston, MA 02111-1307, USA.
*
*/
+#pragma once
-#ifndef MEImage_H
-#define MEImage_H
-
-/**
- * @addtogroup mindeye
- * @{
- */
+ /**
+ * @addtogroup mindeye
+ * @{
+ */
-/**
- * MEImage
- * @brief Basic image functions
- */
+ /**
+ * MEImage
+ * @brief Basic image functions
+ */
class MEImage
{
public:
@@ -995,5 +1009,3 @@ class MEImage
};
/** @} */
-
-#endif
diff --git a/package_bgs/ck/MotionDetection.cpp b/package_bgs/LBP_MRF/MotionDetection.cpp
similarity index 91%
rename from package_bgs/ck/MotionDetection.cpp
rename to package_bgs/LBP_MRF/MotionDetection.cpp
index 5ac096a..e591faa 100644
--- a/package_bgs/ck/MotionDetection.cpp
+++ b/package_bgs/LBP_MRF/MotionDetection.cpp
@@ -1,4 +1,20 @@
/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+/*
* This file is part of the AiBO+ project
*
* Copyright (C) 2005-2013 Csaba Kertész (csaba.kertesz@gmail.com)
@@ -52,15 +68,15 @@ struct MEPixelDataType
};
MotionDetection::MotionDetection(DetectorType mode) :
-MDMode(md_NotDefined), MDDataState(ps_Uninitialized), Frames(0), ReadyMask(false),
-HUColorSpace(MEImage::csc_RGBtoCIELuv), HULBPMode(MEImage::lbp_Special),
-HUHistogramsPerPixel(3), HUHistogramArea(5), HUHistogramBins(8),
-HUImageWidth(-1), HUImageHeight(-1), HULBPPixelData(NULL),
-HUPrThres(0.75), HUBackgrThres(0.95), HUHistLRate(0.01), HUWeightsLRate(0.01),
-HUSamplePixels(-1), HUDesiredSamplePixels(-1), HUMinCutWeight(8.0),
-HUOFDataState(ps_Uninitialized), HUOFPointsNumber(-1),
-HUOFCamMovementX(0), MaxTrackedPoints(0), HUOFFrames(-1),
-HUOFCamMovement(false)
+ MDMode(md_NotDefined), MDDataState(ps_Uninitialized), Frames(0), ReadyMask(false),
+ HUColorSpace(MEImage::csc_RGBtoCIELuv), HULBPMode(MEImage::lbp_Special),
+ HUHistogramsPerPixel(3), HUHistogramArea(5), HUHistogramBins(8),
+ HUImageWidth(-1), HUImageHeight(-1), HULBPPixelData(NULL),
+ HUPrThres(0.75), HUBackgrThres(0.95), HUHistLRate(0.01), HUWeightsLRate(0.01),
+ HUSamplePixels(-1), HUDesiredSamplePixels(-1), HUMinCutWeight(8.0),
+ HUOFDataState(ps_Uninitialized), HUOFPointsNumber(-1),
+ HUOFCamMovementX(0), MaxTrackedPoints(0), HUOFFrames(-1),
+ HUOFCamMovement(false)
{
HUOFPyramid = NULL;
HUOFPrevPyramid = NULL;
@@ -357,13 +373,13 @@ void MotionDetection::InitHUData(int imagewidth, int imageheight)
for (int i = 0; i < HUImageWidth / 2; ++i)
for (int i1 = 0; i1 < HUImageHeight; ++i1)
{
- HULBPPixelData[i][i1] = new MEPixelDataType;
- HULBPPixelData[i][i1]->Weights = new float[HUHistogramsPerPixel];
- HULBPPixelData[i][i1]->BackgroundHistogram = new bool[HUHistogramsPerPixel];
- HULBPPixelData[i][i1]->Histograms = new float*[HUHistogramsPerPixel];
- for (int i2 = 0; i2 < HUHistogramsPerPixel; ++i2)
- HULBPPixelData[i][i1]->Histograms[i2] = new float[HUHistogramBins];
- HULBPPixelData[i][i1]->PreviousHistogram = new float[HUHistogramBins];
+ HULBPPixelData[i][i1] = new MEPixelDataType;
+ HULBPPixelData[i][i1]->Weights = new float[HUHistogramsPerPixel];
+ HULBPPixelData[i][i1]->BackgroundHistogram = new bool[HUHistogramsPerPixel];
+ HULBPPixelData[i][i1]->Histograms = new float*[HUHistogramsPerPixel];
+ for (int i2 = 0; i2 < HUHistogramsPerPixel; ++i2)
+ HULBPPixelData[i][i1]->Histograms[i2] = new float[HUHistogramBins];
+ HULBPPixelData[i][i1]->PreviousHistogram = new float[HUHistogramBins];
}
// Allocate auxiliary variables
@@ -399,8 +415,8 @@ void MotionDetection::InitHUOFData(int imagewidth, int imageheight)
HUOFPointsNumber = imagewidth*imageheight / 1000;
HUOFPyramid = cvCreateImage(cvSize(imagewidth, imageheight), 8, 1);
HUOFPrevPyramid = cvCreateImage(cvSize(imagewidth, imageheight), 8, 1);
- HUOFPoints[0] = (CvPoint2D32f*)cvAlloc(HUOFPointsNumber*sizeof(HUOFPoints[0][0]));
- HUOFPoints[1] = (CvPoint2D32f*)cvAlloc(HUOFPointsNumber*sizeof(HUOFPoints[1][0]));
+ HUOFPoints[0] = (CvPoint2D32f*)cvAlloc(HUOFPointsNumber * sizeof(HUOFPoints[0][0]));
+ HUOFPoints[1] = (CvPoint2D32f*)cvAlloc(HUOFPointsNumber * sizeof(HUOFPoints[1][0]));
}
}
@@ -412,13 +428,13 @@ void MotionDetection::ReleaseHUData()
for (int i = 0; i < HUImageWidth / 2; i++)
for (int i1 = 0; i1 < HUImageHeight; i1++)
{
- delete[] HULBPPixelData[i][i1]->PreviousHistogram;
- for (int i2 = 0; i2 < HUHistogramsPerPixel; ++i2)
- delete[] HULBPPixelData[i][i1]->Histograms[i2];
- delete[] HULBPPixelData[i][i1]->Histograms;
- delete[] HULBPPixelData[i][i1]->BackgroundHistogram;
- delete[] HULBPPixelData[i][i1]->Weights;
- delete HULBPPixelData[i][i1];
+ delete[] HULBPPixelData[i][i1]->PreviousHistogram;
+ for (int i2 = 0; i2 < HUHistogramsPerPixel; ++i2)
+ delete[] HULBPPixelData[i][i1]->Histograms[i2];
+ delete[] HULBPPixelData[i][i1]->Histograms;
+ delete[] HULBPPixelData[i][i1]->BackgroundHistogram;
+ delete[] HULBPPixelData[i][i1]->Weights;
+ delete HULBPPixelData[i][i1];
}
for (int i = 0; i < HUImageWidth / 2; i++)
@@ -486,15 +502,15 @@ void MotionDetection::ClearHUData()
for (int i = (HUImageWidth / 2) - 1; i >= 0; --i)
for (int i1 = HUImageHeight - 1; i1 >= 0; --i1)
{
- for (int i2 = HUHistogramsPerPixel - 1; i2 >= 0; --i2)
- {
- memset(HULBPPixelData[i][i1]->Histograms[i2], 0,
- HUHistogramBins*sizeof(float));
- HULBPPixelData[i][i1]->Weights[i2] = 1.0 / HUHistogramsPerPixel;
- HULBPPixelData[i][i1]->BackgroundHistogram[i2] = true;
- }
- HULBPPixelData[i][i1]->BackgroundRate = 1.0;
- HULBPPixelData[i][i1]->LifeCycle = 0;
+ for (int i2 = HUHistogramsPerPixel - 1; i2 >= 0; --i2)
+ {
+ memset(HULBPPixelData[i][i1]->Histograms[i2], 0,
+ HUHistogramBins * sizeof(float));
+ HULBPPixelData[i][i1]->Weights[i2] = 1.0 / HUHistogramsPerPixel;
+ HULBPPixelData[i][i1]->BackgroundHistogram[i2] = true;
+ }
+ HULBPPixelData[i][i1]->BackgroundRate = 1.0;
+ HULBPPixelData[i][i1]->LifeCycle = 0;
}
MDDataState = ps_Initialized;
}
@@ -563,13 +579,13 @@ void MotionDetection::DetectMotionsHU(MEImage& image)
else
if (Frames > 1)
{
- PreviousImage = CurrentImage;
- CurrentImage = image;
- // Optical flow correction of the camera movements
- if (MDMode == md_DLBPHistograms)
- {
- OpticalFlowCorrection();
- }
+ PreviousImage = CurrentImage;
+ CurrentImage = image;
+ // Optical flow correction of the camera movements
+ if (MDMode == md_DLBPHistograms)
+ {
+ OpticalFlowCorrection();
+ }
}
newimage.ConvertToGrayscale(MEImage::g_OpenCV);
@@ -915,17 +931,17 @@ void MotionDetection::UpdateHUPixelData(MEPixelDataType* PixelData, const float
for (int i1 = HUHistogramsPerPixel - 1; i1 >= 2; --i1)
for (int i = i1; i >= 1; --i)
{
- if (Weights[i][1] <= Weights[i - 1][1])
- {
- float tmp = Weights[i][0];
- float tmp2 = Weights[i][1];
+ if (Weights[i][1] <= Weights[i - 1][1])
+ {
+ float tmp = Weights[i][0];
+ float tmp2 = Weights[i][1];
- Weights[i][0] = Weights[i - 1][0];
- Weights[i][1] = Weights[i - 1][1];
+ Weights[i][0] = Weights[i - 1][0];
+ Weights[i][1] = Weights[i - 1][1];
- Weights[i - 1][0] = tmp;
- Weights[i - 1][1] = tmp2;
- }
+ Weights[i - 1][0] = tmp;
+ Weights[i - 1][1] = tmp2;
+ }
}
float Sum = 0;
@@ -1056,7 +1072,7 @@ void MotionDetection::OpticalFlowCorrection()
if ((Distances[i][2] > Distances[i - 1][2]) ||
((Distances[i][2] == Distances[i - 1][2]) &&
(abs(Distances[i][0]) + abs(Distances[i][1]) <
- abs(Distances[i - 1][0]) + abs(Distances[i - 1][1]))))
+ abs(Distances[i - 1][0]) + abs(Distances[i - 1][1]))))
{
int tmp = Distances[i][0];
int tmp2 = Distances[i][1];
@@ -1331,10 +1347,10 @@ void MotionDetection::GetMotionsMaskHU(MEImage& mask_image)
MaskImgData[RowStart + x + (HUHistogramArea / 2)] =
((int)(x > 1 && HULBPPixelData[(x / 2) - 1][y]->BackgroundRate == 0.0) +
(int)(x < mask_image.GetWidth() - HUHistogramArea - 1 &&
- HULBPPixelData[(x / 2) + 1][y]->BackgroundRate == 0.0) +
- (int)(y > 0 && HULBPPixelData[x / 2][y - 1]->BackgroundRate == 0.0) +
- (int)(y < mask_image.GetHeight() - HUHistogramArea &&
- HULBPPixelData[x / 2][y + 1]->BackgroundRate == 0.0) > 1)
+ HULBPPixelData[(x / 2) + 1][y]->BackgroundRate == 0.0) +
+ (int)(y > 0 && HULBPPixelData[x / 2][y - 1]->BackgroundRate == 0.0) +
+ (int)(y < mask_image.GetHeight() - HUHistogramArea &&
+ HULBPPixelData[x / 2][y + 1]->BackgroundRate == 0.0) > 1)
? 255 : 0;
}
}
diff --git a/package_bgs/ck/MotionDetection.hpp b/package_bgs/LBP_MRF/MotionDetection.hpp
similarity index 93%
rename from package_bgs/ck/MotionDetection.hpp
rename to package_bgs/LBP_MRF/MotionDetection.hpp
index 6e11521..e58c93c 100644
--- a/package_bgs/ck/MotionDetection.hpp
+++ b/package_bgs/LBP_MRF/MotionDetection.hpp
@@ -1,4 +1,20 @@
/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+/*
* This file is part of the AiBO+ project
*
* Copyright (C) 2005-2013 Csaba Kertész (csaba.kertesz@gmail.com)
@@ -18,14 +34,12 @@
* Foundation, Inc., 59 Temple Street #330, Boston, MA 02111-1307, USA.
*
*/
+#pragma once
-#ifndef MotionDetection_hpp
-#define MotionDetection_hpp
-
-/**
- * @addtogroup mindeye
- * @{
- */
+ /**
+ * @addtogroup mindeye
+ * @{
+ */
#include "MEDefs.hpp"
#include "MEImage.hpp"
@@ -181,7 +195,7 @@ class MotionDetection
*/
void CalculateResults(MEImage& referenceimage, int& tnegatives, int& tpositives,
- int& ttnegatives, int& ttpositives);
+ int& ttnegatives, int& ttpositives);
private:
@@ -397,5 +411,3 @@ class MotionDetection
};
/** @} */
-
-#endif
diff --git a/package_bgs/ck/block.h b/package_bgs/LBP_MRF/block.h
similarity index 51%
rename from package_bgs/ck/block.h
rename to package_bgs/LBP_MRF/block.h
index 98b1201..bd1ab67 100644
--- a/package_bgs/ck/block.h
+++ b/package_bgs/LBP_MRF/block.h
@@ -1,3 +1,19 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
/* block.h */
/*
Copyright 2001 Vladimir Kolmogorov (vnk@cs.cornell.edu), Yuri Boykov (yuri@csd.uwo.ca).
@@ -16,8 +32,6 @@
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
-
-
/*
Template classes Block and DBlock
Implement adding and deleting items of the same type in blocks.
@@ -105,9 +119,7 @@
simultaneously at earlier moments. All memory is
deallocated only when the destructor is called.
*/
-
-#ifndef __BLOCK_H__
-#define __BLOCK_H__
+#pragma once
#include
#include
@@ -118,170 +130,168 @@
namespace ck
{
- template class Block
- {
- public:
- /* Constructor. Arguments are the block size and
+template class Block
+{
+public:
+ /* Constructor. Arguments are the block size and
(optionally) the pointer to the function which
will be called if allocation failed; the message
passed to this function is "Not enough memory!" */
- Block(int size, void(*err_function)(char *) = NULL) { first = last = NULL; block_size = size; error_function = err_function; }
+ Block(int size, void(*err_function)(char *) = NULL) { first = last = NULL; block_size = size; error_function = err_function; }
- /* Destructor. Deallocates all items added so far */
- ~Block() { while (first) { block *next = first->next; delete first; first = next; } }
+ /* Destructor. Deallocates all items added so far */
+ ~Block() { while (first) { block *next = first->next; delete first; first = next; } }
- /* Allocates 'num' consecutive items; returns pointer
+ /* Allocates 'num' consecutive items; returns pointer
to the first item. 'num' cannot be greater than the
block size since items must fit in one block */
- Type *New(int num = 1)
- {
- Type *t;
+ Type *New(int num = 1)
+ {
+ Type *t;
- if (!last || last->current + num > last->last)
+ if (!last || last->current + num > last->last)
+ {
+ if (last && last->next) last = last->next;
+ else
{
- if (last && last->next) last = last->next;
- else
- {
- block *next = (block *) new char[sizeof(block) + (block_size - 1)*sizeof(Type)];
- if (!next) { fprintf(stderr, "Not enough memory!"); exit(1); }
- if (last) last->next = next;
- else first = next;
- last = next;
- last->current = &(last->data[0]);
- last->last = last->current + block_size;
- last->next = NULL;
- }
+ block *next = (block *) new char[sizeof(block) + (block_size - 1)*sizeof(Type)];
+ if (!next) { fprintf(stderr, "Not enough memory!"); exit(1); }
+ if (last) last->next = next;
+ else first = next;
+ last = next;
+ last->current = &(last->data[0]);
+ last->last = last->current + block_size;
+ last->next = NULL;
}
-
- t = last->current;
- last->current += num;
- return t;
}
- /* Returns the first item (or NULL, if no items were added) */
- Type *ScanFirst()
- {
- scan_current_block = first;
- if (!scan_current_block) return NULL;
- scan_current_data = &(scan_current_block->data[0]);
- return scan_current_data++;
- }
+ t = last->current;
+ last->current += num;
+ return t;
+ }
+
+ /* Returns the first item (or NULL, if no items were added) */
+ Type *ScanFirst()
+ {
+ scan_current_block = first;
+ if (!scan_current_block) return NULL;
+ scan_current_data = &(scan_current_block->data[0]);
+ return scan_current_data++;
+ }
- /* Returns the next item (or NULL, if all items have been read)
+ /* Returns the next item (or NULL, if all items have been read)
Can be called only if previous ScanFirst() or ScanNext()
call returned not NULL. */
- Type *ScanNext()
+ Type *ScanNext()
+ {
+ if (scan_current_data >= scan_current_block->current)
{
- if (scan_current_data >= scan_current_block->current)
- {
- scan_current_block = scan_current_block->next;
- if (!scan_current_block) return NULL;
- scan_current_data = &(scan_current_block->data[0]);
- }
- return scan_current_data++;
+ scan_current_block = scan_current_block->next;
+ if (!scan_current_block) return NULL;
+ scan_current_data = &(scan_current_block->data[0]);
}
+ return scan_current_data++;
+ }
- /* Marks all elements as empty */
- void Reset()
+ /* Marks all elements as empty */
+ void Reset()
+ {
+ block *b;
+ if (!first) return;
+ for (b = first;; b = b->next)
{
- block *b;
- if (!first) return;
- for (b = first;; b = b->next)
- {
- b->current = &(b->data[0]);
- if (b == last) break;
- }
- last = first;
+ b->current = &(b->data[0]);
+ if (b == last) break;
}
+ last = first;
+ }
- /***********************************************************************/
+ /***********************************************************************/
- private:
+private:
- typedef struct block_st
- {
- Type *current, *last;
- struct block_st *next;
- Type data[1];
- } block;
+ typedef struct block_st
+ {
+ Type *current, *last;
+ struct block_st *next;
+ Type data[1];
+ } block;
- int block_size;
- block *first;
- block *last;
+ int block_size;
+ block *first;
+ block *last;
- block *scan_current_block;
- Type *scan_current_data;
+ block *scan_current_block;
+ Type *scan_current_data;
- void(*error_function)(char *);
- };
+ void(*error_function)(char *);
+};
- /***********************************************************************/
- /***********************************************************************/
- /***********************************************************************/
+/***********************************************************************/
+/***********************************************************************/
+/***********************************************************************/
- template class DBlock
- {
- public:
- /* Constructor. Arguments are the block size and
+template class DBlock
+{
+public:
+ /* Constructor. Arguments are the block size and
(optionally) the pointer to the function which
will be called if allocation failed; the message
passed to this function is "Not enough memory!" */
- DBlock(int size, void(*err_function)(char *) = NULL) { first = NULL; first_free = NULL; block_size = size; error_function = err_function; }
-
- /* Destructor. Deallocates all items added so far */
- ~DBlock() { while (first) { block *next = first->next; delete first; first = next; } }
-
- /* Allocates one item */
- Type *New()
- {
- block_item *item;
+ DBlock(int size, void(*err_function)(char *) = NULL) { first = NULL; first_free = NULL; block_size = size; error_function = err_function; }
- if (!first_free)
- {
- block *next = first;
- first = (block *) new char[sizeof(block) + (block_size - 1)*sizeof(block_item)];
- if (!first) { fprintf(stderr, "Not enough memory!"); exit(1); }
- first_free = &(first->data[0]);
- for (item = first_free; item < first_free + block_size - 1; item++)
- item->next_free = item + 1;
- item->next_free = NULL;
- first->next = next;
- }
+ /* Destructor. Deallocates all items added so far */
+ ~DBlock() { while (first) { block *next = first->next; delete first; first = next; } }
- item = first_free;
- first_free = item->next_free;
- return (Type *)item;
- }
+ /* Allocates one item */
+ Type *New()
+ {
+ block_item *item;
- /* Deletes an item allocated previously */
- void Delete(Type *t)
+ if (!first_free)
{
- ((block_item *)t)->next_free = first_free;
- first_free = (block_item *)t;
+ block *next = first;
+ first = (block *) new char[sizeof(block) + (block_size - 1)*sizeof(block_item)];
+ if (!first) { fprintf(stderr, "Not enough memory!"); exit(1); }
+ first_free = &(first->data[0]);
+ for (item = first_free; item < first_free + block_size - 1; item++)
+ item->next_free = item + 1;
+ item->next_free = NULL;
+ first->next = next;
}
- /***********************************************************************/
+ item = first_free;
+ first_free = item->next_free;
+ return (Type *)item;
+ }
- private:
+ /* Deletes an item allocated previously */
+ void Delete(Type *t)
+ {
+ ((block_item *)t)->next_free = first_free;
+ first_free = (block_item *)t;
+ }
- typedef union block_item_st
- {
- Type t;
- block_item_st *next_free;
- } block_item;
+ /***********************************************************************/
- typedef struct block_st
- {
- struct block_st *next;
- block_item data[1];
- } block;
+private:
- int block_size;
- block *first;
- block_item *first_free;
+ typedef union block_item_st
+ {
+ Type t;
+ block_item_st *next_free;
+ } block_item;
- void(*error_function)(char *);
- };
-}
+ typedef struct block_st
+ {
+ struct block_st *next;
+ block_item data[1];
+ } block;
+
+ int block_size;
+ block *first;
+ block_item *first_free;
-#endif
+ void(*error_function)(char *);
+};
+}
diff --git a/package_bgs/ck/graph.cpp b/package_bgs/LBP_MRF/graph.cpp
similarity index 78%
rename from package_bgs/ck/graph.cpp
rename to package_bgs/LBP_MRF/graph.cpp
index daed395..9301250 100644
--- a/package_bgs/ck/graph.cpp
+++ b/package_bgs/LBP_MRF/graph.cpp
@@ -1,3 +1,19 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
/* graph.cpp */
/*
Copyright 2001 Vladimir Kolmogorov (vnk@cs.cornell.edu), Yuri Boykov (yuri@csd.uwo.ca).
@@ -80,4 +96,4 @@ namespace ck
flow += (cap_source < cap_sink) ? cap_source : cap_sink;
((node*)i)->tr_cap = cap_source - cap_sink;
}
-}
\ No newline at end of file
+}
diff --git a/package_bgs/ck/graph.h b/package_bgs/LBP_MRF/graph.h
similarity index 60%
rename from package_bgs/ck/graph.h
rename to package_bgs/LBP_MRF/graph.h
index b6799e4..e7b83c7 100644
--- a/package_bgs/ck/graph.h
+++ b/package_bgs/LBP_MRF/graph.h
@@ -1,3 +1,19 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
/* graph.h */
/*
This software library implements the maxflow algorithm
@@ -16,41 +32,36 @@
If you use this software for research purposes, you should cite
the aforementioned paper in any resulting publication.
*/
-
-/*
- Copyright 2001 Vladimir Kolmogorov (vnk@cs.cornell.edu), Yuri Boykov (yuri@csd.uwo.ca).
-
- This program is free software; you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation; either version 2 of the License, or
- (at your option) any later version.
-
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
-
- You should have received a copy of the GNU General Public License
- along with this program; if not, write to the Free Software
- Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
- */
-
-
-/*
- For description, example usage, discussion of graph representation
- and memory usage see README.TXT.
- */
-
-#ifndef __GRAPH_H__
-#define __GRAPH_H__
+ /*
+ Copyright 2001 Vladimir Kolmogorov (vnk@cs.cornell.edu), Yuri Boykov (yuri@csd.uwo.ca).
+
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2 of the License, or
+ (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+ /*
+ For description, example usage, discussion of graph representation
+ and memory usage see README.TXT.
+ */
+#pragma once
#include "block.h"
-/*
- Nodes, arcs and pointers to nodes are
- added in blocks for memory and time efficiency.
- Below are numbers of items in blocks
- */
+ /*
+ Nodes, arcs and pointers to nodes are
+ added in blocks for memory and time efficiency.
+ Below are numbers of items in blocks
+ */
#define NODE_BLOCK_SIZE 512
#define ARC_BLOCK_SIZE 1024
#define NODEPTR_BLOCK_SIZE 128
@@ -67,7 +78,7 @@ namespace ck
} termtype; /* terminals */
/* Type of edge weights.
- Can be changed to char, int, float, double, ... */
+ Can be changed to char, int, float, double, ... */
typedef short captype;
/* Type of total flow */
typedef int flowtype;
@@ -77,9 +88,9 @@ namespace ck
/* interface functions */
/* Constructor. Optional argument is the pointer to the
- function which will be called if an error occurs;
- an error message is passed to this function. If this
- argument is omitted, exit(1) will be called. */
+ function which will be called if an error occurs;
+ an error message is passed to this function. If this
+ argument is omitted, exit(1) will be called. */
Graph(void(*err_function)(char *) = NULL);
/* Destructor */
@@ -89,21 +100,21 @@ namespace ck
node_id add_node();
/* Adds a bidirectional edge between 'from' and 'to'
- with the weights 'cap' and 'rev_cap' */
+ with the weights 'cap' and 'rev_cap' */
void add_edge(node_id from, node_id to, captype cap, captype rev_cap);
/* Sets the weights of the edges 'SOURCE->i' and 'i->SINK'
- Can be called at most once for each node before any call to 'add_tweights'.
- Weights can be negative */
+ Can be called at most once for each node before any call to 'add_tweights'.
+ Weights can be negative */
void set_tweights(node_id i, captype cap_source, captype cap_sink);
/* Adds new edges 'SOURCE->i' and 'i->SINK' with corresponding weights
- Can be called multiple times for each node.
- Weights can be negative */
+ Can be called multiple times for each node.
+ Weights can be negative */
void add_tweights(node_id i, captype cap_source, captype cap_sink);
/* After the maxflow is computed, this function returns to which
- segment the node 'i' belongs (Graph::SOURCE or Graph::SINK) */
+ segment the node 'i' belongs (Graph::SOURCE or Graph::SINK) */
termtype what_segment(node_id i);
/* Computes the maxflow. Can be called only once. */
@@ -125,13 +136,13 @@ namespace ck
arc_st *parent; /* node's parent */
node_st *next; /* pointer to the next active node
- (or to itself if it is the last node in the list) */
+ (or to itself if it is the last node in the list) */
int TS; /* timestamp showing when DIST was computed */
int DIST; /* distance to the terminal */
short is_sink; /* flag showing whether the node is in the source or in the sink tree */
captype tr_cap; /* if tr_cap > 0 then tr_cap is residual capacity of the arc SOURCE->node
- otherwise -tr_cap is residual capacity of the arc node->SINK */
+ otherwise -tr_cap is residual capacity of the arc node->SINK */
} node;
/* arc structure */
@@ -156,8 +167,8 @@ namespace ck
DBlock *nodeptr_block;
void(*error_function)(char *); /* this function is called if a error occurs,
- with a corresponding error message
- (or exit(1) is called if it's NULL) */
+ with a corresponding error message
+ (or exit(1) is called if it's NULL) */
flowtype flow; /* total flow */
@@ -179,5 +190,3 @@ namespace ck
void process_sink_orphan(node *i);
};
}
-
-#endif
diff --git a/package_bgs/ck/maxflow.cpp b/package_bgs/LBP_MRF/maxflow.cpp
similarity index 67%
rename from package_bgs/ck/maxflow.cpp
rename to package_bgs/LBP_MRF/maxflow.cpp
index 53d3705..6ddec50 100644
--- a/package_bgs/ck/maxflow.cpp
+++ b/package_bgs/LBP_MRF/maxflow.cpp
@@ -1,3 +1,19 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
/* maxflow.cpp */
/*
Copyright 2001 Vladimir Kolmogorov (vnk@cs.cornell.edu), Yuri Boykov (yuri@csd.uwo.ca).
@@ -16,33 +32,31 @@
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
-
-
#include
#include "graph.h"
-/*
- special constants for node->parent
- */
+ /*
+ special constants for node->parent
+ */
#define TERMINAL ( (arc *) 1 ) /* to terminal */
#define ORPHAN ( (arc *) 2 ) /* orphan */
#define INFINITE_D 1000000000 /* infinite distance to the terminal */
-/***********************************************************************/
+ /***********************************************************************/
-/*
- Functions for processing active list.
- i->next points to the next node in the list
- (or to i, if i is the last node in the list).
- If i->next is NULL iff i is not in the list.
-
- There are two queues. Active nodes are added
- to the end of the second queue and read from
- the front of the first queue. If the first queue
- is empty, it is replaced by the second queue
- (and the second queue becomes empty).
- */
+ /*
+ Functions for processing active list.
+ i->next points to the next node in the list
+ (or to i, if i is the last node in the list).
+ If i->next is NULL iff i is not in the list.
+
+ There are two queues. Active nodes are added
+ to the end of the second queue and read from
+ the front of the first queue. If the first queue
+ is empty, it is replaced by the second queue
+ (and the second queue becomes empty).
+ */
namespace ck
{
inline void Graph::set_active(node *i)
@@ -58,10 +72,10 @@ namespace ck
}
/*
- Returns the next active node.
- If it is connected to the sink, it stays in the list,
- otherwise it is removed from the list
- */
+ Returns the next active node.
+ If it is connected to the sink, it stays in the list,
+ otherwise it is removed from the list
+ */
inline Graph::node * Graph::next_active()
{
node *i;
@@ -232,45 +246,45 @@ namespace ck
for (a0 = i->first; a0; a0 = a0->next)
if (a0->sister->r_cap)
{
- j = a0->head;
- if (!j->is_sink && (a = j->parent))
- {
- /* checking the origin of j */
- d = 0;
- while (1)
- {
- if (j->TS == TIME)
- {
- d += j->DIST;
- break;
- }
- a = j->parent;
- d++;
- if (a == TERMINAL)
- {
- j->TS = TIME;
- j->DIST = 1;
- break;
- }
- if (a == ORPHAN) { d = INFINITE_D; break; }
- j = a->head;
- }
- if (d < INFINITE_D) /* j originates from the source - done */
+ j = a0->head;
+ if (!j->is_sink && (a = j->parent))
{
- if (d < d_min)
+ /* checking the origin of j */
+ d = 0;
+ while (1)
{
- a0_min = a0;
- d_min = d;
+ if (j->TS == TIME)
+ {
+ d += j->DIST;
+ break;
+ }
+ a = j->parent;
+ d++;
+ if (a == TERMINAL)
+ {
+ j->TS = TIME;
+ j->DIST = 1;
+ break;
+ }
+ if (a == ORPHAN) { d = INFINITE_D; break; }
+ j = a->head;
}
- /* set marks along the path */
- for (j = a0->head; j->TS != TIME; j = j->parent->head)
+ if (d < INFINITE_D) /* j originates from the source - done */
{
- j->TS = TIME;
- j->DIST = d--;
+ if (d < d_min)
+ {
+ a0_min = a0;
+ d_min = d;
+ }
+ /* set marks along the path */
+ for (j = a0->head; j->TS != TIME; j = j->parent->head)
+ {
+ j->TS = TIME;
+ j->DIST = d--;
+ }
}
}
}
- }
if ((i->parent = a0_min))
{
@@ -316,45 +330,45 @@ namespace ck
for (a0 = i->first; a0; a0 = a0->next)
if (a0->r_cap)
{
- j = a0->head;
- if (j->is_sink && (a = j->parent))
- {
- /* checking the origin of j */
- d = 0;
- while (1)
- {
- if (j->TS == TIME)
- {
- d += j->DIST;
- break;
- }
- a = j->parent;
- d++;
- if (a == TERMINAL)
- {
- j->TS = TIME;
- j->DIST = 1;
- break;
- }
- if (a == ORPHAN) { d = INFINITE_D; break; }
- j = a->head;
- }
- if (d < INFINITE_D) /* j originates from the sink - done */
+ j = a0->head;
+ if (j->is_sink && (a = j->parent))
{
- if (d < d_min)
+ /* checking the origin of j */
+ d = 0;
+ while (1)
{
- a0_min = a0;
- d_min = d;
+ if (j->TS == TIME)
+ {
+ d += j->DIST;
+ break;
+ }
+ a = j->parent;
+ d++;
+ if (a == TERMINAL)
+ {
+ j->TS = TIME;
+ j->DIST = 1;
+ break;
+ }
+ if (a == ORPHAN) { d = INFINITE_D; break; }
+ j = a->head;
}
- /* set marks along the path */
- for (j = a0->head; j->TS != TIME; j = j->parent->head)
+ if (d < INFINITE_D) /* j originates from the sink - done */
{
- j->TS = TIME;
- j->DIST = d--;
+ if (d < d_min)
+ {
+ a0_min = a0;
+ d_min = d;
+ }
+ /* set marks along the path */
+ for (j = a0->head; j->TS != TIME; j = j->parent->head)
+ {
+ j->TS = TIME;
+ j->DIST = d--;
+ }
}
}
}
- }
if ((i->parent = a0_min))
{
@@ -419,24 +433,24 @@ namespace ck
for (a = i->first; a; a = a->next)
if (a->r_cap)
{
- j = a->head;
- if (!j->parent)
- {
- j->is_sink = 0;
- j->parent = a->sister;
- j->TS = i->TS;
- j->DIST = i->DIST + 1;
- set_active(j);
- }
- else if (j->is_sink) break;
- else if (j->TS <= i->TS &&
- j->DIST > i->DIST)
- {
- /* heuristic - trying to make the distance from j to the source shorter */
- j->parent = a->sister;
- j->TS = i->TS;
- j->DIST = i->DIST + 1;
- }
+ j = a->head;
+ if (!j->parent)
+ {
+ j->is_sink = 0;
+ j->parent = a->sister;
+ j->TS = i->TS;
+ j->DIST = i->DIST + 1;
+ set_active(j);
+ }
+ else if (j->is_sink) break;
+ else if (j->TS <= i->TS &&
+ j->DIST > i->DIST)
+ {
+ /* heuristic - trying to make the distance from j to the source shorter */
+ j->parent = a->sister;
+ j->TS = i->TS;
+ j->DIST = i->DIST + 1;
+ }
}
}
else
@@ -445,24 +459,24 @@ namespace ck
for (a = i->first; a; a = a->next)
if (a->sister->r_cap)
{
- j = a->head;
- if (!j->parent)
- {
- j->is_sink = 1;
- j->parent = a->sister;
- j->TS = i->TS;
- j->DIST = i->DIST + 1;
- set_active(j);
- }
- else if (!j->is_sink) { a = a->sister; break; }
- else if (j->TS <= i->TS &&
- j->DIST > i->DIST)
- {
- /* heuristic - trying to make the distance from j to the sink shorter */
- j->parent = a->sister;
- j->TS = i->TS;
- j->DIST = i->DIST + 1;
- }
+ j = a->head;
+ if (!j->parent)
+ {
+ j->is_sink = 1;
+ j->parent = a->sister;
+ j->TS = i->TS;
+ j->DIST = i->DIST + 1;
+ set_active(j);
+ }
+ else if (!j->is_sink) { a = a->sister; break; }
+ else if (j->TS <= i->TS &&
+ j->DIST > i->DIST)
+ {
+ /* heuristic - trying to make the distance from j to the sink shorter */
+ j->parent = a->sister;
+ j->TS = i->TS;
+ j->DIST = i->DIST + 1;
+ }
}
}
@@ -513,4 +527,4 @@ namespace ck
return SINK;
}
-}
\ No newline at end of file
+}
diff --git a/package_bgs/LBSP/BackgroundSubtractorLBSP.cpp b/package_bgs/LBSP/BackgroundSubtractorLBSP.cpp
new file mode 100644
index 0000000..2865a30
--- /dev/null
+++ b/package_bgs/LBSP/BackgroundSubtractorLBSP.cpp
@@ -0,0 +1,85 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+#include "BackgroundSubtractorLBSP.h"
+#include "DistanceUtils.h"
+#include "RandUtils.h"
+#include
+#include
+#include
+#include
+#include
+
+#ifndef SIZE_MAX
+# if __WORDSIZE == 64
+# define SIZE_MAX (18446744073709551615UL)
+# else
+# define SIZE_MAX (4294967295U)
+# endif
+#endif
+
+// local define used to determine the default median blur kernel size
+#define DEFAULT_MEDIAN_BLUR_KERNEL_SIZE (9)
+
+BackgroundSubtractorLBSP::BackgroundSubtractorLBSP(float fRelLBSPThreshold, size_t nLBSPThresholdOffset)
+ : m_nImgChannels(0)
+ , m_nImgType(0)
+ , m_nLBSPThresholdOffset(nLBSPThresholdOffset)
+ , m_fRelLBSPThreshold(fRelLBSPThreshold)
+ , m_nTotPxCount(0)
+ , m_nTotRelevantPxCount(0)
+ , m_nFrameIndex(SIZE_MAX)
+ , m_nFramesSinceLastReset(0)
+ , m_nModelResetCooldown(0)
+ , m_aPxIdxLUT(nullptr)
+ , m_aPxInfoLUT(nullptr)
+ , m_nDefaultMedianBlurKernelSize(DEFAULT_MEDIAN_BLUR_KERNEL_SIZE)
+ , m_bInitialized(false)
+ , m_bAutoModelResetEnabled(true)
+ , m_bUsingMovingCamera(false)
+ , nDebugCoordX(0), nDebugCoordY(0) {
+ CV_Assert(m_fRelLBSPThreshold >= 0);
+}
+
+BackgroundSubtractorLBSP::~BackgroundSubtractorLBSP() {}
+
+void BackgroundSubtractorLBSP::initialize(const cv::Mat& oInitImg) {
+ this->initialize(oInitImg, cv::Mat());
+}
+
+/*cv::AlgorithmInfo* BackgroundSubtractorLBSP::info() const {
+ return nullptr;
+}*/
+
+cv::Mat BackgroundSubtractorLBSP::getROICopy() const {
+ return m_oROI.clone();
+}
+
+void BackgroundSubtractorLBSP::setROI(cv::Mat& oROI) {
+ LBSP::validateROI(oROI);
+ CV_Assert(cv::countNonZero(oROI) > 0);
+ if (m_bInitialized) {
+ cv::Mat oLatestBackgroundImage;
+ getBackgroundImage(oLatestBackgroundImage);
+ initialize(oLatestBackgroundImage, oROI);
+ }
+ else
+ m_oROI = oROI.clone();
+}
+
+void BackgroundSubtractorLBSP::setAutomaticModelReset(bool bVal) {
+ m_bAutoModelResetEnabled = bVal;
+}
diff --git a/package_bgs/LBSP/BackgroundSubtractorLBSP.h b/package_bgs/LBSP/BackgroundSubtractorLBSP.h
new file mode 100644
index 0000000..ef0576c
--- /dev/null
+++ b/package_bgs/LBSP/BackgroundSubtractorLBSP.h
@@ -0,0 +1,101 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+#pragma once
+
+#include
+#include
+#include "LBSP.h"
+
+/*!
+ Local Binary Similarity Pattern (LBSP)-based change detection algorithm (abstract version/base class).
+
+ For more details on the different parameters, see P.-L. St-Charles and G.-A. Bilodeau, "Improving Background
+ Subtraction using Local Binary Similarity Patterns", in WACV 2014, or G.-A. Bilodeau et al, "Change Detection
+ in Feature Space Using Local Binary Similarity Patterns", in CRV 2013.
+
+ This algorithm is currently NOT thread-safe.
+ */
+class BackgroundSubtractorLBSP : public cv::BackgroundSubtractor {
+public:
+ //! full constructor
+ BackgroundSubtractorLBSP(float fRelLBSPThreshold, size_t nLBSPThresholdOffset = 0);
+ //! default destructor
+ virtual ~BackgroundSubtractorLBSP();
+ //! (re)initiaization method; needs to be called before starting background subtraction
+ virtual void initialize(const cv::Mat& oInitImg);
+ //! (re)initiaization method; needs to be called before starting background subtraction
+ virtual void initialize(const cv::Mat& oInitImg, const cv::Mat& oROI) = 0;
+ //! primary model update function; the learning param is used to override the internal learning speed (ignored when <= 0)
+ virtual void apply(cv::InputArray image, cv::OutputArray fgmask, double learningRate = 0) = 0;
+ //! unused, always returns nullptr
+ //virtual cv::AlgorithmInfo* info() const;
+ //! returns a copy of the ROI used for descriptor extraction
+ virtual cv::Mat getROICopy() const;
+ //! sets the ROI to be used for descriptor extraction (note: this function will reinit the model and return the usable ROI)
+ virtual void setROI(cv::Mat& oROI);
+ //! turns automatic model reset on or off
+ void setAutomaticModelReset(bool);
+
+protected:
+ struct PxInfoBase {
+ int nImgCoord_Y;
+ int nImgCoord_X;
+ size_t nModelIdx;
+ };
+ //! background model ROI used for LBSP descriptor extraction (specific to the input image size)
+ cv::Mat m_oROI;
+ //! input image size
+ cv::Size m_oImgSize;
+ //! input image channel size
+ size_t m_nImgChannels;
+ //! input image type
+ int m_nImgType;
+ //! LBSP internal threshold offset value, used to reduce texture noise in dark regions
+ const size_t m_nLBSPThresholdOffset;
+ //! LBSP relative internal threshold (kept here since we don't keep an LBSP object)
+ const float m_fRelLBSPThreshold;
+ //! total number of pixels (depends on the input frame size) & total number of relevant pixels
+ size_t m_nTotPxCount, m_nTotRelevantPxCount;
+ //! current frame index, frame count since last model reset & model reset cooldown counters
+ size_t m_nFrameIndex, m_nFramesSinceLastReset, m_nModelResetCooldown;
+ //! pre-allocated internal LBSP threshold values LUT for all possible 8-bit intensities
+ size_t m_anLBSPThreshold_8bitLUT[UCHAR_MAX + 1];
+ //! internal pixel index LUT for all relevant analysis regions (based on the provided ROI)
+ size_t* m_aPxIdxLUT;
+ //! internal pixel info LUT for all possible pixel indexes
+ PxInfoBase* m_aPxInfoLUT;
+ //! default kernel size for median blur post-proc filtering
+ const int m_nDefaultMedianBlurKernelSize;
+ //! specifies whether the algorithm is fully initialized or not
+ bool m_bInitialized;
+ //! specifies whether automatic model resets are enabled or not
+ bool m_bAutoModelResetEnabled;
+ //! specifies whether the camera is considered moving or not
+ bool m_bUsingMovingCamera;
+ //! copy of latest pixel intensities (used when refreshing model)
+ cv::Mat m_oLastColorFrame;
+ //! copy of latest descriptors (used when refreshing model)
+ cv::Mat m_oLastDescFrame;
+ //! the foreground mask generated by the method at [t-1]
+ cv::Mat m_oLastFGMask;
+
+public:
+ // ######## DEBUG PURPOSES ONLY ##########
+ int nDebugCoordX, nDebugCoordY;
+ std::string sDebugName;
+};
+
diff --git a/package_bgs/LBSP/BackgroundSubtractorLBSP_.cpp b/package_bgs/LBSP/BackgroundSubtractorLBSP_.cpp
new file mode 100644
index 0000000..4e5d4a6
--- /dev/null
+++ b/package_bgs/LBSP/BackgroundSubtractorLBSP_.cpp
@@ -0,0 +1,79 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+#include "BackgroundSubtractorLBSP_.h"
+#include "DistanceUtils.h"
+#include "RandUtils.h"
+#include
+#include
+#include
+#include
+#include
+
+// local define used to determine the default median blur kernel size
+#define DEFAULT_MEDIAN_BLUR_KERNEL_SIZE (9)
+
+BackgroundSubtractorLBSP_::BackgroundSubtractorLBSP_(float fRelLBSPThreshold, size_t nLBSPThresholdOffset)
+ : m_nImgChannels(0)
+ , m_nImgType(0)
+ , m_nLBSPThresholdOffset(nLBSPThresholdOffset)
+ , m_fRelLBSPThreshold(fRelLBSPThreshold)
+ , m_nTotPxCount(0)
+ , m_nTotRelevantPxCount(0)
+ , m_nFrameIndex(SIZE_MAX)
+ , m_nFramesSinceLastReset(0)
+ , m_nModelResetCooldown(0)
+ , m_aPxIdxLUT(nullptr)
+ , m_aPxInfoLUT(nullptr)
+ , m_nDefaultMedianBlurKernelSize(DEFAULT_MEDIAN_BLUR_KERNEL_SIZE)
+ , m_bInitialized(false)
+ , m_bAutoModelResetEnabled(true)
+ , m_bUsingMovingCamera(false)
+ , m_nDebugCoordX(0)
+ , m_nDebugCoordY(0)
+ , m_pDebugFS(nullptr) {
+ CV_Assert(m_fRelLBSPThreshold >= 0);
+}
+
+BackgroundSubtractorLBSP_::~BackgroundSubtractorLBSP_() {}
+
+void BackgroundSubtractorLBSP_::initialize(const cv::Mat& oInitImg) {
+ this->initialize(oInitImg, cv::Mat());
+}
+/*
+cv::AlgorithmInfo* BackgroundSubtractorLBSP_::info() const {
+ return nullptr;
+}
+*/
+cv::Mat BackgroundSubtractorLBSP_::getROICopy() const {
+ return m_oROI.clone();
+}
+
+void BackgroundSubtractorLBSP_::setROI(cv::Mat& oROI) {
+ LBSP_::validateROI(oROI);
+ CV_Assert(cv::countNonZero(oROI) > 0);
+ if (m_bInitialized) {
+ cv::Mat oLatestBackgroundImage;
+ getBackgroundImage(oLatestBackgroundImage);
+ initialize(oLatestBackgroundImage, oROI);
+ }
+ else
+ m_oROI = oROI.clone();
+}
+
+void BackgroundSubtractorLBSP_::setAutomaticModelReset(bool bVal) {
+ m_bAutoModelResetEnabled = bVal;
+}
diff --git a/package_bgs/LBSP/BackgroundSubtractorLBSP_.h b/package_bgs/LBSP/BackgroundSubtractorLBSP_.h
new file mode 100644
index 0000000..861f78a
--- /dev/null
+++ b/package_bgs/LBSP/BackgroundSubtractorLBSP_.h
@@ -0,0 +1,107 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+#pragma once
+
+#include
+#include
+#include "LBSP_.h"
+
+/*!
+ Local Binary Similarity Pattern (LBSP)-based change detection algorithm (abstract version/base class).
+
+ For more details on the different parameters, see P.-L. St-Charles and G.-A. Bilodeau, "Improving Background
+ Subtraction using Local Binary Similarity Patterns", in WACV 2014, or G.-A. Bilodeau et al, "Change Detection
+ in Feature Space Using Local Binary Similarity Patterns", in CRV 2013.
+
+ This algorithm is currently NOT thread-safe.
+ */
+class BackgroundSubtractorLBSP_ : public cv::BackgroundSubtractor {
+public:
+ //! full constructor
+ BackgroundSubtractorLBSP_(float fRelLBSPThreshold, size_t nLBSPThresholdOffset = 0);
+ //! default destructor
+ virtual ~BackgroundSubtractorLBSP_();
+ //! (re)initiaization method; needs to be called before starting background subtraction
+ virtual void initialize(const cv::Mat& oInitImg);
+ //! (re)initiaization method; needs to be called before starting background subtraction
+ virtual void initialize(const cv::Mat& oInitImg, const cv::Mat& oROI) = 0;
+ //! primary model update function; the learning param is used to override the internal learning speed (ignored when <= 0)
+ virtual void apply(cv::InputArray image, cv::OutputArray fgmask, double learningRate = 0) = 0;
+ //! unused, always returns nullptr
+ //virtual cv::AlgorithmInfo* info() const;
+ //! returns a copy of the ROI used for descriptor extraction
+ virtual cv::Mat getROICopy() const;
+ //! sets the ROI to be used for descriptor extraction (note: this function will reinit the model and return the usable ROI)
+ virtual void setROI(cv::Mat& oROI);
+ //! turns automatic model reset on or off
+ void setAutomaticModelReset(bool);
+
+protected:
+ struct PxInfoBase {
+ int nImgCoord_Y;
+ int nImgCoord_X;
+ size_t nModelIdx;
+ };
+ //! background model ROI used for LBSP descriptor extraction (specific to the input image size)
+ cv::Mat m_oROI;
+ //! input image size
+ cv::Size m_oImgSize;
+ //! input image channel size
+ size_t m_nImgChannels;
+ //! input image type
+ int m_nImgType;
+ //! LBSP internal threshold offset value, used to reduce texture noise in dark regions
+ const size_t m_nLBSPThresholdOffset;
+ //! LBSP relative internal threshold (kept here since we don't keep an LBSP object)
+ const float m_fRelLBSPThreshold;
+ //! total number of pixels (depends on the input frame size) & total number of relevant pixels
+ size_t m_nTotPxCount, m_nTotRelevantPxCount;
+ //! current frame index, frame count since last model reset & model reset cooldown counters
+ size_t m_nFrameIndex, m_nFramesSinceLastReset, m_nModelResetCooldown;
+ //! pre-allocated internal LBSP threshold values LUT for all possible 8-bit intensities
+ size_t m_anLBSPThreshold_8bitLUT[UCHAR_MAX + 1];
+ //! internal pixel index LUT for all relevant analysis regions (based on the provided ROI)
+ size_t* m_aPxIdxLUT;
+ //! internal pixel info LUT for all possible pixel indexes
+ PxInfoBase* m_aPxInfoLUT;
+ //! default kernel size for median blur post-proc filtering
+ const int m_nDefaultMedianBlurKernelSize;
+ //! specifies whether the algorithm is fully initialized or not
+ bool m_bInitialized;
+ //! specifies whether automatic model resets are enabled or not
+ bool m_bAutoModelResetEnabled;
+ //! specifies whether the camera is considered moving or not
+ bool m_bUsingMovingCamera;
+ //! copy of latest pixel intensities (used when refreshing model)
+ cv::Mat m_oLastColorFrame;
+ //! copy of latest descriptors (used when refreshing model)
+ cv::Mat m_oLastDescFrame;
+ //! the foreground mask generated by the method at [t-1]
+ cv::Mat m_oLastFGMask;
+
+private:
+ //! copy constructor -- disabled since this class (and its children) use lots of dynamic structs based on raw pointers
+ BackgroundSubtractorLBSP_(const BackgroundSubtractorLBSP_&);
+ //! assignment operator -- disabled since this class (and its children) use lots of dynamic structs based on raw pointers
+ BackgroundSubtractorLBSP_& operator=(const BackgroundSubtractorLBSP_&);
+
+public:
+ // ######## DEBUG PURPOSES ONLY ##########
+ int m_nDebugCoordX, m_nDebugCoordY;
+ std::string m_sDebugName;
+ cv::FileStorage* m_pDebugFS;
+};
diff --git a/package_bgs/LBSP/BackgroundSubtractorLOBSTER.cpp b/package_bgs/LBSP/BackgroundSubtractorLOBSTER.cpp
new file mode 100644
index 0000000..9648c5c
--- /dev/null
+++ b/package_bgs/LBSP/BackgroundSubtractorLOBSTER.cpp
@@ -0,0 +1,342 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+#include "BackgroundSubtractorLOBSTER.h"
+#include "DistanceUtils.h"
+#include "RandUtils.h"
+#include
+#include
+#include
+#include
+
+BackgroundSubtractorLOBSTER::BackgroundSubtractorLOBSTER(float fRelLBSPThreshold
+ , size_t nLBSPThresholdOffset
+ , size_t nDescDistThreshold
+ , size_t nColorDistThreshold
+ , size_t nBGSamples
+ , size_t nRequiredBGSamples)
+ : BackgroundSubtractorLBSP(fRelLBSPThreshold, nLBSPThresholdOffset)
+ , m_nColorDistThreshold(nColorDistThreshold)
+ , m_nDescDistThreshold(nDescDistThreshold)
+ , m_nBGSamples(nBGSamples)
+ , m_nRequiredBGSamples(nRequiredBGSamples) {
+ CV_Assert(m_nRequiredBGSamples <= m_nBGSamples);
+ m_bAutoModelResetEnabled = false; // @@@@@@ not supported here for now
+}
+
+BackgroundSubtractorLOBSTER::~BackgroundSubtractorLOBSTER() {
+ if (m_aPxIdxLUT)
+ delete[] m_aPxIdxLUT;
+ if (m_aPxInfoLUT)
+ delete[] m_aPxInfoLUT;
+}
+
+void BackgroundSubtractorLOBSTER::initialize(const cv::Mat& oInitImg, const cv::Mat& oROI) {
+ CV_Assert(!oInitImg.empty() && oInitImg.cols > 0 && oInitImg.rows > 0);
+ CV_Assert(oInitImg.isContinuous());
+ CV_Assert(oInitImg.type() == CV_8UC1 || oInitImg.type() == CV_8UC3);
+ if (oInitImg.type() == CV_8UC3) {
+ std::vector voInitImgChannels;
+ cv::split(oInitImg, voInitImgChannels);
+ if (!cv::countNonZero((voInitImgChannels[0] != voInitImgChannels[1]) | (voInitImgChannels[2] != voInitImgChannels[1])))
+ std::cout << std::endl << "\tBackgroundSubtractorLOBSTER : Warning, grayscale images should always be passed in CV_8UC1 format for optimal performance." << std::endl;
+ }
+ cv::Mat oNewBGROI;
+ if (oROI.empty() && (m_oROI.empty() || oROI.size() != oInitImg.size())) {
+ oNewBGROI.create(oInitImg.size(), CV_8UC1);
+ oNewBGROI = cv::Scalar_(UCHAR_MAX);
+ }
+ else if (oROI.empty())
+ oNewBGROI = m_oROI;
+ else {
+ CV_Assert(oROI.size() == oInitImg.size() && oROI.type() == CV_8UC1);
+ CV_Assert(cv::countNonZero((oROI < UCHAR_MAX)&(oROI > 0)) == 0);
+ oNewBGROI = oROI.clone();
+ }
+ LBSP::validateROI(oNewBGROI);
+ const size_t nROIPxCount = (size_t)cv::countNonZero(oNewBGROI);
+ CV_Assert(nROIPxCount > 0);
+ m_oROI = oNewBGROI;
+ m_oImgSize = oInitImg.size();
+ m_nImgType = oInitImg.type();
+ m_nImgChannels = oInitImg.channels();
+ m_nTotPxCount = m_oImgSize.area();
+ m_nTotRelevantPxCount = nROIPxCount;
+ m_nFrameIndex = 0;
+ m_nFramesSinceLastReset = 0;
+ m_nModelResetCooldown = 0;
+ m_oLastFGMask.create(m_oImgSize, CV_8UC1);
+ m_oLastFGMask = cv::Scalar_(0);
+ m_oLastColorFrame.create(m_oImgSize, CV_8UC((int)m_nImgChannels));
+ m_oLastColorFrame = cv::Scalar_::all(0);
+ m_oLastDescFrame.create(m_oImgSize, CV_16UC((int)m_nImgChannels));
+ m_oLastDescFrame = cv::Scalar_::all(0);
+ m_voBGColorSamples.resize(m_nBGSamples);
+ m_voBGDescSamples.resize(m_nBGSamples);
+ for (size_t s = 0; s < m_nBGSamples; ++s) {
+ m_voBGColorSamples[s].create(m_oImgSize, CV_8UC((int)m_nImgChannels));
+ m_voBGColorSamples[s] = cv::Scalar_::all(0);
+ m_voBGDescSamples[s].create(m_oImgSize, CV_16UC((int)m_nImgChannels));
+ m_voBGDescSamples[s] = cv::Scalar_::all(0);
+ }
+ if (m_aPxIdxLUT)
+ delete[] m_aPxIdxLUT;
+ if (m_aPxInfoLUT)
+ delete[] m_aPxInfoLUT;
+ m_aPxIdxLUT = new size_t[m_nTotRelevantPxCount];
+ m_aPxInfoLUT = new PxInfoBase[m_nTotPxCount];
+ if (m_nImgChannels == 1) {
+ CV_Assert(m_oLastColorFrame.step.p[0] == (size_t)m_oImgSize.width && m_oLastColorFrame.step.p[1] == 1);
+ CV_Assert(m_oLastDescFrame.step.p[0] == m_oLastColorFrame.step.p[0] * 2 && m_oLastDescFrame.step.p[1] == m_oLastColorFrame.step.p[1] * 2);
+ for (size_t t = 0; t <= UCHAR_MAX; ++t)
+ m_anLBSPThreshold_8bitLUT[t] = cv::saturate_cast((t*m_fRelLBSPThreshold + m_nLBSPThresholdOffset) / 2);
+ for (size_t nPxIter = 0, nModelIter = 0; nPxIter < m_nTotPxCount; ++nPxIter) {
+ if (m_oROI.data[nPxIter]) {
+ m_aPxIdxLUT[nModelIter] = nPxIter;
+ m_aPxInfoLUT[nPxIter].nImgCoord_Y = (int)nPxIter / m_oImgSize.width;
+ m_aPxInfoLUT[nPxIter].nImgCoord_X = (int)nPxIter%m_oImgSize.width;
+ m_aPxInfoLUT[nPxIter].nModelIdx = nModelIter;
+ m_oLastColorFrame.data[nPxIter] = oInitImg.data[nPxIter];
+ const size_t nDescIter = nPxIter * 2;
+ LBSP::computeGrayscaleDescriptor(oInitImg, oInitImg.data[nPxIter], m_aPxInfoLUT[nPxIter].nImgCoord_X, m_aPxInfoLUT[nPxIter].nImgCoord_Y, m_anLBSPThreshold_8bitLUT[oInitImg.data[nPxIter]], *((ushort*)(m_oLastDescFrame.data + nDescIter)));
+ ++nModelIter;
+ }
+ }
+ }
+ else { //m_nImgChannels==3
+ CV_Assert(m_oLastColorFrame.step.p[0] == (size_t)m_oImgSize.width * 3 && m_oLastColorFrame.step.p[1] == 3);
+ CV_Assert(m_oLastDescFrame.step.p[0] == m_oLastColorFrame.step.p[0] * 2 && m_oLastDescFrame.step.p[1] == m_oLastColorFrame.step.p[1] * 2);
+ for (size_t t = 0; t <= UCHAR_MAX; ++t)
+ m_anLBSPThreshold_8bitLUT[t] = cv::saturate_cast(t*m_fRelLBSPThreshold + m_nLBSPThresholdOffset);
+ for (size_t nPxIter = 0, nModelIter = 0; nPxIter < m_nTotPxCount; ++nPxIter) {
+ if (m_oROI.data[nPxIter]) {
+ m_aPxIdxLUT[nModelIter] = nPxIter;
+ m_aPxInfoLUT[nPxIter].nImgCoord_Y = (int)nPxIter / m_oImgSize.width;
+ m_aPxInfoLUT[nPxIter].nImgCoord_X = (int)nPxIter%m_oImgSize.width;
+ m_aPxInfoLUT[nPxIter].nModelIdx = nModelIter;
+ const size_t nPxRGBIter = nPxIter * 3;
+ const size_t nDescRGBIter = nPxRGBIter * 2;
+ for (size_t c = 0; c < 3; ++c) {
+ m_oLastColorFrame.data[nPxRGBIter + c] = oInitImg.data[nPxRGBIter + c];
+ LBSP::computeSingleRGBDescriptor(oInitImg, oInitImg.data[nPxRGBIter + c], m_aPxInfoLUT[nPxIter].nImgCoord_X, m_aPxInfoLUT[nPxIter].nImgCoord_Y, c, m_anLBSPThreshold_8bitLUT[oInitImg.data[nPxRGBIter + c]], ((ushort*)(m_oLastDescFrame.data + nDescRGBIter))[c]);
+ }
+ ++nModelIter;
+ }
+ }
+ }
+ m_bInitialized = true;
+ refreshModel(1.0f);
+}
+
+void BackgroundSubtractorLOBSTER::refreshModel(float fSamplesRefreshFrac, bool bForceFGUpdate) {
+ // == refresh
+ CV_Assert(m_bInitialized);
+ CV_Assert(fSamplesRefreshFrac > 0.0f && fSamplesRefreshFrac <= 1.0f);
+ const size_t nModelsToRefresh = fSamplesRefreshFrac < 1.0f ? (size_t)(fSamplesRefreshFrac*m_nBGSamples) : m_nBGSamples;
+ const size_t nRefreshStartPos = fSamplesRefreshFrac < 1.0f ? rand() % m_nBGSamples : 0;
+ if (m_nImgChannels == 1) {
+ for (size_t nModelIter = 0; nModelIter < m_nTotRelevantPxCount; ++nModelIter) {
+ const size_t nPxIter = m_aPxIdxLUT[nModelIter];
+ if (bForceFGUpdate || !m_oLastFGMask.data[nPxIter]) {
+ for (size_t nCurrModelIdx = nRefreshStartPos; nCurrModelIdx < nRefreshStartPos + nModelsToRefresh; ++nCurrModelIdx) {
+ int nSampleImgCoord_Y, nSampleImgCoord_X;
+ getRandSamplePosition(nSampleImgCoord_X, nSampleImgCoord_Y, m_aPxInfoLUT[nPxIter].nImgCoord_X, m_aPxInfoLUT[nPxIter].nImgCoord_Y, LBSP::PATCH_SIZE / 2, m_oImgSize);
+ const size_t nSamplePxIdx = m_oImgSize.width*nSampleImgCoord_Y + nSampleImgCoord_X;
+ if (bForceFGUpdate || !m_oLastFGMask.data[nSamplePxIdx]) {
+ const size_t nCurrRealModelIdx = nCurrModelIdx%m_nBGSamples;
+ m_voBGColorSamples[nCurrRealModelIdx].data[nPxIter] = m_oLastColorFrame.data[nSamplePxIdx];
+ *((ushort*)(m_voBGDescSamples[nCurrRealModelIdx].data + nPxIter * 2)) = *((ushort*)(m_oLastDescFrame.data + nSamplePxIdx * 2));
+ }
+ }
+ }
+ }
+ }
+ else { //m_nImgChannels==3
+ for (size_t nModelIter = 0; nModelIter < m_nTotRelevantPxCount; ++nModelIter) {
+ const size_t nPxIter = m_aPxIdxLUT[nModelIter];
+ if (bForceFGUpdate || !m_oLastFGMask.data[nPxIter]) {
+ for (size_t nCurrModelIdx = nRefreshStartPos; nCurrModelIdx < nRefreshStartPos + nModelsToRefresh; ++nCurrModelIdx) {
+ int nSampleImgCoord_Y, nSampleImgCoord_X;
+ getRandSamplePosition(nSampleImgCoord_X, nSampleImgCoord_Y, m_aPxInfoLUT[nPxIter].nImgCoord_X, m_aPxInfoLUT[nPxIter].nImgCoord_Y, LBSP::PATCH_SIZE / 2, m_oImgSize);
+ const size_t nSamplePxIdx = m_oImgSize.width*nSampleImgCoord_Y + nSampleImgCoord_X;
+ if (bForceFGUpdate || !m_oLastFGMask.data[nSamplePxIdx]) {
+ const size_t nCurrRealModelIdx = nCurrModelIdx%m_nBGSamples;
+ for (size_t c = 0; c < 3; ++c) {
+ m_voBGColorSamples[nCurrRealModelIdx].data[nPxIter * 3 + c] = m_oLastColorFrame.data[nSamplePxIdx * 3 + c];
+ *((ushort*)(m_voBGDescSamples[nCurrRealModelIdx].data + (nPxIter * 3 + c) * 2)) = *((ushort*)(m_oLastDescFrame.data + (nSamplePxIdx * 3 + c) * 2));
+ }
+ }
+ }
+ }
+ }
+ }
+}
+
+void BackgroundSubtractorLOBSTER::apply(cv::InputArray _image, cv::OutputArray _fgmask, double learningRate) {
+ CV_Assert(m_bInitialized);
+ CV_Assert(learningRate > 0);
+ cv::Mat oInputImg = _image.getMat();
+ CV_Assert(oInputImg.type() == m_nImgType && oInputImg.size() == m_oImgSize);
+ CV_Assert(oInputImg.isContinuous());
+ _fgmask.create(m_oImgSize, CV_8UC1);
+ cv::Mat oCurrFGMask = _fgmask.getMat();
+ oCurrFGMask = cv::Scalar_(0);
+ const size_t nLearningRate = (size_t)ceil(learningRate);
+ if (m_nImgChannels == 1) {
+ for (size_t nModelIter = 0; nModelIter < m_nTotRelevantPxCount; ++nModelIter) {
+ const size_t nPxIter = m_aPxIdxLUT[nModelIter];
+ const size_t nDescIter = nPxIter * 2;
+ const int nCurrImgCoord_X = m_aPxInfoLUT[nPxIter].nImgCoord_X;
+ const int nCurrImgCoord_Y = m_aPxInfoLUT[nPxIter].nImgCoord_Y;
+ const uchar nCurrColor = oInputImg.data[nPxIter];
+ size_t nGoodSamplesCount = 0, nModelIdx = 0;
+ ushort nCurrInputDesc;
+ while (nGoodSamplesCount < m_nRequiredBGSamples && nModelIdx < m_nBGSamples) {
+ const uchar nBGColor = m_voBGColorSamples[nModelIdx].data[nPxIter];
+ {
+ const size_t nColorDist = L1dist(nCurrColor, nBGColor);
+ if (nColorDist > m_nColorDistThreshold / 2)
+ goto failedcheck1ch;
+ LBSP::computeGrayscaleDescriptor(oInputImg, nBGColor, nCurrImgCoord_X, nCurrImgCoord_Y, m_anLBSPThreshold_8bitLUT[nBGColor], nCurrInputDesc);
+ const size_t nDescDist = hdist(nCurrInputDesc, *((ushort*)(m_voBGDescSamples[nModelIdx].data + nDescIter)));
+ if (nDescDist > m_nDescDistThreshold)
+ goto failedcheck1ch;
+ nGoodSamplesCount++;
+ }
+ failedcheck1ch:
+ nModelIdx++;
+ }
+ if (nGoodSamplesCount < m_nRequiredBGSamples)
+ oCurrFGMask.data[nPxIter] = UCHAR_MAX;
+ else {
+ if ((rand() % nLearningRate) == 0) {
+ const size_t nSampleModelIdx = rand() % m_nBGSamples;
+ ushort& nRandInputDesc = *((ushort*)(m_voBGDescSamples[nSampleModelIdx].data + nDescIter));
+ LBSP::computeGrayscaleDescriptor(oInputImg, nCurrColor, nCurrImgCoord_X, nCurrImgCoord_Y, m_anLBSPThreshold_8bitLUT[nCurrColor], nRandInputDesc);
+ m_voBGColorSamples[nSampleModelIdx].data[nPxIter] = nCurrColor;
+ }
+ if ((rand() % nLearningRate) == 0) {
+ int nSampleImgCoord_Y, nSampleImgCoord_X;
+ getRandNeighborPosition_3x3(nSampleImgCoord_X, nSampleImgCoord_Y, nCurrImgCoord_X, nCurrImgCoord_Y, LBSP::PATCH_SIZE / 2, m_oImgSize);
+ const size_t nSampleModelIdx = rand() % m_nBGSamples;
+ ushort& nRandInputDesc = m_voBGDescSamples[nSampleModelIdx].at(nSampleImgCoord_Y, nSampleImgCoord_X);
+ LBSP::computeGrayscaleDescriptor(oInputImg, nCurrColor, nCurrImgCoord_X, nCurrImgCoord_Y, m_anLBSPThreshold_8bitLUT[nCurrColor], nRandInputDesc);
+ m_voBGColorSamples[nSampleModelIdx].at(nSampleImgCoord_Y, nSampleImgCoord_X) = nCurrColor;
+ }
+ }
+ }
+ }
+ else { //m_nImgChannels==3
+ const size_t nCurrDescDistThreshold = m_nDescDistThreshold * 3;
+ const size_t nCurrColorDistThreshold = m_nColorDistThreshold * 3;
+ const size_t nCurrSCDescDistThreshold = nCurrDescDistThreshold / 2;
+ const size_t nCurrSCColorDistThreshold = nCurrColorDistThreshold / 2;
+ const size_t desc_row_step = m_voBGDescSamples[0].step.p[0];
+ const size_t img_row_step = m_voBGColorSamples[0].step.p[0];
+ for (size_t nModelIter = 0; nModelIter < m_nTotRelevantPxCount; ++nModelIter) {
+ const size_t nPxIter = m_aPxIdxLUT[nModelIter];
+ const int nCurrImgCoord_X = m_aPxInfoLUT[nPxIter].nImgCoord_X;
+ const int nCurrImgCoord_Y = m_aPxInfoLUT[nPxIter].nImgCoord_Y;
+ const size_t nPxIterRGB = nPxIter * 3;
+ const size_t nDescIterRGB = nPxIterRGB * 2;
+ const uchar* const anCurrColor = oInputImg.data + nPxIterRGB;
+ size_t nGoodSamplesCount = 0, nModelIdx = 0;
+ ushort anCurrInputDesc[3];
+ while (nGoodSamplesCount < m_nRequiredBGSamples && nModelIdx < m_nBGSamples) {
+ const ushort* const anBGDesc = (ushort*)(m_voBGDescSamples[nModelIdx].data + nDescIterRGB);
+ const uchar* const anBGColor = m_voBGColorSamples[nModelIdx].data + nPxIterRGB;
+ size_t nTotColorDist = 0;
+ size_t nTotDescDist = 0;
+ for (size_t c = 0; c < 3; ++c) {
+ const size_t nColorDist = L1dist(anCurrColor[c], anBGColor[c]);
+ if (nColorDist > nCurrSCColorDistThreshold)
+ goto failedcheck3ch;
+ LBSP::computeSingleRGBDescriptor(oInputImg, anBGColor[c], nCurrImgCoord_X, nCurrImgCoord_Y, c, m_anLBSPThreshold_8bitLUT[anBGColor[c]], anCurrInputDesc[c]);
+ const size_t nDescDist = hdist(anCurrInputDesc[c], anBGDesc[c]);
+ if (nDescDist > nCurrSCDescDistThreshold)
+ goto failedcheck3ch;
+ nTotColorDist += nColorDist;
+ nTotDescDist += nDescDist;
+ }
+ if (nTotDescDist <= nCurrDescDistThreshold && nTotColorDist <= nCurrColorDistThreshold)
+ nGoodSamplesCount++;
+ failedcheck3ch:
+ nModelIdx++;
+ }
+ if (nGoodSamplesCount < m_nRequiredBGSamples)
+ oCurrFGMask.data[nPxIter] = UCHAR_MAX;
+ else {
+ if ((rand() % nLearningRate) == 0) {
+ const size_t nSampleModelIdx = rand() % m_nBGSamples;
+ ushort* anRandInputDesc = ((ushort*)(m_voBGDescSamples[nSampleModelIdx].data + nDescIterRGB));
+ const size_t anCurrIntraLBSPThresholds[3] = { m_anLBSPThreshold_8bitLUT[anCurrColor[0]],m_anLBSPThreshold_8bitLUT[anCurrColor[1]],m_anLBSPThreshold_8bitLUT[anCurrColor[2]] };
+ LBSP::computeRGBDescriptor(oInputImg, anCurrColor, nCurrImgCoord_X, nCurrImgCoord_Y, anCurrIntraLBSPThresholds, anRandInputDesc);
+ for (size_t c = 0; c < 3; ++c)
+ *(m_voBGColorSamples[nSampleModelIdx].data + nPxIterRGB + c) = anCurrColor[c];
+ }
+ if ((rand() % nLearningRate) == 0) {
+ int nSampleImgCoord_Y, nSampleImgCoord_X;
+ getRandNeighborPosition_3x3(nSampleImgCoord_X, nSampleImgCoord_Y, nCurrImgCoord_X, nCurrImgCoord_Y, LBSP::PATCH_SIZE / 2, m_oImgSize);
+ const size_t nSampleModelIdx = rand() % m_nBGSamples;
+ ushort* anRandInputDesc = ((ushort*)(m_voBGDescSamples[nSampleModelIdx].data + desc_row_step*nSampleImgCoord_Y + 6 * nSampleImgCoord_X));
+ const size_t anCurrIntraLBSPThresholds[3] = { m_anLBSPThreshold_8bitLUT[anCurrColor[0]],m_anLBSPThreshold_8bitLUT[anCurrColor[1]],m_anLBSPThreshold_8bitLUT[anCurrColor[2]] };
+ LBSP::computeRGBDescriptor(oInputImg, anCurrColor, nCurrImgCoord_X, nCurrImgCoord_Y, anCurrIntraLBSPThresholds, anRandInputDesc);
+ for (size_t c = 0; c < 3; ++c)
+ *(m_voBGColorSamples[nSampleModelIdx].data + img_row_step*nSampleImgCoord_Y + 3 * nSampleImgCoord_X + c) = anCurrColor[c];
+ }
+ }
+ }
+ }
+ cv::medianBlur(oCurrFGMask, m_oLastFGMask, m_nDefaultMedianBlurKernelSize);
+ m_oLastFGMask.copyTo(oCurrFGMask);
+}
+
+void BackgroundSubtractorLOBSTER::getBackgroundImage(cv::OutputArray backgroundImage) const {
+ CV_DbgAssert(m_bInitialized);
+ cv::Mat oAvgBGImg = cv::Mat::zeros(m_oImgSize, CV_32FC((int)m_nImgChannels));
+ for (size_t s = 0; s < m_nBGSamples; ++s) {
+ for (int y = 0; y < m_oImgSize.height; ++y) {
+ for (int x = 0; x < m_oImgSize.width; ++x) {
+ const size_t idx_nimg = m_voBGColorSamples[s].step.p[0] * y + m_voBGColorSamples[s].step.p[1] * x;
+ const size_t idx_flt32 = idx_nimg * 4;
+ float* oAvgBgImgPtr = (float*)(oAvgBGImg.data + idx_flt32);
+ const uchar* const oBGImgPtr = m_voBGColorSamples[s].data + idx_nimg;
+ for (size_t c = 0; c < m_nImgChannels; ++c)
+ oAvgBgImgPtr[c] += ((float)oBGImgPtr[c]) / m_nBGSamples;
+ }
+ }
+ }
+ oAvgBGImg.convertTo(backgroundImage, CV_8U);
+}
+
+void BackgroundSubtractorLOBSTER::getBackgroundDescriptorsImage(cv::OutputArray backgroundDescImage) const {
+ CV_Assert(LBSP::DESC_SIZE == 2);
+ CV_Assert(m_bInitialized);
+ cv::Mat oAvgBGDesc = cv::Mat::zeros(m_oImgSize, CV_32FC((int)m_nImgChannels));
+ for (size_t n = 0; n < m_voBGDescSamples.size(); ++n) {
+ for (int y = 0; y < m_oImgSize.height; ++y) {
+ for (int x = 0; x < m_oImgSize.width; ++x) {
+ const size_t idx_ndesc = m_voBGDescSamples[n].step.p[0] * y + m_voBGDescSamples[n].step.p[1] * x;
+ const size_t idx_flt32 = idx_ndesc * 2;
+ float* oAvgBgDescPtr = (float*)(oAvgBGDesc.data + idx_flt32);
+ const ushort* const oBGDescPtr = (ushort*)(m_voBGDescSamples[n].data + idx_ndesc);
+ for (size_t c = 0; c < m_nImgChannels; ++c)
+ oAvgBgDescPtr[c] += ((float)oBGDescPtr[c]) / m_voBGDescSamples.size();
+ }
+ }
+ }
+ oAvgBGDesc.convertTo(backgroundDescImage, CV_16U);
+}
diff --git a/package_bgs/LBSP/BackgroundSubtractorLOBSTER.h b/package_bgs/LBSP/BackgroundSubtractorLOBSTER.h
new file mode 100644
index 0000000..d69fd1c
--- /dev/null
+++ b/package_bgs/LBSP/BackgroundSubtractorLOBSTER.h
@@ -0,0 +1,83 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+#pragma once
+
+#include "BackgroundSubtractorLBSP.h"
+
+//! defines the default value for BackgroundSubtractorLBSP::m_fRelLBSPThreshold
+#define BGSLOBSTER_DEFAULT_LBSP_REL_SIMILARITY_THRESHOLD (0.365f)
+//! defines the default value for BackgroundSubtractorLBSP::m_nLBSPThresholdOffset
+#define BGSLOBSTER_DEFAULT_LBSP_OFFSET_SIMILARITY_THRESHOLD (0)
+//! defines the default value for BackgroundSubtractorLOBSTER::m_nDescDistThreshold
+#define BGSLOBSTER_DEFAULT_DESC_DIST_THRESHOLD (4)
+//! defines the default value for BackgroundSubtractorLOBSTER::m_nColorDistThreshold
+#define BGSLOBSTER_DEFAULT_COLOR_DIST_THRESHOLD (30)
+//! defines the default value for BackgroundSubtractorLOBSTER::m_nBGSamples
+#define BGSLOBSTER_DEFAULT_NB_BG_SAMPLES (35)
+//! defines the default value for BackgroundSubtractorLOBSTER::m_nRequiredBGSamples
+#define BGSLOBSTER_DEFAULT_REQUIRED_NB_BG_SAMPLES (2)
+//! defines the default value for the learning rate passed to BackgroundSubtractorLOBSTER::operator()
+#define BGSLOBSTER_DEFAULT_LEARNING_RATE (16)
+
+/*!
+ LOcal Binary Similarity segmenTER (LOBSTER) change detection algorithm.
+
+ Note: both grayscale and RGB/BGR images may be used with this extractor (parameters are adjusted automatically).
+ For optimal grayscale results, use CV_8UC1 frames instead of CV_8UC3.
+
+ For more details on the different parameters or on the algorithm itself, see P.-L. St-Charles and
+ G.-A. Bilodeau, "Improving Background Subtraction using Local Binary Similarity Patterns", in WACV 2014.
+
+ This algorithm is currently NOT thread-safe.
+ */
+class BackgroundSubtractorLOBSTER : public BackgroundSubtractorLBSP {
+public:
+ //! full constructor
+ BackgroundSubtractorLOBSTER(float fRelLBSPThreshold = BGSLOBSTER_DEFAULT_LBSP_REL_SIMILARITY_THRESHOLD,
+ size_t nLBSPThresholdOffset = BGSLOBSTER_DEFAULT_LBSP_OFFSET_SIMILARITY_THRESHOLD,
+ size_t nDescDistThreshold = BGSLOBSTER_DEFAULT_DESC_DIST_THRESHOLD,
+ size_t nColorDistThreshold = BGSLOBSTER_DEFAULT_COLOR_DIST_THRESHOLD,
+ size_t nBGSamples = BGSLOBSTER_DEFAULT_NB_BG_SAMPLES,
+ size_t nRequiredBGSamples = BGSLOBSTER_DEFAULT_REQUIRED_NB_BG_SAMPLES);
+ //! default destructor
+ virtual ~BackgroundSubtractorLOBSTER();
+ //! (re)initiaization method; needs to be called before starting background subtraction
+ virtual void initialize(const cv::Mat& oInitImg, const cv::Mat& oROI);
+ //! refreshes all samples based on the last analyzed frame
+ virtual void refreshModel(float fSamplesRefreshFrac, bool bForceFGUpdate = false);
+ //! primary model update function; the learning param is reinterpreted as an integer and should be > 0 (smaller values == faster adaptation)
+ virtual void apply(cv::InputArray image, cv::OutputArray fgmask, double learningRateOverride = BGSLOBSTER_DEFAULT_LEARNING_RATE);
+ //! returns a copy of the latest reconstructed background image
+ void getBackgroundImage(cv::OutputArray backgroundImage) const;
+ //! returns a copy of the latest reconstructed background descriptors image
+ virtual void getBackgroundDescriptorsImage(cv::OutputArray backgroundDescImage) const;
+
+protected:
+ //! absolute color distance threshold
+ const size_t m_nColorDistThreshold;
+ //! absolute descriptor distance threshold
+ const size_t m_nDescDistThreshold;
+ //! number of different samples per pixel/block to be taken from input frames to build the background model
+ const size_t m_nBGSamples;
+ //! number of similar samples needed to consider the current pixel/block as 'background'
+ const size_t m_nRequiredBGSamples;
+ //! background model pixel intensity samples
+ std::vector m_voBGColorSamples;
+ //! background model descriptors samples
+ std::vector m_voBGDescSamples;
+};
+
diff --git a/package_bgs/LBSP/BackgroundSubtractorPAWCS.cpp b/package_bgs/LBSP/BackgroundSubtractorPAWCS.cpp
new file mode 100644
index 0000000..6c48df3
--- /dev/null
+++ b/package_bgs/LBSP/BackgroundSubtractorPAWCS.cpp
@@ -0,0 +1,1349 @@
+/*
+This file is part of BGSLibrary.
+
+BGSLibrary is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+BGSLibrary is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with BGSLibrary. If not, see .
+*/
+#include "BackgroundSubtractorPAWCS.h"
+#include "DistanceUtils.h"
+#include "RandUtils.h"
+#include
+#include
+#include
+#include
+
+/*
+ *
+ * Intrinsic configuration parameters are defined here; tuning these for better
+ * performance should not be required in most cases -- although improvements in
+ * very specific scenarios are always possible.
+ *
+ */
+ //! parameter used for dynamic distance threshold adjustments ('R(x)')
+#define FEEDBACK_R_VAR (0.01f)
+//! parameters used to adjust the variation step size of 'v(x)'
+#define FEEDBACK_V_INCR (1.000f)
+#define FEEDBACK_V_DECR (0.100f)
+//! parameters used to scale dynamic learning rate adjustments ('T(x)')
+#define FEEDBACK_T_DECR (0.2500f)
+#define FEEDBACK_T_INCR (0.5000f)
+#define FEEDBACK_T_LOWER (1.0000f)
+#define FEEDBACK_T_UPPER (256.00f)
+//! parameters used to define 'unstable' regions, based on segm noise/bg dynamics and local dist threshold values
+#define UNSTABLE_REG_RATIO_MIN (0.100f)
+#define UNSTABLE_REG_RDIST_MIN (3.000f)
+//! parameters used to scale the relative LBSP intensity threshold used for internal comparisons
+#define LBSPDESC_RATIO_MIN (0.100f)
+#define LBSPDESC_RATIO_MAX (0.500f)
+//! parameters used to trigger auto model resets in our frame-level component
+#define FRAMELEVEL_MIN_L1DIST_THRES (45)
+#define FRAMELEVEL_MIN_CDIST_THRES (FRAMELEVEL_MIN_L1DIST_THRES/10)
+#define FRAMELEVEL_DOWNSAMPLE_RATIO (8)
+//! parameters used to downscale gword maps & scale thresholds to make comparisons easier
+#define GWORD_LOOKUP_MAPS_DOWNSAMPLE_RATIO (2)
+#define GWORD_DEFAULT_NB_INIT_SAMPL_PASSES (2)
+#define GWORD_DESC_THRES_BITS_MATCH_FACTOR (4)
+
+// local define used to specify the default frame size (320x240 = QVGA)
+#define DEFAULT_FRAME_SIZE cv::Size(320,240)
+// local define used to specify the default lword/gword update rate (16 = like vibe)
+#define DEFAULT_RESAMPLING_RATE (16)
+// local define used to specify the bootstrap window size for faster model stabilization
+#define DEFAULT_BOOTSTRAP_WIN_SIZE (500)
+// local define for the amount of weight offset to apply to words, making sure new words aren't always better than old ones
+#define DEFAULT_LWORD_WEIGHT_OFFSET (DEFAULT_BOOTSTRAP_WIN_SIZE*2)
+// local define used to set the default local word occurrence increment
+#define DEFAULT_LWORD_OCC_INCR 1
+// local define for the maximum weight a word can achieve before cutting off occ incr (used to make sure model stays good for long-term uses)
+#define DEFAULT_LWORD_MAX_WEIGHT (1.0f)
+// local define for the initial weight of a new word (used to make sure old words aren't worse off than new seeds)
+#define DEFAULT_LWORD_INIT_WEIGHT (1.0f/m_nLocalWordWeightOffset)
+// local define used to specify the desc dist threshold offset used for unstable regions
+#define UNSTAB_DESC_DIST_OFFSET (m_nDescDistThresholdOffset)
+// local define used to specify the min descriptor bit count for flat regions
+#define FLAT_REGION_BIT_COUNT (s_nDescMaxDataRange_1ch/8)
+
+static const size_t s_nColorMaxDataRange_1ch = UCHAR_MAX;
+static const size_t s_nDescMaxDataRange_1ch = LBSP_::DESC_SIZE * 8;
+static const size_t s_nColorMaxDataRange_3ch = s_nColorMaxDataRange_1ch * 3;
+static const size_t s_nDescMaxDataRange_3ch = s_nDescMaxDataRange_1ch * 3;
+
+BackgroundSubtractorPAWCS::BackgroundSubtractorPAWCS(float fRelLBSPThreshold
+ , size_t nDescDistThresholdOffset
+ , size_t nMinColorDistThreshold
+ , size_t nMaxNbWords
+ , size_t nSamplesForMovingAvgs)
+ : BackgroundSubtractorLBSP_(fRelLBSPThreshold)
+ , m_nMinColorDistThreshold(nMinColorDistThreshold)
+ , m_nDescDistThresholdOffset(nDescDistThresholdOffset)
+ , m_nMaxLocalWords(nMaxNbWords)
+ , m_nCurrLocalWords(0)
+ , m_nMaxGlobalWords(nMaxNbWords / 2)
+ , m_nCurrGlobalWords(0)
+ , m_nSamplesForMovingAvgs(nSamplesForMovingAvgs)
+ , m_fLastNonFlatRegionRatio(0.0f)
+ , m_nMedianBlurKernelSize(m_nDefaultMedianBlurKernelSize)
+ , m_nDownSampledROIPxCount(0)
+ , m_nLocalWordWeightOffset(DEFAULT_LWORD_WEIGHT_OFFSET)
+ , m_apLocalWordDict(nullptr)
+ , m_aLocalWordList_1ch(nullptr)
+ , m_pLocalWordListIter_1ch(nullptr)
+ , m_aLocalWordList_3ch(nullptr)
+ , m_pLocalWordListIter_3ch(nullptr)
+ , m_apGlobalWordDict(nullptr)
+ , m_aGlobalWordList_1ch(nullptr)
+ , m_pGlobalWordListIter_1ch(nullptr)
+ , m_aGlobalWordList_3ch(nullptr)
+ , m_pGlobalWordListIter_3ch(nullptr)
+ , m_aPxInfoLUT_PAWCS(nullptr) {
+ CV_Assert(m_nMaxLocalWords > 0 && m_nMaxGlobalWords > 0);
+}
+
+BackgroundSubtractorPAWCS::~BackgroundSubtractorPAWCS() {
+ CleanupDictionaries();
+}
+
+void BackgroundSubtractorPAWCS::initialize(const cv::Mat& oInitImg, const cv::Mat& oROI) {
+ // == init
+ CV_Assert(!oInitImg.empty() && oInitImg.cols > 0 && oInitImg.rows > 0);
+ CV_Assert(oInitImg.isContinuous());
+ CV_Assert(oInitImg.type() == CV_8UC3 || oInitImg.type() == CV_8UC1);
+ if (oInitImg.type() == CV_8UC3) {
+ std::vector