完善目录结构
完善了目录结构,添加了以前的web段com组件调用的代码(在/测试目录下)(部署没有使用到)
This commit is contained in:
@@ -0,0 +1,2 @@
|
||||
SUBDIRS = src include
|
||||
|
||||
538
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/Makefile.in
Normal file
538
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/Makefile.in
Normal file
@@ -0,0 +1,538 @@
|
||||
# Makefile.in generated by automake 1.9.6 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
# 2003, 2004, 2005 Free Software Foundation, Inc.
|
||||
# This Makefile.in is free software; the Free Software Foundation
|
||||
# gives unlimited permission to copy and/or distribute it,
|
||||
# with or without modifications, as long as this notice is preserved.
|
||||
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY, to the extent permitted by law; without
|
||||
# even the implied warranty of MERCHANTABILITY or FITNESS FOR A
|
||||
# PARTICULAR PURPOSE.
|
||||
|
||||
@SET_MAKE@
|
||||
srcdir = @srcdir@
|
||||
top_srcdir = @top_srcdir@
|
||||
VPATH = @srcdir@
|
||||
pkgdatadir = $(datadir)/@PACKAGE@
|
||||
pkglibdir = $(libdir)/@PACKAGE@
|
||||
pkgincludedir = $(includedir)/@PACKAGE@
|
||||
top_builddir = ..
|
||||
am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd
|
||||
INSTALL = @INSTALL@
|
||||
install_sh_DATA = $(install_sh) -c -m 644
|
||||
install_sh_PROGRAM = $(install_sh) -c
|
||||
install_sh_SCRIPT = $(install_sh) -c
|
||||
INSTALL_HEADER = $(INSTALL_DATA)
|
||||
transform = $(program_transform_name)
|
||||
NORMAL_INSTALL = :
|
||||
PRE_INSTALL = :
|
||||
POST_INSTALL = :
|
||||
NORMAL_UNINSTALL = :
|
||||
PRE_UNINSTALL = :
|
||||
POST_UNINSTALL = :
|
||||
build_triplet = @build@
|
||||
host_triplet = @host@
|
||||
target_triplet = @target@
|
||||
subdir = cvaux
|
||||
DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in
|
||||
ACLOCAL_M4 = $(top_srcdir)/aclocal.m4
|
||||
am__aclocal_m4_deps = $(top_srcdir)/autotools/aclocal/az_python.m4 \
|
||||
$(top_srcdir)/autotools/aclocal/pkg.m4 \
|
||||
$(top_srcdir)/autotools/aclocal/swig_complete.m4 \
|
||||
$(top_srcdir)/autotools/aclocal/version_at_least.m4 \
|
||||
$(top_srcdir)/configure.in
|
||||
am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \
|
||||
$(ACLOCAL_M4)
|
||||
mkinstalldirs = $(SHELL) $(top_srcdir)/autotools/mkinstalldirs
|
||||
CONFIG_HEADER = $(top_builddir)/cvconfig.h
|
||||
CONFIG_CLEAN_FILES =
|
||||
SOURCES =
|
||||
DIST_SOURCES =
|
||||
RECURSIVE_TARGETS = all-recursive check-recursive dvi-recursive \
|
||||
html-recursive info-recursive install-data-recursive \
|
||||
install-exec-recursive install-info-recursive \
|
||||
install-recursive installcheck-recursive installdirs-recursive \
|
||||
pdf-recursive ps-recursive uninstall-info-recursive \
|
||||
uninstall-recursive
|
||||
ETAGS = etags
|
||||
CTAGS = ctags
|
||||
DIST_SUBDIRS = $(SUBDIRS)
|
||||
DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST)
|
||||
ACLOCAL = @ACLOCAL@
|
||||
ALLOCA = @ALLOCA@
|
||||
AMDEP_FALSE = @AMDEP_FALSE@
|
||||
AMDEP_TRUE = @AMDEP_TRUE@
|
||||
AMTAR = @AMTAR@
|
||||
AR = @AR@
|
||||
AS = @AS@
|
||||
AUTOCONF = @AUTOCONF@
|
||||
AUTOHEADER = @AUTOHEADER@
|
||||
AUTOMAKE = @AUTOMAKE@
|
||||
AWK = @AWK@
|
||||
BUILD_APPS_FALSE = @BUILD_APPS_FALSE@
|
||||
BUILD_APPS_TRUE = @BUILD_APPS_TRUE@
|
||||
BUILD_CARBON_FALSE = @BUILD_CARBON_FALSE@
|
||||
BUILD_CARBON_TRUE = @BUILD_CARBON_TRUE@
|
||||
BUILD_DC1394_FALSE = @BUILD_DC1394_FALSE@
|
||||
BUILD_DC1394_TRUE = @BUILD_DC1394_TRUE@
|
||||
BUILD_FFMPEG_FALSE = @BUILD_FFMPEG_FALSE@
|
||||
BUILD_FFMPEG_TRUE = @BUILD_FFMPEG_TRUE@
|
||||
BUILD_GTK_FALSE = @BUILD_GTK_FALSE@
|
||||
BUILD_GTK_TRUE = @BUILD_GTK_TRUE@
|
||||
BUILD_PYTHON_WRAPPERS_FALSE = @BUILD_PYTHON_WRAPPERS_FALSE@
|
||||
BUILD_PYTHON_WRAPPERS_TRUE = @BUILD_PYTHON_WRAPPERS_TRUE@
|
||||
BUILD_QUICKTIME_FALSE = @BUILD_QUICKTIME_FALSE@
|
||||
BUILD_QUICKTIME_TRUE = @BUILD_QUICKTIME_TRUE@
|
||||
BUILD_V4L_FALSE = @BUILD_V4L_FALSE@
|
||||
BUILD_V4L_TRUE = @BUILD_V4L_TRUE@
|
||||
BUILD_XINE_FALSE = @BUILD_XINE_FALSE@
|
||||
BUILD_XINE_TRUE = @BUILD_XINE_TRUE@
|
||||
CARBON_CFLAGS = @CARBON_CFLAGS@
|
||||
CARBON_LIBS = @CARBON_LIBS@
|
||||
CC = @CC@
|
||||
CCDEPMODE = @CCDEPMODE@
|
||||
CFLAGS = @CFLAGS@
|
||||
CPP = @CPP@
|
||||
CPPFLAGS = @CPPFLAGS@
|
||||
CXX = @CXX@
|
||||
CXXCPP = @CXXCPP@
|
||||
CXXDEPMODE = @CXXDEPMODE@
|
||||
CXXFLAGS = @CXXFLAGS@
|
||||
CYGPATH_W = @CYGPATH_W@
|
||||
DEBUG = @DEBUG@
|
||||
DEFS = @DEFS@
|
||||
DEPDIR = @DEPDIR@
|
||||
DLLTOOL = @DLLTOOL@
|
||||
ECHO = @ECHO@
|
||||
ECHO_C = @ECHO_C@
|
||||
ECHO_N = @ECHO_N@
|
||||
ECHO_T = @ECHO_T@
|
||||
EGREP = @EGREP@
|
||||
EXEEXT = @EXEEXT@
|
||||
F77 = @F77@
|
||||
FFLAGS = @FFLAGS@
|
||||
FFMPEGLIBS = @FFMPEGLIBS@
|
||||
GREP = @GREP@
|
||||
GTHREAD_CFLAGS = @GTHREAD_CFLAGS@
|
||||
GTHREAD_LIBS = @GTHREAD_LIBS@
|
||||
GTK_CFLAGS = @GTK_CFLAGS@
|
||||
GTK_LIBS = @GTK_LIBS@
|
||||
IEEE1394LIBS = @IEEE1394LIBS@
|
||||
IMAGELIBS = @IMAGELIBS@
|
||||
INSTALL_DATA = @INSTALL_DATA@
|
||||
INSTALL_PROGRAM = @INSTALL_PROGRAM@
|
||||
INSTALL_SCRIPT = @INSTALL_SCRIPT@
|
||||
INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@
|
||||
LDFLAGS = @LDFLAGS@
|
||||
LIBOBJS = @LIBOBJS@
|
||||
LIBS = @LIBS@
|
||||
LIBTOOL = @LIBTOOL@
|
||||
LN_S = @LN_S@
|
||||
LTLIBOBJS = @LTLIBOBJS@
|
||||
LT_VERSION = @LT_VERSION@
|
||||
MAKEINFO = @MAKEINFO@
|
||||
MMAJOR = @MMAJOR@
|
||||
MMINOR = @MMINOR@
|
||||
MSUBMINOR = @MSUBMINOR@
|
||||
OBJDUMP = @OBJDUMP@
|
||||
OBJEXT = @OBJEXT@
|
||||
PACKAGE = @PACKAGE@
|
||||
PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@
|
||||
PACKAGE_NAME = @PACKAGE_NAME@
|
||||
PACKAGE_STRING = @PACKAGE_STRING@
|
||||
PACKAGE_TARNAME = @PACKAGE_TARNAME@
|
||||
PACKAGE_VERSION = @PACKAGE_VERSION@
|
||||
PATH_SEPARATOR = @PATH_SEPARATOR@
|
||||
PKG_CONFIG = @PKG_CONFIG@
|
||||
PYTHON = @PYTHON@
|
||||
PYTHON_CSPEC = @PYTHON_CSPEC@
|
||||
PYTHON_EXEC_PREFIX = @PYTHON_EXEC_PREFIX@
|
||||
PYTHON_LSPEC = @PYTHON_LSPEC@
|
||||
PYTHON_PLATFORM = @PYTHON_PLATFORM@
|
||||
PYTHON_PREFIX = @PYTHON_PREFIX@
|
||||
PYTHON_VERSION = @PYTHON_VERSION@
|
||||
QUICKTIME_CFLAGS = @QUICKTIME_CFLAGS@
|
||||
QUICKTIME_LIBS = @QUICKTIME_LIBS@
|
||||
RANLIB = @RANLIB@
|
||||
SET_MAKE = @SET_MAKE@
|
||||
SHELL = @SHELL@
|
||||
STRIP = @STRIP@
|
||||
SWIG = @SWIG@
|
||||
SWIG_PYTHON_LIBS = @SWIG_PYTHON_LIBS@
|
||||
SWIG_PYTHON_OPT = @SWIG_PYTHON_OPT@
|
||||
SWIG_RUNTIME_LIBS_DIR = @SWIG_RUNTIME_LIBS_DIR@
|
||||
SWIG_VERSION = @SWIG_VERSION@
|
||||
UPDATE_SWIG_WRAPPERS_FALSE = @UPDATE_SWIG_WRAPPERS_FALSE@
|
||||
UPDATE_SWIG_WRAPPERS_TRUE = @UPDATE_SWIG_WRAPPERS_TRUE@
|
||||
VERSION = @VERSION@
|
||||
XINE_LIBS = @XINE_LIBS@
|
||||
ac_ct_CC = @ac_ct_CC@
|
||||
ac_ct_CXX = @ac_ct_CXX@
|
||||
ac_ct_F77 = @ac_ct_F77@
|
||||
am__fastdepCC_FALSE = @am__fastdepCC_FALSE@
|
||||
am__fastdepCC_TRUE = @am__fastdepCC_TRUE@
|
||||
am__fastdepCXX_FALSE = @am__fastdepCXX_FALSE@
|
||||
am__fastdepCXX_TRUE = @am__fastdepCXX_TRUE@
|
||||
am__include = @am__include@
|
||||
am__leading_dot = @am__leading_dot@
|
||||
am__quote = @am__quote@
|
||||
am__tar = @am__tar@
|
||||
am__untar = @am__untar@
|
||||
bindir = @bindir@
|
||||
build = @build@
|
||||
build_alias = @build_alias@
|
||||
build_cpu = @build_cpu@
|
||||
build_os = @build_os@
|
||||
build_vendor = @build_vendor@
|
||||
datadir = @datadir@
|
||||
datarootdir = @datarootdir@
|
||||
docdir = @docdir@
|
||||
dvidir = @dvidir@
|
||||
exec_prefix = @exec_prefix@
|
||||
host = @host@
|
||||
host_alias = @host_alias@
|
||||
host_cpu = @host_cpu@
|
||||
host_os = @host_os@
|
||||
host_vendor = @host_vendor@
|
||||
htmldir = @htmldir@
|
||||
includedir = @includedir@
|
||||
infodir = @infodir@
|
||||
install_sh = @install_sh@
|
||||
libdir = @libdir@
|
||||
libexecdir = @libexecdir@
|
||||
localedir = @localedir@
|
||||
localstatedir = @localstatedir@
|
||||
mandir = @mandir@
|
||||
mkdir_p = @mkdir_p@
|
||||
oldincludedir = @oldincludedir@
|
||||
pdfdir = @pdfdir@
|
||||
pkgpyexecdir = @pkgpyexecdir@
|
||||
pkgpythondir = @pkgpythondir@
|
||||
prefix = @prefix@
|
||||
program_transform_name = @program_transform_name@
|
||||
psdir = @psdir@
|
||||
pyexecdir = @pyexecdir@
|
||||
pythondir = @pythondir@
|
||||
sbindir = @sbindir@
|
||||
sharedstatedir = @sharedstatedir@
|
||||
sysconfdir = @sysconfdir@
|
||||
target = @target@
|
||||
target_alias = @target_alias@
|
||||
target_cpu = @target_cpu@
|
||||
target_os = @target_os@
|
||||
target_vendor = @target_vendor@
|
||||
SUBDIRS = src include
|
||||
all: all-recursive
|
||||
|
||||
.SUFFIXES:
|
||||
$(srcdir)/Makefile.in: $(srcdir)/Makefile.am $(am__configure_deps)
|
||||
@for dep in $?; do \
|
||||
case '$(am__configure_deps)' in \
|
||||
*$$dep*) \
|
||||
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh \
|
||||
&& exit 0; \
|
||||
exit 1;; \
|
||||
esac; \
|
||||
done; \
|
||||
echo ' cd $(top_srcdir) && $(AUTOMAKE) --gnu cvaux/Makefile'; \
|
||||
cd $(top_srcdir) && \
|
||||
$(AUTOMAKE) --gnu cvaux/Makefile
|
||||
.PRECIOUS: Makefile
|
||||
Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status
|
||||
@case '$?' in \
|
||||
*config.status*) \
|
||||
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh;; \
|
||||
*) \
|
||||
echo ' cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe)'; \
|
||||
cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe);; \
|
||||
esac;
|
||||
|
||||
$(top_builddir)/config.status: $(top_srcdir)/configure $(CONFIG_STATUS_DEPENDENCIES)
|
||||
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh
|
||||
|
||||
$(top_srcdir)/configure: $(am__configure_deps)
|
||||
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh
|
||||
$(ACLOCAL_M4): $(am__aclocal_m4_deps)
|
||||
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh
|
||||
|
||||
mostlyclean-libtool:
|
||||
-rm -f *.lo
|
||||
|
||||
clean-libtool:
|
||||
-rm -rf .libs _libs
|
||||
|
||||
distclean-libtool:
|
||||
-rm -f libtool
|
||||
uninstall-info-am:
|
||||
|
||||
# This directory's subdirectories are mostly independent; you can cd
|
||||
# into them and run `make' without going through this Makefile.
|
||||
# To change the values of `make' variables: instead of editing Makefiles,
|
||||
# (1) if the variable is set in `config.status', edit `config.status'
|
||||
# (which will cause the Makefiles to be regenerated when you run `make');
|
||||
# (2) otherwise, pass the desired values on the `make' command line.
|
||||
$(RECURSIVE_TARGETS):
|
||||
@failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
*k*) failcom='fail=yes';; \
|
||||
esac; \
|
||||
done; \
|
||||
dot_seen=no; \
|
||||
target=`echo $@ | sed s/-recursive//`; \
|
||||
list='$(SUBDIRS)'; for subdir in $$list; do \
|
||||
echo "Making $$target in $$subdir"; \
|
||||
if test "$$subdir" = "."; then \
|
||||
dot_seen=yes; \
|
||||
local_target="$$target-am"; \
|
||||
else \
|
||||
local_target="$$target"; \
|
||||
fi; \
|
||||
(cd $$subdir && $(MAKE) $(AM_MAKEFLAGS) $$local_target) \
|
||||
|| eval $$failcom; \
|
||||
done; \
|
||||
if test "$$dot_seen" = "no"; then \
|
||||
$(MAKE) $(AM_MAKEFLAGS) "$$target-am" || exit 1; \
|
||||
fi; test -z "$$fail"
|
||||
|
||||
mostlyclean-recursive clean-recursive distclean-recursive \
|
||||
maintainer-clean-recursive:
|
||||
@failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
*k*) failcom='fail=yes';; \
|
||||
esac; \
|
||||
done; \
|
||||
dot_seen=no; \
|
||||
case "$@" in \
|
||||
distclean-* | maintainer-clean-*) list='$(DIST_SUBDIRS)' ;; \
|
||||
*) list='$(SUBDIRS)' ;; \
|
||||
esac; \
|
||||
rev=''; for subdir in $$list; do \
|
||||
if test "$$subdir" = "."; then :; else \
|
||||
rev="$$subdir $$rev"; \
|
||||
fi; \
|
||||
done; \
|
||||
rev="$$rev ."; \
|
||||
target=`echo $@ | sed s/-recursive//`; \
|
||||
for subdir in $$rev; do \
|
||||
echo "Making $$target in $$subdir"; \
|
||||
if test "$$subdir" = "."; then \
|
||||
local_target="$$target-am"; \
|
||||
else \
|
||||
local_target="$$target"; \
|
||||
fi; \
|
||||
(cd $$subdir && $(MAKE) $(AM_MAKEFLAGS) $$local_target) \
|
||||
|| eval $$failcom; \
|
||||
done && test -z "$$fail"
|
||||
tags-recursive:
|
||||
list='$(SUBDIRS)'; for subdir in $$list; do \
|
||||
test "$$subdir" = . || (cd $$subdir && $(MAKE) $(AM_MAKEFLAGS) tags); \
|
||||
done
|
||||
ctags-recursive:
|
||||
list='$(SUBDIRS)'; for subdir in $$list; do \
|
||||
test "$$subdir" = . || (cd $$subdir && $(MAKE) $(AM_MAKEFLAGS) ctags); \
|
||||
done
|
||||
|
||||
ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES)
|
||||
list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \
|
||||
unique=`for i in $$list; do \
|
||||
if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
|
||||
done | \
|
||||
$(AWK) ' { files[$$0] = 1; } \
|
||||
END { for (i in files) print i; }'`; \
|
||||
mkid -fID $$unique
|
||||
tags: TAGS
|
||||
|
||||
TAGS: tags-recursive $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \
|
||||
$(TAGS_FILES) $(LISP)
|
||||
tags=; \
|
||||
here=`pwd`; \
|
||||
if ($(ETAGS) --etags-include --version) >/dev/null 2>&1; then \
|
||||
include_option=--etags-include; \
|
||||
empty_fix=.; \
|
||||
else \
|
||||
include_option=--include; \
|
||||
empty_fix=; \
|
||||
fi; \
|
||||
list='$(SUBDIRS)'; for subdir in $$list; do \
|
||||
if test "$$subdir" = .; then :; else \
|
||||
test ! -f $$subdir/TAGS || \
|
||||
tags="$$tags $$include_option=$$here/$$subdir/TAGS"; \
|
||||
fi; \
|
||||
done; \
|
||||
list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \
|
||||
unique=`for i in $$list; do \
|
||||
if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
|
||||
done | \
|
||||
$(AWK) ' { files[$$0] = 1; } \
|
||||
END { for (i in files) print i; }'`; \
|
||||
if test -z "$(ETAGS_ARGS)$$tags$$unique"; then :; else \
|
||||
test -n "$$unique" || unique=$$empty_fix; \
|
||||
$(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \
|
||||
$$tags $$unique; \
|
||||
fi
|
||||
ctags: CTAGS
|
||||
CTAGS: ctags-recursive $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \
|
||||
$(TAGS_FILES) $(LISP)
|
||||
tags=; \
|
||||
here=`pwd`; \
|
||||
list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \
|
||||
unique=`for i in $$list; do \
|
||||
if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
|
||||
done | \
|
||||
$(AWK) ' { files[$$0] = 1; } \
|
||||
END { for (i in files) print i; }'`; \
|
||||
test -z "$(CTAGS_ARGS)$$tags$$unique" \
|
||||
|| $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \
|
||||
$$tags $$unique
|
||||
|
||||
GTAGS:
|
||||
here=`$(am__cd) $(top_builddir) && pwd` \
|
||||
&& cd $(top_srcdir) \
|
||||
&& gtags -i $(GTAGS_ARGS) $$here
|
||||
|
||||
distclean-tags:
|
||||
-rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags
|
||||
|
||||
distdir: $(DISTFILES)
|
||||
@srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; \
|
||||
topsrcdirstrip=`echo "$(top_srcdir)" | sed 's|.|.|g'`; \
|
||||
list='$(DISTFILES)'; for file in $$list; do \
|
||||
case $$file in \
|
||||
$(srcdir)/*) file=`echo "$$file" | sed "s|^$$srcdirstrip/||"`;; \
|
||||
$(top_srcdir)/*) file=`echo "$$file" | sed "s|^$$topsrcdirstrip/|$(top_builddir)/|"`;; \
|
||||
esac; \
|
||||
if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \
|
||||
dir=`echo "$$file" | sed -e 's,/[^/]*$$,,'`; \
|
||||
if test "$$dir" != "$$file" && test "$$dir" != "."; then \
|
||||
dir="/$$dir"; \
|
||||
$(mkdir_p) "$(distdir)$$dir"; \
|
||||
else \
|
||||
dir=''; \
|
||||
fi; \
|
||||
if test -d $$d/$$file; then \
|
||||
if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \
|
||||
cp -pR $(srcdir)/$$file $(distdir)$$dir || exit 1; \
|
||||
fi; \
|
||||
cp -pR $$d/$$file $(distdir)$$dir || exit 1; \
|
||||
else \
|
||||
test -f $(distdir)/$$file \
|
||||
|| cp -p $$d/$$file $(distdir)/$$file \
|
||||
|| exit 1; \
|
||||
fi; \
|
||||
done
|
||||
list='$(DIST_SUBDIRS)'; for subdir in $$list; do \
|
||||
if test "$$subdir" = .; then :; else \
|
||||
test -d "$(distdir)/$$subdir" \
|
||||
|| $(mkdir_p) "$(distdir)/$$subdir" \
|
||||
|| exit 1; \
|
||||
distdir=`$(am__cd) $(distdir) && pwd`; \
|
||||
top_distdir=`$(am__cd) $(top_distdir) && pwd`; \
|
||||
(cd $$subdir && \
|
||||
$(MAKE) $(AM_MAKEFLAGS) \
|
||||
top_distdir="$$top_distdir" \
|
||||
distdir="$$distdir/$$subdir" \
|
||||
distdir) \
|
||||
|| exit 1; \
|
||||
fi; \
|
||||
done
|
||||
check-am: all-am
|
||||
check: check-recursive
|
||||
all-am: Makefile
|
||||
installdirs: installdirs-recursive
|
||||
installdirs-am:
|
||||
install: install-recursive
|
||||
install-exec: install-exec-recursive
|
||||
install-data: install-data-recursive
|
||||
uninstall: uninstall-recursive
|
||||
|
||||
install-am: all-am
|
||||
@$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am
|
||||
|
||||
installcheck: installcheck-recursive
|
||||
install-strip:
|
||||
$(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \
|
||||
install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \
|
||||
`test -z '$(STRIP)' || \
|
||||
echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install
|
||||
mostlyclean-generic:
|
||||
|
||||
clean-generic:
|
||||
|
||||
distclean-generic:
|
||||
-test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES)
|
||||
|
||||
maintainer-clean-generic:
|
||||
@echo "This command is intended for maintainers to use"
|
||||
@echo "it deletes files that may require special tools to rebuild."
|
||||
clean: clean-recursive
|
||||
|
||||
clean-am: clean-generic clean-libtool mostlyclean-am
|
||||
|
||||
distclean: distclean-recursive
|
||||
-rm -f Makefile
|
||||
distclean-am: clean-am distclean-generic distclean-libtool \
|
||||
distclean-tags
|
||||
|
||||
dvi: dvi-recursive
|
||||
|
||||
dvi-am:
|
||||
|
||||
html: html-recursive
|
||||
|
||||
info: info-recursive
|
||||
|
||||
info-am:
|
||||
|
||||
install-data-am:
|
||||
|
||||
install-exec-am:
|
||||
|
||||
install-info: install-info-recursive
|
||||
|
||||
install-man:
|
||||
|
||||
installcheck-am:
|
||||
|
||||
maintainer-clean: maintainer-clean-recursive
|
||||
-rm -f Makefile
|
||||
maintainer-clean-am: distclean-am maintainer-clean-generic
|
||||
|
||||
mostlyclean: mostlyclean-recursive
|
||||
|
||||
mostlyclean-am: mostlyclean-generic mostlyclean-libtool
|
||||
|
||||
pdf: pdf-recursive
|
||||
|
||||
pdf-am:
|
||||
|
||||
ps: ps-recursive
|
||||
|
||||
ps-am:
|
||||
|
||||
uninstall-am: uninstall-info-am
|
||||
|
||||
uninstall-info: uninstall-info-recursive
|
||||
|
||||
.PHONY: $(RECURSIVE_TARGETS) CTAGS GTAGS all all-am check check-am \
|
||||
clean clean-generic clean-libtool clean-recursive ctags \
|
||||
ctags-recursive distclean distclean-generic distclean-libtool \
|
||||
distclean-recursive distclean-tags distdir dvi dvi-am html \
|
||||
html-am info info-am install install-am install-data \
|
||||
install-data-am install-exec install-exec-am install-info \
|
||||
install-info-am install-man install-strip installcheck \
|
||||
installcheck-am installdirs installdirs-am maintainer-clean \
|
||||
maintainer-clean-generic maintainer-clean-recursive \
|
||||
mostlyclean mostlyclean-generic mostlyclean-libtool \
|
||||
mostlyclean-recursive pdf pdf-am ps ps-am tags tags-recursive \
|
||||
uninstall uninstall-am uninstall-info-am
|
||||
|
||||
# Tell versions [3.59,3.63) of GNU make to not export all variables.
|
||||
# Otherwise a system limit (for SysV at least) may be exceeded.
|
||||
.NOEXPORT:
|
||||
@@ -0,0 +1,5 @@
|
||||
# The directory where the include files will be installed
|
||||
libcvauxincludedir = $(includedir)/opencv
|
||||
|
||||
# Which header files to install
|
||||
libcvauxinclude_HEADERS = cvaux.h cvmat.hpp cvaux.hpp cvvidsurv.hpp
|
||||
@@ -0,0 +1,464 @@
|
||||
# Makefile.in generated by automake 1.9.6 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
# 2003, 2004, 2005 Free Software Foundation, Inc.
|
||||
# This Makefile.in is free software; the Free Software Foundation
|
||||
# gives unlimited permission to copy and/or distribute it,
|
||||
# with or without modifications, as long as this notice is preserved.
|
||||
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY, to the extent permitted by law; without
|
||||
# even the implied warranty of MERCHANTABILITY or FITNESS FOR A
|
||||
# PARTICULAR PURPOSE.
|
||||
|
||||
@SET_MAKE@
|
||||
|
||||
srcdir = @srcdir@
|
||||
top_srcdir = @top_srcdir@
|
||||
VPATH = @srcdir@
|
||||
pkgdatadir = $(datadir)/@PACKAGE@
|
||||
pkglibdir = $(libdir)/@PACKAGE@
|
||||
pkgincludedir = $(includedir)/@PACKAGE@
|
||||
top_builddir = ../..
|
||||
am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd
|
||||
INSTALL = @INSTALL@
|
||||
install_sh_DATA = $(install_sh) -c -m 644
|
||||
install_sh_PROGRAM = $(install_sh) -c
|
||||
install_sh_SCRIPT = $(install_sh) -c
|
||||
INSTALL_HEADER = $(INSTALL_DATA)
|
||||
transform = $(program_transform_name)
|
||||
NORMAL_INSTALL = :
|
||||
PRE_INSTALL = :
|
||||
POST_INSTALL = :
|
||||
NORMAL_UNINSTALL = :
|
||||
PRE_UNINSTALL = :
|
||||
POST_UNINSTALL = :
|
||||
build_triplet = @build@
|
||||
host_triplet = @host@
|
||||
target_triplet = @target@
|
||||
subdir = cvaux/include
|
||||
DIST_COMMON = $(libcvauxinclude_HEADERS) $(srcdir)/Makefile.am \
|
||||
$(srcdir)/Makefile.in
|
||||
ACLOCAL_M4 = $(top_srcdir)/aclocal.m4
|
||||
am__aclocal_m4_deps = $(top_srcdir)/autotools/aclocal/az_python.m4 \
|
||||
$(top_srcdir)/autotools/aclocal/pkg.m4 \
|
||||
$(top_srcdir)/autotools/aclocal/swig_complete.m4 \
|
||||
$(top_srcdir)/autotools/aclocal/version_at_least.m4 \
|
||||
$(top_srcdir)/configure.in
|
||||
am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \
|
||||
$(ACLOCAL_M4)
|
||||
mkinstalldirs = $(SHELL) $(top_srcdir)/autotools/mkinstalldirs
|
||||
CONFIG_HEADER = $(top_builddir)/cvconfig.h
|
||||
CONFIG_CLEAN_FILES =
|
||||
SOURCES =
|
||||
DIST_SOURCES =
|
||||
am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`;
|
||||
am__vpath_adj = case $$p in \
|
||||
$(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \
|
||||
*) f=$$p;; \
|
||||
esac;
|
||||
am__strip_dir = `echo $$p | sed -e 's|^.*/||'`;
|
||||
am__installdirs = "$(DESTDIR)$(libcvauxincludedir)"
|
||||
libcvauxincludeHEADERS_INSTALL = $(INSTALL_HEADER)
|
||||
HEADERS = $(libcvauxinclude_HEADERS)
|
||||
ETAGS = etags
|
||||
CTAGS = ctags
|
||||
DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST)
|
||||
ACLOCAL = @ACLOCAL@
|
||||
ALLOCA = @ALLOCA@
|
||||
AMDEP_FALSE = @AMDEP_FALSE@
|
||||
AMDEP_TRUE = @AMDEP_TRUE@
|
||||
AMTAR = @AMTAR@
|
||||
AR = @AR@
|
||||
AS = @AS@
|
||||
AUTOCONF = @AUTOCONF@
|
||||
AUTOHEADER = @AUTOHEADER@
|
||||
AUTOMAKE = @AUTOMAKE@
|
||||
AWK = @AWK@
|
||||
BUILD_APPS_FALSE = @BUILD_APPS_FALSE@
|
||||
BUILD_APPS_TRUE = @BUILD_APPS_TRUE@
|
||||
BUILD_CARBON_FALSE = @BUILD_CARBON_FALSE@
|
||||
BUILD_CARBON_TRUE = @BUILD_CARBON_TRUE@
|
||||
BUILD_DC1394_FALSE = @BUILD_DC1394_FALSE@
|
||||
BUILD_DC1394_TRUE = @BUILD_DC1394_TRUE@
|
||||
BUILD_FFMPEG_FALSE = @BUILD_FFMPEG_FALSE@
|
||||
BUILD_FFMPEG_TRUE = @BUILD_FFMPEG_TRUE@
|
||||
BUILD_GTK_FALSE = @BUILD_GTK_FALSE@
|
||||
BUILD_GTK_TRUE = @BUILD_GTK_TRUE@
|
||||
BUILD_PYTHON_WRAPPERS_FALSE = @BUILD_PYTHON_WRAPPERS_FALSE@
|
||||
BUILD_PYTHON_WRAPPERS_TRUE = @BUILD_PYTHON_WRAPPERS_TRUE@
|
||||
BUILD_QUICKTIME_FALSE = @BUILD_QUICKTIME_FALSE@
|
||||
BUILD_QUICKTIME_TRUE = @BUILD_QUICKTIME_TRUE@
|
||||
BUILD_V4L_FALSE = @BUILD_V4L_FALSE@
|
||||
BUILD_V4L_TRUE = @BUILD_V4L_TRUE@
|
||||
BUILD_XINE_FALSE = @BUILD_XINE_FALSE@
|
||||
BUILD_XINE_TRUE = @BUILD_XINE_TRUE@
|
||||
CARBON_CFLAGS = @CARBON_CFLAGS@
|
||||
CARBON_LIBS = @CARBON_LIBS@
|
||||
CC = @CC@
|
||||
CCDEPMODE = @CCDEPMODE@
|
||||
CFLAGS = @CFLAGS@
|
||||
CPP = @CPP@
|
||||
CPPFLAGS = @CPPFLAGS@
|
||||
CXX = @CXX@
|
||||
CXXCPP = @CXXCPP@
|
||||
CXXDEPMODE = @CXXDEPMODE@
|
||||
CXXFLAGS = @CXXFLAGS@
|
||||
CYGPATH_W = @CYGPATH_W@
|
||||
DEBUG = @DEBUG@
|
||||
DEFS = @DEFS@
|
||||
DEPDIR = @DEPDIR@
|
||||
DLLTOOL = @DLLTOOL@
|
||||
ECHO = @ECHO@
|
||||
ECHO_C = @ECHO_C@
|
||||
ECHO_N = @ECHO_N@
|
||||
ECHO_T = @ECHO_T@
|
||||
EGREP = @EGREP@
|
||||
EXEEXT = @EXEEXT@
|
||||
F77 = @F77@
|
||||
FFLAGS = @FFLAGS@
|
||||
FFMPEGLIBS = @FFMPEGLIBS@
|
||||
GREP = @GREP@
|
||||
GTHREAD_CFLAGS = @GTHREAD_CFLAGS@
|
||||
GTHREAD_LIBS = @GTHREAD_LIBS@
|
||||
GTK_CFLAGS = @GTK_CFLAGS@
|
||||
GTK_LIBS = @GTK_LIBS@
|
||||
IEEE1394LIBS = @IEEE1394LIBS@
|
||||
IMAGELIBS = @IMAGELIBS@
|
||||
INSTALL_DATA = @INSTALL_DATA@
|
||||
INSTALL_PROGRAM = @INSTALL_PROGRAM@
|
||||
INSTALL_SCRIPT = @INSTALL_SCRIPT@
|
||||
INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@
|
||||
LDFLAGS = @LDFLAGS@
|
||||
LIBOBJS = @LIBOBJS@
|
||||
LIBS = @LIBS@
|
||||
LIBTOOL = @LIBTOOL@
|
||||
LN_S = @LN_S@
|
||||
LTLIBOBJS = @LTLIBOBJS@
|
||||
LT_VERSION = @LT_VERSION@
|
||||
MAKEINFO = @MAKEINFO@
|
||||
MMAJOR = @MMAJOR@
|
||||
MMINOR = @MMINOR@
|
||||
MSUBMINOR = @MSUBMINOR@
|
||||
OBJDUMP = @OBJDUMP@
|
||||
OBJEXT = @OBJEXT@
|
||||
PACKAGE = @PACKAGE@
|
||||
PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@
|
||||
PACKAGE_NAME = @PACKAGE_NAME@
|
||||
PACKAGE_STRING = @PACKAGE_STRING@
|
||||
PACKAGE_TARNAME = @PACKAGE_TARNAME@
|
||||
PACKAGE_VERSION = @PACKAGE_VERSION@
|
||||
PATH_SEPARATOR = @PATH_SEPARATOR@
|
||||
PKG_CONFIG = @PKG_CONFIG@
|
||||
PYTHON = @PYTHON@
|
||||
PYTHON_CSPEC = @PYTHON_CSPEC@
|
||||
PYTHON_EXEC_PREFIX = @PYTHON_EXEC_PREFIX@
|
||||
PYTHON_LSPEC = @PYTHON_LSPEC@
|
||||
PYTHON_PLATFORM = @PYTHON_PLATFORM@
|
||||
PYTHON_PREFIX = @PYTHON_PREFIX@
|
||||
PYTHON_VERSION = @PYTHON_VERSION@
|
||||
QUICKTIME_CFLAGS = @QUICKTIME_CFLAGS@
|
||||
QUICKTIME_LIBS = @QUICKTIME_LIBS@
|
||||
RANLIB = @RANLIB@
|
||||
SET_MAKE = @SET_MAKE@
|
||||
SHELL = @SHELL@
|
||||
STRIP = @STRIP@
|
||||
SWIG = @SWIG@
|
||||
SWIG_PYTHON_LIBS = @SWIG_PYTHON_LIBS@
|
||||
SWIG_PYTHON_OPT = @SWIG_PYTHON_OPT@
|
||||
SWIG_RUNTIME_LIBS_DIR = @SWIG_RUNTIME_LIBS_DIR@
|
||||
SWIG_VERSION = @SWIG_VERSION@
|
||||
UPDATE_SWIG_WRAPPERS_FALSE = @UPDATE_SWIG_WRAPPERS_FALSE@
|
||||
UPDATE_SWIG_WRAPPERS_TRUE = @UPDATE_SWIG_WRAPPERS_TRUE@
|
||||
VERSION = @VERSION@
|
||||
XINE_LIBS = @XINE_LIBS@
|
||||
ac_ct_CC = @ac_ct_CC@
|
||||
ac_ct_CXX = @ac_ct_CXX@
|
||||
ac_ct_F77 = @ac_ct_F77@
|
||||
am__fastdepCC_FALSE = @am__fastdepCC_FALSE@
|
||||
am__fastdepCC_TRUE = @am__fastdepCC_TRUE@
|
||||
am__fastdepCXX_FALSE = @am__fastdepCXX_FALSE@
|
||||
am__fastdepCXX_TRUE = @am__fastdepCXX_TRUE@
|
||||
am__include = @am__include@
|
||||
am__leading_dot = @am__leading_dot@
|
||||
am__quote = @am__quote@
|
||||
am__tar = @am__tar@
|
||||
am__untar = @am__untar@
|
||||
bindir = @bindir@
|
||||
build = @build@
|
||||
build_alias = @build_alias@
|
||||
build_cpu = @build_cpu@
|
||||
build_os = @build_os@
|
||||
build_vendor = @build_vendor@
|
||||
datadir = @datadir@
|
||||
datarootdir = @datarootdir@
|
||||
docdir = @docdir@
|
||||
dvidir = @dvidir@
|
||||
exec_prefix = @exec_prefix@
|
||||
host = @host@
|
||||
host_alias = @host_alias@
|
||||
host_cpu = @host_cpu@
|
||||
host_os = @host_os@
|
||||
host_vendor = @host_vendor@
|
||||
htmldir = @htmldir@
|
||||
includedir = @includedir@
|
||||
infodir = @infodir@
|
||||
install_sh = @install_sh@
|
||||
libdir = @libdir@
|
||||
libexecdir = @libexecdir@
|
||||
localedir = @localedir@
|
||||
localstatedir = @localstatedir@
|
||||
mandir = @mandir@
|
||||
mkdir_p = @mkdir_p@
|
||||
oldincludedir = @oldincludedir@
|
||||
pdfdir = @pdfdir@
|
||||
pkgpyexecdir = @pkgpyexecdir@
|
||||
pkgpythondir = @pkgpythondir@
|
||||
prefix = @prefix@
|
||||
program_transform_name = @program_transform_name@
|
||||
psdir = @psdir@
|
||||
pyexecdir = @pyexecdir@
|
||||
pythondir = @pythondir@
|
||||
sbindir = @sbindir@
|
||||
sharedstatedir = @sharedstatedir@
|
||||
sysconfdir = @sysconfdir@
|
||||
target = @target@
|
||||
target_alias = @target_alias@
|
||||
target_cpu = @target_cpu@
|
||||
target_os = @target_os@
|
||||
target_vendor = @target_vendor@
|
||||
|
||||
# The directory where the include files will be installed
|
||||
libcvauxincludedir = $(includedir)/opencv
|
||||
|
||||
# Which header files to install
|
||||
libcvauxinclude_HEADERS = cvaux.h cvmat.hpp cvaux.hpp cvvidsurv.hpp
|
||||
all: all-am
|
||||
|
||||
.SUFFIXES:
|
||||
$(srcdir)/Makefile.in: $(srcdir)/Makefile.am $(am__configure_deps)
|
||||
@for dep in $?; do \
|
||||
case '$(am__configure_deps)' in \
|
||||
*$$dep*) \
|
||||
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh \
|
||||
&& exit 0; \
|
||||
exit 1;; \
|
||||
esac; \
|
||||
done; \
|
||||
echo ' cd $(top_srcdir) && $(AUTOMAKE) --gnu cvaux/include/Makefile'; \
|
||||
cd $(top_srcdir) && \
|
||||
$(AUTOMAKE) --gnu cvaux/include/Makefile
|
||||
.PRECIOUS: Makefile
|
||||
Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status
|
||||
@case '$?' in \
|
||||
*config.status*) \
|
||||
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh;; \
|
||||
*) \
|
||||
echo ' cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe)'; \
|
||||
cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe);; \
|
||||
esac;
|
||||
|
||||
$(top_builddir)/config.status: $(top_srcdir)/configure $(CONFIG_STATUS_DEPENDENCIES)
|
||||
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh
|
||||
|
||||
$(top_srcdir)/configure: $(am__configure_deps)
|
||||
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh
|
||||
$(ACLOCAL_M4): $(am__aclocal_m4_deps)
|
||||
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh
|
||||
|
||||
mostlyclean-libtool:
|
||||
-rm -f *.lo
|
||||
|
||||
clean-libtool:
|
||||
-rm -rf .libs _libs
|
||||
|
||||
distclean-libtool:
|
||||
-rm -f libtool
|
||||
uninstall-info-am:
|
||||
install-libcvauxincludeHEADERS: $(libcvauxinclude_HEADERS)
|
||||
@$(NORMAL_INSTALL)
|
||||
test -z "$(libcvauxincludedir)" || $(mkdir_p) "$(DESTDIR)$(libcvauxincludedir)"
|
||||
@list='$(libcvauxinclude_HEADERS)'; for p in $$list; do \
|
||||
if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \
|
||||
f=$(am__strip_dir) \
|
||||
echo " $(libcvauxincludeHEADERS_INSTALL) '$$d$$p' '$(DESTDIR)$(libcvauxincludedir)/$$f'"; \
|
||||
$(libcvauxincludeHEADERS_INSTALL) "$$d$$p" "$(DESTDIR)$(libcvauxincludedir)/$$f"; \
|
||||
done
|
||||
|
||||
uninstall-libcvauxincludeHEADERS:
|
||||
@$(NORMAL_UNINSTALL)
|
||||
@list='$(libcvauxinclude_HEADERS)'; for p in $$list; do \
|
||||
f=$(am__strip_dir) \
|
||||
echo " rm -f '$(DESTDIR)$(libcvauxincludedir)/$$f'"; \
|
||||
rm -f "$(DESTDIR)$(libcvauxincludedir)/$$f"; \
|
||||
done
|
||||
|
||||
ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES)
|
||||
list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \
|
||||
unique=`for i in $$list; do \
|
||||
if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
|
||||
done | \
|
||||
$(AWK) ' { files[$$0] = 1; } \
|
||||
END { for (i in files) print i; }'`; \
|
||||
mkid -fID $$unique
|
||||
tags: TAGS
|
||||
|
||||
TAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \
|
||||
$(TAGS_FILES) $(LISP)
|
||||
tags=; \
|
||||
here=`pwd`; \
|
||||
list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \
|
||||
unique=`for i in $$list; do \
|
||||
if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
|
||||
done | \
|
||||
$(AWK) ' { files[$$0] = 1; } \
|
||||
END { for (i in files) print i; }'`; \
|
||||
if test -z "$(ETAGS_ARGS)$$tags$$unique"; then :; else \
|
||||
test -n "$$unique" || unique=$$empty_fix; \
|
||||
$(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \
|
||||
$$tags $$unique; \
|
||||
fi
|
||||
ctags: CTAGS
|
||||
CTAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \
|
||||
$(TAGS_FILES) $(LISP)
|
||||
tags=; \
|
||||
here=`pwd`; \
|
||||
list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \
|
||||
unique=`for i in $$list; do \
|
||||
if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
|
||||
done | \
|
||||
$(AWK) ' { files[$$0] = 1; } \
|
||||
END { for (i in files) print i; }'`; \
|
||||
test -z "$(CTAGS_ARGS)$$tags$$unique" \
|
||||
|| $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \
|
||||
$$tags $$unique
|
||||
|
||||
GTAGS:
|
||||
here=`$(am__cd) $(top_builddir) && pwd` \
|
||||
&& cd $(top_srcdir) \
|
||||
&& gtags -i $(GTAGS_ARGS) $$here
|
||||
|
||||
distclean-tags:
|
||||
-rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags
|
||||
|
||||
distdir: $(DISTFILES)
|
||||
@srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; \
|
||||
topsrcdirstrip=`echo "$(top_srcdir)" | sed 's|.|.|g'`; \
|
||||
list='$(DISTFILES)'; for file in $$list; do \
|
||||
case $$file in \
|
||||
$(srcdir)/*) file=`echo "$$file" | sed "s|^$$srcdirstrip/||"`;; \
|
||||
$(top_srcdir)/*) file=`echo "$$file" | sed "s|^$$topsrcdirstrip/|$(top_builddir)/|"`;; \
|
||||
esac; \
|
||||
if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \
|
||||
dir=`echo "$$file" | sed -e 's,/[^/]*$$,,'`; \
|
||||
if test "$$dir" != "$$file" && test "$$dir" != "."; then \
|
||||
dir="/$$dir"; \
|
||||
$(mkdir_p) "$(distdir)$$dir"; \
|
||||
else \
|
||||
dir=''; \
|
||||
fi; \
|
||||
if test -d $$d/$$file; then \
|
||||
if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \
|
||||
cp -pR $(srcdir)/$$file $(distdir)$$dir || exit 1; \
|
||||
fi; \
|
||||
cp -pR $$d/$$file $(distdir)$$dir || exit 1; \
|
||||
else \
|
||||
test -f $(distdir)/$$file \
|
||||
|| cp -p $$d/$$file $(distdir)/$$file \
|
||||
|| exit 1; \
|
||||
fi; \
|
||||
done
|
||||
check-am: all-am
|
||||
check: check-am
|
||||
all-am: Makefile $(HEADERS)
|
||||
installdirs:
|
||||
for dir in "$(DESTDIR)$(libcvauxincludedir)"; do \
|
||||
test -z "$$dir" || $(mkdir_p) "$$dir"; \
|
||||
done
|
||||
install: install-am
|
||||
install-exec: install-exec-am
|
||||
install-data: install-data-am
|
||||
uninstall: uninstall-am
|
||||
|
||||
install-am: all-am
|
||||
@$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am
|
||||
|
||||
installcheck: installcheck-am
|
||||
install-strip:
|
||||
$(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \
|
||||
install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \
|
||||
`test -z '$(STRIP)' || \
|
||||
echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install
|
||||
mostlyclean-generic:
|
||||
|
||||
clean-generic:
|
||||
|
||||
distclean-generic:
|
||||
-test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES)
|
||||
|
||||
maintainer-clean-generic:
|
||||
@echo "This command is intended for maintainers to use"
|
||||
@echo "it deletes files that may require special tools to rebuild."
|
||||
clean: clean-am
|
||||
|
||||
clean-am: clean-generic clean-libtool mostlyclean-am
|
||||
|
||||
distclean: distclean-am
|
||||
-rm -f Makefile
|
||||
distclean-am: clean-am distclean-generic distclean-libtool \
|
||||
distclean-tags
|
||||
|
||||
dvi: dvi-am
|
||||
|
||||
dvi-am:
|
||||
|
||||
html: html-am
|
||||
|
||||
info: info-am
|
||||
|
||||
info-am:
|
||||
|
||||
install-data-am: install-libcvauxincludeHEADERS
|
||||
|
||||
install-exec-am:
|
||||
|
||||
install-info: install-info-am
|
||||
|
||||
install-man:
|
||||
|
||||
installcheck-am:
|
||||
|
||||
maintainer-clean: maintainer-clean-am
|
||||
-rm -f Makefile
|
||||
maintainer-clean-am: distclean-am maintainer-clean-generic
|
||||
|
||||
mostlyclean: mostlyclean-am
|
||||
|
||||
mostlyclean-am: mostlyclean-generic mostlyclean-libtool
|
||||
|
||||
pdf: pdf-am
|
||||
|
||||
pdf-am:
|
||||
|
||||
ps: ps-am
|
||||
|
||||
ps-am:
|
||||
|
||||
uninstall-am: uninstall-info-am uninstall-libcvauxincludeHEADERS
|
||||
|
||||
.PHONY: CTAGS GTAGS all all-am check check-am clean clean-generic \
|
||||
clean-libtool ctags distclean distclean-generic \
|
||||
distclean-libtool distclean-tags distdir dvi dvi-am html \
|
||||
html-am info info-am install install-am install-data \
|
||||
install-data-am install-exec install-exec-am install-info \
|
||||
install-info-am install-libcvauxincludeHEADERS install-man \
|
||||
install-strip installcheck installcheck-am installdirs \
|
||||
maintainer-clean maintainer-clean-generic mostlyclean \
|
||||
mostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \
|
||||
tags uninstall uninstall-am uninstall-info-am \
|
||||
uninstall-libcvauxincludeHEADERS
|
||||
|
||||
# Tell versions [3.59,3.63) of GNU make to not export all variables.
|
||||
# Otherwise a system limit (for SysV at least) may be exceeded.
|
||||
.NOEXPORT:
|
||||
1464
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/include/cvaux.h
Normal file
1464
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/include/cvaux.h
Normal file
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,144 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#ifndef __CVAUX_HPP__
|
||||
#define __CVAUX_HPP__
|
||||
|
||||
#ifdef __cplusplus
|
||||
|
||||
/****************************************************************************************\
|
||||
* Image class *
|
||||
\****************************************************************************************/
|
||||
|
||||
class CV_EXPORTS CvCamShiftTracker
|
||||
{
|
||||
public:
|
||||
|
||||
CvCamShiftTracker();
|
||||
virtual ~CvCamShiftTracker();
|
||||
|
||||
/**** Characteristics of the object that are calculated by track_object method *****/
|
||||
float get_orientation() const // orientation of the object in degrees
|
||||
{ return m_box.angle; }
|
||||
float get_length() const // the larger linear size of the object
|
||||
{ return m_box.size.height; }
|
||||
float get_width() const // the smaller linear size of the object
|
||||
{ return m_box.size.width; }
|
||||
CvPoint2D32f get_center() const // center of the object
|
||||
{ return m_box.center; }
|
||||
CvRect get_window() const // bounding rectangle for the object
|
||||
{ return m_comp.rect; }
|
||||
|
||||
/*********************** Tracking parameters ************************/
|
||||
int get_threshold() const // thresholding value that applied to back project
|
||||
{ return m_threshold; }
|
||||
|
||||
int get_hist_dims( int* dims = 0 ) const // returns number of histogram dimensions and sets
|
||||
{ return m_hist ? cvGetDims( m_hist->bins, dims ) : 0; }
|
||||
|
||||
int get_min_ch_val( int channel ) const // get the minimum allowed value of the specified channel
|
||||
{ return m_min_ch_val[channel]; }
|
||||
|
||||
int get_max_ch_val( int channel ) const // get the maximum allowed value of the specified channel
|
||||
{ return m_max_ch_val[channel]; }
|
||||
|
||||
// set initial object rectangle (must be called before initial calculation of the histogram)
|
||||
bool set_window( CvRect window)
|
||||
{ m_comp.rect = window; return true; }
|
||||
|
||||
bool set_threshold( int threshold ) // threshold applied to the histogram bins
|
||||
{ m_threshold = threshold; return true; }
|
||||
|
||||
bool set_hist_bin_range( int dim, int min_val, int max_val );
|
||||
|
||||
bool set_hist_dims( int c_dims, int* dims );// set the histogram parameters
|
||||
|
||||
bool set_min_ch_val( int channel, int val ) // set the minimum allowed value of the specified channel
|
||||
{ m_min_ch_val[channel] = val; return true; }
|
||||
bool set_max_ch_val( int channel, int val ) // set the maximum allowed value of the specified channel
|
||||
{ m_max_ch_val[channel] = val; return true; }
|
||||
|
||||
/************************ The processing methods *********************************/
|
||||
// update object position
|
||||
virtual bool track_object( const IplImage* cur_frame );
|
||||
|
||||
// update object histogram
|
||||
virtual bool update_histogram( const IplImage* cur_frame );
|
||||
|
||||
// reset histogram
|
||||
virtual void reset_histogram();
|
||||
|
||||
/************************ Retrieving internal data *******************************/
|
||||
// get back project image
|
||||
virtual IplImage* get_back_project()
|
||||
{ return m_back_project; }
|
||||
|
||||
float query( int* bin ) const
|
||||
{ return m_hist ? cvQueryHistValue_nD( m_hist, bin ) : 0.f; }
|
||||
|
||||
protected:
|
||||
|
||||
// internal method for color conversion: fills m_color_planes group
|
||||
virtual void color_transform( const IplImage* img );
|
||||
|
||||
CvHistogram* m_hist;
|
||||
|
||||
CvBox2D m_box;
|
||||
CvConnectedComp m_comp;
|
||||
|
||||
float m_hist_ranges_data[CV_MAX_DIM][2];
|
||||
float* m_hist_ranges[CV_MAX_DIM];
|
||||
|
||||
int m_min_ch_val[CV_MAX_DIM];
|
||||
int m_max_ch_val[CV_MAX_DIM];
|
||||
int m_threshold;
|
||||
|
||||
IplImage* m_color_planes[CV_MAX_DIM];
|
||||
IplImage* m_back_project;
|
||||
IplImage* m_temp;
|
||||
IplImage* m_mask;
|
||||
};
|
||||
|
||||
#endif /* __cplusplus */
|
||||
|
||||
#endif /* __CVAUX_HPP__ */
|
||||
|
||||
/* End of file. */
|
||||
2326
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/include/cvmat.hpp
Normal file
2326
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/include/cvmat.hpp
Normal file
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1 @@
|
||||
*.aps *.o Makefile .libs
|
||||
@@ -0,0 +1,54 @@
|
||||
EXTRA_DIST = cvaux.dsp cvaux.vcproj cvaux.rc resource.h
|
||||
|
||||
INCLUDES = -I. -I$(top_srcdir)/cvaux/include -I$(top_srcdir)/cxcore/include -I$(top_srcdir)/cv/include -I$(top_srcdir)/cv/src -I$(top_srcdir)
|
||||
|
||||
noinst_HEADERS = _cvaux.h _cvfacedetection.h _cvvectrack.h _cvvm.h
|
||||
noinst_LTLIBRARIES = lib_cvaux.la
|
||||
lib_LTLIBRARIES = libcvaux.la
|
||||
|
||||
# convenience library
|
||||
lib_cvaux_la_SOURCES = \
|
||||
camshift.cpp cv3dtracker.cpp cvaux.cpp cvauxutils.cpp \
|
||||
cvbgfg_acmmm2003.cpp cvbgfg_common.cpp cvbgfg_gaussmix.cpp \
|
||||
cvcalibfilter.cpp cvclique.cpp cvcorrespond.cpp cvcorrimages.cpp \
|
||||
cvcreatehandmask.cpp cvdpstereo.cpp cveigenobjects.cpp \
|
||||
cvepilines.cpp cvface.cpp cvfacedetection.cpp cvfacetemplate.cpp \
|
||||
cvfindface.cpp cvfindhandregion.cpp cvhmm1d.cpp cvhmm.cpp \
|
||||
cvhmmobs.cpp cvlcm.cpp cvlee.cpp cvlevmar.cpp cvlevmarprojbandle.cpp \
|
||||
cvlevmartrif.cpp cvlines.cpp cvlmeds.cpp cvmat.cpp cvmorphcontours.cpp \
|
||||
cvmorphing.cpp cvprewarp.cpp cvscanlines.cpp cvsegment.cpp \
|
||||
cvsubdiv2.cpp cvtexture.cpp cvtrifocal.cpp cvvecfacetracking.cpp \
|
||||
cvvideo.cpp decomppoly.cpp enmin.cpp extendededges.cpp \
|
||||
precomp.cpp \
|
||||
\
|
||||
vs/bgfg_estimation.cpp \
|
||||
vs/blobtrackanalysis.cpp \
|
||||
vs/blobtrackanalysishist.cpp \
|
||||
vs/blobtrackanalysisior.cpp \
|
||||
vs/blobtrackanalysistrackdist.cpp \
|
||||
vs/blobtrackgen1.cpp \
|
||||
vs/blobtrackgenyml.cpp \
|
||||
vs/blobtrackingauto.cpp \
|
||||
vs/blobtrackingcc.cpp \
|
||||
vs/blobtrackingccwithcr.cpp \
|
||||
vs/blobtrackingkalman.cpp \
|
||||
vs/blobtrackinglist.cpp \
|
||||
vs/blobtrackingmsfg.cpp \
|
||||
vs/blobtrackingmsfgs.cpp \
|
||||
vs/blobtrackpostprockalman.cpp \
|
||||
vs/blobtrackpostproclinear.cpp \
|
||||
vs/blobtrackpostproclist.cpp \
|
||||
vs/enteringblobdetection.cpp \
|
||||
vs/enteringblobdetectionreal.cpp \
|
||||
vs/testseq.cpp
|
||||
|
||||
lib_cvaux_la_LDFLAGS = -no-undefined @LDFLAGS@
|
||||
|
||||
# real library
|
||||
libcvaux_la_SOURCES = dummy.cpp
|
||||
libcvaux_la_LDFLAGS = -no-undefined -version-info @LT_VERSION@ @LDFLAGS@
|
||||
libcvaux_la_LIBADD = \
|
||||
lib_cvaux.la \
|
||||
$(top_builddir)/cxcore/src/libcxcore.la \
|
||||
$(top_builddir)/cv/src/libcv.la \
|
||||
@LTLIBOBJS@
|
||||
@@ -0,0 +1,844 @@
|
||||
# Makefile.in generated by automake 1.9.6 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
# 2003, 2004, 2005 Free Software Foundation, Inc.
|
||||
# This Makefile.in is free software; the Free Software Foundation
|
||||
# gives unlimited permission to copy and/or distribute it,
|
||||
# with or without modifications, as long as this notice is preserved.
|
||||
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY, to the extent permitted by law; without
|
||||
# even the implied warranty of MERCHANTABILITY or FITNESS FOR A
|
||||
# PARTICULAR PURPOSE.
|
||||
|
||||
@SET_MAKE@
|
||||
|
||||
|
||||
srcdir = @srcdir@
|
||||
top_srcdir = @top_srcdir@
|
||||
VPATH = @srcdir@
|
||||
pkgdatadir = $(datadir)/@PACKAGE@
|
||||
pkglibdir = $(libdir)/@PACKAGE@
|
||||
pkgincludedir = $(includedir)/@PACKAGE@
|
||||
top_builddir = ../..
|
||||
am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd
|
||||
INSTALL = @INSTALL@
|
||||
install_sh_DATA = $(install_sh) -c -m 644
|
||||
install_sh_PROGRAM = $(install_sh) -c
|
||||
install_sh_SCRIPT = $(install_sh) -c
|
||||
INSTALL_HEADER = $(INSTALL_DATA)
|
||||
transform = $(program_transform_name)
|
||||
NORMAL_INSTALL = :
|
||||
PRE_INSTALL = :
|
||||
POST_INSTALL = :
|
||||
NORMAL_UNINSTALL = :
|
||||
PRE_UNINSTALL = :
|
||||
POST_UNINSTALL = :
|
||||
build_triplet = @build@
|
||||
host_triplet = @host@
|
||||
target_triplet = @target@
|
||||
subdir = cvaux/src
|
||||
DIST_COMMON = $(noinst_HEADERS) $(srcdir)/Makefile.am \
|
||||
$(srcdir)/Makefile.in
|
||||
ACLOCAL_M4 = $(top_srcdir)/aclocal.m4
|
||||
am__aclocal_m4_deps = $(top_srcdir)/autotools/aclocal/az_python.m4 \
|
||||
$(top_srcdir)/autotools/aclocal/pkg.m4 \
|
||||
$(top_srcdir)/autotools/aclocal/swig_complete.m4 \
|
||||
$(top_srcdir)/autotools/aclocal/version_at_least.m4 \
|
||||
$(top_srcdir)/configure.in
|
||||
am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \
|
||||
$(ACLOCAL_M4)
|
||||
mkinstalldirs = $(SHELL) $(top_srcdir)/autotools/mkinstalldirs
|
||||
CONFIG_HEADER = $(top_builddir)/cvconfig.h
|
||||
CONFIG_CLEAN_FILES =
|
||||
am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`;
|
||||
am__vpath_adj = case $$p in \
|
||||
$(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \
|
||||
*) f=$$p;; \
|
||||
esac;
|
||||
am__strip_dir = `echo $$p | sed -e 's|^.*/||'`;
|
||||
am__installdirs = "$(DESTDIR)$(libdir)"
|
||||
libLTLIBRARIES_INSTALL = $(INSTALL)
|
||||
LTLIBRARIES = $(lib_LTLIBRARIES) $(noinst_LTLIBRARIES)
|
||||
lib_cvaux_la_LIBADD =
|
||||
am_lib_cvaux_la_OBJECTS = camshift.lo cv3dtracker.lo cvaux.lo \
|
||||
cvauxutils.lo cvbgfg_acmmm2003.lo cvbgfg_common.lo \
|
||||
cvbgfg_gaussmix.lo cvcalibfilter.lo cvclique.lo \
|
||||
cvcorrespond.lo cvcorrimages.lo cvcreatehandmask.lo \
|
||||
cvdpstereo.lo cveigenobjects.lo cvepilines.lo cvface.lo \
|
||||
cvfacedetection.lo cvfacetemplate.lo cvfindface.lo \
|
||||
cvfindhandregion.lo cvhmm1d.lo cvhmm.lo cvhmmobs.lo cvlcm.lo \
|
||||
cvlee.lo cvlevmar.lo cvlevmarprojbandle.lo cvlevmartrif.lo \
|
||||
cvlines.lo cvlmeds.lo cvmat.lo cvmorphcontours.lo \
|
||||
cvmorphing.lo cvprewarp.lo cvscanlines.lo cvsegment.lo \
|
||||
cvsubdiv2.lo cvtexture.lo cvtrifocal.lo cvvecfacetracking.lo \
|
||||
cvvideo.lo decomppoly.lo enmin.lo extendededges.lo precomp.lo \
|
||||
bgfg_estimation.lo blobtrackanalysis.lo \
|
||||
blobtrackanalysishist.lo blobtrackanalysisior.lo \
|
||||
blobtrackanalysistrackdist.lo blobtrackgen1.lo \
|
||||
blobtrackgenyml.lo blobtrackingauto.lo blobtrackingcc.lo \
|
||||
blobtrackingccwithcr.lo blobtrackingkalman.lo \
|
||||
blobtrackinglist.lo blobtrackingmsfg.lo blobtrackingmsfgs.lo \
|
||||
blobtrackpostprockalman.lo blobtrackpostproclinear.lo \
|
||||
blobtrackpostproclist.lo enteringblobdetection.lo \
|
||||
enteringblobdetectionreal.lo testseq.lo
|
||||
lib_cvaux_la_OBJECTS = $(am_lib_cvaux_la_OBJECTS)
|
||||
libcvaux_la_DEPENDENCIES = lib_cvaux.la \
|
||||
$(top_builddir)/cxcore/src/libcxcore.la \
|
||||
$(top_builddir)/cv/src/libcv.la @LTLIBOBJS@
|
||||
am_libcvaux_la_OBJECTS = dummy.lo
|
||||
libcvaux_la_OBJECTS = $(am_libcvaux_la_OBJECTS)
|
||||
DEFAULT_INCLUDES = -I. -I$(srcdir) -I$(top_builddir)
|
||||
depcomp = $(SHELL) $(top_srcdir)/autotools/depcomp
|
||||
am__depfiles_maybe = depfiles
|
||||
COMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \
|
||||
$(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS)
|
||||
LTCOMPILE = $(LIBTOOL) --tag=CC --mode=compile $(CC) $(DEFS) \
|
||||
$(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \
|
||||
$(AM_CFLAGS) $(CFLAGS)
|
||||
CCLD = $(CC)
|
||||
LINK = $(LIBTOOL) --tag=CC --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \
|
||||
$(AM_LDFLAGS) $(LDFLAGS) -o $@
|
||||
CXXCOMPILE = $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) \
|
||||
$(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS)
|
||||
LTCXXCOMPILE = $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) \
|
||||
$(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \
|
||||
$(AM_CXXFLAGS) $(CXXFLAGS)
|
||||
CXXLD = $(CXX)
|
||||
CXXLINK = $(LIBTOOL) --tag=CXX --mode=link $(CXXLD) $(AM_CXXFLAGS) \
|
||||
$(CXXFLAGS) $(AM_LDFLAGS) $(LDFLAGS) -o $@
|
||||
SOURCES = $(lib_cvaux_la_SOURCES) $(libcvaux_la_SOURCES)
|
||||
DIST_SOURCES = $(lib_cvaux_la_SOURCES) $(libcvaux_la_SOURCES)
|
||||
HEADERS = $(noinst_HEADERS)
|
||||
ETAGS = etags
|
||||
CTAGS = ctags
|
||||
DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST)
|
||||
ACLOCAL = @ACLOCAL@
|
||||
ALLOCA = @ALLOCA@
|
||||
AMDEP_FALSE = @AMDEP_FALSE@
|
||||
AMDEP_TRUE = @AMDEP_TRUE@
|
||||
AMTAR = @AMTAR@
|
||||
AR = @AR@
|
||||
AS = @AS@
|
||||
AUTOCONF = @AUTOCONF@
|
||||
AUTOHEADER = @AUTOHEADER@
|
||||
AUTOMAKE = @AUTOMAKE@
|
||||
AWK = @AWK@
|
||||
BUILD_APPS_FALSE = @BUILD_APPS_FALSE@
|
||||
BUILD_APPS_TRUE = @BUILD_APPS_TRUE@
|
||||
BUILD_CARBON_FALSE = @BUILD_CARBON_FALSE@
|
||||
BUILD_CARBON_TRUE = @BUILD_CARBON_TRUE@
|
||||
BUILD_DC1394_FALSE = @BUILD_DC1394_FALSE@
|
||||
BUILD_DC1394_TRUE = @BUILD_DC1394_TRUE@
|
||||
BUILD_FFMPEG_FALSE = @BUILD_FFMPEG_FALSE@
|
||||
BUILD_FFMPEG_TRUE = @BUILD_FFMPEG_TRUE@
|
||||
BUILD_GTK_FALSE = @BUILD_GTK_FALSE@
|
||||
BUILD_GTK_TRUE = @BUILD_GTK_TRUE@
|
||||
BUILD_PYTHON_WRAPPERS_FALSE = @BUILD_PYTHON_WRAPPERS_FALSE@
|
||||
BUILD_PYTHON_WRAPPERS_TRUE = @BUILD_PYTHON_WRAPPERS_TRUE@
|
||||
BUILD_QUICKTIME_FALSE = @BUILD_QUICKTIME_FALSE@
|
||||
BUILD_QUICKTIME_TRUE = @BUILD_QUICKTIME_TRUE@
|
||||
BUILD_V4L_FALSE = @BUILD_V4L_FALSE@
|
||||
BUILD_V4L_TRUE = @BUILD_V4L_TRUE@
|
||||
BUILD_XINE_FALSE = @BUILD_XINE_FALSE@
|
||||
BUILD_XINE_TRUE = @BUILD_XINE_TRUE@
|
||||
CARBON_CFLAGS = @CARBON_CFLAGS@
|
||||
CARBON_LIBS = @CARBON_LIBS@
|
||||
CC = @CC@
|
||||
CCDEPMODE = @CCDEPMODE@
|
||||
CFLAGS = @CFLAGS@
|
||||
CPP = @CPP@
|
||||
CPPFLAGS = @CPPFLAGS@
|
||||
CXX = @CXX@
|
||||
CXXCPP = @CXXCPP@
|
||||
CXXDEPMODE = @CXXDEPMODE@
|
||||
CXXFLAGS = @CXXFLAGS@
|
||||
CYGPATH_W = @CYGPATH_W@
|
||||
DEBUG = @DEBUG@
|
||||
DEFS = @DEFS@
|
||||
DEPDIR = @DEPDIR@
|
||||
DLLTOOL = @DLLTOOL@
|
||||
ECHO = @ECHO@
|
||||
ECHO_C = @ECHO_C@
|
||||
ECHO_N = @ECHO_N@
|
||||
ECHO_T = @ECHO_T@
|
||||
EGREP = @EGREP@
|
||||
EXEEXT = @EXEEXT@
|
||||
F77 = @F77@
|
||||
FFLAGS = @FFLAGS@
|
||||
FFMPEGLIBS = @FFMPEGLIBS@
|
||||
GREP = @GREP@
|
||||
GTHREAD_CFLAGS = @GTHREAD_CFLAGS@
|
||||
GTHREAD_LIBS = @GTHREAD_LIBS@
|
||||
GTK_CFLAGS = @GTK_CFLAGS@
|
||||
GTK_LIBS = @GTK_LIBS@
|
||||
IEEE1394LIBS = @IEEE1394LIBS@
|
||||
IMAGELIBS = @IMAGELIBS@
|
||||
INSTALL_DATA = @INSTALL_DATA@
|
||||
INSTALL_PROGRAM = @INSTALL_PROGRAM@
|
||||
INSTALL_SCRIPT = @INSTALL_SCRIPT@
|
||||
INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@
|
||||
LDFLAGS = @LDFLAGS@
|
||||
LIBOBJS = @LIBOBJS@
|
||||
LIBS = @LIBS@
|
||||
LIBTOOL = @LIBTOOL@
|
||||
LN_S = @LN_S@
|
||||
LTLIBOBJS = @LTLIBOBJS@
|
||||
LT_VERSION = @LT_VERSION@
|
||||
MAKEINFO = @MAKEINFO@
|
||||
MMAJOR = @MMAJOR@
|
||||
MMINOR = @MMINOR@
|
||||
MSUBMINOR = @MSUBMINOR@
|
||||
OBJDUMP = @OBJDUMP@
|
||||
OBJEXT = @OBJEXT@
|
||||
PACKAGE = @PACKAGE@
|
||||
PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@
|
||||
PACKAGE_NAME = @PACKAGE_NAME@
|
||||
PACKAGE_STRING = @PACKAGE_STRING@
|
||||
PACKAGE_TARNAME = @PACKAGE_TARNAME@
|
||||
PACKAGE_VERSION = @PACKAGE_VERSION@
|
||||
PATH_SEPARATOR = @PATH_SEPARATOR@
|
||||
PKG_CONFIG = @PKG_CONFIG@
|
||||
PYTHON = @PYTHON@
|
||||
PYTHON_CSPEC = @PYTHON_CSPEC@
|
||||
PYTHON_EXEC_PREFIX = @PYTHON_EXEC_PREFIX@
|
||||
PYTHON_LSPEC = @PYTHON_LSPEC@
|
||||
PYTHON_PLATFORM = @PYTHON_PLATFORM@
|
||||
PYTHON_PREFIX = @PYTHON_PREFIX@
|
||||
PYTHON_VERSION = @PYTHON_VERSION@
|
||||
QUICKTIME_CFLAGS = @QUICKTIME_CFLAGS@
|
||||
QUICKTIME_LIBS = @QUICKTIME_LIBS@
|
||||
RANLIB = @RANLIB@
|
||||
SET_MAKE = @SET_MAKE@
|
||||
SHELL = @SHELL@
|
||||
STRIP = @STRIP@
|
||||
SWIG = @SWIG@
|
||||
SWIG_PYTHON_LIBS = @SWIG_PYTHON_LIBS@
|
||||
SWIG_PYTHON_OPT = @SWIG_PYTHON_OPT@
|
||||
SWIG_RUNTIME_LIBS_DIR = @SWIG_RUNTIME_LIBS_DIR@
|
||||
SWIG_VERSION = @SWIG_VERSION@
|
||||
UPDATE_SWIG_WRAPPERS_FALSE = @UPDATE_SWIG_WRAPPERS_FALSE@
|
||||
UPDATE_SWIG_WRAPPERS_TRUE = @UPDATE_SWIG_WRAPPERS_TRUE@
|
||||
VERSION = @VERSION@
|
||||
XINE_LIBS = @XINE_LIBS@
|
||||
ac_ct_CC = @ac_ct_CC@
|
||||
ac_ct_CXX = @ac_ct_CXX@
|
||||
ac_ct_F77 = @ac_ct_F77@
|
||||
am__fastdepCC_FALSE = @am__fastdepCC_FALSE@
|
||||
am__fastdepCC_TRUE = @am__fastdepCC_TRUE@
|
||||
am__fastdepCXX_FALSE = @am__fastdepCXX_FALSE@
|
||||
am__fastdepCXX_TRUE = @am__fastdepCXX_TRUE@
|
||||
am__include = @am__include@
|
||||
am__leading_dot = @am__leading_dot@
|
||||
am__quote = @am__quote@
|
||||
am__tar = @am__tar@
|
||||
am__untar = @am__untar@
|
||||
bindir = @bindir@
|
||||
build = @build@
|
||||
build_alias = @build_alias@
|
||||
build_cpu = @build_cpu@
|
||||
build_os = @build_os@
|
||||
build_vendor = @build_vendor@
|
||||
datadir = @datadir@
|
||||
datarootdir = @datarootdir@
|
||||
docdir = @docdir@
|
||||
dvidir = @dvidir@
|
||||
exec_prefix = @exec_prefix@
|
||||
host = @host@
|
||||
host_alias = @host_alias@
|
||||
host_cpu = @host_cpu@
|
||||
host_os = @host_os@
|
||||
host_vendor = @host_vendor@
|
||||
htmldir = @htmldir@
|
||||
includedir = @includedir@
|
||||
infodir = @infodir@
|
||||
install_sh = @install_sh@
|
||||
libdir = @libdir@
|
||||
libexecdir = @libexecdir@
|
||||
localedir = @localedir@
|
||||
localstatedir = @localstatedir@
|
||||
mandir = @mandir@
|
||||
mkdir_p = @mkdir_p@
|
||||
oldincludedir = @oldincludedir@
|
||||
pdfdir = @pdfdir@
|
||||
pkgpyexecdir = @pkgpyexecdir@
|
||||
pkgpythondir = @pkgpythondir@
|
||||
prefix = @prefix@
|
||||
program_transform_name = @program_transform_name@
|
||||
psdir = @psdir@
|
||||
pyexecdir = @pyexecdir@
|
||||
pythondir = @pythondir@
|
||||
sbindir = @sbindir@
|
||||
sharedstatedir = @sharedstatedir@
|
||||
sysconfdir = @sysconfdir@
|
||||
target = @target@
|
||||
target_alias = @target_alias@
|
||||
target_cpu = @target_cpu@
|
||||
target_os = @target_os@
|
||||
target_vendor = @target_vendor@
|
||||
EXTRA_DIST = cvaux.dsp cvaux.vcproj cvaux.rc resource.h
|
||||
INCLUDES = -I. -I$(top_srcdir)/cvaux/include -I$(top_srcdir)/cxcore/include -I$(top_srcdir)/cv/include -I$(top_srcdir)/cv/src -I$(top_srcdir)
|
||||
noinst_HEADERS = _cvaux.h _cvfacedetection.h _cvvectrack.h _cvvm.h
|
||||
noinst_LTLIBRARIES = lib_cvaux.la
|
||||
lib_LTLIBRARIES = libcvaux.la
|
||||
|
||||
# convenience library
|
||||
lib_cvaux_la_SOURCES = \
|
||||
camshift.cpp cv3dtracker.cpp cvaux.cpp cvauxutils.cpp \
|
||||
cvbgfg_acmmm2003.cpp cvbgfg_common.cpp cvbgfg_gaussmix.cpp \
|
||||
cvcalibfilter.cpp cvclique.cpp cvcorrespond.cpp cvcorrimages.cpp \
|
||||
cvcreatehandmask.cpp cvdpstereo.cpp cveigenobjects.cpp \
|
||||
cvepilines.cpp cvface.cpp cvfacedetection.cpp cvfacetemplate.cpp \
|
||||
cvfindface.cpp cvfindhandregion.cpp cvhmm1d.cpp cvhmm.cpp \
|
||||
cvhmmobs.cpp cvlcm.cpp cvlee.cpp cvlevmar.cpp cvlevmarprojbandle.cpp \
|
||||
cvlevmartrif.cpp cvlines.cpp cvlmeds.cpp cvmat.cpp cvmorphcontours.cpp \
|
||||
cvmorphing.cpp cvprewarp.cpp cvscanlines.cpp cvsegment.cpp \
|
||||
cvsubdiv2.cpp cvtexture.cpp cvtrifocal.cpp cvvecfacetracking.cpp \
|
||||
cvvideo.cpp decomppoly.cpp enmin.cpp extendededges.cpp \
|
||||
precomp.cpp \
|
||||
\
|
||||
vs/bgfg_estimation.cpp \
|
||||
vs/blobtrackanalysis.cpp \
|
||||
vs/blobtrackanalysishist.cpp \
|
||||
vs/blobtrackanalysisior.cpp \
|
||||
vs/blobtrackanalysistrackdist.cpp \
|
||||
vs/blobtrackgen1.cpp \
|
||||
vs/blobtrackgenyml.cpp \
|
||||
vs/blobtrackingauto.cpp \
|
||||
vs/blobtrackingcc.cpp \
|
||||
vs/blobtrackingccwithcr.cpp \
|
||||
vs/blobtrackingkalman.cpp \
|
||||
vs/blobtrackinglist.cpp \
|
||||
vs/blobtrackingmsfg.cpp \
|
||||
vs/blobtrackingmsfgs.cpp \
|
||||
vs/blobtrackpostprockalman.cpp \
|
||||
vs/blobtrackpostproclinear.cpp \
|
||||
vs/blobtrackpostproclist.cpp \
|
||||
vs/enteringblobdetection.cpp \
|
||||
vs/enteringblobdetectionreal.cpp \
|
||||
vs/testseq.cpp
|
||||
|
||||
lib_cvaux_la_LDFLAGS = -no-undefined @LDFLAGS@
|
||||
|
||||
# real library
|
||||
libcvaux_la_SOURCES = dummy.cpp
|
||||
libcvaux_la_LDFLAGS = -no-undefined -version-info @LT_VERSION@ @LDFLAGS@
|
||||
libcvaux_la_LIBADD = \
|
||||
lib_cvaux.la \
|
||||
$(top_builddir)/cxcore/src/libcxcore.la \
|
||||
$(top_builddir)/cv/src/libcv.la \
|
||||
@LTLIBOBJS@
|
||||
|
||||
all: all-am
|
||||
|
||||
.SUFFIXES:
|
||||
.SUFFIXES: .c .cpp .lo .o .obj
|
||||
$(srcdir)/Makefile.in: $(srcdir)/Makefile.am $(am__configure_deps)
|
||||
@for dep in $?; do \
|
||||
case '$(am__configure_deps)' in \
|
||||
*$$dep*) \
|
||||
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh \
|
||||
&& exit 0; \
|
||||
exit 1;; \
|
||||
esac; \
|
||||
done; \
|
||||
echo ' cd $(top_srcdir) && $(AUTOMAKE) --gnu cvaux/src/Makefile'; \
|
||||
cd $(top_srcdir) && \
|
||||
$(AUTOMAKE) --gnu cvaux/src/Makefile
|
||||
.PRECIOUS: Makefile
|
||||
Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status
|
||||
@case '$?' in \
|
||||
*config.status*) \
|
||||
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh;; \
|
||||
*) \
|
||||
echo ' cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe)'; \
|
||||
cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe);; \
|
||||
esac;
|
||||
|
||||
$(top_builddir)/config.status: $(top_srcdir)/configure $(CONFIG_STATUS_DEPENDENCIES)
|
||||
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh
|
||||
|
||||
$(top_srcdir)/configure: $(am__configure_deps)
|
||||
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh
|
||||
$(ACLOCAL_M4): $(am__aclocal_m4_deps)
|
||||
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh
|
||||
install-libLTLIBRARIES: $(lib_LTLIBRARIES)
|
||||
@$(NORMAL_INSTALL)
|
||||
test -z "$(libdir)" || $(mkdir_p) "$(DESTDIR)$(libdir)"
|
||||
@list='$(lib_LTLIBRARIES)'; for p in $$list; do \
|
||||
if test -f $$p; then \
|
||||
f=$(am__strip_dir) \
|
||||
echo " $(LIBTOOL) --mode=install $(libLTLIBRARIES_INSTALL) $(INSTALL_STRIP_FLAG) '$$p' '$(DESTDIR)$(libdir)/$$f'"; \
|
||||
$(LIBTOOL) --mode=install $(libLTLIBRARIES_INSTALL) $(INSTALL_STRIP_FLAG) "$$p" "$(DESTDIR)$(libdir)/$$f"; \
|
||||
else :; fi; \
|
||||
done
|
||||
|
||||
uninstall-libLTLIBRARIES:
|
||||
@$(NORMAL_UNINSTALL)
|
||||
@set -x; list='$(lib_LTLIBRARIES)'; for p in $$list; do \
|
||||
p=$(am__strip_dir) \
|
||||
echo " $(LIBTOOL) --mode=uninstall rm -f '$(DESTDIR)$(libdir)/$$p'"; \
|
||||
$(LIBTOOL) --mode=uninstall rm -f "$(DESTDIR)$(libdir)/$$p"; \
|
||||
done
|
||||
|
||||
clean-libLTLIBRARIES:
|
||||
-test -z "$(lib_LTLIBRARIES)" || rm -f $(lib_LTLIBRARIES)
|
||||
@list='$(lib_LTLIBRARIES)'; for p in $$list; do \
|
||||
dir="`echo $$p | sed -e 's|/[^/]*$$||'`"; \
|
||||
test "$$dir" != "$$p" || dir=.; \
|
||||
echo "rm -f \"$${dir}/so_locations\""; \
|
||||
rm -f "$${dir}/so_locations"; \
|
||||
done
|
||||
|
||||
clean-noinstLTLIBRARIES:
|
||||
-test -z "$(noinst_LTLIBRARIES)" || rm -f $(noinst_LTLIBRARIES)
|
||||
@list='$(noinst_LTLIBRARIES)'; for p in $$list; do \
|
||||
dir="`echo $$p | sed -e 's|/[^/]*$$||'`"; \
|
||||
test "$$dir" != "$$p" || dir=.; \
|
||||
echo "rm -f \"$${dir}/so_locations\""; \
|
||||
rm -f "$${dir}/so_locations"; \
|
||||
done
|
||||
lib_cvaux.la: $(lib_cvaux_la_OBJECTS) $(lib_cvaux_la_DEPENDENCIES)
|
||||
$(CXXLINK) $(lib_cvaux_la_LDFLAGS) $(lib_cvaux_la_OBJECTS) $(lib_cvaux_la_LIBADD) $(LIBS)
|
||||
libcvaux.la: $(libcvaux_la_OBJECTS) $(libcvaux_la_DEPENDENCIES)
|
||||
$(CXXLINK) -rpath $(libdir) $(libcvaux_la_LDFLAGS) $(libcvaux_la_OBJECTS) $(libcvaux_la_LIBADD) $(LIBS)
|
||||
|
||||
mostlyclean-compile:
|
||||
-rm -f *.$(OBJEXT)
|
||||
|
||||
distclean-compile:
|
||||
-rm -f *.tab.c
|
||||
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/bgfg_estimation.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/blobtrackanalysis.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/blobtrackanalysishist.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/blobtrackanalysisior.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/blobtrackanalysistrackdist.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/blobtrackgen1.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/blobtrackgenyml.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/blobtrackingauto.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/blobtrackingcc.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/blobtrackingccwithcr.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/blobtrackingkalman.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/blobtrackinglist.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/blobtrackingmsfg.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/blobtrackingmsfgs.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/blobtrackpostprockalman.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/blobtrackpostproclinear.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/blobtrackpostproclist.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/camshift.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cv3dtracker.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvaux.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvauxutils.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvbgfg_acmmm2003.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvbgfg_common.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvbgfg_gaussmix.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvcalibfilter.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvclique.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvcorrespond.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvcorrimages.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvcreatehandmask.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvdpstereo.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cveigenobjects.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvepilines.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvface.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvfacedetection.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvfacetemplate.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvfindface.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvfindhandregion.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvhmm.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvhmm1d.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvhmmobs.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvlcm.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvlee.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvlevmar.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvlevmarprojbandle.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvlevmartrif.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvlines.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvlmeds.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvmat.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvmorphcontours.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvmorphing.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvprewarp.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvscanlines.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvsegment.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvsubdiv2.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvtexture.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvtrifocal.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvvecfacetracking.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cvvideo.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/decomppoly.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/dummy.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/enmin.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/enteringblobdetection.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/enteringblobdetectionreal.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/extendededges.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/precomp.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/testseq.Plo@am__quote@
|
||||
|
||||
.c.o:
|
||||
@am__fastdepCC_TRUE@ if $(COMPILE) -MT $@ -MD -MP -MF "$(DEPDIR)/$*.Tpo" -c -o $@ $<; \
|
||||
@am__fastdepCC_TRUE@ then mv -f "$(DEPDIR)/$*.Tpo" "$(DEPDIR)/$*.Po"; else rm -f "$(DEPDIR)/$*.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCC_FALSE@ $(COMPILE) -c $<
|
||||
|
||||
.c.obj:
|
||||
@am__fastdepCC_TRUE@ if $(COMPILE) -MT $@ -MD -MP -MF "$(DEPDIR)/$*.Tpo" -c -o $@ `$(CYGPATH_W) '$<'`; \
|
||||
@am__fastdepCC_TRUE@ then mv -f "$(DEPDIR)/$*.Tpo" "$(DEPDIR)/$*.Po"; else rm -f "$(DEPDIR)/$*.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'`
|
||||
|
||||
.c.lo:
|
||||
@am__fastdepCC_TRUE@ if $(LTCOMPILE) -MT $@ -MD -MP -MF "$(DEPDIR)/$*.Tpo" -c -o $@ $<; \
|
||||
@am__fastdepCC_TRUE@ then mv -f "$(DEPDIR)/$*.Tpo" "$(DEPDIR)/$*.Plo"; else rm -f "$(DEPDIR)/$*.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $<
|
||||
|
||||
.cpp.o:
|
||||
@am__fastdepCXX_TRUE@ if $(CXXCOMPILE) -MT $@ -MD -MP -MF "$(DEPDIR)/$*.Tpo" -c -o $@ $<; \
|
||||
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/$*.Tpo" "$(DEPDIR)/$*.Po"; else rm -f "$(DEPDIR)/$*.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCXX_FALSE@ $(CXXCOMPILE) -c -o $@ $<
|
||||
|
||||
.cpp.obj:
|
||||
@am__fastdepCXX_TRUE@ if $(CXXCOMPILE) -MT $@ -MD -MP -MF "$(DEPDIR)/$*.Tpo" -c -o $@ `$(CYGPATH_W) '$<'`; \
|
||||
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/$*.Tpo" "$(DEPDIR)/$*.Po"; else rm -f "$(DEPDIR)/$*.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCXX_FALSE@ $(CXXCOMPILE) -c -o $@ `$(CYGPATH_W) '$<'`
|
||||
|
||||
.cpp.lo:
|
||||
@am__fastdepCXX_TRUE@ if $(LTCXXCOMPILE) -MT $@ -MD -MP -MF "$(DEPDIR)/$*.Tpo" -c -o $@ $<; \
|
||||
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/$*.Tpo" "$(DEPDIR)/$*.Plo"; else rm -f "$(DEPDIR)/$*.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCXX_FALSE@ $(LTCXXCOMPILE) -c -o $@ $<
|
||||
|
||||
bgfg_estimation.lo: vs/bgfg_estimation.cpp
|
||||
@am__fastdepCXX_TRUE@ if $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT bgfg_estimation.lo -MD -MP -MF "$(DEPDIR)/bgfg_estimation.Tpo" -c -o bgfg_estimation.lo `test -f 'vs/bgfg_estimation.cpp' || echo '$(srcdir)/'`vs/bgfg_estimation.cpp; \
|
||||
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/bgfg_estimation.Tpo" "$(DEPDIR)/bgfg_estimation.Plo"; else rm -f "$(DEPDIR)/bgfg_estimation.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='vs/bgfg_estimation.cpp' object='bgfg_estimation.lo' libtool=yes @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCXX_FALSE@ $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o bgfg_estimation.lo `test -f 'vs/bgfg_estimation.cpp' || echo '$(srcdir)/'`vs/bgfg_estimation.cpp
|
||||
|
||||
blobtrackanalysis.lo: vs/blobtrackanalysis.cpp
|
||||
@am__fastdepCXX_TRUE@ if $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT blobtrackanalysis.lo -MD -MP -MF "$(DEPDIR)/blobtrackanalysis.Tpo" -c -o blobtrackanalysis.lo `test -f 'vs/blobtrackanalysis.cpp' || echo '$(srcdir)/'`vs/blobtrackanalysis.cpp; \
|
||||
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/blobtrackanalysis.Tpo" "$(DEPDIR)/blobtrackanalysis.Plo"; else rm -f "$(DEPDIR)/blobtrackanalysis.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='vs/blobtrackanalysis.cpp' object='blobtrackanalysis.lo' libtool=yes @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCXX_FALSE@ $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o blobtrackanalysis.lo `test -f 'vs/blobtrackanalysis.cpp' || echo '$(srcdir)/'`vs/blobtrackanalysis.cpp
|
||||
|
||||
blobtrackanalysishist.lo: vs/blobtrackanalysishist.cpp
|
||||
@am__fastdepCXX_TRUE@ if $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT blobtrackanalysishist.lo -MD -MP -MF "$(DEPDIR)/blobtrackanalysishist.Tpo" -c -o blobtrackanalysishist.lo `test -f 'vs/blobtrackanalysishist.cpp' || echo '$(srcdir)/'`vs/blobtrackanalysishist.cpp; \
|
||||
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/blobtrackanalysishist.Tpo" "$(DEPDIR)/blobtrackanalysishist.Plo"; else rm -f "$(DEPDIR)/blobtrackanalysishist.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='vs/blobtrackanalysishist.cpp' object='blobtrackanalysishist.lo' libtool=yes @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCXX_FALSE@ $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o blobtrackanalysishist.lo `test -f 'vs/blobtrackanalysishist.cpp' || echo '$(srcdir)/'`vs/blobtrackanalysishist.cpp
|
||||
|
||||
blobtrackanalysisior.lo: vs/blobtrackanalysisior.cpp
|
||||
@am__fastdepCXX_TRUE@ if $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT blobtrackanalysisior.lo -MD -MP -MF "$(DEPDIR)/blobtrackanalysisior.Tpo" -c -o blobtrackanalysisior.lo `test -f 'vs/blobtrackanalysisior.cpp' || echo '$(srcdir)/'`vs/blobtrackanalysisior.cpp; \
|
||||
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/blobtrackanalysisior.Tpo" "$(DEPDIR)/blobtrackanalysisior.Plo"; else rm -f "$(DEPDIR)/blobtrackanalysisior.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='vs/blobtrackanalysisior.cpp' object='blobtrackanalysisior.lo' libtool=yes @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCXX_FALSE@ $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o blobtrackanalysisior.lo `test -f 'vs/blobtrackanalysisior.cpp' || echo '$(srcdir)/'`vs/blobtrackanalysisior.cpp
|
||||
|
||||
blobtrackanalysistrackdist.lo: vs/blobtrackanalysistrackdist.cpp
|
||||
@am__fastdepCXX_TRUE@ if $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT blobtrackanalysistrackdist.lo -MD -MP -MF "$(DEPDIR)/blobtrackanalysistrackdist.Tpo" -c -o blobtrackanalysistrackdist.lo `test -f 'vs/blobtrackanalysistrackdist.cpp' || echo '$(srcdir)/'`vs/blobtrackanalysistrackdist.cpp; \
|
||||
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/blobtrackanalysistrackdist.Tpo" "$(DEPDIR)/blobtrackanalysistrackdist.Plo"; else rm -f "$(DEPDIR)/blobtrackanalysistrackdist.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='vs/blobtrackanalysistrackdist.cpp' object='blobtrackanalysistrackdist.lo' libtool=yes @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCXX_FALSE@ $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o blobtrackanalysistrackdist.lo `test -f 'vs/blobtrackanalysistrackdist.cpp' || echo '$(srcdir)/'`vs/blobtrackanalysistrackdist.cpp
|
||||
|
||||
blobtrackgen1.lo: vs/blobtrackgen1.cpp
|
||||
@am__fastdepCXX_TRUE@ if $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT blobtrackgen1.lo -MD -MP -MF "$(DEPDIR)/blobtrackgen1.Tpo" -c -o blobtrackgen1.lo `test -f 'vs/blobtrackgen1.cpp' || echo '$(srcdir)/'`vs/blobtrackgen1.cpp; \
|
||||
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/blobtrackgen1.Tpo" "$(DEPDIR)/blobtrackgen1.Plo"; else rm -f "$(DEPDIR)/blobtrackgen1.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='vs/blobtrackgen1.cpp' object='blobtrackgen1.lo' libtool=yes @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCXX_FALSE@ $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o blobtrackgen1.lo `test -f 'vs/blobtrackgen1.cpp' || echo '$(srcdir)/'`vs/blobtrackgen1.cpp
|
||||
|
||||
blobtrackgenyml.lo: vs/blobtrackgenyml.cpp
|
||||
@am__fastdepCXX_TRUE@ if $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT blobtrackgenyml.lo -MD -MP -MF "$(DEPDIR)/blobtrackgenyml.Tpo" -c -o blobtrackgenyml.lo `test -f 'vs/blobtrackgenyml.cpp' || echo '$(srcdir)/'`vs/blobtrackgenyml.cpp; \
|
||||
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/blobtrackgenyml.Tpo" "$(DEPDIR)/blobtrackgenyml.Plo"; else rm -f "$(DEPDIR)/blobtrackgenyml.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='vs/blobtrackgenyml.cpp' object='blobtrackgenyml.lo' libtool=yes @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCXX_FALSE@ $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o blobtrackgenyml.lo `test -f 'vs/blobtrackgenyml.cpp' || echo '$(srcdir)/'`vs/blobtrackgenyml.cpp
|
||||
|
||||
blobtrackingauto.lo: vs/blobtrackingauto.cpp
|
||||
@am__fastdepCXX_TRUE@ if $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT blobtrackingauto.lo -MD -MP -MF "$(DEPDIR)/blobtrackingauto.Tpo" -c -o blobtrackingauto.lo `test -f 'vs/blobtrackingauto.cpp' || echo '$(srcdir)/'`vs/blobtrackingauto.cpp; \
|
||||
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/blobtrackingauto.Tpo" "$(DEPDIR)/blobtrackingauto.Plo"; else rm -f "$(DEPDIR)/blobtrackingauto.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='vs/blobtrackingauto.cpp' object='blobtrackingauto.lo' libtool=yes @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCXX_FALSE@ $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o blobtrackingauto.lo `test -f 'vs/blobtrackingauto.cpp' || echo '$(srcdir)/'`vs/blobtrackingauto.cpp
|
||||
|
||||
blobtrackingcc.lo: vs/blobtrackingcc.cpp
|
||||
@am__fastdepCXX_TRUE@ if $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT blobtrackingcc.lo -MD -MP -MF "$(DEPDIR)/blobtrackingcc.Tpo" -c -o blobtrackingcc.lo `test -f 'vs/blobtrackingcc.cpp' || echo '$(srcdir)/'`vs/blobtrackingcc.cpp; \
|
||||
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/blobtrackingcc.Tpo" "$(DEPDIR)/blobtrackingcc.Plo"; else rm -f "$(DEPDIR)/blobtrackingcc.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='vs/blobtrackingcc.cpp' object='blobtrackingcc.lo' libtool=yes @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCXX_FALSE@ $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o blobtrackingcc.lo `test -f 'vs/blobtrackingcc.cpp' || echo '$(srcdir)/'`vs/blobtrackingcc.cpp
|
||||
|
||||
blobtrackingccwithcr.lo: vs/blobtrackingccwithcr.cpp
|
||||
@am__fastdepCXX_TRUE@ if $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT blobtrackingccwithcr.lo -MD -MP -MF "$(DEPDIR)/blobtrackingccwithcr.Tpo" -c -o blobtrackingccwithcr.lo `test -f 'vs/blobtrackingccwithcr.cpp' || echo '$(srcdir)/'`vs/blobtrackingccwithcr.cpp; \
|
||||
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/blobtrackingccwithcr.Tpo" "$(DEPDIR)/blobtrackingccwithcr.Plo"; else rm -f "$(DEPDIR)/blobtrackingccwithcr.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='vs/blobtrackingccwithcr.cpp' object='blobtrackingccwithcr.lo' libtool=yes @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCXX_FALSE@ $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o blobtrackingccwithcr.lo `test -f 'vs/blobtrackingccwithcr.cpp' || echo '$(srcdir)/'`vs/blobtrackingccwithcr.cpp
|
||||
|
||||
blobtrackingkalman.lo: vs/blobtrackingkalman.cpp
|
||||
@am__fastdepCXX_TRUE@ if $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT blobtrackingkalman.lo -MD -MP -MF "$(DEPDIR)/blobtrackingkalman.Tpo" -c -o blobtrackingkalman.lo `test -f 'vs/blobtrackingkalman.cpp' || echo '$(srcdir)/'`vs/blobtrackingkalman.cpp; \
|
||||
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/blobtrackingkalman.Tpo" "$(DEPDIR)/blobtrackingkalman.Plo"; else rm -f "$(DEPDIR)/blobtrackingkalman.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='vs/blobtrackingkalman.cpp' object='blobtrackingkalman.lo' libtool=yes @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCXX_FALSE@ $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o blobtrackingkalman.lo `test -f 'vs/blobtrackingkalman.cpp' || echo '$(srcdir)/'`vs/blobtrackingkalman.cpp
|
||||
|
||||
blobtrackinglist.lo: vs/blobtrackinglist.cpp
|
||||
@am__fastdepCXX_TRUE@ if $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT blobtrackinglist.lo -MD -MP -MF "$(DEPDIR)/blobtrackinglist.Tpo" -c -o blobtrackinglist.lo `test -f 'vs/blobtrackinglist.cpp' || echo '$(srcdir)/'`vs/blobtrackinglist.cpp; \
|
||||
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/blobtrackinglist.Tpo" "$(DEPDIR)/blobtrackinglist.Plo"; else rm -f "$(DEPDIR)/blobtrackinglist.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='vs/blobtrackinglist.cpp' object='blobtrackinglist.lo' libtool=yes @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCXX_FALSE@ $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o blobtrackinglist.lo `test -f 'vs/blobtrackinglist.cpp' || echo '$(srcdir)/'`vs/blobtrackinglist.cpp
|
||||
|
||||
blobtrackingmsfg.lo: vs/blobtrackingmsfg.cpp
|
||||
@am__fastdepCXX_TRUE@ if $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT blobtrackingmsfg.lo -MD -MP -MF "$(DEPDIR)/blobtrackingmsfg.Tpo" -c -o blobtrackingmsfg.lo `test -f 'vs/blobtrackingmsfg.cpp' || echo '$(srcdir)/'`vs/blobtrackingmsfg.cpp; \
|
||||
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/blobtrackingmsfg.Tpo" "$(DEPDIR)/blobtrackingmsfg.Plo"; else rm -f "$(DEPDIR)/blobtrackingmsfg.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='vs/blobtrackingmsfg.cpp' object='blobtrackingmsfg.lo' libtool=yes @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCXX_FALSE@ $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o blobtrackingmsfg.lo `test -f 'vs/blobtrackingmsfg.cpp' || echo '$(srcdir)/'`vs/blobtrackingmsfg.cpp
|
||||
|
||||
blobtrackingmsfgs.lo: vs/blobtrackingmsfgs.cpp
|
||||
@am__fastdepCXX_TRUE@ if $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT blobtrackingmsfgs.lo -MD -MP -MF "$(DEPDIR)/blobtrackingmsfgs.Tpo" -c -o blobtrackingmsfgs.lo `test -f 'vs/blobtrackingmsfgs.cpp' || echo '$(srcdir)/'`vs/blobtrackingmsfgs.cpp; \
|
||||
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/blobtrackingmsfgs.Tpo" "$(DEPDIR)/blobtrackingmsfgs.Plo"; else rm -f "$(DEPDIR)/blobtrackingmsfgs.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='vs/blobtrackingmsfgs.cpp' object='blobtrackingmsfgs.lo' libtool=yes @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCXX_FALSE@ $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o blobtrackingmsfgs.lo `test -f 'vs/blobtrackingmsfgs.cpp' || echo '$(srcdir)/'`vs/blobtrackingmsfgs.cpp
|
||||
|
||||
blobtrackpostprockalman.lo: vs/blobtrackpostprockalman.cpp
|
||||
@am__fastdepCXX_TRUE@ if $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT blobtrackpostprockalman.lo -MD -MP -MF "$(DEPDIR)/blobtrackpostprockalman.Tpo" -c -o blobtrackpostprockalman.lo `test -f 'vs/blobtrackpostprockalman.cpp' || echo '$(srcdir)/'`vs/blobtrackpostprockalman.cpp; \
|
||||
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/blobtrackpostprockalman.Tpo" "$(DEPDIR)/blobtrackpostprockalman.Plo"; else rm -f "$(DEPDIR)/blobtrackpostprockalman.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='vs/blobtrackpostprockalman.cpp' object='blobtrackpostprockalman.lo' libtool=yes @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCXX_FALSE@ $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o blobtrackpostprockalman.lo `test -f 'vs/blobtrackpostprockalman.cpp' || echo '$(srcdir)/'`vs/blobtrackpostprockalman.cpp
|
||||
|
||||
blobtrackpostproclinear.lo: vs/blobtrackpostproclinear.cpp
|
||||
@am__fastdepCXX_TRUE@ if $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT blobtrackpostproclinear.lo -MD -MP -MF "$(DEPDIR)/blobtrackpostproclinear.Tpo" -c -o blobtrackpostproclinear.lo `test -f 'vs/blobtrackpostproclinear.cpp' || echo '$(srcdir)/'`vs/blobtrackpostproclinear.cpp; \
|
||||
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/blobtrackpostproclinear.Tpo" "$(DEPDIR)/blobtrackpostproclinear.Plo"; else rm -f "$(DEPDIR)/blobtrackpostproclinear.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='vs/blobtrackpostproclinear.cpp' object='blobtrackpostproclinear.lo' libtool=yes @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCXX_FALSE@ $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o blobtrackpostproclinear.lo `test -f 'vs/blobtrackpostproclinear.cpp' || echo '$(srcdir)/'`vs/blobtrackpostproclinear.cpp
|
||||
|
||||
blobtrackpostproclist.lo: vs/blobtrackpostproclist.cpp
|
||||
@am__fastdepCXX_TRUE@ if $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT blobtrackpostproclist.lo -MD -MP -MF "$(DEPDIR)/blobtrackpostproclist.Tpo" -c -o blobtrackpostproclist.lo `test -f 'vs/blobtrackpostproclist.cpp' || echo '$(srcdir)/'`vs/blobtrackpostproclist.cpp; \
|
||||
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/blobtrackpostproclist.Tpo" "$(DEPDIR)/blobtrackpostproclist.Plo"; else rm -f "$(DEPDIR)/blobtrackpostproclist.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='vs/blobtrackpostproclist.cpp' object='blobtrackpostproclist.lo' libtool=yes @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCXX_FALSE@ $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o blobtrackpostproclist.lo `test -f 'vs/blobtrackpostproclist.cpp' || echo '$(srcdir)/'`vs/blobtrackpostproclist.cpp
|
||||
|
||||
enteringblobdetection.lo: vs/enteringblobdetection.cpp
|
||||
@am__fastdepCXX_TRUE@ if $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT enteringblobdetection.lo -MD -MP -MF "$(DEPDIR)/enteringblobdetection.Tpo" -c -o enteringblobdetection.lo `test -f 'vs/enteringblobdetection.cpp' || echo '$(srcdir)/'`vs/enteringblobdetection.cpp; \
|
||||
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/enteringblobdetection.Tpo" "$(DEPDIR)/enteringblobdetection.Plo"; else rm -f "$(DEPDIR)/enteringblobdetection.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='vs/enteringblobdetection.cpp' object='enteringblobdetection.lo' libtool=yes @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCXX_FALSE@ $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o enteringblobdetection.lo `test -f 'vs/enteringblobdetection.cpp' || echo '$(srcdir)/'`vs/enteringblobdetection.cpp
|
||||
|
||||
enteringblobdetectionreal.lo: vs/enteringblobdetectionreal.cpp
|
||||
@am__fastdepCXX_TRUE@ if $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT enteringblobdetectionreal.lo -MD -MP -MF "$(DEPDIR)/enteringblobdetectionreal.Tpo" -c -o enteringblobdetectionreal.lo `test -f 'vs/enteringblobdetectionreal.cpp' || echo '$(srcdir)/'`vs/enteringblobdetectionreal.cpp; \
|
||||
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/enteringblobdetectionreal.Tpo" "$(DEPDIR)/enteringblobdetectionreal.Plo"; else rm -f "$(DEPDIR)/enteringblobdetectionreal.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='vs/enteringblobdetectionreal.cpp' object='enteringblobdetectionreal.lo' libtool=yes @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCXX_FALSE@ $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o enteringblobdetectionreal.lo `test -f 'vs/enteringblobdetectionreal.cpp' || echo '$(srcdir)/'`vs/enteringblobdetectionreal.cpp
|
||||
|
||||
testseq.lo: vs/testseq.cpp
|
||||
@am__fastdepCXX_TRUE@ if $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT testseq.lo -MD -MP -MF "$(DEPDIR)/testseq.Tpo" -c -o testseq.lo `test -f 'vs/testseq.cpp' || echo '$(srcdir)/'`vs/testseq.cpp; \
|
||||
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/testseq.Tpo" "$(DEPDIR)/testseq.Plo"; else rm -f "$(DEPDIR)/testseq.Tpo"; exit 1; fi
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='vs/testseq.cpp' object='testseq.lo' libtool=yes @AMDEPBACKSLASH@
|
||||
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCXX_FALSE@ $(LIBTOOL) --tag=CXX --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o testseq.lo `test -f 'vs/testseq.cpp' || echo '$(srcdir)/'`vs/testseq.cpp
|
||||
|
||||
mostlyclean-libtool:
|
||||
-rm -f *.lo
|
||||
|
||||
clean-libtool:
|
||||
-rm -rf .libs _libs
|
||||
|
||||
distclean-libtool:
|
||||
-rm -f libtool
|
||||
uninstall-info-am:
|
||||
|
||||
ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES)
|
||||
list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \
|
||||
unique=`for i in $$list; do \
|
||||
if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
|
||||
done | \
|
||||
$(AWK) ' { files[$$0] = 1; } \
|
||||
END { for (i in files) print i; }'`; \
|
||||
mkid -fID $$unique
|
||||
tags: TAGS
|
||||
|
||||
TAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \
|
||||
$(TAGS_FILES) $(LISP)
|
||||
tags=; \
|
||||
here=`pwd`; \
|
||||
list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \
|
||||
unique=`for i in $$list; do \
|
||||
if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
|
||||
done | \
|
||||
$(AWK) ' { files[$$0] = 1; } \
|
||||
END { for (i in files) print i; }'`; \
|
||||
if test -z "$(ETAGS_ARGS)$$tags$$unique"; then :; else \
|
||||
test -n "$$unique" || unique=$$empty_fix; \
|
||||
$(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \
|
||||
$$tags $$unique; \
|
||||
fi
|
||||
ctags: CTAGS
|
||||
CTAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \
|
||||
$(TAGS_FILES) $(LISP)
|
||||
tags=; \
|
||||
here=`pwd`; \
|
||||
list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \
|
||||
unique=`for i in $$list; do \
|
||||
if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
|
||||
done | \
|
||||
$(AWK) ' { files[$$0] = 1; } \
|
||||
END { for (i in files) print i; }'`; \
|
||||
test -z "$(CTAGS_ARGS)$$tags$$unique" \
|
||||
|| $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \
|
||||
$$tags $$unique
|
||||
|
||||
GTAGS:
|
||||
here=`$(am__cd) $(top_builddir) && pwd` \
|
||||
&& cd $(top_srcdir) \
|
||||
&& gtags -i $(GTAGS_ARGS) $$here
|
||||
|
||||
distclean-tags:
|
||||
-rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags
|
||||
|
||||
distdir: $(DISTFILES)
|
||||
@srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; \
|
||||
topsrcdirstrip=`echo "$(top_srcdir)" | sed 's|.|.|g'`; \
|
||||
list='$(DISTFILES)'; for file in $$list; do \
|
||||
case $$file in \
|
||||
$(srcdir)/*) file=`echo "$$file" | sed "s|^$$srcdirstrip/||"`;; \
|
||||
$(top_srcdir)/*) file=`echo "$$file" | sed "s|^$$topsrcdirstrip/|$(top_builddir)/|"`;; \
|
||||
esac; \
|
||||
if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \
|
||||
dir=`echo "$$file" | sed -e 's,/[^/]*$$,,'`; \
|
||||
if test "$$dir" != "$$file" && test "$$dir" != "."; then \
|
||||
dir="/$$dir"; \
|
||||
$(mkdir_p) "$(distdir)$$dir"; \
|
||||
else \
|
||||
dir=''; \
|
||||
fi; \
|
||||
if test -d $$d/$$file; then \
|
||||
if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \
|
||||
cp -pR $(srcdir)/$$file $(distdir)$$dir || exit 1; \
|
||||
fi; \
|
||||
cp -pR $$d/$$file $(distdir)$$dir || exit 1; \
|
||||
else \
|
||||
test -f $(distdir)/$$file \
|
||||
|| cp -p $$d/$$file $(distdir)/$$file \
|
||||
|| exit 1; \
|
||||
fi; \
|
||||
done
|
||||
check-am: all-am
|
||||
check: check-am
|
||||
all-am: Makefile $(LTLIBRARIES) $(HEADERS)
|
||||
installdirs:
|
||||
for dir in "$(DESTDIR)$(libdir)"; do \
|
||||
test -z "$$dir" || $(mkdir_p) "$$dir"; \
|
||||
done
|
||||
install: install-am
|
||||
install-exec: install-exec-am
|
||||
install-data: install-data-am
|
||||
uninstall: uninstall-am
|
||||
|
||||
install-am: all-am
|
||||
@$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am
|
||||
|
||||
installcheck: installcheck-am
|
||||
install-strip:
|
||||
$(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \
|
||||
install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \
|
||||
`test -z '$(STRIP)' || \
|
||||
echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install
|
||||
mostlyclean-generic:
|
||||
|
||||
clean-generic:
|
||||
|
||||
distclean-generic:
|
||||
-test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES)
|
||||
|
||||
maintainer-clean-generic:
|
||||
@echo "This command is intended for maintainers to use"
|
||||
@echo "it deletes files that may require special tools to rebuild."
|
||||
clean: clean-am
|
||||
|
||||
clean-am: clean-generic clean-libLTLIBRARIES clean-libtool \
|
||||
clean-noinstLTLIBRARIES mostlyclean-am
|
||||
|
||||
distclean: distclean-am
|
||||
-rm -rf ./$(DEPDIR)
|
||||
-rm -f Makefile
|
||||
distclean-am: clean-am distclean-compile distclean-generic \
|
||||
distclean-libtool distclean-tags
|
||||
|
||||
dvi: dvi-am
|
||||
|
||||
dvi-am:
|
||||
|
||||
html: html-am
|
||||
|
||||
info: info-am
|
||||
|
||||
info-am:
|
||||
|
||||
install-data-am:
|
||||
|
||||
install-exec-am: install-libLTLIBRARIES
|
||||
|
||||
install-info: install-info-am
|
||||
|
||||
install-man:
|
||||
|
||||
installcheck-am:
|
||||
|
||||
maintainer-clean: maintainer-clean-am
|
||||
-rm -rf ./$(DEPDIR)
|
||||
-rm -f Makefile
|
||||
maintainer-clean-am: distclean-am maintainer-clean-generic
|
||||
|
||||
mostlyclean: mostlyclean-am
|
||||
|
||||
mostlyclean-am: mostlyclean-compile mostlyclean-generic \
|
||||
mostlyclean-libtool
|
||||
|
||||
pdf: pdf-am
|
||||
|
||||
pdf-am:
|
||||
|
||||
ps: ps-am
|
||||
|
||||
ps-am:
|
||||
|
||||
uninstall-am: uninstall-info-am uninstall-libLTLIBRARIES
|
||||
|
||||
.PHONY: CTAGS GTAGS all all-am check check-am clean clean-generic \
|
||||
clean-libLTLIBRARIES clean-libtool clean-noinstLTLIBRARIES \
|
||||
ctags distclean distclean-compile distclean-generic \
|
||||
distclean-libtool distclean-tags distdir dvi dvi-am html \
|
||||
html-am info info-am install install-am install-data \
|
||||
install-data-am install-exec install-exec-am install-info \
|
||||
install-info-am install-libLTLIBRARIES install-man \
|
||||
install-strip installcheck installcheck-am installdirs \
|
||||
maintainer-clean maintainer-clean-generic mostlyclean \
|
||||
mostlyclean-compile mostlyclean-generic mostlyclean-libtool \
|
||||
pdf pdf-am ps ps-am tags uninstall uninstall-am \
|
||||
uninstall-info-am uninstall-libLTLIBRARIES
|
||||
|
||||
# Tell versions [3.59,3.63) of GNU make to not export all variables.
|
||||
# Otherwise a system limit (for SysV at least) may be exceeded.
|
||||
.NOEXPORT:
|
||||
@@ -0,0 +1,73 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
#ifndef __CVAUX_H__
|
||||
#define __CVAUX_H__
|
||||
|
||||
#if _MSC_VER >= 1200
|
||||
#pragma warning( disable: 4710 4711 4514 4996 ) /* function AAA selected for automatic inline expansion */
|
||||
#endif
|
||||
|
||||
#include "cvaux.h"
|
||||
#include "cxmisc.h"
|
||||
#include "_cvmatrix.h"
|
||||
|
||||
typedef unsigned short ushort;
|
||||
|
||||
CV_INLINE bool operator == (CvSize size1, CvSize size2 );
|
||||
CV_INLINE bool operator == (CvSize size1, CvSize size2 )
|
||||
{
|
||||
return size1.width == size2.width && size1.height == size2.height;
|
||||
}
|
||||
|
||||
CV_INLINE bool operator != (CvSize size1, CvSize size2 );
|
||||
CV_INLINE bool operator != (CvSize size1, CvSize size2 )
|
||||
{
|
||||
return size1.width != size2.width || size1.height != size2.height;
|
||||
}
|
||||
|
||||
#ifndef FALSE
|
||||
#define FALSE 0
|
||||
#endif
|
||||
#ifndef TRUE
|
||||
#define TRUE 1
|
||||
#endif
|
||||
|
||||
#endif /* __CVAUX_H__ */
|
||||
@@ -0,0 +1,412 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
///////////////////////////////////////////////
|
||||
//// Created by Khudyakov V.A. bober@gorodok.net
|
||||
// FaceDetection.h: interface for the FaceDetection class.
|
||||
//
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
|
||||
#ifndef _CVFACEDETECTION_H_
|
||||
#define _CVFACEDETECTION_H_
|
||||
|
||||
#define MAX_LAYERS 64
|
||||
|
||||
class FaceFeature
|
||||
{
|
||||
public:
|
||||
FaceFeature(double dWeight,void * lpContour,bool bIsFeature);
|
||||
FaceFeature();
|
||||
virtual ~FaceFeature();
|
||||
inline bool isFaceFeature();
|
||||
inline void * GetContour();
|
||||
inline double GetWeight();
|
||||
inline void SetContour(void * lpContour);
|
||||
inline void SetWeight(double dWeight);
|
||||
inline void SetFeature(bool bIsFeature);
|
||||
private:
|
||||
double m_dWeight;
|
||||
void * m_lpContour;
|
||||
bool m_bIsFaceFeature;
|
||||
};//class FaceFeature
|
||||
|
||||
inline void FaceFeature::SetFeature(bool bIsFeature)
|
||||
{
|
||||
m_bIsFaceFeature = bIsFeature;
|
||||
}
|
||||
|
||||
inline bool FaceFeature::isFaceFeature()
|
||||
{
|
||||
return m_bIsFaceFeature;
|
||||
}//inline bool FaceFeature::isFaceFeature()
|
||||
|
||||
inline void * FaceFeature::GetContour()
|
||||
{
|
||||
return m_lpContour;
|
||||
}//inline void * FaceFeature::GetContour()
|
||||
|
||||
inline double FaceFeature::GetWeight()
|
||||
{
|
||||
return m_dWeight;
|
||||
}//inline long FaceFeature::GetWeight()
|
||||
|
||||
inline void FaceFeature::SetContour(void * lpContour)
|
||||
{
|
||||
m_lpContour = lpContour;
|
||||
}//inline void FaceFeature::SetContour(void * lpContour)
|
||||
|
||||
inline void FaceFeature::SetWeight(double dWeight)
|
||||
{
|
||||
m_dWeight = dWeight;
|
||||
}//inline void FaceFeature::SetWeight(double * dWeight)
|
||||
|
||||
|
||||
|
||||
class FaceTemplate
|
||||
{
|
||||
public:
|
||||
FaceTemplate(long lFeatureCount) {m_lFeturesCount = lFeatureCount; m_lpFeaturesList = new FaceFeature[lFeatureCount];};
|
||||
virtual ~FaceTemplate();
|
||||
|
||||
inline long GetCount();
|
||||
inline FaceFeature * GetFeatures();
|
||||
|
||||
protected:
|
||||
FaceFeature * m_lpFeaturesList;
|
||||
private:
|
||||
long m_lFeturesCount;
|
||||
};//class FaceTemplate
|
||||
|
||||
|
||||
inline long FaceTemplate::GetCount()
|
||||
{
|
||||
return m_lFeturesCount;
|
||||
}//inline long FaceTemplate::GetCount()
|
||||
|
||||
|
||||
inline FaceFeature * FaceTemplate::GetFeatures()
|
||||
{
|
||||
return m_lpFeaturesList;
|
||||
}//inline FaceFeature * FaceTemplate::GetFeatures()
|
||||
|
||||
////////////
|
||||
//class RFaceTemplate
|
||||
///////////
|
||||
|
||||
class MouthFaceTemplate:public FaceTemplate
|
||||
{
|
||||
public:
|
||||
inline MouthFaceTemplate(long lNumber,CvRect rect,double dEyeWidth,double dEyeHeight,double dDistanceBetweenEye,double dDistanceEyeAboveMouth);
|
||||
~MouthFaceTemplate();
|
||||
};//class MouthFaceTemplate:public FaceTemplate
|
||||
|
||||
|
||||
inline MouthFaceTemplate::MouthFaceTemplate(long lNumber,CvRect rect,double dEyeWidth,double dEyeHeight,
|
||||
double dDistanceBetweenEye,double dDistanceEyeAboveMouth):FaceTemplate(lNumber)
|
||||
{
|
||||
|
||||
CvRect MouthRect = rect;
|
||||
|
||||
|
||||
CvRect LeftEyeRect = cvRect(cvRound(rect.x - (dEyeWidth + dDistanceBetweenEye/(double)2 - (double)rect.width/(double)2)),
|
||||
cvRound(rect.y - dDistanceEyeAboveMouth - dEyeHeight),
|
||||
cvRound(dEyeWidth),
|
||||
cvRound(dEyeHeight) );
|
||||
|
||||
CvRect RightEyeRect = cvRect(cvRound(rect.x + (double)rect.width/(double)2 + dDistanceBetweenEye/(double)2),
|
||||
cvRound(rect.y - dDistanceEyeAboveMouth - dEyeHeight),
|
||||
cvRound(dEyeWidth),
|
||||
cvRound(dEyeHeight) );
|
||||
|
||||
// CvRect NoseRect = cvRect(cvRound(rect.x + (double)rect.width/(double)4),
|
||||
// cvRound(rect.y - (double)rect.width/(double)2 - (double)rect.height/(double)4),
|
||||
// cvRound((double)rect.width/(double)2),
|
||||
// cvRound((double)rect.width/(double)2) );
|
||||
/*
|
||||
CvRect CheenRect = cvRect(rect.x,rect.y + 3*rect.height/2,rect.width,rect.height);
|
||||
|
||||
*/
|
||||
|
||||
CvRect * lpMouthRect = new CvRect();
|
||||
*lpMouthRect = MouthRect;
|
||||
m_lpFeaturesList[0].SetContour(lpMouthRect);
|
||||
m_lpFeaturesList[0].SetWeight(1);
|
||||
m_lpFeaturesList[0].SetFeature(false);
|
||||
|
||||
|
||||
CvRect * lpLeftEyeRect = new CvRect();
|
||||
*lpLeftEyeRect = LeftEyeRect;
|
||||
m_lpFeaturesList[1].SetContour(lpLeftEyeRect);
|
||||
m_lpFeaturesList[1].SetWeight(1);
|
||||
m_lpFeaturesList[1].SetFeature(true);
|
||||
|
||||
CvRect * lpRightEyeRect = new CvRect();
|
||||
*lpRightEyeRect = RightEyeRect;
|
||||
m_lpFeaturesList[2].SetContour(lpRightEyeRect);
|
||||
m_lpFeaturesList[2].SetWeight(1);
|
||||
m_lpFeaturesList[2].SetFeature(true);
|
||||
|
||||
|
||||
// CvRect * lpNoseRect = new CvRect();
|
||||
// *lpNoseRect = NoseRect;
|
||||
// m_lpFeaturesList[3].SetContour(lpNoseRect);
|
||||
// m_lpFeaturesList[3].SetWeight(0);
|
||||
// m_lpFeaturesList[3].SetFeature(true);
|
||||
|
||||
/* CvRect * lpCheenRect = new CvRect();
|
||||
*lpCheenRect = CheenRect;
|
||||
m_lpFeaturesList[4].SetContour(lpCheenRect);
|
||||
m_lpFeaturesList[4].SetWeight(1);
|
||||
m_lpFeaturesList[4].SetFeature(false);
|
||||
|
||||
*/
|
||||
|
||||
}//constructor MouthFaceTemplate(long lNumFeatures,CvRect rect,double dEyeWidth,double dEyeHeight,double dDistanceBetweenEye,double dDistanceEyeAboveMouth);
|
||||
|
||||
|
||||
typedef struct CvContourRect
|
||||
{
|
||||
int iNumber;
|
||||
int iType;
|
||||
int iFlags;
|
||||
CvSeq *seqContour;
|
||||
int iContourLength;
|
||||
CvRect r;
|
||||
CvPoint pCenter;
|
||||
int iColor;
|
||||
} CvContourRect;
|
||||
|
||||
class Face
|
||||
{
|
||||
public:
|
||||
Face(FaceTemplate * lpFaceTemplate);
|
||||
virtual ~Face();
|
||||
|
||||
inline bool isFeature(void * lpElem);
|
||||
|
||||
virtual void Show(IplImage * /*Image*/){};
|
||||
virtual void ShowIdeal(IplImage* /*Image*/){};
|
||||
|
||||
virtual void CreateFace(void * lpData) = 0;
|
||||
virtual bool CheckElem(void * lpCandidat,void * lpIdeal) = 0;
|
||||
virtual double GetWeight() = 0;
|
||||
protected:
|
||||
FaceFeature * m_lpIdealFace;//ideal face definition
|
||||
long m_lFaceFeaturesNumber; //total number of diferent face fetures
|
||||
long * m_lplFaceFeaturesCount;//number of each fetures fouded for this face
|
||||
FaceFeature ** m_lppFoundedFaceFeatures;//founded features of curen face
|
||||
double m_dWeight;
|
||||
};
|
||||
|
||||
inline bool Face::isFeature(void * lpElem)
|
||||
{
|
||||
for (int i = 0;i < m_lFaceFeaturesNumber;i ++)
|
||||
{
|
||||
void * lpIdeal = m_lpIdealFace[i].GetContour();
|
||||
|
||||
if ( CheckElem( lpElem,lpIdeal) )
|
||||
{
|
||||
if (m_lplFaceFeaturesCount[i] < 3*MAX_LAYERS)
|
||||
{
|
||||
double dWeight = m_lpIdealFace[i].GetWeight();
|
||||
bool bIsFeature = m_lpIdealFace[i].isFaceFeature();
|
||||
|
||||
|
||||
if (bIsFeature)
|
||||
{
|
||||
m_lppFoundedFaceFeatures[i][m_lplFaceFeaturesCount[i]].SetWeight(dWeight);
|
||||
m_lppFoundedFaceFeatures[i][m_lplFaceFeaturesCount[i]].SetContour(lpElem);
|
||||
m_lppFoundedFaceFeatures[i][m_lplFaceFeaturesCount[i]].SetFeature(bIsFeature);
|
||||
m_lplFaceFeaturesCount[i] ++;
|
||||
}
|
||||
|
||||
m_dWeight += dWeight;
|
||||
|
||||
if (bIsFeature)
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
return false;
|
||||
}//inline bool RFace::isFeature(void * lpElem);
|
||||
|
||||
|
||||
struct FaceData
|
||||
{
|
||||
CvRect LeftEyeRect;
|
||||
CvRect RightEyeRect;
|
||||
CvRect MouthRect;
|
||||
double Error;
|
||||
};//struct FaceData
|
||||
|
||||
class RFace:public Face
|
||||
{
|
||||
public:
|
||||
RFace(FaceTemplate * lpFaceTemplate);
|
||||
virtual ~RFace();
|
||||
virtual bool CheckElem(void * lpCandidat,void * lpIdeal);
|
||||
virtual void CreateFace(void * lpData);
|
||||
virtual void Show(IplImage* Image);
|
||||
virtual void ShowIdeal(IplImage* Image);
|
||||
virtual double GetWeight();
|
||||
private:
|
||||
bool isPointInRect(CvPoint p,CvRect rect);
|
||||
bool m_bIsGenerated;
|
||||
void ResizeRect(CvRect Rect,CvRect * lpRect,long lDir,long lD);
|
||||
void CalculateError(FaceData * lpFaceData);
|
||||
};
|
||||
|
||||
|
||||
class ListElem
|
||||
{
|
||||
public:
|
||||
ListElem();
|
||||
ListElem(Face * pFace,ListElem * pHead);
|
||||
virtual ~ListElem();
|
||||
ListElem * m_pNext;
|
||||
ListElem * m_pPrev;
|
||||
Face * m_pFace;
|
||||
};//class ListElem
|
||||
|
||||
class List
|
||||
{
|
||||
public:
|
||||
List();
|
||||
int AddElem(Face * pFace);
|
||||
virtual ~List();
|
||||
Face* GetData();
|
||||
long m_FacesCount;
|
||||
private:
|
||||
ListElem * m_pHead;
|
||||
ListElem * m_pCurElem;
|
||||
};//class List
|
||||
|
||||
|
||||
class FaceDetection
|
||||
{
|
||||
public:
|
||||
void FindFace(IplImage* img);
|
||||
void CreateResults(CvSeq * lpSeq);
|
||||
FaceDetection();
|
||||
virtual ~FaceDetection();
|
||||
void SetBoosting(bool bBoosting) {m_bBoosting = bBoosting;}
|
||||
bool isPostBoosting() {return m_bBoosting;}
|
||||
protected:
|
||||
|
||||
IplImage* m_imgGray;
|
||||
IplImage* m_imgThresh;
|
||||
int m_iNumLayers;
|
||||
CvMemStorage* m_mstgContours;
|
||||
CvSeq* m_seqContours[MAX_LAYERS];
|
||||
CvMemStorage* m_mstgRects;
|
||||
CvSeq* m_seqRects;
|
||||
|
||||
bool m_bBoosting;
|
||||
List * m_pFaceList;
|
||||
|
||||
protected:
|
||||
void ResetImage();
|
||||
void FindContours(IplImage* imgGray);
|
||||
void AddContours2Rect(CvSeq* seq, int color, int iLayer);
|
||||
void ThresholdingParam(IplImage* imgGray, int iNumLayers, int& iMinLevel, int& iMaxLevel, int& iStep);
|
||||
void FindCandidats();
|
||||
void PostBoostingFindCandidats(IplImage * FaceImage);
|
||||
};
|
||||
|
||||
inline void ReallocImage(IplImage** ppImage, CvSize sz, long lChNum)
|
||||
{
|
||||
IplImage* pImage;
|
||||
if( ppImage == NULL )
|
||||
return;
|
||||
pImage = *ppImage;
|
||||
if( pImage != NULL )
|
||||
{
|
||||
if (pImage->width != sz.width || pImage->height != sz.height || pImage->nChannels != lChNum)
|
||||
cvReleaseImage( &pImage );
|
||||
}
|
||||
if( pImage == NULL )
|
||||
pImage = cvCreateImage( sz, IPL_DEPTH_8U, lChNum);
|
||||
*ppImage = pImage;
|
||||
}
|
||||
|
||||
////////////
|
||||
//class RFaceTemplate
|
||||
///////////
|
||||
|
||||
class BoostingFaceTemplate:public FaceTemplate
|
||||
{
|
||||
public:
|
||||
inline BoostingFaceTemplate(long lNumber,CvRect rect);
|
||||
~BoostingFaceTemplate() {};
|
||||
};//class RFaceTemplate:public FaceTemplate
|
||||
|
||||
|
||||
inline BoostingFaceTemplate::BoostingFaceTemplate(long lNumber,CvRect rect):FaceTemplate(lNumber)
|
||||
{
|
||||
long EyeWidth = rect.width/5;
|
||||
long EyeHeight = EyeWidth;
|
||||
|
||||
CvRect LeftEyeRect = cvRect(rect.x + EyeWidth,rect.y + rect.height/2 - EyeHeight,EyeWidth,EyeHeight);
|
||||
CvRect RightEyeRect = cvRect(rect.x + 3*EyeWidth,rect.y + rect.height/2 - EyeHeight,EyeWidth,EyeHeight);
|
||||
CvRect MouthRect = cvRect(rect.x + 3*EyeWidth/2,rect.y + 3*rect.height/4 - EyeHeight/2,2*EyeWidth,EyeHeight);
|
||||
|
||||
CvRect * lpMouthRect = new CvRect();
|
||||
*lpMouthRect = MouthRect;
|
||||
m_lpFeaturesList[0].SetContour(lpMouthRect);
|
||||
m_lpFeaturesList[0].SetWeight(1);
|
||||
m_lpFeaturesList[0].SetFeature(true);
|
||||
|
||||
CvRect * lpLeftEyeRect = new CvRect();
|
||||
*lpLeftEyeRect = LeftEyeRect;
|
||||
m_lpFeaturesList[1].SetContour(lpLeftEyeRect);
|
||||
m_lpFeaturesList[1].SetWeight(1);
|
||||
m_lpFeaturesList[1].SetFeature(true);
|
||||
|
||||
CvRect * lpRightEyeRect = new CvRect();
|
||||
*lpRightEyeRect = RightEyeRect;
|
||||
m_lpFeaturesList[2].SetContour(lpRightEyeRect);
|
||||
m_lpFeaturesList[2].SetWeight(1);
|
||||
m_lpFeaturesList[2].SetFeature(true);
|
||||
|
||||
}//inline BoostingFaceTemplate::BoostingFaceTemplate(long lNumber,CvRect rect):FaceTemplate(lNumber)
|
||||
|
||||
#endif // !defined(AFX_FACEDETECTION_H__55865033_D8E5_4DD5_8925_34C2285BB1BE__INCLUDED_)
|
||||
@@ -0,0 +1,163 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
|
||||
#ifndef __CVVECTRACK_H__
|
||||
#define __CVVECTRACK_H__
|
||||
|
||||
#include <string.h>
|
||||
#include <math.h>
|
||||
#include <time.h>
|
||||
#include <stdio.h>
|
||||
|
||||
#undef max
|
||||
#undef min
|
||||
|
||||
#define max(a,b) ((a)<(b) ? (b) : (a))
|
||||
#define min(a,b) ((a)>(b) ? (a) : (b))
|
||||
|
||||
inline int pow2(int v)
|
||||
{
|
||||
return (v*v);
|
||||
}
|
||||
|
||||
inline int operator == (const CvRect& r1, const CvRect& r2)
|
||||
{
|
||||
return (r1.x == r2.x) && (r1.y == r2.y) &&
|
||||
(r1.width == r2.width) && (r1.height == r2.height);
|
||||
}
|
||||
|
||||
inline int operator != (const CvRect& r1, const CvRect& r2)
|
||||
{
|
||||
return !(r1 == r2);
|
||||
}
|
||||
|
||||
inline
|
||||
int CmpPoints(const CvPoint& p1, const CvPoint& p2, int err)
|
||||
{
|
||||
/* Simakov: modify __max to max */
|
||||
return (max(abs(p1.x - p2.x), abs(p1.y - p2.y)) < err);
|
||||
}
|
||||
|
||||
inline
|
||||
int PointInRect(const CvPoint& p, const CvRect& r)
|
||||
{
|
||||
return ((p.x > r.x) && (p.x < (r.x + r.width)) &&
|
||||
(p.y > r.y) && (p.y < (r.y + r.height)));
|
||||
}
|
||||
|
||||
inline
|
||||
int RectInRect(const CvRect& r1, const CvRect& r2)
|
||||
{
|
||||
CvPoint plt = {r1.x, r1.y};
|
||||
CvPoint prb = {r1.x + r1.width, r1.y + r1.height};
|
||||
return (PointInRect(plt, r2) && PointInRect(prb, r2));
|
||||
}
|
||||
|
||||
inline
|
||||
CvRect Increase(const CvRect& r, int decr)
|
||||
{
|
||||
CvRect rect;
|
||||
rect.x = r.x * decr;
|
||||
rect.y = r.y * decr;
|
||||
rect.width = r.width * decr;
|
||||
rect.height = r.height * decr;
|
||||
return rect;
|
||||
}
|
||||
|
||||
inline
|
||||
CvPoint Increase(const CvPoint& p, int decr)
|
||||
{
|
||||
CvPoint point;
|
||||
point.x = p.x * decr;
|
||||
point.y = p.y * decr;
|
||||
return point;
|
||||
}
|
||||
|
||||
inline
|
||||
void Move(CvRect& r, int dx, int dy)
|
||||
{
|
||||
r.x += dx;
|
||||
r.y += dy;
|
||||
}
|
||||
|
||||
inline
|
||||
void Move(CvPoint& p, int dx, int dy)
|
||||
{
|
||||
p.x += dx;
|
||||
p.y += dy;
|
||||
}
|
||||
|
||||
inline
|
||||
void Extend(CvRect& r, int d)
|
||||
{
|
||||
r.x -= d;
|
||||
r.y -= d;
|
||||
r.width += 2*d;
|
||||
r.height += 2*d;
|
||||
}
|
||||
|
||||
inline
|
||||
CvPoint Center(const CvRect& r)
|
||||
{
|
||||
CvPoint p;
|
||||
p.x = r.x + r.width / 2;
|
||||
p.y = r.y + r.height / 2;
|
||||
return p;
|
||||
}
|
||||
|
||||
inline void ReallocImage(IplImage** ppImage, CvSize sz, long lChNum)
|
||||
{
|
||||
IplImage* pImage;
|
||||
if( ppImage == NULL )
|
||||
return;
|
||||
pImage = *ppImage;
|
||||
if( pImage != NULL )
|
||||
{
|
||||
if (pImage->width != sz.width || pImage->height != sz.height || pImage->nChannels != lChNum)
|
||||
cvReleaseImage( &pImage );
|
||||
}
|
||||
if( pImage == NULL )
|
||||
pImage = cvCreateImage( sz, IPL_DEPTH_8U, lChNum);
|
||||
*ppImage = pImage;
|
||||
}
|
||||
|
||||
#endif //__VECTRACK_H__
|
||||
298
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/src/_cvvm.h
Normal file
298
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/src/_cvvm.h
Normal file
@@ -0,0 +1,298 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#ifndef _CV_VM_H_
|
||||
#define _CV_VM_H_
|
||||
|
||||
/*----------------------- Internal ViewMorphing Functions ------------------------------*/
|
||||
|
||||
/*======================================================================================*/
|
||||
|
||||
typedef struct CvMatrix4
|
||||
{
|
||||
float m[4][4];
|
||||
}
|
||||
CvMatrix4;
|
||||
|
||||
|
||||
/* Scanline section. Find coordinates by fundamental matrix */
|
||||
|
||||
/* Epsilon and real zero */
|
||||
#define EPSILON 1.e-4
|
||||
//#define REAL_ZERO(x) ( (x) < EPSILON && (x) > -EPSILON)
|
||||
#define REAL_ZERO(x) ( (x) < 1e-8 && (x) > -1e-8)
|
||||
|
||||
#define SIGN(x) ( (x)<0 ? -1:((x)>0?1:0 ) )
|
||||
|
||||
CvStatus icvMakeScanlinesLengths( int* scanlines,
|
||||
int numlines,
|
||||
int* lens);
|
||||
|
||||
/*=============================== PreWarp section ======================================*/
|
||||
|
||||
CV_INLINE int icvGetColor(uchar* valueRGB);
|
||||
|
||||
CvStatus icvFindRunsInOneImage(
|
||||
int numLines, /* number of scanlines */
|
||||
uchar* prewarp, /* prewarp image */
|
||||
int* line_lens, /* line lengths in pixels */
|
||||
int* runs, /* result runs */
|
||||
int* num_runs);
|
||||
|
||||
/*================================ Morphing section ====================================*/
|
||||
|
||||
CvStatus icvMorphEpilines8uC3( uchar* first_pix, /* raster epiline from the first image */
|
||||
uchar* second_pix, /* raster epiline from the second image */
|
||||
uchar* dst_pix, /* raster epiline from the destination image */
|
||||
/* (it's an output parameter) */
|
||||
float alpha, /* relative position of camera */
|
||||
int* first, /* first sequence of runs */
|
||||
int first_runs, /* it's length */
|
||||
int* second, /* second sequence of runs */
|
||||
int second_runs,
|
||||
int* first_corr, /* correspond information for the 1st seq */
|
||||
int* second_corr,
|
||||
int dst_len); /* correspond information for the 2nd seq */
|
||||
|
||||
/*========================== Dynamic correspond section ================================*/
|
||||
|
||||
CvStatus icvDynamicCorrespond( int* first, /* first sequence of runs */
|
||||
/* s0|w0|s1|w1|...|s(n-1)|w(n-1)|sn */
|
||||
int first_runs, /* number of runs */
|
||||
int* second, /* second sequence of runs */
|
||||
int second_runs,
|
||||
int* first_corr, /* s0'|e0'|s1'|e1'|... */
|
||||
int* second_corr );
|
||||
|
||||
/*============================= PostWarp Functions =====================================*/
|
||||
|
||||
CvStatus icvFetchLine8uC3R(
|
||||
uchar* src, int src_step,
|
||||
uchar* dst, int* dst_num,
|
||||
CvSize src_size,
|
||||
CvPoint start,
|
||||
CvPoint end );
|
||||
|
||||
CvStatus icvDrawLine8uC3R(
|
||||
uchar* src, int src_num,
|
||||
uchar* dst, int dst_step,
|
||||
CvSize dst_size,
|
||||
CvPoint start,
|
||||
CvPoint end );
|
||||
|
||||
|
||||
/*============================== Fundamental Matrix Functions ==========================*/
|
||||
CvStatus icvPoint7( int* points1,
|
||||
int* points2,
|
||||
double* F,
|
||||
int* amount
|
||||
);
|
||||
|
||||
CvStatus icvCubic( double a2, double a1,
|
||||
double a0, double* squares );
|
||||
|
||||
double icvDet( double* M );
|
||||
double icvMinor( double* M, int x, int y );
|
||||
|
||||
int
|
||||
icvGaussMxN( double *A, double *B, int M, int N, double **solutions );
|
||||
|
||||
CvStatus
|
||||
icvGetCoef( double *f1, double *f2, double *a2, double *a1, double *a0 );
|
||||
|
||||
/*================================= Scanlines Functions ================================*/
|
||||
|
||||
CvStatus icvGetCoefficient( CvMatrix3* matrix,
|
||||
CvSize imgSize,
|
||||
int* scanlines_1,
|
||||
int* scanlines_2,
|
||||
int* numlines);
|
||||
|
||||
CvStatus icvGetCoefficientDefault( CvMatrix3* matrix,
|
||||
CvSize imgSize,
|
||||
int* scanlines_1,
|
||||
int* scanlines_2,
|
||||
int* numlines);
|
||||
|
||||
CvStatus icvGetCoefficientStereo( CvMatrix3* matrix,
|
||||
CvSize imgSize,
|
||||
float* l_epipole,
|
||||
float* r_epipole,
|
||||
int* scanlines_1,
|
||||
int* scanlines_2,
|
||||
int* numlines
|
||||
);
|
||||
|
||||
CvStatus icvGetCoefficientOrto( CvMatrix3* matrix,
|
||||
CvSize imgSize,
|
||||
int* scanlines_1,
|
||||
int* scanlines_2,
|
||||
int* numlines);
|
||||
|
||||
|
||||
CvStatus icvGetCrossEpilineFrame( CvSize imgSize,
|
||||
float* epiline,
|
||||
int* x1,
|
||||
int* y1,
|
||||
int* x2,
|
||||
int* y2
|
||||
);
|
||||
|
||||
CvStatus icvBuildScanlineLeftStereo(
|
||||
CvSize imgSize,
|
||||
CvMatrix3* matrix,
|
||||
float* l_epipole,
|
||||
float* l_angle,
|
||||
float l_radius,
|
||||
int* scanlines_1,
|
||||
int* scanlines_2,
|
||||
int* numlines);
|
||||
|
||||
CvStatus icvBuildScanlineRightStereo(
|
||||
CvSize imgSize,
|
||||
CvMatrix3* matrix,
|
||||
float* r_epipole,
|
||||
float* r_angle,
|
||||
float r_radius,
|
||||
int* scanlines_1,
|
||||
int* scanlines_2,
|
||||
int* numlines);
|
||||
|
||||
CvStatus icvGetStartEnd1(
|
||||
CvMatrix3* matrix,
|
||||
CvSize imgSize,
|
||||
float* l_start_end,
|
||||
float* r_start_end );
|
||||
|
||||
CvStatus icvGetStartEnd2(
|
||||
CvMatrix3* matrix,
|
||||
CvSize imgSize,
|
||||
float* l_start_end,
|
||||
float* r_start_end );
|
||||
|
||||
CvStatus icvGetStartEnd3(
|
||||
CvMatrix3* matrix,
|
||||
CvSize imgSize,
|
||||
float* l_start_end,
|
||||
float* r_start_end );
|
||||
|
||||
CvStatus icvGetStartEnd4(
|
||||
CvMatrix3* matrix,
|
||||
CvSize imgSize,
|
||||
float* l_start_end,
|
||||
float* r_start_end );
|
||||
|
||||
CvStatus icvBuildScanlineLeft(
|
||||
CvMatrix3* matrix,
|
||||
CvSize imgSize,
|
||||
int* scanlines_1,
|
||||
int* scanlines_2,
|
||||
float* l_start_end,
|
||||
int* numlines
|
||||
);
|
||||
|
||||
CvStatus icvBuildScanlineRight(
|
||||
CvMatrix3* matrix,
|
||||
CvSize imgSize,
|
||||
int* scanlines_1,
|
||||
int* scanlines_2,
|
||||
float* r_start_end,
|
||||
int* numlines
|
||||
);
|
||||
|
||||
|
||||
/*=================================== LMedS Functions ==================================*/
|
||||
CvStatus icvLMedS7(
|
||||
int* points1,
|
||||
int* points2,
|
||||
CvMatrix3* matrix);
|
||||
|
||||
|
||||
CvStatus icvLMedS( int* points1,
|
||||
int* points2,
|
||||
int numPoints,
|
||||
CvMatrix3* fundamentalMatrix );
|
||||
|
||||
|
||||
/*
|
||||
CvStatus icvFindFundamentalMatrix(
|
||||
int* points1,
|
||||
int* points2,
|
||||
int numpoints,
|
||||
int method,
|
||||
CvMatrix3* matrix);
|
||||
*/
|
||||
void icvChoose7( int* ml, int* mr,
|
||||
int num, int* ml7,
|
||||
int* mr7 );
|
||||
|
||||
double icvMedian( int* ml, int* mr,
|
||||
int num, double* F );
|
||||
|
||||
int icvBoltingPoints( int* ml, int* mr,
|
||||
int num, double* F,
|
||||
double Mj, int* *new_ml,
|
||||
int* *new_mr, int* new_num);
|
||||
|
||||
CvStatus icvPoints8( int* ml, int* mr,
|
||||
int num, double* F );
|
||||
|
||||
CvStatus icvRank2Constraint( double* F );
|
||||
|
||||
CvStatus icvSort( double* array, int length );
|
||||
|
||||
double icvAnalyticPoints8( double* A,
|
||||
int num, double* F );
|
||||
|
||||
int icvSingularValueDecomposition( int M,
|
||||
int N,
|
||||
double* A,
|
||||
double* W,
|
||||
int get_U,
|
||||
double* U,
|
||||
int get_V,
|
||||
double* V
|
||||
);
|
||||
|
||||
|
||||
/*======================================================================================*/
|
||||
#endif/*_CV_VM_H_*/
|
||||
|
||||
@@ -0,0 +1,285 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
#include "_cvaux.h"
|
||||
|
||||
CvCamShiftTracker::CvCamShiftTracker()
|
||||
{
|
||||
int i;
|
||||
|
||||
memset( &m_box, 0, sizeof(m_box));
|
||||
memset( &m_comp, 0, sizeof(m_comp));
|
||||
memset( m_color_planes, 0, sizeof(m_color_planes));
|
||||
m_threshold = 0;
|
||||
|
||||
for( i = 0; i < CV_MAX_DIM; i++ )
|
||||
{
|
||||
m_min_ch_val[i] = 0;
|
||||
m_max_ch_val[i] = 255;
|
||||
m_hist_ranges[i] = m_hist_ranges_data[i];
|
||||
m_hist_ranges[i][0] = 0.f;
|
||||
m_hist_ranges[i][1] = 256.f;
|
||||
}
|
||||
|
||||
m_hist = 0;
|
||||
m_back_project = 0;
|
||||
m_temp = 0;
|
||||
m_mask = 0;
|
||||
}
|
||||
|
||||
|
||||
CvCamShiftTracker::~CvCamShiftTracker()
|
||||
{
|
||||
int i;
|
||||
|
||||
cvReleaseHist( &m_hist );
|
||||
for( i = 0; i < CV_MAX_DIM; i++ )
|
||||
cvReleaseImage( &m_color_planes[i] );
|
||||
cvReleaseImage( &m_back_project );
|
||||
cvReleaseImage( &m_temp );
|
||||
cvReleaseImage( &m_mask );
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
CvCamShiftTracker::color_transform( const IplImage* image )
|
||||
{
|
||||
CvSize size = cvGetSize(image);
|
||||
uchar* color_data = 0, *mask = 0;
|
||||
uchar* planes[CV_MAX_DIM];
|
||||
int x, color_step = 0, plane_step = 0, mask_step;
|
||||
int dims[CV_MAX_DIM];
|
||||
int i, n = get_hist_dims(dims);
|
||||
|
||||
assert( image->nChannels == 3 && m_hist != 0 );
|
||||
|
||||
if( !m_temp || !m_mask || !m_color_planes[0] || !m_color_planes[n-1] || !m_back_project ||
|
||||
m_temp->width != size.width || m_temp->height != size.height ||
|
||||
m_temp->nChannels != 3 )
|
||||
{
|
||||
cvReleaseImage( &m_temp );
|
||||
m_temp = cvCreateImage( size, IPL_DEPTH_8U, 3 );
|
||||
cvReleaseImage( &m_mask );
|
||||
m_mask = cvCreateImage( size, IPL_DEPTH_8U, 1 );
|
||||
cvReleaseImage( &m_back_project );
|
||||
m_back_project = cvCreateImage( size, IPL_DEPTH_8U, 1 );
|
||||
for( i = 0; i < CV_MAX_DIM; i++ )
|
||||
{
|
||||
cvReleaseImage( &m_color_planes[i] );
|
||||
if( i < n )
|
||||
m_color_planes[i] = cvCreateImage( size, IPL_DEPTH_8U, 1 );
|
||||
}
|
||||
}
|
||||
|
||||
cvCvtColor( image, m_temp, CV_BGR2HSV );
|
||||
cvGetRawData( m_temp, &color_data, &color_step, &size );
|
||||
cvGetRawData( m_mask, &mask, &mask_step, &size );
|
||||
|
||||
for( i = 0; i < n; i++ )
|
||||
cvGetRawData( m_color_planes[i], &planes[i], &plane_step, &size );
|
||||
|
||||
for( ; size.height--; color_data += color_step, mask += mask_step )
|
||||
{
|
||||
for( x = 0; x < size.width; x++ )
|
||||
{
|
||||
int val0 = color_data[x*3];
|
||||
int val1 = color_data[x*3+1];
|
||||
int val2 = color_data[x*3+2];
|
||||
if( m_min_ch_val[0] <= val0 && val0 <= m_max_ch_val[0] &&
|
||||
m_min_ch_val[1] <= val1 && val1 <= m_max_ch_val[1] &&
|
||||
m_min_ch_val[2] <= val2 && val2 <= m_max_ch_val[2] )
|
||||
{
|
||||
// hue is written to the 0-th plane, saturation - to the 1-st one,
|
||||
// so 1d histogram will automagically correspond to hue-based tracking,
|
||||
// 2d histogram - to saturation-based tracking.
|
||||
planes[0][x] = (uchar)val0;
|
||||
if( n > 1 )
|
||||
planes[1][x] = (uchar)val1;
|
||||
if( n > 2 )
|
||||
planes[2][x] = (uchar)val2;
|
||||
|
||||
mask[x] = (uchar)255;
|
||||
}
|
||||
else
|
||||
{
|
||||
planes[0][x] = 0;
|
||||
if( n > 1 )
|
||||
planes[1][x] = 0;
|
||||
if( n > 2 )
|
||||
planes[2][x] = 0;
|
||||
mask[x] = 0;
|
||||
}
|
||||
}
|
||||
for( i = 0; i < n; i++ )
|
||||
planes[i] += plane_step;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
bool
|
||||
CvCamShiftTracker::update_histogram( const IplImage* cur_frame )
|
||||
{
|
||||
float max_val = 0;
|
||||
int i, dims;
|
||||
|
||||
if( m_comp.rect.width == 0 || m_comp.rect.height == 0 ||
|
||||
m_hist == 0 )
|
||||
{
|
||||
assert(0);
|
||||
return false;
|
||||
}
|
||||
|
||||
color_transform(cur_frame);
|
||||
|
||||
dims = cvGetDims( m_hist->bins );
|
||||
for( i = 0; i < dims; i++ )
|
||||
cvSetImageROI( m_color_planes[i], m_comp.rect );
|
||||
cvSetImageROI( m_mask, m_comp.rect );
|
||||
|
||||
cvSetHistBinRanges( m_hist, m_hist_ranges, 1 );
|
||||
cvCalcHist( m_color_planes, m_hist, 0, m_mask );
|
||||
|
||||
for( i = 0; i < dims; i++ )
|
||||
cvSetImageROI( m_color_planes[i], m_comp.rect );
|
||||
|
||||
for( i = 0; i < dims; i++ )
|
||||
cvResetImageROI( m_color_planes[i] );
|
||||
cvResetImageROI( m_mask );
|
||||
|
||||
cvGetMinMaxHistValue( m_hist, 0, &max_val );
|
||||
cvScale( m_hist->bins, m_hist->bins, max_val ? 255. / max_val : 0. );
|
||||
|
||||
return max_val != 0;
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
CvCamShiftTracker::reset_histogram()
|
||||
{
|
||||
if( m_hist )
|
||||
cvClearHist( m_hist );
|
||||
}
|
||||
|
||||
|
||||
bool
|
||||
CvCamShiftTracker::track_object( const IplImage* cur_frame )
|
||||
{
|
||||
CvRect rect;
|
||||
CvSize bp_size;
|
||||
|
||||
union
|
||||
{
|
||||
void** arr;
|
||||
IplImage** img;
|
||||
} u;
|
||||
|
||||
if( m_comp.rect.width == 0 || m_comp.rect.height == 0 ||
|
||||
m_hist == 0 )
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
color_transform( cur_frame );
|
||||
u.img = m_color_planes;
|
||||
cvCalcArrBackProject( u.arr, m_back_project, m_hist );
|
||||
cvAnd( m_back_project, m_mask, m_back_project );
|
||||
|
||||
rect = m_comp.rect;
|
||||
bp_size = cvGetSize( m_back_project );
|
||||
if( rect.x < 0 )
|
||||
rect.x = 0;
|
||||
if( rect.x + rect.width > bp_size.width )
|
||||
rect.width = bp_size.width - rect.x;
|
||||
if( rect.y < 0 )
|
||||
rect.y = 0;
|
||||
if( rect.y + rect.height > bp_size.height )
|
||||
rect.height = bp_size.height - rect.y;
|
||||
|
||||
cvCamShift( m_back_project, rect,
|
||||
cvTermCriteria( CV_TERMCRIT_EPS | CV_TERMCRIT_ITER, 10, 1 ),
|
||||
&m_comp, &m_box );
|
||||
|
||||
if( m_comp.rect.width == 0 || m_comp.rect.height == 0 )
|
||||
m_comp.rect = rect; // do not allow tracker to loose the object
|
||||
|
||||
return m_comp.rect.width != 0 && m_comp.rect.height != 0;
|
||||
}
|
||||
|
||||
|
||||
bool
|
||||
CvCamShiftTracker::set_hist_dims( int c_dims, int *dims )
|
||||
{
|
||||
if( (unsigned)(c_dims-1) >= (unsigned)CV_MAX_DIM || dims == 0 )
|
||||
return false;
|
||||
|
||||
if( m_hist )
|
||||
{
|
||||
int dims2[CV_MAX_DIM];
|
||||
int c_dims2 = cvGetDims( m_hist->bins, dims2 );
|
||||
|
||||
if( c_dims2 == c_dims && memcmp( dims, dims2, c_dims*sizeof(dims[0])) == 0 )
|
||||
return true;
|
||||
|
||||
cvReleaseHist( &m_hist );
|
||||
}
|
||||
|
||||
m_hist = cvCreateHist( c_dims, dims, CV_HIST_ARRAY, 0, 0 );
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
bool
|
||||
CvCamShiftTracker::set_hist_bin_range( int channel, int min_val, int max_val )
|
||||
{
|
||||
if( (unsigned)channel >= (unsigned)CV_MAX_DIM ||
|
||||
min_val >= max_val || min_val < 0 || max_val > 256 )
|
||||
{
|
||||
assert(0);
|
||||
return false;
|
||||
}
|
||||
|
||||
m_hist_ranges[channel][0] = (float)min_val;
|
||||
m_hist_ranges[channel][1] = (float)max_val;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/* End of file. */
|
||||
@@ -0,0 +1,586 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2002, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistributions of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistributions in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
#if _MSC_VER >= 1200
|
||||
#pragma warning(disable:4786) // Disable MSVC warnings in the standard library.
|
||||
#pragma warning(disable:4100)
|
||||
#pragma warning(disable:4512)
|
||||
#endif
|
||||
#include <stdio.h>
|
||||
#include <map>
|
||||
#include <algorithm>
|
||||
#if _MSC_VER >= 1200
|
||||
#pragma warning(default:4100)
|
||||
#pragma warning(default:4512)
|
||||
#endif
|
||||
|
||||
#define ARRAY_SIZEOF(a) (sizeof(a)/sizeof((a)[0]))
|
||||
|
||||
static void FillObjectPoints(CvPoint3D32f *obj_points, CvSize etalon_size, float square_size);
|
||||
static void DrawEtalon(IplImage *img, CvPoint2D32f *corners,
|
||||
int corner_count, CvSize etalon_size, int draw_ordered);
|
||||
static void MultMatrix(float rm[4][4], const float m1[4][4], const float m2[4][4]);
|
||||
static void MultVectorMatrix(float rv[4], const float v[4], const float m[4][4]);
|
||||
static CvPoint3D32f ImageCStoWorldCS(const Cv3dTrackerCameraInfo &camera_info, CvPoint2D32f p);
|
||||
static bool intersection(CvPoint3D32f o1, CvPoint3D32f p1,
|
||||
CvPoint3D32f o2, CvPoint3D32f p2,
|
||||
CvPoint3D32f &r1, CvPoint3D32f &r2);
|
||||
|
||||
/////////////////////////////////
|
||||
// cv3dTrackerCalibrateCameras //
|
||||
/////////////////////////////////
|
||||
CV_IMPL CvBool cv3dTrackerCalibrateCameras(int num_cameras,
|
||||
const Cv3dTrackerCameraIntrinsics camera_intrinsics[], // size is num_cameras
|
||||
CvSize etalon_size,
|
||||
float square_size,
|
||||
IplImage *samples[], // size is num_cameras
|
||||
Cv3dTrackerCameraInfo camera_info[]) // size is num_cameras
|
||||
{
|
||||
CV_FUNCNAME("cv3dTrackerCalibrateCameras");
|
||||
const int num_points = etalon_size.width * etalon_size.height;
|
||||
int cameras_done = 0; // the number of cameras whose positions have been determined
|
||||
CvPoint3D32f *object_points = NULL; // real-world coordinates of checkerboard points
|
||||
CvPoint2D32f *points = NULL; // 2d coordinates of checkerboard points as seen by a camera
|
||||
IplImage *gray_img = NULL; // temporary image for color conversion
|
||||
IplImage *tmp_img = NULL; // temporary image used by FindChessboardCornerGuesses
|
||||
int c, i, j;
|
||||
|
||||
if (etalon_size.width < 3 || etalon_size.height < 3)
|
||||
CV_ERROR(CV_StsBadArg, "Chess board size is invalid");
|
||||
|
||||
for (c = 0; c < num_cameras; c++)
|
||||
{
|
||||
// CV_CHECK_IMAGE is not available in the cvaux library
|
||||
// so perform the checks inline.
|
||||
|
||||
//CV_CALL(CV_CHECK_IMAGE(samples[c]));
|
||||
|
||||
if( samples[c] == NULL )
|
||||
CV_ERROR( CV_HeaderIsNull, "Null image" );
|
||||
|
||||
if( samples[c]->dataOrder != IPL_DATA_ORDER_PIXEL && samples[c]->nChannels > 1 )
|
||||
CV_ERROR( CV_BadOrder, "Unsupported image format" );
|
||||
|
||||
if( samples[c]->maskROI != 0 || samples[c]->tileInfo != 0 )
|
||||
CV_ERROR( CV_StsBadArg, "Unsupported image format" );
|
||||
|
||||
if( samples[c]->imageData == 0 )
|
||||
CV_ERROR( CV_BadDataPtr, "Null image data" );
|
||||
|
||||
if( samples[c]->roi &&
|
||||
((samples[c]->roi->xOffset | samples[c]->roi->yOffset
|
||||
| samples[c]->roi->width | samples[c]->roi->height) < 0 ||
|
||||
samples[c]->roi->xOffset + samples[c]->roi->width > samples[c]->width ||
|
||||
samples[c]->roi->yOffset + samples[c]->roi->height > samples[c]->height ||
|
||||
(unsigned) (samples[c]->roi->coi) > (unsigned) (samples[c]->nChannels)))
|
||||
CV_ERROR( CV_BadROISize, "Invalid ROI" );
|
||||
|
||||
// End of CV_CHECK_IMAGE inline expansion
|
||||
|
||||
if (samples[c]->depth != IPL_DEPTH_8U)
|
||||
CV_ERROR(CV_BadDepth, "Channel depth of source image must be 8");
|
||||
|
||||
if (samples[c]->nChannels != 3 && samples[c]->nChannels != 1)
|
||||
CV_ERROR(CV_BadNumChannels, "Source image must have 1 or 3 channels");
|
||||
}
|
||||
|
||||
CV_CALL(object_points = (CvPoint3D32f *)cvAlloc(num_points * sizeof(CvPoint3D32f)));
|
||||
CV_CALL(points = (CvPoint2D32f *)cvAlloc(num_points * sizeof(CvPoint2D32f)));
|
||||
|
||||
// fill in the real-world coordinates of the checkerboard points
|
||||
FillObjectPoints(object_points, etalon_size, square_size);
|
||||
|
||||
for (c = 0; c < num_cameras; c++)
|
||||
{
|
||||
CvSize image_size = cvSize(samples[c]->width, samples[c]->height);
|
||||
IplImage *img;
|
||||
|
||||
// The input samples are not required to all have the same size or color
|
||||
// format. If they have different sizes, the temporary images are
|
||||
// reallocated as necessary.
|
||||
if (samples[c]->nChannels == 3)
|
||||
{
|
||||
// convert to gray
|
||||
if (gray_img == NULL || !CV_ARE_SIZES_EQ(gray_img, samples[c]))
|
||||
{
|
||||
if (gray_img != NULL)
|
||||
cvReleaseImage(&gray_img);
|
||||
CV_CALL(gray_img = cvCreateImage(image_size, IPL_DEPTH_8U, 1));
|
||||
}
|
||||
|
||||
CV_CALL(cvCvtColor(samples[c], gray_img, CV_BGR2GRAY));
|
||||
|
||||
img = gray_img;
|
||||
}
|
||||
else
|
||||
{
|
||||
// no color conversion required
|
||||
img = samples[c];
|
||||
}
|
||||
|
||||
if (tmp_img == NULL || !CV_ARE_SIZES_EQ(tmp_img, samples[c]))
|
||||
{
|
||||
if (tmp_img != NULL)
|
||||
cvReleaseImage(&tmp_img);
|
||||
CV_CALL(tmp_img = cvCreateImage(image_size, IPL_DEPTH_8U, 1));
|
||||
}
|
||||
|
||||
int count = num_points;
|
||||
bool found = cvFindChessBoardCornerGuesses(img, tmp_img, 0,
|
||||
etalon_size, points, &count) != 0;
|
||||
if (count == 0)
|
||||
continue;
|
||||
|
||||
// If found is true, it means all the points were found (count = num_points).
|
||||
// If found is false but count is non-zero, it means that not all points were found.
|
||||
|
||||
cvFindCornerSubPix(img, points, count, cvSize(5,5), cvSize(-1,-1),
|
||||
cvTermCriteria(CV_TERMCRIT_ITER|CV_TERMCRIT_EPS, 10, 0.01f));
|
||||
|
||||
// If the image origin is BL (bottom-left), fix the y coordinates
|
||||
// so they are relative to the true top of the image.
|
||||
if (samples[c]->origin == IPL_ORIGIN_BL)
|
||||
{
|
||||
for (i = 0; i < count; i++)
|
||||
points[i].y = samples[c]->height - 1 - points[i].y;
|
||||
}
|
||||
|
||||
if (found)
|
||||
{
|
||||
// Make sure x coordinates are increasing and y coordinates are decreasing.
|
||||
// (The y coordinate of point (0,0) should be the greatest, because the point
|
||||
// on the checkerboard that is the origin is nearest the bottom of the image.)
|
||||
// This is done after adjusting the y coordinates according to the image origin.
|
||||
if (points[0].x > points[1].x)
|
||||
{
|
||||
// reverse points in each row
|
||||
for (j = 0; j < etalon_size.height; j++)
|
||||
{
|
||||
CvPoint2D32f *row = &points[j*etalon_size.width];
|
||||
for (i = 0; i < etalon_size.width/2; i++)
|
||||
std::swap(row[i], row[etalon_size.width-i-1]);
|
||||
}
|
||||
}
|
||||
|
||||
if (points[0].y < points[etalon_size.width].y)
|
||||
{
|
||||
// reverse points in each column
|
||||
for (i = 0; i < etalon_size.width; i++)
|
||||
{
|
||||
for (j = 0; j < etalon_size.height/2; j++)
|
||||
std::swap(points[i+j*etalon_size.width],
|
||||
points[i+(etalon_size.height-j-1)*etalon_size.width]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
DrawEtalon(samples[c], points, count, etalon_size, found);
|
||||
|
||||
if (!found)
|
||||
continue;
|
||||
|
||||
float rotVect[3];
|
||||
float rotMatr[9];
|
||||
float transVect[3];
|
||||
|
||||
cvFindExtrinsicCameraParams(count,
|
||||
image_size,
|
||||
points,
|
||||
object_points,
|
||||
const_cast<float *>(camera_intrinsics[c].focal_length),
|
||||
camera_intrinsics[c].principal_point,
|
||||
const_cast<float *>(camera_intrinsics[c].distortion),
|
||||
rotVect,
|
||||
transVect);
|
||||
|
||||
// Check result against an arbitrary limit to eliminate impossible values.
|
||||
// (If the chess board were truly that far away, the camera wouldn't be able to
|
||||
// see the squares.)
|
||||
if (transVect[0] > 1000*square_size
|
||||
|| transVect[1] > 1000*square_size
|
||||
|| transVect[2] > 1000*square_size)
|
||||
{
|
||||
// ignore impossible results
|
||||
continue;
|
||||
}
|
||||
|
||||
CvMat rotMatrDescr = cvMat(3, 3, CV_32FC1, rotMatr);
|
||||
CvMat rotVectDescr = cvMat(3, 1, CV_32FC1, rotVect);
|
||||
|
||||
/* Calc rotation matrix by Rodrigues Transform */
|
||||
cvRodrigues2( &rotVectDescr, &rotMatrDescr );
|
||||
|
||||
//combine the two transformations into one matrix
|
||||
//order is important! rotations are not commutative
|
||||
float tmat[4][4] = { { 1.f, 0.f, 0.f, 0.f },
|
||||
{ 0.f, 1.f, 0.f, 0.f },
|
||||
{ 0.f, 0.f, 1.f, 0.f },
|
||||
{ transVect[0], transVect[1], transVect[2], 1.f } };
|
||||
|
||||
float rmat[4][4] = { { rotMatr[0], rotMatr[1], rotMatr[2], 0.f },
|
||||
{ rotMatr[3], rotMatr[4], rotMatr[5], 0.f },
|
||||
{ rotMatr[6], rotMatr[7], rotMatr[8], 0.f },
|
||||
{ 0.f, 0.f, 0.f, 1.f } };
|
||||
|
||||
|
||||
MultMatrix(camera_info[c].mat, tmat, rmat);
|
||||
|
||||
// change the transformation of the cameras to put them in the world coordinate
|
||||
// system we want to work with.
|
||||
|
||||
// Start with an identity matrix; then fill in the values to accomplish
|
||||
// the desired transformation.
|
||||
float smat[4][4] = { { 1.f, 0.f, 0.f, 0.f },
|
||||
{ 0.f, 1.f, 0.f, 0.f },
|
||||
{ 0.f, 0.f, 1.f, 0.f },
|
||||
{ 0.f, 0.f, 0.f, 1.f } };
|
||||
|
||||
// First, reflect through the origin by inverting all three axes.
|
||||
smat[0][0] = -1.f;
|
||||
smat[1][1] = -1.f;
|
||||
smat[2][2] = -1.f;
|
||||
MultMatrix(tmat, camera_info[c].mat, smat);
|
||||
|
||||
// Scale x and y coordinates by the focal length (allowing for non-square pixels
|
||||
// and/or non-symmetrical lenses).
|
||||
smat[0][0] = 1.0f / camera_intrinsics[c].focal_length[0];
|
||||
smat[1][1] = 1.0f / camera_intrinsics[c].focal_length[1];
|
||||
smat[2][2] = 1.0f;
|
||||
MultMatrix(camera_info[c].mat, smat, tmat);
|
||||
|
||||
camera_info[c].principal_point = camera_intrinsics[c].principal_point;
|
||||
camera_info[c].valid = true;
|
||||
|
||||
cameras_done++;
|
||||
}
|
||||
|
||||
exit:
|
||||
cvReleaseImage(&gray_img);
|
||||
cvReleaseImage(&tmp_img);
|
||||
cvFree(&object_points);
|
||||
cvFree(&points);
|
||||
|
||||
return cameras_done == num_cameras;
|
||||
}
|
||||
|
||||
// fill in the real-world coordinates of the checkerboard points
|
||||
static void FillObjectPoints(CvPoint3D32f *obj_points, CvSize etalon_size, float square_size)
|
||||
{
|
||||
int x, y, i;
|
||||
|
||||
for (y = 0, i = 0; y < etalon_size.height; y++)
|
||||
{
|
||||
for (x = 0; x < etalon_size.width; x++, i++)
|
||||
{
|
||||
obj_points[i].x = square_size * x;
|
||||
obj_points[i].y = square_size * y;
|
||||
obj_points[i].z = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Mark the points found on the input image
|
||||
// The marks are drawn multi-colored if all the points were found.
|
||||
static void DrawEtalon(IplImage *img, CvPoint2D32f *corners,
|
||||
int corner_count, CvSize etalon_size, int draw_ordered)
|
||||
{
|
||||
const int r = 4;
|
||||
int i;
|
||||
int x, y;
|
||||
CvPoint prev_pt = { 0, 0 };
|
||||
static const CvScalar rgb_colors[] = {
|
||||
{{0,0,255}},
|
||||
{{0,128,255}},
|
||||
{{0,200,200}},
|
||||
{{0,255,0}},
|
||||
{{200,200,0}},
|
||||
{{255,0,0}},
|
||||
{{255,0,255}} };
|
||||
static const CvScalar gray_colors[] = {
|
||||
{{80}}, {{120}}, {{160}}, {{200}}, {{100}}, {{140}}, {{180}}
|
||||
};
|
||||
const CvScalar* colors = img->nChannels == 3 ? rgb_colors : gray_colors;
|
||||
|
||||
CvScalar color = colors[0];
|
||||
for (y = 0, i = 0; y < etalon_size.height; y++)
|
||||
{
|
||||
if (draw_ordered)
|
||||
color = colors[y % ARRAY_SIZEOF(rgb_colors)];
|
||||
|
||||
for (x = 0; x < etalon_size.width && i < corner_count; x++, i++)
|
||||
{
|
||||
CvPoint pt;
|
||||
pt.x = cvRound(corners[i].x);
|
||||
pt.y = cvRound(corners[i].y);
|
||||
if (img->origin == IPL_ORIGIN_BL)
|
||||
pt.y = img->height - 1 - pt.y;
|
||||
|
||||
if (draw_ordered)
|
||||
{
|
||||
if (i != 0)
|
||||
cvLine(img, prev_pt, pt, color, 1, CV_AA);
|
||||
prev_pt = pt;
|
||||
}
|
||||
|
||||
cvLine( img, cvPoint(pt.x - r, pt.y - r),
|
||||
cvPoint(pt.x + r, pt.y + r), color, 1, CV_AA );
|
||||
cvLine( img, cvPoint(pt.x - r, pt.y + r),
|
||||
cvPoint(pt.x + r, pt.y - r), color, 1, CV_AA );
|
||||
cvCircle( img, pt, r+1, color, 1, CV_AA );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Find the midpoint of the line segment between two points.
|
||||
static CvPoint3D32f midpoint(const CvPoint3D32f &p1, const CvPoint3D32f &p2)
|
||||
{
|
||||
return cvPoint3D32f((p1.x+p2.x)/2, (p1.y+p2.y)/2, (p1.z+p2.z)/2);
|
||||
}
|
||||
|
||||
static void operator +=(CvPoint3D32f &p1, const CvPoint3D32f &p2)
|
||||
{
|
||||
p1.x += p2.x;
|
||||
p1.y += p2.y;
|
||||
p1.z += p2.z;
|
||||
}
|
||||
|
||||
static CvPoint3D32f operator /(const CvPoint3D32f &p, int d)
|
||||
{
|
||||
return cvPoint3D32f(p.x/d, p.y/d, p.z/d);
|
||||
}
|
||||
|
||||
static const Cv3dTracker2dTrackedObject *find(const Cv3dTracker2dTrackedObject v[], int num_objects, int id)
|
||||
{
|
||||
for (int i = 0; i < num_objects; i++)
|
||||
{
|
||||
if (v[i].id == id)
|
||||
return &v[i];
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
#define CAMERA_POS(c) (cvPoint3D32f((c).mat[3][0], (c).mat[3][1], (c).mat[3][2]))
|
||||
|
||||
//////////////////////////////
|
||||
// cv3dTrackerLocateObjects //
|
||||
//////////////////////////////
|
||||
CV_IMPL int cv3dTrackerLocateObjects(int num_cameras, int num_objects,
|
||||
const Cv3dTrackerCameraInfo camera_info[], // size is num_cameras
|
||||
const Cv3dTracker2dTrackedObject tracking_info[], // size is num_objects*num_cameras
|
||||
Cv3dTrackerTrackedObject tracked_objects[]) // size is num_objects
|
||||
{
|
||||
/*CV_FUNCNAME("cv3dTrackerLocateObjects");*/
|
||||
int found_objects = 0;
|
||||
|
||||
// count how many cameras could see each object
|
||||
std::map<int, int> count;
|
||||
for (int c = 0; c < num_cameras; c++)
|
||||
{
|
||||
if (!camera_info[c].valid)
|
||||
continue;
|
||||
|
||||
for (int i = 0; i < num_objects; i++)
|
||||
{
|
||||
const Cv3dTracker2dTrackedObject *o = &tracking_info[c*num_objects+i];
|
||||
if (o->id != -1)
|
||||
count[o->id]++;
|
||||
}
|
||||
}
|
||||
|
||||
// process each object that was seen by at least two cameras
|
||||
for (std::map<int, int>::iterator i = count.begin(); i != count.end(); i++)
|
||||
{
|
||||
if (i->second < 2)
|
||||
continue; // ignore object seen by only one camera
|
||||
int id = i->first;
|
||||
|
||||
// find an approximation of the objects location for each pair of cameras that
|
||||
// could see this object, and average them
|
||||
CvPoint3D32f total = cvPoint3D32f(0, 0, 0);
|
||||
int weight = 0;
|
||||
|
||||
for (int c1 = 0; c1 < num_cameras-1; c1++)
|
||||
{
|
||||
if (!camera_info[c1].valid)
|
||||
continue;
|
||||
|
||||
const Cv3dTracker2dTrackedObject *o1 = find(&tracking_info[c1*num_objects],
|
||||
num_objects, id);
|
||||
if (o1 == NULL)
|
||||
continue; // this camera didn't see this object
|
||||
|
||||
CvPoint3D32f p1a = CAMERA_POS(camera_info[c1]);
|
||||
CvPoint3D32f p1b = ImageCStoWorldCS(camera_info[c1], o1->p);
|
||||
|
||||
for (int c2 = c1 + 1; c2 < num_cameras; c2++)
|
||||
{
|
||||
if (!camera_info[c2].valid)
|
||||
continue;
|
||||
|
||||
const Cv3dTracker2dTrackedObject *o2 = find(&tracking_info[c2*num_objects],
|
||||
num_objects, id);
|
||||
if (o2 == NULL)
|
||||
continue; // this camera didn't see this object
|
||||
|
||||
CvPoint3D32f p2a = CAMERA_POS(camera_info[c2]);
|
||||
CvPoint3D32f p2b = ImageCStoWorldCS(camera_info[c2], o2->p);
|
||||
|
||||
// these variables are initialized simply to avoid erroneous error messages
|
||||
// from the compiler
|
||||
CvPoint3D32f r1 = cvPoint3D32f(0, 0, 0);
|
||||
CvPoint3D32f r2 = cvPoint3D32f(0, 0, 0);
|
||||
|
||||
// find the intersection of the two lines (or the points of closest
|
||||
// approach, if they don't intersect)
|
||||
if (!intersection(p1a, p1b, p2a, p2b, r1, r2))
|
||||
continue;
|
||||
|
||||
total += midpoint(r1, r2);
|
||||
weight++;
|
||||
}
|
||||
}
|
||||
|
||||
CvPoint3D32f center = total/weight;
|
||||
tracked_objects[found_objects++] = cv3dTrackerTrackedObject(id, center);
|
||||
}
|
||||
|
||||
return found_objects;
|
||||
}
|
||||
|
||||
#define EPS 1e-9
|
||||
|
||||
// Compute the determinant of the 3x3 matrix represented by 3 row vectors.
|
||||
static inline double det(CvPoint3D32f v1, CvPoint3D32f v2, CvPoint3D32f v3)
|
||||
{
|
||||
return v1.x*v2.y*v3.z + v1.z*v2.x*v3.y + v1.y*v2.z*v3.x
|
||||
- v1.z*v2.y*v3.x - v1.x*v2.z*v3.y - v1.y*v2.x*v3.z;
|
||||
}
|
||||
|
||||
static CvPoint3D32f operator +(CvPoint3D32f a, CvPoint3D32f b)
|
||||
{
|
||||
return cvPoint3D32f(a.x + b.x, a.y + b.y, a.z + b.z);
|
||||
}
|
||||
|
||||
static CvPoint3D32f operator -(CvPoint3D32f a, CvPoint3D32f b)
|
||||
{
|
||||
return cvPoint3D32f(a.x - b.x, a.y - b.y, a.z - b.z);
|
||||
}
|
||||
|
||||
static CvPoint3D32f operator *(CvPoint3D32f v, double f)
|
||||
{
|
||||
return cvPoint3D32f(f*v.x, f*v.y, f*v.z);
|
||||
}
|
||||
|
||||
|
||||
// Find the intersection of two lines, or if they don't intersect,
|
||||
// the points of closest approach.
|
||||
// The lines are defined by (o1,p1) and (o2, p2).
|
||||
// If they intersect, r1 and r2 will be the same.
|
||||
// Returns false on error.
|
||||
static bool intersection(CvPoint3D32f o1, CvPoint3D32f p1,
|
||||
CvPoint3D32f o2, CvPoint3D32f p2,
|
||||
CvPoint3D32f &r1, CvPoint3D32f &r2)
|
||||
{
|
||||
CvPoint3D32f x = o2 - o1;
|
||||
CvPoint3D32f d1 = p1 - o1;
|
||||
CvPoint3D32f d2 = p2 - o2;
|
||||
|
||||
CvPoint3D32f cross = cvPoint3D32f(d1.y*d2.z - d1.z*d2.y,
|
||||
d1.z*d2.x - d1.x*d2.z,
|
||||
d1.x*d2.y - d1.y*d2.x);
|
||||
double den = cross.x*cross.x + cross.y*cross.y + cross.z*cross.z;
|
||||
|
||||
if (den < EPS)
|
||||
return false;
|
||||
|
||||
double t1 = det(x, d2, cross) / den;
|
||||
double t2 = det(x, d1, cross) / den;
|
||||
|
||||
r1 = o1 + d1 * t1;
|
||||
r2 = o2 + d2 * t2;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
// Convert from image to camera space by transforming point p in
|
||||
// the image plane by the camera matrix.
|
||||
static CvPoint3D32f ImageCStoWorldCS(const Cv3dTrackerCameraInfo &camera_info, CvPoint2D32f p)
|
||||
{
|
||||
float tp[4];
|
||||
tp[0] = (float)p.x - camera_info.principal_point.x;
|
||||
tp[1] = (float)p.y - camera_info.principal_point.y;
|
||||
tp[2] = 1.f;
|
||||
tp[3] = 1.f;
|
||||
|
||||
float tr[4];
|
||||
//multiply tp by mat to get tr
|
||||
MultVectorMatrix(tr, tp, camera_info.mat);
|
||||
|
||||
return cvPoint3D32f(tr[0]/tr[3], tr[1]/tr[3], tr[2]/tr[3]);
|
||||
}
|
||||
|
||||
// Multiply affine transformation m1 by the affine transformation m2 and
|
||||
// return the result in rm.
|
||||
static void MultMatrix(float rm[4][4], const float m1[4][4], const float m2[4][4])
|
||||
{
|
||||
for (int i=0; i<=3; i++)
|
||||
for (int j=0; j<=3; j++)
|
||||
{
|
||||
rm[i][j]= 0.0;
|
||||
for (int k=0; k <= 3; k++)
|
||||
rm[i][j] += m1[i][k]*m2[k][j];
|
||||
}
|
||||
}
|
||||
|
||||
// Multiply the vector v by the affine transformation matrix m and return the
|
||||
// result in rv.
|
||||
void MultVectorMatrix(float rv[4], const float v[4], const float m[4][4])
|
||||
{
|
||||
for (int i=0; i<=3; i++)
|
||||
{
|
||||
rv[i] = 0.f;
|
||||
for (int j=0;j<=3;j++)
|
||||
rv[i] += v[j] * m[j][i];
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,44 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
/* End of file. */
|
||||
522
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/src/cvaux.dsp
Normal file
522
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/src/cvaux.dsp
Normal file
@@ -0,0 +1,522 @@
|
||||
# Microsoft Developer Studio Project File - Name="cvaux" - Package Owner=<4>
|
||||
# Microsoft Developer Studio Generated Build File, Format Version 6.00
|
||||
# ** DO NOT EDIT **
|
||||
|
||||
# TARGTYPE "Win32 (x86) Dynamic-Link Library" 0x0102
|
||||
|
||||
CFG=cvaux - Win32 Debug64 Itanium
|
||||
!MESSAGE This is not a valid makefile. To build this project using NMAKE,
|
||||
!MESSAGE use the Export Makefile command and run
|
||||
!MESSAGE
|
||||
!MESSAGE NMAKE /f "cvaux.mak".
|
||||
!MESSAGE
|
||||
!MESSAGE You can specify a configuration when running NMAKE
|
||||
!MESSAGE by defining the macro CFG on the command line. For example:
|
||||
!MESSAGE
|
||||
!MESSAGE NMAKE /f "cvaux.mak" CFG="cvaux - Win32 Debug64 Itanium"
|
||||
!MESSAGE
|
||||
!MESSAGE Possible choices for configuration are:
|
||||
!MESSAGE
|
||||
!MESSAGE "cvaux - Win32 Release" (based on "Win32 (x86) Dynamic-Link Library")
|
||||
!MESSAGE "cvaux - Win32 Debug" (based on "Win32 (x86) Dynamic-Link Library")
|
||||
!MESSAGE "cvaux - Win32 Release64" (based on "Win32 (x86) Dynamic-Link Library")
|
||||
!MESSAGE "cvaux - Win32 Debug64" (based on "Win32 (x86) Dynamic-Link Library")
|
||||
!MESSAGE "cvaux - Win32 Release64 Itanium" (based on "Win32 (x86) Dynamic-Link Library")
|
||||
!MESSAGE "cvaux - Win32 Debug64 Itanium" (based on "Win32 (x86) Dynamic-Link Library")
|
||||
!MESSAGE
|
||||
|
||||
# Begin Project
|
||||
# PROP AllowPerConfigDependencies 0
|
||||
# PROP Scc_ProjName ""
|
||||
# PROP Scc_LocalPath ""
|
||||
CPP=xicl6.exe
|
||||
MTL=midl.exe
|
||||
RSC=rc.exe
|
||||
|
||||
!IF "$(CFG)" == "cvaux - Win32 Release"
|
||||
|
||||
# PROP BASE Use_MFC 0
|
||||
# PROP BASE Use_Debug_Libraries 0
|
||||
# PROP BASE Output_Dir "Release"
|
||||
# PROP BASE Intermediate_Dir "Release"
|
||||
# PROP BASE Target_Dir ""
|
||||
# PROP Use_MFC 0
|
||||
# PROP Use_Debug_Libraries 0
|
||||
# PROP Output_Dir "..\..\_temp\cvaux_Rls"
|
||||
# PROP Intermediate_Dir "..\..\_temp\cvaux_Rls"
|
||||
# PROP Ignore_Export_Lib 0
|
||||
# PROP Target_Dir ""
|
||||
LIB32=link.exe -lib
|
||||
# ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "cvaux_EXPORTS" /Yu"stdafx.h" /FD /c
|
||||
# ADD CPP /nologo /MD /W4 /Zi /O2 /Ob2 /I "." /I ".." /I "../include" /I "../../cxcore/include" /I "../../cv/include" /I "../../cv/src" /D "NDEBUG" /D "CVAPI_EXPORTS" /D "WIN32" /D "_WINDOWS" /Yu"_cvaux.h" /FD /Zm200 /c
|
||||
# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32
|
||||
# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32
|
||||
# ADD BASE RSC /l 0x419 /d "NDEBUG"
|
||||
# ADD RSC /l 0x419 /d "NDEBUG"
|
||||
BSC32=bscmake.exe
|
||||
# ADD BASE BSC32 /nologo
|
||||
# ADD BSC32 /nologo
|
||||
LINK32=xilink6.exe
|
||||
# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386
|
||||
# ADD LINK32 cv.lib cxcore.lib kernel32.lib user32.lib gdi32.lib /nologo /dll /pdb:"..\..\bin/cvaux100.pdb" /debug /machine:I386 /nodefaultlib:"libmmd.lib" /out:"..\..\bin/cvaux100.dll" /implib:"..\..\lib/cvaux.lib" /libpath:"..\..\lib"
|
||||
# SUBTRACT LINK32 /profile /pdb:none
|
||||
|
||||
!ELSEIF "$(CFG)" == "cvaux - Win32 Debug"
|
||||
|
||||
# PROP BASE Use_MFC 0
|
||||
# PROP BASE Use_Debug_Libraries 1
|
||||
# PROP BASE Output_Dir "Debug"
|
||||
# PROP BASE Intermediate_Dir "Debug"
|
||||
# PROP BASE Target_Dir ""
|
||||
# PROP Use_MFC 0
|
||||
# PROP Use_Debug_Libraries 1
|
||||
# PROP Output_Dir "..\..\_temp\cvaux_Dbg"
|
||||
# PROP Intermediate_Dir "..\..\_temp\cvaux_Dbg"
|
||||
# PROP Ignore_Export_Lib 0
|
||||
# PROP Target_Dir ""
|
||||
LIB32=link.exe -lib
|
||||
# ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "cvaux_EXPORTS" /Yu"stdafx.h" /FD /GZ /c
|
||||
# ADD CPP /nologo /MDd /W4 /Gm /Zi /Od /I "." /I ".." /I "../include" /I "../../cxcore/include" /I "../../cv/include" /I "../../cv/src" /D "_DEBUG" /D "CVAPI_EXPORTS" /D "WIN32" /D "_WINDOWS" /FR /Yu"_cvaux.h" /FD /GZ /Zm200 /c
|
||||
# SUBTRACT CPP /X
|
||||
# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32
|
||||
# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32
|
||||
# ADD BASE RSC /l 0x419 /d "_DEBUG"
|
||||
# ADD RSC /l 0x419 /d "_DEBUG"
|
||||
BSC32=bscmake.exe
|
||||
# ADD BASE BSC32 /nologo
|
||||
# ADD BSC32 /nologo
|
||||
LINK32=xilink6.exe
|
||||
# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept
|
||||
# ADD LINK32 cvd.lib cxcored.lib kernel32.lib user32.lib gdi32.lib /nologo /dll /pdb:"..\..\bin/cvaux100d.pdb" /debug /machine:I386 /nodefaultlib:"libmmdd.lib" /out:"..\..\bin/cvaux100d.dll" /implib:"..\..\lib/cvauxd.lib" /pdbtype:sept /libpath:"..\..\lib"
|
||||
# SUBTRACT LINK32 /pdb:none
|
||||
|
||||
!ELSEIF "$(CFG)" == "cvaux - Win32 Release64"
|
||||
|
||||
# PROP BASE Use_MFC 0
|
||||
# PROP BASE Use_Debug_Libraries 0
|
||||
# PROP BASE Output_Dir "cvaux___Win32_Release64"
|
||||
# PROP BASE Intermediate_Dir "cvaux___Win32_Release64"
|
||||
# PROP BASE Ignore_Export_Lib 0
|
||||
# PROP BASE Target_Dir ""
|
||||
# PROP Use_MFC 0
|
||||
# PROP Use_Debug_Libraries 0
|
||||
# PROP Output_Dir "..\..\_temp\cvaux_Rls64"
|
||||
# PROP Intermediate_Dir "..\..\_temp\cvaux_Rls64"
|
||||
# PROP Ignore_Export_Lib 0
|
||||
# PROP Target_Dir ""
|
||||
LIB32=link.exe -lib
|
||||
# ADD BASE CPP /nologo /MD /W4 /Zi /O2 /Ob2 /I "../include" /I "../../cxcore/include" /I "../../cv/include" /I "../../cv/src" /D "NDEBUG" /D "CVAPI_EXPORTS" /D "WIN32" /D "_WINDOWS" /Yu"_cvaux.h" /FD /Zm200 /c
|
||||
# ADD CPP /nologo /MD /W4 /Zi /O2 /Ob2 /I "." /I ".." /I "../include" /I "../../cxcore/include" /I "../../cv/include" /I "../../cv/src" /D "CVAPI_EXPORTS" /D "_WINDOWS" /D "NDEBUG" /D "WIN32" /D "WIN64" /D "EM64T" /Yu"_cvaux.h" /FD /Zm200 /c
|
||||
# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32
|
||||
# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32
|
||||
# ADD BASE RSC /l 0x419 /d "NDEBUG"
|
||||
# ADD RSC /l 0x419 /d "NDEBUG"
|
||||
BSC32=bscmake.exe
|
||||
# ADD BASE BSC32 /nologo
|
||||
# ADD BSC32 /nologo
|
||||
LINK32=xilink6.exe
|
||||
# ADD BASE LINK32 cv.lib cxcore.lib kernel32.lib user32.lib gdi32.lib /nologo /dll /debug /machine:IX86 /nodefaultlib:"libmmd.lib" /out:"..\..\bin/cvaux100.dll" /implib:"..\..\lib/cvaux.lib" /libpath:"..\..\lib" /machine:AMD64
|
||||
# SUBTRACT BASE LINK32 /profile
|
||||
# ADD LINK32 cv_64.lib cxcore_64.lib kernel32.lib user32.lib gdi32.lib /nologo /dll /debug /machine:IX86 /nodefaultlib:"libmmd.lib" /out:"..\..\bin/cvaux100_64.dll" /implib:"..\..\lib/cvaux_64.lib" /libpath:"..\..\lib" /machine:AMD64
|
||||
# SUBTRACT LINK32 /pdb:none
|
||||
|
||||
!ELSEIF "$(CFG)" == "cvaux - Win32 Debug64"
|
||||
|
||||
# PROP BASE Use_MFC 0
|
||||
# PROP BASE Use_Debug_Libraries 1
|
||||
# PROP BASE Output_Dir "cvaux___Win32_Debug64"
|
||||
# PROP BASE Intermediate_Dir "cvaux___Win32_Debug64"
|
||||
# PROP BASE Ignore_Export_Lib 0
|
||||
# PROP BASE Target_Dir ""
|
||||
# PROP Use_MFC 0
|
||||
# PROP Use_Debug_Libraries 1
|
||||
# PROP Output_Dir "..\..\_temp\cvaux_Dbg64"
|
||||
# PROP Intermediate_Dir "..\..\_temp\cvaux_Dbg64"
|
||||
# PROP Ignore_Export_Lib 0
|
||||
# PROP Target_Dir ""
|
||||
LIB32=link.exe -lib
|
||||
# ADD BASE CPP /nologo /MDd /W4 /Gm /Zi /Od /I "../include" /I "../../cxcore/include" /I "../../cv/include" /I "../../cv/src" /D "_DEBUG" /D "CVAPI_EXPORTS" /D "WIN32" /D "_WINDOWS" /FR /Yu"_cvaux.h" /FD /GZ /Zm200 /c
|
||||
# SUBTRACT BASE CPP /X
|
||||
# ADD CPP /nologo /MDd /W4 /Gm /Zi /Od /I "." /I ".." /I "../include" /I "../../cxcore/include" /I "../../cv/include" /I "../../cv/src" /D "CVAPI_EXPORTS" /D "_WINDOWS" /D "_DEBUG" /D "WIN32" /D "WIN64" /D "EM64T" /FR /Yu"_cvaux.h" /FD /Zm200 /Wp64 /c
|
||||
# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32
|
||||
# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32
|
||||
# ADD BASE RSC /l 0x419 /d "_DEBUG"
|
||||
# ADD RSC /l 0x419 /d "_DEBUG"
|
||||
BSC32=bscmake.exe
|
||||
# ADD BASE BSC32 /nologo
|
||||
# ADD BSC32 /nologo
|
||||
LINK32=xilink6.exe
|
||||
# ADD BASE LINK32 cvd.lib cxcored.lib kernel32.lib user32.lib gdi32.lib /nologo /dll /debug /machine:IX86 /nodefaultlib:"libmmdd.lib" /out:"..\..\bin/cvaux100d.dll" /implib:"..\..\lib/cvauxd.lib" /pdbtype:sept /libpath:"..\..\lib" /machine:AMD64
|
||||
# SUBTRACT BASE LINK32 /pdb:none
|
||||
# ADD LINK32 cvd_64.lib cxcored_64.lib kernel32.lib user32.lib gdi32.lib /nologo /dll /pdb:"..\..\bin/cvaux100d_64.pdb" /debug /machine:IX86 /nodefaultlib:"libmmdd.lib" /out:"..\..\bin/cvaux100d_64.dll" /implib:"..\..\lib/cvauxd_64.lib" /pdbtype:sept /libpath:"..\..\lib" /machine:AMD64
|
||||
# SUBTRACT LINK32 /pdb:none
|
||||
|
||||
!ELSEIF "$(CFG)" == "cvaux - Win32 Release64 Itanium"
|
||||
|
||||
# PROP BASE Use_MFC 0
|
||||
# PROP BASE Use_Debug_Libraries 0
|
||||
# PROP BASE Output_Dir "cvaux___Win32_Release64_Itanium"
|
||||
# PROP BASE Intermediate_Dir "cvaux___Win32_Release64_Itanium"
|
||||
# PROP BASE Ignore_Export_Lib 0
|
||||
# PROP BASE Target_Dir ""
|
||||
# PROP Use_MFC 0
|
||||
# PROP Use_Debug_Libraries 0
|
||||
# PROP Output_Dir "..\..\_temp\cvaux_RlsI7"
|
||||
# PROP Intermediate_Dir "..\..\_temp\cvaux_RlsI7"
|
||||
# PROP Ignore_Export_Lib 0
|
||||
# PROP Target_Dir ""
|
||||
LIB32=link.exe -lib
|
||||
# ADD BASE CPP /nologo /MD /W4 /Zi /O2 /Ob2 /I "../include" /I "../../cxcore/include" /I "../../cv/include" /I "../../cv/src" /D "CVAPI_EXPORTS" /D "_WINDOWS" /D "NDEBUG" /D "WIN32" /D "WIN64" /D "EM64T" /Yu"_cvaux.h" /FD /Zm200 /c
|
||||
# ADD CPP /nologo /MD /w /W0 /Zi /O2 /Ob2 /I "." /I ".." /I "../include" /I "../../cxcore/include" /I "../../cv/include" /I "../../cv/src" /D "CVAPI_EXPORTS" /D "_WINDOWS" /D "NDEBUG" /D "WIN32" /D "WIN64" /Yu"_cvaux.h" /FD /Zm200 /c
|
||||
# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32
|
||||
# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32
|
||||
# ADD BASE RSC /l 0x419 /d "NDEBUG"
|
||||
# ADD RSC /l 0x419 /d "NDEBUG"
|
||||
BSC32=bscmake.exe
|
||||
# ADD BASE BSC32 /nologo
|
||||
# ADD BSC32 /nologo
|
||||
LINK32=xilink6.exe
|
||||
# ADD BASE LINK32 cv_i7.lib cxcore_i7.lib kernel32.lib user32.lib gdi32.lib /nologo /dll /debug /machine:IX86 /nodefaultlib:"libmmd.lib" /out:"..\..\bin/cvaux100_i7.dll" /implib:"..\..\lib/cvaux_i7.lib" /libpath:"..\..\lib" /machine:IA64
|
||||
# SUBTRACT BASE LINK32 /pdb:none
|
||||
# ADD LINK32 cv_i7.lib cxcore_i7.lib kernel32.lib user32.lib gdi32.lib /nologo /dll /debug /machine:IX86 /out:"..\..\bin/cvaux100_i7.dll" /implib:"..\..\lib/cvaux_i7.lib" /libpath:"..\..\lib" /machine:IA64
|
||||
# SUBTRACT LINK32 /pdb:none
|
||||
|
||||
!ELSEIF "$(CFG)" == "cvaux - Win32 Debug64 Itanium"
|
||||
|
||||
# PROP BASE Use_MFC 0
|
||||
# PROP BASE Use_Debug_Libraries 1
|
||||
# PROP BASE Output_Dir "cvaux___Win32_Debug64_Itanium"
|
||||
# PROP BASE Intermediate_Dir "cvaux___Win32_Debug64_Itanium"
|
||||
# PROP BASE Ignore_Export_Lib 0
|
||||
# PROP BASE Target_Dir ""
|
||||
# PROP Use_MFC 0
|
||||
# PROP Use_Debug_Libraries 1
|
||||
# PROP Output_Dir "..\..\_temp\cvaux_DbgI7"
|
||||
# PROP Intermediate_Dir "..\..\_temp\cvaux_DbgI7"
|
||||
# PROP Ignore_Export_Lib 0
|
||||
# PROP Target_Dir ""
|
||||
LIB32=link.exe -lib
|
||||
# ADD BASE CPP /nologo /MDd /W4 /Gm /Zi /Od /I "../include" /I "../../cxcore/include" /I "../../cv/include" /I "../../cv/src" /D "CVAPI_EXPORTS" /D "_WINDOWS" /D "_DEBUG" /D "WIN32" /D "WIN64" /D "EM64T" /FR /Yu"_cvaux.h" /FD /Zm200 /Wp64 /c
|
||||
# ADD CPP /nologo /MDd /W3 /Gm /Zi /Od /I "." /I ".." /I "../include" /I "../../cxcore/include" /I "../../cv/include" /I "../../cv/src" /D "CVAPI_EXPORTS" /D "_WINDOWS" /D "_DEBUG" /D "WIN32" /D "WIN64" /FR /Yu"_cvaux.h" /FD /Zm200 /Qwd167 /c
|
||||
# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32
|
||||
# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32
|
||||
# ADD BASE RSC /l 0x419 /d "_DEBUG"
|
||||
# ADD RSC /l 0x419 /d "_DEBUG"
|
||||
BSC32=bscmake.exe
|
||||
# ADD BASE BSC32 /nologo
|
||||
# ADD BSC32 /nologo
|
||||
LINK32=xilink6.exe
|
||||
# ADD BASE LINK32 cvd_i7.lib cxcored_i7.lib kernel32.lib user32.lib gdi32.lib /nologo /dll /pdb:"..\..\bin/cvaux100d_i7.pdb" /debug /machine:IX86 /nodefaultlib:"libmmdd.lib" /out:"..\..\bin/cvaux100d_i7.dll" /implib:"..\..\lib/cvauxd_i7.lib" /pdbtype:sept /libpath:"..\..\lib" /machine:IA64
|
||||
# SUBTRACT BASE LINK32 /pdb:none
|
||||
# ADD LINK32 cvd_i7.lib cxcored_i7.lib kernel32.lib user32.lib gdi32.lib /nologo /dll /pdb:"..\..\bin/cvaux100d_i7.pdb" /debug /machine:IX86 /out:"..\..\bin/cvaux100d_i7.dll" /implib:"..\..\lib/cvauxd_i7.lib" /pdbtype:sept /libpath:"..\..\lib" /machine:IA64
|
||||
# SUBTRACT LINK32 /pdb:none
|
||||
|
||||
!ENDIF
|
||||
|
||||
# Begin Target
|
||||
|
||||
# Name "cvaux - Win32 Release"
|
||||
# Name "cvaux - Win32 Debug"
|
||||
# Name "cvaux - Win32 Release64"
|
||||
# Name "cvaux - Win32 Debug64"
|
||||
# Name "cvaux - Win32 Release64 Itanium"
|
||||
# Name "cvaux - Win32 Debug64 Itanium"
|
||||
# Begin Group "Src"
|
||||
|
||||
# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat"
|
||||
# Begin Group "VideoSurveillance"
|
||||
|
||||
# PROP Default_Filter ""
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\vs\bgfg_estimation.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\vs\blobtrackanalysis.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\vs\blobtrackanalysishist.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\vs\blobtrackanalysisior.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\vs\blobtrackanalysistrackdist.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\vs\blobtrackgen1.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\vs\blobtrackgenyml.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\vs\blobtrackingauto.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\vs\blobtrackingcc.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\vs\blobtrackingccwithcr.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\vs\blobtrackingkalman.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\vs\blobtrackinglist.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\vs\blobtrackingmsfg.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\vs\blobtrackingmsfgs.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\vs\blobtrackpostprockalman.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\vs\blobtrackpostproclinear.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\vs\blobtrackpostproclist.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\vs\enteringblobdetection.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\vs\enteringblobdetectionreal.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\vs\TestSeq.cpp
|
||||
# End Source File
|
||||
# End Group
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\camshift.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cv3dtracker.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvaux.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvaux.rc
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvauxutils.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvbgfg_acmmm2003.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvbgfg_common.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvbgfg_gaussmix.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvcalibfilter.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvcorrespond.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvcorrimages.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvcreatehandmask.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvdpstereo.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cveigenobjects.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvepilines.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvface.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvfacedetection.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvfacetemplate.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvfindface.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvfindhandregion.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvhmm.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvhmm1d.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvhmmobs.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvlcm.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvlee.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvlevmar.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvlevmarprojbandle.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvlevmartrif.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvlines.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvlmeds.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvmorphcontours.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvmorphing.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvprewarp.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvscanlines.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvsegment.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvsubdiv2.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvtexture.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvtrifocal.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvvecfacetracking.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cvvideo.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\precomp.cpp
|
||||
# ADD CPP /Yc"_cvaux.h"
|
||||
# End Source File
|
||||
# End Group
|
||||
# Begin Group "Include"
|
||||
|
||||
# PROP Default_Filter "h;hpp;hxx;hm;inl"
|
||||
# Begin Group "Internal"
|
||||
|
||||
# PROP Default_Filter ""
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\_cvaux.h
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\_cvfacedetection.h
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\_cvvectrack.h
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\_cvvm.h
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\resource.h
|
||||
# End Source File
|
||||
# End Group
|
||||
# Begin Group "External"
|
||||
|
||||
# PROP Default_Filter ""
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=..\include\cvaux.h
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=..\include\cvaux.hpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=..\include\cvvidsurv.hpp
|
||||
# End Source File
|
||||
# End Group
|
||||
# End Group
|
||||
# End Target
|
||||
# End Project
|
||||
121
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/src/cvaux.rc
Normal file
121
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/src/cvaux.rc
Normal file
@@ -0,0 +1,121 @@
|
||||
//Microsoft Developer Studio generated resource script.
|
||||
//
|
||||
#include "resource.h"
|
||||
|
||||
#define APSTUDIO_READONLY_SYMBOLS
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Generated from the TEXTINCLUDE 2 resource.
|
||||
//
|
||||
#include "afxres.h"
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
#undef APSTUDIO_READONLY_SYMBOLS
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// Russian resources
|
||||
|
||||
#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_RUS)
|
||||
#ifdef _WIN32
|
||||
LANGUAGE LANG_RUSSIAN, SUBLANG_DEFAULT
|
||||
#pragma code_page(1251)
|
||||
#endif //_WIN32
|
||||
|
||||
#ifdef APSTUDIO_INVOKED
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// TEXTINCLUDE
|
||||
//
|
||||
|
||||
1 TEXTINCLUDE DISCARDABLE
|
||||
BEGIN
|
||||
"resource.h\0"
|
||||
END
|
||||
|
||||
2 TEXTINCLUDE DISCARDABLE
|
||||
BEGIN
|
||||
"#include ""afxres.h""\r\n"
|
||||
"\0"
|
||||
END
|
||||
|
||||
3 TEXTINCLUDE DISCARDABLE
|
||||
BEGIN
|
||||
"\r\n"
|
||||
"\0"
|
||||
END
|
||||
|
||||
#endif // APSTUDIO_INVOKED
|
||||
|
||||
#endif // Russian resources
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// English (U.S.) resources
|
||||
|
||||
#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU)
|
||||
#ifdef _WIN32
|
||||
LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US
|
||||
#pragma code_page(1252)
|
||||
#endif //_WIN32
|
||||
|
||||
#ifndef _MAC
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Version
|
||||
//
|
||||
|
||||
VS_VERSION_INFO VERSIONINFO
|
||||
FILEVERSION 1,0,0,1
|
||||
PRODUCTVERSION 1,0,0,1
|
||||
FILEFLAGSMASK 0x3fL
|
||||
#ifdef _DEBUG
|
||||
FILEFLAGS 0x1L
|
||||
#else
|
||||
FILEFLAGS 0x0L
|
||||
#endif
|
||||
FILEOS 0x40004L
|
||||
FILETYPE 0x2L
|
||||
FILESUBTYPE 0x0L
|
||||
BEGIN
|
||||
BLOCK "StringFileInfo"
|
||||
BEGIN
|
||||
BLOCK "040904b0"
|
||||
BEGIN
|
||||
VALUE "Comments", "Intel® Open Source Computer Vision Library: The experimental part.\0"
|
||||
VALUE "CompanyName", "Intel Corporation.\0"
|
||||
VALUE "FileDescription", "The exterimental OpenCV functions\0"
|
||||
VALUE "FileVersion", "1, 0, 0, 1\0"
|
||||
VALUE "InternalName", "cvaux100.dll\0"
|
||||
VALUE "LegalCopyright", "Copyright © 2002-2006\0"
|
||||
VALUE "LegalTrademarks", "\0"
|
||||
VALUE "OriginalFilename", "cvaux100.dll\0"
|
||||
VALUE "PrivateBuild", "\0"
|
||||
VALUE "ProductName", "Intel® Open Source Computer Vision Library\0"
|
||||
VALUE "ProductVersion", "1, 0, 0, 1\0"
|
||||
VALUE "SpecialBuild", "\0"
|
||||
END
|
||||
END
|
||||
BLOCK "VarFileInfo"
|
||||
BEGIN
|
||||
VALUE "Translation", 0x409, 1200
|
||||
END
|
||||
END
|
||||
|
||||
#endif // !_MAC
|
||||
|
||||
#endif // English (U.S.) resources
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
|
||||
|
||||
#ifndef APSTUDIO_INVOKED
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Generated from the TEXTINCLUDE 3 resource.
|
||||
//
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
#endif // not APSTUDIO_INVOKED
|
||||
|
||||
2930
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/src/cvaux.vcproj
Normal file
2930
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/src/cvaux.vcproj
Normal file
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,44 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
/* End of file. */
|
||||
@@ -0,0 +1,686 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
#include <math.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
//#include <algorithm>
|
||||
|
||||
static double* _cv_max_element( double* start, double* end )
|
||||
{
|
||||
double* p = start++;
|
||||
for( ; start != end; start++ )
|
||||
if( *p < *start )
|
||||
p = start;
|
||||
return p;
|
||||
}
|
||||
|
||||
static void CV_CDECL icvReleaseFGDStatModel( CvFGDStatModel** model );
|
||||
static int CV_CDECL icvUpdateFGDStatModel( IplImage* curr_frame,
|
||||
CvFGDStatModel* model );
|
||||
|
||||
// Function cvCreateFGDStatModel initializes foreground detection process
|
||||
// parameters:
|
||||
// first_frame - frame from video sequence
|
||||
// parameters - (optional) if NULL default parameters of the algorithm will be used
|
||||
// p_model - pointer to CvFGDStatModel structure
|
||||
CV_IMPL CvBGStatModel*
|
||||
cvCreateFGDStatModel( IplImage* first_frame, CvFGDStatModelParams* parameters )
|
||||
{
|
||||
CvFGDStatModel* p_model = 0;
|
||||
|
||||
CV_FUNCNAME( "cvCreateFGDStatModel" );
|
||||
|
||||
__BEGIN__;
|
||||
|
||||
int i, j, k, pixel_count, buf_size;
|
||||
CvFGDStatModelParams params;
|
||||
|
||||
if( !CV_IS_IMAGE(first_frame) )
|
||||
CV_ERROR( CV_StsBadArg, "Invalid or NULL first_frame parameter" );
|
||||
|
||||
//init parameters
|
||||
if( parameters == NULL )
|
||||
{
|
||||
params.Lc = CV_BGFG_FGD_LC;
|
||||
params.N1c = CV_BGFG_FGD_N1C;
|
||||
params.N2c = CV_BGFG_FGD_N2C;
|
||||
params.Lcc = CV_BGFG_FGD_LCC;
|
||||
params.N1cc = CV_BGFG_FGD_N1CC;
|
||||
params.N2cc = CV_BGFG_FGD_N2CC;
|
||||
params.delta = CV_BGFG_FGD_DELTA;
|
||||
params.alpha1 = CV_BGFG_FGD_ALPHA_1;
|
||||
params.alpha2 = CV_BGFG_FGD_ALPHA_2;
|
||||
params.alpha3 = CV_BGFG_FGD_ALPHA_3;
|
||||
params.T = CV_BGFG_FGD_T;
|
||||
params.minArea = CV_BGFG_FGD_MINAREA;
|
||||
params.is_obj_without_holes = 1;
|
||||
params.perform_morphing = 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
params = *parameters;
|
||||
}
|
||||
|
||||
CV_CALL( p_model = (CvFGDStatModel*)cvAlloc( sizeof(*p_model) ));
|
||||
memset( p_model, 0, sizeof(*p_model) );
|
||||
p_model->type = CV_BG_MODEL_FGD;
|
||||
p_model->release = (CvReleaseBGStatModel)icvReleaseFGDStatModel;
|
||||
p_model->update = (CvUpdateBGStatModel)icvUpdateFGDStatModel;;
|
||||
p_model->params = params;
|
||||
|
||||
//init storages
|
||||
pixel_count = first_frame->width*first_frame->height;
|
||||
|
||||
buf_size = pixel_count*sizeof(p_model->pixel_stat[0]);
|
||||
CV_CALL( p_model->pixel_stat = (CvBGPixelStat*)cvAlloc(buf_size) );
|
||||
memset( p_model->pixel_stat, 0, buf_size );
|
||||
|
||||
buf_size = pixel_count*params.N2c*sizeof(p_model->pixel_stat[0].ctable[0]);
|
||||
CV_CALL( p_model->pixel_stat[0].ctable = (CvBGPixelCStatTable*)cvAlloc(buf_size) );
|
||||
memset( p_model->pixel_stat[0].ctable, 0, buf_size );
|
||||
|
||||
buf_size = pixel_count*params.N2cc*sizeof(p_model->pixel_stat[0].cctable[0]);
|
||||
CV_CALL( p_model->pixel_stat[0].cctable = (CvBGPixelCCStatTable*)cvAlloc(buf_size) );
|
||||
memset( p_model->pixel_stat[0].cctable, 0, buf_size );
|
||||
|
||||
for( i = 0, k = 0; i < first_frame->height; i++ )
|
||||
for( j = 0; j < first_frame->width; j++, k++ )
|
||||
{
|
||||
p_model->pixel_stat[k].ctable = p_model->pixel_stat[0].ctable + k*params.N2c;
|
||||
p_model->pixel_stat[k].cctable = p_model->pixel_stat[0].cctable + k*params.N2cc;
|
||||
}
|
||||
|
||||
//init temporary images
|
||||
CV_CALL( p_model->Ftd = cvCreateImage(cvSize(first_frame->width, first_frame->height), IPL_DEPTH_8U, 1));
|
||||
CV_CALL( p_model->Fbd = cvCreateImage(cvSize(first_frame->width, first_frame->height), IPL_DEPTH_8U, 1));
|
||||
CV_CALL( p_model->foreground = cvCreateImage(cvSize(first_frame->width, first_frame->height), IPL_DEPTH_8U, 1));
|
||||
|
||||
CV_CALL( p_model->background = cvCloneImage(first_frame));
|
||||
CV_CALL( p_model->prev_frame = cvCloneImage(first_frame));
|
||||
CV_CALL( p_model->storage = cvCreateMemStorage());
|
||||
|
||||
__END__;
|
||||
|
||||
if( cvGetErrStatus() < 0 )
|
||||
{
|
||||
CvBGStatModel* base_ptr = (CvBGStatModel*)p_model;
|
||||
|
||||
if( p_model && p_model->release )
|
||||
p_model->release( &base_ptr );
|
||||
else
|
||||
cvFree( &p_model );
|
||||
p_model = 0;
|
||||
}
|
||||
|
||||
return (CvBGStatModel*)p_model;
|
||||
}
|
||||
|
||||
|
||||
static void CV_CDECL
|
||||
icvReleaseFGDStatModel( CvFGDStatModel** _model )
|
||||
{
|
||||
CV_FUNCNAME( "icvReleaseFGDStatModel" );
|
||||
|
||||
__BEGIN__;
|
||||
|
||||
if( !_model )
|
||||
CV_ERROR( CV_StsNullPtr, "" );
|
||||
|
||||
if( *_model )
|
||||
{
|
||||
CvFGDStatModel* model = *_model;
|
||||
if( model->pixel_stat )
|
||||
{
|
||||
cvFree( &model->pixel_stat[0].ctable );
|
||||
cvFree( &model->pixel_stat[0].cctable );
|
||||
cvFree( &model->pixel_stat );
|
||||
}
|
||||
|
||||
cvReleaseImage( &model->Ftd );
|
||||
cvReleaseImage( &model->Fbd );
|
||||
cvReleaseImage( &model->foreground );
|
||||
cvReleaseImage( &model->background );
|
||||
cvReleaseImage( &model->prev_frame );
|
||||
cvReleaseMemStorage(&model->storage);
|
||||
|
||||
cvFree( _model );
|
||||
}
|
||||
|
||||
__END__;
|
||||
}
|
||||
|
||||
// Function cvChangeDetection performs change detection for Foreground detection algorithm
|
||||
// parameters:
|
||||
// prev_frame -
|
||||
// curr_frame -
|
||||
// change_mask -
|
||||
CV_IMPL int
|
||||
cvChangeDetection( IplImage* prev_frame,
|
||||
IplImage* curr_frame,
|
||||
IplImage* change_mask )
|
||||
{
|
||||
int i, j, b, x, y, thres;
|
||||
const int PIXELRANGE=256;
|
||||
|
||||
if( !prev_frame || !curr_frame || !change_mask ||
|
||||
prev_frame->nChannels != 3 || curr_frame->nChannels != 3 || change_mask->nChannels != 1 ||
|
||||
prev_frame->depth != IPL_DEPTH_8U || curr_frame->depth != IPL_DEPTH_8U || change_mask->depth != IPL_DEPTH_8U ||
|
||||
!CV_ARE_SIZES_EQ( prev_frame, curr_frame ) || !CV_ARE_SIZES_EQ( prev_frame, change_mask ) ) return 0;
|
||||
|
||||
cvZero ( change_mask );
|
||||
|
||||
// All operations per colour
|
||||
for (b=0 ; b<prev_frame->nChannels ; b++) {
|
||||
// create histogram
|
||||
|
||||
long HISTOGRAM[PIXELRANGE];
|
||||
for (i=0 ; i<PIXELRANGE; i++) HISTOGRAM[i]=0;
|
||||
|
||||
for (y=0 ; y<curr_frame->height ; y++)
|
||||
{
|
||||
uchar* rowStart1 = (uchar*)curr_frame->imageData + y * curr_frame->widthStep + b;
|
||||
uchar* rowStart2 = (uchar*)prev_frame->imageData + y * prev_frame->widthStep + b;
|
||||
for (x=0 ; x<curr_frame->width ; x++, rowStart1+=curr_frame->nChannels, rowStart2+=prev_frame->nChannels) {
|
||||
int diff = abs( int(*rowStart1) - int(*rowStart2) );
|
||||
HISTOGRAM[diff]++;
|
||||
}
|
||||
}
|
||||
|
||||
double relativeVariance[PIXELRANGE];
|
||||
for (i=0 ; i<PIXELRANGE; i++) relativeVariance[i]=0;
|
||||
|
||||
for (thres=PIXELRANGE-2; thres>=0 ; thres--)
|
||||
{
|
||||
// fprintf(stderr, "Iter %d\n", thres);
|
||||
double sum=0;
|
||||
double sqsum=0;
|
||||
int count=0;
|
||||
// fprintf(stderr, "Iter %d entering loop\n", thres);
|
||||
for (j=thres ; j<PIXELRANGE ; j++) {
|
||||
sum += double(j)*double(HISTOGRAM[j]);
|
||||
sqsum += double(j*j)*double(HISTOGRAM[j]);
|
||||
count += HISTOGRAM[j];
|
||||
}
|
||||
count = count == 0 ? 1 : count;
|
||||
// fprintf(stderr, "Iter %d finishing loop\n", thres);
|
||||
double my = sum / count;
|
||||
double sigma = sqrt( sqsum/count - my*my);
|
||||
// fprintf(stderr, "Iter %d sum=%g sqsum=%g count=%d sigma = %g\n", thres, sum, sqsum, count, sigma);
|
||||
// fprintf(stderr, "Writing to %x\n", &(relativeVariance[thres]));
|
||||
relativeVariance[thres] = sigma;
|
||||
// fprintf(stderr, "Iter %d finished\n", thres);
|
||||
}
|
||||
// find maximum
|
||||
uchar bestThres = 0;
|
||||
|
||||
double* pBestThres = _cv_max_element(relativeVariance, relativeVariance+PIXELRANGE);
|
||||
bestThres = (uchar)(*pBestThres); if (bestThres <10) bestThres=10;
|
||||
|
||||
for (y=0 ; y<prev_frame->height ; y++)
|
||||
{
|
||||
uchar* rowStart1 = (uchar*)(curr_frame->imageData) + y * curr_frame->widthStep + b;
|
||||
uchar* rowStart2 = (uchar*)(prev_frame->imageData) + y * prev_frame->widthStep + b;
|
||||
uchar* rowStart3 = (uchar*)(change_mask->imageData) + y * change_mask->widthStep;
|
||||
for (x = 0; x < curr_frame->width; x++, rowStart1+=curr_frame->nChannels,
|
||||
rowStart2+=prev_frame->nChannels, rowStart3+=change_mask->nChannels) {
|
||||
// OR between different color channels
|
||||
int diff = abs( int(*rowStart1) - int(*rowStart2) );
|
||||
if ( diff > bestThres)
|
||||
*rowStart3 |=255;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
||||
#define MIN_PV 1E-10
|
||||
|
||||
|
||||
#define V_C(k,l) ctable[k].v[l]
|
||||
#define PV_C(k) ctable[k].Pv
|
||||
#define PVB_C(k) ctable[k].Pvb
|
||||
#define V_CC(k,l) cctable[k].v[l]
|
||||
#define PV_CC(k) cctable[k].Pv
|
||||
#define PVB_CC(k) cctable[k].Pvb
|
||||
|
||||
|
||||
// Function cvUpdateFGDStatModel updates statistical model and returns number of foreground regions
|
||||
// parameters:
|
||||
// curr_frame - current frame from video sequence
|
||||
// p_model - pointer to CvFGDStatModel structure
|
||||
static int CV_CDECL
|
||||
icvUpdateFGDStatModel( IplImage* curr_frame, CvFGDStatModel* model )
|
||||
{
|
||||
int mask_step = model->Ftd->widthStep;
|
||||
CvSeq *first_seq = NULL, *prev_seq = NULL, *seq = NULL;
|
||||
IplImage* prev_frame = model->prev_frame;
|
||||
int region_count = 0;
|
||||
int FG_pixels_count = 0;
|
||||
int deltaC = cvRound(model->params.delta * 256 / model->params.Lc);
|
||||
int deltaCC = cvRound(model->params.delta * 256 / model->params.Lcc);
|
||||
int i, j, k, l;
|
||||
|
||||
//clear storages
|
||||
cvClearMemStorage(model->storage);
|
||||
cvZero(model->foreground);
|
||||
|
||||
//form FG pixels candidates using image differencing with adaptive threshold [P.Rosin, Thresholding for change detection, ICCV, 1998 ]
|
||||
cvChangeDetection( prev_frame, curr_frame, model->Ftd );
|
||||
cvChangeDetection( model->background, curr_frame, model->Fbd );
|
||||
|
||||
for( i = 0; i < model->Ftd->height; i++ )
|
||||
{
|
||||
for( j = 0; j < model->Ftd->width; j++ )
|
||||
{
|
||||
if( ((uchar*)model->Fbd->imageData)[i*mask_step+j] || ((uchar*)model->Ftd->imageData)[i*mask_step+j] )
|
||||
{
|
||||
float Pb=0, Pv=0, Pvb=0;
|
||||
CvBGPixelStat* stat = model->pixel_stat + i * model->Ftd->width + j;
|
||||
CvBGPixelCStatTable* ctable = stat->ctable;
|
||||
CvBGPixelCCStatTable* cctable = stat->cctable;
|
||||
|
||||
uchar* curr_data = (uchar*)(curr_frame->imageData)+i*curr_frame->widthStep+j*3;
|
||||
uchar* prev_data = (uchar*)(prev_frame->imageData)+i*prev_frame->widthStep+j*3;
|
||||
|
||||
int val = 0;
|
||||
// is it a motion pixel?
|
||||
if( ((uchar*)model->Ftd->imageData)[i*mask_step+j] )
|
||||
{
|
||||
if( !stat->is_trained_dyn_model ) val = 1;
|
||||
else
|
||||
{
|
||||
//compare with stored CCt vectors
|
||||
for( k = 0; PV_CC(k) > model->params.alpha2 && k < model->params.N1cc; k++ )
|
||||
{
|
||||
if ( abs( V_CC(k,0) - prev_data[0]) <= deltaCC &&
|
||||
abs( V_CC(k,1) - prev_data[1]) <= deltaCC &&
|
||||
abs( V_CC(k,2) - prev_data[2]) <= deltaCC &&
|
||||
abs( V_CC(k,3) - curr_data[0]) <= deltaCC &&
|
||||
abs( V_CC(k,4) - curr_data[1]) <= deltaCC &&
|
||||
abs( V_CC(k,5) - curr_data[2]) <= deltaCC)
|
||||
{
|
||||
Pv += PV_CC(k);
|
||||
Pvb += PVB_CC(k);
|
||||
}
|
||||
}
|
||||
Pb = stat->Pbcc;
|
||||
if( 2 * Pvb * Pb <= Pv ) val = 1;
|
||||
}
|
||||
}
|
||||
else if( stat->is_trained_st_model )
|
||||
{
|
||||
//compare with stored Ct vectors
|
||||
for( k = 0; PV_C(k) > model->params.alpha2 && k < model->params.N1c; k++ )
|
||||
{
|
||||
if ( abs( V_C(k,0) - curr_data[0]) <= deltaC &&
|
||||
abs( V_C(k,1) - curr_data[1]) <= deltaC &&
|
||||
abs( V_C(k,2) - curr_data[2]) <= deltaC )
|
||||
{
|
||||
Pv += PV_C(k);
|
||||
Pvb += PVB_C(k);
|
||||
}
|
||||
}
|
||||
Pb = stat->Pbc;
|
||||
if( 2 * Pvb * Pb <= Pv ) val = 1;
|
||||
}
|
||||
//update FG
|
||||
((uchar*)model->foreground->imageData)[i*mask_step+j] = (uchar)(val*255);
|
||||
FG_pixels_count += val;
|
||||
}// end if( change detection...
|
||||
}//for j...
|
||||
} //for i...
|
||||
//end BG/FG classification
|
||||
|
||||
//foreground segmentation
|
||||
//smooth FG map
|
||||
if( model->params.perform_morphing ){
|
||||
cvMorphologyEx( model->foreground, model->foreground, 0, 0, CV_MOP_OPEN, 1 );
|
||||
cvMorphologyEx( model->foreground, model->foreground, 0, 0, CV_MOP_CLOSE, 1 );
|
||||
}
|
||||
|
||||
|
||||
if( model->params.minArea > 0 || model->params.is_obj_without_holes ){
|
||||
//filter small regions
|
||||
cvFindContours( model->foreground, model->storage, &first_seq, sizeof(CvContour), CV_RETR_LIST );
|
||||
for( seq = first_seq; seq; seq = seq->h_next )
|
||||
{
|
||||
CvContour* cnt = (CvContour*)seq;
|
||||
if( cnt->rect.width * cnt->rect.height < model->params.minArea ||
|
||||
(model->params.is_obj_without_holes && CV_IS_SEQ_HOLE(seq)) )
|
||||
{
|
||||
//delete small contour
|
||||
prev_seq = seq->h_prev;
|
||||
if( prev_seq )
|
||||
{
|
||||
prev_seq->h_next = seq->h_next;
|
||||
if( seq->h_next ) seq->h_next->h_prev = prev_seq;
|
||||
}
|
||||
else
|
||||
{
|
||||
first_seq = seq->h_next;
|
||||
if( seq->h_next ) seq->h_next->h_prev = NULL;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
region_count++;
|
||||
}
|
||||
}
|
||||
model->foreground_regions = first_seq;
|
||||
cvZero(model->foreground);
|
||||
cvDrawContours(model->foreground, first_seq, CV_RGB(0, 0, 255), CV_RGB(0, 0, 255), 10, -1);
|
||||
}
|
||||
else{
|
||||
model->foreground_regions = NULL;
|
||||
}
|
||||
|
||||
//check ALL BG update condition
|
||||
if( ((float)FG_pixels_count/(model->Ftd->width*model->Ftd->height)) > CV_BGFG_FGD_BG_UPDATE_TRESH )
|
||||
{
|
||||
for( i = 0; i < model->Ftd->height; i++ )
|
||||
for( j = 0; j < model->Ftd->width; j++ )
|
||||
{
|
||||
CvBGPixelStat* stat = model->pixel_stat + i * model->Ftd->width + j;
|
||||
stat->is_trained_st_model = stat->is_trained_dyn_model = 1;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//update BG model
|
||||
for( i = 0; i < model->Ftd->height; i++ )
|
||||
{
|
||||
for( j = 0; j < model->Ftd->width; j++ )
|
||||
{
|
||||
CvBGPixelStat* stat = model->pixel_stat + i * model->Ftd->width + j;
|
||||
CvBGPixelCStatTable* ctable = stat->ctable;
|
||||
CvBGPixelCCStatTable* cctable = stat->cctable;
|
||||
|
||||
uchar *curr_data = (uchar*)(curr_frame->imageData)+i*curr_frame->widthStep+j*3;
|
||||
uchar *prev_data = (uchar*)(prev_frame->imageData)+i*prev_frame->widthStep+j*3;
|
||||
|
||||
if( ((uchar*)model->Ftd->imageData)[i*mask_step+j] || !stat->is_trained_dyn_model )
|
||||
{
|
||||
float alpha = stat->is_trained_dyn_model ? model->params.alpha2 : model->params.alpha3;
|
||||
float diff = 0;
|
||||
int dist, min_dist = 2147483647, indx = -1;
|
||||
|
||||
//update Pb
|
||||
stat->Pbcc *= (1.f-alpha);
|
||||
if( !((uchar*)model->foreground->imageData)[i*mask_step+j] )
|
||||
{
|
||||
stat->Pbcc += alpha;
|
||||
}
|
||||
|
||||
// find best Vi match
|
||||
for(k = 0; PV_CC(k) && k < model->params.N2cc; k++ )
|
||||
{
|
||||
// Exponential decay of memory
|
||||
PV_CC(k) *= (1-alpha);
|
||||
PVB_CC(k) *= (1-alpha);
|
||||
if( PV_CC(k) < MIN_PV )
|
||||
{
|
||||
PV_CC(k) = 0;
|
||||
PVB_CC(k) = 0;
|
||||
continue;
|
||||
}
|
||||
|
||||
dist = 0;
|
||||
for( l = 0; l < 3; l++ )
|
||||
{
|
||||
int val = abs( V_CC(k,l) - prev_data[l] );
|
||||
if( val > deltaCC ) break;
|
||||
dist += val;
|
||||
val = abs( V_CC(k,l+3) - curr_data[l] );
|
||||
if( val > deltaCC) break;
|
||||
dist += val;
|
||||
}
|
||||
if( l == 3 && dist < min_dist )
|
||||
{
|
||||
min_dist = dist;
|
||||
indx = k;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if( indx < 0 )
|
||||
{//N2th elem in the table is replaced by a new features
|
||||
indx = model->params.N2cc - 1;
|
||||
PV_CC(indx) = alpha;
|
||||
PVB_CC(indx) = alpha;
|
||||
//udate Vt
|
||||
for( l = 0; l < 3; l++ )
|
||||
{
|
||||
V_CC(indx,l) = prev_data[l];
|
||||
V_CC(indx,l+3) = curr_data[l];
|
||||
}
|
||||
}
|
||||
else
|
||||
{//update
|
||||
PV_CC(indx) += alpha;
|
||||
if( !((uchar*)model->foreground->imageData)[i*mask_step+j] )
|
||||
{
|
||||
PVB_CC(indx) += alpha;
|
||||
}
|
||||
}
|
||||
|
||||
//re-sort CCt table by Pv
|
||||
for( k = 0; k < indx; k++ )
|
||||
{
|
||||
if( PV_CC(k) <= PV_CC(indx) )
|
||||
{
|
||||
//shift elements
|
||||
CvBGPixelCCStatTable tmp1, tmp2 = cctable[indx];
|
||||
for( l = k; l <= indx; l++ )
|
||||
{
|
||||
tmp1 = cctable[l];
|
||||
cctable[l] = tmp2;
|
||||
tmp2 = tmp1;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
float sum1=0, sum2=0;
|
||||
//check "once-off" changes
|
||||
for(k = 0; PV_CC(k) && k < model->params.N1cc; k++ )
|
||||
{
|
||||
sum1 += PV_CC(k);
|
||||
sum2 += PVB_CC(k);
|
||||
}
|
||||
if( sum1 > model->params.T ) stat->is_trained_dyn_model = 1;
|
||||
|
||||
diff = sum1 - stat->Pbcc * sum2;
|
||||
//update stat table
|
||||
if( diff > model->params.T )
|
||||
{
|
||||
//printf("once off change at motion mode\n");
|
||||
//new BG features are discovered
|
||||
for( k = 0; PV_CC(k) && k < model->params.N1cc; k++ )
|
||||
{
|
||||
PVB_CC(k) =
|
||||
(PV_CC(k)-stat->Pbcc*PVB_CC(k))/(1-stat->Pbcc);
|
||||
}
|
||||
assert(stat->Pbcc<=1 && stat->Pbcc>=0);
|
||||
}
|
||||
}
|
||||
|
||||
//case of stational pixel
|
||||
if( !((uchar*)model->Ftd->imageData)[i*mask_step+j] )
|
||||
{
|
||||
float alpha = stat->is_trained_st_model ? model->params.alpha2 : model->params.alpha3;
|
||||
float diff = 0;
|
||||
int dist, min_dist = 2147483647, indx = -1;
|
||||
|
||||
//update Pb
|
||||
stat->Pbc *= (1.f-alpha);
|
||||
if( !((uchar*)model->foreground->imageData)[i*mask_step+j] )
|
||||
{
|
||||
stat->Pbc += alpha;
|
||||
}
|
||||
|
||||
//find best Vi match
|
||||
for( k = 0; k < model->params.N2c; k++ )
|
||||
{
|
||||
// Exponential decay of memory
|
||||
PV_C(k) *= (1-alpha);
|
||||
PVB_C(k) *= (1-alpha);
|
||||
if( PV_C(k) < MIN_PV )
|
||||
{
|
||||
PV_C(k) = 0;
|
||||
PVB_C(k) = 0;
|
||||
continue;
|
||||
}
|
||||
|
||||
dist = 0;
|
||||
for( l = 0; l < 3; l++ )
|
||||
{
|
||||
int val = abs( V_C(k,l) - curr_data[l] );
|
||||
if( val > deltaC ) break;
|
||||
dist += val;
|
||||
}
|
||||
if( l == 3 && dist < min_dist )
|
||||
{
|
||||
min_dist = dist;
|
||||
indx = k;
|
||||
}
|
||||
}
|
||||
|
||||
if( indx < 0 )
|
||||
{//N2th elem in the table is replaced by a new features
|
||||
indx = model->params.N2c - 1;
|
||||
PV_C(indx) = alpha;
|
||||
PVB_C(indx) = alpha;
|
||||
//udate Vt
|
||||
for( l = 0; l < 3; l++ )
|
||||
{
|
||||
V_C(indx,l) = curr_data[l];
|
||||
}
|
||||
} else
|
||||
{//update
|
||||
PV_C(indx) += alpha;
|
||||
if( !((uchar*)model->foreground->imageData)[i*mask_step+j] )
|
||||
{
|
||||
PVB_C(indx) += alpha;
|
||||
}
|
||||
}
|
||||
|
||||
//re-sort Ct table by Pv
|
||||
for( k = 0; k < indx; k++ )
|
||||
{
|
||||
if( PV_C(k) <= PV_C(indx) )
|
||||
{
|
||||
//shift elements
|
||||
CvBGPixelCStatTable tmp1, tmp2 = ctable[indx];
|
||||
for( l = k; l <= indx; l++ )
|
||||
{
|
||||
tmp1 = ctable[l];
|
||||
ctable[l] = tmp2;
|
||||
tmp2 = tmp1;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
//check "once-off" changes
|
||||
float sum1=0, sum2=0;
|
||||
for( k = 0; PV_C(k) && k < model->params.N1c; k++ )
|
||||
{
|
||||
sum1 += PV_C(k);
|
||||
sum2 += PVB_C(k);
|
||||
}
|
||||
diff = sum1 - stat->Pbc * sum2;
|
||||
if( sum1 > model->params.T ) stat->is_trained_st_model = 1;
|
||||
|
||||
//update stat table
|
||||
if( diff > model->params.T )
|
||||
{
|
||||
//printf("once off change at stat mode\n");
|
||||
//new BG features are discovered
|
||||
for( k = 0; PV_C(k) && k < model->params.N1c; k++ )
|
||||
{
|
||||
PVB_C(k) = (PV_C(k)-stat->Pbc*PVB_C(k))/(1-stat->Pbc);
|
||||
}
|
||||
stat->Pbc = 1 - stat->Pbc;
|
||||
}
|
||||
}//if !(change detection) at pixel (i,j)
|
||||
|
||||
//update the reference BG image
|
||||
if( !((uchar*)model->foreground->imageData)[i*mask_step+j])
|
||||
{
|
||||
uchar* ptr = ((uchar*)model->background->imageData) + i*model->background->widthStep+j*3;
|
||||
|
||||
if( !((uchar*)model->Ftd->imageData)[i*mask_step+j] &&
|
||||
!((uchar*)model->Fbd->imageData)[i*mask_step+j] )
|
||||
{
|
||||
//apply IIR filter
|
||||
for( l = 0; l < 3; l++ )
|
||||
{
|
||||
int a = cvRound(ptr[l]*(1 - model->params.alpha1) + model->params.alpha1*curr_data[l]);
|
||||
ptr[l] = (uchar)a;
|
||||
//((uchar*)model->background->imageData)[i*model->background->widthStep+j*3+l]*=(1 - model->params.alpha1);
|
||||
//((uchar*)model->background->imageData)[i*model->background->widthStep+j*3+l] += model->params.alpha1*curr_data[l];
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
//background change is detected
|
||||
for( l = 0; l < 3; l++ )
|
||||
{
|
||||
//((uchar*)model->background->imageData)[i*model->background->widthStep+j*3+l] = curr_data[l];
|
||||
ptr[l] = curr_data[l];
|
||||
}
|
||||
}
|
||||
}
|
||||
}//j
|
||||
}//i
|
||||
|
||||
//keep prev frame
|
||||
cvCopy( curr_frame, model->prev_frame );
|
||||
|
||||
return region_count;
|
||||
}
|
||||
|
||||
/* End of file. */
|
||||
@@ -0,0 +1,70 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
// Function cvRefineForegroundMaskBySegm preforms FG post-processing based on segmentation
|
||||
// (all pixels of the segment will be classified as FG if majority of pixels of the region are FG).
|
||||
// parameters:
|
||||
// segments - pointer to result of segmentation (for example MeanShiftSegmentation)
|
||||
// bg_model - pointer to CvBGStatModel structure
|
||||
CV_IMPL void cvRefineForegroundMaskBySegm( CvSeq* segments, CvBGStatModel* bg_model )
|
||||
{
|
||||
IplImage* tmp_image = cvCreateImage(cvSize(bg_model->foreground->width,bg_model->foreground->height),
|
||||
IPL_DEPTH_8U, 1);
|
||||
for( ; segments; segments = ((CvSeq*)segments)->h_next )
|
||||
{
|
||||
CvSeq seq = *segments;
|
||||
seq.v_next = seq.h_next = NULL;
|
||||
cvZero(tmp_image);
|
||||
cvDrawContours( tmp_image, &seq, CV_RGB(0, 0, 255), CV_RGB(0, 0, 255), 10, -1);
|
||||
int num1 = cvCountNonZero(tmp_image);
|
||||
cvAnd(tmp_image, bg_model->foreground, tmp_image);
|
||||
int num2 = cvCountNonZero(tmp_image);
|
||||
if( num2 > num1*0.5 )
|
||||
cvDrawContours( bg_model->foreground, &seq, CV_RGB(0, 0, 255), CV_RGB(0, 0, 255), 10, -1);
|
||||
else
|
||||
cvDrawContours( bg_model->foreground, &seq, CV_RGB(0, 0, 0), CV_RGB(0, 0, 0), 10, -1);
|
||||
}
|
||||
cvReleaseImage(&tmp_image);
|
||||
}
|
||||
|
||||
/* End of file. */
|
||||
|
||||
@@ -0,0 +1,592 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
|
||||
//This is based on the "An Improved Adaptive Background Mixture Model for
|
||||
//Real-time Tracking and Shadow Detection" by P. KaewTraKulPong and R. Bowden
|
||||
//The windowing method is used, but not the shadow detection. I make some of my
|
||||
//own modifications which make more sense. There are some errors in some of their
|
||||
//equations.
|
||||
//IplImage values of image that are useful
|
||||
//int nSize; /* sizeof(IplImage) */
|
||||
//int depth; /* pixel depth in bits: IPL_DEPTH_8U ...*/
|
||||
//int nChannels; /* OpenCV functions support 1,2,3 or 4 channels */
|
||||
//int width; /* image width in pixels */
|
||||
//int height; /* image height in pixels */
|
||||
//int imageSize; /* image data size in bytes in case of interleaved data)*/
|
||||
//char *imageData; /* pointer to aligned image data */
|
||||
//char *imageDataOrigin; /* pointer to very origin of image -deallocation */
|
||||
//Values useful for gaussian integral
|
||||
//0.5 - 0.19146 - 0.38292
|
||||
//1.0 - 0.34134 - 0.68268
|
||||
//1.5 - 0.43319 - 0.86638
|
||||
//2.0 - 0.47725 - 0.95450
|
||||
//2.5 - 0.49379 - 0.98758
|
||||
//3.0 - 0.49865 - 0.99730
|
||||
//3.5 - 0.4997674 - 0.9995348
|
||||
//4.0 - 0.4999683 - 0.9999366
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
|
||||
//internal functions for gaussian background detection
|
||||
static void icvInsertionSortGaussians( CvGaussBGPoint* g_point, double* sort_key, CvGaussBGStatModelParams *bg_model_params );
|
||||
|
||||
/*
|
||||
Test whether pixel can be explained by background model;
|
||||
Return -1 if no match was found; otherwise the index in match[] is returned
|
||||
|
||||
icvMatchTest(...) assumes what all color channels component exhibit the same variance
|
||||
icvMatchTest2(...) accounts for different variances per color channel
|
||||
*/
|
||||
static int icvMatchTest( double* src_pixel, int nChannels, int* match,
|
||||
const CvGaussBGPoint* g_point, const CvGaussBGStatModelParams *bg_model_params );
|
||||
/*static int icvMatchTest2( double* src_pixel, int nChannels, int* match,
|
||||
const CvGaussBGPoint* g_point, const CvGaussBGStatModelParams *bg_model_params );*/
|
||||
|
||||
|
||||
/*
|
||||
The update procedure differs between
|
||||
* the initialization phase (named *Partial* ) and
|
||||
* the normal phase (named *Full* )
|
||||
The initalization phase is defined as not having processed <win_size> frames yet
|
||||
*/
|
||||
static void icvUpdateFullWindow( double* src_pixel, int nChannels,
|
||||
int* match,
|
||||
CvGaussBGPoint* g_point,
|
||||
const CvGaussBGStatModelParams *bg_model_params );
|
||||
static void icvUpdateFullNoMatch( IplImage* gm_image, int p,
|
||||
int* match,
|
||||
CvGaussBGPoint* g_point,
|
||||
const CvGaussBGStatModelParams *bg_model_params);
|
||||
static void icvUpdatePartialWindow( double* src_pixel, int nChannels, int* match,
|
||||
CvGaussBGPoint* g_point, const CvGaussBGStatModelParams *bg_model_params );
|
||||
static void icvUpdatePartialNoMatch( double* src_pixel, int nChannels,
|
||||
int* match,
|
||||
CvGaussBGPoint* g_point,
|
||||
const CvGaussBGStatModelParams *bg_model_params);
|
||||
|
||||
|
||||
static void icvGetSortKey( const int nChannels, double* sort_key, const CvGaussBGPoint* g_point,
|
||||
const CvGaussBGStatModelParams *bg_model_params );
|
||||
static void icvBackgroundTest( const int nChannels, int n, int p, int *match, CvGaussBGModel* bg_model );
|
||||
|
||||
static void CV_CDECL icvReleaseGaussianBGModel( CvGaussBGModel** bg_model );
|
||||
static int CV_CDECL icvUpdateGaussianBGModel( IplImage* curr_frame, CvGaussBGModel* bg_model );
|
||||
|
||||
//#define for if(0);else for
|
||||
|
||||
//g = 1 for first gaussian in list that matches else g = 0
|
||||
//Rw is the learning rate for weight and Rg is leaning rate for mean and variance
|
||||
//Ms is the match_sum which is the sum of matches for a particular gaussian
|
||||
//Ms values are incremented until the sum of Ms values in the list equals window size L
|
||||
//SMs is the sum of match_sums for gaussians in the list
|
||||
//Rw = 1/SMs note the smallest Rw gets is 1/L
|
||||
//Rg = g/Ms for SMs < L and Rg = g/(w*L) for SMs = L
|
||||
//The list is maintained in sorted order using w/sqrt(variance) as a key
|
||||
//If there is no match the last gaussian in the list is replaced by the new gaussian
|
||||
//This will result in changes to SMs which results in changes in Rw and Rg.
|
||||
//If a gaussian is replaced and SMs previously equaled L values of Ms are computed from w
|
||||
//w[n+1] = w[n] + Rw*(g - w[n]) weight
|
||||
//u[n+1] = u[n] + Rg*(x[n+1] - u[n]) mean value Sg is sum n values of g
|
||||
//v[n+1] = v[n] + Rg*((x[n+1] - u[n])*(x[n+1] - u[n])) - v[n]) variance
|
||||
//
|
||||
|
||||
CV_IMPL CvBGStatModel*
|
||||
cvCreateGaussianBGModel( IplImage* first_frame, CvGaussBGStatModelParams* parameters )
|
||||
{
|
||||
CvGaussBGModel* bg_model = 0;
|
||||
|
||||
CV_FUNCNAME( "cvCreateGaussianBGModel" );
|
||||
|
||||
__BEGIN__;
|
||||
|
||||
double var_init;
|
||||
CvGaussBGStatModelParams params;
|
||||
int i, j, k, n, m, p;
|
||||
|
||||
//init parameters
|
||||
if( parameters == NULL )
|
||||
{
|
||||
params.win_size = CV_BGFG_MOG_WINDOW_SIZE;
|
||||
params.bg_threshold = CV_BGFG_MOG_BACKGROUND_THRESHOLD;
|
||||
params.std_threshold = CV_BGFG_MOG_STD_THRESHOLD;
|
||||
params.weight_init = CV_BGFG_MOG_WEIGHT_INIT;
|
||||
params.variance_init = CV_BGFG_MOG_SIGMA_INIT*CV_BGFG_MOG_SIGMA_INIT;
|
||||
params.minArea = CV_BGFG_MOG_MINAREA;
|
||||
params.n_gauss = CV_BGFG_MOG_NGAUSSIANS;
|
||||
}
|
||||
else
|
||||
{
|
||||
params = *parameters;
|
||||
}
|
||||
|
||||
if( !CV_IS_IMAGE(first_frame) )
|
||||
CV_ERROR( CV_StsBadArg, "Invalid or NULL first_frame parameter" );
|
||||
|
||||
CV_CALL( bg_model = (CvGaussBGModel*)cvAlloc( sizeof(*bg_model) ));
|
||||
memset( bg_model, 0, sizeof(*bg_model) );
|
||||
bg_model->type = CV_BG_MODEL_MOG;
|
||||
bg_model->release = (CvReleaseBGStatModel)icvReleaseGaussianBGModel;
|
||||
bg_model->update = (CvUpdateBGStatModel)icvUpdateGaussianBGModel;
|
||||
|
||||
bg_model->params = params;
|
||||
|
||||
//prepare storages
|
||||
CV_CALL( bg_model->g_point = (CvGaussBGPoint*)cvAlloc(sizeof(CvGaussBGPoint)*
|
||||
((first_frame->width*first_frame->height) + 256)));
|
||||
|
||||
CV_CALL( bg_model->background = cvCreateImage(cvSize(first_frame->width,
|
||||
first_frame->height), IPL_DEPTH_8U, first_frame->nChannels));
|
||||
CV_CALL( bg_model->foreground = cvCreateImage(cvSize(first_frame->width,
|
||||
first_frame->height), IPL_DEPTH_8U, 1));
|
||||
|
||||
CV_CALL( bg_model->storage = cvCreateMemStorage());
|
||||
|
||||
//initializing
|
||||
var_init = 2 * params.std_threshold * params.std_threshold;
|
||||
CV_CALL( bg_model->g_point[0].g_values =
|
||||
(CvGaussBGValues*)cvAlloc( sizeof(CvGaussBGValues)*params.n_gauss*
|
||||
(first_frame->width*first_frame->height + 128)));
|
||||
|
||||
for( i = 0, p = 0, n = 0; i < first_frame->height; i++ )
|
||||
{
|
||||
for( j = 0; j < first_frame->width; j++, n++ )
|
||||
{
|
||||
bg_model->g_point[n].g_values =
|
||||
bg_model->g_point[0].g_values + n*params.n_gauss;
|
||||
bg_model->g_point[n].g_values[0].weight = 1; //the first value seen has weight one
|
||||
bg_model->g_point[n].g_values[0].match_sum = 1;
|
||||
for( m = 0; m < first_frame->nChannels; m++)
|
||||
{
|
||||
bg_model->g_point[n].g_values[0].variance[m] = var_init;
|
||||
bg_model->g_point[n].g_values[0].mean[m] = (unsigned char)first_frame->imageData[p + m];
|
||||
}
|
||||
for( k = 1; k < params.n_gauss; k++)
|
||||
{
|
||||
bg_model->g_point[n].g_values[k].weight = 0;
|
||||
bg_model->g_point[n].g_values[k].match_sum = 0;
|
||||
for( m = 0; m < first_frame->nChannels; m++){
|
||||
bg_model->g_point[n].g_values[k].variance[m] = var_init;
|
||||
bg_model->g_point[n].g_values[k].mean[m] = 0;
|
||||
}
|
||||
}
|
||||
p += first_frame->nChannels;
|
||||
}
|
||||
}
|
||||
|
||||
bg_model->countFrames = 0;
|
||||
|
||||
__END__;
|
||||
|
||||
if( cvGetErrStatus() < 0 )
|
||||
{
|
||||
CvBGStatModel* base_ptr = (CvBGStatModel*)bg_model;
|
||||
|
||||
if( bg_model && bg_model->release )
|
||||
bg_model->release( &base_ptr );
|
||||
else
|
||||
cvFree( &bg_model );
|
||||
bg_model = 0;
|
||||
}
|
||||
|
||||
return (CvBGStatModel*)bg_model;
|
||||
}
|
||||
|
||||
|
||||
static void CV_CDECL
|
||||
icvReleaseGaussianBGModel( CvGaussBGModel** _bg_model )
|
||||
{
|
||||
CV_FUNCNAME( "icvReleaseGaussianBGModel" );
|
||||
|
||||
__BEGIN__;
|
||||
|
||||
if( !_bg_model )
|
||||
CV_ERROR( CV_StsNullPtr, "" );
|
||||
|
||||
if( *_bg_model )
|
||||
{
|
||||
CvGaussBGModel* bg_model = *_bg_model;
|
||||
if( bg_model->g_point )
|
||||
{
|
||||
cvFree( &bg_model->g_point[0].g_values );
|
||||
cvFree( &bg_model->g_point );
|
||||
}
|
||||
|
||||
cvReleaseImage( &bg_model->background );
|
||||
cvReleaseImage( &bg_model->foreground );
|
||||
cvReleaseMemStorage(&bg_model->storage);
|
||||
memset( bg_model, 0, sizeof(*bg_model) );
|
||||
cvFree( _bg_model );
|
||||
}
|
||||
|
||||
__END__;
|
||||
}
|
||||
|
||||
|
||||
static int CV_CDECL
|
||||
icvUpdateGaussianBGModel( IplImage* curr_frame, CvGaussBGModel* bg_model )
|
||||
{
|
||||
int i, j, k;
|
||||
int region_count = 0;
|
||||
CvSeq *first_seq = NULL, *prev_seq = NULL, *seq = NULL;
|
||||
|
||||
bg_model->countFrames++;
|
||||
|
||||
for( i = 0; i < curr_frame->height; i++ )
|
||||
{
|
||||
for( j = 0; j < curr_frame->width; j++ )
|
||||
{
|
||||
int match[CV_BGFG_MOG_MAX_NGAUSSIANS];
|
||||
double sort_key[CV_BGFG_MOG_MAX_NGAUSSIANS];
|
||||
const int nChannels = curr_frame->nChannels;
|
||||
const int n = i*curr_frame->width+j;
|
||||
const int p = n*curr_frame->nChannels;
|
||||
|
||||
// A few short cuts
|
||||
CvGaussBGPoint* g_point = &bg_model->g_point[n];
|
||||
const CvGaussBGStatModelParams bg_model_params = bg_model->params;
|
||||
double pixel[4];
|
||||
int no_match;
|
||||
|
||||
for( k = 0; k < nChannels; k++ )
|
||||
pixel[k] = (uchar)curr_frame->imageData[p+k];
|
||||
|
||||
no_match = icvMatchTest( pixel, nChannels, match, g_point, &bg_model_params );
|
||||
if( bg_model->countFrames == bg_model->params.win_size )
|
||||
{
|
||||
icvUpdateFullWindow( pixel, nChannels, match, g_point, &bg_model->params );
|
||||
if( no_match == -1)
|
||||
icvUpdateFullNoMatch( curr_frame, p, match, g_point, &bg_model_params );
|
||||
}
|
||||
else
|
||||
{
|
||||
icvUpdatePartialWindow( pixel, nChannels, match, g_point, &bg_model_params );
|
||||
if( no_match == -1)
|
||||
icvUpdatePartialNoMatch( pixel, nChannels, match, g_point, &bg_model_params );
|
||||
}
|
||||
icvGetSortKey( nChannels, sort_key, g_point, &bg_model_params );
|
||||
icvInsertionSortGaussians( g_point, sort_key, (CvGaussBGStatModelParams *)&bg_model_params );
|
||||
icvBackgroundTest( nChannels, n, p, match, bg_model );
|
||||
}
|
||||
}
|
||||
|
||||
//foreground filtering
|
||||
|
||||
//filter small regions
|
||||
cvClearMemStorage(bg_model->storage);
|
||||
|
||||
//cvMorphologyEx( bg_model->foreground, bg_model->foreground, 0, 0, CV_MOP_OPEN, 1 );
|
||||
//cvMorphologyEx( bg_model->foreground, bg_model->foreground, 0, 0, CV_MOP_CLOSE, 1 );
|
||||
|
||||
cvFindContours( bg_model->foreground, bg_model->storage, &first_seq, sizeof(CvContour), CV_RETR_LIST );
|
||||
for( seq = first_seq; seq; seq = seq->h_next )
|
||||
{
|
||||
CvContour* cnt = (CvContour*)seq;
|
||||
if( cnt->rect.width * cnt->rect.height < bg_model->params.minArea )
|
||||
{
|
||||
//delete small contour
|
||||
prev_seq = seq->h_prev;
|
||||
if( prev_seq )
|
||||
{
|
||||
prev_seq->h_next = seq->h_next;
|
||||
if( seq->h_next ) seq->h_next->h_prev = prev_seq;
|
||||
}
|
||||
else
|
||||
{
|
||||
first_seq = seq->h_next;
|
||||
if( seq->h_next ) seq->h_next->h_prev = NULL;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
region_count++;
|
||||
}
|
||||
}
|
||||
bg_model->foreground_regions = first_seq;
|
||||
cvZero(bg_model->foreground);
|
||||
cvDrawContours(bg_model->foreground, first_seq, CV_RGB(0, 0, 255), CV_RGB(0, 0, 255), 10, -1);
|
||||
|
||||
return region_count;
|
||||
}
|
||||
|
||||
static void icvInsertionSortGaussians( CvGaussBGPoint* g_point, double* sort_key, CvGaussBGStatModelParams *bg_model_params )
|
||||
{
|
||||
int i, j;
|
||||
for( i = 1; i < bg_model_params->n_gauss; i++ )
|
||||
{
|
||||
double index = sort_key[i];
|
||||
for( j = i; j > 0 && sort_key[j-1] < index; j-- ) //sort decending order
|
||||
{
|
||||
double temp_sort_key = sort_key[j];
|
||||
sort_key[j] = sort_key[j-1];
|
||||
sort_key[j-1] = temp_sort_key;
|
||||
|
||||
CvGaussBGValues temp_gauss_values = g_point->g_values[j];
|
||||
g_point->g_values[j] = g_point->g_values[j-1];
|
||||
g_point->g_values[j-1] = temp_gauss_values;
|
||||
}
|
||||
// sort_key[j] = index;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static int icvMatchTest( double* src_pixel, int nChannels, int* match,
|
||||
const CvGaussBGPoint* g_point,
|
||||
const CvGaussBGStatModelParams *bg_model_params )
|
||||
{
|
||||
int k;
|
||||
int matchPosition=-1;
|
||||
for ( k = 0; k < bg_model_params->n_gauss; k++) match[k]=0;
|
||||
|
||||
for ( k = 0; k < bg_model_params->n_gauss; k++) {
|
||||
double sum_d2 = 0.0;
|
||||
double var_threshold = 0.0;
|
||||
for(int m = 0; m < nChannels; m++){
|
||||
double d = g_point->g_values[k].mean[m]- src_pixel[m];
|
||||
sum_d2 += (d*d);
|
||||
var_threshold += g_point->g_values[k].variance[m];
|
||||
} //difference < STD_LIMIT*STD_LIMIT or difference**2 < STD_LIMIT*STD_LIMIT*VAR
|
||||
var_threshold = bg_model_params->std_threshold*bg_model_params->std_threshold*var_threshold;
|
||||
if(sum_d2 < var_threshold){
|
||||
match[k] = 1;
|
||||
matchPosition = k;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return matchPosition;
|
||||
}
|
||||
|
||||
/*
|
||||
static int icvMatchTest2( double* src_pixel, int nChannels, int* match,
|
||||
const CvGaussBGPoint* g_point,
|
||||
const CvGaussBGStatModelParams *bg_model_params )
|
||||
{
|
||||
int k, m;
|
||||
int matchPosition=-1;
|
||||
|
||||
for( k = 0; k < bg_model_params->n_gauss; k++ )
|
||||
match[k] = 0;
|
||||
|
||||
for( k = 0; k < bg_model_params->n_gauss; k++ )
|
||||
{
|
||||
double sum_d2 = 0.0, var_threshold;
|
||||
for( m = 0; m < nChannels; m++ )
|
||||
{
|
||||
double d = g_point->g_values[k].mean[m]- src_pixel[m];
|
||||
sum_d2 += (d*d) / (g_point->g_values[k].variance[m] * g_point->g_values[k].variance[m]);
|
||||
} //difference < STD_LIMIT*STD_LIMIT or difference**2 < STD_LIMIT*STD_LIMIT*VAR
|
||||
|
||||
var_threshold = bg_model_params->std_threshold*bg_model_params->std_threshold;
|
||||
if( sum_d2 < var_threshold )
|
||||
{
|
||||
match[k] = 1;
|
||||
matchPosition = k;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return matchPosition;
|
||||
}
|
||||
*/
|
||||
|
||||
static void icvUpdateFullWindow( double* src_pixel, int nChannels, int* match,
|
||||
CvGaussBGPoint* g_point,
|
||||
const CvGaussBGStatModelParams *bg_model_params )
|
||||
{
|
||||
const double learning_rate_weight = (1.0/(double)bg_model_params->win_size);
|
||||
for(int k = 0; k < bg_model_params->n_gauss; k++){
|
||||
g_point->g_values[k].weight = g_point->g_values[k].weight +
|
||||
(learning_rate_weight*((double)match[k] -
|
||||
g_point->g_values[k].weight));
|
||||
if(match[k]){
|
||||
double learning_rate_gaussian = (double)match[k]/(g_point->g_values[k].weight*
|
||||
(double)bg_model_params->win_size);
|
||||
for(int m = 0; m < nChannels; m++){
|
||||
const double tmpDiff = src_pixel[m] - g_point->g_values[k].mean[m];
|
||||
g_point->g_values[k].mean[m] = g_point->g_values[k].mean[m] +
|
||||
(learning_rate_gaussian * tmpDiff);
|
||||
g_point->g_values[k].variance[m] = g_point->g_values[k].variance[m]+
|
||||
(learning_rate_gaussian*((tmpDiff*tmpDiff) - g_point->g_values[k].variance[m]));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static void icvUpdatePartialWindow( double* src_pixel, int nChannels, int* match, CvGaussBGPoint* g_point, const CvGaussBGStatModelParams *bg_model_params )
|
||||
{
|
||||
int k, m;
|
||||
int window_current = 0;
|
||||
|
||||
for( k = 0; k < bg_model_params->n_gauss; k++ )
|
||||
window_current += g_point->g_values[k].match_sum;
|
||||
|
||||
for( k = 0; k < bg_model_params->n_gauss; k++ )
|
||||
{
|
||||
g_point->g_values[k].match_sum += match[k];
|
||||
double learning_rate_weight = (1.0/((double)window_current + 1.0)); //increased by one since sum
|
||||
g_point->g_values[k].weight = g_point->g_values[k].weight +
|
||||
(learning_rate_weight*((double)match[k] - g_point->g_values[k].weight));
|
||||
|
||||
if( g_point->g_values[k].match_sum > 0 && match[k] )
|
||||
{
|
||||
double learning_rate_gaussian = (double)match[k]/((double)g_point->g_values[k].match_sum);
|
||||
for( m = 0; m < nChannels; m++ )
|
||||
{
|
||||
const double tmpDiff = src_pixel[m] - g_point->g_values[k].mean[m];
|
||||
g_point->g_values[k].mean[m] = g_point->g_values[k].mean[m] +
|
||||
(learning_rate_gaussian*tmpDiff);
|
||||
g_point->g_values[k].variance[m] = g_point->g_values[k].variance[m]+
|
||||
(learning_rate_gaussian*((tmpDiff*tmpDiff) - g_point->g_values[k].variance[m]));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void icvUpdateFullNoMatch( IplImage* gm_image, int p, int* match,
|
||||
CvGaussBGPoint* g_point,
|
||||
const CvGaussBGStatModelParams *bg_model_params)
|
||||
{
|
||||
int k, m;
|
||||
double alpha;
|
||||
int match_sum_total = 0;
|
||||
|
||||
//new value of last one
|
||||
g_point->g_values[bg_model_params->n_gauss - 1].match_sum = 1;
|
||||
|
||||
//get sum of all but last value of match_sum
|
||||
|
||||
for( k = 0; k < bg_model_params->n_gauss ; k++ )
|
||||
match_sum_total += g_point->g_values[k].match_sum;
|
||||
|
||||
g_point->g_values[bg_model_params->n_gauss - 1].weight = 1./(double)match_sum_total;
|
||||
for( m = 0; m < gm_image->nChannels ; m++ )
|
||||
{
|
||||
// first pass mean is image value
|
||||
g_point->g_values[bg_model_params->n_gauss - 1].variance[m] = bg_model_params->variance_init;
|
||||
g_point->g_values[bg_model_params->n_gauss - 1].mean[m] = (unsigned char)gm_image->imageData[p + m];
|
||||
}
|
||||
|
||||
alpha = 1.0 - (1.0/bg_model_params->win_size);
|
||||
for( k = 0; k < bg_model_params->n_gauss - 1; k++ )
|
||||
{
|
||||
g_point->g_values[k].weight *= alpha;
|
||||
if( match[k] )
|
||||
g_point->g_values[k].weight += alpha;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static void
|
||||
icvUpdatePartialNoMatch(double *pixel,
|
||||
int nChannels,
|
||||
int* /*match*/,
|
||||
CvGaussBGPoint* g_point,
|
||||
const CvGaussBGStatModelParams *bg_model_params)
|
||||
{
|
||||
int k, m;
|
||||
//new value of last one
|
||||
g_point->g_values[bg_model_params->n_gauss - 1].match_sum = 1;
|
||||
|
||||
//get sum of all but last value of match_sum
|
||||
int match_sum_total = 0;
|
||||
for(k = 0; k < bg_model_params->n_gauss ; k++)
|
||||
match_sum_total += g_point->g_values[k].match_sum;
|
||||
|
||||
for(m = 0; m < nChannels; m++)
|
||||
{
|
||||
//first pass mean is image value
|
||||
g_point->g_values[bg_model_params->n_gauss - 1].variance[m] = bg_model_params->variance_init;
|
||||
g_point->g_values[bg_model_params->n_gauss - 1].mean[m] = pixel[m];
|
||||
}
|
||||
for(k = 0; k < bg_model_params->n_gauss; k++)
|
||||
{
|
||||
g_point->g_values[k].weight = (double)g_point->g_values[k].match_sum /
|
||||
(double)match_sum_total;
|
||||
}
|
||||
}
|
||||
|
||||
static void icvGetSortKey( const int nChannels, double* sort_key, const CvGaussBGPoint* g_point,
|
||||
const CvGaussBGStatModelParams *bg_model_params )
|
||||
{
|
||||
int k, m;
|
||||
for( k = 0; k < bg_model_params->n_gauss; k++ )
|
||||
{
|
||||
// Avoid division by zero
|
||||
if( g_point->g_values[k].match_sum > 0 )
|
||||
{
|
||||
// Independence assumption between components
|
||||
double variance_sum = 0.0;
|
||||
for( m = 0; m < nChannels; m++ )
|
||||
variance_sum += g_point->g_values[k].variance[m];
|
||||
|
||||
sort_key[k] = g_point->g_values[k].weight/sqrt(variance_sum);
|
||||
}
|
||||
else
|
||||
sort_key[k]= 0.0;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static void icvBackgroundTest( const int nChannels, int n, int p, int *match, CvGaussBGModel* bg_model )
|
||||
{
|
||||
int m, b;
|
||||
uchar pixelValue = (uchar)255; // will switch to 0 if match found
|
||||
double weight_sum = 0.0;
|
||||
CvGaussBGPoint* g_point = bg_model->g_point;
|
||||
|
||||
for( m = 0; m < nChannels; m++)
|
||||
bg_model->background->imageData[p+m] = (unsigned char)(g_point[n].g_values[0].mean[m]+0.5);
|
||||
|
||||
for( b = 0; b < bg_model->params.n_gauss; b++)
|
||||
{
|
||||
weight_sum += g_point[n].g_values[b].weight;
|
||||
if( match[b] )
|
||||
pixelValue = 0;
|
||||
if( weight_sum > bg_model->params.bg_threshold )
|
||||
break;
|
||||
}
|
||||
|
||||
bg_model->foreground->imageData[p/nChannels] = pixelValue;
|
||||
}
|
||||
|
||||
/* End of file. */
|
||||
@@ -0,0 +1,905 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
#include <stdio.h>
|
||||
|
||||
#undef quad
|
||||
|
||||
#if _MSC_VER >= 1200
|
||||
#pragma warning( disable: 4701 )
|
||||
#endif
|
||||
|
||||
CvCalibFilter::CvCalibFilter()
|
||||
{
|
||||
/* etalon data */
|
||||
etalonType = CV_CALIB_ETALON_USER;
|
||||
etalonParamCount = 0;
|
||||
etalonParams = 0;
|
||||
etalonPointCount = 0;
|
||||
etalonPoints = 0;
|
||||
|
||||
/* camera data */
|
||||
cameraCount = 1;
|
||||
|
||||
memset( points, 0, sizeof(points));
|
||||
memset( undistMap, 0, sizeof(undistMap));
|
||||
undistImg = 0;
|
||||
memset( latestCounts, 0, sizeof(latestCounts));
|
||||
memset( latestPoints, 0, sizeof(latestPoints));
|
||||
maxPoints = 0;
|
||||
framesTotal = 15;
|
||||
framesAccepted = 0;
|
||||
isCalibrated = false;
|
||||
|
||||
imgSize = cvSize(0,0);
|
||||
grayImg = 0;
|
||||
tempImg = 0;
|
||||
storage = 0;
|
||||
|
||||
memset( rectMap, 0, sizeof(rectMap));
|
||||
}
|
||||
|
||||
|
||||
CvCalibFilter::~CvCalibFilter()
|
||||
{
|
||||
SetCameraCount(0);
|
||||
cvFree( &etalonParams );
|
||||
cvFree( &etalonPoints );
|
||||
cvReleaseMat( &grayImg );
|
||||
cvReleaseMat( &tempImg );
|
||||
cvReleaseMat( &undistImg );
|
||||
cvReleaseMemStorage( &storage );
|
||||
}
|
||||
|
||||
|
||||
bool CvCalibFilter::SetEtalon( CvCalibEtalonType type, double* params,
|
||||
int pointCount, CvPoint2D32f* points )
|
||||
{
|
||||
int i, arrSize;
|
||||
|
||||
Stop();
|
||||
|
||||
for( i = 0; i < MAX_CAMERAS; i++ )
|
||||
cvFree( latestPoints + i );
|
||||
|
||||
if( type == CV_CALIB_ETALON_USER || type != etalonType )
|
||||
{
|
||||
cvFree( &etalonParams );
|
||||
}
|
||||
|
||||
etalonType = type;
|
||||
|
||||
switch( etalonType )
|
||||
{
|
||||
case CV_CALIB_ETALON_CHESSBOARD:
|
||||
etalonParamCount = 3;
|
||||
if( !params || cvRound(params[0]) != params[0] || params[0] < 3 ||
|
||||
cvRound(params[1]) != params[1] || params[1] < 3 || params[2] <= 0 )
|
||||
{
|
||||
assert(0);
|
||||
return false;
|
||||
}
|
||||
|
||||
pointCount = cvRound((params[0] - 1)*(params[1] - 1));
|
||||
break;
|
||||
|
||||
case CV_CALIB_ETALON_USER:
|
||||
etalonParamCount = 0;
|
||||
|
||||
if( !points || pointCount < 4 )
|
||||
{
|
||||
assert(0);
|
||||
return false;
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
assert(0);
|
||||
return false;
|
||||
}
|
||||
|
||||
if( etalonParamCount > 0 )
|
||||
{
|
||||
arrSize = etalonParamCount * sizeof(etalonParams[0]);
|
||||
etalonParams = (double*)cvAlloc( arrSize );
|
||||
}
|
||||
|
||||
arrSize = pointCount * sizeof(etalonPoints[0]);
|
||||
|
||||
if( etalonPointCount != pointCount )
|
||||
{
|
||||
cvFree( &etalonPoints );
|
||||
etalonPointCount = pointCount;
|
||||
etalonPoints = (CvPoint2D32f*)cvAlloc( arrSize );
|
||||
}
|
||||
|
||||
switch( etalonType )
|
||||
{
|
||||
case CV_CALIB_ETALON_CHESSBOARD:
|
||||
{
|
||||
int etalonWidth = cvRound( params[0] ) - 1;
|
||||
int etalonHeight = cvRound( params[1] ) - 1;
|
||||
int x, y, k = 0;
|
||||
|
||||
etalonParams[0] = etalonWidth;
|
||||
etalonParams[1] = etalonHeight;
|
||||
etalonParams[2] = params[2];
|
||||
|
||||
for( y = 0; y < etalonHeight; y++ )
|
||||
for( x = 0; x < etalonWidth; x++ )
|
||||
{
|
||||
etalonPoints[k++] = cvPoint2D32f( (etalonWidth - 1 - x)*params[2],
|
||||
y*params[2] );
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
case CV_CALIB_ETALON_USER:
|
||||
memcpy( etalonParams, params, arrSize );
|
||||
memcpy( etalonPoints, points, arrSize );
|
||||
break;
|
||||
|
||||
default:
|
||||
assert(0);
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
CvCalibEtalonType
|
||||
CvCalibFilter::GetEtalon( int* paramCount, const double** params,
|
||||
int* pointCount, const CvPoint2D32f** points ) const
|
||||
{
|
||||
if( paramCount )
|
||||
*paramCount = etalonParamCount;
|
||||
|
||||
if( params )
|
||||
*params = etalonParams;
|
||||
|
||||
if( pointCount )
|
||||
*pointCount = etalonPointCount;
|
||||
|
||||
if( points )
|
||||
*points = etalonPoints;
|
||||
|
||||
return etalonType;
|
||||
}
|
||||
|
||||
|
||||
void CvCalibFilter::SetCameraCount( int count )
|
||||
{
|
||||
Stop();
|
||||
|
||||
if( count != cameraCount )
|
||||
{
|
||||
for( int i = 0; i < cameraCount; i++ )
|
||||
{
|
||||
cvFree( points + i );
|
||||
cvFree( latestPoints + i );
|
||||
cvReleaseMat( &undistMap[i][0] );
|
||||
cvReleaseMat( &undistMap[i][1] );
|
||||
cvReleaseMat( &rectMap[i][0] );
|
||||
cvReleaseMat( &rectMap[i][1] );
|
||||
}
|
||||
|
||||
memset( latestCounts, 0, sizeof(latestPoints) );
|
||||
maxPoints = 0;
|
||||
cameraCount = count;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
bool CvCalibFilter::SetFrames( int frames )
|
||||
{
|
||||
if( frames < 5 )
|
||||
{
|
||||
assert(0);
|
||||
return false;
|
||||
}
|
||||
|
||||
framesTotal = frames;
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
void CvCalibFilter::Stop( bool calibrate )
|
||||
{
|
||||
int i, j;
|
||||
isCalibrated = false;
|
||||
|
||||
// deallocate undistortion maps
|
||||
for( i = 0; i < cameraCount; i++ )
|
||||
{
|
||||
cvReleaseMat( &undistMap[i][0] );
|
||||
cvReleaseMat( &undistMap[i][1] );
|
||||
cvReleaseMat( &rectMap[i][0] );
|
||||
cvReleaseMat( &rectMap[i][1] );
|
||||
}
|
||||
|
||||
if( calibrate && framesAccepted > 0 )
|
||||
{
|
||||
int n = framesAccepted;
|
||||
CvPoint3D32f* buffer =
|
||||
(CvPoint3D32f*)cvAlloc( n * etalonPointCount * sizeof(buffer[0]));
|
||||
CvMat mat;
|
||||
float* rotMatr = (float*)cvAlloc( n * 9 * sizeof(rotMatr[0]));
|
||||
float* transVect = (float*)cvAlloc( n * 3 * sizeof(transVect[0]));
|
||||
int* counts = (int*)cvAlloc( n * sizeof(counts[0]));
|
||||
|
||||
cvInitMatHeader( &mat, 1, sizeof(CvCamera)/sizeof(float), CV_32FC1, 0 );
|
||||
memset( cameraParams, 0, cameraCount * sizeof(cameraParams[0]));
|
||||
|
||||
for( i = 0; i < framesAccepted; i++ )
|
||||
{
|
||||
counts[i] = etalonPointCount;
|
||||
for( j = 0; j < etalonPointCount; j++ )
|
||||
buffer[i * etalonPointCount + j] = cvPoint3D32f( etalonPoints[j].x,
|
||||
etalonPoints[j].y, 0 );
|
||||
}
|
||||
|
||||
for( i = 0; i < cameraCount; i++ )
|
||||
{
|
||||
cvCalibrateCamera( framesAccepted, counts,
|
||||
imgSize, points[i], buffer,
|
||||
cameraParams[i].distortion,
|
||||
cameraParams[i].matrix,
|
||||
transVect, rotMatr, 0 );
|
||||
|
||||
cameraParams[i].imgSize[0] = (float)imgSize.width;
|
||||
cameraParams[i].imgSize[1] = (float)imgSize.height;
|
||||
|
||||
// cameraParams[i].focalLength[0] = cameraParams[i].matrix[0];
|
||||
// cameraParams[i].focalLength[1] = cameraParams[i].matrix[4];
|
||||
|
||||
// cameraParams[i].principalPoint[0] = cameraParams[i].matrix[2];
|
||||
// cameraParams[i].principalPoint[1] = cameraParams[i].matrix[5];
|
||||
|
||||
memcpy( cameraParams[i].rotMatr, rotMatr, 9 * sizeof(rotMatr[0]));
|
||||
memcpy( cameraParams[i].transVect, transVect, 3 * sizeof(transVect[0]));
|
||||
|
||||
mat.data.ptr = (uchar*)(cameraParams + i);
|
||||
|
||||
/* check resultant camera parameters: if there are some INF's or NAN's,
|
||||
stop and reset results */
|
||||
if( !cvCheckArr( &mat, CV_CHECK_RANGE | CV_CHECK_QUIET, -10000, 10000 ))
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
|
||||
isCalibrated = i == cameraCount;
|
||||
|
||||
{/* calibrate stereo cameras */
|
||||
if( cameraCount == 2 )
|
||||
{
|
||||
stereo.camera[0] = &cameraParams[0];
|
||||
stereo.camera[1] = &cameraParams[1];
|
||||
|
||||
icvStereoCalibration( framesAccepted, counts,
|
||||
imgSize,
|
||||
points[0],points[1],
|
||||
buffer,
|
||||
&stereo);
|
||||
|
||||
for( i = 0; i < 9; i++ )
|
||||
{
|
||||
stereo.fundMatr[i] = stereo.fundMatr[i];
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
cvFree( &buffer );
|
||||
cvFree( &counts );
|
||||
cvFree( &rotMatr );
|
||||
cvFree( &transVect );
|
||||
}
|
||||
|
||||
framesAccepted = 0;
|
||||
}
|
||||
|
||||
|
||||
bool CvCalibFilter::FindEtalon( IplImage** imgs )
|
||||
{
|
||||
return FindEtalon( (CvMat**)imgs );
|
||||
}
|
||||
|
||||
|
||||
bool CvCalibFilter::FindEtalon( CvMat** mats )
|
||||
{
|
||||
bool result = true;
|
||||
|
||||
if( !mats || etalonPointCount == 0 )
|
||||
{
|
||||
assert(0);
|
||||
result = false;
|
||||
}
|
||||
|
||||
if( result )
|
||||
{
|
||||
int i, tempPointCount0 = etalonPointCount*2;
|
||||
|
||||
for( i = 0; i < cameraCount; i++ )
|
||||
{
|
||||
if( !latestPoints[i] )
|
||||
latestPoints[i] = (CvPoint2D32f*)
|
||||
cvAlloc( tempPointCount0*2*sizeof(latestPoints[0]));
|
||||
}
|
||||
|
||||
for( i = 0; i < cameraCount; i++ )
|
||||
{
|
||||
CvSize size;
|
||||
int tempPointCount = tempPointCount0;
|
||||
bool found = false;
|
||||
|
||||
if( !CV_IS_MAT(mats[i]) && !CV_IS_IMAGE(mats[i]))
|
||||
{
|
||||
assert(0);
|
||||
break;
|
||||
}
|
||||
|
||||
size = cvGetSize(mats[i]);
|
||||
|
||||
if( size.width != imgSize.width || size.height != imgSize.height )
|
||||
{
|
||||
imgSize = size;
|
||||
}
|
||||
|
||||
if( !grayImg || grayImg->width != imgSize.width ||
|
||||
grayImg->height != imgSize.height )
|
||||
{
|
||||
cvReleaseMat( &grayImg );
|
||||
cvReleaseMat( &tempImg );
|
||||
grayImg = cvCreateMat( imgSize.height, imgSize.width, CV_8UC1 );
|
||||
tempImg = cvCreateMat( imgSize.height, imgSize.width, CV_8UC1 );
|
||||
}
|
||||
|
||||
if( !storage )
|
||||
storage = cvCreateMemStorage();
|
||||
|
||||
switch( etalonType )
|
||||
{
|
||||
case CV_CALIB_ETALON_CHESSBOARD:
|
||||
if( CV_MAT_CN(cvGetElemType(mats[i])) == 1 )
|
||||
cvCopy( mats[i], grayImg );
|
||||
else
|
||||
cvCvtColor( mats[i], grayImg, CV_BGR2GRAY );
|
||||
found = cvFindChessBoardCornerGuesses( grayImg, tempImg, storage,
|
||||
cvSize( cvRound(etalonParams[0]),
|
||||
cvRound(etalonParams[1])),
|
||||
latestPoints[i], &tempPointCount ) != 0;
|
||||
if( found )
|
||||
cvFindCornerSubPix( grayImg, latestPoints[i], tempPointCount,
|
||||
cvSize(5,5), cvSize(-1,-1),
|
||||
cvTermCriteria(CV_TERMCRIT_ITER|CV_TERMCRIT_EPS,10,0.1));
|
||||
break;
|
||||
default:
|
||||
assert(0);
|
||||
result = false;
|
||||
break;
|
||||
}
|
||||
|
||||
latestCounts[i] = found ? tempPointCount : -tempPointCount;
|
||||
result = result && found;
|
||||
}
|
||||
}
|
||||
|
||||
if( storage )
|
||||
cvClearMemStorage( storage );
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
bool CvCalibFilter::Push( const CvPoint2D32f** pts )
|
||||
{
|
||||
bool result = true;
|
||||
int i, newMaxPoints = etalonPointCount*(MAX(framesAccepted,framesTotal) + 1);
|
||||
|
||||
isCalibrated = false;
|
||||
|
||||
if( !pts )
|
||||
{
|
||||
for( i = 0; i < cameraCount; i++ )
|
||||
if( latestCounts[i] <= 0 )
|
||||
return false;
|
||||
pts = (const CvPoint2D32f**)latestPoints;
|
||||
}
|
||||
|
||||
for( i = 0; i < cameraCount; i++ )
|
||||
{
|
||||
if( !pts[i] )
|
||||
{
|
||||
assert(0);
|
||||
break;
|
||||
}
|
||||
|
||||
if( maxPoints < newMaxPoints )
|
||||
{
|
||||
CvPoint2D32f* prev = points[i];
|
||||
cvFree( points + i );
|
||||
points[i] = (CvPoint2D32f*)cvAlloc( newMaxPoints * sizeof(prev[0]));
|
||||
memcpy( points[i], prev, maxPoints * sizeof(prev[0]));
|
||||
}
|
||||
|
||||
memcpy( points[i] + framesAccepted*etalonPointCount, pts[i],
|
||||
etalonPointCount*sizeof(points[0][0]));
|
||||
}
|
||||
|
||||
if( maxPoints < newMaxPoints )
|
||||
maxPoints = newMaxPoints;
|
||||
|
||||
result = i == cameraCount;
|
||||
|
||||
if( ++framesAccepted >= framesTotal )
|
||||
Stop( true );
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
bool CvCalibFilter::GetLatestPoints( int idx, CvPoint2D32f** pts,
|
||||
int* count, bool* found )
|
||||
{
|
||||
int n;
|
||||
|
||||
if( (unsigned)idx >= (unsigned)cameraCount ||
|
||||
!pts || !count || !found )
|
||||
{
|
||||
assert(0);
|
||||
return false;
|
||||
}
|
||||
|
||||
n = latestCounts[idx];
|
||||
|
||||
*found = n > 0;
|
||||
*count = abs(n);
|
||||
*pts = latestPoints[idx];
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
void CvCalibFilter::DrawPoints( IplImage** dst )
|
||||
{
|
||||
DrawPoints( (CvMat**)dst );
|
||||
}
|
||||
|
||||
|
||||
void CvCalibFilter::DrawPoints( CvMat** dstarr )
|
||||
{
|
||||
int i, j;
|
||||
|
||||
if( !dstarr )
|
||||
{
|
||||
assert(0);
|
||||
return;
|
||||
}
|
||||
|
||||
if( latestCounts )
|
||||
{
|
||||
for( i = 0; i < cameraCount; i++ )
|
||||
{
|
||||
if( dstarr[i] && latestCounts[i] )
|
||||
{
|
||||
CvMat dst_stub, *dst;
|
||||
int count = 0;
|
||||
bool found = false;
|
||||
CvPoint2D32f* pts = 0;
|
||||
|
||||
GetLatestPoints( i, &pts, &count, &found );
|
||||
|
||||
dst = cvGetMat( dstarr[i], &dst_stub );
|
||||
|
||||
static const CvScalar line_colors[] =
|
||||
{
|
||||
{{0,0,255}},
|
||||
{{0,128,255}},
|
||||
{{0,200,200}},
|
||||
{{0,255,0}},
|
||||
{{200,200,0}},
|
||||
{{255,0,0}},
|
||||
{{255,0,255}}
|
||||
};
|
||||
|
||||
const int colorCount = sizeof(line_colors)/sizeof(line_colors[0]);
|
||||
const int r = 4;
|
||||
CvScalar color = line_colors[0];
|
||||
CvPoint prev_pt = { 0, 0};
|
||||
|
||||
for( j = 0; j < count; j++ )
|
||||
{
|
||||
CvPoint pt;
|
||||
pt.x = cvRound(pts[j].x);
|
||||
pt.y = cvRound(pts[j].y);
|
||||
|
||||
if( found )
|
||||
{
|
||||
if( etalonType == CV_CALIB_ETALON_CHESSBOARD )
|
||||
color = line_colors[(j/cvRound(etalonParams[0]))%colorCount];
|
||||
else
|
||||
color = CV_RGB(0,255,0);
|
||||
|
||||
if( j != 0 )
|
||||
cvLine( dst, prev_pt, pt, color, 1, CV_AA );
|
||||
}
|
||||
|
||||
cvLine( dst, cvPoint( pt.x - r, pt.y - r ),
|
||||
cvPoint( pt.x + r, pt.y + r ), color, 1, CV_AA );
|
||||
|
||||
cvLine( dst, cvPoint( pt.x - r, pt.y + r),
|
||||
cvPoint( pt.x + r, pt.y - r), color, 1, CV_AA );
|
||||
|
||||
cvCircle( dst, pt, r+1, color, 1, CV_AA );
|
||||
|
||||
prev_pt = pt;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* Get total number of frames and already accepted pair of frames */
|
||||
int CvCalibFilter::GetFrameCount( int* total ) const
|
||||
{
|
||||
if( total )
|
||||
*total = framesTotal;
|
||||
|
||||
return framesAccepted;
|
||||
}
|
||||
|
||||
|
||||
/* Get camera parameters for specified camera. If camera is not calibrated
|
||||
the function returns 0 */
|
||||
const CvCamera* CvCalibFilter::GetCameraParams( int idx ) const
|
||||
{
|
||||
if( (unsigned)idx >= (unsigned)cameraCount )
|
||||
{
|
||||
assert(0);
|
||||
return 0;
|
||||
}
|
||||
|
||||
return isCalibrated ? cameraParams + idx : 0;
|
||||
}
|
||||
|
||||
|
||||
/* Get camera parameters for specified camera. If camera is not calibrated
|
||||
the function returns 0 */
|
||||
const CvStereoCamera* CvCalibFilter::GetStereoParams() const
|
||||
{
|
||||
if( !(isCalibrated && cameraCount == 2) )
|
||||
{
|
||||
assert(0);
|
||||
return 0;
|
||||
}
|
||||
|
||||
return &stereo;
|
||||
}
|
||||
|
||||
|
||||
/* Sets camera parameters for all cameras */
|
||||
bool CvCalibFilter::SetCameraParams( CvCamera* params )
|
||||
{
|
||||
CvMat mat;
|
||||
int arrSize;
|
||||
|
||||
Stop();
|
||||
|
||||
if( !params )
|
||||
{
|
||||
assert(0);
|
||||
return false;
|
||||
}
|
||||
|
||||
arrSize = cameraCount * sizeof(params[0]);
|
||||
|
||||
cvInitMatHeader( &mat, 1, cameraCount * (arrSize/sizeof(float)),
|
||||
CV_32FC1, params );
|
||||
cvCheckArr( &mat, CV_CHECK_RANGE, -10000, 10000 );
|
||||
|
||||
memcpy( cameraParams, params, arrSize );
|
||||
isCalibrated = true;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
bool CvCalibFilter::SaveCameraParams( const char* filename )
|
||||
{
|
||||
if( isCalibrated )
|
||||
{
|
||||
int i, j;
|
||||
|
||||
FILE* f = fopen( filename, "w" );
|
||||
|
||||
if( !f ) return false;
|
||||
|
||||
fprintf( f, "%d\n\n", cameraCount );
|
||||
|
||||
for( i = 0; i < cameraCount; i++ )
|
||||
{
|
||||
for( j = 0; j < (int)(sizeof(cameraParams[i])/sizeof(float)); j++ )
|
||||
{
|
||||
fprintf( f, "%15.10f ", ((float*)(cameraParams + i))[j] );
|
||||
}
|
||||
fprintf( f, "\n\n" );
|
||||
}
|
||||
|
||||
/* Save stereo params */
|
||||
|
||||
/* Save quad */
|
||||
for( i = 0; i < 2; i++ )
|
||||
{
|
||||
for( j = 0; j < 4; j++ )
|
||||
{
|
||||
fprintf(f, "%15.10f ", stereo.quad[i][j].x );
|
||||
fprintf(f, "%15.10f ", stereo.quad[i][j].y );
|
||||
}
|
||||
fprintf(f, "\n");
|
||||
}
|
||||
|
||||
/* Save coeffs */
|
||||
for( i = 0; i < 2; i++ )
|
||||
{
|
||||
for( j = 0; j < 9; j++ )
|
||||
{
|
||||
fprintf(f, "%15.10lf ", stereo.coeffs[i][j/3][j%3] );
|
||||
}
|
||||
fprintf(f, "\n");
|
||||
}
|
||||
|
||||
|
||||
fclose(f);
|
||||
return true;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
bool CvCalibFilter::LoadCameraParams( const char* filename )
|
||||
{
|
||||
int i, j;
|
||||
int d = 0;
|
||||
FILE* f = fopen( filename, "r" );
|
||||
|
||||
isCalibrated = false;
|
||||
|
||||
if( !f ) return false;
|
||||
|
||||
if( fscanf( f, "%d", &d ) != 1 || d <= 0 || d > 10 )
|
||||
return false;
|
||||
|
||||
SetCameraCount( d );
|
||||
|
||||
for( i = 0; i < cameraCount; i++ )
|
||||
{
|
||||
for( j = 0; j < (int)(sizeof(cameraParams[i])/sizeof(float)); j++ )
|
||||
{
|
||||
fscanf( f, "%f", &((float*)(cameraParams + i))[j] );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* Load stereo params */
|
||||
|
||||
/* load quad */
|
||||
for( i = 0; i < 2; i++ )
|
||||
{
|
||||
for( j = 0; j < 4; j++ )
|
||||
{
|
||||
fscanf(f, "%f ", &(stereo.quad[i][j].x) );
|
||||
fscanf(f, "%f ", &(stereo.quad[i][j].y) );
|
||||
}
|
||||
}
|
||||
|
||||
/* Load coeffs */
|
||||
for( i = 0; i < 2; i++ )
|
||||
{
|
||||
for( j = 0; j < 9; j++ )
|
||||
{
|
||||
fscanf(f, "%lf ", &(stereo.coeffs[i][j/3][j%3]) );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
fclose(f);
|
||||
|
||||
stereo.warpSize = cvSize( cvRound(cameraParams[0].imgSize[0]), cvRound(cameraParams[0].imgSize[1]));
|
||||
|
||||
isCalibrated = true;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
bool CvCalibFilter::Rectify( IplImage** srcarr, IplImage** dstarr )
|
||||
{
|
||||
return Rectify( (CvMat**)srcarr, (CvMat**)dstarr );
|
||||
}
|
||||
|
||||
bool CvCalibFilter::Rectify( CvMat** srcarr, CvMat** dstarr )
|
||||
{
|
||||
int i;
|
||||
|
||||
if( !srcarr || !dstarr )
|
||||
{
|
||||
assert(0);
|
||||
return false;
|
||||
}
|
||||
|
||||
if( isCalibrated && cameraCount == 2 )
|
||||
{
|
||||
for( i = 0; i < cameraCount; i++ )
|
||||
{
|
||||
if( srcarr[i] && dstarr[i] )
|
||||
{
|
||||
IplImage src_stub, *src;
|
||||
IplImage dst_stub, *dst;
|
||||
|
||||
src = cvGetImage( srcarr[i], &src_stub );
|
||||
dst = cvGetImage( dstarr[i], &dst_stub );
|
||||
|
||||
if( src->imageData == dst->imageData )
|
||||
{
|
||||
if( !undistImg ||
|
||||
undistImg->width != src->width ||
|
||||
undistImg->height != src->height ||
|
||||
CV_MAT_CN(undistImg->type) != src->nChannels )
|
||||
{
|
||||
cvReleaseMat( &undistImg );
|
||||
undistImg = cvCreateMat( src->height, src->width,
|
||||
CV_8U + (src->nChannels-1)*8 );
|
||||
}
|
||||
cvCopy( src, undistImg );
|
||||
src = cvGetImage( undistImg, &src_stub );
|
||||
}
|
||||
|
||||
cvZero( dst );
|
||||
|
||||
if( !rectMap[i][0] || rectMap[i][0]->width != src->width ||
|
||||
rectMap[i][0]->height != src->height )
|
||||
{
|
||||
cvReleaseMat( &rectMap[i][0] );
|
||||
cvReleaseMat( &rectMap[i][1] );
|
||||
rectMap[i][0] = cvCreateMat(stereo.warpSize.height,stereo.warpSize.width,CV_32FC1);
|
||||
rectMap[i][1] = cvCreateMat(stereo.warpSize.height,stereo.warpSize.width,CV_32FC1);
|
||||
cvComputePerspectiveMap(stereo.coeffs[i], rectMap[i][0], rectMap[i][1]);
|
||||
}
|
||||
cvRemap( src, dst, rectMap[i][0], rectMap[i][1] );
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
for( i = 0; i < cameraCount; i++ )
|
||||
{
|
||||
if( srcarr[i] != dstarr[i] )
|
||||
cvCopy( srcarr[i], dstarr[i] );
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CvCalibFilter::Undistort( IplImage** srcarr, IplImage** dstarr )
|
||||
{
|
||||
return Undistort( (CvMat**)srcarr, (CvMat**)dstarr );
|
||||
}
|
||||
|
||||
|
||||
bool CvCalibFilter::Undistort( CvMat** srcarr, CvMat** dstarr )
|
||||
{
|
||||
int i;
|
||||
|
||||
if( !srcarr || !dstarr )
|
||||
{
|
||||
assert(0);
|
||||
return false;
|
||||
}
|
||||
|
||||
if( isCalibrated )
|
||||
{
|
||||
for( i = 0; i < cameraCount; i++ )
|
||||
{
|
||||
if( srcarr[i] && dstarr[i] )
|
||||
{
|
||||
CvMat src_stub, *src;
|
||||
CvMat dst_stub, *dst;
|
||||
|
||||
src = cvGetMat( srcarr[i], &src_stub );
|
||||
dst = cvGetMat( dstarr[i], &dst_stub );
|
||||
|
||||
if( src->data.ptr == dst->data.ptr )
|
||||
{
|
||||
if( !undistImg || undistImg->width != src->width ||
|
||||
undistImg->height != src->height ||
|
||||
CV_ARE_TYPES_EQ( undistImg, src ))
|
||||
{
|
||||
cvReleaseMat( &undistImg );
|
||||
undistImg = cvCreateMat( src->height, src->width, src->type );
|
||||
}
|
||||
|
||||
cvCopy( src, undistImg );
|
||||
src = undistImg;
|
||||
}
|
||||
|
||||
#if 1
|
||||
{
|
||||
CvMat A = cvMat( 3, 3, CV_32FC1, cameraParams[i].matrix );
|
||||
CvMat k = cvMat( 1, 4, CV_32FC1, cameraParams[i].distortion );
|
||||
|
||||
if( !undistMap[i][0] || undistMap[i][0]->width != src->width ||
|
||||
undistMap[i][0]->height != src->height )
|
||||
{
|
||||
cvReleaseMat( &undistMap[i][0] );
|
||||
cvReleaseMat( &undistMap[i][1] );
|
||||
undistMap[i][0] = cvCreateMat( src->height, src->width, CV_32FC1 );
|
||||
undistMap[i][1] = cvCreateMat( src->height, src->width, CV_32FC1 );
|
||||
cvInitUndistortMap( &A, &k, undistMap[i][0], undistMap[i][1] );
|
||||
}
|
||||
|
||||
cvRemap( src, dst, undistMap[i][0], undistMap[i][1] );
|
||||
#else
|
||||
cvUndistort2( src, dst, &A, &k );
|
||||
#endif
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
for( i = 0; i < cameraCount; i++ )
|
||||
{
|
||||
if( srcarr[i] != dstarr[i] )
|
||||
cvCopy( srcarr[i], dstarr[i] );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -0,0 +1,709 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
#if 0
|
||||
|
||||
#include <float.h>
|
||||
#include <limits.h>
|
||||
#include <stdio.h>
|
||||
|
||||
|
||||
#include "_cvutils.h"
|
||||
#include "_cvwrap.h"
|
||||
|
||||
/*typedef struct CvCliqueFinder
|
||||
{
|
||||
CvGraph* graph;
|
||||
int** adj_matr;
|
||||
int N; //graph size
|
||||
|
||||
// stacks, counters etc/
|
||||
int k; //stack size
|
||||
int* current_comp;
|
||||
int** All;
|
||||
|
||||
int* ne;
|
||||
int* ce;
|
||||
int* fixp; //node with minimal disconnections
|
||||
int* nod;
|
||||
int* s; //for selected candidate
|
||||
int status;
|
||||
int best_score;
|
||||
|
||||
} CvCliqueFinder;
|
||||
*/
|
||||
|
||||
#define GO 1
|
||||
#define BACK 2
|
||||
#define PEREBOR 3
|
||||
#define NEXT PEREBOR
|
||||
#define END 4
|
||||
|
||||
|
||||
#define CV_GET_ADJ_VTX( vertex, edge ) \
|
||||
( \
|
||||
assert(edge->vtx[0]==vertex||edge->vtx[1] == vertex ), \
|
||||
(edge->vtx[0] == vertex)?edge->vtx[1]:edge->vtx[0] \
|
||||
)
|
||||
|
||||
|
||||
#define NUMBER( v ) ((v)->flags >> 1 )
|
||||
|
||||
void _MarkNodes( CvGraph* graph )
|
||||
{
|
||||
//set number of vertices to their flags
|
||||
for( int i = 0; i < graph->total; i++ )
|
||||
{
|
||||
CvGraphVtx* ver = cvGetGraphVtx( graph, i );
|
||||
if( ver )
|
||||
{
|
||||
ver->flags = i<<1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void _FillAdjMatrix( CvGraph* graph, int** connected, int reverse )
|
||||
{
|
||||
//assume all vertices are marked
|
||||
for( int i = 0; i < graph->total; i++ )
|
||||
{
|
||||
for( int j = 0; j < graph->total; j++ )
|
||||
{
|
||||
connected[i][j] = 0|reverse;
|
||||
}
|
||||
//memset( connected[i], 0, sizeof(int)*graph->total );
|
||||
CvGraphVtx* ver = cvGetGraphVtx( graph, i );
|
||||
if( ver )
|
||||
{
|
||||
connected[i][i] = 1;
|
||||
for( CvGraphEdge* e = ver->first; e ; e = CV_NEXT_GRAPH_EDGE( e, ver ) )
|
||||
{
|
||||
CvGraphVtx* v = CV_GET_ADJ_VTX( ver, e );
|
||||
connected[i][NUMBER(v)] = 1^reverse;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void cvStartFindCliques( CvGraph* graph, CvCliqueFinder* finder, int reverse, int weighted, int weighted_edges )
|
||||
{
|
||||
int i;
|
||||
|
||||
if (weighted)
|
||||
{
|
||||
finder->weighted = 1;
|
||||
finder->best_weight = 0;
|
||||
finder->vertex_weights = (float*)malloc( sizeof(float)*(graph->total+1));
|
||||
finder->cur_weight = (float*)malloc( sizeof(float)*(graph->total+1));
|
||||
finder->cand_weight = (float*)malloc( sizeof(float)*(graph->total+1));
|
||||
|
||||
finder->cur_weight[0] = 0;
|
||||
finder->cand_weight[0] = 0;
|
||||
for( i = 0 ; i < graph->total; i++ )
|
||||
{
|
||||
CvGraphWeightedVtx* ver = (CvGraphWeightedVtx*)cvGetGraphVtx( graph, i );
|
||||
assert(ver);
|
||||
assert(ver->weight>=0);
|
||||
finder->vertex_weights[i] = ver->weight;
|
||||
finder->cand_weight[0] += ver->weight;
|
||||
}
|
||||
}
|
||||
else finder->weighted = 0;
|
||||
|
||||
if (weighted_edges)
|
||||
{
|
||||
finder->weighted_edges = 1;
|
||||
//finder->best_weight = 0;
|
||||
finder->edge_weights = (float*)malloc( sizeof(float)*(graph->total)*(graph->total));
|
||||
//finder->cur_weight = (float*)malloc( sizeof(float)*(graph->total+1));
|
||||
//finder->cand_weight = (float*)malloc( sizeof(float)*(graph->total+1));
|
||||
|
||||
//finder->cur_weight[0] = 0;
|
||||
//finder->cand_weight[0] = 0;
|
||||
memset( finder->edge_weights, 0, sizeof(float)*(graph->total)*(graph->total) );
|
||||
for( i = 0 ; i < graph->total; i++ )
|
||||
{
|
||||
CvGraphVtx* ver1 = cvGetGraphVtx( graph, i );
|
||||
if(!ver1) continue;
|
||||
for( int j = i ; j < graph->total; j++ )
|
||||
{
|
||||
CvGraphVtx* ver2 = cvGetGraphVtx( graph, j );
|
||||
if(!ver2) continue;
|
||||
CvGraphEdge* edge = cvFindGraphEdgeByPtr( graph, ver1, ver2 );
|
||||
if( edge )
|
||||
{
|
||||
assert( ((CvGraphWeightedEdge*)edge)->weight >= 0 );
|
||||
finder->edge_weights[ i * graph->total + j ] =
|
||||
finder->edge_weights[ j * graph->total + i ] = ((CvGraphWeightedEdge*)edge)->weight;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
else finder->weighted_edges = 0;
|
||||
|
||||
|
||||
//int* Compsub; //current component (vertex stack)
|
||||
finder->k = 0; //counter of steps
|
||||
int N = finder->N = graph->total;
|
||||
finder->current_comp = new int[N];
|
||||
finder->All = new int*[N];
|
||||
for( i = 0 ; i < finder->N; i++ )
|
||||
{
|
||||
finder->All[i] = new int[N];
|
||||
}
|
||||
|
||||
finder->ne = new int[N+1];
|
||||
finder->ce = new int[N+1];
|
||||
finder->fixp = new int[N+1]; //node with minimal disconnections
|
||||
finder->nod = new int[N+1];
|
||||
finder->s = new int[N+1]; //for selected candidate
|
||||
|
||||
//form adj matrix
|
||||
finder->adj_matr = new int*[N]; //assume filled with 0
|
||||
for( i = 0 ; i < N; i++ )
|
||||
{
|
||||
finder->adj_matr[i] = new int[N];
|
||||
}
|
||||
|
||||
//set number to vertices
|
||||
_MarkNodes( graph );
|
||||
_FillAdjMatrix( graph, finder->adj_matr, reverse );
|
||||
|
||||
//init all arrays
|
||||
int k = finder->k = 0; //stack size
|
||||
memset( finder->All[k], 0, sizeof(int) * N );
|
||||
for( i = 0; i < N; i++ ) finder->All[k][i] = i;
|
||||
finder->ne[0] = 0;
|
||||
finder->ce[0] = N;
|
||||
|
||||
finder->status = GO;
|
||||
finder->best_score = 0;
|
||||
|
||||
}
|
||||
|
||||
void cvEndFindCliques( CvCliqueFinder* finder )
|
||||
{
|
||||
int i;
|
||||
|
||||
//int* Compsub; //current component (vertex stack)
|
||||
delete finder->current_comp;
|
||||
for( i = 0 ; i < finder->N; i++ )
|
||||
{
|
||||
delete finder->All[i];
|
||||
}
|
||||
delete finder->All;
|
||||
|
||||
delete finder->ne;
|
||||
delete finder->ce;
|
||||
delete finder->fixp; //node with minimal disconnections
|
||||
delete finder->nod;
|
||||
delete finder->s; //for selected candidate
|
||||
|
||||
//delete adj matrix
|
||||
for( i = 0 ; i < finder->N; i++ )
|
||||
{
|
||||
delete finder->adj_matr[i];
|
||||
}
|
||||
delete finder->adj_matr;
|
||||
|
||||
if(finder->weighted)
|
||||
{
|
||||
free(finder->vertex_weights);
|
||||
free(finder->cur_weight);
|
||||
free(finder->cand_weight);
|
||||
}
|
||||
if(finder->weighted_edges)
|
||||
{
|
||||
free(finder->edge_weights);
|
||||
}
|
||||
}
|
||||
|
||||
int cvFindNextMaximalClique( CvCliqueFinder* finder )
|
||||
{
|
||||
int** connected = finder->adj_matr;
|
||||
// int N = finder->N; //graph size
|
||||
|
||||
// stacks, counters etc/
|
||||
int k = finder->k; //stack size
|
||||
int* Compsub = finder->current_comp;
|
||||
int** All = finder->All;
|
||||
|
||||
int* ne = finder->ne;
|
||||
int* ce = finder->ce;
|
||||
int* fixp = finder->fixp; //node with minimal disconnections
|
||||
int* nod = finder->nod;
|
||||
int* s = finder->s; //for selected candidate
|
||||
|
||||
//START
|
||||
while( k >= 0)
|
||||
{
|
||||
int* old = All[k];
|
||||
switch(finder->status)
|
||||
{
|
||||
case GO://Forward step
|
||||
/* we have all sets and will choose fixed point */
|
||||
{
|
||||
//check potential size of clique
|
||||
if( (!finder->weighted) && (k + ce[k] - ne[k] < finder->best_score) )
|
||||
{
|
||||
finder->status = BACK;
|
||||
break;
|
||||
}
|
||||
//check potential weight
|
||||
if( finder->weighted && !finder->weighted_edges &&
|
||||
finder->cur_weight[k] + finder->cand_weight[k] < finder->best_weight )
|
||||
{
|
||||
finder->status = BACK;
|
||||
break;
|
||||
}
|
||||
|
||||
int minnod = ce[k];
|
||||
nod[k] = 0;
|
||||
|
||||
//for every vertex of All determine counter value and choose minimum
|
||||
for( int i = 0; i < ce[k] && minnod != 0; i++)
|
||||
{
|
||||
int p = old[i]; //current point
|
||||
int count = 0; //counter
|
||||
int pos = 0;
|
||||
|
||||
/* Count disconnections with candidates */
|
||||
for (int j = ne[k]; j < ce[k] && (count < minnod); j++)
|
||||
{
|
||||
if ( !connected[p][old[j]] )
|
||||
{
|
||||
count++;
|
||||
/* Save position of potential candidate */
|
||||
pos = j;
|
||||
}
|
||||
}
|
||||
|
||||
/* Test new minimum */
|
||||
if (count < minnod)
|
||||
{
|
||||
fixp[k] = p; //set current point as fixed
|
||||
minnod = count; //new value for minnod
|
||||
if (i < ne[k]) //if current fixed point belongs to 'not'
|
||||
{
|
||||
s[k] = pos; //s - selected candidate
|
||||
}
|
||||
else
|
||||
{
|
||||
s[k] = i; //selected candidate is fixed point itself
|
||||
/* preincr */
|
||||
nod[k] = 1; //nod is aux variable, 1 means fixp == s
|
||||
}
|
||||
}
|
||||
}//for
|
||||
|
||||
nod[k] = minnod + nod[k];
|
||||
finder->status = NEXT;//go to backtrackcycle
|
||||
}
|
||||
break;
|
||||
case NEXT:
|
||||
//here we will look for candidate to translate into not
|
||||
//s[k] now contains index of choosen candidate
|
||||
{
|
||||
int* new_ = All[k+1];
|
||||
if( nod[k] != 0 )
|
||||
{
|
||||
//swap selected and first candidate
|
||||
int i, p = old[s[k]];
|
||||
old[s[k]] = old[ne[k]];
|
||||
int sel = old[ne[k]] = p;
|
||||
|
||||
int newne = 0;
|
||||
//fill new set 'not'
|
||||
for ( i = 0; i < ne[k]; i++)
|
||||
{
|
||||
if (connected[sel][old[i]])
|
||||
{
|
||||
new_[newne] = old[i];
|
||||
newne++;
|
||||
|
||||
}
|
||||
}
|
||||
//fill new set 'candidate'
|
||||
int newce = newne;
|
||||
i++;//skip selected candidate
|
||||
|
||||
float candweight = 0;
|
||||
|
||||
for (; i < ce[k]; i++)
|
||||
{
|
||||
if (connected[sel][old[i]])
|
||||
{
|
||||
new_[newce] = old[i];
|
||||
|
||||
if( finder->weighted )
|
||||
candweight += finder->vertex_weights[old[i]];
|
||||
|
||||
newce++;
|
||||
}
|
||||
}
|
||||
|
||||
nod[k]--;
|
||||
|
||||
//add selected to stack
|
||||
Compsub[k] = sel;
|
||||
|
||||
k++;
|
||||
assert( k <= finder->N );
|
||||
if( finder->weighted )
|
||||
{
|
||||
//update weights of current clique and candidates
|
||||
finder->cur_weight[k] = finder->cur_weight[k-1] + finder->vertex_weights[sel];
|
||||
finder->cand_weight[k] = candweight;
|
||||
}
|
||||
if( finder->weighted_edges )
|
||||
{
|
||||
//update total weight by edge weights
|
||||
float added = 0;
|
||||
for( int ind = 0; ind < k-1; ind++ )
|
||||
{
|
||||
added += finder->edge_weights[ Compsub[ind] * finder->N + sel ];
|
||||
}
|
||||
finder->cur_weight[k] += added;
|
||||
}
|
||||
|
||||
//check if 'not' and 'cand' are both empty
|
||||
if( newce == 0 )
|
||||
{
|
||||
finder->best_score = MAX(finder->best_score, k );
|
||||
|
||||
if( finder->weighted )
|
||||
finder->best_weight = MAX( finder->best_weight, finder->cur_weight[k] );
|
||||
/*FILE* file = fopen("cliques.txt", "a" );
|
||||
|
||||
for (int t=0; t<k; t++)
|
||||
{
|
||||
fprintf(file, "%d ", Compsub[t]);
|
||||
}
|
||||
fprintf(file, "\n");
|
||||
|
||||
fclose(file);
|
||||
*/
|
||||
|
||||
//output new clique//************************
|
||||
finder->status = BACK;
|
||||
finder->k = k;
|
||||
|
||||
return CLIQUE_FOUND;
|
||||
|
||||
}
|
||||
else //check nonempty set of candidates
|
||||
if( newne < newce )
|
||||
{
|
||||
//go further
|
||||
ne[k] = newne;
|
||||
ce[k] = newce;
|
||||
finder->status = GO;
|
||||
break;
|
||||
}
|
||||
|
||||
}
|
||||
else
|
||||
finder->status = BACK;
|
||||
|
||||
}
|
||||
break;
|
||||
|
||||
case BACK:
|
||||
{
|
||||
//decrease stack
|
||||
k--;
|
||||
old = All[k];
|
||||
if( k < 0 ) break;
|
||||
|
||||
//add to not
|
||||
ne[k]++;
|
||||
|
||||
if( nod[k] > 0 )
|
||||
{
|
||||
//select next candidate
|
||||
for( s[k] = ne[k]; s[k] < ce[k]; s[k]++ )
|
||||
{
|
||||
if( !connected[fixp[k]][old[s[k]]])
|
||||
break;
|
||||
}
|
||||
assert( s[k] < ce[k] );
|
||||
finder->status = NEXT;
|
||||
}
|
||||
else
|
||||
finder->status = BACK;
|
||||
|
||||
}
|
||||
break;
|
||||
case END: assert(0);
|
||||
|
||||
}
|
||||
}//end while
|
||||
|
||||
finder->status = END;
|
||||
return CLIQUE_END;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
void cvBronKerbosch( CvGraph* graph )
|
||||
{
|
||||
int* Compsub; //current component (vertex stack)
|
||||
int k = 0; //counter of steps
|
||||
int N = graph->total;
|
||||
int i;
|
||||
Compsub = new int[N];
|
||||
int** All = new int*[N];
|
||||
for( i = 0 ; i < N; i++ )
|
||||
{
|
||||
All[i] = new int[N];
|
||||
}
|
||||
|
||||
int* ne = new int[N];
|
||||
int* ce = new int[N];
|
||||
int* fixp = new int[N]; //node with minimal disconnections
|
||||
int* nod = new int[N];
|
||||
int* s = new int[N]; //for selected candidate
|
||||
|
||||
//form adj matrix
|
||||
int** connected = new int*[N]; //assume filled with 0
|
||||
for( i = 0 ; i < N; i++ )
|
||||
{
|
||||
connected[i] = new int[N];
|
||||
}
|
||||
|
||||
|
||||
|
||||
//set number to vertices
|
||||
_MarkNodes( graph );
|
||||
_FillAdjMatrix( graph, connected, 0 );
|
||||
|
||||
//init all arrays
|
||||
k = 0; //stack size
|
||||
memset( All[k], 0, sizeof(int) * N );
|
||||
for( i = 0; i < N; i++ ) All[k][i] = i;
|
||||
ne[0] = 0;
|
||||
ce[0] = N;
|
||||
|
||||
int status = GO;
|
||||
int best_score = 0;
|
||||
|
||||
//START
|
||||
while( k >= 0)
|
||||
{
|
||||
int* old = All[k];
|
||||
switch(status)
|
||||
{
|
||||
case GO://Forward step
|
||||
/* we have all sets and will choose fixed point */
|
||||
{
|
||||
|
||||
if( k + ce[k] - ne[k] < best_score )
|
||||
{
|
||||
status = BACK;
|
||||
break;
|
||||
}
|
||||
|
||||
int minnod = ce[k];
|
||||
nod[k] = 0;
|
||||
|
||||
//for every vertex of All determine counter value and choose minimum
|
||||
for( int i = 0; i < ce[k] && minnod != 0; i++)
|
||||
{
|
||||
int p = old[i]; //current point
|
||||
int count = 0; //counter
|
||||
int pos = 0;
|
||||
|
||||
/* Count disconnections with candidates */
|
||||
for (int j = ne[k]; j < ce[k] && (count < minnod); j++)
|
||||
{
|
||||
if ( !connected[p][old[j]] )
|
||||
{
|
||||
count++;
|
||||
/* Save position of potential candidate */
|
||||
pos = j;
|
||||
}
|
||||
}
|
||||
|
||||
/* Test new minimum */
|
||||
if (count < minnod)
|
||||
{
|
||||
fixp[k] = p; //set current point as fixed
|
||||
minnod = count; //new value for minnod
|
||||
if (i < ne[k]) //if current fixed point belongs to 'not'
|
||||
{
|
||||
s[k] = pos; //s - selected candidate
|
||||
}
|
||||
else
|
||||
{
|
||||
s[k] = i; //selected candidate is fixed point itself
|
||||
/* preincr */
|
||||
nod[k] = 1; //nod is aux variable, 1 means fixp == s
|
||||
}
|
||||
}
|
||||
}//for
|
||||
|
||||
nod[k] = minnod + nod[k];
|
||||
status = NEXT;//go to backtrackcycle
|
||||
}
|
||||
break;
|
||||
case NEXT:
|
||||
//here we will look for candidate to translate into not
|
||||
//s[k] now contains index of choosen candidate
|
||||
{
|
||||
int* new_ = All[k+1];
|
||||
if( nod[k] != 0 )
|
||||
{
|
||||
//swap selected and first candidate
|
||||
int p = old[s[k]];
|
||||
old[s[k]] = old[ne[k]];
|
||||
int sel = old[ne[k]] = p;
|
||||
|
||||
int newne = 0;
|
||||
//fill new set 'not'
|
||||
for ( i = 0; i < ne[k]; i++)
|
||||
{
|
||||
if (connected[sel][old[i]])
|
||||
{
|
||||
new_[newne] = old[i];
|
||||
newne++;
|
||||
|
||||
}
|
||||
}
|
||||
//fill new set 'candidate'
|
||||
int newce = newne;
|
||||
i++;//skip selected candidate
|
||||
for (; i < ce[k]; i++)
|
||||
{
|
||||
if (connected[sel][old[i]])
|
||||
{
|
||||
new_[newce] = old[i];
|
||||
newce++;
|
||||
}
|
||||
}
|
||||
|
||||
nod[k]--;
|
||||
|
||||
//add selected to stack
|
||||
Compsub[k] = sel;
|
||||
k++;
|
||||
|
||||
//check if 'not' and 'cand' are both empty
|
||||
if( newce == 0 )
|
||||
{
|
||||
best_score = MAX(best_score, k );
|
||||
|
||||
FILE* file = fopen("cliques.txt", "a" );
|
||||
|
||||
for (int t=0; t<k; t++)
|
||||
{
|
||||
fprintf(file, "%d ", Compsub[t]);
|
||||
}
|
||||
fprintf(file, "\n");
|
||||
|
||||
fclose(file);
|
||||
|
||||
/*for( int t = 0; t < k; t++ )
|
||||
{
|
||||
printf("%d ", Compsub[t] );
|
||||
}
|
||||
printf("\n"); */
|
||||
|
||||
//printf("found %d\n", k);
|
||||
|
||||
//output new clique//************************
|
||||
status = BACK;
|
||||
}
|
||||
else //check nonempty set of candidates
|
||||
if( newne < newce )
|
||||
{
|
||||
//go further
|
||||
ne[k] = newne;
|
||||
ce[k] = newce;
|
||||
status = GO;
|
||||
break;
|
||||
}
|
||||
|
||||
}
|
||||
else
|
||||
status = BACK;
|
||||
|
||||
}
|
||||
break;
|
||||
|
||||
case BACK:
|
||||
{
|
||||
//decrease stack
|
||||
k--;
|
||||
old = All[k];
|
||||
if( k < 0 ) break;
|
||||
|
||||
//add to not
|
||||
ne[k]++;
|
||||
|
||||
if( nod[k] > 0 )
|
||||
{
|
||||
//select next candidate
|
||||
for( s[k] = ne[k]; s[k] < ce[k]; s[k]++ )
|
||||
{
|
||||
if( !connected[fixp[k]][old[s[k]]])
|
||||
break;
|
||||
}
|
||||
assert( s[k] < ce[k] );
|
||||
status = NEXT;
|
||||
}
|
||||
else
|
||||
status = BACK;
|
||||
|
||||
}
|
||||
break;
|
||||
|
||||
|
||||
}
|
||||
}//end while
|
||||
|
||||
}//end cvBronKerbosch
|
||||
|
||||
#endif
|
||||
|
||||
@@ -0,0 +1,403 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
#include "_cvaux.h"
|
||||
#include "_cvvm.h"
|
||||
#include <stdlib.h>
|
||||
#include <assert.h>
|
||||
|
||||
|
||||
/*======================================================================================*/
|
||||
|
||||
CvStatus
|
||||
icvDynamicCorrespond( int *first, /* first sequence of runs */
|
||||
/* s0|w0|s1|w1|...|s(n-1)|w(n-1)|sn */
|
||||
int first_runs, /* number of runs */
|
||||
int *second, /* second sequence of runs */
|
||||
int second_runs, int *first_corr, /* s0'|e0'|s1'|e1'|... */
|
||||
int *second_corr )
|
||||
{
|
||||
|
||||
float Pd, Fi, S;
|
||||
float Occlusion;
|
||||
float *costTable;
|
||||
uchar *matchEdges;
|
||||
int prev;
|
||||
int curr;
|
||||
int baseIndex;
|
||||
int i, j;
|
||||
int i_1, j_1;
|
||||
int n;
|
||||
int l_beg, r_beg, l_end, r_end, l_len, r_len;
|
||||
int first_curr;
|
||||
int second_curr;
|
||||
int l_color, r_color;
|
||||
int len_color;
|
||||
float cost, cost1;
|
||||
float min1, min2, min3;
|
||||
float cmin;
|
||||
uchar cpath;
|
||||
int row_size;
|
||||
|
||||
/* Test arguments for errors */
|
||||
|
||||
if( (first == 0) ||
|
||||
(first_runs < 1) ||
|
||||
(second == 0) || (second_runs < 1) || (first_corr == 0) || (second_corr == 0) )
|
||||
|
||||
return CV_BADFACTOR_ERR;
|
||||
|
||||
|
||||
Pd = 0.95f;
|
||||
Fi = (float) CV_PI;
|
||||
S = 1;
|
||||
|
||||
Occlusion = (float) log( Pd * Fi / ((1 - Pd) * sqrt( fabs( (CV_PI * 2) * (1. / S) ))));
|
||||
|
||||
costTable = (float *)cvAlloc( (first_runs + 1) * (second_runs + 1) * sizeof( float ));
|
||||
|
||||
if( costTable == 0 )
|
||||
return CV_OUTOFMEM_ERR;
|
||||
|
||||
matchEdges = (uchar *)cvAlloc( (first_runs + 1) * (second_runs + 1) * sizeof( uchar ));
|
||||
|
||||
if( matchEdges == 0 )
|
||||
{
|
||||
cvFree( &costTable );
|
||||
return CV_OUTOFMEM_ERR;
|
||||
}
|
||||
|
||||
row_size = first_runs + 1;
|
||||
|
||||
/* ============= Fill costTable ============= */
|
||||
|
||||
costTable[0] = 0.0f;
|
||||
|
||||
/* Fill upper line in the cost Table */
|
||||
|
||||
prev = first[0];
|
||||
curr = 2;
|
||||
|
||||
for( n = 0; n < first_runs; n++ )
|
||||
{
|
||||
|
||||
l_end = first[curr];
|
||||
curr += 2;
|
||||
costTable[n + 1] = costTable[n] + Occlusion * (l_end - prev);
|
||||
prev = l_end;
|
||||
|
||||
} /* for */
|
||||
|
||||
/* Fill lefter line in the cost Table */
|
||||
|
||||
prev = second[0];
|
||||
curr = 2;
|
||||
baseIndex = 0;
|
||||
|
||||
for( n = 0; n < second_runs; n++ )
|
||||
{
|
||||
|
||||
l_end = second[curr];
|
||||
curr += 2;
|
||||
costTable[baseIndex + row_size] = costTable[baseIndex] + Occlusion * (l_end - prev);
|
||||
baseIndex += row_size;
|
||||
prev = l_end;
|
||||
|
||||
} /* for */
|
||||
|
||||
/* Count costs in the all rest cells */
|
||||
|
||||
first_curr = 0;
|
||||
second_curr = 0;
|
||||
|
||||
for( i = 1; i <= first_runs; i++ )
|
||||
{
|
||||
for( j = 1; j <= second_runs; j++ )
|
||||
{
|
||||
|
||||
first_curr = (i - 1) * 2;
|
||||
second_curr = (j - 1) * 2;
|
||||
|
||||
l_beg = first[first_curr];
|
||||
first_curr++;
|
||||
l_color = first[first_curr];
|
||||
first_curr++;
|
||||
l_end = first[first_curr];
|
||||
l_len = l_end - l_beg + 1;
|
||||
|
||||
r_beg = second[second_curr];
|
||||
second_curr++;
|
||||
r_color = second[second_curr];
|
||||
second_curr++;
|
||||
r_end = second[second_curr];
|
||||
r_len = r_end - r_beg + 1;
|
||||
|
||||
i_1 = i - 1;
|
||||
j_1 = j - 1;
|
||||
|
||||
if( r_len == l_len )
|
||||
{
|
||||
cost = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
|
||||
if( r_len > l_len )
|
||||
{
|
||||
cost = (float) (r_len * r_len - l_len * l_len) * (1 / (r_len * l_len));
|
||||
}
|
||||
else
|
||||
{
|
||||
cost = (float) (l_len * l_len - r_len * r_len) * (1 / (r_len * l_len));
|
||||
}
|
||||
} /* if */
|
||||
|
||||
len_color = r_color - l_color;
|
||||
|
||||
cost1 = (float) ((len_color * len_color) >> 2);
|
||||
|
||||
min2 = costTable[i_1 + j * row_size] + Occlusion * l_len;
|
||||
|
||||
min3 = costTable[i + j_1 * row_size] + Occlusion * r_len;
|
||||
|
||||
min1 = costTable[i_1 + j_1 * row_size] + cost + (float) cost1;
|
||||
|
||||
if( min1 < min2 )
|
||||
{
|
||||
|
||||
if( min1 < min3 )
|
||||
{
|
||||
cmin = min1;
|
||||
cpath = 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
cmin = min3;
|
||||
cpath = 3;
|
||||
} /* if */
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
|
||||
if( min2 < min3 )
|
||||
{
|
||||
cmin = min2;
|
||||
cpath = 2;
|
||||
}
|
||||
else
|
||||
{
|
||||
cmin = min3;
|
||||
cpath = 3;
|
||||
} /* if */
|
||||
|
||||
} /* if */
|
||||
|
||||
costTable[i + j * row_size] = cmin;
|
||||
matchEdges[i + j * row_size] = cpath;
|
||||
} /* for */
|
||||
} /* for */
|
||||
|
||||
/* =========== Reconstruct the Path =========== */
|
||||
|
||||
i = first_runs;
|
||||
j = second_runs;
|
||||
|
||||
first_curr = i * 2 - 2;
|
||||
second_curr = j * 2 - 2;
|
||||
|
||||
|
||||
while( i > 0 && j > 0 )
|
||||
{
|
||||
|
||||
/* Connect begins */
|
||||
switch (matchEdges[i + j * row_size])
|
||||
{
|
||||
|
||||
case 1: /* to diagonal */
|
||||
|
||||
first_corr[first_curr] = second[second_curr];
|
||||
first_corr[first_curr + 1] = second[second_curr + 2];
|
||||
second_corr[second_curr] = first[first_curr];
|
||||
second_corr[second_curr + 1] = first[first_curr + 2];
|
||||
|
||||
first_curr -= 2;
|
||||
second_curr -= 2;
|
||||
i--;
|
||||
j--;
|
||||
|
||||
break;
|
||||
|
||||
case 2: /* to left */
|
||||
|
||||
first_corr[first_curr] = second[second_curr + 2];
|
||||
first_corr[first_curr + 1] = second[second_curr + 2];
|
||||
|
||||
first_curr -= 2;
|
||||
i--;
|
||||
|
||||
break;
|
||||
|
||||
case 3: /* to up */
|
||||
|
||||
second_corr[second_curr] = first[first_curr + 2];
|
||||
second_corr[second_curr + 1] = first[first_curr + 2];
|
||||
|
||||
second_curr -= 2;
|
||||
j--;
|
||||
|
||||
break;
|
||||
} /* switch */
|
||||
} /* while */
|
||||
|
||||
/* construct rest of horisontal path if its need */
|
||||
while( i > 0 )
|
||||
{
|
||||
|
||||
first_corr[first_curr] = second[second_curr + 2]; /* connect to begin */
|
||||
first_corr[first_curr + 1] = second[second_curr + 2]; /* connect to begin */
|
||||
|
||||
first_curr -= 2;
|
||||
i--;
|
||||
|
||||
} /* while */
|
||||
|
||||
/* construct rest of vertical path if its need */
|
||||
while( j > 0 )
|
||||
{
|
||||
|
||||
second_corr[second_curr] = first[first_curr + 2];
|
||||
second_corr[second_curr + 1] = first[first_curr + 2];
|
||||
|
||||
second_curr -= 2;
|
||||
j--;
|
||||
|
||||
} /* while */
|
||||
|
||||
cvFree( &costTable );
|
||||
cvFree( &matchEdges );
|
||||
|
||||
return CV_NO_ERR;
|
||||
} /* icvDynamicCorrespond */
|
||||
|
||||
|
||||
/*======================================================================================*/
|
||||
|
||||
static CvStatus
|
||||
icvDynamicCorrespondMulti( int lines, /* number of scanlines */
|
||||
int *first, /* s0|w0|s1|w1|...s(n-1)|w(n-1)|sn */
|
||||
int *first_runs, /* numbers of runs */
|
||||
int *second, int *second_runs, int *first_corr, /* s0'|e0'|s1'|e1'|... */
|
||||
int *second_corr )
|
||||
{
|
||||
CvStatus error;
|
||||
|
||||
int currFirst;
|
||||
int currSecond;
|
||||
int currFirstCorr;
|
||||
int currSecondCorr;
|
||||
int n;
|
||||
|
||||
/* Test errors */
|
||||
|
||||
if( (lines < 1) ||
|
||||
(first == 0) ||
|
||||
(first_runs == 0) ||
|
||||
(second == 0) || (second_runs == 0) || (first_corr == 0) || (second_corr == 0) )
|
||||
return CV_BADFACTOR_ERR;
|
||||
|
||||
currFirst = 0;
|
||||
currSecond = 0;
|
||||
currFirstCorr = 0;
|
||||
currSecondCorr = 0;
|
||||
|
||||
for( n = 0; n < lines; n++ )
|
||||
{
|
||||
|
||||
error = icvDynamicCorrespond( &(first[currFirst]),
|
||||
first_runs[n],
|
||||
&(second[currSecond]),
|
||||
second_runs[n],
|
||||
&(first_corr[currFirstCorr]),
|
||||
&(second_corr[currSecondCorr]) );
|
||||
|
||||
if( error != CV_NO_ERR )
|
||||
return error;
|
||||
|
||||
currFirst += first_runs[n] * 2 + 1;
|
||||
currSecond += second_runs[n] * 2 + 1;
|
||||
currFirstCorr += first_runs[n] * 2;
|
||||
currSecondCorr += second_runs[n] * 2;
|
||||
|
||||
}
|
||||
|
||||
return CV_NO_ERR;
|
||||
|
||||
} /* icvDynamicCorrespondMulti */
|
||||
|
||||
|
||||
/*======================================================================================*/
|
||||
|
||||
/*F///////////////////////////////////////////////////////////////////////////////////////
|
||||
// Name: cvDynamicCorrespondMulti
|
||||
// Purpose: The functions
|
||||
// Context:
|
||||
// Parameters:
|
||||
//
|
||||
// Notes:
|
||||
//F*/
|
||||
CV_IMPL void
|
||||
cvDynamicCorrespondMulti( int lines, /* number of scanlines */
|
||||
int *first, /* s0|w0|s1|w1|...s(n-1)|w(n-1)|sn */
|
||||
int *first_runs, /* numbers of runs */
|
||||
int *second, int *second_runs, int *first_corr, /* s0'|e0'|s1'|e1'|... */
|
||||
int *second_corr )
|
||||
{
|
||||
CV_FUNCNAME( "cvDynamicCorrespondMulti" );
|
||||
__BEGIN__;
|
||||
|
||||
IPPI_CALL( icvDynamicCorrespondMulti( lines, /* number of scanlines */
|
||||
first, /* s0|w0|s1|w1|...s(n-1)|w(n-1)|sn */
|
||||
first_runs, /* numbers of runs */
|
||||
second, second_runs, first_corr, /* s0'|e0'|s1'|e1'|... */
|
||||
second_corr ));
|
||||
__CLEANUP__;
|
||||
__END__;
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,138 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
#include "_cvaux.h"
|
||||
|
||||
#define CV_MAX2( a, b ) ((a)>(b) ? (a) : (b))
|
||||
#define CV_MIN2( a, b ) ((a)<(b) ? (a) : (b))
|
||||
|
||||
/****************************************************************************************\
|
||||
|
||||
create hand mask
|
||||
|
||||
\****************************************************************************************/
|
||||
|
||||
static CvStatus icvCreateHandMask8uC1R(CvSeq * numbers,
|
||||
uchar * image_mask, int step,
|
||||
CvSize size, CvRect * roi )
|
||||
{
|
||||
|
||||
CvSeqReader reader;
|
||||
CvPoint pt;
|
||||
int k_point;
|
||||
int i_min, i_max, j_min, j_max;
|
||||
|
||||
if( numbers == NULL )
|
||||
return CV_NULLPTR_ERR;
|
||||
|
||||
if( !CV_IS_SEQ_POINT_SET( numbers ))
|
||||
return CV_BADFLAG_ERR;
|
||||
|
||||
i_max = j_max = 0;
|
||||
i_min = size.height;
|
||||
j_min = size.width;
|
||||
|
||||
cvStartReadSeq( numbers, &reader, 0 );
|
||||
|
||||
k_point = numbers->total;
|
||||
assert( k_point > 0 );
|
||||
if( k_point <= 0 )
|
||||
return CV_BADSIZE_ERR;
|
||||
|
||||
memset( image_mask, 0, step * size.height );
|
||||
|
||||
while( k_point-- > 0 )
|
||||
{
|
||||
CV_READ_SEQ_ELEM( pt, reader );
|
||||
|
||||
i_min = CV_MIN2( i_min, pt.y );
|
||||
i_max = CV_MAX2( i_max, pt.y );
|
||||
j_min = CV_MIN2( j_min, pt.x );
|
||||
j_max = CV_MAX2( j_max, pt.x );
|
||||
|
||||
*(image_mask + pt.y * step + pt.x) = 255;
|
||||
}
|
||||
|
||||
roi->x = j_min;
|
||||
roi->y = i_min;
|
||||
roi->width = j_max - j_min + 1;
|
||||
roi->height = i_max - i_min + 1;
|
||||
|
||||
return CV_OK;
|
||||
|
||||
}
|
||||
|
||||
|
||||
/*F///////////////////////////////////////////////////////////////////////////////////////
|
||||
// Name: cvCreateHandMask
|
||||
// Purpose: creates hand mask image
|
||||
// Context:
|
||||
// Parameters:
|
||||
// numbers - pointer to the input sequence of the point's indexes inside
|
||||
// hand region
|
||||
// img_mask - pointer to the result mask image
|
||||
// roi - result hand mask ROI
|
||||
//
|
||||
// Notes:
|
||||
//F*/
|
||||
CV_IMPL void
|
||||
cvCreateHandMask( CvSeq * numbers, IplImage * img_mask, CvRect * roi )
|
||||
{
|
||||
uchar *img_mask_data = 0;
|
||||
int img_mask_step = 0;
|
||||
CvSize img_mask_size;
|
||||
|
||||
CV_FUNCNAME( "cvCreateHandMask" );
|
||||
|
||||
__BEGIN__;
|
||||
|
||||
if( img_mask->depth != IPL_DEPTH_8U )
|
||||
CV_ERROR( CV_BadDepth, cvUnsupportedFormat );
|
||||
|
||||
if( img_mask->nChannels != 1 )
|
||||
CV_ERROR( CV_BadNumChannels, "output image have wrong number of channels" );
|
||||
|
||||
cvGetImageRawData( img_mask, &img_mask_data, &img_mask_step, &img_mask_size );
|
||||
|
||||
IPPI_CALL( icvCreateHandMask8uC1R( numbers, img_mask_data,
|
||||
img_mask_step, img_mask_size, roi ));
|
||||
|
||||
__END__;
|
||||
}
|
||||
@@ -0,0 +1,554 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
/****************************************************************************************\
|
||||
The code below is some modification of Stan Birchfield's algorithm described in:
|
||||
|
||||
Depth Discontinuities by Pixel-to-Pixel Stereo
|
||||
Stan Birchfield and Carlo Tomasi
|
||||
International Journal of Computer Vision,
|
||||
35(3): 269-293, December 1999.
|
||||
|
||||
This implementation uses different cost function that results in
|
||||
O(pixPerRow*maxDisparity) complexity of dynamic programming stage versus
|
||||
O(pixPerRow*log(pixPerRow)*maxDisparity) in the above paper.
|
||||
\****************************************************************************************/
|
||||
|
||||
/****************************************************************************************\
|
||||
* Find stereo correspondence by dynamic programming algorithm *
|
||||
\****************************************************************************************/
|
||||
#define ICV_DP_STEP_LEFT 0
|
||||
#define ICV_DP_STEP_UP 1
|
||||
#define ICV_DP_STEP_DIAG 2
|
||||
|
||||
#define ICV_BIRCH_DIFF_LUM 5
|
||||
|
||||
#define ICV_MAX_DP_SUM_VAL (INT_MAX/4)
|
||||
|
||||
typedef struct _CvDPCell
|
||||
{
|
||||
uchar step; //local-optimal step
|
||||
int sum; //current sum
|
||||
}_CvDPCell;
|
||||
|
||||
typedef struct _CvRightImData
|
||||
{
|
||||
uchar min_val, max_val;
|
||||
} _CvRightImData;
|
||||
|
||||
#define CV_IMAX3(a,b,c) ((temp3 = (a) >= (b) ? (a) : (b)),(temp3 >= (c) ? temp3 : (c)))
|
||||
#define CV_IMIN3(a,b,c) ((temp3 = (a) <= (b) ? (a) : (b)),(temp3 <= (c) ? temp3 : (c)))
|
||||
|
||||
void icvFindStereoCorrespondenceByBirchfieldDP( uchar* src1, uchar* src2,
|
||||
uchar* disparities,
|
||||
CvSize size, int widthStep,
|
||||
int maxDisparity,
|
||||
float _param1, float _param2,
|
||||
float _param3, float _param4,
|
||||
float _param5 )
|
||||
{
|
||||
int x, y, i, j, temp3;
|
||||
int d, s;
|
||||
int dispH = maxDisparity + 3;
|
||||
uchar *dispdata;
|
||||
int imgW = size.width;
|
||||
int imgH = size.height;
|
||||
uchar val, prevval, prev, curr;
|
||||
int min_val;
|
||||
uchar* dest = disparities;
|
||||
int param1 = cvRound(_param1);
|
||||
int param2 = cvRound(_param2);
|
||||
int param3 = cvRound(_param3);
|
||||
int param4 = cvRound(_param4);
|
||||
int param5 = cvRound(_param5);
|
||||
|
||||
#define CELL(d,x) cells[(d)+(x)*dispH]
|
||||
|
||||
uchar* dsi = (uchar*)cvAlloc(sizeof(uchar)*imgW*dispH);
|
||||
uchar* edges = (uchar*)cvAlloc(sizeof(uchar)*imgW*imgH);
|
||||
_CvDPCell* cells = (_CvDPCell*)cvAlloc(sizeof(_CvDPCell)*imgW*MAX(dispH,(imgH+1)/2));
|
||||
_CvRightImData* rData = (_CvRightImData*)cvAlloc(sizeof(_CvRightImData)*imgW);
|
||||
int* reliabilities = (int*)cells;
|
||||
|
||||
for( y = 0; y < imgH; y++ )
|
||||
{
|
||||
uchar* srcdata1 = src1 + widthStep * y;
|
||||
uchar* srcdata2 = src2 + widthStep * y;
|
||||
|
||||
//init rData
|
||||
prevval = prev = srcdata2[0];
|
||||
for( j = 1; j < imgW; j++ )
|
||||
{
|
||||
curr = srcdata2[j];
|
||||
val = (uchar)((curr + prev)>>1);
|
||||
rData[j-1].max_val = (uchar)CV_IMAX3( val, prevval, prev );
|
||||
rData[j-1].min_val = (uchar)CV_IMIN3( val, prevval, prev );
|
||||
prevval = val;
|
||||
prev = curr;
|
||||
}
|
||||
rData[j-1] = rData[j-2];//last elem
|
||||
|
||||
// fill dissimularity space image
|
||||
for( i = 1; i <= maxDisparity + 1; i++ )
|
||||
{
|
||||
dsi += imgW;
|
||||
rData--;
|
||||
for( j = i - 1; j < imgW - 1; j++ )
|
||||
{
|
||||
int t;
|
||||
if( (t = srcdata1[j] - rData[j+1].max_val) >= 0 )
|
||||
{
|
||||
dsi[j] = (uchar)t;
|
||||
}
|
||||
else if( (t = rData[j+1].min_val - srcdata1[j]) >= 0 )
|
||||
{
|
||||
dsi[j] = (uchar)t;
|
||||
}
|
||||
else
|
||||
{
|
||||
dsi[j] = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
dsi -= (maxDisparity+1)*imgW;
|
||||
rData += maxDisparity+1;
|
||||
|
||||
//intensity gradients image construction
|
||||
//left row
|
||||
edges[y*imgW] = edges[y*imgW+1] = edges[y*imgW+2] = 2;
|
||||
edges[y*imgW+imgW-1] = edges[y*imgW+imgW-2] = edges[y*imgW+imgW-3] = 1;
|
||||
for( j = 3; j < imgW-4; j++ )
|
||||
{
|
||||
edges[y*imgW+j] = 0;
|
||||
|
||||
if( ( CV_IMAX3( srcdata1[j-3], srcdata1[j-2], srcdata1[j-1] ) -
|
||||
CV_IMIN3( srcdata1[j-3], srcdata1[j-2], srcdata1[j-1] ) ) >= ICV_BIRCH_DIFF_LUM )
|
||||
{
|
||||
edges[y*imgW+j] |= 1;
|
||||
}
|
||||
if( ( CV_IMAX3( srcdata2[j+3], srcdata2[j+2], srcdata2[j+1] ) -
|
||||
CV_IMIN3( srcdata2[j+3], srcdata2[j+2], srcdata2[j+1] ) ) >= ICV_BIRCH_DIFF_LUM )
|
||||
{
|
||||
edges[y*imgW+j] |= 2;
|
||||
}
|
||||
}
|
||||
|
||||
//find correspondence using dynamical programming
|
||||
//init DP table
|
||||
for( x = 0; x < imgW; x++ )
|
||||
{
|
||||
CELL(0,x).sum = CELL(dispH-1,x).sum = ICV_MAX_DP_SUM_VAL;
|
||||
CELL(0,x).step = CELL(dispH-1,x).step = ICV_DP_STEP_LEFT;
|
||||
}
|
||||
for( d = 2; d < dispH; d++ )
|
||||
{
|
||||
CELL(d,d-2).sum = ICV_MAX_DP_SUM_VAL;
|
||||
CELL(d,d-2).step = ICV_DP_STEP_UP;
|
||||
}
|
||||
CELL(1,0).sum = 0;
|
||||
CELL(1,0).step = ICV_DP_STEP_LEFT;
|
||||
|
||||
for( x = 1; x < imgW; x++ )
|
||||
{
|
||||
int d = MIN( x + 1, maxDisparity + 1);
|
||||
uchar* _edges = edges + y*imgW + x;
|
||||
int e0 = _edges[0] & 1;
|
||||
_CvDPCell* _cell = cells + x*dispH;
|
||||
|
||||
do
|
||||
{
|
||||
int s = dsi[d*imgW+x];
|
||||
int sum[3];
|
||||
|
||||
//check left step
|
||||
sum[0] = _cell[d-dispH].sum - param2;
|
||||
|
||||
//check up step
|
||||
if( _cell[d+1].step != ICV_DP_STEP_DIAG && e0 )
|
||||
{
|
||||
sum[1] = _cell[d+1].sum + param1;
|
||||
|
||||
if( _cell[d-1-dispH].step != ICV_DP_STEP_UP && (_edges[1-d] & 2) )
|
||||
{
|
||||
int t;
|
||||
|
||||
sum[2] = _cell[d-1-dispH].sum + param1;
|
||||
|
||||
t = sum[1] < sum[0];
|
||||
|
||||
//choose local-optimal pass
|
||||
if( sum[t] <= sum[2] )
|
||||
{
|
||||
_cell[d].step = (uchar)t;
|
||||
_cell[d].sum = sum[t] + s;
|
||||
}
|
||||
else
|
||||
{
|
||||
_cell[d].step = ICV_DP_STEP_DIAG;
|
||||
_cell[d].sum = sum[2] + s;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if( sum[0] <= sum[1] )
|
||||
{
|
||||
_cell[d].step = ICV_DP_STEP_LEFT;
|
||||
_cell[d].sum = sum[0] + s;
|
||||
}
|
||||
else
|
||||
{
|
||||
_cell[d].step = ICV_DP_STEP_UP;
|
||||
_cell[d].sum = sum[1] + s;
|
||||
}
|
||||
}
|
||||
}
|
||||
else if( _cell[d-1-dispH].step != ICV_DP_STEP_UP && (_edges[1-d] & 2) )
|
||||
{
|
||||
sum[2] = _cell[d-1-dispH].sum + param1;
|
||||
if( sum[0] <= sum[2] )
|
||||
{
|
||||
_cell[d].step = ICV_DP_STEP_LEFT;
|
||||
_cell[d].sum = sum[0] + s;
|
||||
}
|
||||
else
|
||||
{
|
||||
_cell[d].step = ICV_DP_STEP_DIAG;
|
||||
_cell[d].sum = sum[2] + s;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
_cell[d].step = ICV_DP_STEP_LEFT;
|
||||
_cell[d].sum = sum[0] + s;
|
||||
}
|
||||
}
|
||||
while( --d );
|
||||
}// for x
|
||||
|
||||
//extract optimal way and fill disparity image
|
||||
dispdata = dest + widthStep * y;
|
||||
|
||||
//find min_val
|
||||
min_val = ICV_MAX_DP_SUM_VAL;
|
||||
for( i = 1; i <= maxDisparity + 1; i++ )
|
||||
{
|
||||
if( min_val > CELL(i,imgW-1).sum )
|
||||
{
|
||||
d = i;
|
||||
min_val = CELL(i,imgW-1).sum;
|
||||
}
|
||||
}
|
||||
|
||||
//track optimal pass
|
||||
for( x = imgW - 1; x > 0; x-- )
|
||||
{
|
||||
dispdata[x] = (uchar)(d - 1);
|
||||
while( CELL(d,x).step == ICV_DP_STEP_UP ) d++;
|
||||
if ( CELL(d,x).step == ICV_DP_STEP_DIAG )
|
||||
{
|
||||
s = x;
|
||||
while( CELL(d,x).step == ICV_DP_STEP_DIAG )
|
||||
{
|
||||
d--;
|
||||
x--;
|
||||
}
|
||||
for( i = x; i < s; i++ )
|
||||
{
|
||||
dispdata[i] = (uchar)(d-1);
|
||||
}
|
||||
}
|
||||
}//for x
|
||||
}// for y
|
||||
|
||||
//Postprocessing the Disparity Map
|
||||
|
||||
//remove obvious errors in the disparity map
|
||||
for( x = 0; x < imgW; x++ )
|
||||
{
|
||||
for( y = 1; y < imgH - 1; y++ )
|
||||
{
|
||||
if( dest[(y-1)*widthStep+x] == dest[(y+1)*widthStep+x] )
|
||||
{
|
||||
dest[y*widthStep+x] = dest[(y-1)*widthStep+x];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//compute intensity Y-gradients
|
||||
for( x = 0; x < imgW; x++ )
|
||||
{
|
||||
for( y = 1; y < imgH - 1; y++ )
|
||||
{
|
||||
if( ( CV_IMAX3( src1[(y-1)*widthStep+x], src1[y*widthStep+x],
|
||||
src1[(y+1)*widthStep+x] ) -
|
||||
CV_IMIN3( src1[(y-1)*widthStep+x], src1[y*widthStep+x],
|
||||
src1[(y+1)*widthStep+x] ) ) >= ICV_BIRCH_DIFF_LUM )
|
||||
{
|
||||
edges[y*imgW+x] |= 4;
|
||||
edges[(y+1)*imgW+x] |= 4;
|
||||
edges[(y-1)*imgW+x] |= 4;
|
||||
y++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//remove along any particular row, every gradient
|
||||
//for which two adjacent columns do not agree.
|
||||
for( y = 0; y < imgH; y++ )
|
||||
{
|
||||
prev = edges[y*imgW];
|
||||
for( x = 1; x < imgW - 1; x++ )
|
||||
{
|
||||
curr = edges[y*imgW+x];
|
||||
if( (curr & 4) &&
|
||||
( !( prev & 4 ) ||
|
||||
!( edges[y*imgW+x+1] & 4 ) ) )
|
||||
{
|
||||
edges[y*imgW+x] -= 4;
|
||||
}
|
||||
prev = curr;
|
||||
}
|
||||
}
|
||||
|
||||
// define reliability
|
||||
for( x = 0; x < imgW; x++ )
|
||||
{
|
||||
for( y = 1; y < imgH; y++ )
|
||||
{
|
||||
i = y - 1;
|
||||
for( ; y < imgH && dest[y*widthStep+x] == dest[(y-1)*widthStep+x]; y++ )
|
||||
;
|
||||
s = y - i;
|
||||
for( ; i < y; i++ )
|
||||
{
|
||||
reliabilities[i*imgW+x] = s;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//Y - propagate reliable regions
|
||||
for( x = 0; x < imgW; x++ )
|
||||
{
|
||||
for( y = 0; y < imgH; y++ )
|
||||
{
|
||||
d = dest[y*widthStep+x];
|
||||
if( reliabilities[y*imgW+x] >= param4 && !(edges[y*imgW+x] & 4) &&
|
||||
d > 0 )//highly || moderately
|
||||
{
|
||||
disparities[y*widthStep+x] = (uchar)d;
|
||||
//up propagation
|
||||
for( i = y - 1; i >= 0; i-- )
|
||||
{
|
||||
if( ( edges[i*imgW+x] & 4 ) ||
|
||||
( dest[i*widthStep+x] < d &&
|
||||
reliabilities[i*imgW+x] >= param3 ) ||
|
||||
( reliabilities[y*imgW+x] < param5 &&
|
||||
dest[i*widthStep+x] - 1 == d ) ) break;
|
||||
|
||||
disparities[i*widthStep+x] = (uchar)d;
|
||||
}
|
||||
|
||||
//down propagation
|
||||
for( i = y + 1; i < imgH; i++ )
|
||||
{
|
||||
if( ( edges[i*imgW+x] & 4 ) ||
|
||||
( dest[i*widthStep+x] < d &&
|
||||
reliabilities[i*imgW+x] >= param3 ) ||
|
||||
( reliabilities[y*imgW+x] < param5 &&
|
||||
dest[i*widthStep+x] - 1 == d ) ) break;
|
||||
|
||||
disparities[i*widthStep+x] = (uchar)d;
|
||||
}
|
||||
y = i - 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
disparities[y*widthStep+x] = (uchar)d;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// define reliability along X
|
||||
for( y = 0; y < imgH; y++ )
|
||||
{
|
||||
for( x = 1; x < imgW; x++ )
|
||||
{
|
||||
i = x - 1;
|
||||
for( ; x < imgW && dest[y*widthStep+x] == dest[y*widthStep+x-1]; x++ );
|
||||
s = x - i;
|
||||
for( ; i < x; i++ )
|
||||
{
|
||||
reliabilities[y*imgW+i] = s;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//X - propagate reliable regions
|
||||
for( y = 0; y < imgH; y++ )
|
||||
{
|
||||
for( x = 0; x < imgW; x++ )
|
||||
{
|
||||
d = dest[y*widthStep+x];
|
||||
if( reliabilities[y*imgW+x] >= param4 && !(edges[y*imgW+x] & 1) &&
|
||||
d > 0 )//highly || moderately
|
||||
{
|
||||
disparities[y*widthStep+x] = (uchar)d;
|
||||
//up propagation
|
||||
for( i = x - 1; i >= 0; i-- )
|
||||
{
|
||||
if( (edges[y*imgW+i] & 1) ||
|
||||
( dest[y*widthStep+i] < d &&
|
||||
reliabilities[y*imgW+i] >= param3 ) ||
|
||||
( reliabilities[y*imgW+x] < param5 &&
|
||||
dest[y*widthStep+i] - 1 == d ) ) break;
|
||||
|
||||
disparities[y*widthStep+i] = (uchar)d;
|
||||
}
|
||||
|
||||
//down propagation
|
||||
for( i = x + 1; i < imgW; i++ )
|
||||
{
|
||||
if( (edges[y*imgW+i] & 1) ||
|
||||
( dest[y*widthStep+i] < d &&
|
||||
reliabilities[y*imgW+i] >= param3 ) ||
|
||||
( reliabilities[y*imgW+x] < param5 &&
|
||||
dest[y*widthStep+i] - 1 == d ) ) break;
|
||||
|
||||
disparities[y*widthStep+i] = (uchar)d;
|
||||
}
|
||||
x = i - 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
disparities[y*widthStep+x] = (uchar)d;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//release resources
|
||||
cvFree( &dsi );
|
||||
cvFree( &edges );
|
||||
cvFree( &cells );
|
||||
cvFree( &rData );
|
||||
}
|
||||
|
||||
|
||||
/*F///////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Name: cvFindStereoCorrespondence
|
||||
// Purpose: find stereo correspondence on stereo-pair
|
||||
// Context:
|
||||
// Parameters:
|
||||
// leftImage - left image of stereo-pair (format 8uC1).
|
||||
// rightImage - right image of stereo-pair (format 8uC1).
|
||||
// mode -mode of correspondance retrieval (now CV_RETR_DP_BIRCHFIELD only)
|
||||
// dispImage - destination disparity image
|
||||
// maxDisparity - maximal disparity
|
||||
// param1, param2, param3, param4, param5 - parameters of algorithm
|
||||
// Returns:
|
||||
// Notes:
|
||||
// Images must be rectified.
|
||||
// All images must have format 8uC1.
|
||||
//F*/
|
||||
CV_IMPL void
|
||||
cvFindStereoCorrespondence(
|
||||
const CvArr* leftImage, const CvArr* rightImage,
|
||||
int mode,
|
||||
CvArr* depthImage,
|
||||
int maxDisparity,
|
||||
double param1, double param2, double param3,
|
||||
double param4, double param5 )
|
||||
{
|
||||
CV_FUNCNAME( "cvFindStereoCorrespondence" );
|
||||
|
||||
__BEGIN__;
|
||||
|
||||
CvMat *src1, *src2;
|
||||
CvMat *dst;
|
||||
CvMat src1_stub, src2_stub, dst_stub;
|
||||
int coi;
|
||||
|
||||
CV_CALL( src1 = cvGetMat( leftImage, &src1_stub, &coi ));
|
||||
if( coi ) CV_ERROR( CV_BadCOI, "COI is not supported by the function" );
|
||||
CV_CALL( src2 = cvGetMat( rightImage, &src2_stub, &coi ));
|
||||
if( coi ) CV_ERROR( CV_BadCOI, "COI is not supported by the function" );
|
||||
CV_CALL( dst = cvGetMat( depthImage, &dst_stub, &coi ));
|
||||
if( coi ) CV_ERROR( CV_BadCOI, "COI is not supported by the function" );
|
||||
|
||||
// check args
|
||||
if( CV_MAT_TYPE( src1->type ) != CV_8UC1 ||
|
||||
CV_MAT_TYPE( src2->type ) != CV_8UC1 ||
|
||||
CV_MAT_TYPE( dst->type ) != CV_8UC1) CV_ERROR(CV_StsUnsupportedFormat,
|
||||
"All images must be single-channel and have 8u" );
|
||||
|
||||
if( !CV_ARE_SIZES_EQ( src1, src2 ) || !CV_ARE_SIZES_EQ( src1, dst ) )
|
||||
CV_ERROR( CV_StsUnmatchedSizes, "" );
|
||||
|
||||
if( maxDisparity <= 0 || maxDisparity >= src1->width || maxDisparity > 255 )
|
||||
CV_ERROR(CV_StsOutOfRange,
|
||||
"parameter /maxDisparity/ is out of range");
|
||||
|
||||
if( mode == CV_DISPARITY_BIRCHFIELD )
|
||||
{
|
||||
if( param1 == CV_UNDEF_SC_PARAM ) param1 = CV_IDP_BIRCHFIELD_PARAM1;
|
||||
if( param2 == CV_UNDEF_SC_PARAM ) param2 = CV_IDP_BIRCHFIELD_PARAM2;
|
||||
if( param3 == CV_UNDEF_SC_PARAM ) param3 = CV_IDP_BIRCHFIELD_PARAM3;
|
||||
if( param4 == CV_UNDEF_SC_PARAM ) param4 = CV_IDP_BIRCHFIELD_PARAM4;
|
||||
if( param5 == CV_UNDEF_SC_PARAM ) param5 = CV_IDP_BIRCHFIELD_PARAM5;
|
||||
|
||||
CV_CALL( icvFindStereoCorrespondenceByBirchfieldDP( src1->data.ptr,
|
||||
src2->data.ptr, dst->data.ptr,
|
||||
cvGetMatSize( src1 ), src1->step,
|
||||
maxDisparity, (float)param1, (float)param2, (float)param3,
|
||||
(float)param4, (float)param5 ) );
|
||||
}
|
||||
else
|
||||
{
|
||||
CV_ERROR( CV_StsBadArg, "Unsupported mode of function" );
|
||||
}
|
||||
|
||||
__END__;
|
||||
}
|
||||
|
||||
/* End of file. */
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,354 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
///////////////////////////////////////////////
|
||||
//// Created by Khudyakov V.A. bober@gorodok.net
|
||||
//////////////////////////////////////////////
|
||||
|
||||
#include "_cvaux.h"
|
||||
#include "_cvfacedetection.h"
|
||||
|
||||
Face::Face(FaceTemplate * lpFaceTemplate)
|
||||
{
|
||||
//init number of face elements;
|
||||
m_lFaceFeaturesNumber = lpFaceTemplate->GetCount();
|
||||
|
||||
//init array of numbers of foundet face elements of each type
|
||||
m_lplFaceFeaturesCount = new long[m_lFaceFeaturesNumber];
|
||||
memset(m_lplFaceFeaturesCount,0,m_lFaceFeaturesNumber*sizeof(long));
|
||||
|
||||
//init array of ideal face features
|
||||
m_lpIdealFace = new FaceFeature[m_lFaceFeaturesNumber];
|
||||
|
||||
//init array of founded features
|
||||
m_lppFoundedFaceFeatures = new FaceFeature*[m_lFaceFeaturesNumber];
|
||||
|
||||
for (int i = 0;i < m_lFaceFeaturesNumber;i ++)
|
||||
{
|
||||
m_lppFoundedFaceFeatures[i] = (new FaceFeature[3*MAX_LAYERS]);
|
||||
}
|
||||
|
||||
//set start weight 0
|
||||
m_dWeight = 0;
|
||||
|
||||
}//Face::Face(FaceTemplate * lpFaceTemplate)
|
||||
|
||||
Face::~Face()
|
||||
{
|
||||
for (int i = 0;i < m_lFaceFeaturesNumber;i ++)
|
||||
{
|
||||
delete [] (m_lppFoundedFaceFeatures[i]);
|
||||
}
|
||||
delete [] m_lppFoundedFaceFeatures;
|
||||
|
||||
|
||||
delete [] m_lplFaceFeaturesCount;
|
||||
delete [] m_lpIdealFace;
|
||||
|
||||
}//Face::~Face()
|
||||
|
||||
|
||||
#define UP_SCALE 1
|
||||
#define DOWN_SCALE 2
|
||||
|
||||
|
||||
////////////
|
||||
//class RFace(rect based face)
|
||||
////////////
|
||||
RFace::RFace(FaceTemplate * lpFaceTemplate):Face(lpFaceTemplate)
|
||||
{
|
||||
//init ideal face
|
||||
FaceFeature * lpTmp = lpFaceTemplate->GetFeatures();
|
||||
|
||||
for (int j = 0;j < m_lFaceFeaturesNumber;j ++)
|
||||
{
|
||||
CvRect * lpTmpRect = NULL;
|
||||
lpTmpRect = new CvRect;
|
||||
*lpTmpRect = *(CvRect*)lpTmp[j].GetContour();
|
||||
|
||||
m_lpIdealFace[j].SetContour( lpTmpRect );
|
||||
m_lpIdealFace[j].SetWeight( lpTmp[j].GetWeight() );
|
||||
m_lpIdealFace[j].SetFeature( lpTmp[j].isFaceFeature() );
|
||||
|
||||
}
|
||||
|
||||
m_bIsGenerated = false;
|
||||
}//RFace::RFace(FaceTemplate * lpFaceTemplate)
|
||||
|
||||
RFace::~RFace()
|
||||
{
|
||||
|
||||
}//RFace::~RFace()
|
||||
|
||||
inline bool RFace::isPointInRect(CvPoint p,CvRect rect)
|
||||
{
|
||||
if ( (p.x >= rect.x) && (p.y >= rect.y) && (p.x <= rect.x + rect.width) && (p.y <= rect.y + rect.height) )
|
||||
return true;
|
||||
|
||||
return false;
|
||||
}//inline bool RFace::isPointInRect(CvPoint,CvRect rect)
|
||||
|
||||
double RFace::GetWeight()
|
||||
{
|
||||
return m_dWeight;
|
||||
}//double RFace::GetWeight()
|
||||
|
||||
|
||||
bool RFace::CheckElem(void * lpCandidat,void * lpIdeal)
|
||||
{
|
||||
|
||||
CvRect IdealRect = *(CvRect*)lpIdeal;
|
||||
CvRect Rect = *(CvRect*)lpCandidat;
|
||||
|
||||
if (Rect.height > Rect.width)
|
||||
return false;
|
||||
|
||||
long SizeIdeal = IdealRect.width*IdealRect.height;
|
||||
long Size = Rect.width*Rect.height;
|
||||
|
||||
if ( (Size > SizeIdeal) || ( Size < (SizeIdeal/5) ) )
|
||||
return false;
|
||||
|
||||
// CvRect UpRect;
|
||||
// CvRect DownRect;
|
||||
// ResizeRect(IdealRect,&UpRect,UP_SCALE,7);
|
||||
// ResizeRect(IdealRect,&DownRect,DOWN_SCALE,7);
|
||||
|
||||
long x = Rect.x + cvRound(Rect.width/2);
|
||||
long y = Rect.y + cvRound(Rect.height/2);
|
||||
|
||||
if ( isPointInRect(cvPoint(x,y),IdealRect) )
|
||||
return true;
|
||||
|
||||
// if ( isPointInRect(cvPoint(Rect.x,Rect.y),UpRect) &&
|
||||
// isPointInRect(cvPoint(Rect.x + Rect.width,Rect.y + Rect.height),UpRect ) &&
|
||||
// isPointInRect(cvPoint(DownRect.x,DownRect.y),Rect) &&
|
||||
// isPointInRect(cvPoint(DownRect.x + DownRect.width,DownRect.y + DownRect.height),Rect) )
|
||||
// return true;
|
||||
|
||||
|
||||
// if ( isPointInRect(cvPoint(Rect.x,Rect.y),IdealRect) &&
|
||||
// isPointInRect(cvPoint(Rect.x + Rect.width,Rect.y + Rect.height),IdealRect ) )
|
||||
// return true;
|
||||
|
||||
return false;
|
||||
}//inline bool RFace::CheckElem(CvRect rect)
|
||||
|
||||
|
||||
|
||||
void RFace::CalculateError(FaceData * lpFaceData)
|
||||
{
|
||||
CvRect LeftEyeRect = lpFaceData->LeftEyeRect;
|
||||
CvRect RightEyeRect = lpFaceData->RightEyeRect;
|
||||
CvRect MouthRect = lpFaceData->MouthRect;
|
||||
|
||||
long LeftSquare = LeftEyeRect.width*LeftEyeRect.height;
|
||||
long RightSquare = RightEyeRect.width*RightEyeRect.height;
|
||||
|
||||
long dy = LeftEyeRect.y - RightEyeRect.y;
|
||||
|
||||
long dx1 = LeftEyeRect.x + LeftEyeRect.width/2 - MouthRect.x;
|
||||
long dx2 = RightEyeRect.x + RightEyeRect.width/2 - MouthRect.x - MouthRect.width;
|
||||
|
||||
|
||||
lpFaceData->Error = (double)(LeftSquare - RightSquare)*(double)(LeftSquare - RightSquare)/((double)(LeftSquare + RightSquare)*(LeftSquare + RightSquare)) +
|
||||
(double)(dy*dy)/((double)(LeftEyeRect.height + RightEyeRect.height)*(LeftEyeRect.height + RightEyeRect.height)) +
|
||||
(double)(dx1*dx1)/((double)MouthRect.width*MouthRect.width) +
|
||||
(double)(dx2*dx2)/((double)MouthRect.width*MouthRect.width);
|
||||
|
||||
}//void RFace::CalculateError(FaceData * lpFaceData)
|
||||
|
||||
#define MAX_ERROR 0xFFFFFFFF
|
||||
|
||||
void RFace::CreateFace(void * lpData)
|
||||
{
|
||||
FaceData Data;
|
||||
|
||||
double Error = MAX_ERROR;
|
||||
double CurError = MAX_ERROR;
|
||||
|
||||
FaceData * lpFaceData = (FaceData*)lpData;
|
||||
|
||||
int im = 0;//mouth was find
|
||||
int jl = 0;//left eye was find
|
||||
int kr = 0;//right eye was find
|
||||
|
||||
long MouthNumber = 0;
|
||||
long LeftEyeNumber = 0;
|
||||
long RightEyeNumber = 0;
|
||||
|
||||
for (int i = 0;i < m_lplFaceFeaturesCount[0] + 1;i ++)
|
||||
{
|
||||
|
||||
if ( !m_lplFaceFeaturesCount[0] )
|
||||
Data.MouthRect = *(CvRect*)m_lpIdealFace[0].GetContour();
|
||||
else
|
||||
{
|
||||
if ( i != m_lplFaceFeaturesCount[0] )
|
||||
Data.MouthRect = *(CvRect*)m_lppFoundedFaceFeatures[0][i].GetContour();
|
||||
im = 1;
|
||||
}
|
||||
|
||||
|
||||
for (int j = 0;j < m_lplFaceFeaturesCount[1] + 1;j ++)
|
||||
{
|
||||
|
||||
if ( !m_lplFaceFeaturesCount[1] )
|
||||
Data.LeftEyeRect = *(CvRect*)m_lpIdealFace[1].GetContour();
|
||||
else
|
||||
{
|
||||
if (j != m_lplFaceFeaturesCount[1] )
|
||||
Data.LeftEyeRect = *(CvRect*)m_lppFoundedFaceFeatures[1][j].GetContour();
|
||||
jl = 1;
|
||||
}
|
||||
|
||||
|
||||
for (int k = 0;k < m_lplFaceFeaturesCount[2] + 1;k ++)
|
||||
{
|
||||
|
||||
if ( !m_lplFaceFeaturesCount[2] )
|
||||
Data.RightEyeRect = *(CvRect*)m_lpIdealFace[2].GetContour();
|
||||
else
|
||||
{
|
||||
if (k != m_lplFaceFeaturesCount[2] )
|
||||
Data.RightEyeRect = *(CvRect*)m_lppFoundedFaceFeatures[2][k].GetContour();
|
||||
kr = 1;
|
||||
}
|
||||
|
||||
CalculateError(&Data);
|
||||
|
||||
if ( (im + jl + kr) )
|
||||
{
|
||||
Error = Data.Error/(im + jl + kr);
|
||||
}else
|
||||
Error = MAX_ERROR;
|
||||
|
||||
if (CurError > Error)
|
||||
{
|
||||
CurError = Error;
|
||||
MouthNumber = i;
|
||||
LeftEyeNumber = j;
|
||||
RightEyeNumber = k;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
if ( m_lplFaceFeaturesCount[0] )
|
||||
lpFaceData->MouthRect = *(CvRect*)m_lppFoundedFaceFeatures[0][MouthNumber].GetContour();
|
||||
else
|
||||
lpFaceData->MouthRect = *(CvRect*)m_lpIdealFace[0].GetContour();
|
||||
|
||||
if ( m_lplFaceFeaturesCount[1] )
|
||||
lpFaceData->LeftEyeRect = *(CvRect*)m_lppFoundedFaceFeatures[1][LeftEyeNumber].GetContour();
|
||||
else
|
||||
lpFaceData->LeftEyeRect = *(CvRect*)m_lpIdealFace[1].GetContour();
|
||||
|
||||
if ( m_lplFaceFeaturesCount[2] )
|
||||
lpFaceData->RightEyeRect = *(CvRect*)m_lppFoundedFaceFeatures[2][RightEyeNumber].GetContour();
|
||||
else
|
||||
lpFaceData->RightEyeRect = *(CvRect*)m_lpIdealFace[2].GetContour();
|
||||
|
||||
lpFaceData->Error = CurError;
|
||||
|
||||
}//void * RFace::CreateFace()
|
||||
|
||||
void RFace::Show(IplImage * Image)
|
||||
{
|
||||
for (int i = 0;i < m_lFaceFeaturesNumber;i ++)
|
||||
{
|
||||
if (m_lplFaceFeaturesCount[i])
|
||||
{
|
||||
for (int j = 0;j < m_lplFaceFeaturesCount[i];j ++)
|
||||
{
|
||||
CvRect rect = *(CvRect*)m_lppFoundedFaceFeatures[i][j].GetContour();
|
||||
CvPoint p1 = cvPoint(rect.x,rect.y);
|
||||
CvPoint p2 = cvPoint(rect.x + rect.width,rect.y + rect.height);
|
||||
cvRectangle(Image,p1,p2,CV_RGB(255,0,0),1);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}//void RFace::Show(IplImage * Image)
|
||||
|
||||
void RFace::ShowIdeal(IplImage* Image)
|
||||
{
|
||||
for (int i = 0;i < m_lFaceFeaturesNumber;i ++)
|
||||
{
|
||||
CvRect Rect = *(CvRect*)m_lpIdealFace[i].GetContour();
|
||||
CvPoint p1 = cvPoint(Rect.x,Rect.y);
|
||||
CvPoint p2 = cvPoint(Rect.x + Rect.width,Rect.y + Rect.height);
|
||||
cvRectangle(Image,p1,p2,CV_RGB(0,0,255),1);
|
||||
}
|
||||
}//void RFace::ShowIdeal(IplImage* Image)
|
||||
|
||||
|
||||
inline void RFace::ResizeRect(CvRect Rect,CvRect * lpRect,long lDir,long lD)
|
||||
{
|
||||
if (lDir == UP_SCALE)
|
||||
{
|
||||
lpRect->x = Rect.x - lD;
|
||||
lpRect->y = Rect.y - lD;
|
||||
lpRect->width = Rect.width + 2*lD;
|
||||
lpRect->height = Rect.height + 2*lD;
|
||||
}
|
||||
if (lDir == DOWN_SCALE)
|
||||
{
|
||||
lpRect->x = Rect.x + lD;
|
||||
lpRect->y = Rect.y + lD;
|
||||
if (Rect.width - 2*lD >= 0)
|
||||
{
|
||||
lpRect->width = Rect.width - 2*lD;
|
||||
}else
|
||||
lpRect->width = 0;
|
||||
|
||||
if (Rect.height - 2*lD >= 0)
|
||||
{
|
||||
lpRect->height = Rect.height - 2*lD;
|
||||
}else
|
||||
lpRect->height = 0;
|
||||
}
|
||||
|
||||
}// inline void RFace::ResizeRect(CvRect * lpRect,long lDir,long lD)
|
||||
|
||||
136
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/src/cvface.h
Normal file
136
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/src/cvface.h
Normal file
@@ -0,0 +1,136 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
///////////////////////////////////////////////
|
||||
//// Created by Khudyakov V.A. bober@gorodok.net
|
||||
//////////////////////////////////////////////
|
||||
|
||||
#ifndef __CVFACE_H__
|
||||
#define __CVFACE_H__
|
||||
|
||||
#include "cvfacetemplate.h"
|
||||
|
||||
#define MAX_LAYERS 64
|
||||
|
||||
class Face
|
||||
{
|
||||
public:
|
||||
Face(FaceTemplate * lpFaceTemplate);
|
||||
virtual ~Face();
|
||||
|
||||
inline bool isFeature(void * lpElem);
|
||||
|
||||
virtual void Show(IplImage * /*Image*/){};
|
||||
virtual void ShowIdeal(IplImage* /*Image*/){};
|
||||
|
||||
virtual void CreateFace(void * lpData) = 0;
|
||||
virtual bool CheckElem(void * lpCandidat,void * lpIdeal) = 0;
|
||||
virtual double GetWeight() = 0;
|
||||
protected:
|
||||
FaceFeature * m_lpIdealFace;//ideal face definition
|
||||
long m_lFaceFeaturesNumber; //total number of diferent face fetures
|
||||
long * m_lplFaceFeaturesCount;//number of each fetures fouded for this face
|
||||
FaceFeature ** m_lppFoundedFaceFeatures;//founded features of curen face
|
||||
double m_dWeight;
|
||||
};
|
||||
|
||||
inline bool Face::isFeature(void * lpElem)
|
||||
{
|
||||
for (int i = 0;i < m_lFaceFeaturesNumber;i ++)
|
||||
{
|
||||
void * lpIdeal = m_lpIdealFace[i].GetContour();
|
||||
|
||||
if ( CheckElem( lpElem,lpIdeal) )
|
||||
{
|
||||
if (m_lplFaceFeaturesCount[i] < 3*MAX_LAYERS)
|
||||
{
|
||||
double dWeight = m_lpIdealFace[i].GetWeight();
|
||||
bool bIsFeature = m_lpIdealFace[i].isFaceFeature();
|
||||
|
||||
|
||||
if (bIsFeature)
|
||||
{
|
||||
m_lppFoundedFaceFeatures[i][m_lplFaceFeaturesCount[i]].SetWeight(dWeight);
|
||||
m_lppFoundedFaceFeatures[i][m_lplFaceFeaturesCount[i]].SetContour(lpElem);
|
||||
m_lppFoundedFaceFeatures[i][m_lplFaceFeaturesCount[i]].SetFeature(bIsFeature);
|
||||
m_lplFaceFeaturesCount[i] ++;
|
||||
}
|
||||
|
||||
m_dWeight += dWeight;
|
||||
|
||||
if (bIsFeature)
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
return false;
|
||||
}//inline bool RFace::isFeature(void * lpElem);
|
||||
|
||||
|
||||
struct FaceData
|
||||
{
|
||||
CvRect LeftEyeRect;
|
||||
CvRect RightEyeRect;
|
||||
CvRect MouthRect;
|
||||
double Error;
|
||||
};//struct FaceData
|
||||
|
||||
class RFace:public Face
|
||||
{
|
||||
public:
|
||||
RFace(FaceTemplate * lpFaceTemplate);
|
||||
virtual ~RFace();
|
||||
virtual bool CheckElem(void * lpCandidat,void * lpIdeal);
|
||||
virtual void CreateFace(void * lpData);
|
||||
virtual void Show(IplImage* Image);
|
||||
virtual void ShowIdeal(IplImage* Image);
|
||||
virtual double GetWeight();
|
||||
private:
|
||||
bool isPointInRect(CvPoint p,CvRect rect);
|
||||
bool m_bIsGenerated;
|
||||
void ResizeRect(CvRect Rect,CvRect * lpRect,long lDir,long lD);
|
||||
void CalculateError(FaceData * lpFaceData);
|
||||
};
|
||||
|
||||
|
||||
#endif //__FACE_H__
|
||||
|
||||
@@ -0,0 +1,486 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
///////////////////////////////////////////////
|
||||
//// Created by Khudyakov V.A. bober@gorodok.net
|
||||
//////////////////////////////////////////////
|
||||
// FaceDetection.cpp: implementation of the FaceDetection class.
|
||||
//
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
|
||||
#include "_cvaux.h"
|
||||
#include "_cvfacedetection.h"
|
||||
|
||||
|
||||
int CV_CDECL CompareContourRect(const void* el1, const void* el2, void* userdata);
|
||||
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
// Construction/Destruction
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
|
||||
FaceDetection::FaceDetection()
|
||||
{
|
||||
|
||||
m_imgGray = NULL;
|
||||
m_imgThresh = NULL;
|
||||
m_mstgContours = NULL;
|
||||
memset(m_seqContours, 0, sizeof(CvSeq*) * MAX_LAYERS);
|
||||
m_mstgRects = NULL;
|
||||
m_seqRects = NULL;
|
||||
m_iNumLayers = 16;
|
||||
assert(m_iNumLayers <= MAX_LAYERS);
|
||||
m_pFaceList = new List();
|
||||
|
||||
|
||||
|
||||
m_bBoosting = false;
|
||||
|
||||
}// FaceDetection()
|
||||
|
||||
FaceDetection::~FaceDetection()
|
||||
{
|
||||
if (m_imgGray)
|
||||
cvReleaseImage(&m_imgGray);
|
||||
|
||||
if (m_imgThresh)
|
||||
cvReleaseImage(&m_imgThresh);
|
||||
|
||||
if (m_mstgContours)
|
||||
cvReleaseMemStorage(&m_mstgContours);
|
||||
|
||||
if (m_mstgRects)
|
||||
cvReleaseMemStorage(&m_mstgRects);
|
||||
|
||||
|
||||
}// ~FaceDetection()
|
||||
|
||||
void FaceDetection::FindContours(IplImage* imgGray)
|
||||
{
|
||||
ReallocImage(&m_imgThresh, cvGetSize(imgGray), 1);
|
||||
if (NULL == m_imgThresh)
|
||||
return;
|
||||
//
|
||||
int iNumLayers = m_iNumLayers;
|
||||
int iMinLevel = 0, iMaxLevel = 255, iStep = 255 / iNumLayers;
|
||||
ThresholdingParam(imgGray, iNumLayers, iMinLevel, iMaxLevel, iStep);
|
||||
// init
|
||||
cvReleaseMemStorage(&m_mstgContours);
|
||||
m_mstgContours = cvCreateMemStorage();
|
||||
if (NULL == m_mstgContours)
|
||||
return;
|
||||
memset(m_seqContours, 0, sizeof(CvSeq*) * MAX_LAYERS);
|
||||
|
||||
cvReleaseMemStorage(&m_mstgRects);
|
||||
m_mstgRects = cvCreateMemStorage();
|
||||
if (NULL == m_mstgRects)
|
||||
return;
|
||||
m_seqRects = cvCreateSeq(0, sizeof(CvSeq), sizeof(CvContourRect), m_mstgRects);
|
||||
if (NULL == m_seqRects)
|
||||
return;
|
||||
// find contours
|
||||
for (int l = iMinLevel, i = 0; l < iMaxLevel; l += iStep, i++)
|
||||
{
|
||||
cvThreshold(imgGray, m_imgThresh, (double)l, (double)255, CV_THRESH_BINARY);
|
||||
if (cvFindContours(m_imgThresh, m_mstgContours, &m_seqContours[i], sizeof(CvContour), CV_RETR_CCOMP, CV_CHAIN_APPROX_SIMPLE))
|
||||
AddContours2Rect(m_seqContours[i], l, i);
|
||||
}
|
||||
// sort rects
|
||||
cvSeqSort(m_seqRects, CompareContourRect, NULL);
|
||||
}// void FaceDetection::FindContours(IplImage* imgGray)
|
||||
|
||||
#define GIST_STEP 10
|
||||
#define GIST_NUM (256 / GIST_STEP)
|
||||
#define GIST_MIN 32
|
||||
|
||||
void FaceDetection::ThresholdingParam(IplImage *imgGray, int iNumLayers, int &iMinLevel, int &iMaxLevel, int &iStep)
|
||||
{
|
||||
assert(imgGray != NULL);
|
||||
assert(imgGray->nChannels == 1);
|
||||
int i, j;
|
||||
// create gistogramm
|
||||
uchar* buffImg = (uchar*)imgGray->imageData;
|
||||
int gistImg[GIST_NUM + 1] = {0};
|
||||
|
||||
for (j = 0; j < imgGray->height; j ++)
|
||||
{
|
||||
for (i = 0; i < imgGray->width; i ++)
|
||||
{
|
||||
int ind = buffImg[i] / GIST_STEP;
|
||||
gistImg[ind] ++;
|
||||
}
|
||||
buffImg += imgGray->widthStep;
|
||||
}
|
||||
// params
|
||||
|
||||
for (i = 0; i <= GIST_NUM; i ++)
|
||||
{
|
||||
if (gistImg[i] >= GIST_MIN)
|
||||
break;
|
||||
}
|
||||
|
||||
iMinLevel = i * GIST_STEP;
|
||||
|
||||
for (i = GIST_NUM; i >= 0; i --)
|
||||
{
|
||||
if (gistImg[i] >= GIST_MIN)
|
||||
break;
|
||||
}
|
||||
|
||||
iMaxLevel = i * GIST_STEP;
|
||||
|
||||
int dLevels = iMaxLevel - iMinLevel;
|
||||
if (dLevels <= 0)
|
||||
{
|
||||
iMinLevel = 0;
|
||||
iMaxLevel = 255;
|
||||
}
|
||||
else if (dLevels <= iNumLayers)
|
||||
{
|
||||
iMinLevel = iMaxLevel - iNumLayers;
|
||||
if (iMinLevel < 0)
|
||||
{
|
||||
iMinLevel = 0;
|
||||
iMaxLevel = iNumLayers;
|
||||
}
|
||||
}
|
||||
iStep = (iMaxLevel - iMinLevel) / iNumLayers;
|
||||
|
||||
}// void FaceDetection::ThresholdingParam(IplImage *imgGray, int iNumLayers, int &iMinLevel, int &iMaxLevel, int &iStep)
|
||||
|
||||
#ifndef MAX_ERROR
|
||||
#define MAX_ERROR 0xFFFFFFFF
|
||||
#endif //MAX_ERROR
|
||||
|
||||
|
||||
void FaceDetection::CreateResults(CvSeq * lpSeq)
|
||||
{
|
||||
|
||||
Face * tmp;
|
||||
|
||||
double Max = 0;
|
||||
double CurStat = 0;
|
||||
|
||||
FaceData tmpData;
|
||||
if (m_bBoosting)
|
||||
{
|
||||
tmp = m_pFaceList->GetData();
|
||||
tmp->CreateFace(&tmpData);
|
||||
|
||||
CvFace tmpFace;
|
||||
tmpFace.MouthRect = tmpData.MouthRect;
|
||||
tmpFace.LeftEyeRect = tmpData.LeftEyeRect;
|
||||
tmpFace.RightEyeRect = tmpData.RightEyeRect;
|
||||
|
||||
cvSeqPush(lpSeq,&tmpFace);
|
||||
|
||||
}else
|
||||
{
|
||||
while ( (tmp = m_pFaceList->GetData()) != 0 )
|
||||
{
|
||||
CurStat = tmp->GetWeight();
|
||||
if (CurStat > Max)
|
||||
Max = CurStat;
|
||||
}
|
||||
|
||||
while ( (tmp = m_pFaceList->GetData()) != 0 )
|
||||
{
|
||||
tmp->CreateFace(&tmpData);
|
||||
CurStat = tmp->GetWeight();
|
||||
|
||||
if (CurStat == Max)
|
||||
{
|
||||
CvFace tmpFace;
|
||||
tmpFace.MouthRect = tmpData.MouthRect;
|
||||
tmpFace.LeftEyeRect = tmpData.LeftEyeRect;
|
||||
tmpFace.RightEyeRect = tmpData.RightEyeRect;
|
||||
cvSeqPush(lpSeq,&tmpFace);
|
||||
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
}// void FaceDetection::DrawResult(IplImage* img)
|
||||
|
||||
void FaceDetection::ResetImage()
|
||||
{
|
||||
delete m_pFaceList;
|
||||
m_pFaceList = new List();
|
||||
|
||||
}//FaceDetection::ResetImage
|
||||
|
||||
void FaceDetection::AddContours2Rect(CvSeq *seq, int color, int iLayer)
|
||||
{
|
||||
assert(m_mstgRects != NULL);
|
||||
assert(m_seqRects != NULL);
|
||||
|
||||
CvContourRect cr;
|
||||
for (CvSeq* external = seq; external; external = external->h_next)
|
||||
{
|
||||
cr.r = cvContourBoundingRect(external, 1 );
|
||||
cr.pCenter.x = cr.r.x + cr.r.width / 2;
|
||||
cr.pCenter.y = cr.r.y + cr.r.height / 2;
|
||||
cr.iNumber = iLayer;
|
||||
cr.iType = 6;
|
||||
cr.iFlags = 0;
|
||||
cr.seqContour = external;
|
||||
cr.iContourLength = external->total;
|
||||
cr.iColor = color;
|
||||
cvSeqPush(m_seqRects, &cr);
|
||||
for (CvSeq* internal = external->v_next; internal; internal = internal->h_next)
|
||||
{
|
||||
cr.r = cvContourBoundingRect(internal, 0);
|
||||
cr.pCenter.x = cr.r.x + cr.r.width / 2;
|
||||
cr.pCenter.y = cr.r.y + cr.r.height / 2;
|
||||
cr.iNumber = iLayer;
|
||||
cr.iType = 12;
|
||||
cr.iFlags = 0;
|
||||
cr.seqContour = internal;
|
||||
cr.iContourLength = internal->total;
|
||||
cr.iColor = color;
|
||||
cvSeqPush(m_seqRects, &cr);
|
||||
}
|
||||
}
|
||||
}// void FaceDetection::AddContours2Rect(CvSeq *seq, int color, int iLayer)
|
||||
|
||||
int CV_CDECL CompareContourRect(const void* el1, const void* el2, void* /*userdata*/)
|
||||
{
|
||||
return (((CvContourRect*)el1)->pCenter.y - ((CvContourRect*)el2)->pCenter.y);
|
||||
}// int CV_CDECL CompareContourRect(const void* el1, const void* el2, void* userdata)
|
||||
|
||||
void FaceDetection::FindFace(IplImage *img)
|
||||
{
|
||||
// find all contours
|
||||
FindContours(img);
|
||||
//
|
||||
ResetImage();
|
||||
|
||||
if (m_bBoosting)
|
||||
PostBoostingFindCandidats(img);
|
||||
else
|
||||
FindCandidats();
|
||||
|
||||
}// void FaceDetection::FindFace(IplImage *img)
|
||||
|
||||
|
||||
void FaceDetection::FindCandidats()
|
||||
{
|
||||
bool bFound1 = false;
|
||||
MouthFaceTemplate * lpFaceTemplate1;
|
||||
RFace * lpFace1;
|
||||
bool bInvalidRect1 = false;
|
||||
CvRect * lpRect1 = NULL;
|
||||
|
||||
for (int i = 0; i < m_seqRects->total; i++)
|
||||
{
|
||||
CvContourRect* pRect = (CvContourRect*)cvGetSeqElem(m_seqRects, i);
|
||||
CvRect rect = pRect->r;
|
||||
if (rect.width >= 2*rect.height)
|
||||
{
|
||||
|
||||
lpFaceTemplate1 = new MouthFaceTemplate(3,rect,3*(double)rect.width/(double)4,
|
||||
3*(double)rect.width/(double)4,
|
||||
(double)rect.width/(double)2,
|
||||
(double)rect.width/(double)2);
|
||||
|
||||
|
||||
lpFace1 = new RFace(lpFaceTemplate1);
|
||||
|
||||
for (int j = 0; j < m_seqRects->total; j++)
|
||||
{
|
||||
CvContourRect* pRect = (CvContourRect*)cvGetSeqElem(m_seqRects, j);
|
||||
|
||||
if ( !bInvalidRect1 )
|
||||
{
|
||||
lpRect1 = NULL;
|
||||
lpRect1 = new CvRect();
|
||||
*lpRect1 = pRect->r;
|
||||
}else
|
||||
{
|
||||
delete lpRect1;
|
||||
lpRect1 = new CvRect();
|
||||
*lpRect1 = pRect->r;
|
||||
}
|
||||
|
||||
|
||||
if ( lpFace1->isFeature(lpRect1) )
|
||||
{
|
||||
bFound1 = true;
|
||||
bInvalidRect1 = false;
|
||||
}else
|
||||
bInvalidRect1 = true;
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
if (bFound1)
|
||||
{
|
||||
m_pFaceList->AddElem(lpFace1);
|
||||
bFound1 = false;
|
||||
lpFace1 = NULL;
|
||||
}else
|
||||
{
|
||||
delete lpFace1;
|
||||
lpFace1 = NULL;
|
||||
}
|
||||
|
||||
|
||||
delete lpFaceTemplate1;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
void FaceDetection::PostBoostingFindCandidats(IplImage * FaceImage)
|
||||
{
|
||||
BoostingFaceTemplate * lpFaceTemplate1;
|
||||
RFace * lpFace1;
|
||||
bool bInvalidRect1 = false;
|
||||
CvRect * lpRect1 = NULL;
|
||||
|
||||
if ( ( !FaceImage->roi ) )
|
||||
lpFaceTemplate1 = new BoostingFaceTemplate(3,cvRect(0,0,FaceImage->width,FaceImage->height));
|
||||
else
|
||||
lpFaceTemplate1 = new BoostingFaceTemplate(3,cvRect(FaceImage->roi->xOffset,FaceImage->roi->yOffset,
|
||||
FaceImage->roi->width,FaceImage->roi->height));
|
||||
|
||||
lpFace1 = new RFace(lpFaceTemplate1);
|
||||
|
||||
for (int i = 0; i < m_seqRects->total; i++)
|
||||
{
|
||||
CvContourRect* pRect = (CvContourRect*)cvGetSeqElem(m_seqRects, i);
|
||||
|
||||
if ( !bInvalidRect1 )
|
||||
{
|
||||
lpRect1 = NULL;
|
||||
lpRect1 = new CvRect();
|
||||
*lpRect1 = pRect->r;
|
||||
}else
|
||||
{
|
||||
delete lpRect1;
|
||||
lpRect1 = new CvRect();
|
||||
*lpRect1 = pRect->r;
|
||||
}
|
||||
|
||||
|
||||
if ( lpFace1->isFeature(lpRect1) )
|
||||
{
|
||||
//bFound1 = true;
|
||||
bInvalidRect1 = false;
|
||||
}else
|
||||
bInvalidRect1 = true;
|
||||
|
||||
|
||||
}
|
||||
|
||||
m_pFaceList->AddElem(lpFace1);
|
||||
|
||||
delete lpFaceTemplate1;
|
||||
|
||||
}//void FaceDetection::PostBoostingFindCandidats(IplImage * FaceImage)
|
||||
|
||||
/////////////////////////
|
||||
//class Face
|
||||
|
||||
|
||||
|
||||
//////
|
||||
//List Class
|
||||
/////
|
||||
ListElem::ListElem()
|
||||
{
|
||||
m_pNext = this;
|
||||
m_pPrev = this;
|
||||
m_pFace = NULL;
|
||||
}///ListElem::ListElem()
|
||||
|
||||
ListElem::ListElem(Face * pFace,ListElem * pHead)
|
||||
{
|
||||
m_pNext = pHead;
|
||||
m_pPrev = pHead->m_pPrev;
|
||||
pHead->m_pPrev->m_pNext = this;
|
||||
pHead->m_pPrev = this;
|
||||
|
||||
m_pFace = pFace;
|
||||
}//ListElem::ListElem(Face * pFace)
|
||||
|
||||
|
||||
|
||||
ListElem::~ListElem()
|
||||
{
|
||||
delete m_pFace;
|
||||
m_pNext->m_pPrev = m_pPrev;
|
||||
m_pPrev->m_pNext = m_pNext;
|
||||
|
||||
}//ListElem::~ListElem()
|
||||
|
||||
List::List()
|
||||
{
|
||||
m_pHead = new ListElem();
|
||||
m_FacesCount = 0;
|
||||
m_pCurElem = m_pHead;
|
||||
}//List::List()
|
||||
|
||||
List::~List()
|
||||
{
|
||||
void * tmp;
|
||||
while((tmp = m_pHead->m_pNext->m_pFace) != 0)
|
||||
delete m_pHead->m_pNext;
|
||||
|
||||
delete m_pHead;
|
||||
|
||||
}//List::~List()
|
||||
|
||||
|
||||
int List::AddElem(Face * pFace)
|
||||
{
|
||||
new ListElem(pFace,m_pHead);
|
||||
return m_FacesCount++;
|
||||
}//List::AddElem(Face * pFace)
|
||||
|
||||
Face * List::GetData()
|
||||
{
|
||||
m_pCurElem = m_pCurElem->m_pNext;
|
||||
return m_pCurElem->m_pFace;
|
||||
}//Face * List::GetData()
|
||||
|
||||
|
||||
@@ -0,0 +1,100 @@
|
||||
// FaceDetection.h: interface for the FaceDetection class.
|
||||
//
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
|
||||
#ifndef _CVFACEDETECTION_H_
|
||||
#define _CVFACEDETECTION_H_
|
||||
|
||||
#include "cvfacetemplate.h"
|
||||
#include "cvface.h"
|
||||
#include "cvboostingtemplate.h"
|
||||
|
||||
typedef struct CvContourRect
|
||||
{
|
||||
int iNumber; //ïîðÿäêîâûé íîìåð àòðèáóòà
|
||||
int iType; //òèï îáúåêòà
|
||||
int iFlags; //ñâîáîäíîå ïîëå
|
||||
CvSeq *seqContour; //àäðåñ íà÷àëà çàïèñè îáúåêòà
|
||||
int iContourLength; //äëèíà çàïèñè âåêòîðîâ
|
||||
CvRect r; //îïèñàíûé ïðÿìîóãîëüíèê
|
||||
CvPoint pCenter; // center of rect
|
||||
int iColor;// öâåò çàïîëíåíèÿ êîíòóðà
|
||||
} CvContourRect;
|
||||
|
||||
//class Face;
|
||||
|
||||
class ListElem
|
||||
{
|
||||
public:
|
||||
ListElem();
|
||||
ListElem(Face * pFace,ListElem * pHead);
|
||||
virtual ~ListElem();
|
||||
ListElem * m_pNext;
|
||||
ListElem * m_pPrev;
|
||||
Face * m_pFace;
|
||||
};//class ListElem
|
||||
|
||||
class List
|
||||
{
|
||||
public:
|
||||
List();
|
||||
int AddElem(Face * pFace);
|
||||
virtual ~List();
|
||||
Face* GetData();
|
||||
long m_FacesCount;
|
||||
private:
|
||||
ListElem * m_pHead;
|
||||
ListElem * m_pCurElem;
|
||||
};//class List
|
||||
|
||||
|
||||
class FaceDetection
|
||||
{
|
||||
public:
|
||||
void FindFace(IplImage* img);
|
||||
void CreateResults(CvSeq * lpSeq);
|
||||
FaceDetection();
|
||||
virtual ~FaceDetection();
|
||||
void SetBoosting(bool bBoosting) {m_bBoosting = bBoosting;}
|
||||
bool isPostBoosting() {return m_bBoosting;}
|
||||
protected:
|
||||
|
||||
IplImage* m_imgGray;
|
||||
IplImage* m_imgThresh;
|
||||
int m_iNumLayers;
|
||||
CvMemStorage* m_mstgContours;
|
||||
CvSeq* m_seqContours[MAX_LAYERS];
|
||||
CvMemStorage* m_mstgRects;
|
||||
CvSeq* m_seqRects;
|
||||
|
||||
bool m_bBoosting;
|
||||
List * m_pFaceList;
|
||||
|
||||
protected:
|
||||
void ResetImage();
|
||||
void FindContours(IplImage* imgGray);
|
||||
void AddContours2Rect(CvSeq* seq, int color, int iLayer);
|
||||
void ThresholdingParam(IplImage* imgGray, int iNumLayers, int& iMinLevel, int& iMaxLevel, int& iStep);
|
||||
void FindCandidats();
|
||||
void PostBoostingFindCandidats(IplImage * FaceImage);
|
||||
};
|
||||
|
||||
inline void ReallocImage(IplImage** ppImage, CvSize sz, long lChNum)
|
||||
{
|
||||
IplImage* pImage;
|
||||
if( ppImage == NULL )
|
||||
return;
|
||||
pImage = *ppImage;
|
||||
if( pImage != NULL )
|
||||
{
|
||||
if (pImage->width != sz.width || pImage->height != sz.height || pImage->nChannels != lChNum)
|
||||
cvReleaseImage( &pImage );
|
||||
}
|
||||
if( pImage == NULL )
|
||||
pImage = cvCreateImage( sz, IPL_DEPTH_8U, lChNum);
|
||||
*ppImage = pImage;
|
||||
};
|
||||
|
||||
|
||||
|
||||
#endif // !defined(AFX_FACEDETECTION_H__55865033_D8E5_4DD5_8925_34C2285BB1BE__INCLUDED_)
|
||||
@@ -0,0 +1,86 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
///////////////////////////////////////////////
|
||||
//// Created by Khudyakov V.A. bober@gorodok.net
|
||||
//////////////////////////////////////////////
|
||||
|
||||
#include "_cvaux.h"
|
||||
#include "_cvfacedetection.h"
|
||||
|
||||
///class FaceFeature
|
||||
FaceFeature::FaceFeature(double dWeight,void * lpContour,bool bIsFeature)
|
||||
{
|
||||
m_lpContour = lpContour;
|
||||
m_dWeight = dWeight;
|
||||
m_bIsFaceFeature = bIsFeature;
|
||||
}//FaceFeature::FaceFeature(long lWeight,void * lpContour)
|
||||
|
||||
FaceFeature::~FaceFeature()
|
||||
{
|
||||
if (m_lpContour)
|
||||
delete (char*)m_lpContour;
|
||||
}//FaceFeature::~FaceFeature()
|
||||
|
||||
FaceFeature::FaceFeature()
|
||||
{
|
||||
m_lpContour = NULL;
|
||||
m_dWeight = 0;
|
||||
m_bIsFaceFeature = false;
|
||||
}
|
||||
|
||||
|
||||
////class FaceTemplate
|
||||
|
||||
FaceTemplate::~FaceTemplate()
|
||||
{
|
||||
delete [] m_lpFeaturesList;
|
||||
}//FaceTemplate::~FaceTemplate()
|
||||
|
||||
|
||||
/////
|
||||
//class RFaceTemplate
|
||||
/////
|
||||
|
||||
|
||||
MouthFaceTemplate::~MouthFaceTemplate()
|
||||
{
|
||||
|
||||
}//RFaceTemplate::~RFaceTemplate()
|
||||
@@ -0,0 +1,202 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
///////////////////////////////////////////////
|
||||
//// Created by Khudyakov V.A. bober@gorodok.net
|
||||
//////////////////////////////////////////////
|
||||
|
||||
#ifndef __CVFACETEMPLATE_H__
|
||||
#define __CVFACETEMPLATE_H__
|
||||
|
||||
class FaceFeature
|
||||
{
|
||||
public:
|
||||
FaceFeature(double dWeight,void * lpContour,bool bIsFeature);
|
||||
FaceFeature();
|
||||
virtual ~FaceFeature();
|
||||
inline bool isFaceFeature();
|
||||
inline void * GetContour();
|
||||
inline double GetWeight();
|
||||
inline void SetContour(void * lpContour);
|
||||
inline void SetWeight(double dWeight);
|
||||
inline void SetFeature(bool bIsFeature);
|
||||
private:
|
||||
double m_dWeight;
|
||||
void * m_lpContour;
|
||||
bool m_bIsFaceFeature;
|
||||
};//class FaceFeature
|
||||
|
||||
inline void FaceFeature::SetFeature(bool bIsFeature)
|
||||
{
|
||||
m_bIsFaceFeature = bIsFeature;
|
||||
}
|
||||
|
||||
inline bool FaceFeature::isFaceFeature()
|
||||
{
|
||||
return m_bIsFaceFeature;
|
||||
}//inline bool FaceFeature::isFaceFeature()
|
||||
|
||||
inline void * FaceFeature::GetContour()
|
||||
{
|
||||
return m_lpContour;
|
||||
}//inline void * FaceFeature::GetContour()
|
||||
|
||||
inline double FaceFeature::GetWeight()
|
||||
{
|
||||
return m_dWeight;
|
||||
}//inline long FaceFeature::GetWeight()
|
||||
|
||||
inline void FaceFeature::SetContour(void * lpContour)
|
||||
{
|
||||
m_lpContour = lpContour;
|
||||
}//inline void FaceFeature::SetContour(void * lpContour)
|
||||
|
||||
inline void FaceFeature::SetWeight(double dWeight)
|
||||
{
|
||||
m_dWeight = dWeight;
|
||||
}//inline void FaceFeature::SetWeight(double * dWeight)
|
||||
|
||||
|
||||
|
||||
class FaceTemplate
|
||||
{
|
||||
public:
|
||||
FaceTemplate(long lFeatureCount) {m_lFeturesCount = lFeatureCount; m_lpFeaturesList = new FaceFeature[lFeatureCount];};
|
||||
virtual ~FaceTemplate();
|
||||
|
||||
inline long GetCount();
|
||||
inline FaceFeature * GetFeatures();
|
||||
|
||||
protected:
|
||||
FaceFeature * m_lpFeaturesList;
|
||||
private:
|
||||
long m_lFeturesCount;
|
||||
};//class FaceTemplate
|
||||
|
||||
|
||||
inline long FaceTemplate::GetCount()
|
||||
{
|
||||
return m_lFeturesCount;
|
||||
}//inline long FaceTemplate::GetCount()
|
||||
|
||||
|
||||
inline FaceFeature * FaceTemplate::GetFeatures()
|
||||
{
|
||||
return m_lpFeaturesList;
|
||||
}//inline FaceFeature * FaceTemplate::GetFeatures()
|
||||
|
||||
////////////
|
||||
//class RFaceTemplate
|
||||
///////////
|
||||
|
||||
class MouthFaceTemplate:public FaceTemplate
|
||||
{
|
||||
public:
|
||||
inline MouthFaceTemplate(long lNumber,CvRect rect,double dEyeWidth,double dEyeHeight,double dDistanceBetweenEye,double dDistanceEyeAboveMouth);
|
||||
~MouthFaceTemplate();
|
||||
};//class MouthFaceTemplate:public FaceTemplate
|
||||
|
||||
|
||||
inline MouthFaceTemplate::MouthFaceTemplate(long lNumber,CvRect rect,double dEyeWidth,double dEyeHeight,
|
||||
double dDistanceBetweenEye,double dDistanceEyeAboveMouth):FaceTemplate(lNumber)
|
||||
{
|
||||
|
||||
CvRect MouthRect = rect;
|
||||
|
||||
|
||||
CvRect LeftEyeRect = cvRect(cvRound(rect.x - (dEyeWidth + dDistanceBetweenEye/(double)2 - (double)rect.width/(double)2)),
|
||||
cvRound(rect.y - dDistanceEyeAboveMouth - dEyeHeight),
|
||||
cvRound(dEyeWidth),
|
||||
cvRound(dEyeHeight) );
|
||||
|
||||
CvRect RightEyeRect = cvRect(cvRound(rect.x + (double)rect.width/(double)2 + dDistanceBetweenEye/(double)2),
|
||||
cvRound(rect.y - dDistanceEyeAboveMouth - dEyeHeight),
|
||||
cvRound(dEyeWidth),
|
||||
cvRound(dEyeHeight) );
|
||||
|
||||
// CvRect NoseRect = cvRect(cvRound(rect.x + (double)rect.width/(double)4),
|
||||
// cvRound(rect.y - (double)rect.width/(double)2 - (double)rect.height/(double)4),
|
||||
// cvRound((double)rect.width/(double)2),
|
||||
// cvRound((double)rect.width/(double)2) );
|
||||
/*
|
||||
CvRect CheenRect = cvRect(rect.x,rect.y + 3*rect.height/2,rect.width,rect.height);
|
||||
|
||||
*/
|
||||
|
||||
CvRect * lpMouthRect = new CvRect();
|
||||
*lpMouthRect = MouthRect;
|
||||
m_lpFeaturesList[0].SetContour(lpMouthRect);
|
||||
m_lpFeaturesList[0].SetWeight(1);
|
||||
m_lpFeaturesList[0].SetFeature(false);
|
||||
|
||||
|
||||
CvRect * lpLeftEyeRect = new CvRect();
|
||||
*lpLeftEyeRect = LeftEyeRect;
|
||||
m_lpFeaturesList[1].SetContour(lpLeftEyeRect);
|
||||
m_lpFeaturesList[1].SetWeight(1);
|
||||
m_lpFeaturesList[1].SetFeature(true);
|
||||
|
||||
CvRect * lpRightEyeRect = new CvRect();
|
||||
*lpRightEyeRect = RightEyeRect;
|
||||
m_lpFeaturesList[2].SetContour(lpRightEyeRect);
|
||||
m_lpFeaturesList[2].SetWeight(1);
|
||||
m_lpFeaturesList[2].SetFeature(true);
|
||||
|
||||
|
||||
// CvRect * lpNoseRect = new CvRect();
|
||||
// *lpNoseRect = NoseRect;
|
||||
// m_lpFeaturesList[3].SetContour(lpNoseRect);
|
||||
// m_lpFeaturesList[3].SetWeight(0);
|
||||
// m_lpFeaturesList[3].SetFeature(true);
|
||||
|
||||
/* CvRect * lpCheenRect = new CvRect();
|
||||
*lpCheenRect = CheenRect;
|
||||
m_lpFeaturesList[4].SetContour(lpCheenRect);
|
||||
m_lpFeaturesList[4].SetWeight(1);
|
||||
m_lpFeaturesList[4].SetFeature(false);
|
||||
|
||||
*/
|
||||
|
||||
};//constructor MouthFaceTemplate(long lNumFeatures,CvRect rect,double dEyeWidth,double dEyeHeight,double dDistanceBetweenEye,double dDistanceEyeAboveMouth);
|
||||
|
||||
|
||||
|
||||
#endif//__FACETEMPLATE_H__
|
||||
|
||||
@@ -0,0 +1,68 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
///////////////////////////////////////////////
|
||||
//// Created by Khudyakov V.A. bober@gorodok.net
|
||||
//////////////////////////////////////////////
|
||||
|
||||
#include "_cvaux.h"
|
||||
#include "_cvfacedetection.h"
|
||||
|
||||
CvSeq * cvFindFace(IplImage * Image,CvMemStorage* lpStorage)
|
||||
{
|
||||
FaceDetection FD;
|
||||
FD.SetBoosting(false);
|
||||
FD.FindFace(Image);
|
||||
CvSeq * lpSeq = cvCreateSeq(0,sizeof(*lpSeq),sizeof(CvFace),lpStorage);
|
||||
FD.CreateResults(lpSeq);
|
||||
return lpSeq;
|
||||
}//cvFindFace(IplImage * Image)
|
||||
|
||||
CvSeq * cvPostBoostingFindFace(IplImage * Image,CvMemStorage* lpStorage)
|
||||
{
|
||||
FaceDetection FD;
|
||||
FD.SetBoosting(true);
|
||||
FD.FindFace(Image);
|
||||
CvSeq * lpSeq = cvCreateSeq(0,sizeof(*lpSeq),sizeof(CvFace),lpStorage);
|
||||
FD.CreateResults(lpSeq);
|
||||
|
||||
return lpSeq;
|
||||
}//cvPostBoostingFindFace(IplImage * Image)
|
||||
|
||||
@@ -0,0 +1,645 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
#include "_cvaux.h"
|
||||
|
||||
#define _CV_NORM_L2(a) (float)(icvSqrt32f(a[0]*a[0] + a[1]*a[1] + a[2]*a[2]))
|
||||
#define _CV_NORM_L22(a) (float)(a[0]*a[0] + a[1]*a[1] + a[2]*a[2])
|
||||
|
||||
/****************************************************************************************\
|
||||
|
||||
find region where hand is (for gesture recognition)
|
||||
flag = 0 (use left bucket) flag = 1 (use right bucket)
|
||||
|
||||
\****************************************************************************************/
|
||||
|
||||
static CvStatus CV_STDCALL
|
||||
icvFindHandRegion( CvPoint3D32f * points, int count,
|
||||
CvSeq * indexs,
|
||||
float *line, CvSize2D32f size, int flag,
|
||||
CvPoint3D32f * center,
|
||||
CvMemStorage * storage, CvSeq ** numbers )
|
||||
{
|
||||
|
||||
/* IppmVect32f sub, cros; */
|
||||
float *sub, *cros;
|
||||
CvSeqWriter writer;
|
||||
CvSeqReader reader;
|
||||
|
||||
CvStatus status;
|
||||
int nbins = 20, i, l, i_point, left, right;
|
||||
int *bin_counts = 0; // pointer to the point's counter in the bickets
|
||||
int low_count; // low threshold
|
||||
|
||||
CvPoint *tmp_number = 0, *pt;
|
||||
float value, vmin, vmax, vl, bsize, vc;
|
||||
float hand_length, hand_length2, hand_left, hand_right;
|
||||
float threshold, threshold2;
|
||||
float *vv = 0;
|
||||
float a[3];
|
||||
|
||||
status = CV_OK;
|
||||
|
||||
hand_length = size.width;
|
||||
hand_length2 = hand_length / 2;
|
||||
|
||||
threshold = (float) (size.height * 3 / 5.);
|
||||
threshold2 = threshold * threshold;
|
||||
|
||||
/* low_count = count/nbins; */
|
||||
low_count = (int) (count / 60.);
|
||||
|
||||
assert( points != NULL && line != NULL );
|
||||
if( points == NULL || line == NULL )
|
||||
return CV_NULLPTR_ERR;
|
||||
|
||||
assert( count > 5 );
|
||||
if( count < 5 )
|
||||
return CV_BADFLAG_ERR;
|
||||
|
||||
assert( flag == 0 || flag == 1 );
|
||||
if( flag != 0 && flag != 1 )
|
||||
return CV_BADFLAG_ERR;
|
||||
|
||||
/* create vectors */
|
||||
sub = icvCreateVector_32f( 3 );
|
||||
cros = icvCreateVector_32f( 3 );
|
||||
if( sub == NULL || cros == NULL )
|
||||
return CV_OUTOFMEM_ERR;
|
||||
|
||||
/* alloc memory for the point's projections on the line */
|
||||
vv = (float *) cvAlloc( count * sizeof( float ));
|
||||
|
||||
if( vv == NULL )
|
||||
return CV_OUTOFMEM_ERR;
|
||||
|
||||
/* alloc memory for the point's counter in the bickets */
|
||||
bin_counts = (int *) cvAlloc( nbins * sizeof( int ));
|
||||
|
||||
if( bin_counts == NULL )
|
||||
{
|
||||
status = CV_OUTOFMEM_ERR;
|
||||
goto M_END;
|
||||
}
|
||||
memset( bin_counts, 0, nbins * sizeof( int ));
|
||||
|
||||
cvStartReadSeq( indexs, &reader, 0 );
|
||||
|
||||
/* alloc memory for the temporale point's numbers */
|
||||
tmp_number = (CvPoint *) cvAlloc( count * sizeof( CvPoint ));
|
||||
if( tmp_number == NULL )
|
||||
{
|
||||
status = CV_OUTOFMEM_ERR;
|
||||
goto M_END;
|
||||
}
|
||||
|
||||
/* find min and max point's projection on the line */
|
||||
vmin = 1000;
|
||||
vmax = -1000;
|
||||
i_point = 0;
|
||||
for( i = 0; i < count; i++ )
|
||||
{
|
||||
/*
|
||||
icvSubVector_32f ((IppmVect32f )&points[i], (IppmVect32f )&line[3], sub, 3);
|
||||
|
||||
icvCrossProduct2L_32f ((IppmVect32f )&line[0], sub, cros);
|
||||
*/
|
||||
|
||||
sub[0] = points[i].x - line[3];
|
||||
sub[1] = points[i].y - line[4];
|
||||
sub[2] = points[i].z - line[5];
|
||||
a[0] = sub[0] * line[1] - sub[1] * line[0];
|
||||
a[1] = sub[1] * line[2] - sub[2] * line[1];
|
||||
a[2] = sub[2] * line[0] - sub[0] * line[2];
|
||||
|
||||
/* if(IPPI_NORM_L22 ( cros ) < threshold2) */
|
||||
if( _CV_NORM_L22( a ) < threshold2 )
|
||||
{
|
||||
value = (float)icvDotProduct_32f( sub, &line[0], 3 );
|
||||
if( value > vmax )
|
||||
vmax = value;
|
||||
if( value < vmin )
|
||||
vmin = value;
|
||||
|
||||
vv[i_point] = value;
|
||||
|
||||
pt = (CvPoint*)cvGetSeqElem( indexs, i );
|
||||
tmp_number[i_point] = *pt;
|
||||
i_point++;
|
||||
}
|
||||
}
|
||||
|
||||
/* compute the length of one bucket */
|
||||
vl = vmax - vmin;
|
||||
bsize = vl / nbins;
|
||||
|
||||
/* compute the number of points in each bucket */
|
||||
for( i = 0; i < i_point; i++ )
|
||||
{
|
||||
l = cvRound( (vv[i] - vmin) / bsize );
|
||||
bin_counts[l]++;
|
||||
}
|
||||
|
||||
*numbers = cvCreateSeq( CV_SEQ_POINT_SET, sizeof( CvSeq ), sizeof( CvPoint ), storage );
|
||||
assert( numbers != 0 );
|
||||
if( numbers == NULL )
|
||||
{
|
||||
status = CV_OUTOFMEM_ERR;
|
||||
goto M_END;
|
||||
}
|
||||
|
||||
cvStartAppendToSeq( *numbers, &writer );
|
||||
|
||||
if( flag == 0 )
|
||||
{
|
||||
/* find the leftmost bucket */
|
||||
for( l = 0; l < nbins; l++ )
|
||||
{
|
||||
if( bin_counts[l] > low_count )
|
||||
break;
|
||||
}
|
||||
left = l;
|
||||
|
||||
/* compute center point of the left hand */
|
||||
hand_left = vmin + left * bsize;
|
||||
vc = hand_left + hand_length2;
|
||||
hand_right = hand_left + hand_length;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* find the rightmost bucket */
|
||||
for( l = nbins - 1; l >= 0; l-- )
|
||||
{
|
||||
if( bin_counts[l] > low_count )
|
||||
break;
|
||||
}
|
||||
right = l;
|
||||
|
||||
/* compute center point of the right hand */
|
||||
hand_right = vmax - (nbins - right - 1) * bsize;
|
||||
vc = hand_right - hand_length2;
|
||||
hand_left = hand_right - hand_length;
|
||||
}
|
||||
|
||||
icvScaleVector_32f( &line[0], sub, 3, vc );
|
||||
icvAddVector_32f( &line[3], sub, (float *) center, 3 );
|
||||
|
||||
/* select hand's points and calculate mean value */
|
||||
|
||||
//ss.x = ss.y = ss.z = 0;
|
||||
for( l = 0; l < i_point; l++ )
|
||||
{
|
||||
if( vv[l] >= hand_left && vv[l] <= hand_right )
|
||||
{
|
||||
CV_WRITE_SEQ_ELEM( tmp_number[l], writer );
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
cvEndWriteSeq( &writer );
|
||||
|
||||
M_END:
|
||||
if( tmp_number != NULL )
|
||||
cvFree( &tmp_number );
|
||||
if( bin_counts != NULL )
|
||||
cvFree( &bin_counts );
|
||||
if( vv != NULL )
|
||||
cvFree( &vv );
|
||||
if( sub != NULL ) icvDeleteVector (sub);
|
||||
if( cros != NULL ) icvDeleteVector (cros);
|
||||
|
||||
return status;
|
||||
|
||||
}
|
||||
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////////////////
|
||||
//////////////////////////////////////////////////////////////////////////////////////////
|
||||
//////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
|
||||
#define _CV_NORM_L31(a) (float)(icvSqrt32f(a[0]*a[0] + a[1]*a[1] + a[2]*a[2]))
|
||||
#define _CV_NORM_L32(a) (float)(a[0]*a[0] + a[1]*a[1] + a[2]*a[2])
|
||||
|
||||
/****************************************************************************************\
|
||||
|
||||
find region where hand is (for gesture recognition)
|
||||
flag = 0 (use left bucket) flag = 1 (use right bucket)
|
||||
|
||||
\****************************************************************************************/
|
||||
|
||||
static CvStatus CV_STDCALL
|
||||
icvFindHandRegionA( CvPoint3D32f * points, int count,
|
||||
CvSeq * indexs,
|
||||
float *line, CvSize2D32f size, int jc,
|
||||
CvPoint3D32f * center,
|
||||
CvMemStorage * storage, CvSeq ** numbers )
|
||||
{
|
||||
|
||||
/* IppmVect32f sub, cros; */
|
||||
float *sub, *cros;
|
||||
float eps = (float) 0.01;
|
||||
CvSeqWriter writer;
|
||||
CvSeqReader reader;
|
||||
|
||||
CvStatus status;
|
||||
float gor[3] = { 1, 0, 0 };
|
||||
float ver[3] = { 0, 1, 0 };
|
||||
|
||||
int nbins = 20, i, l, i_point, left, right, jmin, jmax, jl;
|
||||
int j_left, j_right;
|
||||
int *bin_counts = 0; // pointer to the point's counter in the bickets
|
||||
|
||||
// int *bin_countsj = 0; // pointer to the index's counter in the bickets
|
||||
int low_count; // low threshold
|
||||
|
||||
CvPoint *tmp_number = 0, *pt;
|
||||
float value, vmin, vmax, vl, bsize, bsizej, vc, vcl, vcr;
|
||||
double v_ver, v_gor;
|
||||
float hand_length, hand_length2, hand_left, hand_right;
|
||||
float threshold, threshold2;
|
||||
float *vv = 0;
|
||||
float a[3];
|
||||
char log;
|
||||
|
||||
status = CV_OK;
|
||||
|
||||
hand_length = size.width;
|
||||
hand_length2 = hand_length / 2;
|
||||
|
||||
threshold = (float) (size.height * 3 / 5.);
|
||||
threshold2 = threshold * threshold;
|
||||
|
||||
/* low_count = count/nbins; */
|
||||
low_count = (int) (count / 60.);
|
||||
|
||||
assert( points != NULL && line != NULL );
|
||||
if( points == NULL || line == NULL )
|
||||
return CV_NULLPTR_ERR;
|
||||
|
||||
assert( count > 5 );
|
||||
if( count < 5 )
|
||||
return CV_BADFLAG_ERR;
|
||||
|
||||
/* create vectors */
|
||||
sub = icvCreateVector_32f( 3 );
|
||||
cros = icvCreateVector_32f( 3 );
|
||||
if( sub == NULL || cros == NULL )
|
||||
return CV_OUTOFMEM_ERR;
|
||||
|
||||
/* alloc memory for the point's projections on the line */
|
||||
vv = (float *) cvAlloc( count * sizeof( float ));
|
||||
|
||||
if( vv == NULL )
|
||||
return CV_OUTOFMEM_ERR;
|
||||
|
||||
/* alloc memory for the point's counter in the bickets */
|
||||
bin_counts = (int *) cvAlloc( nbins * sizeof( int ));
|
||||
|
||||
if( bin_counts == NULL )
|
||||
{
|
||||
status = CV_OUTOFMEM_ERR;
|
||||
goto M_END;
|
||||
}
|
||||
memset( bin_counts, 0, nbins * sizeof( int ));
|
||||
|
||||
/* alloc memory for the point's counter in the bickets */
|
||||
// bin_countsj = (int*) icvAlloc(nbins*sizeof(int));
|
||||
// if(bin_countsj == NULL) {status = CV_OUTOFMEM_ERR; goto M_END;}
|
||||
// memset(bin_countsj,0,nbins*sizeof(int));
|
||||
|
||||
cvStartReadSeq( indexs, &reader, 0 );
|
||||
|
||||
/* alloc memory for the temporale point's numbers */
|
||||
tmp_number = (CvPoint *) cvAlloc( count * sizeof( CvPoint ));
|
||||
if( tmp_number == NULL )
|
||||
{
|
||||
status = CV_OUTOFMEM_ERR;
|
||||
goto M_END;
|
||||
}
|
||||
|
||||
/* find min and max point's projection on the line */
|
||||
vmin = 1000;
|
||||
vmax = -1000;
|
||||
jmin = 1000;
|
||||
jmax = -1000;
|
||||
i_point = 0;
|
||||
for( i = 0; i < count; i++ )
|
||||
{
|
||||
/*
|
||||
icvSubVector_32f ((IppmVect32f )&points[i], (IppmVect32f )&line[3], sub, 3);
|
||||
|
||||
icvCrossProduct2L_32f ((IppmVect32f )&line[0], sub, cros);
|
||||
*/
|
||||
|
||||
sub[0] = points[i].x - line[3];
|
||||
sub[1] = points[i].y - line[4];
|
||||
sub[2] = points[i].z - line[5];
|
||||
|
||||
// if(fabs(sub[0])<eps||fabs(sub[1])<eps||fabs(sub[2])<eps) continue;
|
||||
|
||||
a[0] = sub[0] * line[1] - sub[1] * line[0];
|
||||
a[1] = sub[1] * line[2] - sub[2] * line[1];
|
||||
a[2] = sub[2] * line[0] - sub[0] * line[2];
|
||||
|
||||
v_gor = icvDotProduct_32f( gor, &line[0], 3 );
|
||||
v_ver = icvDotProduct_32f( ver, &line[0], 3 );
|
||||
|
||||
if( v_ver > v_gor )
|
||||
log = true;
|
||||
else
|
||||
log = false;
|
||||
|
||||
|
||||
/* if(IPPI_NORM_L22 ( cros ) < threshold2) */
|
||||
/*
|
||||
if(fabs(a[0])<eps && fabs(a[1])<eps && fabs(a[2])<eps)
|
||||
{
|
||||
icvDotProduct_32f( sub, &line[0], 3, &value);
|
||||
if(value > vmax) vmax = value;
|
||||
if(value < vmin) vmin = value;
|
||||
|
||||
vv[i_point] = value;
|
||||
|
||||
pt = (CvPoint* )icvGetSeqElem ( indexs, i, 0);
|
||||
|
||||
if(pt->x > jmax) jmax = pt->x;
|
||||
if(pt->x < jmin) jmin = pt->x;
|
||||
|
||||
tmp_number[i_point] = *pt;
|
||||
i_point++;
|
||||
}
|
||||
else
|
||||
*/
|
||||
{
|
||||
if( _CV_NORM_L32( a ) < threshold2 )
|
||||
{
|
||||
value = (float)icvDotProduct_32f( sub, &line[0], 3 );
|
||||
if( value > vmax )
|
||||
vmax = value;
|
||||
if( value < vmin )
|
||||
vmin = value;
|
||||
|
||||
vv[i_point] = value;
|
||||
|
||||
pt = (CvPoint*)cvGetSeqElem( indexs, i );
|
||||
|
||||
if( !log )
|
||||
{
|
||||
if( pt->x > jmax )
|
||||
jmax = pt->x;
|
||||
if( pt->x < jmin )
|
||||
jmin = pt->x;
|
||||
}
|
||||
else
|
||||
{
|
||||
if( pt->y > jmax )
|
||||
jmax = pt->y;
|
||||
if( pt->y < jmin )
|
||||
jmin = pt->y;
|
||||
}
|
||||
|
||||
|
||||
tmp_number[i_point] = *pt;
|
||||
i_point++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* compute the length of one bucket along the line */
|
||||
vl = vmax - vmin;
|
||||
|
||||
/* examining on the arm's existence */
|
||||
if( vl < eps )
|
||||
{
|
||||
*numbers = NULL;
|
||||
status = CV_OK;
|
||||
goto M_END;
|
||||
}
|
||||
|
||||
bsize = vl / nbins;
|
||||
|
||||
/* compute the number of points in each bucket along the line */
|
||||
for( i = 0; i < i_point; i++ )
|
||||
{
|
||||
l = cvRound( (vv[i] - vmin) / bsize );
|
||||
bin_counts[l]++;
|
||||
}
|
||||
|
||||
/* compute the length of one bucket along the X axe */
|
||||
jl = jmax - jmin;
|
||||
if( jl <= 1 )
|
||||
{
|
||||
*numbers = NULL;
|
||||
status = CV_OK;
|
||||
goto M_END;
|
||||
}
|
||||
|
||||
bsizej = (float) (jl / (nbins + 0.));
|
||||
|
||||
/* compute the number of points in each bucket along the X axe */
|
||||
// for(i=0;i<i_point;i++)
|
||||
// {
|
||||
// l = cvRound((tmp_number[i].x - jmin)/bsizej);
|
||||
// bin_countsj[l]++;
|
||||
// }
|
||||
|
||||
|
||||
left = right = -1;
|
||||
|
||||
/* find the leftmost and the rightmost buckets */
|
||||
for( l = 0; l < nbins; l++ )
|
||||
{
|
||||
if( bin_counts[l] > low_count && left == -1 )
|
||||
left = l;
|
||||
else if( bin_counts[l] > low_count && left >= 0 )
|
||||
right = l;
|
||||
|
||||
}
|
||||
|
||||
/* compute center point of the left hand */
|
||||
if( left == -1 && right == -1 )
|
||||
{
|
||||
*numbers = NULL;
|
||||
status = CV_OK;
|
||||
goto M_END;
|
||||
}
|
||||
|
||||
hand_left = vmin + left * bsize;
|
||||
j_left = (int) (jmin + left * bsizej);
|
||||
|
||||
vcl = hand_left + hand_length2;
|
||||
|
||||
/* compute center point of the right hand */
|
||||
hand_right = vmax - (nbins - right - 1) * bsize;
|
||||
vcr = hand_right - hand_length2;
|
||||
|
||||
j_right = (int) (jmax - (nbins - right - 1) * bsizej);
|
||||
|
||||
j_left = abs( j_left - jc );
|
||||
j_right = abs( j_right - jc );
|
||||
|
||||
if( j_left <= j_right )
|
||||
{
|
||||
hand_right = hand_left + hand_length;
|
||||
vc = vcl;
|
||||
}
|
||||
else
|
||||
{
|
||||
hand_left = hand_right - hand_length;
|
||||
vc = vcr;
|
||||
}
|
||||
|
||||
icvScaleVector_32f( &line[0], sub, 3, vc );
|
||||
icvAddVector_32f( &line[3], sub, (float *) center, 3 );
|
||||
|
||||
/* select hand's points and calculate mean value */
|
||||
*numbers = cvCreateSeq( CV_SEQ_POINT_SET, sizeof( CvSeq ), sizeof( CvPoint ), storage );
|
||||
assert( *numbers != 0 );
|
||||
if( *numbers == NULL )
|
||||
{
|
||||
status = CV_OUTOFMEM_ERR;
|
||||
goto M_END;
|
||||
}
|
||||
|
||||
cvStartAppendToSeq( *numbers, &writer );
|
||||
|
||||
for( l = 0; l < i_point; l++ )
|
||||
{
|
||||
if( vv[l] >= hand_left && vv[l] <= hand_right )
|
||||
{
|
||||
CV_WRITE_SEQ_ELEM( tmp_number[l], writer );
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
cvEndWriteSeq( &writer );
|
||||
|
||||
M_END:
|
||||
if( tmp_number != NULL )
|
||||
cvFree( &tmp_number );
|
||||
// if(bin_countsj != NULL) cvFree( &bin_countsj );
|
||||
if( bin_counts != NULL )
|
||||
cvFree( &bin_counts );
|
||||
|
||||
if( vv != NULL )
|
||||
cvFree( &vv );
|
||||
|
||||
if( sub != NULL ) icvDeleteVector (sub);
|
||||
if( cros != NULL ) icvDeleteVector (cros);
|
||||
|
||||
return status;
|
||||
}
|
||||
|
||||
|
||||
/*F///////////////////////////////////////////////////////////////////////////////////////
|
||||
// Name: cvFindHandRegion
|
||||
// Purpose: finds hand region in range image data
|
||||
// Context:
|
||||
// Parameters:
|
||||
// points - pointer to the input point's set.
|
||||
// count - the number of the input points.
|
||||
// indexs - pointer to the input sequence of the point's indexes
|
||||
// line - pointer to the 3D-line
|
||||
// size - size of the hand in meters
|
||||
// flag - hand direction's flag (0 - left, -1 - right,
|
||||
// otherwise j-index of the initial image center)
|
||||
// center - pointer to the output hand center
|
||||
// storage - pointer to the memory storage
|
||||
// numbers - pointer to the output sequence of the point's indexes inside
|
||||
// hand region
|
||||
//
|
||||
// Notes:
|
||||
//F*/
|
||||
CV_IMPL void
|
||||
cvFindHandRegion( CvPoint3D32f * points, int count,
|
||||
CvSeq * indexs,
|
||||
float *line, CvSize2D32f size, int flag,
|
||||
CvPoint3D32f * center, CvMemStorage * storage, CvSeq ** numbers )
|
||||
{
|
||||
CV_FUNCNAME( "cvFindHandRegion" );
|
||||
__BEGIN__;
|
||||
|
||||
if(flag == 0 || flag == -1)
|
||||
{
|
||||
IPPI_CALL( icvFindHandRegion( points, count, indexs, line, size, -flag,
|
||||
center, storage, numbers ));
|
||||
}
|
||||
else
|
||||
IPPI_CALL( icvFindHandRegionA( points, count, indexs, line, size, flag,
|
||||
center, storage, numbers ));
|
||||
|
||||
__CLEANUP__;
|
||||
__END__;
|
||||
}
|
||||
|
||||
/*F///////////////////////////////////////////////////////////////////////////////////////
|
||||
// Name: cvFindHandRegionA
|
||||
// Purpose: finds hand region in range image data
|
||||
// Context:
|
||||
// Parameters:
|
||||
// points - pointer to the input point's set.
|
||||
// count - the number of the input points.
|
||||
// indexs - pointer to the input sequence of the point's indexes
|
||||
// line - pointer to the 3D-line
|
||||
// size - size of the hand in meters
|
||||
// jc - j-index of the initial image center
|
||||
// center - pointer to the output hand center
|
||||
// storage - pointer to the memory storage
|
||||
// numbers - pointer to the output sequence of the point's indexes inside
|
||||
// hand region
|
||||
//
|
||||
// Notes:
|
||||
//F*/
|
||||
CV_IMPL void
|
||||
cvFindHandRegionA( CvPoint3D32f * points, int count,
|
||||
CvSeq * indexs,
|
||||
float *line, CvSize2D32f size, int jc,
|
||||
CvPoint3D32f * center, CvMemStorage * storage, CvSeq ** numbers )
|
||||
{
|
||||
CV_FUNCNAME( "cvFindHandRegionA" );
|
||||
__BEGIN__;
|
||||
|
||||
IPPI_CALL( icvFindHandRegionA( points, count, indexs, line, size, jc,
|
||||
center, storage, numbers ));
|
||||
__CLEANUP__;
|
||||
__END__;
|
||||
}
|
||||
|
||||
1770
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/src/cvhmm.cpp
Normal file
1770
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/src/cvhmm.cpp
Normal file
File diff suppressed because it is too large
Load Diff
1151
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/src/cvhmm1d.cpp
Normal file
1151
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/src/cvhmm1d.cpp
Normal file
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,634 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
#include "_cvaux.h"
|
||||
|
||||
//*F///////////////////////////////////////////////////////////////////////////////////////
|
||||
// Name: icvImgToObs_DCT_8u32f_C1R
|
||||
// Purpose: The function takes as input an image and returns the sequnce of observations
|
||||
// to be used with an embedded HMM; Each observation is top-left block of DCT
|
||||
// coefficient matrix.
|
||||
// Context:
|
||||
// Parameters: img - pointer to the original image ROI
|
||||
// imgStep - full row width of the image in bytes
|
||||
// roi - width and height of ROI in pixels
|
||||
// obs - pointer to resultant observation vectors
|
||||
// dctSize - size of the block for which DCT is calculated
|
||||
// obsSize - size of top-left block of DCT coeffs matrix, which is treated
|
||||
// as observation. Each observation vector consists of
|
||||
// obsSize.width * obsSize.height floats.
|
||||
// The following conditions should be satisfied:
|
||||
// 0 < objSize.width <= dctSize.width,
|
||||
// 0 < objSize.height <= dctSize.height.
|
||||
// delta - dctBlocks are overlapped and this parameter specifies horizontal
|
||||
// and vertical shift.
|
||||
// Returns:
|
||||
// CV_NO_ERR or error code
|
||||
// Notes:
|
||||
// The algorithm is following:
|
||||
// 1. First, number of observation vectors per row and per column are calculated:
|
||||
//
|
||||
// Nx = floor((roi.width - dctSize.width + delta.width)/delta.width);
|
||||
// Ny = floor((roi.height - dctSize.height + delta.height)/delta.height);
|
||||
//
|
||||
// So, total number of observation vectors is Nx*Ny, and total size of
|
||||
// array obs must be >= Nx*Ny*obsSize.width*obsSize.height*sizeof(float).
|
||||
// 2. Observation vectors are calculated in the following loop
|
||||
// ( actual implementation may be different ), where
|
||||
// I[x1:x2,y1:y2] means block of pixels from source image with
|
||||
// x1 <= x < x2, y1 <= y < y2,
|
||||
// D[x1:x2,y1:y2] means sub matrix of DCT matrix D.
|
||||
// O[x,y] means observation vector that corresponds to position
|
||||
// (x*delta.width,y*delta.height) in the source image
|
||||
// ( all indices are counted from 0 ).
|
||||
//
|
||||
// for( y = 0; y < Ny; y++ )
|
||||
// {
|
||||
// for( x = 0; x < Nx; x++ )
|
||||
// {
|
||||
// D = DCT(I[x*delta.width : x*delta.width + dctSize.width,
|
||||
// y*delta.height : y*delta.height + dctSize.height]);
|
||||
// O[x,y] = D[0:obsSize.width, 0:obsSize.height];
|
||||
// }
|
||||
// }
|
||||
//F*/
|
||||
|
||||
/*comment out the following line to make DCT be calculated in floating-point arithmetics*/
|
||||
//#define _CV_INT_DCT
|
||||
|
||||
/* for integer DCT only */
|
||||
#define DCT_SCALE 15
|
||||
|
||||
#ifdef _CV_INT_DCT
|
||||
typedef int work_t;
|
||||
|
||||
#define DESCALE CV_DESCALE
|
||||
#define SCALE(x) CV_FLT_TO_FIX((x),DCT_SCALE)
|
||||
#else
|
||||
typedef float work_t;
|
||||
|
||||
#define DESCALE(x,n) (float)(x)
|
||||
#define SCALE(x) (float)(x)
|
||||
#endif
|
||||
|
||||
/* calculate dct transform matrix */
|
||||
static void icvCalcDCTMatrix( work_t * cfs, int n );
|
||||
|
||||
#define MAX_DCT_SIZE 32
|
||||
|
||||
static CvStatus CV_STDCALL
|
||||
icvImgToObs_DCT_8u32f_C1R( uchar * img, int imgStep, CvSize roi,
|
||||
float *obs, CvSize dctSize,
|
||||
CvSize obsSize, CvSize delta )
|
||||
{
|
||||
/* dct transform matrices: horizontal and vertical */
|
||||
work_t tab_x[MAX_DCT_SIZE * MAX_DCT_SIZE / 2 + 2];
|
||||
work_t tab_y[MAX_DCT_SIZE * MAX_DCT_SIZE / 2 + 2];
|
||||
|
||||
/* temporary buffers for dct */
|
||||
work_t temp0[MAX_DCT_SIZE * 4];
|
||||
work_t temp1[MAX_DCT_SIZE * 4];
|
||||
work_t *buffer = 0;
|
||||
work_t *buf_limit;
|
||||
|
||||
double s;
|
||||
|
||||
int y;
|
||||
int Nx, Ny;
|
||||
|
||||
int n1 = dctSize.height, m1 = n1 / 2;
|
||||
int n2 = dctSize.width, m2 = n2 / 2;
|
||||
|
||||
if( !img || !obs )
|
||||
return CV_NULLPTR_ERR;
|
||||
|
||||
if( roi.width <= 0 || roi.height <= 0 )
|
||||
return CV_BADSIZE_ERR;
|
||||
|
||||
if( delta.width <= 0 || delta.height <= 0 )
|
||||
return CV_BADRANGE_ERR;
|
||||
|
||||
if( obsSize.width <= 0 || dctSize.width < obsSize.width ||
|
||||
obsSize.height <= 0 || dctSize.height < obsSize.height )
|
||||
return CV_BADRANGE_ERR;
|
||||
|
||||
if( dctSize.width > MAX_DCT_SIZE || dctSize.height > MAX_DCT_SIZE )
|
||||
return CV_BADRANGE_ERR;
|
||||
|
||||
Nx = (roi.width - dctSize.width + delta.width) / delta.width;
|
||||
Ny = (roi.height - dctSize.height + delta.height) / delta.height;
|
||||
|
||||
if( Nx <= 0 || Ny <= 0 )
|
||||
return CV_BADRANGE_ERR;
|
||||
|
||||
buffer = (work_t *)cvAlloc( roi.width * obsSize.height * sizeof( buffer[0] ));
|
||||
if( !buffer )
|
||||
return CV_OUTOFMEM_ERR;
|
||||
|
||||
icvCalcDCTMatrix( tab_x, dctSize.width );
|
||||
icvCalcDCTMatrix( tab_y, dctSize.height );
|
||||
|
||||
buf_limit = buffer + obsSize.height * roi.width;
|
||||
|
||||
for( y = 0; y < Ny; y++, img += delta.height * imgStep )
|
||||
{
|
||||
int x, i, j, k;
|
||||
work_t k0 = 0;
|
||||
|
||||
/* do transfroms for each column. Calc only first obsSize.height DCT coefficients */
|
||||
for( x = 0; x < roi.width; x++ )
|
||||
{
|
||||
float is = 0;
|
||||
work_t *buf = buffer + x;
|
||||
work_t *tab = tab_y + 2;
|
||||
|
||||
if( n1 & 1 )
|
||||
{
|
||||
is = img[x + m1 * imgStep];
|
||||
k0 = ((work_t) is) * tab[-1];
|
||||
}
|
||||
|
||||
/* first coefficient */
|
||||
for( j = 0; j < m1; j++ )
|
||||
{
|
||||
float t0 = img[x + j * imgStep];
|
||||
float t1 = img[x + (n1 - 1 - j) * imgStep];
|
||||
float t2 = t0 + t1;
|
||||
|
||||
t0 -= t1;
|
||||
temp0[j] = (work_t) t2;
|
||||
is += t2;
|
||||
temp1[j] = (work_t) t0;
|
||||
}
|
||||
|
||||
buf[0] = DESCALE( is * tab[-2], PASS1_SHIFT );
|
||||
if( (buf += roi.width) >= buf_limit )
|
||||
continue;
|
||||
|
||||
/* other coefficients */
|
||||
for( ;; )
|
||||
{
|
||||
s = 0;
|
||||
|
||||
for( k = 0; k < m1; k++ )
|
||||
s += temp1[k] * tab[k];
|
||||
|
||||
buf[0] = DESCALE( s, PASS1_SHIFT );
|
||||
if( (buf += roi.width) >= buf_limit )
|
||||
break;
|
||||
|
||||
tab += m1;
|
||||
s = 0;
|
||||
|
||||
if( n1 & 1 )
|
||||
{
|
||||
k0 = -k0;
|
||||
s = k0;
|
||||
}
|
||||
for( k = 0; k < m1; k++ )
|
||||
s += temp0[k] * tab[k];
|
||||
|
||||
buf[0] = DESCALE( s, PASS1_SHIFT );
|
||||
tab += m1;
|
||||
|
||||
if( (buf += roi.width) >= buf_limit )
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
k0 = 0;
|
||||
|
||||
/* do transforms for rows. */
|
||||
for( x = 0; x + dctSize.width <= roi.width; x += delta.width )
|
||||
{
|
||||
for( i = 0; i < obsSize.height; i++ )
|
||||
{
|
||||
work_t *buf = buffer + x + roi.width * i;
|
||||
work_t *tab = tab_x + 2;
|
||||
float *obs_limit = obs + obsSize.width;
|
||||
|
||||
s = 0;
|
||||
|
||||
if( n2 & 1 )
|
||||
{
|
||||
s = buf[m2];
|
||||
k0 = (work_t) (s * tab[-1]);
|
||||
}
|
||||
|
||||
/* first coefficient */
|
||||
for( j = 0; j < m2; j++ )
|
||||
{
|
||||
work_t t0 = buf[j];
|
||||
work_t t1 = buf[n2 - 1 - j];
|
||||
work_t t2 = t0 + t1;
|
||||
|
||||
t0 -= t1;
|
||||
temp0[j] = (work_t) t2;
|
||||
s += t2;
|
||||
temp1[j] = (work_t) t0;
|
||||
}
|
||||
|
||||
*obs++ = (float) DESCALE( s * tab[-2], PASS2_SHIFT );
|
||||
|
||||
if( obs == obs_limit )
|
||||
continue;
|
||||
|
||||
/* other coefficients */
|
||||
for( ;; )
|
||||
{
|
||||
s = 0;
|
||||
|
||||
for( k = 0; k < m2; k++ )
|
||||
s += temp1[k] * tab[k];
|
||||
|
||||
obs[0] = (float) DESCALE( s, PASS2_SHIFT );
|
||||
if( ++obs == obs_limit )
|
||||
break;
|
||||
|
||||
tab += m2;
|
||||
|
||||
s = 0;
|
||||
|
||||
if( n2 & 1 )
|
||||
{
|
||||
k0 = -k0;
|
||||
s = k0;
|
||||
}
|
||||
for( k = 0; k < m2; k++ )
|
||||
s += temp0[k] * tab[k];
|
||||
obs[0] = (float) DESCALE( s, PASS2_SHIFT );
|
||||
|
||||
tab += m2;
|
||||
if( ++obs == obs_limit )
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
cvFree( &buffer );
|
||||
return CV_NO_ERR;
|
||||
}
|
||||
|
||||
|
||||
static CvStatus CV_STDCALL
|
||||
icvImgToObs_DCT_32f_C1R( float * img, int imgStep, CvSize roi,
|
||||
float *obs, CvSize dctSize,
|
||||
CvSize obsSize, CvSize delta )
|
||||
{
|
||||
/* dct transform matrices: horizontal and vertical */
|
||||
work_t tab_x[MAX_DCT_SIZE * MAX_DCT_SIZE / 2 + 2];
|
||||
work_t tab_y[MAX_DCT_SIZE * MAX_DCT_SIZE / 2 + 2];
|
||||
|
||||
/* temporary buffers for dct */
|
||||
work_t temp0[MAX_DCT_SIZE * 4];
|
||||
work_t temp1[MAX_DCT_SIZE * 4];
|
||||
work_t *buffer = 0;
|
||||
work_t *buf_limit;
|
||||
|
||||
double s;
|
||||
|
||||
int y;
|
||||
int Nx, Ny;
|
||||
|
||||
int n1 = dctSize.height, m1 = n1 / 2;
|
||||
int n2 = dctSize.width, m2 = n2 / 2;
|
||||
|
||||
if( !img || !obs )
|
||||
return CV_NULLPTR_ERR;
|
||||
|
||||
if( roi.width <= 0 || roi.height <= 0 )
|
||||
return CV_BADSIZE_ERR;
|
||||
|
||||
if( delta.width <= 0 || delta.height <= 0 )
|
||||
return CV_BADRANGE_ERR;
|
||||
|
||||
if( obsSize.width <= 0 || dctSize.width < obsSize.width ||
|
||||
obsSize.height <= 0 || dctSize.height < obsSize.height )
|
||||
return CV_BADRANGE_ERR;
|
||||
|
||||
if( dctSize.width > MAX_DCT_SIZE || dctSize.height > MAX_DCT_SIZE )
|
||||
return CV_BADRANGE_ERR;
|
||||
|
||||
Nx = (roi.width - dctSize.width + delta.width) / delta.width;
|
||||
Ny = (roi.height - dctSize.height + delta.height) / delta.height;
|
||||
|
||||
if( Nx <= 0 || Ny <= 0 )
|
||||
return CV_BADRANGE_ERR;
|
||||
|
||||
buffer = (work_t *)cvAlloc( roi.width * obsSize.height * sizeof( buffer[0] ));
|
||||
if( !buffer )
|
||||
return CV_OUTOFMEM_ERR;
|
||||
|
||||
icvCalcDCTMatrix( tab_x, dctSize.width );
|
||||
icvCalcDCTMatrix( tab_y, dctSize.height );
|
||||
|
||||
buf_limit = buffer + obsSize.height * roi.width;
|
||||
|
||||
imgStep /= sizeof(img[0]);
|
||||
|
||||
for( y = 0; y < Ny; y++, img += delta.height * imgStep )
|
||||
{
|
||||
int x, i, j, k;
|
||||
work_t k0 = 0;
|
||||
|
||||
/* do transfroms for each column. Calc only first obsSize.height DCT coefficients */
|
||||
for( x = 0; x < roi.width; x++ )
|
||||
{
|
||||
float is = 0;
|
||||
work_t *buf = buffer + x;
|
||||
work_t *tab = tab_y + 2;
|
||||
|
||||
if( n1 & 1 )
|
||||
{
|
||||
is = img[x + m1 * imgStep];
|
||||
k0 = ((work_t) is) * tab[-1];
|
||||
}
|
||||
|
||||
/* first coefficient */
|
||||
for( j = 0; j < m1; j++ )
|
||||
{
|
||||
float t0 = img[x + j * imgStep];
|
||||
float t1 = img[x + (n1 - 1 - j) * imgStep];
|
||||
float t2 = t0 + t1;
|
||||
|
||||
t0 -= t1;
|
||||
temp0[j] = (work_t) t2;
|
||||
is += t2;
|
||||
temp1[j] = (work_t) t0;
|
||||
}
|
||||
|
||||
buf[0] = DESCALE( is * tab[-2], PASS1_SHIFT );
|
||||
if( (buf += roi.width) >= buf_limit )
|
||||
continue;
|
||||
|
||||
/* other coefficients */
|
||||
for( ;; )
|
||||
{
|
||||
s = 0;
|
||||
|
||||
for( k = 0; k < m1; k++ )
|
||||
s += temp1[k] * tab[k];
|
||||
|
||||
buf[0] = DESCALE( s, PASS1_SHIFT );
|
||||
if( (buf += roi.width) >= buf_limit )
|
||||
break;
|
||||
|
||||
tab += m1;
|
||||
s = 0;
|
||||
|
||||
if( n1 & 1 )
|
||||
{
|
||||
k0 = -k0;
|
||||
s = k0;
|
||||
}
|
||||
for( k = 0; k < m1; k++ )
|
||||
s += temp0[k] * tab[k];
|
||||
|
||||
buf[0] = DESCALE( s, PASS1_SHIFT );
|
||||
tab += m1;
|
||||
|
||||
if( (buf += roi.width) >= buf_limit )
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
k0 = 0;
|
||||
|
||||
/* do transforms for rows. */
|
||||
for( x = 0; x + dctSize.width <= roi.width; x += delta.width )
|
||||
{
|
||||
for( i = 0; i < obsSize.height; i++ )
|
||||
{
|
||||
work_t *buf = buffer + x + roi.width * i;
|
||||
work_t *tab = tab_x + 2;
|
||||
float *obs_limit = obs + obsSize.width;
|
||||
|
||||
s = 0;
|
||||
|
||||
if( n2 & 1 )
|
||||
{
|
||||
s = buf[m2];
|
||||
k0 = (work_t) (s * tab[-1]);
|
||||
}
|
||||
|
||||
/* first coefficient */
|
||||
for( j = 0; j < m2; j++ )
|
||||
{
|
||||
work_t t0 = buf[j];
|
||||
work_t t1 = buf[n2 - 1 - j];
|
||||
work_t t2 = t0 + t1;
|
||||
|
||||
t0 -= t1;
|
||||
temp0[j] = (work_t) t2;
|
||||
s += t2;
|
||||
temp1[j] = (work_t) t0;
|
||||
}
|
||||
|
||||
*obs++ = (float) DESCALE( s * tab[-2], PASS2_SHIFT );
|
||||
|
||||
if( obs == obs_limit )
|
||||
continue;
|
||||
|
||||
/* other coefficients */
|
||||
for( ;; )
|
||||
{
|
||||
s = 0;
|
||||
|
||||
for( k = 0; k < m2; k++ )
|
||||
s += temp1[k] * tab[k];
|
||||
|
||||
obs[0] = (float) DESCALE( s, PASS2_SHIFT );
|
||||
if( ++obs == obs_limit )
|
||||
break;
|
||||
|
||||
tab += m2;
|
||||
|
||||
s = 0;
|
||||
|
||||
if( n2 & 1 )
|
||||
{
|
||||
k0 = -k0;
|
||||
s = k0;
|
||||
}
|
||||
for( k = 0; k < m2; k++ )
|
||||
s += temp0[k] * tab[k];
|
||||
obs[0] = (float) DESCALE( s, PASS2_SHIFT );
|
||||
|
||||
tab += m2;
|
||||
if( ++obs == obs_limit )
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
cvFree( &buffer );
|
||||
return CV_NO_ERR;
|
||||
}
|
||||
|
||||
|
||||
static void
|
||||
icvCalcDCTMatrix( work_t * cfs, int n )
|
||||
{
|
||||
static const double sqrt2 = 1.4142135623730950488016887242097;
|
||||
static const double pi = 3.1415926535897932384626433832795;
|
||||
|
||||
static const double sincos[16 * 2] = {
|
||||
1.00000000000000000, 0.00000000000000006,
|
||||
0.70710678118654746, 0.70710678118654757,
|
||||
0.49999999999999994, 0.86602540378443871,
|
||||
0.38268343236508978, 0.92387953251128674,
|
||||
0.30901699437494740, 0.95105651629515353,
|
||||
0.25881904510252074, 0.96592582628906831,
|
||||
0.22252093395631439, 0.97492791218182362,
|
||||
0.19509032201612825, 0.98078528040323043,
|
||||
0.17364817766693033, 0.98480775301220802,
|
||||
0.15643446504023087, 0.98768834059513777,
|
||||
0.14231483827328514, 0.98982144188093268,
|
||||
0.13052619222005157, 0.99144486137381038,
|
||||
0.12053668025532305, 0.99270887409805397,
|
||||
0.11196447610330786, 0.99371220989324260,
|
||||
0.10452846326765346, 0.99452189536827329,
|
||||
0.09801714032956060, 0.99518472667219693,
|
||||
};
|
||||
|
||||
#define ROTATE( c, s, dc, ds ) \
|
||||
{ \
|
||||
t = c*dc - s*ds; \
|
||||
s = c*ds + s*dc; \
|
||||
c = t; \
|
||||
}
|
||||
|
||||
#define WRITE2( j, a, b ) \
|
||||
{ \
|
||||
cfs[j] = SCALE(a); \
|
||||
cfs2[j] = SCALE(b); \
|
||||
}
|
||||
|
||||
double t, scale = 1. / sqrt( (double)n );
|
||||
int i, j, m = n / 2;
|
||||
|
||||
cfs[0] = SCALE( scale );
|
||||
scale *= sqrt2;
|
||||
cfs[1] = SCALE( scale );
|
||||
cfs += 2 - m;
|
||||
|
||||
if( n > 1 )
|
||||
{
|
||||
double a0, b0;
|
||||
double da0, db0;
|
||||
work_t *cfs2 = cfs + m * n;
|
||||
|
||||
if( n <= 16 )
|
||||
{
|
||||
da0 = a0 = sincos[2 * n - 1];
|
||||
db0 = b0 = sincos[2 * n - 2];
|
||||
}
|
||||
else
|
||||
{
|
||||
t = pi / (2 * n);
|
||||
da0 = a0 = cos( t );
|
||||
db0 = b0 = sin( t );
|
||||
}
|
||||
|
||||
/* other rows */
|
||||
for( i = 1; i <= m; i++ )
|
||||
{
|
||||
double a = a0 * scale;
|
||||
double b = b0 * scale;
|
||||
double da = a0 * a0 - b0 * b0;
|
||||
double db = a0 * b0 + a0 * b0;
|
||||
|
||||
cfs += m;
|
||||
cfs2 -= m;
|
||||
|
||||
for( j = 0; j < m; j += 2 )
|
||||
{
|
||||
WRITE2( j, a, b );
|
||||
ROTATE( a, b, da, db );
|
||||
if( j + 1 < m )
|
||||
{
|
||||
WRITE2( j + 1, a, -b );
|
||||
ROTATE( a, b, da, db );
|
||||
}
|
||||
}
|
||||
|
||||
ROTATE( a0, b0, da0, db0 );
|
||||
}
|
||||
}
|
||||
#undef ROTATE
|
||||
#undef WRITE2
|
||||
}
|
||||
|
||||
|
||||
CV_IMPL void
|
||||
cvImgToObs_DCT( const void* arr, float *obs, CvSize dctSize,
|
||||
CvSize obsSize, CvSize delta )
|
||||
{
|
||||
CV_FUNCNAME( "cvImgToObs_DCT" );
|
||||
|
||||
__BEGIN__;
|
||||
|
||||
CvMat stub, *mat = (CvMat*)arr;
|
||||
|
||||
CV_CALL( mat = cvGetMat( arr, &stub ));
|
||||
|
||||
switch( CV_MAT_TYPE( mat->type ))
|
||||
{
|
||||
case CV_8UC1:
|
||||
IPPI_CALL( icvImgToObs_DCT_8u32f_C1R( mat->data.ptr, mat->step,
|
||||
cvGetMatSize(mat), obs,
|
||||
dctSize, obsSize, delta ));
|
||||
break;
|
||||
case CV_32FC1:
|
||||
IPPI_CALL( icvImgToObs_DCT_32f_C1R( mat->data.fl, mat->step,
|
||||
cvGetMatSize(mat), obs,
|
||||
dctSize, obsSize, delta ));
|
||||
break;
|
||||
default:
|
||||
CV_ERROR( CV_StsUnsupportedFormat, "" );
|
||||
}
|
||||
|
||||
__END__;
|
||||
}
|
||||
|
||||
|
||||
/* End of file. */
|
||||
724
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/src/cvlcm.cpp
Normal file
724
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/src/cvlcm.cpp
Normal file
@@ -0,0 +1,724 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
/* Hybrid linear-contour model reconstruction */
|
||||
#include "_cvaux.h"
|
||||
|
||||
#define CV_IMPL CV_EXTERN_C
|
||||
|
||||
const float LCM_CONST_ZERO = 1e-6f;
|
||||
|
||||
/****************************************************************************************\
|
||||
* Auxiliary struct definitions *
|
||||
\****************************************************************************************/
|
||||
typedef struct CvLCM
|
||||
{
|
||||
CvGraph* Graph;
|
||||
CvVoronoiDiagram2D* VoronoiDiagram;
|
||||
CvMemStorage* ContourStorage;
|
||||
CvMemStorage* EdgeStorage;
|
||||
float maxWidth;
|
||||
} CvLCM;
|
||||
|
||||
typedef struct CvLCMComplexNodeData
|
||||
{
|
||||
CvVoronoiNode2D edge_node;
|
||||
CvPoint2D32f site_first_pt;
|
||||
CvPoint2D32f site_last_pt;
|
||||
CvVoronoiSite2D* site_first;
|
||||
CvVoronoiSite2D* site_last;
|
||||
CvVoronoiEdge2D* edge;
|
||||
} CvLCMComplexNodeData;
|
||||
|
||||
typedef struct CvLCMData
|
||||
{
|
||||
CvVoronoiNode2D* pnode;
|
||||
CvVoronoiSite2D* psite;
|
||||
CvVoronoiEdge2D* pedge;
|
||||
} CvLCMData;
|
||||
|
||||
|
||||
/****************************************************************************************\
|
||||
* Function definitions *
|
||||
\****************************************************************************************/
|
||||
|
||||
#define _CV_READ_SEQ_ELEM( elem, reader, type ) \
|
||||
{ \
|
||||
assert( (reader).seq->elem_size == sizeof(*elem)); \
|
||||
elem = (type)(reader).ptr; \
|
||||
CV_NEXT_SEQ_ELEM( sizeof(*elem), reader ) \
|
||||
}
|
||||
|
||||
#define _CV_IS_SITE_REFLEX( SITE ) ((SITE) ->node[0] == (SITE) ->node[1])
|
||||
#define _CV_IS_EDGE_REFLEX( EDGE ) (( (EDGE)->site[0]->node[0] == (EDGE)->site[0]->node[0] ) || \
|
||||
( (EDGE)->site[1]->node[0] == (EDGE)->site[1]->node[0] ) )
|
||||
|
||||
#define _CV_INITIALIZE_CVLCMDATA(STRUCT,SITE,EDGE,NODE)\
|
||||
{ (STRUCT)->psite = SITE ; (STRUCT)->pedge = EDGE; (STRUCT)->pnode = NODE;}
|
||||
/*F///////////////////////////////////////////////////////////////////////////////////////
|
||||
// Author: Andrey Sobolev
|
||||
// Name: _cvConstructLCM
|
||||
// Purpose: Function constructs hybrid model
|
||||
// Context:
|
||||
// Parameters:
|
||||
// LCM : in&out.
|
||||
// Returns: 1, if hybrid model was succesfully constructed
|
||||
// 0, if some error occures
|
||||
//F*/
|
||||
CV_IMPL
|
||||
int _cvConstructLCM(CvLCM* LCM);
|
||||
|
||||
/*F///////////////////////////////////////////////////////////////////////////////////////
|
||||
// Author: Andrey Sobolev
|
||||
// Name: _cvConstructLCMComplexNode
|
||||
// Purpose: Function constructs Complex Node (node, which consists of
|
||||
// two points and more) of hybrid model
|
||||
// Context:
|
||||
// Parameters:
|
||||
// pLCM : in&out.
|
||||
// pLCMEdge: in, input edge of hybrid model
|
||||
// pLCMInputData: in, input parameters
|
||||
// Returns: pointer to constructed node
|
||||
//F*/
|
||||
CV_IMPL
|
||||
CvLCMNode* _cvConstructLCMComplexNode(CvLCM* pLCM,
|
||||
CvLCMEdge* pLCMEdge,
|
||||
CvLCMData* pLCMInputData);
|
||||
|
||||
/*F///////////////////////////////////////////////////////////////////////////////////////
|
||||
// Author: Andrey Sobolev
|
||||
// Name: _cvConstructLCMSimpleNode
|
||||
// Purpose: Function constructs Simple Node (node, which consists of
|
||||
// one point) of hybrid model
|
||||
// Context:
|
||||
// Parameters:
|
||||
// pLCM : in&out.
|
||||
// pLCMEdge: in, input edge of hybrid model
|
||||
// pLCMInputData: in, input parameters
|
||||
// Returns: pointer to constructed node
|
||||
//F*/
|
||||
CV_IMPL
|
||||
CvLCMNode* _cvConstructLCMSimpleNode(CvLCM* pLCM,
|
||||
CvLCMEdge* pLCMEdge,
|
||||
CvLCMData* pLCMInputData);
|
||||
|
||||
/*F///////////////////////////////////////////////////////////////////////////////////////
|
||||
// Author: Andrey Sobolev
|
||||
// Name: _cvConstructLCMSimpleNode
|
||||
// Purpose: Function constructs Edge of hybrid model
|
||||
// Context:
|
||||
// Parameters:
|
||||
// pLCM : in&out.
|
||||
// pLCMInputData: in, input parameters
|
||||
// Returns: pointer to constructed edge
|
||||
//F*/
|
||||
CV_IMPL
|
||||
CvLCMEdge* _cvConstructLCMEdge(CvLCM* pLCM,
|
||||
CvLCMData* pLCMInputData);
|
||||
|
||||
/*F///////////////////////////////////////////////////////////////////////////////////////
|
||||
// Author: Andrey Sobolev
|
||||
// Name: _cvTreatExeptionalCase
|
||||
// Purpose: Function treats triangles and regular polygons
|
||||
// Context:
|
||||
// Parameters:
|
||||
// pLCM : in, information about graph
|
||||
// pLCMInputData: in, input parameters
|
||||
// Returns: pointer to graph node
|
||||
//F*/
|
||||
CV_IMPL
|
||||
CvLCMNode* _cvTreatExeptionalCase(CvLCM* pLCM,
|
||||
CvLCMData* pLCMInputData);
|
||||
|
||||
/*F///////////////////////////////////////////////////////////////////////////////////////
|
||||
// Author: Andrey Sobolev
|
||||
// Name: _cvNodeMultyplicity
|
||||
// Purpose: Function seeks all non-boundary edges incident to
|
||||
// given node and correspondent incident sites
|
||||
// Context:
|
||||
// Parameters:
|
||||
// pEdge : in, original edge
|
||||
// pNode : in, given node
|
||||
// LinkedEdges : out, matrix of incident edges
|
||||
// LinkedSites : out, matrix of incident sites
|
||||
// pSite: in, original site (pNode must be the begin point of pEdge
|
||||
// for this pSite, this property hold out far all edges)
|
||||
// Returns: number of incident edges (must be less than 10)
|
||||
//F*/
|
||||
CV_IMPL
|
||||
int _cvNodeMultyplicity(CvVoronoiSite2D* pSite,
|
||||
CvVoronoiEdge2D* pEdge,
|
||||
CvVoronoiNode2D* pNode,
|
||||
CvVoronoiEdge2D** LinkedEdges,
|
||||
CvVoronoiSite2D** LinkedSites);
|
||||
|
||||
/*F///////////////////////////////////////////////////////////////////////////////////////
|
||||
// Author: Andrey Sobolev
|
||||
// Name: _cvCreateLCMNode
|
||||
// Purpose: Function create graph node
|
||||
// Context:
|
||||
// Parameters:
|
||||
// pLCM : in, information about graph
|
||||
// Returns: pointer to graph node
|
||||
//F*/
|
||||
CV_IMPL
|
||||
CvLCMNode* _cvCreateLCMNode(CvLCM* pLCM);
|
||||
|
||||
/*F///////////////////////////////////////////////////////////////////////////////////////
|
||||
// Author: Andrey Sobolev
|
||||
// Name: _cvCreateLCMEdge
|
||||
// Purpose: Function create graph edge
|
||||
// Context:
|
||||
// Parameters:
|
||||
// pLCM : in, information about graph
|
||||
// Returns: pointer to graph edge
|
||||
//F*/
|
||||
CV_IMPL
|
||||
CvLCMEdge* _cvCreateLCMEdge(CvLCM* pLCM);
|
||||
|
||||
/*F///////////////////////////////////////////////////////////////////////////////////////
|
||||
// Author: Andrey Sobolev
|
||||
// Name: _cvCreateLCMNode
|
||||
// Purpose: Function establishs the connection between node and ege
|
||||
// Context:
|
||||
// Parameters:
|
||||
// LCMNode : in, graph node
|
||||
// LCMEdge : in, graph edge
|
||||
// LCMEdge_prev : in&out, previous edge, connected with given node
|
||||
// index: in,
|
||||
// i : =0, if node is initial for edge
|
||||
// =1, if node is terminal for edge
|
||||
// Returns:
|
||||
//F*/
|
||||
CV_IMPL
|
||||
void _cvAttachLCMEdgeToLCMNode(CvLCMNode* LCMNode,
|
||||
CvLCMEdge* LCMEdge,
|
||||
CvLCMEdge* &LCMEdge_prev,
|
||||
int index,
|
||||
int i);
|
||||
/*F///////////////////////////////////////////////////////////////////////////////////////
|
||||
// Author: Andrey Sobolev
|
||||
// Name: _cvProjectionPointToSegment
|
||||
// Purpose: Function computes the ortogonal projection of PointO to
|
||||
// to segment[PointA, PointB]
|
||||
// Context:
|
||||
// Parameters:
|
||||
// PointO, PointA,PointB: in, given points
|
||||
// PrPoint : out, projection
|
||||
// dist : distance from PointO to PrPoint
|
||||
// Returns:
|
||||
//F*/
|
||||
CV_IMPL
|
||||
void _cvProjectionPointToSegment(CvPoint2D32f* PointO,
|
||||
CvPoint2D32f* PointA,
|
||||
CvPoint2D32f* PointB,
|
||||
CvPoint2D32f* PrPoint,
|
||||
float* dist);
|
||||
|
||||
/*F///////////////////////////////////////////////////////////////////////////////////////
|
||||
// Author: Andrey Sobolev
|
||||
// Name: _cvPrepareData
|
||||
// Purpose: Function fills up the struct CvLCMComplexNodeData
|
||||
// Context:
|
||||
// Parameters:
|
||||
// pLCMData : in
|
||||
// pLCMCCNData : out
|
||||
// Returns:
|
||||
//F*/
|
||||
CV_IMPL
|
||||
void _cvPrepareData(CvLCMComplexNodeData* pLCMCCNData,
|
||||
CvLCMData* pLCMData);
|
||||
|
||||
/****************************************************************************************\
|
||||
* Function realization *
|
||||
\****************************************************************************************/
|
||||
|
||||
CV_IMPL CvGraph* cvLinearContorModelFromVoronoiDiagram(CvVoronoiDiagram2D* VoronoiDiagram,
|
||||
float maxWidth)
|
||||
{
|
||||
CvMemStorage* LCMstorage;
|
||||
CvSet* SiteSet;
|
||||
CvLCM LCM = {NULL, VoronoiDiagram,NULL,NULL,maxWidth};
|
||||
|
||||
CV_FUNCNAME( "cvLinearContorModelFromVoronoiDiagram" );
|
||||
__BEGIN__;
|
||||
|
||||
if( !VoronoiDiagram )
|
||||
CV_ERROR( CV_StsBadArg,"Voronoi Diagram is not defined" );
|
||||
if( maxWidth < 0 )
|
||||
CV_ERROR( CV_StsBadArg,"Treshold parameter must be non negative" );
|
||||
|
||||
for(SiteSet = VoronoiDiagram->sites;
|
||||
SiteSet != NULL;
|
||||
SiteSet = (CvSet*)SiteSet->h_next)
|
||||
{
|
||||
if(SiteSet->v_next)
|
||||
CV_ERROR( CV_StsBadArg,"Can't operate with multiconnected domains" );
|
||||
if(SiteSet->total > 70000)
|
||||
CV_ERROR( CV_StsBadArg,"Can't operate with large domains" );
|
||||
}
|
||||
|
||||
|
||||
LCMstorage = cvCreateMemStorage(0);
|
||||
LCM.EdgeStorage = cvCreateChildMemStorage(LCMstorage);
|
||||
LCM.ContourStorage = cvCreateChildMemStorage(LCMstorage);
|
||||
LCM.Graph = cvCreateGraph(CV_SEQ_KIND_GRAPH|CV_GRAPH_FLAG_ORIENTED,
|
||||
sizeof(CvGraph),
|
||||
sizeof(CvLCMNode),
|
||||
sizeof(CvLCMEdge),
|
||||
LCMstorage);
|
||||
if(!_cvConstructLCM(&LCM))
|
||||
cvReleaseLinearContorModelStorage(&LCM.Graph);
|
||||
|
||||
|
||||
__END__;
|
||||
return LCM.Graph;
|
||||
}//end of cvLinearContorModelFromVoronoiDiagram
|
||||
|
||||
CV_IMPL int cvReleaseLinearContorModelStorage(CvGraph** Graph)
|
||||
{
|
||||
CvSeq* LCMNodeSeq, *LCMEdgeSeq;
|
||||
CvLCMNode* pLCMNode;
|
||||
CvLCMEdge* pLCMEdge;
|
||||
|
||||
/*CV_FUNCNAME( "cvReleaseLinearContorModelStorage" );*/
|
||||
__BEGIN__;
|
||||
|
||||
if(!Graph || !(*Graph))
|
||||
return 0;
|
||||
|
||||
LCMNodeSeq = (CvSeq*)(*Graph);
|
||||
LCMEdgeSeq = (CvSeq*)(*Graph)->edges;
|
||||
if(LCMNodeSeq->total > 0)
|
||||
{
|
||||
pLCMNode = (CvLCMNode*)cvGetSeqElem(LCMNodeSeq,0);
|
||||
if(pLCMNode->contour->storage)
|
||||
cvReleaseMemStorage(&pLCMNode->contour->storage);
|
||||
}
|
||||
if(LCMEdgeSeq->total > 0)
|
||||
{
|
||||
pLCMEdge = (CvLCMEdge*)cvGetSeqElem(LCMEdgeSeq,0);
|
||||
if(pLCMEdge->chain->storage)
|
||||
cvReleaseMemStorage(&pLCMEdge->chain->storage);
|
||||
}
|
||||
if((*Graph)->storage)
|
||||
cvReleaseMemStorage(&(*Graph)->storage);
|
||||
*Graph = NULL;
|
||||
|
||||
|
||||
__END__;
|
||||
return 1;
|
||||
}//end of cvReleaseLinearContorModelStorage
|
||||
|
||||
int _cvConstructLCM(CvLCM* LCM)
|
||||
{
|
||||
CvVoronoiSite2D* pSite = 0;
|
||||
CvVoronoiEdge2D* pEdge = 0, *pEdge1;
|
||||
CvVoronoiNode2D* pNode, *pNode1;
|
||||
|
||||
CvVoronoiEdge2D* LinkedEdges[10];
|
||||
CvVoronoiSite2D* LinkedSites[10];
|
||||
|
||||
CvSeqReader reader;
|
||||
CvLCMData LCMdata;
|
||||
int i;
|
||||
|
||||
for(CvSet* SiteSet = LCM->VoronoiDiagram->sites;
|
||||
SiteSet != NULL;
|
||||
SiteSet = (CvSet*)SiteSet->h_next)
|
||||
{
|
||||
cvStartReadSeq((CvSeq*)SiteSet, &reader);
|
||||
for(i = 0; i < SiteSet->total; i++)
|
||||
{
|
||||
_CV_READ_SEQ_ELEM(pSite,reader,CvVoronoiSite2D*);
|
||||
if(pSite->node[0] == pSite->node[1])
|
||||
continue;
|
||||
pEdge = CV_LAST_VORONOIEDGE2D(pSite);
|
||||
pNode = CV_VORONOIEDGE2D_BEGINNODE(pEdge,pSite);
|
||||
if(pNode->radius > LCM->maxWidth)
|
||||
goto PREPARECOMPLEXNODE;
|
||||
|
||||
pEdge1 = CV_PREV_VORONOIEDGE2D(pEdge,pSite);
|
||||
pNode1 = CV_VORONOIEDGE2D_BEGINNODE(pEdge1,pSite);
|
||||
if(pNode1->radius > LCM->maxWidth)
|
||||
goto PREPARECOMPLEXNODE;
|
||||
if(pNode1->radius == 0)
|
||||
continue;
|
||||
if(_cvNodeMultyplicity(pSite, pEdge,pNode,LinkedEdges,LinkedSites) == 1)
|
||||
goto PREPARESIMPLENODE;
|
||||
}
|
||||
// treate triangle or regular polygon
|
||||
_CV_INITIALIZE_CVLCMDATA(&LCMdata,pSite,pEdge,CV_VORONOIEDGE2D_ENDNODE(pEdge,pSite));
|
||||
if(!_cvTreatExeptionalCase(LCM,&LCMdata))
|
||||
return 0;
|
||||
continue;
|
||||
|
||||
PREPARECOMPLEXNODE:
|
||||
_CV_INITIALIZE_CVLCMDATA(&LCMdata,pSite,pEdge,CV_VORONOIEDGE2D_ENDNODE(pEdge,pSite));
|
||||
if(!_cvConstructLCMComplexNode(LCM,NULL,&LCMdata))
|
||||
return 0;
|
||||
continue;
|
||||
|
||||
PREPARESIMPLENODE:
|
||||
_CV_INITIALIZE_CVLCMDATA(&LCMdata,pSite,pEdge,CV_VORONOIEDGE2D_ENDNODE(pEdge,pSite));
|
||||
if(!_cvConstructLCMSimpleNode(LCM,NULL,&LCMdata))
|
||||
return 0;
|
||||
continue;
|
||||
}
|
||||
return 1;
|
||||
}//end of _cvConstructLCM
|
||||
|
||||
CvLCMNode* _cvConstructLCMComplexNode(CvLCM* pLCM,
|
||||
CvLCMEdge* pLCMEdge,
|
||||
CvLCMData* pLCMInputData)
|
||||
{
|
||||
CvLCMNode* pLCMNode;
|
||||
CvLCMEdge* pLCMEdge_prev = NULL;
|
||||
CvSeqWriter writer;
|
||||
CvVoronoiSite2D* pSite, *pSite_first, *pSite_last;
|
||||
CvVoronoiEdge2D* pEdge, *pEdge_stop;
|
||||
CvVoronoiNode2D* pNode0, *pNode1;
|
||||
CvLCMData LCMOutputData;
|
||||
CvLCMComplexNodeData LCMCCNData;
|
||||
int index = 0;
|
||||
|
||||
_cvPrepareData(&LCMCCNData,pLCMInputData);
|
||||
|
||||
pLCMNode = _cvCreateLCMNode(pLCM);
|
||||
_cvAttachLCMEdgeToLCMNode(pLCMNode,pLCMEdge,pLCMEdge_prev,1,1);
|
||||
cvStartAppendToSeq((CvSeq*)pLCMNode->contour,&writer);
|
||||
CV_WRITE_SEQ_ELEM(LCMCCNData.site_last_pt, writer);
|
||||
index++;
|
||||
|
||||
if(pLCMEdge)
|
||||
{
|
||||
CV_WRITE_SEQ_ELEM(LCMCCNData.edge_node.pt, writer );
|
||||
CV_WRITE_SEQ_ELEM(LCMCCNData.site_first_pt, writer );
|
||||
index+=2;
|
||||
}
|
||||
|
||||
pSite_first = LCMCCNData.site_first;
|
||||
pSite_last = LCMCCNData.site_last;
|
||||
pEdge = LCMCCNData.edge;
|
||||
|
||||
for(pSite = pSite_first;
|
||||
pSite != pSite_last;
|
||||
pSite = CV_NEXT_VORONOISITE2D(pSite),
|
||||
pEdge = CV_PREV_VORONOIEDGE2D(CV_LAST_VORONOIEDGE2D(pSite),pSite))
|
||||
{
|
||||
pEdge_stop = CV_FIRST_VORONOIEDGE2D(pSite);
|
||||
for(;pEdge && pEdge != pEdge_stop;
|
||||
pEdge = CV_PREV_VORONOIEDGE2D(pEdge,pSite))
|
||||
{
|
||||
pNode0 = CV_VORONOIEDGE2D_BEGINNODE(pEdge,pSite);
|
||||
pNode1 = CV_VORONOIEDGE2D_ENDNODE(pEdge,pSite);
|
||||
if(pNode0->radius <= pLCM->maxWidth && pNode1->radius <= pLCM->maxWidth)
|
||||
{
|
||||
_CV_INITIALIZE_CVLCMDATA(&LCMOutputData,pSite,pEdge,pNode1);
|
||||
_cvPrepareData(&LCMCCNData,&LCMOutputData);
|
||||
CV_WRITE_SEQ_ELEM(LCMCCNData.site_first_pt, writer);
|
||||
CV_WRITE_SEQ_ELEM(LCMCCNData.edge_node.pt, writer );
|
||||
index+=2;
|
||||
pLCMEdge = _cvConstructLCMEdge(pLCM,&LCMOutputData);
|
||||
_cvAttachLCMEdgeToLCMNode(pLCMNode,pLCMEdge,pLCMEdge_prev,index - 1,0);
|
||||
CV_WRITE_SEQ_ELEM(LCMCCNData.site_last_pt, writer);
|
||||
index++;
|
||||
|
||||
pSite = CV_TWIN_VORONOISITE2D(pSite,pEdge);
|
||||
pEdge_stop = CV_FIRST_VORONOIEDGE2D(pSite);
|
||||
if(pSite == pSite_last)
|
||||
break;
|
||||
}
|
||||
}
|
||||
if(pSite == pSite_last)
|
||||
break;
|
||||
|
||||
CV_WRITE_SEQ_ELEM(pSite->node[1]->pt, writer);
|
||||
index++;
|
||||
}
|
||||
|
||||
if(pLCMEdge_prev)
|
||||
pLCMEdge_prev->next[(pLCMEdge_prev == (CvLCMEdge*)pLCMNode->first)] = pLCMNode->first;
|
||||
cvEndWriteSeq(&writer);
|
||||
return pLCMNode;
|
||||
}//end of _cvConstructLCMComplexNode
|
||||
|
||||
CvLCMNode* _cvConstructLCMSimpleNode(CvLCM* pLCM,
|
||||
CvLCMEdge* pLCMEdge,
|
||||
CvLCMData* pLCMInputData)
|
||||
{
|
||||
CvVoronoiEdge2D* pEdge = pLCMInputData->pedge;
|
||||
CvVoronoiSite2D* pSite = pLCMInputData->psite;
|
||||
CvVoronoiNode2D* pNode = CV_VORONOIEDGE2D_BEGINNODE(pEdge,pSite);
|
||||
|
||||
CvVoronoiEdge2D* LinkedEdges[10];
|
||||
CvVoronoiSite2D* LinkedSites[10];
|
||||
int multyplicity = _cvNodeMultyplicity(pSite,pEdge,pNode,LinkedEdges,LinkedSites);
|
||||
if(multyplicity == 2)
|
||||
{
|
||||
pLCMInputData->pedge = LinkedEdges[1];
|
||||
pLCMInputData->psite = CV_TWIN_VORONOISITE2D(LinkedSites[1],LinkedEdges[1]);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
CvLCMEdge* pLCMEdge_prev = NULL;
|
||||
CvLCMNode* pLCMNode;
|
||||
CvLCMData LCMOutputData;
|
||||
|
||||
pLCMNode = _cvCreateLCMNode(pLCM);
|
||||
cvSeqPush((CvSeq*)pLCMNode->contour,&pNode->pt);
|
||||
_cvAttachLCMEdgeToLCMNode(pLCMNode,pLCMEdge,pLCMEdge_prev,0,1);
|
||||
|
||||
for(int i = (int)(pLCMEdge != NULL);i < multyplicity; i++)
|
||||
{
|
||||
pEdge = LinkedEdges[i];
|
||||
pSite = LinkedSites[i];
|
||||
_CV_INITIALIZE_CVLCMDATA(&LCMOutputData,CV_TWIN_VORONOISITE2D(pSite,pEdge),pEdge,pNode);
|
||||
pLCMEdge = _cvConstructLCMEdge(pLCM,&LCMOutputData);
|
||||
_cvAttachLCMEdgeToLCMNode(pLCMNode,pLCMEdge,pLCMEdge_prev,0,0);
|
||||
}
|
||||
pLCMEdge_prev->next[(pLCMEdge_prev == (CvLCMEdge*)pLCMNode->first)] = pLCMNode->first;
|
||||
return pLCMNode;
|
||||
}//end of _cvConstructLCMSimpleNode
|
||||
|
||||
CvLCMEdge* _cvConstructLCMEdge(CvLCM* pLCM,
|
||||
CvLCMData* pLCMInputData)
|
||||
{
|
||||
CvVoronoiEdge2D* pEdge = pLCMInputData->pedge;
|
||||
CvVoronoiSite2D* pSite = pLCMInputData->psite;
|
||||
float width = 0;
|
||||
|
||||
CvLCMData LCMData;
|
||||
CvVoronoiNode2D* pNode0,*pNode1;
|
||||
|
||||
CvLCMEdge* pLCMEdge = _cvCreateLCMEdge(pLCM);
|
||||
|
||||
CvSeqWriter writer;
|
||||
cvStartAppendToSeq(pLCMEdge->chain,&writer );
|
||||
|
||||
pNode0 = pNode1 = pLCMInputData->pnode;
|
||||
CV_WRITE_SEQ_ELEM(pNode0->pt, writer);
|
||||
width += pNode0->radius;
|
||||
|
||||
for(int counter = 0;
|
||||
counter < pLCM->VoronoiDiagram->edges->total;
|
||||
counter++)
|
||||
{
|
||||
pNode1 = CV_VORONOIEDGE2D_BEGINNODE(pEdge,pSite);
|
||||
if(pNode1->radius >= pLCM->maxWidth)
|
||||
goto CREATECOMPLEXNODE;
|
||||
|
||||
CV_WRITE_SEQ_ELEM(pNode1->pt,writer);
|
||||
width += pNode1->radius;
|
||||
_CV_INITIALIZE_CVLCMDATA(&LCMData,pSite,pEdge,pNode1);
|
||||
if(_cvConstructLCMSimpleNode(pLCM,pLCMEdge,&LCMData))
|
||||
goto LCMEDGEEXIT;
|
||||
|
||||
pEdge = LCMData.pedge; pSite = LCMData.psite;
|
||||
pNode0 = pNode1;
|
||||
}
|
||||
return NULL;
|
||||
|
||||
CREATECOMPLEXNODE:
|
||||
_CV_INITIALIZE_CVLCMDATA(&LCMData,pSite,pEdge,pNode0);
|
||||
CV_WRITE_SEQ_ELEM(LCMData.pnode->pt,writer);
|
||||
width += LCMData.pnode->radius;
|
||||
_cvConstructLCMComplexNode(pLCM,pLCMEdge,&LCMData);
|
||||
|
||||
LCMEDGEEXIT:
|
||||
cvEndWriteSeq(&writer);
|
||||
pLCMEdge->width = width/pLCMEdge->chain->total;
|
||||
return pLCMEdge;
|
||||
}//end of _cvConstructLCMEdge
|
||||
|
||||
CvLCMNode* _cvTreatExeptionalCase(CvLCM* pLCM,
|
||||
CvLCMData* pLCMInputData)
|
||||
{
|
||||
CvVoronoiEdge2D* pEdge = pLCMInputData->pedge;
|
||||
CvVoronoiSite2D* pSite = pLCMInputData->psite;
|
||||
CvVoronoiNode2D* pNode = CV_VORONOIEDGE2D_BEGINNODE(pEdge,pSite);
|
||||
CvLCMNode* pLCMNode = _cvCreateLCMNode(pLCM);
|
||||
cvSeqPush((CvSeq*)pLCMNode->contour,&pNode->pt);
|
||||
return pLCMNode;
|
||||
}//end of _cvConstructLCMEdge
|
||||
|
||||
CV_INLINE
|
||||
CvLCMNode* _cvCreateLCMNode(CvLCM* pLCM)
|
||||
{
|
||||
CvLCMNode* pLCMNode;
|
||||
cvSetAdd((CvSet*)pLCM->Graph, NULL, (CvSetElem**)&pLCMNode );
|
||||
pLCMNode->contour = (CvContour*)cvCreateSeq(0, sizeof(CvContour),
|
||||
sizeof(CvPoint2D32f),pLCM->ContourStorage);
|
||||
pLCMNode->first = NULL;
|
||||
return pLCMNode;
|
||||
}//end of _cvCreateLCMNode
|
||||
|
||||
CV_INLINE
|
||||
CvLCMEdge* _cvCreateLCMEdge(CvLCM* pLCM)
|
||||
{
|
||||
CvLCMEdge* pLCMEdge;
|
||||
cvSetAdd( (CvSet*)(pLCM->Graph->edges), 0, (CvSetElem**)&pLCMEdge );
|
||||
pLCMEdge->chain = cvCreateSeq(0, sizeof(CvSeq),sizeof(CvPoint2D32f),pLCM->EdgeStorage);
|
||||
pLCMEdge->next[0] = pLCMEdge->next[1] = NULL;
|
||||
pLCMEdge->vtx[0] = pLCMEdge->vtx[1] = NULL;
|
||||
pLCMEdge->index1 = pLCMEdge->index2 = -1;
|
||||
return pLCMEdge;
|
||||
}//end of _cvCreateLCMEdge
|
||||
|
||||
CV_INLINE
|
||||
void _cvAttachLCMEdgeToLCMNode(CvLCMNode* LCMNode,
|
||||
CvLCMEdge* LCMEdge,
|
||||
CvLCMEdge* &LCMEdge_prev,
|
||||
int index,
|
||||
int i)
|
||||
{
|
||||
if(!LCMEdge)
|
||||
return;
|
||||
if(i==0)
|
||||
LCMEdge->index1 = index;
|
||||
else
|
||||
LCMEdge->index2 = index;
|
||||
|
||||
LCMEdge->vtx[i] = (CvGraphVtx*)LCMNode;
|
||||
if(!LCMEdge_prev)
|
||||
LCMNode->first = (CvGraphEdge*)LCMEdge;
|
||||
else
|
||||
// LCMEdge_prev->next[(LCMEdge_prev == (CvLCMEdge*)LCMNode->first)] = (CvGraphEdge*)LCMEdge;
|
||||
LCMEdge_prev->next[(LCMEdge_prev->vtx[0] != (CvGraphVtx*)LCMNode)] = (CvGraphEdge*)LCMEdge;
|
||||
|
||||
LCMEdge->next[i] = LCMNode->first;
|
||||
LCMEdge_prev = LCMEdge;
|
||||
}//end of _cvAttachLCMEdgeToLCMNode
|
||||
|
||||
|
||||
int _cvNodeMultyplicity(CvVoronoiSite2D* pSite,
|
||||
CvVoronoiEdge2D* pEdge,
|
||||
CvVoronoiNode2D* pNode,
|
||||
CvVoronoiEdge2D** LinkedEdges,
|
||||
CvVoronoiSite2D** LinkedSites)
|
||||
{
|
||||
if(!pNode->radius)
|
||||
return -1;
|
||||
assert(pNode == CV_VORONOIEDGE2D_BEGINNODE(pEdge,pSite));
|
||||
|
||||
int multyplicity = 0;
|
||||
CvVoronoiEdge2D* pEdge_cur = pEdge;
|
||||
do
|
||||
{
|
||||
if(pEdge_cur->node[0]->radius && pEdge_cur->node[1]->radius)
|
||||
{
|
||||
LinkedEdges[multyplicity] = pEdge_cur;
|
||||
LinkedSites[multyplicity] = pSite;
|
||||
multyplicity++;
|
||||
}
|
||||
pEdge_cur = CV_PREV_VORONOIEDGE2D(pEdge_cur,pSite);
|
||||
pSite = CV_TWIN_VORONOISITE2D(pSite,pEdge_cur);
|
||||
}while(pEdge_cur != pEdge);
|
||||
return multyplicity;
|
||||
}//end of _cvNodeMultyplicity
|
||||
|
||||
|
||||
CV_INLINE
|
||||
void _cvPrepareData(CvLCMComplexNodeData* pLCMCCNData,
|
||||
CvLCMData* pLCMData)
|
||||
{
|
||||
pLCMCCNData->site_first = pLCMData->psite;
|
||||
pLCMCCNData->site_last = CV_TWIN_VORONOISITE2D(pLCMData->psite,pLCMData->pedge);
|
||||
if(pLCMData->pedge == CV_LAST_VORONOIEDGE2D(pLCMData->psite))
|
||||
{
|
||||
pLCMCCNData->edge = CV_PREV_VORONOIEDGE2D(pLCMData->pedge,pLCMData->psite);
|
||||
pLCMCCNData->edge_node = *pLCMData->pnode;
|
||||
pLCMCCNData->site_first_pt = pLCMData->psite->node[0]->pt;
|
||||
pLCMCCNData->site_last_pt = pLCMData->psite->node[0]->pt;
|
||||
}
|
||||
else
|
||||
{
|
||||
pLCMCCNData->edge = pLCMData->pedge;
|
||||
pLCMCCNData->edge_node = *pLCMData->pnode;
|
||||
_cvProjectionPointToSegment(&pLCMCCNData->edge_node.pt,
|
||||
&pLCMCCNData->site_first->node[0]->pt,
|
||||
&pLCMCCNData->site_first->node[1]->pt,
|
||||
&pLCMCCNData->site_first_pt,
|
||||
NULL);
|
||||
_cvProjectionPointToSegment(&pLCMCCNData->edge_node.pt,
|
||||
&pLCMCCNData->site_last->node[0]->pt,
|
||||
&pLCMCCNData->site_last->node[1]->pt,
|
||||
&pLCMCCNData->site_last_pt,
|
||||
NULL);
|
||||
}
|
||||
}//end of _cvPrepareData
|
||||
|
||||
|
||||
void _cvProjectionPointToSegment(CvPoint2D32f* PointO,
|
||||
CvPoint2D32f* PointA,
|
||||
CvPoint2D32f* PointB,
|
||||
CvPoint2D32f* PrPoint,
|
||||
float* dist)
|
||||
{
|
||||
float scal_AO_AB, scal_AB_AB;
|
||||
CvPoint2D32f VectorAB = {PointB->x - PointA->x, PointB->y - PointA->y};
|
||||
scal_AB_AB = VectorAB.x*VectorAB.x + VectorAB.y*VectorAB.y;
|
||||
if(scal_AB_AB < LCM_CONST_ZERO)
|
||||
{
|
||||
*PrPoint = *PointA;
|
||||
if(dist)
|
||||
*dist = (float)sqrt( (double)(PointO->x -PointA->x)*(PointO->x -PointA->x) + (PointO->y - PointA->y)*(PointO->y - PointA->y));
|
||||
return;
|
||||
}
|
||||
|
||||
CvPoint2D32f VectorAO = {PointO->x - PointA->x, PointO->y - PointA->y};
|
||||
scal_AO_AB = VectorAO.x*VectorAB.x + VectorAO.y*VectorAB.y;
|
||||
|
||||
if(dist)
|
||||
{
|
||||
float vector_AO_AB = (float)fabs(VectorAO.x*VectorAB.y - VectorAO.y*VectorAB.x);
|
||||
*dist = (float)(vector_AO_AB/sqrt((double)scal_AB_AB));
|
||||
}
|
||||
|
||||
float alfa = scal_AO_AB/scal_AB_AB;
|
||||
PrPoint->x = PointO->x - VectorAO.x + alfa*VectorAB.x;
|
||||
PrPoint->y = PointO->y - VectorAO.y + alfa*VectorAB.y;
|
||||
return;
|
||||
}//end of _cvProjectionPointToSegment
|
||||
|
||||
|
||||
|
||||
|
||||
4718
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/src/cvlee.cpp
Normal file
4718
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/src/cvlee.cpp
Normal file
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,320 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
#include "cvtypes.h"
|
||||
#include <float.h>
|
||||
#include <limits.h>
|
||||
#include "cv.h"
|
||||
|
||||
/* Valery Mosyagin */
|
||||
|
||||
//#define TRACKLEVMAR
|
||||
|
||||
typedef void (*pointer_LMJac)( const CvMat* src, CvMat* dst );
|
||||
typedef void (*pointer_LMFunc)( const CvMat* src, CvMat* dst );
|
||||
|
||||
/* Optimization using Levenberg-Marquardt */
|
||||
void cvLevenbergMarquardtOptimization(pointer_LMJac JacobianFunction,
|
||||
pointer_LMFunc function,
|
||||
/*pointer_Err error_function,*/
|
||||
CvMat *X0,CvMat *observRes,CvMat *resultX,
|
||||
int maxIter,double epsilon)
|
||||
{
|
||||
/* This is not sparce method */
|
||||
/* Make optimization using */
|
||||
/* func - function to compute */
|
||||
/* uses function to compute jacobian */
|
||||
|
||||
/* Allocate memory */
|
||||
CvMat *vectX = 0;
|
||||
CvMat *vectNewX = 0;
|
||||
CvMat *resFunc = 0;
|
||||
CvMat *resNewFunc = 0;
|
||||
CvMat *error = 0;
|
||||
CvMat *errorNew = 0;
|
||||
CvMat *Jac = 0;
|
||||
CvMat *delta = 0;
|
||||
CvMat *matrJtJ = 0;
|
||||
CvMat *matrJtJN = 0;
|
||||
CvMat *matrJt = 0;
|
||||
CvMat *vectB = 0;
|
||||
|
||||
CV_FUNCNAME( "cvLevenbegrMarquardtOptimization" );
|
||||
__BEGIN__;
|
||||
|
||||
|
||||
if( JacobianFunction == 0 || function == 0 || X0 == 0 || observRes == 0 || resultX == 0 )
|
||||
{
|
||||
CV_ERROR( CV_StsNullPtr, "Some of parameters is a NULL pointer" );
|
||||
}
|
||||
|
||||
if( !CV_IS_MAT(X0) || !CV_IS_MAT(observRes) || !CV_IS_MAT(resultX) )
|
||||
{
|
||||
CV_ERROR( CV_StsUnsupportedFormat, "Some of input parameters must be a matrices" );
|
||||
}
|
||||
|
||||
|
||||
int numVal;
|
||||
int numFunc;
|
||||
double valError;
|
||||
double valNewError;
|
||||
|
||||
numVal = X0->rows;
|
||||
numFunc = observRes->rows;
|
||||
|
||||
/* test input data */
|
||||
if( X0->cols != 1 )
|
||||
{
|
||||
CV_ERROR( CV_StsUnmatchedSizes, "Number of colomn of vector X0 must be 1" );
|
||||
}
|
||||
|
||||
if( observRes->cols != 1 )
|
||||
{
|
||||
CV_ERROR( CV_StsUnmatchedSizes, "Number of colomn of vector observed rusult must be 1" );
|
||||
}
|
||||
|
||||
if( resultX->cols != 1 || resultX->rows != numVal )
|
||||
{
|
||||
CV_ERROR( CV_StsUnmatchedSizes, "Size of result vector X must be equals to X0" );
|
||||
}
|
||||
|
||||
if( maxIter <= 0 )
|
||||
{
|
||||
CV_ERROR( CV_StsUnmatchedSizes, "Number of maximum iteration must be > 0" );
|
||||
}
|
||||
|
||||
if( epsilon < 0 )
|
||||
{
|
||||
CV_ERROR( CV_StsUnmatchedSizes, "Epsilon must be >= 0" );
|
||||
}
|
||||
|
||||
/* copy x0 to current value of x */
|
||||
CV_CALL( vectX = cvCreateMat(numVal, 1, CV_64F) );
|
||||
CV_CALL( vectNewX = cvCreateMat(numVal, 1, CV_64F) );
|
||||
CV_CALL( resFunc = cvCreateMat(numFunc,1, CV_64F) );
|
||||
CV_CALL( resNewFunc = cvCreateMat(numFunc,1, CV_64F) );
|
||||
CV_CALL( error = cvCreateMat(numFunc,1, CV_64F) );
|
||||
CV_CALL( errorNew = cvCreateMat(numFunc,1, CV_64F) );
|
||||
CV_CALL( Jac = cvCreateMat(numFunc,numVal, CV_64F) );
|
||||
CV_CALL( delta = cvCreateMat(numVal, 1, CV_64F) );
|
||||
CV_CALL( matrJtJ = cvCreateMat(numVal, numVal, CV_64F) );
|
||||
CV_CALL( matrJtJN = cvCreateMat(numVal, numVal, CV_64F) );
|
||||
CV_CALL( matrJt = cvCreateMat(numVal, numFunc,CV_64F) );
|
||||
CV_CALL( vectB = cvCreateMat(numVal, 1, CV_64F) );
|
||||
|
||||
cvCopy(X0,vectX);
|
||||
|
||||
/* ========== Main optimization loop ============ */
|
||||
double change;
|
||||
int currIter;
|
||||
double alpha;
|
||||
|
||||
change = 1;
|
||||
currIter = 0;
|
||||
alpha = 0.001;
|
||||
|
||||
do {
|
||||
|
||||
/* Compute value of function */
|
||||
function(vectX,resFunc);
|
||||
/* Print result of function to file */
|
||||
|
||||
/* Compute error */
|
||||
cvSub(observRes,resFunc,error);
|
||||
|
||||
//valError = error_function(observRes,resFunc);
|
||||
/* Need to use new version of computing error (norm) */
|
||||
valError = cvNorm(observRes,resFunc);
|
||||
|
||||
/* Compute Jacobian for given point vectX */
|
||||
JacobianFunction(vectX,Jac);
|
||||
|
||||
/* Define optimal delta for J'*J*delta=J'*error */
|
||||
/* compute J'J */
|
||||
cvMulTransposed(Jac,matrJtJ,1);
|
||||
|
||||
cvCopy(matrJtJ,matrJtJN);
|
||||
|
||||
/* compute J'*error */
|
||||
cvTranspose(Jac,matrJt);
|
||||
cvmMul(matrJt,error,vectB);
|
||||
|
||||
|
||||
/* Solve normal equation for given alpha and Jacobian */
|
||||
do
|
||||
{
|
||||
/* Increase diagonal elements by alpha */
|
||||
for( int i = 0; i < numVal; i++ )
|
||||
{
|
||||
double val;
|
||||
val = cvmGet(matrJtJ,i,i);
|
||||
cvmSet(matrJtJN,i,i,(1+alpha)*val);
|
||||
}
|
||||
|
||||
/* Solve system to define delta */
|
||||
cvSolve(matrJtJN,vectB,delta,CV_SVD);
|
||||
|
||||
/* We know delta and we can define new value of vector X */
|
||||
cvAdd(vectX,delta,vectNewX);
|
||||
|
||||
/* Compute result of function for new vector X */
|
||||
function(vectNewX,resNewFunc);
|
||||
cvSub(observRes,resNewFunc,errorNew);
|
||||
|
||||
valNewError = cvNorm(observRes,resNewFunc);
|
||||
|
||||
currIter++;
|
||||
|
||||
if( valNewError < valError )
|
||||
{/* accept new value */
|
||||
valError = valNewError;
|
||||
|
||||
/* Compute relative change of required parameter vectorX. change = norm(curr-prev) / norm(curr) ) */
|
||||
change = cvNorm(vectX, vectNewX, CV_RELATIVE_L2);
|
||||
|
||||
alpha /= 10;
|
||||
cvCopy(vectNewX,vectX);
|
||||
break;
|
||||
}
|
||||
else
|
||||
{
|
||||
alpha *= 10;
|
||||
}
|
||||
|
||||
} while ( currIter < maxIter );
|
||||
/* new value of X and alpha were accepted */
|
||||
|
||||
} while ( change > epsilon && currIter < maxIter );
|
||||
|
||||
|
||||
/* result was computed */
|
||||
cvCopy(vectX,resultX);
|
||||
|
||||
__END__;
|
||||
|
||||
cvReleaseMat(&vectX);
|
||||
cvReleaseMat(&vectNewX);
|
||||
cvReleaseMat(&resFunc);
|
||||
cvReleaseMat(&resNewFunc);
|
||||
cvReleaseMat(&error);
|
||||
cvReleaseMat(&errorNew);
|
||||
cvReleaseMat(&Jac);
|
||||
cvReleaseMat(&delta);
|
||||
cvReleaseMat(&matrJtJ);
|
||||
cvReleaseMat(&matrJtJN);
|
||||
cvReleaseMat(&matrJt);
|
||||
cvReleaseMat(&vectB);
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
/*------------------------------------------------------------------------------*/
|
||||
#if 0
|
||||
//tests
|
||||
void Jac_Func2(CvMat *vectX,CvMat *Jac)
|
||||
{
|
||||
double x = cvmGet(vectX,0,0);
|
||||
double y = cvmGet(vectX,1,0);
|
||||
cvmSet(Jac,0,0,2*(x-2));
|
||||
cvmSet(Jac,0,1,2*(y+3));
|
||||
|
||||
cvmSet(Jac,1,0,1);
|
||||
cvmSet(Jac,1,1,1);
|
||||
return;
|
||||
}
|
||||
|
||||
void Res_Func2(CvMat *vectX,CvMat *res)
|
||||
{
|
||||
double x = cvmGet(vectX,0,0);
|
||||
double y = cvmGet(vectX,1,0);
|
||||
cvmSet(res,0,0,(x-2)*(x-2)+(y+3)*(y+3));
|
||||
cvmSet(res,1,0,x+y);
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
double Err_Func2(CvMat *obs,CvMat *res)
|
||||
{
|
||||
CvMat *tmp;
|
||||
tmp = cvCreateMat(obs->rows,1,CV_64F);
|
||||
cvSub(obs,res,tmp);
|
||||
|
||||
double e;
|
||||
e = cvNorm(tmp);
|
||||
|
||||
return e;
|
||||
}
|
||||
|
||||
|
||||
void TestOptimX2Y2()
|
||||
{
|
||||
CvMat vectX0;
|
||||
double vectX0_dat[2];
|
||||
vectX0 = cvMat(2,1,CV_64F,vectX0_dat);
|
||||
vectX0_dat[0] = 5;
|
||||
vectX0_dat[1] = -7;
|
||||
|
||||
CvMat observRes;
|
||||
double observRes_dat[2];
|
||||
observRes = cvMat(2,1,CV_64F,observRes_dat);
|
||||
observRes_dat[0] = 0;
|
||||
observRes_dat[1] = -1;
|
||||
observRes_dat[0] = 0;
|
||||
observRes_dat[1] = -1.2;
|
||||
|
||||
CvMat optimX;
|
||||
double optimX_dat[2];
|
||||
optimX = cvMat(2,1,CV_64F,optimX_dat);
|
||||
|
||||
|
||||
LevenbegrMarquardtOptimization( Jac_Func2, Res_Func2, Err_Func2,
|
||||
&vectX0,&observRes,&optimX,100,0.000001);
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,497 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
#include "cvtypes.h"
|
||||
#include <float.h>
|
||||
#include <limits.h>
|
||||
#include "cv.h"
|
||||
|
||||
/* Valery Mosyagin */
|
||||
|
||||
typedef void (*pointer_LMJac)( const CvMat* src, CvMat* dst );
|
||||
typedef void (*pointer_LMFunc)( const CvMat* src, CvMat* dst );
|
||||
|
||||
void cvLevenbergMarquardtOptimization(pointer_LMJac JacobianFunction,
|
||||
pointer_LMFunc function,
|
||||
/*pointer_Err error_function,*/
|
||||
CvMat *X0,CvMat *observRes,CvMat *resultX,
|
||||
int maxIter,double epsilon);
|
||||
|
||||
void icvReconstructPointsFor3View( CvMat* projMatr1,CvMat* projMatr2,CvMat* projMatr3,
|
||||
CvMat* projPoints1,CvMat* projPoints2,CvMat* projPoints3,
|
||||
CvMat* points4D);
|
||||
|
||||
|
||||
/* Jacobian computation for trifocal case */
|
||||
void icvJacobianFunction_ProjTrifocal(const CvMat *vectX,CvMat *Jacobian)
|
||||
{
|
||||
CV_FUNCNAME( "icvJacobianFunction_ProjTrifocal" );
|
||||
__BEGIN__;
|
||||
|
||||
/* Test data for errors */
|
||||
if( vectX == 0 || Jacobian == 0 )
|
||||
{
|
||||
CV_ERROR( CV_StsNullPtr, "Some of parameters is a NULL pointer" );
|
||||
}
|
||||
|
||||
if( !CV_IS_MAT(vectX) || !CV_IS_MAT(Jacobian) )
|
||||
{
|
||||
CV_ERROR( CV_StsUnsupportedFormat, "Input parameters must be a matrices" );
|
||||
}
|
||||
|
||||
int numPoints;
|
||||
numPoints = (vectX->rows - 36)/4;
|
||||
|
||||
if( numPoints < 1 )//!!! Need to correct this minimal number of points
|
||||
{
|
||||
CV_ERROR( CV_StsUnmatchedSizes, "number of points must be more than 0" );
|
||||
}
|
||||
|
||||
if( Jacobian->rows == numPoints*6 || Jacobian->cols != 36+numPoints*4 )
|
||||
{
|
||||
CV_ERROR( CV_StsUnmatchedSizes, "Size of Jacobian is not correct it must be 6*numPoints x (36+numPoints*4)" );
|
||||
}
|
||||
|
||||
/* Computed Jacobian in a given point */
|
||||
/* This is for function with 3 projection matrices */
|
||||
/* vector X consists of projection matrices and points3D */
|
||||
/* each 3D points has X,Y,Z,W */
|
||||
/* each projection matrices has 3x4 coeffs */
|
||||
/* For N points 4D we have Jacobian 2N x (12*3+4N) */
|
||||
|
||||
/* Will store derivates as */
|
||||
/* Fill Jacobian matrix */
|
||||
int currProjPoint;
|
||||
int currMatr;
|
||||
|
||||
cvZero(Jacobian);
|
||||
for( currMatr = 0; currMatr < 3; currMatr++ )
|
||||
{
|
||||
double p[12];
|
||||
for( int i=0;i<12;i++ )
|
||||
{
|
||||
p[i] = cvmGet(vectX,currMatr*12+i,0);
|
||||
}
|
||||
|
||||
int currVal = 36;
|
||||
for( currProjPoint = 0; currProjPoint < numPoints; currProjPoint++ )
|
||||
{
|
||||
/* Compute */
|
||||
double X[4];
|
||||
X[0] = cvmGet(vectX,currVal++,0);
|
||||
X[1] = cvmGet(vectX,currVal++,0);
|
||||
X[2] = cvmGet(vectX,currVal++,0);
|
||||
X[3] = cvmGet(vectX,currVal++,0);
|
||||
|
||||
double piX[3];
|
||||
piX[0] = X[0]*p[0] + X[1]*p[1] + X[2]*p[2] + X[3]*p[3];
|
||||
piX[1] = X[0]*p[4] + X[1]*p[5] + X[2]*p[6] + X[3]*p[7];
|
||||
piX[2] = X[0]*p[8] + X[1]*p[9] + X[2]*p[10] + X[3]*p[11];
|
||||
|
||||
int i,j;
|
||||
/* fill derivate by point */
|
||||
|
||||
double tmp3 = 1/(piX[2]*piX[2]);
|
||||
|
||||
double tmp1 = -piX[0]*tmp3;
|
||||
double tmp2 = -piX[1]*tmp3;
|
||||
for( j = 0; j < 2; j++ )//for x and y
|
||||
{
|
||||
for( i = 0; i < 4; i++ )// for X,Y,Z,W
|
||||
{
|
||||
cvmSet( Jacobian,
|
||||
currMatr*numPoints*2+currProjPoint*2+j, 36+currProjPoint*4+i,
|
||||
(p[j*4+i]*piX[2]-p[8+i]*piX[j]) * tmp3 );
|
||||
}
|
||||
}
|
||||
/* fill derivate by projection matrix */
|
||||
for( i = 0; i < 4; i++ )
|
||||
{
|
||||
/* derivate for x */
|
||||
cvmSet(Jacobian,currMatr*numPoints*2+currProjPoint*2,currMatr*12+i,X[i]/piX[2]);//x' p1i
|
||||
cvmSet(Jacobian,currMatr*numPoints*2+currProjPoint*2,currMatr*12+8+i,X[i]*tmp1);//x' p3i
|
||||
|
||||
/* derivate for y */
|
||||
cvmSet(Jacobian,currMatr*numPoints*2+currProjPoint*2+1,currMatr*12+4+i,X[i]/piX[2]);//y' p2i
|
||||
cvmSet(Jacobian,currMatr*numPoints*2+currProjPoint*2+1,currMatr*12+8+i,X[i]*tmp2);//y' p3i
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
__END__;
|
||||
return;
|
||||
}
|
||||
|
||||
void icvFunc_ProjTrifocal(const CvMat *vectX, CvMat *resFunc)
|
||||
{
|
||||
/* Computes function in a given point */
|
||||
/* Computers project points using 3 projection matrices and points 3D */
|
||||
|
||||
/* vector X consists of projection matrices and points3D */
|
||||
/* each projection matrices has 3x4 coeffs */
|
||||
/* each 3D points has X,Y,Z,W(?) */
|
||||
|
||||
/* result of function is projection of N 3D points using 3 projection matrices */
|
||||
/* projected points store as (projection by matrix P1),(projection by matrix P2),(projection by matrix P3) */
|
||||
/* each projection is x1,y1,x2,y2,x3,y3,x4,y4 */
|
||||
|
||||
/* Compute projection of points */
|
||||
|
||||
/* Fill projection matrices */
|
||||
|
||||
CV_FUNCNAME( "icvFunc_ProjTrifocal" );
|
||||
__BEGIN__;
|
||||
|
||||
/* Test data for errors */
|
||||
if( vectX == 0 || resFunc == 0 )
|
||||
{
|
||||
CV_ERROR( CV_StsNullPtr, "Some of parameters is a NULL pointer" );
|
||||
}
|
||||
|
||||
if( !CV_IS_MAT(vectX) || !CV_IS_MAT(resFunc) )
|
||||
{
|
||||
CV_ERROR( CV_StsUnsupportedFormat, "Input parameters must be a matrices" );
|
||||
}
|
||||
|
||||
int numPoints;
|
||||
numPoints = (vectX->rows - 36)/4;
|
||||
|
||||
if( numPoints < 1 )//!!! Need to correct this minimal number of points
|
||||
{
|
||||
CV_ERROR( CV_StsUnmatchedSizes, "number of points must be more than 0" );
|
||||
}
|
||||
|
||||
if( resFunc->rows == 2*numPoints*3 || resFunc->cols != 1 )
|
||||
{
|
||||
CV_ERROR( CV_StsUnmatchedSizes, "Size of resFunc is not correct it must be 2*numPoints*3 x 1");
|
||||
}
|
||||
|
||||
|
||||
CvMat projMatrs[3];
|
||||
double projMatrs_dat[36];
|
||||
projMatrs[0] = cvMat(3,4,CV_64F,projMatrs_dat);
|
||||
projMatrs[1] = cvMat(3,4,CV_64F,projMatrs_dat+12);
|
||||
projMatrs[2] = cvMat(3,4,CV_64F,projMatrs_dat+24);
|
||||
|
||||
CvMat point3D;
|
||||
double point3D_dat[3];
|
||||
point3D = cvMat(3,1,CV_64F,point3D_dat);
|
||||
|
||||
int currMatr;
|
||||
int currV;
|
||||
int i,j;
|
||||
|
||||
currV=0;
|
||||
for( currMatr = 0; currMatr < 3; currMatr++ )
|
||||
{
|
||||
for( i = 0; i < 3; i++ )
|
||||
{
|
||||
for( j = 0;j < 4; j++ )
|
||||
{
|
||||
double val = cvmGet(vectX,currV,0);
|
||||
cvmSet(&projMatrs[currMatr],i,j,val);
|
||||
currV++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* Project points */
|
||||
int currPoint;
|
||||
CvMat point4D;
|
||||
double point4D_dat[4];
|
||||
point4D = cvMat(4,1,CV_64F,point4D_dat);
|
||||
for( currPoint = 0; currPoint < numPoints; currPoint++ )
|
||||
{
|
||||
/* get curr point */
|
||||
point4D_dat[0] = cvmGet(vectX,currV++,0);
|
||||
point4D_dat[1] = cvmGet(vectX,currV++,0);
|
||||
point4D_dat[2] = cvmGet(vectX,currV++,0);
|
||||
point4D_dat[3] = cvmGet(vectX,currV++,0);
|
||||
|
||||
for( currMatr = 0; currMatr < 3; currMatr++ )
|
||||
{
|
||||
/* Compute projection for current point */
|
||||
cvmMul(&projMatrs[currMatr],&point4D,&point3D);
|
||||
double z = point3D_dat[2];
|
||||
cvmSet(resFunc,currMatr*numPoints*2 + currPoint*2, 0,point3D_dat[0]/z);
|
||||
cvmSet(resFunc,currMatr*numPoints*2 + currPoint*2+1,0,point3D_dat[1]/z);
|
||||
}
|
||||
}
|
||||
|
||||
__END__;
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
/*----------------------------------------------------------------------------------------*/
|
||||
|
||||
void icvOptimizeProjectionTrifocal(CvMat **projMatrs,CvMat **projPoints,
|
||||
CvMat **resultProjMatrs, CvMat *resultPoints4D)
|
||||
{
|
||||
|
||||
CvMat *optimX = 0;
|
||||
CvMat *points4D = 0;
|
||||
CvMat *vectorX0 = 0;
|
||||
CvMat *observRes = 0;
|
||||
//CvMat *error = 0;
|
||||
|
||||
CV_FUNCNAME( "icvOptimizeProjectionTrifocal" );
|
||||
__BEGIN__;
|
||||
|
||||
/* Test data for errors */
|
||||
if( projMatrs == 0 || projPoints == 0 || resultProjMatrs == 0 || resultPoints4D == 0)
|
||||
{
|
||||
CV_ERROR( CV_StsNullPtr, "Some of parameters is a NULL pointer" );
|
||||
}
|
||||
|
||||
if( !CV_IS_MAT(resultPoints4D) )
|
||||
{
|
||||
CV_ERROR( CV_StsUnsupportedFormat, "resultPoints4D must be a matrix" );
|
||||
}
|
||||
|
||||
int numPoints;
|
||||
numPoints = resultPoints4D->cols;
|
||||
if( numPoints < 1 )
|
||||
{
|
||||
CV_ERROR( CV_StsOutOfRange, "Number points of resultPoints4D must be more than 0" );
|
||||
}
|
||||
|
||||
if( resultPoints4D->rows != 4 )
|
||||
{
|
||||
CV_ERROR( CV_StsUnmatchedSizes, "Number of coordinates of points4D must be 4" );
|
||||
}
|
||||
|
||||
int i;
|
||||
for( i = 0; i < 3; i++ )
|
||||
{
|
||||
if( projMatrs[i] == 0 )
|
||||
{
|
||||
CV_ERROR( CV_StsNullPtr, "Some of projMatrs is a NULL pointer" );
|
||||
}
|
||||
|
||||
if( projPoints[i] == 0 )
|
||||
{
|
||||
CV_ERROR( CV_StsNullPtr, "Some of projPoints is a NULL pointer" );
|
||||
}
|
||||
|
||||
if( resultProjMatrs[i] == 0 )
|
||||
{
|
||||
CV_ERROR( CV_StsNullPtr, "Some of resultProjMatrs is a NULL pointer" );
|
||||
}
|
||||
|
||||
/* ----------- test for matrix ------------- */
|
||||
if( !CV_IS_MAT(projMatrs[i]) )
|
||||
{
|
||||
CV_ERROR( CV_StsUnsupportedFormat, "Each of projMatrs must be a matrix" );
|
||||
}
|
||||
|
||||
if( !CV_IS_MAT(projPoints[i]) )
|
||||
{
|
||||
CV_ERROR( CV_StsUnsupportedFormat, "Each of projPoints must be a matrix" );
|
||||
}
|
||||
|
||||
if( !CV_IS_MAT(resultProjMatrs[i]) )
|
||||
{
|
||||
CV_ERROR( CV_StsUnsupportedFormat, "Each of resultProjMatrs must be a matrix" );
|
||||
}
|
||||
|
||||
/* ------------- Test sizes --------------- */
|
||||
if( projMatrs[i]->rows != 3 || projMatrs[i]->cols != 4 )
|
||||
{
|
||||
CV_ERROR( CV_StsUnmatchedSizes, "Size of projMatr must be 3x4" );
|
||||
}
|
||||
|
||||
if( projPoints[i]->rows != 2 || projPoints[i]->cols != numPoints )
|
||||
{
|
||||
CV_ERROR( CV_StsUnmatchedSizes, "Size of resultProjMatrs must be 3x4" );
|
||||
}
|
||||
|
||||
if( resultProjMatrs[i]->rows != 3 || resultProjMatrs[i]->cols != 4 )
|
||||
{
|
||||
CV_ERROR( CV_StsUnmatchedSizes, "Size of resultProjMatrs must be 3x4" );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* Allocate memory for points 4D */
|
||||
CV_CALL( points4D = cvCreateMat(4,numPoints,CV_64F) );
|
||||
CV_CALL( vectorX0 = cvCreateMat(36 + numPoints*4,1,CV_64F) );
|
||||
CV_CALL( observRes = cvCreateMat(2*numPoints*3,1,CV_64F) );
|
||||
CV_CALL( optimX = cvCreateMat(36+numPoints*4,1,CV_64F) );
|
||||
//CV_CALL( error = cvCreateMat(numPoints*2*3,1,CV_64F) );
|
||||
|
||||
|
||||
/* Reconstruct points 4D using projected points and projection matrices */
|
||||
icvReconstructPointsFor3View( projMatrs[0],projMatrs[1],projMatrs[2],
|
||||
projPoints[0],projPoints[1],projPoints[2],
|
||||
points4D);
|
||||
|
||||
|
||||
|
||||
/* Fill observed points on images */
|
||||
/* result of function is projection of N 3D points using 3 projection matrices */
|
||||
/* projected points store as (projection by matrix P1),(projection by matrix P2),(projection by matrix P3) */
|
||||
/* each projection is x1,y1,x2,y2,x3,y3,x4,y4 */
|
||||
int currMatr;
|
||||
for( currMatr = 0; currMatr < 3; currMatr++ )
|
||||
{
|
||||
for( i = 0; i < numPoints; i++ )
|
||||
{
|
||||
cvmSet(observRes,currMatr*numPoints*2+i*2 ,0,cvmGet(projPoints[currMatr],0,i) );/* x */
|
||||
cvmSet(observRes,currMatr*numPoints*2+i*2+1,0,cvmGet(projPoints[currMatr],1,i) );/* y */
|
||||
}
|
||||
}
|
||||
|
||||
/* Fill with projection matrices */
|
||||
for( currMatr = 0; currMatr < 3; currMatr++ )
|
||||
{
|
||||
int i;
|
||||
for( i = 0; i < 12; i++ )
|
||||
{
|
||||
cvmSet(vectorX0,currMatr*12+i,0,cvmGet(projMatrs[currMatr],i/4,i%4));
|
||||
}
|
||||
}
|
||||
|
||||
/* Fill with 4D points */
|
||||
|
||||
int currPoint;
|
||||
for( currPoint = 0; currPoint < numPoints; currPoint++ )
|
||||
{
|
||||
cvmSet(vectorX0,36 + currPoint*4 + 0,0,cvmGet(points4D,0,currPoint));
|
||||
cvmSet(vectorX0,36 + currPoint*4 + 1,0,cvmGet(points4D,1,currPoint));
|
||||
cvmSet(vectorX0,36 + currPoint*4 + 2,0,cvmGet(points4D,2,currPoint));
|
||||
cvmSet(vectorX0,36 + currPoint*4 + 3,0,cvmGet(points4D,3,currPoint));
|
||||
}
|
||||
|
||||
|
||||
/* Allocate memory for result */
|
||||
cvLevenbergMarquardtOptimization( icvJacobianFunction_ProjTrifocal, icvFunc_ProjTrifocal,
|
||||
vectorX0,observRes,optimX,100,1e-6);
|
||||
|
||||
/* Copy results */
|
||||
for( currMatr = 0; currMatr < 3; currMatr++ )
|
||||
{
|
||||
/* Copy projection matrices */
|
||||
for(int i=0;i<12;i++)
|
||||
{
|
||||
cvmSet(resultProjMatrs[currMatr],i/4,i%4,cvmGet(optimX,currMatr*12+i,0));
|
||||
}
|
||||
}
|
||||
|
||||
/* Copy 4D points */
|
||||
for( currPoint = 0; currPoint < numPoints; currPoint++ )
|
||||
{
|
||||
cvmSet(resultPoints4D,0,currPoint,cvmGet(optimX,36 + currPoint*4,0));
|
||||
cvmSet(resultPoints4D,1,currPoint,cvmGet(optimX,36 + currPoint*4+1,0));
|
||||
cvmSet(resultPoints4D,2,currPoint,cvmGet(optimX,36 + currPoint*4+2,0));
|
||||
cvmSet(resultPoints4D,3,currPoint,cvmGet(optimX,36 + currPoint*4+3,0));
|
||||
}
|
||||
|
||||
__END__;
|
||||
|
||||
/* Free allocated memory */
|
||||
cvReleaseMat(&optimX);
|
||||
cvReleaseMat(&points4D);
|
||||
cvReleaseMat(&vectorX0);
|
||||
cvReleaseMat(&observRes);
|
||||
|
||||
return;
|
||||
|
||||
|
||||
}
|
||||
|
||||
/*------------------------------------------------------------------------------*/
|
||||
/* Create good points using status information */
|
||||
void icvCreateGoodPoints(CvMat *points,CvMat **goodPoints, CvMat *status)
|
||||
{
|
||||
*goodPoints = 0;
|
||||
|
||||
CV_FUNCNAME( "icvCreateGoodPoints" );
|
||||
__BEGIN__;
|
||||
|
||||
int numPoints;
|
||||
numPoints = points->cols;
|
||||
|
||||
if( numPoints < 1 )
|
||||
{
|
||||
CV_ERROR( CV_StsOutOfRange, "Number of points must be more than 0" );
|
||||
}
|
||||
|
||||
int numCoord;
|
||||
numCoord = points->rows;
|
||||
if( numCoord < 1 )
|
||||
{
|
||||
CV_ERROR( CV_StsOutOfRange, "Number of points coordinates must be more than 0" );
|
||||
}
|
||||
|
||||
/* Define number of good points */
|
||||
int goodNum;
|
||||
int i,j;
|
||||
|
||||
goodNum = 0;
|
||||
for( i = 0; i < numPoints; i++)
|
||||
{
|
||||
if( cvmGet(status,0,i) > 0 )
|
||||
goodNum++;
|
||||
}
|
||||
|
||||
/* Allocate memory for good points */
|
||||
CV_CALL( *goodPoints = cvCreateMat(numCoord,goodNum,CV_64F) );
|
||||
|
||||
for( i = 0; i < numCoord; i++ )
|
||||
{
|
||||
int currPoint = 0;
|
||||
for( j = 0; j < numPoints; j++)
|
||||
{
|
||||
if( cvmGet(status,0,j) > 0 )
|
||||
{
|
||||
cvmSet(*goodPoints,i,currPoint,cvmGet(points,i,j));
|
||||
currPoint++;
|
||||
}
|
||||
}
|
||||
}
|
||||
__END__;
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -0,0 +1,483 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
#include "_cvaux.h"
|
||||
|
||||
#if 0
|
||||
CvStatus
|
||||
icvFetchLine8uC3R( uchar * src, int src_step,
|
||||
uchar * dst, int *dst_num, CvSize src_size, CvPoint start, CvPoint end )
|
||||
{
|
||||
int i;
|
||||
int dx = end.x - start.x, dy = end.y - start.y;
|
||||
int err;
|
||||
|
||||
if( !src || !dst || (src_size.width | src_size.height) < 0 ||
|
||||
src_step < src_size.width * 3 ||
|
||||
(unsigned) start.x >= (unsigned) src_size.width ||
|
||||
(unsigned) start.y >= (unsigned) src_size.height ||
|
||||
(unsigned) end.x >= (unsigned) src_size.width ||
|
||||
(unsigned) end.y >= (unsigned) src_size.height )
|
||||
return CV_BADFACTOR_ERR;
|
||||
|
||||
if( dx < 0 )
|
||||
{
|
||||
dx = -dx;
|
||||
dy = -dy;
|
||||
start.x = end.x;
|
||||
start.y = end.y;
|
||||
}
|
||||
|
||||
src += start.y * src_step + start.x * 3;
|
||||
|
||||
i = dy >> 31;
|
||||
dy = (dy ^ i) - i;
|
||||
src_step = (src_step ^ i) - i;
|
||||
|
||||
if( dx > dy )
|
||||
{
|
||||
if( dst_num )
|
||||
{
|
||||
if( *dst_num <= dx )
|
||||
return CV_BADSIZE_ERR;
|
||||
*dst_num = dx + 1;
|
||||
}
|
||||
err = dx;
|
||||
dx += dx;
|
||||
dy += dy;
|
||||
for( i = dx; i >= 0; i -= 2, dst += 3 )
|
||||
{
|
||||
int mask = (err -= dy) < 0 ? -1 : 0;
|
||||
|
||||
dst[0] = src[0];
|
||||
dst[1] = src[1];
|
||||
dst[2] = src[2];
|
||||
|
||||
err += dx & mask;
|
||||
src += (src_step & mask) + 3;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if( dst_num )
|
||||
{
|
||||
if( *dst_num <= dy )
|
||||
return CV_BADSIZE_ERR;
|
||||
*dst_num = dy + 1;
|
||||
}
|
||||
err = dy;
|
||||
dx += dx;
|
||||
dy += dy;
|
||||
for( i = dy; i >= 0; i -= 2, dst += 3 )
|
||||
{
|
||||
int mask = (err -= dx) < 0 ? -1 : 0;
|
||||
|
||||
dst[0] = src[0];
|
||||
dst[1] = src[1];
|
||||
dst[2] = src[2];
|
||||
|
||||
err += dy & mask;
|
||||
src += src_step + (mask & 3);
|
||||
}
|
||||
}
|
||||
return CV_NO_ERR;
|
||||
}
|
||||
|
||||
CvStatus
|
||||
icvDrawLine8uC3R( uchar * src, int src_num,
|
||||
uchar * dst, int dst_step, CvSize dst_size, CvPoint start, CvPoint end )
|
||||
{
|
||||
int i;
|
||||
int dx = end.x - start.x, dy = end.y - start.y;
|
||||
int err;
|
||||
|
||||
if( !src || !dst || (dst_size.width | dst_size.height) < 0 ||
|
||||
dst_step < dst_size.width * 3 ||
|
||||
(unsigned) start.x >= (unsigned) dst_size.width ||
|
||||
(unsigned) start.y >= (unsigned) dst_size.height ||
|
||||
(unsigned) end.x >= (unsigned) dst_size.width ||
|
||||
(unsigned) end.y >= (unsigned) dst_size.height )
|
||||
return CV_BADFACTOR_ERR;
|
||||
|
||||
if( dx < 0 )
|
||||
{
|
||||
dx = -dx;
|
||||
dy = -dy;
|
||||
start.x = end.x;
|
||||
start.y = end.y;
|
||||
}
|
||||
|
||||
dst += start.y * dst_step + start.x * 3;
|
||||
|
||||
i = dy >> 31;
|
||||
dy = (dy ^ i) - i;
|
||||
dst_step = (dst_step ^ i) - i;
|
||||
|
||||
if( dx > dy )
|
||||
{
|
||||
if( (unsigned) (src_num - 1) < (unsigned) dx )
|
||||
return CV_BADSIZE_ERR;
|
||||
err = dx;
|
||||
dx += dx;
|
||||
dy += dy;
|
||||
for( i = dx; i >= 0; i -= 2, src += 3 )
|
||||
{
|
||||
int mask = (err -= dy) < 0 ? -1 : 0;
|
||||
|
||||
dst[0] = src[0];
|
||||
dst[1] = src[1];
|
||||
dst[2] = src[2];
|
||||
err += dx & mask;
|
||||
dst += (dst_step & mask) + 3;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if( (unsigned) (src_num - 1) < (unsigned) dy )
|
||||
return CV_BADSIZE_ERR;
|
||||
err = dy;
|
||||
dx += dx;
|
||||
dy += dy;
|
||||
for( i = dy; i >= 0; i -= 2, src += 3 )
|
||||
{
|
||||
int mask = (err -= dx) < 0 ? -1 : 0;
|
||||
|
||||
dst[0] = src[0];
|
||||
dst[1] = src[1];
|
||||
dst[2] = src[2];
|
||||
err += dy & mask;
|
||||
dst += dst_step + (mask & 3);
|
||||
}
|
||||
}
|
||||
return CV_NO_ERR;
|
||||
}
|
||||
#endif
|
||||
|
||||
/*======================================================================================*/
|
||||
|
||||
static CvStatus
|
||||
icvPreWarpImage8uC3R( int numLines, /* number of scanlines */
|
||||
uchar * src, /* source image */
|
||||
int src_step, /* line step */
|
||||
uchar * dst, /* dest buffers */
|
||||
int *dst_nums, /* lens of buffer */
|
||||
CvSize src_size, /* image size in pixels */
|
||||
int *scanlines ) /* scanlines array */
|
||||
{
|
||||
int k;
|
||||
CvPoint start;
|
||||
CvPoint end;
|
||||
int curr;
|
||||
int curr_dst;
|
||||
CvMat mat;
|
||||
|
||||
curr = 0;
|
||||
curr_dst = 0;
|
||||
|
||||
cvInitMatHeader( &mat, src_size.height, src_size.width, CV_8UC3, src, src_step );
|
||||
|
||||
for( k = 0; k < numLines; k++ )
|
||||
{
|
||||
start.x = scanlines[curr++];
|
||||
start.y = scanlines[curr++];
|
||||
|
||||
end.x = scanlines[curr++];
|
||||
end.y = scanlines[curr++];
|
||||
|
||||
#ifdef _DEBUG
|
||||
{
|
||||
CvLineIterator iterator;
|
||||
assert( cvInitLineIterator( &mat, start, end, &iterator, 8 ) == dst_nums[k] );
|
||||
}
|
||||
#endif
|
||||
cvSampleLine( &mat, start, end, dst + curr_dst, 8 );
|
||||
curr_dst += dst_nums[k] * 3;
|
||||
|
||||
}
|
||||
|
||||
return CV_NO_ERR;
|
||||
}
|
||||
|
||||
|
||||
/*======================================================================================*/
|
||||
|
||||
static CvStatus
|
||||
icvPostWarpImage8uC3R( int numLines, /* number of scanlines */
|
||||
uchar * src, /* source buffers */
|
||||
int *src_nums, /* lens of buffers */
|
||||
uchar * dst, /* dest image */
|
||||
int dst_step, /* dest image step */
|
||||
CvSize dst_size, /* dest image size */
|
||||
int *scanlines ) /* scanline */
|
||||
{
|
||||
int i, k;
|
||||
CvPoint start;
|
||||
CvPoint end;
|
||||
int curr;
|
||||
int src_num;
|
||||
int curr_src;
|
||||
CvMat mat;
|
||||
CvLineIterator iterator;
|
||||
|
||||
curr = 0;
|
||||
curr_src = 0;
|
||||
|
||||
cvInitMatHeader( &mat, dst_size.height, dst_size.width, CV_8UC3, dst, dst_step );
|
||||
|
||||
for( k = 0; k < numLines; k++ )
|
||||
{
|
||||
start.x = scanlines[curr++];
|
||||
start.y = scanlines[curr++];
|
||||
|
||||
end.x = scanlines[curr++];
|
||||
end.y = scanlines[curr++];
|
||||
|
||||
src_num = src_nums[k];
|
||||
|
||||
if( cvInitLineIterator( &mat, start, end, &iterator, 8 ) != src_num )
|
||||
{
|
||||
assert(0);
|
||||
return CV_NOTDEFINED_ERR;
|
||||
}
|
||||
|
||||
for( i = 0; i < src_num; i++ )
|
||||
{
|
||||
memcpy( iterator.ptr, src + curr_src, 3 );
|
||||
CV_NEXT_LINE_POINT( iterator );
|
||||
curr_src += 3;
|
||||
}
|
||||
|
||||
#if 0
|
||||
err = icvDrawLine8uC3R( src + curr_src, /* sourse buffer */
|
||||
src_num, /* len of buffer */
|
||||
dst, /* dest image */
|
||||
dst_step, /* dest image step */
|
||||
dst_size, /* dest image size */
|
||||
start, /* start point */
|
||||
end ); /* end point */
|
||||
curr_src += src_num * 3;
|
||||
#endif
|
||||
}
|
||||
|
||||
return CV_NO_ERR;
|
||||
|
||||
}
|
||||
|
||||
|
||||
/*======================================================================================*/
|
||||
|
||||
/*F///////////////////////////////////////////////////////////////////////////////////////
|
||||
// Name: icvDeleteMoire8uC3R
|
||||
// Purpose:
|
||||
// Function deletes moire - replaces black uncovered pixels with their neighboors.
|
||||
// Context:
|
||||
// Parameters:
|
||||
// img - image data
|
||||
// img_step - distance between lines in bytes
|
||||
// img_size - width and height of the image in pixels
|
||||
// Returns:
|
||||
// CV_NO_ERR if all Ok or error code
|
||||
// Notes:
|
||||
//F*/
|
||||
static CvStatus
|
||||
icvDeleteMoire8u( uchar * img, int img_step, CvSize img_size, int cn )
|
||||
{
|
||||
int x, y;
|
||||
uchar *src = img, *dst = img + img_step;
|
||||
|
||||
if( !img || img_size.width <= 0 || img_size.height <= 0 || img_step < img_size.width * 3 )
|
||||
return CV_BADFACTOR_ERR;
|
||||
|
||||
img_size.width *= cn;
|
||||
|
||||
for( y = 1; y < img_size.height; y++, src = dst, dst += img_step )
|
||||
{
|
||||
switch( cn )
|
||||
{
|
||||
case 1:
|
||||
for( x = 0; x < img_size.width; x++ )
|
||||
{
|
||||
if( dst[x] == 0 )
|
||||
dst[x] = src[x];
|
||||
}
|
||||
break;
|
||||
case 3:
|
||||
for( x = 0; x < img_size.width; x += 3 )
|
||||
{
|
||||
if( dst[x] == 0 && dst[x + 1] == 0 && dst[x + 2] == 0 )
|
||||
{
|
||||
dst[x] = src[x];
|
||||
dst[x + 1] = src[x + 1];
|
||||
dst[x + 2] = src[x + 2];
|
||||
}
|
||||
}
|
||||
break;
|
||||
default:
|
||||
assert(0);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return CV_NO_ERR;
|
||||
}
|
||||
|
||||
|
||||
/*F///////////////////////////////////////////////////////////////////////////////////////
|
||||
// Name: cvDeleteMoire
|
||||
// Purpose: The functions delete moire on the image after ViewMorphing
|
||||
// Context:
|
||||
// Parameters: img - image on which will delete moire
|
||||
//
|
||||
// Notes:
|
||||
//F*/
|
||||
CV_IMPL void
|
||||
cvDeleteMoire( IplImage * img )
|
||||
{
|
||||
uchar *img_data = 0;
|
||||
int img_step = 0;
|
||||
CvSize img_size;
|
||||
|
||||
CV_FUNCNAME( "cvDeleteMoire" );
|
||||
|
||||
__BEGIN__;
|
||||
|
||||
cvGetImageRawData( img, &img_data, &img_step, &img_size );
|
||||
|
||||
if( img->nChannels != 1 && img->nChannels != 3 )
|
||||
CV_ERROR( CV_BadNumChannels, "Source image must have 3 channel." );
|
||||
if( img->depth != IPL_DEPTH_8U )
|
||||
CV_ERROR( CV_BadDepth, "Channel depth of source image must be 8." );
|
||||
|
||||
CV_CALL( icvDeleteMoire8u( img_data, img_step, img_size, img->nChannels ));
|
||||
|
||||
__CLEANUP__;
|
||||
__END__;
|
||||
|
||||
}
|
||||
|
||||
|
||||
/*F///////////////////////////////////////////////////////////////////////////////////////
|
||||
// Name: cvPreWarpImage
|
||||
// Purpose: The functions warp image for next stage of ViewMorphing
|
||||
// Context:
|
||||
// Parameters: img - initial image (in the beginning)
|
||||
//
|
||||
// Notes:
|
||||
//F*/
|
||||
CV_IMPL void
|
||||
cvPreWarpImage( int numLines, /* number of scanlines */
|
||||
IplImage * img, /* Source Image */
|
||||
uchar * dst, /* dest buffers */
|
||||
int *dst_nums, /* lens of buffer */
|
||||
int *scanlines /* scanlines array */ )
|
||||
{
|
||||
uchar *img_data = 0;
|
||||
int img_step = 0;
|
||||
CvSize img_size;
|
||||
|
||||
CV_FUNCNAME( "cvPreWarpImage" );
|
||||
|
||||
__BEGIN__;
|
||||
|
||||
cvGetImageRawData( img, &img_data, &img_step, &img_size );
|
||||
|
||||
if( img->nChannels != 3 )
|
||||
CV_ERROR( CV_BadNumChannels, "Source image must have 3 channel." );
|
||||
if( img->depth != IPL_DEPTH_8U )
|
||||
CV_ERROR( CV_BadDepth, "Channel depth of image must be 8." );
|
||||
|
||||
CV_CALL( icvPreWarpImage8uC3R( numLines, /* number of scanlines */
|
||||
img_data, /* source image */
|
||||
img_step, /* line step */
|
||||
dst, /* dest buffers */
|
||||
dst_nums, /* lens of buffer */
|
||||
img_size, /* image size in pixels */
|
||||
scanlines /* scanlines array */ ));
|
||||
|
||||
__CLEANUP__;
|
||||
__END__;
|
||||
|
||||
}
|
||||
|
||||
|
||||
/*F///////////////////////////////////////////////////////////////////////////////////////
|
||||
// Name: cvPostWarpImage
|
||||
// Purpose: The functions postwarp the image after morphing
|
||||
// Context:
|
||||
// Parameters: img - initial image (in the beginning)
|
||||
//
|
||||
// Notes:
|
||||
//F*/
|
||||
CV_IMPL void
|
||||
cvPostWarpImage( int numLines, /* number of scanlines */
|
||||
uchar * src, /* source buffers */
|
||||
int *src_nums, /* lens of buffers */
|
||||
IplImage * img, /* dest image */
|
||||
int *scanlines /* scanline */ )
|
||||
{
|
||||
uchar *img_data = 0;
|
||||
int img_step = 0;
|
||||
CvSize img_size;
|
||||
|
||||
CV_FUNCNAME( "cvPostWarpImage" );
|
||||
|
||||
__BEGIN__;
|
||||
|
||||
cvGetImageRawData( img, &img_data, &img_step, &img_size );
|
||||
|
||||
if( img->nChannels != 3 )
|
||||
CV_ERROR( CV_BadNumChannels, "Source image must have 3 channel." );
|
||||
if( img->depth != IPL_DEPTH_8U )
|
||||
CV_ERROR( CV_BadDepth, "Channel depth of image must be 8." );
|
||||
|
||||
CV_CALL( icvPostWarpImage8uC3R( numLines, /* number of scanlines */
|
||||
src, /* source buffers */
|
||||
src_nums, /* lens of buffers */
|
||||
img_data, /* dest image */
|
||||
img_step, /* dest image step */
|
||||
img_size, /* dest image size */
|
||||
scanlines /* scanline */ ));
|
||||
|
||||
__CLEANUP__;
|
||||
__END__;
|
||||
}
|
||||
|
||||
/* End of file */
|
||||
|
||||
1766
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/src/cvlmeds.cpp
Normal file
1766
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/src/cvlmeds.cpp
Normal file
File diff suppressed because it is too large
Load Diff
879
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/src/cvmat.cpp
Normal file
879
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/src/cvmat.cpp
Normal file
@@ -0,0 +1,879 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
// temporarily remove it from build
|
||||
#if 0 && ((_MSC_VER>=1200) || defined __BORLANDC__)
|
||||
|
||||
double CvMAT::get( const uchar* ptr, int type, int coi )
|
||||
{
|
||||
double t = 0;
|
||||
assert( (unsigned)coi < (unsigned)CV_MAT_CN(type) );
|
||||
|
||||
switch( CV_MAT_DEPTH(type) )
|
||||
{
|
||||
case CV_8U:
|
||||
t = ((uchar*)ptr)[coi];
|
||||
break;
|
||||
case CV_8S:
|
||||
t = ((char*)ptr)[coi];
|
||||
break;
|
||||
case CV_16S:
|
||||
t = ((short*)ptr)[coi];
|
||||
break;
|
||||
case CV_32S:
|
||||
t = ((int*)ptr)[coi];
|
||||
break;
|
||||
case CV_32F:
|
||||
t = ((float*)ptr)[coi];
|
||||
break;
|
||||
case CV_64F:
|
||||
t = ((double*)ptr)[coi];
|
||||
break;
|
||||
}
|
||||
|
||||
return t;
|
||||
}
|
||||
|
||||
void CvMAT::set( uchar* ptr, int type, int coi, double d )
|
||||
{
|
||||
int i;
|
||||
assert( (unsigned)coi < (unsigned)CV_MAT_CN(type) );
|
||||
|
||||
switch( CV_MAT_DEPTH(type))
|
||||
{
|
||||
case CV_8U:
|
||||
i = cvRound(d);
|
||||
((uchar*)ptr)[coi] = CV_CAST_8U(i);
|
||||
break;
|
||||
case CV_8S:
|
||||
i = cvRound(d);
|
||||
((char*)ptr)[coi] = CV_CAST_8S(i);
|
||||
break;
|
||||
case CV_16S:
|
||||
i = cvRound(d);
|
||||
((short*)ptr)[coi] = CV_CAST_16S(i);
|
||||
break;
|
||||
case CV_32S:
|
||||
i = cvRound(d);
|
||||
((int*)ptr)[coi] = CV_CAST_32S(i);
|
||||
break;
|
||||
case CV_32F:
|
||||
((float*)ptr)[coi] = (float)d;
|
||||
break;
|
||||
case CV_64F:
|
||||
((double*)ptr)[coi] = d;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void CvMAT::set( uchar* ptr, int type, int coi, int i )
|
||||
{
|
||||
assert( (unsigned)coi < (unsigned)CV_MAT_CN(type) );
|
||||
|
||||
switch( CV_MAT_DEPTH(type))
|
||||
{
|
||||
case CV_8U:
|
||||
((uchar*)ptr)[coi] = CV_CAST_8U(i);
|
||||
break;
|
||||
case CV_8S:
|
||||
((char*)ptr)[coi] = CV_CAST_8S(i);
|
||||
break;
|
||||
case CV_16S:
|
||||
((short*)ptr)[coi] = CV_CAST_16S(i);
|
||||
break;
|
||||
case CV_32S:
|
||||
((int*)ptr)[coi] = i;
|
||||
break;
|
||||
case CV_32F:
|
||||
((float*)ptr)[coi] = (float)i;
|
||||
break;
|
||||
case CV_64F:
|
||||
((double*)ptr)[coi] = (double)i;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void CvMAT::set( uchar* ptr, int type, double d )
|
||||
{
|
||||
int i, cn = CV_MAT_CN(type);
|
||||
|
||||
switch( CV_MAT_DEPTH(type))
|
||||
{
|
||||
case CV_8U:
|
||||
i = cvRound(d);
|
||||
((uchar*)ptr)[0] = CV_CAST_8U(i);
|
||||
i = cn;
|
||||
while( --i ) ((uchar*)ptr)[i] = 0;
|
||||
break;
|
||||
case CV_8S:
|
||||
i = cvRound(d);
|
||||
((char*)ptr)[0] = CV_CAST_8S(i);
|
||||
i = cn;
|
||||
while( --i ) ((char*)ptr)[i] = 0;
|
||||
break;
|
||||
case CV_16S:
|
||||
i = cvRound(d);
|
||||
((short*)ptr)[0] = CV_CAST_16S(i);
|
||||
i = cn;
|
||||
while( --i ) ((short*)ptr)[i] = 0;
|
||||
break;
|
||||
case CV_32S:
|
||||
i = cvRound(d);
|
||||
((int*)ptr)[0] = i;
|
||||
i = cn;
|
||||
while( --i ) ((int*)ptr)[i] = 0;
|
||||
break;
|
||||
case CV_32F:
|
||||
((float*)ptr)[0] = (float)d;
|
||||
i = cn;
|
||||
while( --i ) ((float*)ptr)[i] = 0;
|
||||
break;
|
||||
case CV_64F:
|
||||
((double*)ptr)[0] = d;
|
||||
i = cn;
|
||||
while( --i ) ((double*)ptr)[i] = 0;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void CvMAT::set( uchar* ptr, int type, int i )
|
||||
{
|
||||
int cn = CV_MAT_CN(type);
|
||||
|
||||
switch( CV_MAT_DEPTH(type))
|
||||
{
|
||||
case CV_8U:
|
||||
((uchar*)ptr)[0] = CV_CAST_8U(i);
|
||||
i = cn;
|
||||
while( --i ) ((uchar*)ptr)[i] = 0;
|
||||
break;
|
||||
case CV_8S:
|
||||
((char*)ptr)[0] = CV_CAST_8S(i);
|
||||
i = cn;
|
||||
while( --i ) ((char*)ptr)[i] = 0;
|
||||
break;
|
||||
case CV_16S:
|
||||
((short*)ptr)[0] = CV_CAST_16S(i);
|
||||
i = cn;
|
||||
while( --i ) ((short*)ptr)[i] = 0;
|
||||
break;
|
||||
case CV_32S:
|
||||
((int*)ptr)[0] = i;
|
||||
i = cn;
|
||||
while( --i ) ((int*)ptr)[i] = 0;
|
||||
break;
|
||||
case CV_32F:
|
||||
((float*)ptr)[0] = (float)i;
|
||||
i = cn;
|
||||
while( --i ) ((float*)ptr)[i] = 0;
|
||||
break;
|
||||
case CV_64F:
|
||||
((double*)ptr)[0] = (double)i;
|
||||
i = cn;
|
||||
while( --i ) ((double*)ptr)[i] = 0;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
CvMAT::CvMAT( const _CvMAT_T_& mat_t )
|
||||
{
|
||||
data.ptr = 0;
|
||||
type = 0;
|
||||
refcount = 0;
|
||||
*this = mat_t;
|
||||
}
|
||||
|
||||
|
||||
CvMAT::CvMAT( const _CvMAT_ADD_& mat_add )
|
||||
{
|
||||
data.ptr = 0;
|
||||
type = 0;
|
||||
refcount = 0;
|
||||
*this = mat_add;
|
||||
}
|
||||
|
||||
|
||||
CvMAT::CvMAT( const _CvMAT_ADD_EX_& mat_add )
|
||||
{
|
||||
data.ptr = 0;
|
||||
type = 0;
|
||||
refcount = 0;
|
||||
*this = mat_add;
|
||||
}
|
||||
|
||||
|
||||
CvMAT::CvMAT( const _CvMAT_SCALE_& scale_mat )
|
||||
{
|
||||
data.ptr = 0;
|
||||
type = 0;
|
||||
refcount = 0;
|
||||
*this = scale_mat;
|
||||
}
|
||||
|
||||
|
||||
CvMAT::CvMAT( const _CvMAT_SCALE_SHIFT_& scale_shift_mat )
|
||||
{
|
||||
data.ptr = 0;
|
||||
type = 0;
|
||||
refcount = 0;
|
||||
*this = scale_shift_mat;
|
||||
}
|
||||
|
||||
|
||||
CvMAT::CvMAT( const _CvMAT_MUL_& mmul )
|
||||
{
|
||||
data.ptr = 0;
|
||||
type = 0;
|
||||
refcount = 0;
|
||||
*this = mmul;
|
||||
}
|
||||
|
||||
|
||||
CvMAT::CvMAT( const _CvMAT_MUL_ADD_& mmuladd )
|
||||
{
|
||||
data.ptr = 0;
|
||||
type = 0;
|
||||
refcount = 0;
|
||||
*this = mmuladd;
|
||||
}
|
||||
|
||||
|
||||
CvMAT::CvMAT( const _CvMAT_INV_& inv_mat )
|
||||
{
|
||||
data.ptr = 0;
|
||||
type = 0;
|
||||
refcount = 0;
|
||||
*this = inv_mat;
|
||||
}
|
||||
|
||||
|
||||
CvMAT::CvMAT( const _CvMAT_NOT_& not_mat )
|
||||
{
|
||||
type = 0;
|
||||
data.ptr = 0;
|
||||
refcount = 0;
|
||||
*this = not_mat;
|
||||
}
|
||||
|
||||
|
||||
CvMAT::CvMAT( const _CvMAT_UN_LOGIC_& mat_logic )
|
||||
{
|
||||
type = 0;
|
||||
data.ptr = 0;
|
||||
refcount = 0;
|
||||
*this = mat_logic;
|
||||
}
|
||||
|
||||
|
||||
CvMAT::CvMAT( const _CvMAT_LOGIC_& mat_logic )
|
||||
{
|
||||
type = 0;
|
||||
data.ptr = 0;
|
||||
refcount = 0;
|
||||
*this = mat_logic;
|
||||
}
|
||||
|
||||
|
||||
CvMAT::CvMAT( const _CvMAT_COPY_& mat_copy )
|
||||
{
|
||||
CvMAT* src = (CvMAT*)mat_copy.a;
|
||||
create( src->height, src->width, src->type );
|
||||
cvCopy( src, this );
|
||||
}
|
||||
|
||||
|
||||
CvMAT::CvMAT( const _CvMAT_CVT_& mat_cvt )
|
||||
{
|
||||
type = 0;
|
||||
data.ptr = 0;
|
||||
refcount = 0;
|
||||
*this = mat_cvt;
|
||||
}
|
||||
|
||||
|
||||
CvMAT::CvMAT( const _CvMAT_DOT_OP_& dot_op )
|
||||
{
|
||||
data.ptr = 0;
|
||||
type = 0;
|
||||
refcount = 0;
|
||||
*this = dot_op;
|
||||
}
|
||||
|
||||
|
||||
CvMAT::CvMAT( const _CvMAT_SOLVE_& solve_mat )
|
||||
{
|
||||
type = 0;
|
||||
data.ptr = 0;
|
||||
refcount = 0;
|
||||
*this = solve_mat;
|
||||
}
|
||||
|
||||
|
||||
CvMAT::CvMAT( const _CvMAT_CMP_& cmp_mat )
|
||||
{
|
||||
type = 0;
|
||||
data.ptr = 0;
|
||||
refcount = 0;
|
||||
*this = cmp_mat;
|
||||
}
|
||||
|
||||
|
||||
/****************************************************************************************\
|
||||
* CvMAT::operator = *
|
||||
\****************************************************************************************/
|
||||
|
||||
CvMAT& CvMAT::operator = ( const _CvMAT_T_& mat_t )
|
||||
{
|
||||
CvMAT* src = (CvMAT*)&mat_t.a;
|
||||
if( !data.ptr )
|
||||
{
|
||||
create( src->width, src->height, src->type );
|
||||
}
|
||||
|
||||
cvTranspose( src, this );
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
||||
CvMAT& CvMAT::operator = ( const _CvMAT_ADD_& mat_add )
|
||||
{
|
||||
CvMAT* a = mat_add.a;
|
||||
CvMAT* b = mat_add.b;
|
||||
|
||||
if( !data.ptr )
|
||||
{
|
||||
create( a->height, a->width, a->type );
|
||||
}
|
||||
|
||||
if( mat_add.beta == 1 )
|
||||
{
|
||||
cvAdd( a, b, this );
|
||||
return *this;
|
||||
}
|
||||
|
||||
if( mat_add.beta == -1 )
|
||||
{
|
||||
cvSub( a, b, this );
|
||||
return *this;
|
||||
}
|
||||
|
||||
if( CV_MAT_DEPTH(a->type) >= CV_32F && CV_MAT_CN(a->type) <= 2 )
|
||||
cvScaleAdd( b, cvScalar(mat_add.beta), a, this );
|
||||
else
|
||||
cvAddWeighted( a, 1, b, mat_add.beta, 0, this );
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
||||
CvMAT& CvMAT::operator = ( const _CvMAT_ADD_EX_& mat_add )
|
||||
{
|
||||
CvMAT* a = mat_add.a;
|
||||
CvMAT* b = mat_add.b;
|
||||
|
||||
if( !data.ptr )
|
||||
{
|
||||
create( a->height, a->width, a->type );
|
||||
}
|
||||
|
||||
cvAddWeighted( a, mat_add.alpha, b, mat_add.beta, mat_add.gamma, this );
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
||||
CvMAT& CvMAT::operator = ( const _CvMAT_SCALE_& scale_mat )
|
||||
{
|
||||
CvMAT* src = scale_mat.a;
|
||||
|
||||
if( !data.ptr )
|
||||
{
|
||||
create( src->height, src->width, src->type );
|
||||
}
|
||||
|
||||
cvConvertScale( src, this, scale_mat.alpha, 0 );
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
||||
CvMAT& CvMAT::operator = ( const _CvMAT_SCALE_SHIFT_& scale_shift_mat )
|
||||
{
|
||||
CvMAT* src = scale_shift_mat.a;
|
||||
|
||||
if( !data.ptr )
|
||||
{
|
||||
create( src->height, src->width, src->type );
|
||||
}
|
||||
|
||||
cvConvertScale( src, this, scale_shift_mat.alpha, scale_shift_mat.beta );
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
||||
CvMAT& CvMAT::operator = ( const _CvMAT_MUL_& mmul )
|
||||
{
|
||||
CvMAT* a = mmul.a;
|
||||
CvMAT* b = mmul.b;
|
||||
int t_a = mmul.t_ab & 1;
|
||||
int t_b = (mmul.t_ab & 2) != 0;
|
||||
int m = (&(a->rows))[t_a];
|
||||
int n = (&(b->rows))[t_b ^ 1];
|
||||
/* this(m x n) = (a^o1(t))(m x l) * (b^o2(t))(l x n) */
|
||||
|
||||
if( !data.ptr )
|
||||
{
|
||||
create( m, n, a->type );
|
||||
}
|
||||
|
||||
if( mmul.alpha == 1 )
|
||||
{
|
||||
if( mmul.t_ab == 0 )
|
||||
{
|
||||
cvMatMulAdd( a, b, 0, this );
|
||||
return *this;
|
||||
}
|
||||
|
||||
if( a->data.ptr == b->data.ptr && mmul.t_ab < 3 &&
|
||||
a->rows == b->rows && a->cols == b->cols &&
|
||||
a->data.ptr != data.ptr )
|
||||
{
|
||||
cvMulTransposed( a, this, mmul.t_ab & 1 );
|
||||
return *this;
|
||||
}
|
||||
}
|
||||
|
||||
cvGEMM( a, b, mmul.alpha, 0, 0, this, mmul.t_ab );
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
||||
CvMAT& CvMAT::operator = ( const _CvMAT_MUL_ADD_& mmuladd )
|
||||
{
|
||||
CvMAT* a = mmuladd.a;
|
||||
CvMAT* b = mmuladd.b;
|
||||
CvMAT* c = mmuladd.c;
|
||||
int t_a = mmuladd.t_abc & 1;
|
||||
int t_b = (mmuladd.t_abc & 2) != 0;
|
||||
int m = (&(a->rows))[t_a];
|
||||
int n = (&(b->rows))[t_b ^ 1];
|
||||
/* this(m x n) = (a^o1(t))(m x l) * (b^o2(t))(l x n) */
|
||||
|
||||
if( !data.ptr )
|
||||
{
|
||||
create( m, n, a->type );
|
||||
}
|
||||
|
||||
if( mmuladd.t_abc == 0 && mmuladd.alpha == 1 && mmuladd.beta == 1 )
|
||||
cvMatMulAdd( a, b, c, this );
|
||||
else
|
||||
cvGEMM( a, b, mmuladd.alpha, c, mmuladd.beta, this, mmuladd.t_abc );
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
||||
CvMAT& CvMAT::operator = ( const _CvMAT_INV_& inv_mat )
|
||||
{
|
||||
CvMAT* src = (CvMAT*)&inv_mat.a;
|
||||
|
||||
if( !data.ptr )
|
||||
{
|
||||
create( src->height, src->width, src->type );
|
||||
}
|
||||
|
||||
if( inv_mat.method == 0 )
|
||||
cvInvert( src, this );
|
||||
else
|
||||
cvPseudoInv( src, this );
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
||||
CvMAT& CvMAT::operator = ( const _CvMAT_NOT_& not_mat )
|
||||
{
|
||||
CvMAT* src = not_mat.a;
|
||||
|
||||
if( !data.ptr )
|
||||
{
|
||||
create( src->height, src->width, src->type );
|
||||
}
|
||||
|
||||
cvNot( src, this );
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
||||
CvMAT& CvMAT::operator = ( const _CvMAT_LOGIC_& mat_logic )
|
||||
{
|
||||
CvMAT* a = mat_logic.a;
|
||||
CvMAT* b = mat_logic.b;
|
||||
int flags = mat_logic.flags;
|
||||
_CvMAT_LOGIC_::Op op = mat_logic.op;
|
||||
|
||||
if( !data.ptr )
|
||||
{
|
||||
create( a->height, a->width, a->type );
|
||||
}
|
||||
|
||||
switch( op )
|
||||
{
|
||||
case _CvMAT_LOGIC_::AND:
|
||||
|
||||
if( flags == 0 )
|
||||
cvAnd( a, b, this );
|
||||
else if( flags == 3 )
|
||||
{
|
||||
cvOr( a, b, this );
|
||||
cvNot( this, this );
|
||||
}
|
||||
else if( flags == 1 )
|
||||
{
|
||||
if( data.ptr == b->data.ptr )
|
||||
{
|
||||
cvNot( b, this );
|
||||
cvOr( this, a, this );
|
||||
cvNot( this, this );
|
||||
}
|
||||
else
|
||||
{
|
||||
cvNot( a, this );
|
||||
cvAnd( this, b, this );
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if( data.ptr == a->data.ptr )
|
||||
{
|
||||
cvNot( a, this );
|
||||
cvOr( this, b, this );
|
||||
cvNot( this, this );
|
||||
}
|
||||
else
|
||||
{
|
||||
cvNot( b, this );
|
||||
cvAnd( this, a, this );
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
case _CvMAT_LOGIC_::OR:
|
||||
|
||||
if( flags == 0 )
|
||||
cvOr( a, b, this );
|
||||
else if( flags == 3 )
|
||||
{
|
||||
cvAnd( a, b, this );
|
||||
cvNot( this, this );
|
||||
}
|
||||
else if( flags == 1 )
|
||||
{
|
||||
if( data.ptr == b->data.ptr )
|
||||
{
|
||||
cvNot( b, this );
|
||||
cvAnd( this, a, this );
|
||||
cvNot( this, this );
|
||||
}
|
||||
else
|
||||
{
|
||||
cvNot( a, this );
|
||||
cvOr( this, b, this );
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if( data.ptr == a->data.ptr )
|
||||
{
|
||||
cvNot( a, this );
|
||||
cvAnd( this, b, this );
|
||||
cvNot( this, this );
|
||||
}
|
||||
else
|
||||
{
|
||||
cvNot( b, this );
|
||||
cvOr( this, a, this );
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
case _CvMAT_LOGIC_::XOR:
|
||||
|
||||
cvXor( a, b, this );
|
||||
if( flags == 1 || flags == 2 )
|
||||
cvNot( this, this );
|
||||
break;
|
||||
}
|
||||
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
||||
CvMAT& CvMAT::operator = ( const _CvMAT_UN_LOGIC_& mat_logic )
|
||||
{
|
||||
CvMAT* a = mat_logic.a;
|
||||
CvScalar scalar = cvScalarAll( mat_logic.alpha );
|
||||
int flags = mat_logic.flags;
|
||||
_CvMAT_LOGIC_::Op op = mat_logic.op;
|
||||
|
||||
if( !data.ptr )
|
||||
{
|
||||
create( a->height, a->width, a->type );
|
||||
}
|
||||
|
||||
switch( op )
|
||||
{
|
||||
case _CvMAT_LOGIC_::AND:
|
||||
|
||||
if( flags == 0 )
|
||||
cvAndS( a, scalar, this );
|
||||
else
|
||||
{
|
||||
cvNot( a, this );
|
||||
cvAndS( this, scalar, this );
|
||||
}
|
||||
break;
|
||||
|
||||
case _CvMAT_LOGIC_::OR:
|
||||
|
||||
if( flags == 0 )
|
||||
cvOrS( a, scalar, this );
|
||||
else
|
||||
{
|
||||
cvNot( a, this );
|
||||
cvOrS( this, scalar, this );
|
||||
}
|
||||
break;
|
||||
|
||||
case _CvMAT_LOGIC_::XOR:
|
||||
|
||||
if( flags == 0 )
|
||||
cvXorS( a, scalar, this );
|
||||
else
|
||||
cvXorS( a, ~scalar, this );
|
||||
break;
|
||||
}
|
||||
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
||||
CvMAT& CvMAT::operator = ( const _CvMAT_COPY_& mat_copy )
|
||||
{
|
||||
CvMAT* src = (CvMAT*)mat_copy.a;
|
||||
|
||||
if( !data.ptr )
|
||||
{
|
||||
create( src->height, src->width, src->type );
|
||||
}
|
||||
|
||||
if( src != this )
|
||||
cvCopy( src, this );
|
||||
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
||||
CvMAT& CvMAT::operator = ( const _CvMAT_CVT_& mat_cvt )
|
||||
{
|
||||
CvMAT* src = (CvMAT*)&mat_cvt.a;
|
||||
|
||||
if( !data.ptr )
|
||||
{
|
||||
int depth = mat_cvt.newdepth;
|
||||
create( src->height, src->width, depth < 0 ? src->type :
|
||||
CV_MAT_CN(src->type)|CV_MAT_DEPTH(depth));
|
||||
}
|
||||
|
||||
cvCvtScale( src, this, mat_cvt.scale, mat_cvt.shift );
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
||||
CvMAT& CvMAT::operator = ( const _CvMAT_DOT_OP_& dot_op )
|
||||
{
|
||||
CvMAT* a = (CvMAT*)&(dot_op.a);
|
||||
CvMAT* b = dot_op.b;
|
||||
|
||||
if( !data.ptr )
|
||||
{
|
||||
create( a->height, a->width, a->type );
|
||||
}
|
||||
|
||||
switch( dot_op.op )
|
||||
{
|
||||
case '*':
|
||||
cvMul( a, b, this, dot_op.alpha );
|
||||
break;
|
||||
case '/':
|
||||
if( b != 0 )
|
||||
cvDiv( a, b, this, dot_op.alpha );
|
||||
else
|
||||
cvDiv( 0, a, this, dot_op.alpha );
|
||||
break;
|
||||
case 'm':
|
||||
if( b != 0 )
|
||||
cvMin( a, b, this );
|
||||
else
|
||||
cvMinS( a, dot_op.alpha, this );
|
||||
break;
|
||||
case 'M':
|
||||
if( b != 0 )
|
||||
cvMax( a, b, this );
|
||||
else
|
||||
cvMaxS( a, dot_op.alpha, this );
|
||||
break;
|
||||
case 'a':
|
||||
if( b != 0 )
|
||||
cvAbsDiff( a, b, this );
|
||||
else
|
||||
cvAbsDiffS( a, this, cvScalar(dot_op.alpha) );
|
||||
break;
|
||||
default:
|
||||
assert(0);
|
||||
}
|
||||
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
||||
CvMAT& CvMAT::operator = ( const _CvMAT_SOLVE_& solve_mat )
|
||||
{
|
||||
CvMAT* a = (CvMAT*)(solve_mat.a);
|
||||
CvMAT* b = (CvMAT*)(solve_mat.b);
|
||||
|
||||
if( !data.ptr )
|
||||
{
|
||||
create( a->height, b->width, a->type );
|
||||
}
|
||||
|
||||
if( solve_mat.method == 0 )
|
||||
cvSolve( a, b, this );
|
||||
else
|
||||
{
|
||||
CvMAT temp;
|
||||
cvInitMatHeader( &temp, a->cols, a->rows, a->type );
|
||||
cvCreateData( &temp );
|
||||
|
||||
cvPseudoInv( a, &temp );
|
||||
cvMatMul( &temp, b, this );
|
||||
}
|
||||
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
||||
CvMAT& CvMAT::operator = ( const _CvMAT_CMP_& mat_cmp )
|
||||
{
|
||||
CvMAT* a = mat_cmp.a;
|
||||
CvMAT* b = mat_cmp.b;
|
||||
|
||||
if( !data.ptr )
|
||||
{
|
||||
create( a->height, a->width, CV_8UC1 );
|
||||
}
|
||||
|
||||
if( b )
|
||||
cvCmp( a, b, this, mat_cmp.cmp_op );
|
||||
else
|
||||
cvCmpS( a, mat_cmp.alpha, this, mat_cmp.cmp_op );
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
||||
/****************************************************************************************\
|
||||
* CvMAT I/O operations *
|
||||
\****************************************************************************************/
|
||||
|
||||
void CvMAT::write( const char* name, FILE* f, const char* fmt )
|
||||
{
|
||||
int i, j, w = width * CV_MAT_CN(type);
|
||||
FILE* out = f ? f : stdout;
|
||||
|
||||
if( name )
|
||||
fprintf( stdout, "%s(%d x %d) =\n\t", name, rows, cols );
|
||||
|
||||
for( i = 0; i < rows; i++ )
|
||||
{
|
||||
switch( CV_MAT_DEPTH(type))
|
||||
{
|
||||
case CV_8U: if( !fmt )
|
||||
fmt = "%4d";
|
||||
for( j = 0; j < w; j++ )
|
||||
fprintf( out, fmt, ((uchar*)(data.ptr + i*step))[j] );
|
||||
break;
|
||||
case CV_8S: if( !fmt )
|
||||
fmt = "%5d";
|
||||
for( j = 0; j < w; j++ )
|
||||
fprintf( out, fmt, ((char*)(data.ptr + i*step))[j] );
|
||||
break;
|
||||
case CV_16S: if( !fmt )
|
||||
fmt = "%7d";
|
||||
for( j = 0; j < w; j++ )
|
||||
fprintf( out, fmt, ((short*)(data.ptr + i*step))[j] );
|
||||
break;
|
||||
case CV_32S: if( !fmt )
|
||||
fmt = " %08x";
|
||||
for( j = 0; j < w; j++ )
|
||||
fprintf( out, fmt, ((int*)(data.ptr + i*step))[j] );
|
||||
break;
|
||||
case CV_32F: if( !fmt )
|
||||
fmt = "%15g";
|
||||
for( j = 0; j < w; j++ )
|
||||
fprintf( out, fmt, ((float*)(data.ptr + i*step))[j] );
|
||||
break;
|
||||
case CV_64F: if( !fmt )
|
||||
fmt = "%15g";
|
||||
for( j = 0; j < w; j++ )
|
||||
fprintf( out, fmt, ((double*)(data.ptr + i*step))[j] );
|
||||
break;
|
||||
}
|
||||
fprintf( out, "\n%s", i < rows - 1 ? "\t" : "" );
|
||||
}
|
||||
fprintf( out, "\n" );
|
||||
}
|
||||
|
||||
#endif /* _MSC_VER || __BORLANDC__ */
|
||||
|
||||
/* End of file. */
|
||||
|
||||
|
||||
@@ -0,0 +1,855 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
#define PATH_TO_E 1
|
||||
#define PATH_TO_SE 2
|
||||
#define PATH_TO_S 3
|
||||
|
||||
#define K_S 2
|
||||
#define E_S 2
|
||||
#define C_S .01
|
||||
#define K_Z 5000
|
||||
#define K_NM 50000
|
||||
#define K_B 40
|
||||
#define NULL_EDGE 0.001f
|
||||
#define inf DBL_MAX
|
||||
|
||||
typedef struct __CvWork
|
||||
{
|
||||
double w_east;
|
||||
double w_southeast;
|
||||
double w_south;
|
||||
char path_e;
|
||||
char path_se;
|
||||
char path_s;
|
||||
}_CvWork;
|
||||
|
||||
|
||||
double _cvBendingWork( CvPoint2D32f* B0,
|
||||
CvPoint2D32f* F0,
|
||||
CvPoint2D32f* B1,
|
||||
CvPoint2D32f* F1/*,
|
||||
CvPoint* K */);
|
||||
|
||||
double _cvStretchingWork(CvPoint2D32f* P1,
|
||||
CvPoint2D32f* P2);
|
||||
|
||||
void _cvWorkEast (int i, int j, _CvWork** W, CvPoint2D32f* edges1, CvPoint2D32f* edges2);
|
||||
void _cvWorkSouthEast(int i, int j, _CvWork** W, CvPoint2D32f* edges1, CvPoint2D32f* edges2);
|
||||
void _cvWorkSouth (int i, int j, _CvWork** W, CvPoint2D32f* edges1, CvPoint2D32f* edges2);
|
||||
|
||||
static CvPoint2D32f null_edge = {0,0};
|
||||
|
||||
double _cvStretchingWork(CvPoint2D32f* P1,
|
||||
CvPoint2D32f* P2)
|
||||
{
|
||||
double L1,L2, L_min, dL;
|
||||
|
||||
L1 = sqrt( (double)P1->x*P1->x + P1->y*P1->y);
|
||||
L2 = sqrt( (double)P2->x*P2->x + P2->y*P2->y);
|
||||
|
||||
L_min = MIN(L1, L2);
|
||||
dL = fabs( L1 - L2 );
|
||||
|
||||
return K_S * pow( dL, E_S ) / ( L_min + C_S*dL );
|
||||
}
|
||||
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////
|
||||
double _cvBendingWork( CvPoint2D32f* B0,
|
||||
CvPoint2D32f* F0,
|
||||
CvPoint2D32f* B1,
|
||||
CvPoint2D32f* F1/*,
|
||||
CvPoint* K*/)
|
||||
{
|
||||
CvPoint2D32f Q( CvPoint2D32f q0, CvPoint2D32f q1, CvPoint2D32f q2, double t );
|
||||
double angle( CvPoint2D32f A, CvPoint2D32f B );
|
||||
|
||||
CvPoint2D32f Q0, Q1, Q2;
|
||||
CvPoint2D32f Q1_nm = { 0, 0 }, Q2_nm = { 0, 0 };
|
||||
double d0, d1, d2, des, t_zero;
|
||||
double k_zero, k_nonmon;
|
||||
CvPoint2D32f center;
|
||||
double check01, check02;
|
||||
char check_origin;
|
||||
double d_angle, d_nm_angle;
|
||||
/*
|
||||
if( (B0->x==0) && (B0->y==0) )
|
||||
{
|
||||
if( (F0->x==0) && (F0->y==0) )
|
||||
{
|
||||
B1->x = -B1->x;
|
||||
B1->y = -B1->y;
|
||||
|
||||
d_angle = acos( (B1->x*F1->x + B1->y*F1->y)/sqrt( (B1->x*B1->x + B1->y*B1->y)*(F1->x*F1->x + F1->y*F1->y) ) );
|
||||
d_angle = CV_PI - d_angle;
|
||||
|
||||
B1->x = -B1->x;
|
||||
B1->y = -B1->y;
|
||||
|
||||
//return d_angle*K_B;
|
||||
return 100;
|
||||
}
|
||||
K->x = -K->x;
|
||||
K->y = -K->y;
|
||||
B1->x = -B1->x;
|
||||
B1->y = -B1->y;
|
||||
|
||||
d_angle = acos( (B1->x*F1->x + B1->y*F1->y)/sqrt( (B1->x*B1->x + B1->y*B1->y)*(F1->x*F1->x + F1->y*F1->y) ) );
|
||||
d_angle = d_angle - acos( (F0->x*K->x + F0->y*K->y)/sqrt( (F0->x*F0->x + F0->y*F0->y)*(K->x*K->x + K->y*K->y) ) );
|
||||
d_angle = d_angle - CV_PI*0.5;
|
||||
d_angle = fabs(d_angle);
|
||||
|
||||
|
||||
K->x = -K->x;
|
||||
K->y = -K->y;
|
||||
B1->x = -B1->x;
|
||||
B1->y = -B1->y;
|
||||
|
||||
//return d_angle*K_B;
|
||||
return 100;
|
||||
}
|
||||
|
||||
|
||||
if( (F0->x==0) && (F0->y==0) )
|
||||
{
|
||||
K->x = -K->x;
|
||||
K->y = -K->y;
|
||||
B1->x = -B1->x;
|
||||
B1->y = -B1->y;
|
||||
|
||||
d_angle = acos( (B1->x*F1->x + B1->y*F1->y)/sqrt( (B1->x*B1->x + B1->y*B1->y)*(F1->x*F1->x + F1->y*F1->y) ) );
|
||||
d_angle = d_angle - acos( (B0->x*K->x + B0->y*K->y)/sqrt( (B0->x*B0->x + B0->y*B0->y)*(K->x*K->x + K->y*K->y) ) );
|
||||
d_angle = d_angle - CV_PI*0.5;
|
||||
d_angle = fabs(d_angle);
|
||||
|
||||
K->x = -K->x;
|
||||
K->y = -K->y;
|
||||
B1->x = -B1->x;
|
||||
B1->y = -B1->y;
|
||||
|
||||
//return d_angle*K_B;
|
||||
return 100;
|
||||
}
|
||||
///////////////
|
||||
|
||||
if( (B1->x==0) && (B1->y==0) )
|
||||
{
|
||||
if( (F1->x==0) && (F1->y==0) )
|
||||
{
|
||||
B0->x = -B0->x;
|
||||
B0->y = -B0->y;
|
||||
|
||||
d_angle = acos( (B0->x*F0->x + B0->y*F0->y)/sqrt( (B0->x*B0->x + B0->y*B0->y)*(F0->x*F0->x + F0->y*F0->y) ) );
|
||||
d_angle = CV_PI - d_angle;
|
||||
|
||||
B0->x = -B0->x;
|
||||
B0->y = -B0->y;
|
||||
|
||||
//return d_angle*K_B;
|
||||
return 100;
|
||||
}
|
||||
K->x = -K->x;
|
||||
K->y = -K->y;
|
||||
B0->x = -B0->x;
|
||||
B0->y = -B0->y;
|
||||
|
||||
d_angle = acos( (B0->x*F0->x + B0->y*F0->y)/sqrt( (B0->x*B0->x + B0->y*B0->y)*(F0->x*F0->x + F0->y*F0->y) ) );
|
||||
d_angle = d_angle - acos( (F1->x*K->x + F1->y*K->y)/sqrt( (F1->x*F1->x + F1->y*F1->y)*(K->x*K->x + K->y*K->y) ) );
|
||||
d_angle = d_angle - CV_PI*0.5;
|
||||
d_angle = fabs(d_angle);
|
||||
|
||||
K->x = -K->x;
|
||||
K->y = -K->y;
|
||||
B0->x = -B0->x;
|
||||
B0->y = -B0->y;
|
||||
|
||||
//return d_angle*K_B;
|
||||
return 100;
|
||||
}
|
||||
|
||||
|
||||
if( (F1->x==0) && (F1->y==0) )
|
||||
{
|
||||
K->x = -K->x;
|
||||
K->y = -K->y;
|
||||
B0->x = -B0->x;
|
||||
B0->y = -B0->y;
|
||||
|
||||
d_angle = acos( (B0->x*F0->x + B0->y*F0->y)/sqrt( (B0->x*B0->x + B0->y*B0->y)*(F0->x*F0->x + F0->y*F0->y) ) );
|
||||
d_angle = d_angle - acos( (B1->x*K->x + B1->y*K->y)/sqrt( (B1->x*B1->x + B1->y*B1->y)*(K->x*K->x + K->y*K->y) ) );
|
||||
d_angle = d_angle - CV_PI*0.5;
|
||||
d_angle = fabs(d_angle);
|
||||
|
||||
K->x = -K->x;
|
||||
K->y = -K->y;
|
||||
B0->x = -B0->x;
|
||||
B0->y = -B0->y;
|
||||
|
||||
//return d_angle*K_B;
|
||||
return 100;
|
||||
}
|
||||
|
||||
*/
|
||||
|
||||
/*
|
||||
B0->x = -B0->x;
|
||||
B0->y = -B0->y;
|
||||
B1->x = -B1->x;
|
||||
B1->y = -B1->y;
|
||||
*/
|
||||
Q0.x = F0->x * (-B0->x) + F0->y * (-B0->y);
|
||||
Q0.y = F0->x * (-B0->y) - F0->y * (-B0->x);
|
||||
|
||||
Q1.x = 0.5f*( (F1->x * (-B0->x) + F1->y * (-B0->y)) + (F0->x * (-B1->x) + F0->y * (-B1->y)) );
|
||||
Q1.y = 0.5f*( (F1->x * (-B0->y) - F1->y * (-B0->x)) + (F0->x * (-B1->y) - F0->y * (-B1->x)) );
|
||||
|
||||
Q2.x = F1->x * (-B1->x) + F1->y * (-B1->y);
|
||||
Q2.y = F1->x * (-B1->y) - F1->y * (-B1->x);
|
||||
|
||||
d0 = Q0.x * Q1.y - Q0.y * Q1.x;
|
||||
d1 = 0.5f*(Q0.x * Q2.y - Q0.y * Q2.x);
|
||||
d2 = Q1.x * Q2.y - Q1.y * Q2.x;
|
||||
|
||||
// Check angles goes to zero
|
||||
des = Q1.y*Q1.y - Q0.y*Q2.y;
|
||||
|
||||
k_zero = 0;
|
||||
|
||||
if( des >= 0 )
|
||||
{
|
||||
t_zero = ( Q0.y - Q1.y + sqrt(des) )/( Q0.y - 2*Q1.y + Q2.y );
|
||||
|
||||
if( (0 < t_zero) && (t_zero < 1) && ( Q(Q0, Q1, Q2, t_zero).x > 0 ) )
|
||||
{
|
||||
k_zero = inf;
|
||||
}
|
||||
|
||||
t_zero = ( Q0.y - Q1.y - sqrt(des) )/( Q0.y - 2*Q1.y + Q2.y );
|
||||
|
||||
if( (0 < t_zero) && (t_zero < 1) && ( Q(Q0, Q1, Q2, t_zero).x > 0 ) )
|
||||
{
|
||||
k_zero = inf;
|
||||
}
|
||||
}
|
||||
|
||||
// Check nonmonotonic
|
||||
des = d1*d1 - d0*d2;
|
||||
|
||||
k_nonmon = 0;
|
||||
|
||||
if( des >= 0 )
|
||||
{
|
||||
t_zero = ( d0 - d1 - sqrt(des) )/( d0 - 2*d1 + d2 );
|
||||
|
||||
if( (0 < t_zero) && (t_zero < 1) )
|
||||
{
|
||||
k_nonmon = 1;
|
||||
Q1_nm = Q(Q0, Q1, Q2, t_zero);
|
||||
}
|
||||
|
||||
t_zero = ( d0 - d1 + sqrt(des) )/( d0 - 2*d1 + d2 );
|
||||
|
||||
if( (0 < t_zero) && (t_zero < 1) )
|
||||
{
|
||||
k_nonmon += 2;
|
||||
Q2_nm = Q(Q0, Q1, Q2, t_zero);
|
||||
}
|
||||
}
|
||||
|
||||
// Finde origin lie in Q0Q1Q2
|
||||
check_origin = 1;
|
||||
|
||||
center.x = (Q0.x + Q1.x + Q2.x)/3;
|
||||
center.y = (Q0.y + Q1.y + Q2.y)/3;
|
||||
|
||||
check01 = (center.x - Q0.x)*(Q1.y - Q0.y) + (center.y - Q0.y)*(Q1.x - Q0.x);
|
||||
check02 = (-Q0.x)*(Q1.y - Q0.y) + (-Q0.y)*(Q1.x - Q0.x);
|
||||
if( check01*check02 > 0 )
|
||||
{
|
||||
check01 = (center.x - Q1.x)*(Q2.y - Q1.y) + (center.y - Q1.y)*(Q2.x - Q1.x);
|
||||
check02 = (-Q1.x)*(Q2.y - Q1.y) + (-Q1.y)*(Q2.x - Q1.x);
|
||||
if( check01*check02 > 0 )
|
||||
{
|
||||
check01 = (center.x - Q2.x)*(Q0.y - Q2.y) + (center.y - Q2.y)*(Q0.x - Q2.x);
|
||||
check02 = (-Q2.x)*(Q0.y - Q2.y) + (-Q2.y)*(Q0.x - Q2.x);
|
||||
if( check01*check02 > 0 )
|
||||
{
|
||||
check_origin = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Calculate angle
|
||||
d_nm_angle = 0;
|
||||
d_angle = angle(Q0,Q2);
|
||||
if( k_nonmon == 0 )
|
||||
{
|
||||
if( check_origin == 0 )
|
||||
{
|
||||
}
|
||||
else
|
||||
{
|
||||
d_angle = 2*CV_PI - d_angle;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if( k_nonmon == 1 )
|
||||
{
|
||||
d_nm_angle = angle(Q0,Q1_nm);
|
||||
if(d_nm_angle > d_angle)
|
||||
{
|
||||
d_nm_angle = d_nm_angle - d_angle;
|
||||
}
|
||||
}
|
||||
|
||||
if( k_nonmon == 2 )
|
||||
{
|
||||
d_nm_angle = angle(Q0,Q2_nm);
|
||||
if(d_nm_angle > d_angle)
|
||||
{
|
||||
d_nm_angle = d_nm_angle - d_angle;
|
||||
}
|
||||
}
|
||||
|
||||
if( k_nonmon == 3 )
|
||||
{
|
||||
d_nm_angle = angle(Q0,Q1_nm);
|
||||
if(d_nm_angle > d_angle)
|
||||
{
|
||||
d_nm_angle = d_nm_angle - d_angle;
|
||||
d_nm_angle = d_nm_angle + angle(Q0, Q2_nm);
|
||||
}
|
||||
else
|
||||
{
|
||||
d_nm_angle = d_nm_angle + angle(Q2,Q2_nm);
|
||||
}
|
||||
}
|
||||
}
|
||||
/*
|
||||
B0->x = -B0->x;
|
||||
B0->y = -B0->y;
|
||||
B1->x = -B1->x;
|
||||
B1->y = -B1->y;
|
||||
*/
|
||||
return d_angle*K_B + d_nm_angle*K_NM + k_zero*K_Z;
|
||||
//return 0;
|
||||
}
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////
|
||||
void _cvWorkEast(int i, int j, _CvWork** W, CvPoint2D32f* edges1, CvPoint2D32f* edges2)
|
||||
{
|
||||
double w1,w2;
|
||||
CvPoint2D32f small_edge;
|
||||
|
||||
//W[i,j].w_east
|
||||
w1 = W[i-1][j].w_east /*+ _cvBendingWork( &edges1[i-2],
|
||||
&edges1[i-1],
|
||||
&null_edge ,
|
||||
&null_edge,
|
||||
NULL)*/;
|
||||
|
||||
small_edge.x = NULL_EDGE*edges1[i-1].x;
|
||||
small_edge.y = NULL_EDGE*edges1[i-1].y;
|
||||
|
||||
w2 = W[i-1][j].w_southeast + _cvBendingWork(&edges1[i-2],
|
||||
&edges1[i-1],
|
||||
&edges2[j-1],
|
||||
/*&null_edge*/&small_edge/*,
|
||||
&edges2[j]*/);
|
||||
|
||||
if(w1<w2)
|
||||
{
|
||||
W[i][j].w_east = w1 + _cvStretchingWork( &edges1[i-1], &null_edge );
|
||||
W[i][j].path_e = PATH_TO_E;
|
||||
}
|
||||
else
|
||||
{
|
||||
W[i][j].w_east = w2 + _cvStretchingWork( &edges1[i-1], &null_edge );
|
||||
W[i][j].path_e = PATH_TO_SE;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////
|
||||
void _cvWorkSouthEast(int i, int j, _CvWork** W, CvPoint2D32f* edges1, CvPoint2D32f* edges2)
|
||||
{
|
||||
double w1,w2,w3;
|
||||
CvPoint2D32f small_edge;
|
||||
|
||||
//W[i,j].w_southeast
|
||||
small_edge.x = NULL_EDGE*edges1[i-2].x;
|
||||
small_edge.y = NULL_EDGE*edges1[i-2].y;
|
||||
|
||||
w1 = W[i-1][j-1].w_east + _cvBendingWork(&edges1[i-2],
|
||||
&edges1[i-1],
|
||||
/*&null_edge*/&small_edge,
|
||||
&edges2[j-1]/*,
|
||||
&edges2[j-2]*/);
|
||||
|
||||
w2 = W[i-1][j-1].w_southeast + _cvBendingWork( &edges1[i-2],
|
||||
&edges1[i-1],
|
||||
&edges2[j-2],
|
||||
&edges2[j-1]/*,
|
||||
NULL*/);
|
||||
|
||||
small_edge.x = NULL_EDGE*edges2[j-2].x;
|
||||
small_edge.y = NULL_EDGE*edges2[j-2].y;
|
||||
|
||||
w3 = W[i-1][j-1].w_south + _cvBendingWork( /*&null_edge*/&small_edge,
|
||||
&edges1[i-1],
|
||||
&edges2[j-2],
|
||||
&edges2[j-1]/*,
|
||||
&edges1[i-2]*/);
|
||||
|
||||
if( w1<w2 )
|
||||
{
|
||||
if(w1<w3)
|
||||
{
|
||||
W[i][j].w_southeast = w1 + _cvStretchingWork( &edges1[i-1], &edges2[j-1] );
|
||||
W[i][j].path_se = PATH_TO_E;
|
||||
}
|
||||
else
|
||||
{
|
||||
W[i][j].w_southeast = w3 + _cvStretchingWork( &edges1[i-1], &edges2[j-1] );
|
||||
W[i][j].path_se = 3;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if( w2<w3)
|
||||
{
|
||||
W[i][j].w_southeast = w2 + _cvStretchingWork( &edges1[i-1], &edges2[j-1] );
|
||||
W[i][j].path_se = PATH_TO_SE;
|
||||
}
|
||||
else
|
||||
{
|
||||
W[i][j].w_southeast = w3 + _cvStretchingWork( &edges1[i-1], &edges2[j-1] );
|
||||
W[i][j].path_se = 3;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////////////
|
||||
void _cvWorkSouth(int i, int j, _CvWork** W, CvPoint2D32f* edges1, CvPoint2D32f* edges2)
|
||||
{
|
||||
double w1,w2;
|
||||
CvPoint2D32f small_edge;
|
||||
|
||||
//W[i,j].w_south
|
||||
|
||||
small_edge.x = NULL_EDGE*edges2[j-1].x;
|
||||
small_edge.y = NULL_EDGE*edges2[j-1].y;
|
||||
|
||||
w1 = W[i][j-1].w_southeast + _cvBendingWork(&edges1[i-1],
|
||||
/*&null_edge*/&small_edge,
|
||||
&edges2[j-2],
|
||||
&edges2[j-1]/*,
|
||||
&edges1[i]*/);
|
||||
|
||||
w2 = W[i][j-1].w_south /*+ _cvBendingWork( &null_edge ,
|
||||
&null_edge,
|
||||
&edges2[j-2],
|
||||
&edges2[j-1],
|
||||
NULL)*/;
|
||||
|
||||
if( w1<w2 )
|
||||
{
|
||||
W[i][j].w_south = w1 + _cvStretchingWork( &null_edge, &edges2[j-1] );
|
||||
W[i][j].path_s = PATH_TO_SE;
|
||||
}
|
||||
else
|
||||
{
|
||||
W[i][j].w_south = w2 + _cvStretchingWork( &null_edge, &edges2[j-1] );
|
||||
W[i][j].path_s = 3;
|
||||
}
|
||||
}
|
||||
|
||||
//===================================================
|
||||
CvPoint2D32f Q(CvPoint2D32f q0,CvPoint2D32f q1,CvPoint2D32f q2,double t)
|
||||
{
|
||||
CvPoint2D32f q;
|
||||
|
||||
q.x = (float)(q0.x*(1-t)*(1-t) + 2*q1.x*t*(1-t) + q2.x*t*t);
|
||||
q.y = (float)(q0.y*(1-t)*(1-t) + 2*q1.y*t*(1-t) + q2.y*t*t);
|
||||
|
||||
return q;
|
||||
}
|
||||
|
||||
double angle(CvPoint2D32f A, CvPoint2D32f B)
|
||||
{
|
||||
return acos( (A.x*B.x + A.y*B.y)/sqrt( (double)(A.x*A.x + A.y*A.y)*(B.x*B.x + B.y*B.y) ) );
|
||||
}
|
||||
|
||||
/***************************************************************************************\
|
||||
*
|
||||
* This function compute intermediate polygon between contour1 and contour2
|
||||
*
|
||||
* Correspondence between points of contours specify by corr
|
||||
*
|
||||
* param = [0,1]; 0 correspondence to contour1, 1 - contour2
|
||||
*
|
||||
\***************************************************************************************/
|
||||
CvSeq* icvBlendContours(CvSeq* contour1,
|
||||
CvSeq* contour2,
|
||||
CvSeq* corr,
|
||||
double param,
|
||||
CvMemStorage* storage)
|
||||
{
|
||||
int j;
|
||||
|
||||
CvSeqWriter writer01;
|
||||
CvSeqReader reader01;
|
||||
|
||||
int Ni,Nj; // size of contours
|
||||
int i; // counter
|
||||
|
||||
CvPoint* point1; // array of first contour point
|
||||
CvPoint* point2; // array of second contour point
|
||||
|
||||
CvPoint point_output; // intermediate storage of ouput point
|
||||
|
||||
int corr_point;
|
||||
|
||||
// Create output sequence.
|
||||
CvSeq* output = cvCreateSeq(0,
|
||||
sizeof(CvSeq),
|
||||
sizeof(CvPoint),
|
||||
storage );
|
||||
|
||||
// Find size of contours.
|
||||
Ni = contour1->total + 1;
|
||||
Nj = contour2->total + 1;
|
||||
|
||||
point1 = (CvPoint* )malloc( Ni*sizeof(CvPoint) );
|
||||
point2 = (CvPoint* )malloc( Nj*sizeof(CvPoint) );
|
||||
|
||||
// Initialize arrays of point
|
||||
cvCvtSeqToArray( contour1, point1, CV_WHOLE_SEQ );
|
||||
cvCvtSeqToArray( contour2, point2, CV_WHOLE_SEQ );
|
||||
|
||||
// First and last point mast be equal.
|
||||
point1[Ni-1] = point1[0];
|
||||
point2[Nj-1] = point2[0];
|
||||
|
||||
// Initializes process of writing to sequence.
|
||||
cvStartAppendToSeq( output, &writer01);
|
||||
|
||||
i = Ni-1; //correspondence to points of contour1
|
||||
for( ; corr; corr = corr->h_next )
|
||||
{
|
||||
//Initializes process of sequential reading from sequence
|
||||
cvStartReadSeq( corr, &reader01, 0 );
|
||||
|
||||
for(j=0; j < corr->total; j++)
|
||||
{
|
||||
// Read element from sequence.
|
||||
CV_READ_SEQ_ELEM( corr_point, reader01 );
|
||||
|
||||
// Compute point of intermediate polygon.
|
||||
point_output.x = cvRound(point1[i].x + param*( point2[corr_point].x - point1[i].x ));
|
||||
point_output.y = cvRound(point1[i].y + param*( point2[corr_point].y - point1[i].y ));
|
||||
|
||||
// Write element to sequence.
|
||||
CV_WRITE_SEQ_ELEM( point_output, writer01 );
|
||||
}
|
||||
i--;
|
||||
}
|
||||
// Updates sequence header.
|
||||
cvFlushSeqWriter( &writer01 );
|
||||
|
||||
return output;
|
||||
}
|
||||
|
||||
/**************************************************************************************************
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
**************************************************************************************************/
|
||||
|
||||
|
||||
void icvCalcContoursCorrespondence(CvSeq* contour1,
|
||||
CvSeq* contour2,
|
||||
CvSeq** corr,
|
||||
CvMemStorage* storage)
|
||||
{
|
||||
int i,j; // counter of cycles
|
||||
int Ni,Nj; // size of contours
|
||||
_CvWork** W; // graph for search minimum of work
|
||||
|
||||
CvPoint* point1; // array of first contour point
|
||||
CvPoint* point2; // array of second contour point
|
||||
CvPoint2D32f* edges1; // array of first contour edge
|
||||
CvPoint2D32f* edges2; // array of second contour edge
|
||||
|
||||
//CvPoint null_edge = {0,0}; //
|
||||
CvPoint2D32f small_edge;
|
||||
//double inf; // infinity
|
||||
|
||||
CvSeq* corr01;
|
||||
CvSeqWriter writer;
|
||||
|
||||
char path; //
|
||||
|
||||
// Find size of contours
|
||||
Ni = contour1->total + 1;
|
||||
Nj = contour2->total + 1;
|
||||
|
||||
// Create arrays
|
||||
W = (_CvWork**)malloc(sizeof(_CvWork*)*Ni);
|
||||
for(i=0; i<Ni; i++)
|
||||
{
|
||||
W[i] = (_CvWork*)malloc(sizeof(_CvWork)*Nj);
|
||||
}
|
||||
|
||||
point1 = (CvPoint* )malloc( Ni*sizeof(CvPoint) );
|
||||
point2 = (CvPoint* )malloc( Nj*sizeof(CvPoint) );
|
||||
edges1 = (CvPoint2D32f* )malloc( (Ni-1)*sizeof(CvPoint2D32f) );
|
||||
edges2 = (CvPoint2D32f* )malloc( (Nj-1)*sizeof(CvPoint2D32f) );
|
||||
|
||||
// Initialize arrays of point
|
||||
cvCvtSeqToArray( contour1, point1, CV_WHOLE_SEQ );
|
||||
cvCvtSeqToArray( contour2, point2, CV_WHOLE_SEQ );
|
||||
|
||||
point1[Ni-1] = point1[0];
|
||||
point2[Nj-1] = point2[0];
|
||||
|
||||
for(i=0;i<Ni-1;i++)
|
||||
{
|
||||
edges1[i].x = (float)( point1[i+1].x - point1[i].x );
|
||||
edges1[i].y = (float)( point1[i+1].y - point1[i].y );
|
||||
};
|
||||
|
||||
for(i=0;i<Nj-1;i++)
|
||||
{
|
||||
edges2[i].x = (float)( point2[i+1].x - point2[i].x );
|
||||
edges2[i].y = (float)( point2[i+1].y - point2[i].y );
|
||||
};
|
||||
|
||||
// Find infinity constant
|
||||
//inf=1;
|
||||
/////////////
|
||||
|
||||
//Find min path in graph
|
||||
|
||||
/////////////
|
||||
W[0][0].w_east = 0;
|
||||
W[0][0].w_south = 0;
|
||||
W[0][0].w_southeast = 0;
|
||||
|
||||
W[1][1].w_southeast = _cvStretchingWork( &edges1[0], &edges2[0] );
|
||||
W[1][1].w_east = inf;
|
||||
W[1][1].w_south = inf;
|
||||
W[1][1].path_se = PATH_TO_SE;
|
||||
|
||||
W[0][1].w_south = _cvStretchingWork( &null_edge, &edges2[0] );
|
||||
W[0][1].path_s = 3;
|
||||
W[1][0].w_east = _cvStretchingWork( &edges2[0], &null_edge );
|
||||
W[1][0].path_e = PATH_TO_E;
|
||||
|
||||
for( i=1; i<Ni; i++ )
|
||||
{
|
||||
W[i][0].w_south = inf;
|
||||
W[i][0].w_southeast = inf;
|
||||
}
|
||||
|
||||
for(j=1; j<Nj; j++)
|
||||
{
|
||||
W[0][j].w_east = inf;
|
||||
W[0][j].w_southeast = inf;
|
||||
}
|
||||
|
||||
for(i=2; i<Ni; i++)
|
||||
{
|
||||
j=0;/////////
|
||||
W[i][j].w_east = W[i-1][j].w_east;
|
||||
W[i][j].w_east = W[i][j].w_east /*+
|
||||
_cvBendingWork( &edges1[i-2], &edges1[i-1], &null_edge, &null_edge, NULL )*/;
|
||||
W[i][j].w_east = W[i][j].w_east + _cvStretchingWork( &edges2[i-1], &null_edge );
|
||||
W[i][j].path_e = PATH_TO_E;
|
||||
|
||||
j=1;//////////
|
||||
W[i][j].w_south = inf;
|
||||
|
||||
_cvWorkEast (i, j, W, edges1, edges2);
|
||||
|
||||
W[i][j].w_southeast = W[i-1][j-1].w_east;
|
||||
W[i][j].w_southeast = W[i][j].w_southeast + _cvStretchingWork( &edges1[i-1], &edges2[j-1] );
|
||||
|
||||
small_edge.x = NULL_EDGE*edges1[i-2].x;
|
||||
small_edge.y = NULL_EDGE*edges1[i-2].y;
|
||||
|
||||
W[i][j].w_southeast = W[i][j].w_southeast +
|
||||
_cvBendingWork( &edges1[i-2], &edges1[i-1], /*&null_edge*/&small_edge, &edges2[j-1]/*, &edges2[Nj-2]*/);
|
||||
|
||||
W[i][j].path_se = PATH_TO_E;
|
||||
}
|
||||
|
||||
for(j=2; j<Nj; j++)
|
||||
{
|
||||
i=0;//////////
|
||||
W[i][j].w_south = W[i][j-1].w_south;
|
||||
W[i][j].w_south = W[i][j].w_south + _cvStretchingWork( &null_edge, &edges2[j-1] );
|
||||
W[i][j].w_south = W[i][j].w_south /*+
|
||||
_cvBendingWork( &null_edge, &null_edge, &edges2[j-2], &edges2[j-1], NULL )*/;
|
||||
W[i][j].path_s = 3;
|
||||
|
||||
i=1;///////////
|
||||
W[i][j].w_east= inf;
|
||||
|
||||
_cvWorkSouth(i, j, W, edges1, edges2);
|
||||
|
||||
W[i][j].w_southeast = W[i-1][j-1].w_south;
|
||||
W[i][j].w_southeast = W[i][j].w_southeast + _cvStretchingWork( &edges1[i-1], &edges2[j-1] );
|
||||
|
||||
small_edge.x = NULL_EDGE*edges2[j-2].x;
|
||||
small_edge.y = NULL_EDGE*edges2[j-2].y;
|
||||
|
||||
W[i][j].w_southeast = W[i][j].w_southeast +
|
||||
_cvBendingWork( /*&null_edge*/&small_edge, &edges1[i-1], &edges2[j-2], &edges2[j-1]/*, &edges1[Ni-2]*/);
|
||||
W[i][j].path_se = 3;
|
||||
}
|
||||
|
||||
for(i=2; i<Ni; i++)
|
||||
for(j=2; j<Nj; j++)
|
||||
{
|
||||
_cvWorkEast (i, j, W, edges1, edges2);
|
||||
_cvWorkSouthEast(i, j, W, edges1, edges2);
|
||||
_cvWorkSouth (i, j, W, edges1, edges2);
|
||||
}
|
||||
|
||||
i=Ni-1;j=Nj-1;
|
||||
|
||||
*corr = cvCreateSeq(0,
|
||||
sizeof(CvSeq),
|
||||
sizeof(int),
|
||||
storage );
|
||||
|
||||
corr01 = *corr;
|
||||
cvStartAppendToSeq( corr01, &writer );
|
||||
if( W[i][j].w_east > W[i][j].w_southeast )
|
||||
{
|
||||
if( W[i][j].w_southeast > W[i][j].w_south )
|
||||
{
|
||||
path = 3;
|
||||
}
|
||||
else
|
||||
{
|
||||
path = PATH_TO_SE;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if( W[i][j].w_east < W[i][j].w_south )
|
||||
{
|
||||
path = PATH_TO_E;
|
||||
}
|
||||
else
|
||||
{
|
||||
path = 3;
|
||||
}
|
||||
}
|
||||
do
|
||||
{
|
||||
CV_WRITE_SEQ_ELEM( j, writer );
|
||||
|
||||
switch( path )
|
||||
{
|
||||
case PATH_TO_E:
|
||||
path = W[i][j].path_e;
|
||||
i--;
|
||||
cvFlushSeqWriter( &writer );
|
||||
corr01->h_next = cvCreateSeq( 0,
|
||||
sizeof(CvSeq),
|
||||
sizeof(int),
|
||||
storage );
|
||||
corr01 = corr01->h_next;
|
||||
cvStartAppendToSeq( corr01, &writer );
|
||||
break;
|
||||
|
||||
case PATH_TO_SE:
|
||||
path = W[i][j].path_se;
|
||||
j--; i--;
|
||||
cvFlushSeqWriter( &writer );
|
||||
corr01->h_next = cvCreateSeq( 0,
|
||||
sizeof(CvSeq),
|
||||
sizeof(int),
|
||||
storage );
|
||||
corr01 = corr01->h_next;
|
||||
cvStartAppendToSeq( corr01, &writer );
|
||||
break;
|
||||
|
||||
case 3:
|
||||
path = W[i][j].path_s;
|
||||
j--;
|
||||
break;
|
||||
}
|
||||
|
||||
} while( (i>=0) && (j>=0) );
|
||||
cvFlushSeqWriter( &writer );
|
||||
|
||||
// Free memory
|
||||
for(i=1;i<Ni;i++)
|
||||
{
|
||||
free(W[i]);
|
||||
}
|
||||
free(W);
|
||||
free(point1);
|
||||
free(point2);
|
||||
free(edges1);
|
||||
free(edges2);
|
||||
}
|
||||
|
||||
@@ -0,0 +1,396 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
#include "_cvaux.h"
|
||||
#include <assert.h>
|
||||
|
||||
|
||||
static CvStatus
|
||||
icvMorphEpilines8uC3( uchar * first_pix, /* raster epiline from image 1 */
|
||||
uchar * second_pix, /* raster epiline from image 2 */
|
||||
uchar * dst_pix, /* raster epiline from dest image */
|
||||
/* (it's an output parameter) */
|
||||
float alpha, /* relative position of camera */
|
||||
int *first, /* first sequence of runs */
|
||||
int first_runs, /* it's length */
|
||||
int *second, /* second sequence of runs */
|
||||
int second_runs, int *first_corr, /* corr data for the 1st seq */
|
||||
int *second_corr, /* corr data for the 2nd seq */
|
||||
int dst_len )
|
||||
{
|
||||
|
||||
float alpha1; /* alpha - 1.0 */
|
||||
int s, s1; /* integer variant of alpha and alpha1 ( 0 <= s,s1 <= 256 ) */
|
||||
int curr; /* current index in run's array */
|
||||
|
||||
float begLine; /* begin of current run */
|
||||
float endLine; /* end of current run */
|
||||
|
||||
float begCorr; /* begin of correspondence destination of run */
|
||||
float endCorr; /* end of correspondence destination of run */
|
||||
|
||||
int begDestLine; /* begin of current destanation of run */
|
||||
int endDestLine; /* end of current destanation of run */
|
||||
int begLineIndex;
|
||||
int endLineIndex;
|
||||
int indexImg1;
|
||||
float step = 0;
|
||||
int n;
|
||||
|
||||
memset( dst_pix, 0, dst_len );
|
||||
alpha1 = (float) (1.0 - alpha);
|
||||
|
||||
s = (int) (alpha * 256);
|
||||
s1 = 256 - s;
|
||||
|
||||
/* --------------Create first line------------- */
|
||||
|
||||
begLineIndex = first[0];
|
||||
begLine = (float) begLineIndex;
|
||||
|
||||
curr = 0;
|
||||
|
||||
for( n = 0; n < first_runs; n++ )
|
||||
{ /* for each run */
|
||||
|
||||
begCorr = (float) first_corr[curr];
|
||||
curr++;
|
||||
endCorr = (float) first_corr[curr];
|
||||
curr++;
|
||||
endLineIndex = first[curr];
|
||||
endLine = (float) endLineIndex;
|
||||
|
||||
begDestLine = (int) (alpha * begLine + alpha1 * begCorr);
|
||||
endDestLine = (int) (alpha * endLine + alpha1 * endCorr);
|
||||
|
||||
indexImg1 = begDestLine * 3;
|
||||
|
||||
step = 0;
|
||||
if( endDestLine != begDestLine )
|
||||
step = (endLine - begLine) / ((float) (endDestLine - begDestLine));
|
||||
|
||||
if( begCorr != endCorr )
|
||||
{
|
||||
|
||||
for( ; begDestLine < endDestLine; begDestLine++ )
|
||||
{
|
||||
/* for each pixel */
|
||||
|
||||
begLineIndex = (int) begLine;
|
||||
begLineIndex *= 3;
|
||||
|
||||
/* Blend R */
|
||||
dst_pix[indexImg1] = (uchar) (((int) (first_pix[begLineIndex]) * s) >> 8);
|
||||
|
||||
indexImg1++;
|
||||
|
||||
/* Blend G */
|
||||
dst_pix[indexImg1] = (uchar) (((int) (first_pix[begLineIndex + 1]) * s) >> 8);
|
||||
|
||||
indexImg1++;
|
||||
|
||||
/* Blend B */
|
||||
dst_pix[indexImg1] = (uchar) (((int) (first_pix[begLineIndex + 2]) * s) >> 8);
|
||||
|
||||
indexImg1++;
|
||||
|
||||
begLine += step;
|
||||
|
||||
} /* for */
|
||||
}
|
||||
else
|
||||
{
|
||||
|
||||
for( ; begDestLine < endDestLine; begDestLine++ )
|
||||
{
|
||||
/* for each pixel */
|
||||
|
||||
begLineIndex = (int) begLine;
|
||||
begLineIndex *= 3;
|
||||
|
||||
/* Blend R */
|
||||
dst_pix[indexImg1] = first_pix[begLineIndex];
|
||||
indexImg1++;
|
||||
|
||||
/* Blend G */
|
||||
dst_pix[indexImg1] = first_pix[begLineIndex + 1];
|
||||
indexImg1++;
|
||||
|
||||
/* Blend B */
|
||||
dst_pix[indexImg1] = first_pix[begLineIndex + 2];
|
||||
|
||||
indexImg1++;
|
||||
|
||||
begLine += step;
|
||||
|
||||
} /* for */
|
||||
} /* if */
|
||||
|
||||
begLineIndex = endLineIndex;
|
||||
begLine = endLine;
|
||||
|
||||
|
||||
} /* for each runs in first line */
|
||||
|
||||
begLineIndex = second[0];
|
||||
begLine = (float) begLineIndex;
|
||||
|
||||
curr = 0;
|
||||
|
||||
/* --------------Create second line------------- */
|
||||
curr = 0;;
|
||||
for( n = 0; n < second_runs; n++ )
|
||||
{ /* for each run */
|
||||
|
||||
begCorr = (float) second_corr[curr];
|
||||
curr++;
|
||||
endCorr = (float) second_corr[curr];
|
||||
curr++;
|
||||
endLineIndex = second[curr];
|
||||
endLine = (float) endLineIndex;
|
||||
|
||||
begDestLine = (int) (alpha1 * begLine + alpha * begCorr);
|
||||
endDestLine = (int) (alpha1 * endLine + alpha * endCorr);
|
||||
|
||||
indexImg1 = begDestLine * 3;
|
||||
|
||||
step = 0;
|
||||
if (endDestLine != begDestLine)
|
||||
step = (endLine - begLine) / ((float) (endDestLine - begDestLine));
|
||||
|
||||
if( begCorr != endCorr )
|
||||
{
|
||||
|
||||
for( ; begDestLine < endDestLine; begDestLine++ )
|
||||
{
|
||||
/* for each pixel */
|
||||
|
||||
begLineIndex = (int) begLine;
|
||||
begLineIndex *= 3;
|
||||
|
||||
/* Blend R */
|
||||
dst_pix[indexImg1] =
|
||||
(uchar) (dst_pix[indexImg1] +
|
||||
(uchar) (((unsigned int) (second_pix[begLineIndex]) * s1) >> 8));
|
||||
|
||||
indexImg1++;
|
||||
|
||||
/* Blend G */
|
||||
dst_pix[indexImg1] =
|
||||
(uchar) (dst_pix[indexImg1] +
|
||||
(uchar) (((unsigned int) (second_pix[begLineIndex + 1]) * s1) >>
|
||||
8));
|
||||
|
||||
indexImg1++;
|
||||
|
||||
/* Blend B */
|
||||
dst_pix[indexImg1] =
|
||||
(uchar) (dst_pix[indexImg1] +
|
||||
(uchar) (((unsigned int) (second_pix[begLineIndex + 2]) * s1) >>
|
||||
8));
|
||||
|
||||
indexImg1++;
|
||||
|
||||
begLine += step;
|
||||
|
||||
} /* for */
|
||||
}
|
||||
else
|
||||
{
|
||||
|
||||
for( ; begDestLine < endDestLine; begDestLine++ )
|
||||
{
|
||||
/* for each pixel */
|
||||
|
||||
begLineIndex = (int) begLine;
|
||||
begLineIndex *= 3;
|
||||
|
||||
/* Blend R */
|
||||
dst_pix[indexImg1] = (uchar) (dst_pix[indexImg1] + second_pix[begLineIndex]);
|
||||
indexImg1++;
|
||||
|
||||
/* Blend G */
|
||||
dst_pix[indexImg1] =
|
||||
(uchar) (dst_pix[indexImg1] + second_pix[begLineIndex + 1]);
|
||||
indexImg1++;
|
||||
|
||||
/* Blend B */
|
||||
dst_pix[indexImg1] =
|
||||
(uchar) (dst_pix[indexImg1] + second_pix[begLineIndex + 2]);
|
||||
/*assert(indexImg1 < dst_len); */
|
||||
|
||||
indexImg1++;
|
||||
|
||||
begLine += step;
|
||||
|
||||
} /* for */
|
||||
} /* if */
|
||||
|
||||
begLineIndex = endLineIndex;
|
||||
begLine = endLine;
|
||||
|
||||
} /* for each runs in second line */
|
||||
|
||||
return CV_NO_ERR;
|
||||
|
||||
} /* icvMorphEpilines8uC3 */
|
||||
|
||||
|
||||
/*======================================================================================*/
|
||||
|
||||
static CvStatus
|
||||
icvMorphEpilines8uC3Multi( int lines, /* number of lines */
|
||||
uchar * first_pix, /* raster epilines from the first image */
|
||||
int *first_num, /* numbers of pixel in first line */
|
||||
uchar * second_pix, /* raster epilines from the second image */
|
||||
int *second_num, /* numbers of pixel in second line */
|
||||
uchar * dst_pix, /* raster epiline from the destination image */
|
||||
/* (it's an output parameter) */
|
||||
int *dst_num, /* numbers of pixel in output line */
|
||||
float alpha, /* relative position of camera */
|
||||
int *first, /* first sequence of runs */
|
||||
int *first_runs, /* it's length */
|
||||
int *second, /* second sequence of runs */
|
||||
int *second_runs, int *first_corr, /* correspond information for the 1st seq */
|
||||
int *second_corr ) /* correspond information for the 2nd seq */
|
||||
{
|
||||
CvStatus error;
|
||||
int currLine;
|
||||
int currFirstPix = 0;
|
||||
//int currFirstNum = 0;
|
||||
int currSecondPix = 0;
|
||||
//int currSecondNum = 0;
|
||||
int currDstPix = 0;
|
||||
int currFirst = 0;
|
||||
//int currFirstRuns = 0;
|
||||
int currSecond = 0;
|
||||
//int currSecondRuns = 0;
|
||||
int currFirstCorr = 0;
|
||||
int currSecondCorr = 0;
|
||||
|
||||
if( lines < 1 ||
|
||||
first_pix == 0 ||
|
||||
first_num == 0 ||
|
||||
second_pix == 0 ||
|
||||
second_num == 0 ||
|
||||
dst_pix == 0 ||
|
||||
dst_num == 0 ||
|
||||
alpha < 0 ||
|
||||
alpha > 1 ||
|
||||
first == 0 ||
|
||||
first_runs == 0 ||
|
||||
second == 0 || second_runs == 0 || first_corr == 0 || second_corr == 0 )
|
||||
return CV_BADFACTOR_ERR;
|
||||
|
||||
for( currLine = 0; currLine < lines; currLine++ )
|
||||
{
|
||||
|
||||
error = icvMorphEpilines8uC3( &(first_pix[currFirstPix]),
|
||||
&(second_pix[currSecondPix]),
|
||||
&(dst_pix[currDstPix]),
|
||||
alpha,
|
||||
&(first[currFirst]),
|
||||
first_runs[currLine],
|
||||
&(second[currSecond]),
|
||||
second_runs[currLine],
|
||||
&(first_corr[currFirstCorr]),
|
||||
&(second_corr[currSecondCorr]), dst_num[currLine] * 3 );
|
||||
|
||||
|
||||
if( error != CV_NO_ERR )
|
||||
return CV_NO_ERR;
|
||||
|
||||
currFirstPix += first_num[currLine] * 3;
|
||||
currSecondPix += second_num[currLine] * 3;
|
||||
currDstPix += dst_num[currLine] * 3;
|
||||
currFirst += (first_runs[currLine] * 2) + 1;
|
||||
currSecond += (second_runs[currLine] * 2) + 1;
|
||||
currFirstCorr += first_runs[currLine] * 2;
|
||||
currSecondCorr += second_runs[currLine] * 2;
|
||||
|
||||
} /* for */
|
||||
|
||||
return CV_NO_ERR;
|
||||
|
||||
} /* icvMorphEpilines8uC3Multi */
|
||||
|
||||
|
||||
|
||||
|
||||
/*======================================================================================*/
|
||||
|
||||
CV_IMPL void
|
||||
cvMorphEpilinesMulti( int lines, /* number of lines */
|
||||
uchar * first_pix, /* raster epilines from the first image */
|
||||
int *first_num, /* numbers of pixel in first line */
|
||||
uchar * second_pix, /* raster epilines from the second image */
|
||||
int *second_num, /* numbers of pixel in second line */
|
||||
uchar * dst_pix, /* raster epiline from the destination image */
|
||||
/* (it's an output parameter) */
|
||||
int *dst_num, /* numbers of pixel in output line */
|
||||
float alpha, /* relative position of camera */
|
||||
int *first, /* first sequence of runs */
|
||||
int *first_runs, /* it's length */
|
||||
int *second, /* second sequence of runs */
|
||||
int *second_runs, int *first_corr, /* correspond information for the 1st seq */
|
||||
int *second_corr /* correspond information for the 2nd seq */
|
||||
)
|
||||
{
|
||||
CV_FUNCNAME( "cvMorphEpilinesMulti" );
|
||||
__BEGIN__;
|
||||
|
||||
IPPI_CALL( icvMorphEpilines8uC3Multi( lines, /* number of lines */
|
||||
first_pix, /* raster epilines from the first image */
|
||||
first_num, /* numbers of pixel in first line */
|
||||
second_pix, /* raster epilines from the second image */
|
||||
second_num, /* numbers of pixel in second line */
|
||||
dst_pix, /* raster epiline from the destination image */
|
||||
/* (it's an output parameter) */
|
||||
dst_num, /* numbers of pixel in output line */
|
||||
alpha, /* relative position of camera */
|
||||
first, /* first sequence of runs */
|
||||
first_runs, /* it's length */
|
||||
second, /* second sequence of runs */
|
||||
second_runs, first_corr, /* correspond information for the 1st seq */
|
||||
second_corr /* correspond information for the 2nd seq */
|
||||
));
|
||||
__END__;
|
||||
}
|
||||
|
||||
@@ -0,0 +1,168 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
#include "_cvaux.h"
|
||||
#include "_cvvm.h"
|
||||
|
||||
/* Valery Mosyagin */
|
||||
|
||||
static CvStatus
|
||||
icvFindRuns( int numLines, /* number of scanlines */
|
||||
uchar * prewarp_1, /* prewarp image 1 */
|
||||
uchar * prewarp_2, /* prewarp image 2 */
|
||||
int *line_lens_1, /* line lengths 1 */
|
||||
int *line_lens_2, /* line lengths 2 */
|
||||
int *runs_1, /* result runs 1 */
|
||||
int *runs_2, /* result runs 2 */
|
||||
int *num_runs_1, /* numbers of first runs */
|
||||
int *num_runs_2 )
|
||||
{
|
||||
CvStatus err;
|
||||
|
||||
err = icvFindRunsInOneImage( numLines, prewarp_1, line_lens_1, runs_1, num_runs_1 );
|
||||
|
||||
if( err != CV_NO_ERR )
|
||||
return err;
|
||||
|
||||
err = icvFindRunsInOneImage( numLines, prewarp_2, line_lens_2, runs_2, num_runs_2 );
|
||||
|
||||
return err;
|
||||
|
||||
}
|
||||
|
||||
|
||||
/*======================================================================================*/
|
||||
|
||||
CV_INLINE int
|
||||
icvGetColor( uchar * valueRGB )
|
||||
{
|
||||
int R = *valueRGB;
|
||||
int G = *(valueRGB + 1);
|
||||
int B = *(valueRGB + 2);
|
||||
|
||||
return ( ((R + G + B) >> 3) & 0xFFFC );
|
||||
} /* vm_GetColor */
|
||||
|
||||
|
||||
/*======================================================================================*/
|
||||
|
||||
CvStatus
|
||||
icvFindRunsInOneImage( int numLines, /* number of scanlines */
|
||||
uchar * prewarp, /* prewarp image */
|
||||
int *line_lens, /* line lengths in pixels */
|
||||
int *runs, /* result runs */
|
||||
int *num_runs )
|
||||
{
|
||||
int epiLine;
|
||||
int run_index;
|
||||
int curr_color;
|
||||
int index;
|
||||
int color;
|
||||
uchar *curr_point;
|
||||
int num;
|
||||
|
||||
|
||||
run_index = 0;
|
||||
|
||||
curr_point = prewarp;
|
||||
|
||||
for( epiLine = 0; epiLine < numLines; epiLine++ )
|
||||
{
|
||||
|
||||
curr_color = icvGetColor( curr_point );
|
||||
|
||||
runs[run_index++] = 0;
|
||||
runs[run_index++] = curr_color;
|
||||
|
||||
curr_point += 3;
|
||||
|
||||
num = 1;
|
||||
for( index = 1; index < line_lens[epiLine]; index++ )
|
||||
{
|
||||
|
||||
color = icvGetColor( curr_point );
|
||||
|
||||
if( color != curr_color )
|
||||
{
|
||||
runs[run_index++] = index;
|
||||
runs[run_index++] = color;
|
||||
curr_color = color;
|
||||
num++;
|
||||
}
|
||||
|
||||
curr_point += 3;
|
||||
}
|
||||
|
||||
runs[run_index++] = index;
|
||||
num_runs[epiLine] = num;
|
||||
}
|
||||
|
||||
return CV_NO_ERR;
|
||||
}
|
||||
|
||||
|
||||
/*======================================================================================*/
|
||||
|
||||
CV_IMPL void
|
||||
cvFindRuns( int numLines, /* number of scanlines */
|
||||
uchar * prewarp_1, /* prewarp image 1 */
|
||||
uchar * prewarp_2, /* prewarp image 2 */
|
||||
int *line_lens_1, /* line lengths 1 */
|
||||
int *line_lens_2, /* line lengths 2 */
|
||||
int *runs_1, /* result runs 1 */
|
||||
int *runs_2, /* result runs 2 */
|
||||
int *num_runs_1, /* numbers of first runs */
|
||||
int *num_runs_2 )
|
||||
{
|
||||
CV_FUNCNAME( "cvFindRuns" );
|
||||
__BEGIN__;
|
||||
|
||||
IPPI_CALL( icvFindRuns( numLines, /* number of scanlines */
|
||||
prewarp_1, /* prewarp image 1 */
|
||||
prewarp_2, /* prewarp image 2 */
|
||||
line_lens_1, /* line lengths 1 */
|
||||
line_lens_2, /* line lengths 2 */
|
||||
runs_1, /* result runs 1 */
|
||||
runs_2, /* result runs 2 */
|
||||
num_runs_1, /* numbers of first runs */
|
||||
num_runs_2 ));
|
||||
__CLEANUP__;
|
||||
__END__;
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,585 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
typedef struct Seg
|
||||
{
|
||||
ushort y;
|
||||
ushort l;
|
||||
ushort r;
|
||||
ushort Prevl;
|
||||
ushort Prevr;
|
||||
short fl;
|
||||
}
|
||||
Seg;
|
||||
|
||||
#define UP 1
|
||||
#define DOWN -1
|
||||
|
||||
#define PUSH(Y,IL,IR,IPL,IPR,FL) { stack[StIn].y=(ushort)(Y); \
|
||||
stack[StIn].l=(ushort)(IL); \
|
||||
stack[StIn].r=(ushort)(IR); \
|
||||
stack[StIn].Prevl=(ushort)(IPL); \
|
||||
stack[StIn].Prevr=(ushort)(IPR); \
|
||||
stack[StIn].fl=(short)(FL); \
|
||||
StIn++; }
|
||||
|
||||
#define POP(Y,IL,IR,IPL,IPR,FL) { StIn--; \
|
||||
Y=stack[StIn].y; \
|
||||
IL=stack[StIn].l; \
|
||||
IR=stack[StIn].r;\
|
||||
IPL=stack[StIn].Prevl; \
|
||||
IPR=stack[StIn].Prevr; \
|
||||
FL=stack[StIn].fl; }
|
||||
|
||||
|
||||
#define DIFF(p1,p2) ((unsigned)((p1)[0] - (p2)[0] + d_lw)<=Interval && \
|
||||
(unsigned)((p1)[1] - (p2)[1] + d_lw)<=Interval && \
|
||||
(unsigned)((p1)[2] - (p2)[2] + d_lw)<=Interval)
|
||||
|
||||
/*#define DIFF(p1,p2) (CV_IABS((p1)[0] - (p2)[0]) + \
|
||||
CV_IABS((p1)[1] - (p2)[1]) + \
|
||||
CV_IABS((p1)[2] - (p2)[2]) <=Interval )*/
|
||||
|
||||
static CvStatus
|
||||
icvSegmFloodFill_Stage1( uchar* pImage, int step,
|
||||
uchar* pMask, int maskStep,
|
||||
CvSize /*roi*/, CvPoint seed,
|
||||
int* newVal, int d_lw, int d_up,
|
||||
CvConnectedComp * region,
|
||||
void *pStack )
|
||||
{
|
||||
uchar* img = pImage + step * seed.y;
|
||||
uchar* mask = pMask + maskStep * (seed.y + 1);
|
||||
unsigned Interval = (unsigned) (d_up + d_lw);
|
||||
Seg *stack = (Seg*)pStack;
|
||||
int StIn = 0;
|
||||
int i, L, R;
|
||||
int area = 0;
|
||||
int sum[] = { 0, 0, 0 };
|
||||
int XMin, XMax, YMin = seed.y, YMax = seed.y;
|
||||
int val0[3];
|
||||
|
||||
L = R = seed.x;
|
||||
img = pImage + seed.y*step;
|
||||
mask = pMask + seed.y*maskStep;
|
||||
mask[L] = 1;
|
||||
|
||||
val0[0] = img[seed.x*3];
|
||||
val0[1] = img[seed.x*3 + 1];
|
||||
val0[2] = img[seed.x*3 + 2];
|
||||
|
||||
while( DIFF( img + (R+1)*3, /*img + R*3*/val0 ) && !mask[R + 1] )
|
||||
mask[++R] = 2;
|
||||
|
||||
while( DIFF( img + (L-1)*3, /*img + L*3*/val0 ) && !mask[L - 1] )
|
||||
mask[--L] = 2;
|
||||
|
||||
XMax = R;
|
||||
XMin = L;
|
||||
PUSH( seed.y, L, R, R + 1, R, UP );
|
||||
|
||||
while( StIn )
|
||||
{
|
||||
int k, YC, PL, PR, flag/*, curstep*/;
|
||||
|
||||
POP( YC, L, R, PL, PR, flag );
|
||||
|
||||
int data[][3] = { {-flag, L, R}, {flag, L, PL-1}, {flag,PR+1,R}};
|
||||
|
||||
if( XMax < R )
|
||||
XMax = R;
|
||||
|
||||
if( XMin > L )
|
||||
XMin = L;
|
||||
|
||||
if( YMax < YC )
|
||||
YMax = YC;
|
||||
|
||||
if( YMin > YC )
|
||||
YMin = YC;
|
||||
|
||||
for( k = 0; k < 3; k++ )
|
||||
{
|
||||
flag = data[k][0];
|
||||
/*curstep = flag * step;*/
|
||||
img = pImage + (YC + flag) * step;
|
||||
mask = pMask + (YC + flag) * maskStep;
|
||||
int left = data[k][1];
|
||||
int right = data[k][2];
|
||||
|
||||
for( i = left; i <= right; i++ )
|
||||
{
|
||||
if( !mask[i] && DIFF( img + i*3, /*img - curstep + i*3*/val0 ))
|
||||
{
|
||||
int j = i;
|
||||
mask[i] = 2;
|
||||
while( !mask[j - 1] && DIFF( img + (j - 1)*3, /*img + j*3*/val0 ))
|
||||
mask[--j] = 2;
|
||||
|
||||
while( !mask[i + 1] &&
|
||||
(DIFF( img + (i+1)*3, /*img + i*3*/val0 ) ||
|
||||
(DIFF( img + (i+1)*3, /*img + (i+1)*3 - curstep*/val0) && i < R)))
|
||||
mask[++i] = 2;
|
||||
|
||||
PUSH( YC + flag, j, i, L, R, -flag );
|
||||
i++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
img = pImage + YC * step;
|
||||
|
||||
for( i = L; i <= R; i++ )
|
||||
{
|
||||
sum[0] += img[i*3];
|
||||
sum[1] += img[i*3 + 1];
|
||||
sum[2] += img[i*3 + 2];
|
||||
}
|
||||
|
||||
area += R - L + 1;
|
||||
}
|
||||
|
||||
region->area = area;
|
||||
region->rect.x = XMin;
|
||||
region->rect.y = YMin;
|
||||
region->rect.width = XMax - XMin + 1;
|
||||
region->rect.height = YMax - YMin + 1;
|
||||
region->value = cvScalarAll(0);
|
||||
|
||||
{
|
||||
double inv_area = area ? 1./area : 0;
|
||||
newVal[0] = cvRound( sum[0] * inv_area );
|
||||
newVal[1] = cvRound( sum[1] * inv_area );
|
||||
newVal[2] = cvRound( sum[2] * inv_area );
|
||||
}
|
||||
|
||||
return CV_NO_ERR;
|
||||
}
|
||||
|
||||
|
||||
#undef PUSH
|
||||
#undef POP
|
||||
#undef DIFF
|
||||
|
||||
|
||||
static CvStatus
|
||||
icvSegmFloodFill_Stage2( uchar* pImage, int step,
|
||||
uchar* pMask, int maskStep,
|
||||
CvSize /*roi*/, int* newVal,
|
||||
CvRect rect )
|
||||
{
|
||||
uchar* img = pImage + step * rect.y + rect.x * 3;
|
||||
uchar* mask = pMask + maskStep * rect.y + rect.x;
|
||||
uchar uv[] = { (uchar)newVal[0], (uchar)newVal[1], (uchar)newVal[2] };
|
||||
int x, y;
|
||||
|
||||
for( y = 0; y < rect.height; y++, img += step, mask += maskStep )
|
||||
for( x = 0; x < rect.width; x++ )
|
||||
if( mask[x] == 2 )
|
||||
{
|
||||
mask[x] = 1;
|
||||
img[x*3] = uv[0];
|
||||
img[x*3+1] = uv[1];
|
||||
img[x*3+2] = uv[2];
|
||||
}
|
||||
|
||||
return CV_OK;
|
||||
}
|
||||
|
||||
#if 0
|
||||
static void color_derv( const CvArr* srcArr, CvArr* dstArr, int thresh )
|
||||
{
|
||||
static int tab[] = { 0, 2, 2, 1 };
|
||||
|
||||
uchar *src = 0, *dst = 0;
|
||||
int dst_step, src_step;
|
||||
int x, y;
|
||||
CvSize size;
|
||||
|
||||
cvGetRawData( srcArr, (uchar**)&src, &src_step, &size );
|
||||
cvGetRawData( dstArr, (uchar**)&dst, &dst_step, 0 );
|
||||
|
||||
memset( dst, 0, size.width*sizeof(dst[0]));
|
||||
memset( (uchar*)dst + dst_step*(size.height-1), 0, size.width*sizeof(dst[0]));
|
||||
src += 3;
|
||||
|
||||
#define CV_IABS(a) (((a) ^ ((a) < 0 ? -1 : 0)) - ((a) < 0 ? -1 : 0))
|
||||
|
||||
for( y = 1; y < size.height - 1; y++ )
|
||||
{
|
||||
src += src_step;
|
||||
dst += dst_step;
|
||||
uchar* src0 = src;
|
||||
|
||||
dst[0] = dst[size.width - 1] = 0;
|
||||
|
||||
for( x = 1; x < size.width - 1; x++, src += 3 )
|
||||
{
|
||||
/*int d[3];
|
||||
int ad[3];
|
||||
int f0, f1;
|
||||
int val;*/
|
||||
int m[3];
|
||||
double val;
|
||||
//double xx, yy;
|
||||
int dh[3];
|
||||
int dv[3];
|
||||
dh[0] = src[0] - src[-3];
|
||||
dv[0] = src[0] - src[-src_step];
|
||||
dh[1] = src[1] - src[-2];
|
||||
dv[1] = src[1] - src[1-src_step];
|
||||
dh[2] = src[2] - src[-1];
|
||||
dv[2] = src[2] - src[2-src_step];
|
||||
|
||||
m[0] = dh[0]*dh[0] + dh[1]*dh[1] + dh[2]*dh[2];
|
||||
m[2] = dh[0]*dv[0] + dh[1]*dv[1] + dh[2]*dv[2];
|
||||
m[1] = dv[0]*dv[0] + dv[1]*dv[1] + dh[2]*dh[2];
|
||||
|
||||
val = (m[0] + m[2]) +
|
||||
sqrt(((double)((double)m[0] - m[2]))*(m[0] - m[2]) + (4.*m[1])*m[1]);
|
||||
|
||||
/*
|
||||
|
||||
xx = m[1];
|
||||
yy = v - m[0];
|
||||
v /= sqrt(xx*xx + yy*yy) + 1e-7;
|
||||
xx *= v;
|
||||
yy *= v;
|
||||
|
||||
dx[x] = (short)cvRound(xx);
|
||||
dy[x] = (short)cvRound(yy);
|
||||
|
||||
//dx[x] = (short)cvRound(v);
|
||||
|
||||
//dx[x] = dy[x] = (short)v;
|
||||
d[0] = src[0] - src[-3];
|
||||
ad[0] = CV_IABS(d[0]);
|
||||
|
||||
d[1] = src[1] - src[-2];
|
||||
ad[1] = CV_IABS(d[1]);
|
||||
|
||||
d[2] = src[2] - src[-1];
|
||||
ad[2] = CV_IABS(d[2]);
|
||||
|
||||
f0 = ad[1] > ad[0];
|
||||
f1 = ad[2] > ad[f0];
|
||||
|
||||
val = d[tab[f0*2 + f1]];
|
||||
|
||||
d[0] = src[0] - src[-src_step];
|
||||
ad[0] = CV_IABS(d[0]);
|
||||
|
||||
d[1] = src[1] - src[1-src_step];
|
||||
ad[1] = CV_IABS(d[1]);
|
||||
|
||||
d[2] = src[2] - src[2-src_step];
|
||||
ad[2] = CV_IABS(d[2]);
|
||||
|
||||
f0 = ad[1] > ad[0];
|
||||
f1 = ad[2] > ad[f0];
|
||||
|
||||
dst[x] = (uchar)(val + d[tab[f0*2 + f1]] > thresh ? 255 : 0);*/
|
||||
dst[x] = (uchar)(val > thresh);
|
||||
}
|
||||
|
||||
src = src0;
|
||||
}
|
||||
|
||||
}
|
||||
#endif
|
||||
|
||||
const CvPoint icvCodeDeltas[8] =
|
||||
{ {1, 0}, {1, -1}, {0, -1}, {-1, -1}, {-1, 0}, {-1, 1}, {0, 1}, {1, 1} };
|
||||
|
||||
static CvSeq*
|
||||
icvGetComponent( uchar* img, int step, CvRect rect,
|
||||
CvMemStorage* storage )
|
||||
{
|
||||
const char nbd = 4;
|
||||
int deltas[16];
|
||||
int x, y;
|
||||
CvSeq* exterior = 0;
|
||||
char* ptr;
|
||||
|
||||
/* initialize local state */
|
||||
CV_INIT_3X3_DELTAS( deltas, step, 1 );
|
||||
memcpy( deltas + 8, deltas, 8 * sizeof( deltas[0] ));
|
||||
|
||||
ptr = (char*)(img + step*rect.y);
|
||||
rect.width += rect.x;
|
||||
rect.height += rect.y;
|
||||
|
||||
for( y = rect.y; y < rect.height; y++, ptr += step )
|
||||
{
|
||||
int prev = ptr[rect.x - 1] & -2;
|
||||
|
||||
for( x = rect.x; x < rect.width; x++ )
|
||||
{
|
||||
int p = ptr[x] & -2;
|
||||
|
||||
//assert( exterior || ((p | prev) & -4) == 0 );
|
||||
|
||||
if( p != prev )
|
||||
{
|
||||
CvSeq *seq = 0;
|
||||
int is_hole = 0;
|
||||
CvSeqWriter writer;
|
||||
char *i0, *i1, *i3, *i4 = 0;
|
||||
int prev_s = -1, s, s_end;
|
||||
CvPoint pt = { x, y };
|
||||
|
||||
if( !(prev == 0 && p == 2) ) /* if not external contour */
|
||||
{
|
||||
/* check hole */
|
||||
if( p != 0 || prev < 1 )
|
||||
{
|
||||
prev = p;
|
||||
continue;
|
||||
}
|
||||
|
||||
is_hole = 1;
|
||||
if( !exterior )
|
||||
{
|
||||
assert(0);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
cvStartWriteSeq( CV_SEQ_CONTOUR | (is_hole ? CV_SEQ_FLAG_HOLE : 0),
|
||||
sizeof(CvContour), sizeof(CvPoint), storage, &writer );
|
||||
s_end = s = is_hole ? 0 : 4;
|
||||
i0 = ptr + x - is_hole;
|
||||
|
||||
do
|
||||
{
|
||||
s = (s - 1) & 7;
|
||||
i1 = i0 + deltas[s];
|
||||
if( (*i1 & -2) != 0 )
|
||||
break;
|
||||
}
|
||||
while( s != s_end );
|
||||
|
||||
if( s == s_end ) /* single pixel domain */
|
||||
{
|
||||
*i0 = (char) (nbd | -128);
|
||||
CV_WRITE_SEQ_ELEM( pt, writer );
|
||||
}
|
||||
else
|
||||
{
|
||||
i3 = i0;
|
||||
prev_s = s ^ 4;
|
||||
|
||||
/* follow border */
|
||||
for( ;; )
|
||||
{
|
||||
s_end = s;
|
||||
|
||||
for( ;; )
|
||||
{
|
||||
i4 = i3 + deltas[++s];
|
||||
if( (*i4 & -2) != 0 )
|
||||
break;
|
||||
}
|
||||
s &= 7;
|
||||
|
||||
/* check "right" bound */
|
||||
if( (unsigned) (s - 1) < (unsigned) s_end )
|
||||
{
|
||||
*i3 = (char) (nbd | -128);
|
||||
}
|
||||
else if( *i3 > 0 )
|
||||
{
|
||||
*i3 = nbd;
|
||||
}
|
||||
|
||||
if( s != prev_s )
|
||||
{
|
||||
CV_WRITE_SEQ_ELEM( pt, writer );
|
||||
prev_s = s;
|
||||
}
|
||||
|
||||
pt.x += icvCodeDeltas[s].x;
|
||||
pt.y += icvCodeDeltas[s].y;
|
||||
|
||||
if( i4 == i0 && i3 == i1 )
|
||||
break;
|
||||
|
||||
i3 = i4;
|
||||
s = (s + 4) & 7;
|
||||
} /* end of border following loop */
|
||||
}
|
||||
|
||||
seq = cvEndWriteSeq( &writer );
|
||||
cvContourBoundingRect( seq, 1 );
|
||||
|
||||
if( !is_hole )
|
||||
exterior = seq;
|
||||
else
|
||||
{
|
||||
seq->v_prev = exterior;
|
||||
seq->h_next = exterior->v_next;
|
||||
if( seq->h_next )
|
||||
seq->h_next->h_prev = seq;
|
||||
exterior->v_next = seq;
|
||||
}
|
||||
|
||||
prev = ptr[x] & -2;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return exterior;
|
||||
}
|
||||
|
||||
|
||||
|
||||
CV_IMPL CvSeq*
|
||||
cvSegmentImage( const CvArr* srcarr, CvArr* dstarr,
|
||||
double canny_threshold,
|
||||
double ffill_threshold,
|
||||
CvMemStorage* storage )
|
||||
{
|
||||
CvSeq* root = 0;
|
||||
CvMat* gray = 0;
|
||||
CvMat* canny = 0;
|
||||
//CvMat* temp = 0;
|
||||
void* stack = 0;
|
||||
|
||||
CV_FUNCNAME( "cvSegmentImage" );
|
||||
|
||||
__BEGIN__;
|
||||
|
||||
CvMat srcstub, *src;
|
||||
CvMat dststub, *dst;
|
||||
CvMat* mask;
|
||||
CvSize size;
|
||||
CvPoint pt;
|
||||
int ffill_lw_up = cvRound( fabs(ffill_threshold) );
|
||||
CvSeq* prev_seq = 0;
|
||||
|
||||
CV_CALL( src = cvGetMat( srcarr, &srcstub ));
|
||||
CV_CALL( dst = cvGetMat( dstarr, &dststub ));
|
||||
|
||||
size = cvGetSize( src );
|
||||
|
||||
CV_CALL( gray = cvCreateMat( size.height, size.width, CV_8UC1 ));
|
||||
CV_CALL( canny = cvCreateMat( size.height, size.width, CV_8UC1 ));
|
||||
//CV_CALL( temp = cvCreateMat( size.height/2, size.width/2, CV_8UC3 ));
|
||||
|
||||
CV_CALL( stack = cvAlloc( size.width * size.height * sizeof(Seg)));
|
||||
|
||||
cvCvtColor( src, gray, CV_BGR2GRAY );
|
||||
cvCanny( gray, canny, 0/*canny_threshold*0.4*/, canny_threshold, 3 );
|
||||
cvThreshold( canny, canny, 1, 1, CV_THRESH_BINARY );
|
||||
//cvZero( canny );
|
||||
//color_derv( src, canny, canny_threshold );
|
||||
|
||||
//cvPyrDown( src, temp );
|
||||
//cvPyrUp( temp, dst );
|
||||
|
||||
//src = dst;
|
||||
mask = canny; // a new name for new role
|
||||
|
||||
// make a non-zero border.
|
||||
cvRectangle( mask, cvPoint(0,0), cvPoint(size.width-1,size.height-1), cvScalarAll(1), 1 );
|
||||
|
||||
for( pt.y = 0; pt.y < size.height; pt.y++ )
|
||||
{
|
||||
for( pt.x = 0; pt.x < size.width; pt.x++ )
|
||||
{
|
||||
if( mask->data.ptr[mask->step*pt.y + pt.x] == 0 )
|
||||
{
|
||||
CvConnectedComp region;
|
||||
int avgVal[3] = { 0, 0, 0 };
|
||||
|
||||
icvSegmFloodFill_Stage1( src->data.ptr, src->step,
|
||||
mask->data.ptr, mask->step,
|
||||
size, pt, avgVal,
|
||||
ffill_lw_up, ffill_lw_up,
|
||||
®ion, stack );
|
||||
|
||||
/*avgVal[0] = (avgVal[0] + 15) & -32;
|
||||
if( avgVal[0] > 255 )
|
||||
avgVal[0] = 255;
|
||||
avgVal[1] = (avgVal[1] + 15) & -32;
|
||||
if( avgVal[1] > 255 )
|
||||
avgVal[1] = 255;
|
||||
avgVal[2] = (avgVal[2] + 15) & -32;
|
||||
if( avgVal[2] > 255 )
|
||||
avgVal[2] = 255;*/
|
||||
|
||||
if( storage )
|
||||
{
|
||||
CvSeq* tmpseq = icvGetComponent( mask->data.ptr, mask->step,
|
||||
region.rect, storage );
|
||||
if( tmpseq != 0 )
|
||||
{
|
||||
((CvContour*)tmpseq)->color = avgVal[0] + (avgVal[1] << 8) + (avgVal[2] << 16);
|
||||
tmpseq->h_prev = prev_seq;
|
||||
if( prev_seq )
|
||||
prev_seq->h_next = tmpseq;
|
||||
else
|
||||
root = tmpseq;
|
||||
prev_seq = tmpseq;
|
||||
}
|
||||
}
|
||||
|
||||
icvSegmFloodFill_Stage2( dst->data.ptr, dst->step,
|
||||
mask->data.ptr, mask->step,
|
||||
size, avgVal,
|
||||
region.rect );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
__END__;
|
||||
|
||||
//cvReleaseMat( &temp );
|
||||
cvReleaseMat( &gray );
|
||||
cvReleaseMat( &canny );
|
||||
cvFree( &stack );
|
||||
|
||||
return root;
|
||||
}
|
||||
|
||||
/* End of file. */
|
||||
@@ -0,0 +1,187 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
CV_IMPL int
|
||||
icvSubdiv2DCheck( CvSubdiv2D* subdiv )
|
||||
{
|
||||
int i, j, total = subdiv->edges->total;
|
||||
int check_result = 0;
|
||||
|
||||
CV_FUNCNAME("icvSubdiv2DCheck");
|
||||
|
||||
__BEGIN__;
|
||||
|
||||
if( !subdiv )
|
||||
CV_ERROR_FROM_STATUS( CV_NULLPTR_ERR );
|
||||
|
||||
for( i = 0; i < total; i++ )
|
||||
{
|
||||
CvQuadEdge2D* edge = (CvQuadEdge2D*)cvGetSetElem(subdiv->edges,i);
|
||||
|
||||
if( edge && CV_IS_SET_ELEM( edge ))
|
||||
{
|
||||
for( j = 0; j < 4; j++ )
|
||||
{
|
||||
CvSubdiv2DEdge e = (CvSubdiv2DEdge)edge + j;
|
||||
CvSubdiv2DEdge o_next = cvSubdiv2DNextEdge(e);
|
||||
CvSubdiv2DEdge o_prev = cvSubdiv2DGetEdge(e, CV_PREV_AROUND_ORG );
|
||||
CvSubdiv2DEdge d_prev = cvSubdiv2DGetEdge(e, CV_PREV_AROUND_DST );
|
||||
CvSubdiv2DEdge d_next = cvSubdiv2DGetEdge(e, CV_NEXT_AROUND_DST );
|
||||
|
||||
// check points
|
||||
if( cvSubdiv2DEdgeOrg(e) != cvSubdiv2DEdgeOrg(o_next))
|
||||
EXIT;
|
||||
if( cvSubdiv2DEdgeOrg(e) != cvSubdiv2DEdgeOrg(o_prev))
|
||||
EXIT;
|
||||
if( cvSubdiv2DEdgeDst(e) != cvSubdiv2DEdgeDst(d_next))
|
||||
EXIT;
|
||||
if( cvSubdiv2DEdgeDst(e) != cvSubdiv2DEdgeDst(d_prev))
|
||||
EXIT;
|
||||
if( j % 2 == 0 )
|
||||
{
|
||||
if( cvSubdiv2DEdgeDst(o_next) != cvSubdiv2DEdgeOrg(d_prev))
|
||||
EXIT;
|
||||
if( cvSubdiv2DEdgeDst(o_prev) != cvSubdiv2DEdgeOrg(d_next))
|
||||
EXIT;
|
||||
if( cvSubdiv2DGetEdge(cvSubdiv2DGetEdge(cvSubdiv2DGetEdge(
|
||||
e,CV_NEXT_AROUND_LEFT),CV_NEXT_AROUND_LEFT),CV_NEXT_AROUND_LEFT) != e )
|
||||
EXIT;
|
||||
if( cvSubdiv2DGetEdge(cvSubdiv2DGetEdge(cvSubdiv2DGetEdge(
|
||||
e,CV_NEXT_AROUND_RIGHT),CV_NEXT_AROUND_RIGHT),CV_NEXT_AROUND_RIGHT) != e)
|
||||
EXIT;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
check_result = 1;
|
||||
|
||||
__END__;
|
||||
|
||||
return check_result;
|
||||
}
|
||||
|
||||
|
||||
|
||||
static void
|
||||
draw_subdiv_facet( CvSubdiv2D * subdiv, IplImage * dst, IplImage * src, CvSubdiv2DEdge edge )
|
||||
{
|
||||
CvSubdiv2DEdge t = edge;
|
||||
int i, count = 0;
|
||||
CvPoint local_buf[100];
|
||||
CvPoint *buf = local_buf;
|
||||
|
||||
// count number of edges in facet
|
||||
do
|
||||
{
|
||||
count++;
|
||||
t = cvSubdiv2DGetEdge( t, CV_NEXT_AROUND_LEFT );
|
||||
}
|
||||
while( t != edge && count < subdiv->quad_edges * 4 );
|
||||
|
||||
if( count * sizeof( buf[0] ) > sizeof( local_buf ))
|
||||
{
|
||||
buf = (CvPoint *) malloc( count * sizeof( buf[0] ));
|
||||
}
|
||||
|
||||
// gather points
|
||||
t = edge;
|
||||
for( i = 0; i < count; i++ )
|
||||
{
|
||||
CvSubdiv2DPoint *pt = cvSubdiv2DEdgeOrg( t );
|
||||
|
||||
if( !pt )
|
||||
break;
|
||||
assert( fabs( pt->pt.x ) < 10000 && fabs( pt->pt.y ) < 10000 );
|
||||
buf[i] = cvPoint( cvRound( pt->pt.x ), cvRound( pt->pt.y ));
|
||||
t = cvSubdiv2DGetEdge( t, CV_NEXT_AROUND_LEFT );
|
||||
}
|
||||
|
||||
if( i == count )
|
||||
{
|
||||
CvSubdiv2DPoint *pt = cvSubdiv2DEdgeDst( cvSubdiv2DRotateEdge( edge, 1 ));
|
||||
CvPoint ip = cvPoint( cvRound( pt->pt.x ), cvRound( pt->pt.y ));
|
||||
CvScalar color = {{0,0,0,0}};
|
||||
|
||||
//printf("count = %d, (%d,%d)\n", ip.x, ip.y );
|
||||
|
||||
if( 0 <= ip.x && ip.x < src->width && 0 <= ip.y && ip.y < src->height )
|
||||
{
|
||||
uchar *ptr = (uchar*)(src->imageData + ip.y * src->widthStep + ip.x * 3);
|
||||
color = CV_RGB( ptr[2], ptr[1], ptr[0] );
|
||||
}
|
||||
|
||||
cvFillConvexPoly( dst, buf, count, color );
|
||||
//draw_subdiv_point( dst, pt->pt, CV_RGB(0,0,0));
|
||||
}
|
||||
|
||||
if( buf != local_buf )
|
||||
free( buf );
|
||||
}
|
||||
|
||||
|
||||
CV_IMPL void
|
||||
icvDrawMosaic( CvSubdiv2D * subdiv, IplImage * src, IplImage * dst )
|
||||
{
|
||||
int i, total = subdiv->edges->total;
|
||||
|
||||
cvCalcSubdivVoronoi2D( subdiv );
|
||||
|
||||
//icvSet( dst, 255 );
|
||||
for( i = 0; i < total; i++ )
|
||||
{
|
||||
CvQuadEdge2D *edge = (CvQuadEdge2D *) cvGetSetElem( subdiv->edges, i );
|
||||
|
||||
if( edge && CV_IS_SET_ELEM( edge ))
|
||||
{
|
||||
CvSubdiv2DEdge e = (CvSubdiv2DEdge) edge;
|
||||
|
||||
// left
|
||||
draw_subdiv_facet( subdiv, dst, src, cvSubdiv2DRotateEdge( e, 1 ));
|
||||
// right
|
||||
draw_subdiv_facet( subdiv, dst, src, cvSubdiv2DRotateEdge( e, 3 ));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* End of file. */
|
||||
@@ -0,0 +1,648 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
/****************************************************************************************\
|
||||
|
||||
Calculation of a texture descriptors from GLCM (Grey Level Co-occurrence Matrix'es)
|
||||
The code was submitted by Daniel Eaton [danieljameseaton@yahoo.com]
|
||||
|
||||
\****************************************************************************************/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
#include <math.h>
|
||||
#include <assert.h>
|
||||
|
||||
#define CV_MAX_NUM_GREY_LEVELS_8U 256
|
||||
|
||||
struct CvGLCM
|
||||
{
|
||||
int matrixSideLength;
|
||||
int numMatrices;
|
||||
double*** matrices;
|
||||
|
||||
int numLookupTableElements;
|
||||
int forwardLookupTable[CV_MAX_NUM_GREY_LEVELS_8U];
|
||||
int reverseLookupTable[CV_MAX_NUM_GREY_LEVELS_8U];
|
||||
|
||||
double** descriptors;
|
||||
int numDescriptors;
|
||||
int descriptorOptimizationType;
|
||||
int optimizationType;
|
||||
};
|
||||
|
||||
|
||||
static void icvCreateGLCM_LookupTable_8u_C1R( const uchar* srcImageData, int srcImageStep,
|
||||
CvSize srcImageSize, CvGLCM* destGLCM,
|
||||
int* steps, int numSteps, int* memorySteps );
|
||||
|
||||
static void
|
||||
icvCreateGLCMDescriptors_AllowDoubleNest( CvGLCM* destGLCM, int matrixIndex );
|
||||
|
||||
|
||||
CV_IMPL CvGLCM*
|
||||
cvCreateGLCM( const IplImage* srcImage,
|
||||
int stepMagnitude,
|
||||
const int* srcStepDirections,/* should be static array..
|
||||
or if not the user should handle de-allocation */
|
||||
int numStepDirections,
|
||||
int optimizationType )
|
||||
{
|
||||
static const int defaultStepDirections[] = { 0,1, -1,1, -1,0, -1,-1 };
|
||||
|
||||
int* memorySteps = 0;
|
||||
CvGLCM* newGLCM = 0;
|
||||
int* stepDirections = 0;
|
||||
|
||||
CV_FUNCNAME( "cvCreateGLCM" );
|
||||
|
||||
__BEGIN__;
|
||||
|
||||
uchar* srcImageData = 0;
|
||||
CvSize srcImageSize;
|
||||
int srcImageStep;
|
||||
int stepLoop;
|
||||
const int maxNumGreyLevels8u = CV_MAX_NUM_GREY_LEVELS_8U;
|
||||
|
||||
if( !srcImage )
|
||||
CV_ERROR( CV_StsNullPtr, "" );
|
||||
|
||||
if( srcImage->nChannels != 1 )
|
||||
CV_ERROR( CV_BadNumChannels, "Number of channels must be 1");
|
||||
|
||||
if( srcImage->depth != IPL_DEPTH_8U )
|
||||
CV_ERROR( CV_BadDepth, "Depth must be equal IPL_DEPTH_8U");
|
||||
|
||||
// no Directions provided, use the default ones - 0 deg, 45, 90, 135
|
||||
if( !srcStepDirections )
|
||||
{
|
||||
srcStepDirections = defaultStepDirections;
|
||||
}
|
||||
|
||||
CV_CALL( stepDirections = (int*)cvAlloc( numStepDirections*2*sizeof(stepDirections[0])));
|
||||
memcpy( stepDirections, srcStepDirections, numStepDirections*2*sizeof(stepDirections[0]));
|
||||
|
||||
cvGetImageRawData( srcImage, &srcImageData, &srcImageStep, &srcImageSize );
|
||||
|
||||
// roll together Directions and magnitudes together with knowledge of image (step)
|
||||
CV_CALL( memorySteps = (int*)cvAlloc( numStepDirections*sizeof(memorySteps[0])));
|
||||
|
||||
for( stepLoop = 0; stepLoop < numStepDirections; stepLoop++ )
|
||||
{
|
||||
stepDirections[stepLoop*2 + 0] *= stepMagnitude;
|
||||
stepDirections[stepLoop*2 + 1] *= stepMagnitude;
|
||||
|
||||
memorySteps[stepLoop] = stepDirections[stepLoop*2 + 0]*srcImageStep +
|
||||
stepDirections[stepLoop*2 + 1];
|
||||
}
|
||||
|
||||
CV_CALL( newGLCM = (CvGLCM*)cvAlloc(sizeof(newGLCM)));
|
||||
memset( newGLCM, 0, sizeof(newGLCM) );
|
||||
|
||||
newGLCM->matrices = 0;
|
||||
newGLCM->numMatrices = numStepDirections;
|
||||
newGLCM->optimizationType = optimizationType;
|
||||
|
||||
if( optimizationType <= CV_GLCM_OPTIMIZATION_LUT )
|
||||
{
|
||||
int lookupTableLoop, imageColLoop, imageRowLoop, lineOffset = 0;
|
||||
|
||||
// if optimization type is set to lut, then make one for the image
|
||||
if( optimizationType == CV_GLCM_OPTIMIZATION_LUT )
|
||||
{
|
||||
for( imageRowLoop = 0; imageRowLoop < srcImageSize.height;
|
||||
imageRowLoop++, lineOffset += srcImageStep )
|
||||
{
|
||||
for( imageColLoop = 0; imageColLoop < srcImageSize.width; imageColLoop++ )
|
||||
{
|
||||
newGLCM->forwardLookupTable[srcImageData[lineOffset+imageColLoop]]=1;
|
||||
}
|
||||
}
|
||||
|
||||
newGLCM->numLookupTableElements = 0;
|
||||
|
||||
for( lookupTableLoop = 0; lookupTableLoop < maxNumGreyLevels8u; lookupTableLoop++ )
|
||||
{
|
||||
if( newGLCM->forwardLookupTable[ lookupTableLoop ] != 0 )
|
||||
{
|
||||
newGLCM->forwardLookupTable[ lookupTableLoop ] =
|
||||
newGLCM->numLookupTableElements;
|
||||
newGLCM->reverseLookupTable[ newGLCM->numLookupTableElements ] =
|
||||
lookupTableLoop;
|
||||
|
||||
newGLCM->numLookupTableElements++;
|
||||
}
|
||||
}
|
||||
}
|
||||
// otherwise make a "LUT" which contains all the gray-levels (for code-reuse)
|
||||
else if( optimizationType == CV_GLCM_OPTIMIZATION_NONE )
|
||||
{
|
||||
for( lookupTableLoop = 0; lookupTableLoop <maxNumGreyLevels8u; lookupTableLoop++ )
|
||||
{
|
||||
newGLCM->forwardLookupTable[ lookupTableLoop ] = lookupTableLoop;
|
||||
newGLCM->reverseLookupTable[ lookupTableLoop ] = lookupTableLoop;
|
||||
}
|
||||
newGLCM->numLookupTableElements = maxNumGreyLevels8u;
|
||||
}
|
||||
|
||||
newGLCM->matrixSideLength = newGLCM->numLookupTableElements;
|
||||
icvCreateGLCM_LookupTable_8u_C1R( srcImageData, srcImageStep, srcImageSize,
|
||||
newGLCM, stepDirections,
|
||||
numStepDirections, memorySteps );
|
||||
}
|
||||
else if( optimizationType == CV_GLCM_OPTIMIZATION_HISTOGRAM )
|
||||
{
|
||||
CV_ERROR( CV_StsBadFlag, "Histogram-based method is not implemented" );
|
||||
|
||||
/* newGLCM->numMatrices *= 2;
|
||||
newGLCM->matrixSideLength = maxNumGreyLevels8u*2;
|
||||
|
||||
icvCreateGLCM_Histogram_8uC1R( srcImageStep, srcImageSize, srcImageData,
|
||||
newGLCM, numStepDirections,
|
||||
stepDirections, memorySteps );
|
||||
*/
|
||||
}
|
||||
|
||||
__END__;
|
||||
|
||||
cvFree( &memorySteps );
|
||||
cvFree( &stepDirections );
|
||||
|
||||
if( cvGetErrStatus() < 0 )
|
||||
{
|
||||
cvFree( &newGLCM );
|
||||
}
|
||||
|
||||
return newGLCM;
|
||||
}
|
||||
|
||||
|
||||
CV_IMPL void
|
||||
cvReleaseGLCM( CvGLCM** GLCM, int flag )
|
||||
{
|
||||
CV_FUNCNAME( "cvReleaseGLCM" );
|
||||
|
||||
__BEGIN__;
|
||||
|
||||
int matrixLoop;
|
||||
|
||||
if( !GLCM )
|
||||
CV_ERROR( CV_StsNullPtr, "" );
|
||||
|
||||
if( *GLCM )
|
||||
EXIT; // repeated deallocation: just skip it.
|
||||
|
||||
if( (flag == CV_GLCM_GLCM || flag == CV_GLCM_ALL) && (*GLCM)->matrices )
|
||||
{
|
||||
for( matrixLoop = 0; matrixLoop < (*GLCM)->numMatrices; matrixLoop++ )
|
||||
{
|
||||
if( (*GLCM)->matrices[ matrixLoop ] )
|
||||
{
|
||||
cvFree( (*GLCM)->matrices[matrixLoop] );
|
||||
cvFree( (*GLCM)->matrices + matrixLoop );
|
||||
}
|
||||
}
|
||||
|
||||
cvFree( &((*GLCM)->matrices) );
|
||||
}
|
||||
|
||||
if( (flag == CV_GLCM_DESC || flag == CV_GLCM_ALL) && (*GLCM)->descriptors )
|
||||
{
|
||||
for( matrixLoop = 0; matrixLoop < (*GLCM)->numMatrices; matrixLoop++ )
|
||||
{
|
||||
cvFree( (*GLCM)->descriptors + matrixLoop );
|
||||
}
|
||||
cvFree( &((*GLCM)->descriptors) );
|
||||
}
|
||||
|
||||
if( flag == CV_GLCM_ALL )
|
||||
{
|
||||
cvFree( GLCM );
|
||||
}
|
||||
|
||||
__END__;
|
||||
}
|
||||
|
||||
|
||||
static void
|
||||
icvCreateGLCM_LookupTable_8u_C1R( const uchar* srcImageData,
|
||||
int srcImageStep,
|
||||
CvSize srcImageSize,
|
||||
CvGLCM* destGLCM,
|
||||
int* steps,
|
||||
int numSteps,
|
||||
int* memorySteps )
|
||||
{
|
||||
int* stepIncrementsCounter = 0;
|
||||
|
||||
CV_FUNCNAME( "icvCreateGLCM_LookupTable_8u_C1R" );
|
||||
|
||||
__BEGIN__;
|
||||
|
||||
int matrixSideLength = destGLCM->matrixSideLength;
|
||||
int stepLoop, sideLoop1, sideLoop2;
|
||||
int colLoop, rowLoop, lineOffset = 0;
|
||||
double*** matrices = 0;
|
||||
|
||||
// allocate memory to the matrices
|
||||
CV_CALL( destGLCM->matrices = (double***)cvAlloc( sizeof(matrices[0])*numSteps ));
|
||||
matrices = destGLCM->matrices;
|
||||
|
||||
for( stepLoop=0; stepLoop<numSteps; stepLoop++ )
|
||||
{
|
||||
CV_CALL( matrices[stepLoop] = (double**)cvAlloc( sizeof(matrices[0])*matrixSideLength ));
|
||||
CV_CALL( matrices[stepLoop][0] = (double*)cvAlloc( sizeof(matrices[0][0])*
|
||||
matrixSideLength*matrixSideLength ));
|
||||
|
||||
memset( matrices[stepLoop][0], 0, matrixSideLength*matrixSideLength*
|
||||
sizeof(matrices[0][0]) );
|
||||
|
||||
for( sideLoop1 = 1; sideLoop1 < matrixSideLength; sideLoop1++ )
|
||||
{
|
||||
matrices[stepLoop][sideLoop1] = matrices[stepLoop][sideLoop1-1] + matrixSideLength;
|
||||
}
|
||||
}
|
||||
|
||||
CV_CALL( stepIncrementsCounter = (int*)cvAlloc( numSteps*sizeof(stepIncrementsCounter[0])));
|
||||
memset( stepIncrementsCounter, 0, numSteps*sizeof(stepIncrementsCounter[0]) );
|
||||
|
||||
// generate GLCM for each step
|
||||
for( rowLoop=0; rowLoop<srcImageSize.height; rowLoop++, lineOffset+=srcImageStep )
|
||||
{
|
||||
for( colLoop=0; colLoop<srcImageSize.width; colLoop++ )
|
||||
{
|
||||
int pixelValue1 = destGLCM->forwardLookupTable[srcImageData[lineOffset + colLoop]];
|
||||
|
||||
for( stepLoop=0; stepLoop<numSteps; stepLoop++ )
|
||||
{
|
||||
int col2, row2;
|
||||
row2 = rowLoop + steps[stepLoop*2 + 0];
|
||||
col2 = colLoop + steps[stepLoop*2 + 1];
|
||||
|
||||
if( col2>=0 && row2>=0 && col2<srcImageSize.width && row2<srcImageSize.height )
|
||||
{
|
||||
int memoryStep = memorySteps[ stepLoop ];
|
||||
int pixelValue2 = destGLCM->forwardLookupTable[ srcImageData[ lineOffset + colLoop + memoryStep ] ];
|
||||
|
||||
// maintain symmetry
|
||||
matrices[stepLoop][pixelValue1][pixelValue2] ++;
|
||||
matrices[stepLoop][pixelValue2][pixelValue1] ++;
|
||||
|
||||
// incremenet counter of total number of increments
|
||||
stepIncrementsCounter[stepLoop] += 2;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// normalize matrices. each element is a probability of gray value i,j adjacency in direction/magnitude k
|
||||
for( sideLoop1=0; sideLoop1<matrixSideLength; sideLoop1++ )
|
||||
{
|
||||
for( sideLoop2=0; sideLoop2<matrixSideLength; sideLoop2++ )
|
||||
{
|
||||
for( stepLoop=0; stepLoop<numSteps; stepLoop++ )
|
||||
{
|
||||
matrices[stepLoop][sideLoop1][sideLoop2] /= double(stepIncrementsCounter[stepLoop]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
destGLCM->matrices = matrices;
|
||||
|
||||
__END__;
|
||||
|
||||
cvFree( &stepIncrementsCounter );
|
||||
|
||||
if( cvGetErrStatus() < 0 )
|
||||
cvReleaseGLCM( &destGLCM, CV_GLCM_GLCM );
|
||||
}
|
||||
|
||||
|
||||
CV_IMPL void
|
||||
cvCreateGLCMDescriptors( CvGLCM* destGLCM, int descriptorOptimizationType )
|
||||
{
|
||||
CV_FUNCNAME( "cvCreateGLCMDescriptors" );
|
||||
|
||||
__BEGIN__;
|
||||
|
||||
int matrixLoop;
|
||||
|
||||
if( !destGLCM )
|
||||
CV_ERROR( CV_StsNullPtr, "" );
|
||||
|
||||
if( !(destGLCM->matrices) )
|
||||
CV_ERROR( CV_StsNullPtr, "Matrices are not allocated" );
|
||||
|
||||
CV_CALL( cvReleaseGLCM( &destGLCM, CV_GLCM_DESC ));
|
||||
|
||||
if( destGLCM->optimizationType != CV_GLCM_OPTIMIZATION_HISTOGRAM )
|
||||
{
|
||||
destGLCM->descriptorOptimizationType = destGLCM->numDescriptors = descriptorOptimizationType;
|
||||
}
|
||||
else
|
||||
{
|
||||
CV_ERROR( CV_StsBadFlag, "Histogram-based method is not implemented" );
|
||||
// destGLCM->descriptorOptimizationType = destGLCM->numDescriptors = CV_GLCMDESC_OPTIMIZATION_HISTOGRAM;
|
||||
}
|
||||
|
||||
CV_CALL( destGLCM->descriptors = (double**)
|
||||
cvAlloc( destGLCM->numMatrices*sizeof(destGLCM->descriptors[0])));
|
||||
|
||||
for( matrixLoop = 0; matrixLoop < destGLCM->numMatrices; matrixLoop ++ )
|
||||
{
|
||||
CV_CALL( destGLCM->descriptors[ matrixLoop ] =
|
||||
(double*)cvAlloc( destGLCM->numDescriptors*sizeof(destGLCM->descriptors[0][0])));
|
||||
memset( destGLCM->descriptors[matrixLoop], 0, destGLCM->numDescriptors*sizeof(double) );
|
||||
|
||||
switch( destGLCM->descriptorOptimizationType )
|
||||
{
|
||||
case CV_GLCMDESC_OPTIMIZATION_ALLOWDOUBLENEST:
|
||||
icvCreateGLCMDescriptors_AllowDoubleNest( destGLCM, matrixLoop );
|
||||
break;
|
||||
default:
|
||||
CV_ERROR( CV_StsBadFlag,
|
||||
"descriptorOptimizationType different from CV_GLCMDESC_OPTIMIZATION_ALLOWDOUBLENEST\n"
|
||||
"is not supported" );
|
||||
/*
|
||||
case CV_GLCMDESC_OPTIMIZATION_ALLOWTRIPLENEST:
|
||||
icvCreateGLCMDescriptors_AllowTripleNest( destGLCM, matrixLoop );
|
||||
break;
|
||||
case CV_GLCMDESC_OPTIMIZATION_HISTOGRAM:
|
||||
if(matrixLoop < destGLCM->numMatrices>>1)
|
||||
icvCreateGLCMDescriptors_Histogram( destGLCM, matrixLoop);
|
||||
break;
|
||||
*/
|
||||
}
|
||||
}
|
||||
|
||||
__END__;
|
||||
|
||||
if( cvGetErrStatus() < 0 )
|
||||
cvReleaseGLCM( &destGLCM, CV_GLCM_DESC );
|
||||
}
|
||||
|
||||
|
||||
static void
|
||||
icvCreateGLCMDescriptors_AllowDoubleNest( CvGLCM* destGLCM, int matrixIndex )
|
||||
{
|
||||
int sideLoop1, sideLoop2;
|
||||
int matrixSideLength = destGLCM->matrixSideLength;
|
||||
|
||||
double** matrix = destGLCM->matrices[ matrixIndex ];
|
||||
double* descriptors = destGLCM->descriptors[ matrixIndex ];
|
||||
|
||||
double* marginalProbability =
|
||||
(double*)cvAlloc( matrixSideLength * sizeof(marginalProbability[0]));
|
||||
memset( marginalProbability, 0, matrixSideLength * sizeof(double) );
|
||||
|
||||
double maximumProbability = 0;
|
||||
double marginalProbabilityEntropy = 0;
|
||||
double correlationMean = 0, correlationStdDeviation = 0, correlationProductTerm = 0;
|
||||
|
||||
for( sideLoop1=0; sideLoop1<matrixSideLength; sideLoop1++ )
|
||||
{
|
||||
int actualSideLoop1 = destGLCM->reverseLookupTable[ sideLoop1 ];
|
||||
|
||||
for( sideLoop2=0; sideLoop2<matrixSideLength; sideLoop2++ )
|
||||
{
|
||||
double entryValue = matrix[ sideLoop1 ][ sideLoop2 ];
|
||||
|
||||
int actualSideLoop2 = destGLCM->reverseLookupTable[ sideLoop2 ];
|
||||
int sideLoopDifference = actualSideLoop1 - actualSideLoop2;
|
||||
int sideLoopDifferenceSquared = sideLoopDifference*sideLoopDifference;
|
||||
|
||||
marginalProbability[ sideLoop1 ] += entryValue;
|
||||
correlationMean += actualSideLoop1*entryValue;
|
||||
|
||||
maximumProbability = MAX( maximumProbability, entryValue );
|
||||
|
||||
if( actualSideLoop2 > actualSideLoop1 )
|
||||
{
|
||||
descriptors[ CV_GLCMDESC_CONTRAST ] += sideLoopDifferenceSquared * entryValue;
|
||||
}
|
||||
|
||||
descriptors[ CV_GLCMDESC_HOMOGENITY ] += entryValue / ( 1.0 + sideLoopDifferenceSquared );
|
||||
|
||||
if( entryValue > 0 )
|
||||
{
|
||||
descriptors[ CV_GLCMDESC_ENTROPY ] += entryValue * log( entryValue );
|
||||
}
|
||||
|
||||
descriptors[ CV_GLCMDESC_ENERGY ] += entryValue*entryValue;
|
||||
}
|
||||
|
||||
if( marginalProbability>0 )
|
||||
marginalProbabilityEntropy += marginalProbability[ actualSideLoop1 ]*log(marginalProbability[ actualSideLoop1 ]);
|
||||
}
|
||||
|
||||
marginalProbabilityEntropy = -marginalProbabilityEntropy;
|
||||
|
||||
descriptors[ CV_GLCMDESC_CONTRAST ] += descriptors[ CV_GLCMDESC_CONTRAST ];
|
||||
descriptors[ CV_GLCMDESC_ENTROPY ] = -descriptors[ CV_GLCMDESC_ENTROPY ];
|
||||
descriptors[ CV_GLCMDESC_MAXIMUMPROBABILITY ] = maximumProbability;
|
||||
|
||||
double HXY = 0, HXY1 = 0, HXY2 = 0;
|
||||
|
||||
HXY = descriptors[ CV_GLCMDESC_ENTROPY ];
|
||||
|
||||
for( sideLoop1=0; sideLoop1<matrixSideLength; sideLoop1++ )
|
||||
{
|
||||
double sideEntryValueSum = 0;
|
||||
int actualSideLoop1 = destGLCM->reverseLookupTable[ sideLoop1 ];
|
||||
|
||||
for( sideLoop2=0; sideLoop2<matrixSideLength; sideLoop2++ )
|
||||
{
|
||||
double entryValue = matrix[ sideLoop1 ][ sideLoop2 ];
|
||||
|
||||
sideEntryValueSum += entryValue;
|
||||
|
||||
int actualSideLoop2 = destGLCM->reverseLookupTable[ sideLoop2 ];
|
||||
|
||||
correlationProductTerm += (actualSideLoop1 - correlationMean) * (actualSideLoop2 - correlationMean) * entryValue;
|
||||
|
||||
double clusterTerm = actualSideLoop1 + actualSideLoop2 - correlationMean - correlationMean;
|
||||
|
||||
descriptors[ CV_GLCMDESC_CLUSTERTENDENCY ] += clusterTerm * clusterTerm * entryValue;
|
||||
descriptors[ CV_GLCMDESC_CLUSTERSHADE ] += clusterTerm * clusterTerm * clusterTerm * entryValue;
|
||||
|
||||
double HXYValue = marginalProbability[ actualSideLoop1 ] * marginalProbability[ actualSideLoop2 ];
|
||||
if( HXYValue>0 )
|
||||
{
|
||||
double HXYValueLog = log( HXYValue );
|
||||
HXY1 += entryValue * HXYValueLog;
|
||||
HXY2 += HXYValue * HXYValueLog;
|
||||
}
|
||||
}
|
||||
|
||||
correlationStdDeviation += (actualSideLoop1-correlationMean) * (actualSideLoop1-correlationMean) * sideEntryValueSum;
|
||||
}
|
||||
|
||||
HXY1 =- HXY1;
|
||||
HXY2 =- HXY2;
|
||||
|
||||
descriptors[ CV_GLCMDESC_CORRELATIONINFO1 ] = ( HXY - HXY1 ) / ( correlationMean );
|
||||
descriptors[ CV_GLCMDESC_CORRELATIONINFO2 ] = sqrt( 1.0 - exp( -2.0 * (HXY2 - HXY ) ) );
|
||||
|
||||
correlationStdDeviation = sqrt( correlationStdDeviation );
|
||||
|
||||
descriptors[ CV_GLCMDESC_CORRELATION ] = correlationProductTerm / (correlationStdDeviation*correlationStdDeviation );
|
||||
|
||||
delete [] marginalProbability;
|
||||
}
|
||||
|
||||
|
||||
CV_IMPL double cvGetGLCMDescriptor( CvGLCM* GLCM, int step, int descriptor )
|
||||
{
|
||||
double value = DBL_MAX;
|
||||
|
||||
CV_FUNCNAME( "cvGetGLCMDescriptor" );
|
||||
|
||||
__BEGIN__;
|
||||
|
||||
if( !GLCM )
|
||||
CV_ERROR( CV_StsNullPtr, "" );
|
||||
|
||||
if( !(GLCM->descriptors) )
|
||||
CV_ERROR( CV_StsNullPtr, "" );
|
||||
|
||||
if( (unsigned)step >= (unsigned)(GLCM->numMatrices))
|
||||
CV_ERROR( CV_StsOutOfRange, "step is not in 0 .. GLCM->numMatrices - 1" );
|
||||
|
||||
if( (unsigned)descriptor >= (unsigned)(GLCM->numDescriptors))
|
||||
CV_ERROR( CV_StsOutOfRange, "descriptor is not in 0 .. GLCM->numDescriptors - 1" );
|
||||
|
||||
value = GLCM->descriptors[step][descriptor];
|
||||
|
||||
__END__;
|
||||
|
||||
return value;
|
||||
}
|
||||
|
||||
|
||||
CV_IMPL void
|
||||
cvGetGLCMDescriptorStatistics( CvGLCM* GLCM, int descriptor,
|
||||
double* _average, double* _standardDeviation )
|
||||
{
|
||||
CV_FUNCNAME( "cvGetGLCMDescriptorStatistics" );
|
||||
|
||||
if( _average )
|
||||
*_average = DBL_MAX;
|
||||
|
||||
if( _standardDeviation )
|
||||
*_standardDeviation = DBL_MAX;
|
||||
|
||||
__BEGIN__;
|
||||
|
||||
int matrixLoop, numMatrices;
|
||||
double average = 0, squareSum = 0;
|
||||
|
||||
if( !GLCM )
|
||||
CV_ERROR( CV_StsNullPtr, "" );
|
||||
|
||||
if( !(GLCM->descriptors))
|
||||
CV_ERROR( CV_StsNullPtr, "Descriptors are not calculated" );
|
||||
|
||||
if( (unsigned)descriptor >= (unsigned)(GLCM->numDescriptors) )
|
||||
CV_ERROR( CV_StsOutOfRange, "Descriptor index is out of range" );
|
||||
|
||||
numMatrices = GLCM->numMatrices;
|
||||
|
||||
for( matrixLoop = 0; matrixLoop < numMatrices; matrixLoop++ )
|
||||
{
|
||||
double temp = GLCM->descriptors[ matrixLoop ][ descriptor ];
|
||||
average += temp;
|
||||
squareSum += temp*temp;
|
||||
}
|
||||
|
||||
average /= numMatrices;
|
||||
|
||||
if( _average )
|
||||
*_average = average;
|
||||
|
||||
if( _standardDeviation )
|
||||
*_standardDeviation = sqrt( (squareSum - average*average*numMatrices)/(numMatrices-1));
|
||||
|
||||
__END__;
|
||||
}
|
||||
|
||||
|
||||
CV_IMPL IplImage*
|
||||
cvCreateGLCMImage( CvGLCM* GLCM, int step )
|
||||
{
|
||||
IplImage* dest = 0;
|
||||
|
||||
CV_FUNCNAME( "cvCreateGLCMImage" );
|
||||
|
||||
__BEGIN__;
|
||||
|
||||
float* destData;
|
||||
int sideLoop1, sideLoop2;
|
||||
|
||||
if( !GLCM )
|
||||
CV_ERROR( CV_StsNullPtr, "" );
|
||||
|
||||
if( !(GLCM->matrices) )
|
||||
CV_ERROR( CV_StsNullPtr, "Matrices are not allocated" );
|
||||
|
||||
if( (unsigned)step >= (unsigned)(GLCM->numMatrices) )
|
||||
CV_ERROR( CV_StsOutOfRange, "The step index is out of range" );
|
||||
|
||||
dest = cvCreateImage( cvSize( GLCM->matrixSideLength, GLCM->matrixSideLength ), IPL_DEPTH_32F, 1 );
|
||||
destData = (float*)(dest->imageData);
|
||||
|
||||
for( sideLoop1 = 0; sideLoop1 < GLCM->matrixSideLength;
|
||||
sideLoop1++, (float*&)destData += dest->widthStep )
|
||||
{
|
||||
for( sideLoop2=0; sideLoop2 < GLCM->matrixSideLength; sideLoop2++ )
|
||||
{
|
||||
double matrixValue = GLCM->matrices[step][sideLoop1][sideLoop2];
|
||||
destData[ sideLoop2 ] = (float)matrixValue;
|
||||
}
|
||||
}
|
||||
|
||||
__END__;
|
||||
|
||||
if( cvGetErrStatus() < 0 )
|
||||
cvReleaseImage( &dest );
|
||||
|
||||
return dest;
|
||||
}
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,975 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
/****************************************************************************************\
|
||||
Contour-based face feature tracking
|
||||
The code was created by Tatiana Cherepanova (tata@sl.iae.nsk.su)
|
||||
\****************************************************************************************/
|
||||
|
||||
#include "_cvaux.h"
|
||||
#include "_cvvectrack.h"
|
||||
|
||||
#define _ASSERT assert
|
||||
#define NUM_FACE_ELEMENTS 3
|
||||
enum
|
||||
{
|
||||
MOUTH = 0,
|
||||
LEYE = 1,
|
||||
REYE = 2,
|
||||
};
|
||||
|
||||
#define MAX_LAYERS 64
|
||||
|
||||
const double pi = 3.1415926535;
|
||||
|
||||
struct CvFaceTracker;
|
||||
struct CvTrackingRect;
|
||||
class CvFaceElement;
|
||||
|
||||
void ThresholdingParam(IplImage *imgGray, int iNumLayers, int &iMinLevel, int &iMaxLevel, float &step, float& power, int iHistMin /*= HIST_MIN*/);
|
||||
int ChoiceTrackingFace3(CvFaceTracker* pTF, const int nElements, const CvFaceElement* big_face, CvTrackingRect* face, int& new_energy);
|
||||
int ChoiceTrackingFace2(CvFaceTracker* pTF, const int nElements, const CvFaceElement* big_face, CvTrackingRect* face, int& new_energy, int noel);
|
||||
inline int GetEnergy(CvTrackingRect** ppNew, const CvTrackingRect* pPrev, CvPoint* ptTempl, CvRect* rTempl);
|
||||
inline int GetEnergy2(CvTrackingRect** ppNew, const CvTrackingRect* pPrev, CvPoint* ptTempl, CvRect* rTempl, int* element);
|
||||
inline double CalculateTransformationLMS3_0( CvPoint* pTemplPoints, CvPoint* pSrcPoints);
|
||||
inline double CalculateTransformationLMS3( CvPoint* pTemplPoints,
|
||||
CvPoint* pSrcPoints,
|
||||
double* pdbAverageScale,
|
||||
double* pdbAverageRotate,
|
||||
double* pdbAverageShiftX,
|
||||
double* pdbAverageShiftY );
|
||||
|
||||
struct CvTrackingRect
|
||||
{
|
||||
CvRect r;
|
||||
CvPoint ptCenter;
|
||||
int iColor;
|
||||
int iEnergy;
|
||||
int nRectsInThis;
|
||||
int nRectsOnLeft;
|
||||
int nRectsOnRight;
|
||||
int nRectsOnTop;
|
||||
int nRectsOnBottom;
|
||||
CvTrackingRect() { memset(this, 0, sizeof(CvTrackingRect)); };
|
||||
int Energy(const CvTrackingRect& prev)
|
||||
{
|
||||
int prev_color = 0 == prev.iColor ? iColor : prev.iColor;
|
||||
iEnergy = 1 * pow2(r.width - prev.r.width) +
|
||||
1 * pow2(r.height - prev.r.height) +
|
||||
1 * pow2(iColor - prev_color) / 4 +
|
||||
- 1 * nRectsInThis +
|
||||
- 0 * nRectsOnTop +
|
||||
+ 0 * nRectsOnLeft +
|
||||
+ 0 * nRectsOnRight +
|
||||
+ 0 * nRectsOnBottom;
|
||||
return iEnergy;
|
||||
}
|
||||
};
|
||||
|
||||
struct CvFaceTracker
|
||||
{
|
||||
CvTrackingRect face[NUM_FACE_ELEMENTS];
|
||||
int iTrackingFaceType;
|
||||
double dbRotateDelta;
|
||||
double dbRotateAngle;
|
||||
CvPoint ptRotate;
|
||||
|
||||
CvPoint ptTempl[NUM_FACE_ELEMENTS];
|
||||
CvRect rTempl[NUM_FACE_ELEMENTS];
|
||||
|
||||
IplImage* imgGray;
|
||||
IplImage* imgThresh;
|
||||
CvMemStorage* mstgContours;
|
||||
CvFaceTracker()
|
||||
{
|
||||
ptRotate.x = 0;
|
||||
ptRotate.y = 0;
|
||||
dbRotateDelta = 0;
|
||||
dbRotateAngle = 0;
|
||||
iTrackingFaceType = -1;
|
||||
imgThresh = NULL;
|
||||
imgGray = NULL;
|
||||
mstgContours = NULL;
|
||||
};
|
||||
~CvFaceTracker()
|
||||
{
|
||||
if (NULL != imgGray)
|
||||
delete imgGray;
|
||||
if (NULL != imgThresh)
|
||||
delete imgThresh;
|
||||
if (NULL != mstgContours)
|
||||
cvReleaseMemStorage(&mstgContours);
|
||||
};
|
||||
int Init(CvRect* pRects, IplImage* imgGray)
|
||||
{
|
||||
for (int i = 0; i < NUM_FACE_ELEMENTS; i++)
|
||||
{
|
||||
face[i].r = pRects[i];
|
||||
face[i].ptCenter = Center(face[i].r);
|
||||
ptTempl[i] = face[i].ptCenter;
|
||||
rTempl[i] = face[i].r;
|
||||
}
|
||||
imgGray = cvCreateImage(cvSize(imgGray->width, imgGray->height), 8, 1);
|
||||
imgThresh = cvCreateImage(cvSize(imgGray->width, imgGray->height), 8, 1);
|
||||
mstgContours = cvCreateMemStorage();
|
||||
if ((NULL == imgGray) ||
|
||||
(NULL == imgThresh) ||
|
||||
(NULL == mstgContours))
|
||||
return FALSE;
|
||||
return TRUE;
|
||||
};
|
||||
int InitNextImage(IplImage* img)
|
||||
{
|
||||
CvSize sz = {img->width, img->height};
|
||||
ReallocImage(&imgGray, sz, 1);
|
||||
ReallocImage(&imgThresh, sz, 1);
|
||||
ptRotate = face[MOUTH].ptCenter;
|
||||
float m[6];
|
||||
CvMat mat = cvMat( 2, 3, CV_32FC1, m );
|
||||
|
||||
if (NULL == imgGray || NULL == imgThresh)
|
||||
return FALSE;
|
||||
|
||||
/*m[0] = (float)cos(-dbRotateAngle*CV_PI/180.);
|
||||
m[1] = (float)sin(-dbRotateAngle*CV_PI/180.);
|
||||
m[2] = (float)ptRotate.x;
|
||||
m[3] = -m[1];
|
||||
m[4] = m[0];
|
||||
m[5] = (float)ptRotate.y;*/
|
||||
cv2DRotationMatrix( cvPointTo32f(ptRotate), -dbRotateAngle, 1., &mat );
|
||||
cvWarpAffine( img, imgGray, &mat );
|
||||
|
||||
if (NULL == mstgContours)
|
||||
mstgContours = cvCreateMemStorage();
|
||||
else
|
||||
cvClearMemStorage(mstgContours);
|
||||
if (NULL == mstgContours)
|
||||
return FALSE;
|
||||
return TRUE;
|
||||
}
|
||||
};
|
||||
|
||||
class CvFaceElement
|
||||
{
|
||||
public:
|
||||
CvSeq* m_seqRects;
|
||||
CvMemStorage* m_mstgRects;
|
||||
CvRect m_rROI;
|
||||
CvTrackingRect m_trPrev;
|
||||
inline CvFaceElement()
|
||||
{
|
||||
m_seqRects = NULL;
|
||||
m_mstgRects = NULL;
|
||||
m_rROI.x = 0;
|
||||
m_rROI.y = 0;
|
||||
m_rROI.width = 0;
|
||||
m_rROI.height = 0;
|
||||
};
|
||||
inline int Init(const CvRect& roi, const CvTrackingRect& prev, CvMemStorage* mstg = NULL)
|
||||
{
|
||||
m_rROI = roi;
|
||||
m_trPrev = prev;
|
||||
if (NULL != mstg)
|
||||
m_mstgRects = mstg;
|
||||
if (NULL == m_mstgRects)
|
||||
return FALSE;
|
||||
if (NULL == m_seqRects)
|
||||
m_seqRects = cvCreateSeq(0, sizeof(CvSeq), sizeof(CvTrackingRect), m_mstgRects);
|
||||
else
|
||||
cvClearSeq(m_seqRects);
|
||||
if (NULL == m_seqRects)
|
||||
return FALSE;
|
||||
return TRUE;
|
||||
};
|
||||
void FindRects(IplImage* img, IplImage* thresh, int nLayers, int dMinSize);
|
||||
protected:
|
||||
void FindContours(IplImage* img, IplImage* thresh, int nLayers, int dMinSize);
|
||||
void MergeRects(int d);
|
||||
void Energy();
|
||||
}; //class CvFaceElement
|
||||
|
||||
int CV_CDECL CompareEnergy(const void* el1, const void* el2, void*)
|
||||
{
|
||||
return ((CvTrackingRect*)el1)->iEnergy - ((CvTrackingRect*)el2)->iEnergy;
|
||||
}// int CV_CDECL CompareEnergy(const void* el1, const void* el2, void*)
|
||||
|
||||
void CvFaceElement::FindRects(IplImage* img, IplImage* thresh, int nLayers, int dMinSize)
|
||||
{
|
||||
FindContours(img, thresh, nLayers, dMinSize / 4);
|
||||
if (0 == m_seqRects->total)
|
||||
return;
|
||||
Energy();
|
||||
cvSeqSort(m_seqRects, CompareEnergy, NULL);
|
||||
CvTrackingRect* pR = (CvTrackingRect*)cvGetSeqElem(m_seqRects, 0);
|
||||
if (m_seqRects->total < 32)
|
||||
{
|
||||
MergeRects(dMinSize / 8);
|
||||
Energy();
|
||||
cvSeqSort(m_seqRects, CompareEnergy, NULL);
|
||||
}
|
||||
pR = (CvTrackingRect*)cvGetSeqElem(m_seqRects, 0);
|
||||
if ((pR->iEnergy > 100 && m_seqRects->total < 32) || (m_seqRects->total < 16))
|
||||
{
|
||||
MergeRects(dMinSize / 4);
|
||||
Energy();
|
||||
cvSeqSort(m_seqRects, CompareEnergy, NULL);
|
||||
}
|
||||
pR = (CvTrackingRect*)cvGetSeqElem(m_seqRects, 0);
|
||||
if ((pR->iEnergy > 100 && m_seqRects->total < 16) || (pR->iEnergy > 200 && m_seqRects->total < 32))
|
||||
{
|
||||
MergeRects(dMinSize / 2);
|
||||
Energy();
|
||||
cvSeqSort(m_seqRects, CompareEnergy, NULL);
|
||||
}
|
||||
|
||||
}// void CvFaceElement::FindRects(IplImage* img, IplImage* thresh, int nLayers, int dMinSize)
|
||||
|
||||
void CvFaceElement::FindContours(IplImage* img, IplImage* thresh, int nLayers, int dMinSize)
|
||||
{
|
||||
CvSeq* seq;
|
||||
CvRect roi = m_rROI;
|
||||
Extend(roi, 1);
|
||||
cvSetImageROI(img, roi);
|
||||
cvSetImageROI(thresh, roi);
|
||||
// layers
|
||||
int colors[MAX_LAYERS] = {0};
|
||||
int iMinLevel = 0, iMaxLevel = 255;
|
||||
float step, power;
|
||||
ThresholdingParam(img, nLayers / 2, iMinLevel, iMaxLevel, step, power, 4);
|
||||
int iMinLevelPrev = iMinLevel;
|
||||
int iMaxLevelPrev = iMinLevel;
|
||||
if (m_trPrev.iColor != 0)
|
||||
{
|
||||
iMinLevelPrev = m_trPrev.iColor - nLayers / 2;
|
||||
iMaxLevelPrev = m_trPrev.iColor + nLayers / 2;
|
||||
}
|
||||
if (iMinLevelPrev < iMinLevel)
|
||||
{
|
||||
iMaxLevelPrev += iMinLevel - iMinLevelPrev;
|
||||
iMinLevelPrev = iMinLevel;
|
||||
}
|
||||
if (iMaxLevelPrev > iMaxLevel)
|
||||
{
|
||||
iMinLevelPrev -= iMaxLevelPrev - iMaxLevel;
|
||||
if (iMinLevelPrev < iMinLevel)
|
||||
iMinLevelPrev = iMinLevel;
|
||||
iMaxLevelPrev = iMaxLevel;
|
||||
}
|
||||
int n = nLayers;
|
||||
n -= (iMaxLevelPrev - iMinLevelPrev + 1) / 2;
|
||||
step = float(iMinLevelPrev - iMinLevel + iMaxLevel - iMaxLevelPrev) / float(n);
|
||||
int j = 0;
|
||||
float level;
|
||||
for (level = (float)iMinLevel; level < iMinLevelPrev && j < nLayers; level += step, j++)
|
||||
colors[j] = int(level + 0.5);
|
||||
for (level = (float)iMinLevelPrev; level < iMaxLevelPrev && j < nLayers; level += 2.0, j++)
|
||||
colors[j] = int(level + 0.5);
|
||||
for (level = (float)iMaxLevelPrev; level < iMaxLevel && j < nLayers; level += step, j++)
|
||||
colors[j] = int(level + 0.5);
|
||||
//
|
||||
for (int i = 0; i < nLayers; i++)
|
||||
{
|
||||
cvThreshold(img, thresh, colors[i], 255.0, CV_THRESH_BINARY);
|
||||
if (cvFindContours(thresh, m_mstgRects, &seq, sizeof(CvContour), CV_RETR_CCOMP, CV_CHAIN_APPROX_SIMPLE))
|
||||
{
|
||||
CvTrackingRect cr;
|
||||
for (CvSeq* external = seq; external; external = external->h_next)
|
||||
{
|
||||
cr.r = cvContourBoundingRect(external);
|
||||
Move(cr.r, roi.x, roi.y);
|
||||
if (RectInRect(cr.r, m_rROI) && cr.r.width > dMinSize && cr.r.height > dMinSize)
|
||||
{
|
||||
cr.ptCenter = Center(cr.r);
|
||||
cr.iColor = colors[i];
|
||||
cvSeqPush(m_seqRects, &cr);
|
||||
}
|
||||
for (CvSeq* internal = external->v_next; internal; internal = internal->h_next)
|
||||
{
|
||||
cr.r = cvContourBoundingRect(internal);
|
||||
Move(cr.r, roi.x, roi.y);
|
||||
if (RectInRect(cr.r, m_rROI) && cr.r.width > dMinSize && cr.r.height > dMinSize)
|
||||
{
|
||||
cr.ptCenter = Center(cr.r);
|
||||
cr.iColor = colors[i];
|
||||
cvSeqPush(m_seqRects, &cr);
|
||||
}
|
||||
}
|
||||
}
|
||||
cvClearSeq(seq);
|
||||
}
|
||||
}
|
||||
cvResetImageROI(img);
|
||||
cvResetImageROI(thresh);
|
||||
}//void CvFaceElement::FindContours(IplImage* img, IplImage* thresh, int nLayers)
|
||||
|
||||
void CvFaceElement::MergeRects(int d)
|
||||
{
|
||||
int nRects = m_seqRects->total;
|
||||
CvSeqReader reader, reader2;
|
||||
cvStartReadSeq( m_seqRects, &reader );
|
||||
int i, j;
|
||||
for (i = 0; i < nRects; i++)
|
||||
{
|
||||
CvTrackingRect* pRect1 = (CvTrackingRect*)(reader.ptr);
|
||||
cvStartReadSeq( m_seqRects, &reader2 );
|
||||
cvSetSeqReaderPos(&reader2, i + 1);
|
||||
for (j = i + 1; j < nRects; j++)
|
||||
{
|
||||
CvTrackingRect* pRect2 = (CvTrackingRect*)(reader2.ptr);
|
||||
if (abs(pRect1->ptCenter.y - pRect2->ptCenter.y) < d &&
|
||||
abs(pRect1->r.height - pRect2->r.height) < d)
|
||||
{
|
||||
CvTrackingRect rNew;
|
||||
rNew.iColor = (pRect1->iColor + pRect2->iColor + 1) / 2;
|
||||
rNew.r.x = min(pRect1->r.x, pRect2->r.x);
|
||||
rNew.r.y = min(pRect1->r.y, pRect2->r.y);
|
||||
rNew.r.width = max(pRect1->r.x + pRect1->r.width, pRect2->r.x + pRect2->r.width) - rNew.r.x;
|
||||
rNew.r.height = min(pRect1->r.y + pRect1->r.height, pRect2->r.y + pRect2->r.height) - rNew.r.y;
|
||||
if (rNew.r != pRect1->r && rNew.r != pRect2->r)
|
||||
{
|
||||
rNew.ptCenter = Center(rNew.r);
|
||||
cvSeqPush(m_seqRects, &rNew);
|
||||
}
|
||||
}
|
||||
CV_NEXT_SEQ_ELEM( sizeof(CvTrackingRect), reader2 );
|
||||
}
|
||||
CV_NEXT_SEQ_ELEM( sizeof(CvTrackingRect), reader );
|
||||
}
|
||||
// delete equal rects
|
||||
for (i = 0; i < m_seqRects->total; i++)
|
||||
{
|
||||
CvTrackingRect* pRect1 = (CvTrackingRect*)cvGetSeqElem(m_seqRects, i);
|
||||
int j_begin = i + 1;
|
||||
for (j = j_begin; j < m_seqRects->total;)
|
||||
{
|
||||
CvTrackingRect* pRect2 = (CvTrackingRect*)cvGetSeqElem(m_seqRects, j);
|
||||
if (pRect1->r == pRect2->r)
|
||||
cvSeqRemove(m_seqRects, j);
|
||||
else
|
||||
j++;
|
||||
}
|
||||
}
|
||||
|
||||
}//void CvFaceElement::MergeRects(int d)
|
||||
|
||||
void CvFaceElement::Energy()
|
||||
{
|
||||
CvSeqReader reader, reader2;
|
||||
cvStartReadSeq( m_seqRects, &reader );
|
||||
for (int i = 0; i < m_seqRects->total; i++)
|
||||
{
|
||||
CvTrackingRect* pRect = (CvTrackingRect*)(reader.ptr);
|
||||
// outside and inside rects
|
||||
cvStartReadSeq( m_seqRects, &reader2 );
|
||||
for (int j = 0; j < m_seqRects->total; j++)
|
||||
{
|
||||
CvTrackingRect* pRect2 = (CvTrackingRect*)(reader2.ptr);
|
||||
if (i != j)
|
||||
{
|
||||
if (RectInRect(pRect2->r, pRect->r))
|
||||
pRect->nRectsInThis ++;
|
||||
else if (pRect2->r.y + pRect2->r.height <= pRect->r.y)
|
||||
pRect->nRectsOnTop ++;
|
||||
else if (pRect2->r.y >= pRect->r.y + pRect->r.height)
|
||||
pRect->nRectsOnBottom ++;
|
||||
else if (pRect2->r.x + pRect2->r.width <= pRect->r.x)
|
||||
pRect->nRectsOnLeft ++;
|
||||
else if (pRect2->r.x >= pRect->r.x + pRect->r.width)
|
||||
pRect->nRectsOnRight ++;
|
||||
}
|
||||
CV_NEXT_SEQ_ELEM( sizeof(CvTrackingRect), reader2 );
|
||||
}
|
||||
// energy
|
||||
pRect->Energy(m_trPrev);
|
||||
CV_NEXT_SEQ_ELEM( sizeof(CvTrackingRect), reader );
|
||||
}
|
||||
}//void CvFaceElement::Energy()
|
||||
|
||||
CV_IMPL CvFaceTracker*
|
||||
cvInitFaceTracker(CvFaceTracker* pFaceTracker, const IplImage* imgGray, CvRect* pRects, int nRects)
|
||||
{
|
||||
_ASSERT(NULL != imgGray);
|
||||
_ASSERT(NULL != pRects);
|
||||
_ASSERT(nRects >= NUM_FACE_ELEMENTS);
|
||||
if ((NULL == imgGray) ||
|
||||
(NULL == pRects) ||
|
||||
(nRects < NUM_FACE_ELEMENTS))
|
||||
return NULL;
|
||||
|
||||
int new_face = FALSE;
|
||||
CvFaceTracker* pFace = pFaceTracker;
|
||||
if (NULL == pFace)
|
||||
{
|
||||
pFace = new CvFaceTracker;
|
||||
if (NULL == pFace)
|
||||
return NULL;
|
||||
new_face = TRUE;
|
||||
}
|
||||
pFace->Init(pRects, (IplImage*)imgGray);
|
||||
return pFace;
|
||||
}//CvFaceTracker* InitFaceTracker(IplImage* imgGray, CvRect* pRects, int nRects)
|
||||
|
||||
CV_IMPL void
|
||||
cvReleaseFaceTracker(CvFaceTracker** ppFaceTracker)
|
||||
{
|
||||
if (NULL == *ppFaceTracker)
|
||||
return;
|
||||
delete *ppFaceTracker;
|
||||
*ppFaceTracker = NULL;
|
||||
}//void ReleaseFaceTracker(CvFaceTracker** ppFaceTracker)
|
||||
|
||||
|
||||
CV_IMPL int
|
||||
cvTrackFace(CvFaceTracker* pFaceTracker, IplImage* imgGray, CvRect* pRects, int nRects, CvPoint* ptRotate, double* dbAngleRotate)
|
||||
{
|
||||
_ASSERT(NULL != pFaceTracker);
|
||||
_ASSERT(NULL != imgGray);
|
||||
_ASSERT(NULL != pRects && nRects >= NUM_FACE_ELEMENTS);
|
||||
if ((NULL == pFaceTracker) ||
|
||||
(NULL == imgGray))
|
||||
return FALSE;
|
||||
pFaceTracker->InitNextImage(imgGray);
|
||||
*ptRotate = pFaceTracker->ptRotate;
|
||||
*dbAngleRotate = pFaceTracker->dbRotateAngle;
|
||||
|
||||
int nElements = 16;
|
||||
double dx = pFaceTracker->face[LEYE].ptCenter.x - pFaceTracker->face[REYE].ptCenter.x;
|
||||
double dy = pFaceTracker->face[LEYE].ptCenter.y - pFaceTracker->face[REYE].ptCenter.y;
|
||||
double d_eyes = sqrt(dx*dx + dy*dy);
|
||||
int d = cvRound(0.25 * d_eyes);
|
||||
int dMinSize = d;
|
||||
int nRestarts = 0;
|
||||
|
||||
int elem;
|
||||
|
||||
CvFaceElement big_face[NUM_FACE_ELEMENTS];
|
||||
START:
|
||||
// init
|
||||
for (elem = 0; elem < NUM_FACE_ELEMENTS; elem++)
|
||||
{
|
||||
CvRect r = pFaceTracker->face[elem].r;
|
||||
Extend(r, d);
|
||||
if (r.width < 4*d)
|
||||
{
|
||||
r.x -= (4*d - r.width) / 2;
|
||||
r.width += 4*d - r.width;
|
||||
}
|
||||
if (r.height < 3*d)
|
||||
{
|
||||
r.y -= (3*d - r.height) / 2;
|
||||
r.height += 3*d - r.height;
|
||||
}
|
||||
if (r.x < 1)
|
||||
r.x = 1;
|
||||
if (r.y < 1)
|
||||
r.y = 1;
|
||||
if (r.x + r.width > pFaceTracker->imgGray->width - 2)
|
||||
r.width = pFaceTracker->imgGray->width - 2 - r.x;
|
||||
if (r.y + r.height > pFaceTracker->imgGray->height - 2)
|
||||
r.height = pFaceTracker->imgGray->height - 2 - r.y;
|
||||
if (!big_face[elem].Init(r, pFaceTracker->face[elem], pFaceTracker->mstgContours))
|
||||
return FALSE;
|
||||
}
|
||||
// find contours
|
||||
for (elem = 0; elem < NUM_FACE_ELEMENTS; elem++)
|
||||
big_face[elem].FindRects(pFaceTracker->imgGray, pFaceTracker->imgThresh, 32, dMinSize);
|
||||
// candidats
|
||||
CvTrackingRect new_face[NUM_FACE_ELEMENTS];
|
||||
int new_energy = 0;
|
||||
int found = ChoiceTrackingFace3(pFaceTracker, nElements, big_face, new_face, new_energy);
|
||||
int restart = FALSE;
|
||||
int find2 = FALSE;
|
||||
int noel = -1;
|
||||
if (found)
|
||||
{
|
||||
if (new_energy > 100000 && -1 != pFaceTracker->iTrackingFaceType)
|
||||
find2 = TRUE;
|
||||
else if (new_energy > 150000)
|
||||
{
|
||||
int elements = 0;
|
||||
for (int el = 0; el < NUM_FACE_ELEMENTS; el++)
|
||||
{
|
||||
if (big_face[el].m_seqRects->total > 16 || (big_face[el].m_seqRects->total > 8 && new_face[el].iEnergy < 100))
|
||||
elements++;
|
||||
else
|
||||
noel = el;
|
||||
}
|
||||
if (2 == elements)
|
||||
find2 = TRUE;
|
||||
else
|
||||
restart = TRUE;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (-1 != pFaceTracker->iTrackingFaceType)
|
||||
find2 = TRUE;
|
||||
else
|
||||
restart = TRUE;
|
||||
}
|
||||
RESTART:
|
||||
if (restart)
|
||||
{
|
||||
if (nRestarts++ < 2)
|
||||
{
|
||||
d = d + d/4;
|
||||
goto START;
|
||||
}
|
||||
}
|
||||
else if (find2)
|
||||
{
|
||||
if (-1 != pFaceTracker->iTrackingFaceType)
|
||||
noel = pFaceTracker->iTrackingFaceType;
|
||||
int found2 = ChoiceTrackingFace2(pFaceTracker, nElements, big_face, new_face, new_energy, noel);
|
||||
if (found2 && new_energy < 100000)
|
||||
{
|
||||
pFaceTracker->iTrackingFaceType = noel;
|
||||
found = TRUE;
|
||||
}
|
||||
else
|
||||
{
|
||||
restart = TRUE;
|
||||
goto RESTART;
|
||||
}
|
||||
}
|
||||
|
||||
if (found)
|
||||
{
|
||||
// angle by mouth & eyes
|
||||
double vx_prev = double(pFaceTracker->face[LEYE].ptCenter.x + pFaceTracker->face[REYE].ptCenter.x) / 2.0 - pFaceTracker->face[MOUTH].ptCenter.x;
|
||||
double vy_prev = double(pFaceTracker->face[LEYE].ptCenter.y + pFaceTracker->face[REYE].ptCenter.y) / 2.0 - pFaceTracker->face[MOUTH].ptCenter.y;
|
||||
double vx_prev1 = vx_prev * cos(pFaceTracker->dbRotateDelta) - vy_prev * sin(pFaceTracker->dbRotateDelta);
|
||||
double vy_prev1 = vx_prev * sin(pFaceTracker->dbRotateDelta) + vy_prev * cos(pFaceTracker->dbRotateDelta);
|
||||
vx_prev = vx_prev1;
|
||||
vy_prev = vy_prev1;
|
||||
for (elem = 0; elem < NUM_FACE_ELEMENTS; elem++)
|
||||
pFaceTracker->face[elem] = new_face[elem];
|
||||
double vx = double(pFaceTracker->face[LEYE].ptCenter.x + pFaceTracker->face[REYE].ptCenter.x) / 2.0 - pFaceTracker->face[MOUTH].ptCenter.x;
|
||||
double vy = double(pFaceTracker->face[LEYE].ptCenter.y + pFaceTracker->face[REYE].ptCenter.y) / 2.0 - pFaceTracker->face[MOUTH].ptCenter.y;
|
||||
pFaceTracker->dbRotateDelta = 0;
|
||||
double n1_n2 = (vx * vx + vy * vy) * (vx_prev * vx_prev + vy_prev * vy_prev);
|
||||
if (n1_n2 != 0)
|
||||
pFaceTracker->dbRotateDelta = asin((vx * vy_prev - vx_prev * vy) / sqrt(n1_n2));
|
||||
pFaceTracker->dbRotateAngle -= pFaceTracker->dbRotateDelta;
|
||||
}
|
||||
else
|
||||
{
|
||||
pFaceTracker->dbRotateDelta = 0;
|
||||
pFaceTracker->dbRotateAngle = 0;
|
||||
}
|
||||
if ((pFaceTracker->dbRotateAngle >= pi/2 && pFaceTracker->dbRotateAngle > 0) ||
|
||||
(pFaceTracker->dbRotateAngle <= -pi/2 && pFaceTracker->dbRotateAngle < 0))
|
||||
{
|
||||
pFaceTracker->dbRotateDelta = 0;
|
||||
pFaceTracker->dbRotateAngle = 0;
|
||||
found = FALSE;
|
||||
}
|
||||
if (found)
|
||||
{
|
||||
for (int i = 0; i < NUM_FACE_ELEMENTS && i < nRects; i++)
|
||||
pRects[i] = pFaceTracker->face[i].r;
|
||||
}
|
||||
return found;
|
||||
}//int FindFaceTracker(CvFaceTracker* pFaceTracker, IplImage* imgGray, CvRect* pRects, int nRects, CvPoint& ptRotate, double& dbAngleRotate)
|
||||
|
||||
void ThresholdingParam(IplImage *imgGray, int iNumLayers, int &iMinLevel, int &iMaxLevel, float &step, float& power, int iHistMin /*= HIST_MIN*/)
|
||||
{
|
||||
_ASSERT(imgGray != NULL);
|
||||
_ASSERT(imgGray->nChannels == 1);
|
||||
int i, j;
|
||||
// create histogram
|
||||
int histImg[256] = {0};
|
||||
uchar* buffImg = (uchar*)imgGray->imageData;
|
||||
CvRect rROI = cvGetImageROI(imgGray);
|
||||
buffImg += rROI.y * imgGray->widthStep + rROI.x;
|
||||
for (j = 0; j < rROI.height; j++)
|
||||
{
|
||||
for (i = 0; i < rROI.width; i++)
|
||||
histImg[buffImg[i]] ++;
|
||||
buffImg += imgGray->widthStep;
|
||||
}
|
||||
// params
|
||||
for (i = 0; i < 256; i++)
|
||||
{
|
||||
if (histImg[i] > iHistMin)
|
||||
break;
|
||||
}
|
||||
iMinLevel = i;
|
||||
for (i = 255; i >= 0; i--)
|
||||
{
|
||||
if (histImg[i] > iHistMin)
|
||||
break;
|
||||
}
|
||||
iMaxLevel = i;
|
||||
if (iMaxLevel <= iMinLevel)
|
||||
{
|
||||
iMaxLevel = 255;
|
||||
iMinLevel = 0;
|
||||
}
|
||||
// power
|
||||
double black = 1;
|
||||
double white = 1;
|
||||
for (i = iMinLevel; i < (iMinLevel + iMaxLevel) / 2; i++)
|
||||
black += histImg[i];
|
||||
for (i = (iMinLevel + iMaxLevel) / 2; i < iMaxLevel; i++)
|
||||
white += histImg[i];
|
||||
power = float(black) / float(2 * white);
|
||||
//
|
||||
step = float(iMaxLevel - iMinLevel) / float(iNumLayers);
|
||||
if (step < 1.0)
|
||||
step = 1.0;
|
||||
}// void ThresholdingParam(IplImage *imgGray, int iNumLayers, int &iMinLevel, int &iMaxLevel, int &iStep)
|
||||
|
||||
int ChoiceTrackingFace3(CvFaceTracker* pTF, const int nElements, const CvFaceElement* big_face, CvTrackingRect* face, int& new_energy)
|
||||
{
|
||||
CvTrackingRect* curr_face[NUM_FACE_ELEMENTS] = {NULL};
|
||||
CvTrackingRect* new_face[NUM_FACE_ELEMENTS] = {NULL};
|
||||
new_energy = 0x7fffffff;
|
||||
int curr_energy = 0x7fffffff;
|
||||
int found = FALSE;
|
||||
int N = 0;
|
||||
CvSeqReader reader_m, reader_l, reader_r;
|
||||
cvStartReadSeq( big_face[MOUTH].m_seqRects, &reader_m );
|
||||
for (int i_mouth = 0; i_mouth < big_face[MOUTH].m_seqRects->total && i_mouth < nElements; i_mouth++)
|
||||
{
|
||||
curr_face[MOUTH] = (CvTrackingRect*)(reader_m.ptr);
|
||||
cvStartReadSeq( big_face[LEYE].m_seqRects, &reader_l );
|
||||
for (int i_left = 0; i_left < big_face[LEYE].m_seqRects->total && i_left < nElements; i_left++)
|
||||
{
|
||||
curr_face[LEYE] = (CvTrackingRect*)(reader_l.ptr);
|
||||
if (curr_face[LEYE]->r.y + curr_face[LEYE]->r.height < curr_face[MOUTH]->r.y)
|
||||
{
|
||||
cvStartReadSeq( big_face[REYE].m_seqRects, &reader_r );
|
||||
for (int i_right = 0; i_right < big_face[REYE].m_seqRects->total && i_right < nElements; i_right++)
|
||||
{
|
||||
curr_face[REYE] = (CvTrackingRect*)(reader_r.ptr);
|
||||
if (curr_face[REYE]->r.y + curr_face[REYE]->r.height < curr_face[MOUTH]->r.y &&
|
||||
curr_face[REYE]->r.x > curr_face[LEYE]->r.x + curr_face[LEYE]->r.width)
|
||||
{
|
||||
curr_energy = GetEnergy(curr_face, pTF->face, pTF->ptTempl, pTF->rTempl);
|
||||
if (curr_energy < new_energy)
|
||||
{
|
||||
for (int elem = 0; elem < NUM_FACE_ELEMENTS; elem++)
|
||||
new_face[elem] = curr_face[elem];
|
||||
new_energy = curr_energy;
|
||||
found = TRUE;
|
||||
}
|
||||
N++;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
if (found)
|
||||
{
|
||||
for (int elem = 0; elem < NUM_FACE_ELEMENTS; elem++)
|
||||
face[elem] = *(new_face[elem]);
|
||||
}
|
||||
return found;
|
||||
} // int ChoiceTrackingFace3(const CvTrackingRect* tr_face, CvTrackingRect* new_face, int& new_energy)
|
||||
|
||||
int ChoiceTrackingFace2(CvFaceTracker* pTF, const int nElements, const CvFaceElement* big_face, CvTrackingRect* face, int& new_energy, int noel)
|
||||
{
|
||||
int element[NUM_FACE_ELEMENTS];
|
||||
for (int i = 0, elem = 0; i < NUM_FACE_ELEMENTS; i++)
|
||||
{
|
||||
if (i != noel)
|
||||
{
|
||||
element[elem] = i;
|
||||
elem ++;
|
||||
}
|
||||
else
|
||||
element[2] = i;
|
||||
}
|
||||
CvTrackingRect* curr_face[NUM_FACE_ELEMENTS] = {NULL};
|
||||
CvTrackingRect* new_face[NUM_FACE_ELEMENTS] = {NULL};
|
||||
new_energy = 0x7fffffff;
|
||||
int curr_energy = 0x7fffffff;
|
||||
int found = FALSE;
|
||||
int N = 0;
|
||||
CvSeqReader reader0, reader1;
|
||||
cvStartReadSeq( big_face[element[0]].m_seqRects, &reader0 );
|
||||
for (int i0 = 0; i0 < big_face[element[0]].m_seqRects->total && i0 < nElements; i0++)
|
||||
{
|
||||
curr_face[element[0]] = (CvTrackingRect*)(reader0.ptr);
|
||||
cvStartReadSeq( big_face[element[1]].m_seqRects, &reader1 );
|
||||
for (int i1 = 0; i1 < big_face[element[1]].m_seqRects->total && i1 < nElements; i1++)
|
||||
{
|
||||
curr_face[element[1]] = (CvTrackingRect*)(reader1.ptr);
|
||||
curr_energy = GetEnergy2(curr_face, pTF->face, pTF->ptTempl, pTF->rTempl, element);
|
||||
if (curr_energy < new_energy)
|
||||
{
|
||||
for (int elem = 0; elem < NUM_FACE_ELEMENTS; elem++)
|
||||
new_face[elem] = curr_face[elem];
|
||||
new_energy = curr_energy;
|
||||
found = TRUE;
|
||||
}
|
||||
N++;
|
||||
}
|
||||
}
|
||||
if (found)
|
||||
{
|
||||
face[element[0]] = *(new_face[element[0]]);
|
||||
face[element[1]] = *(new_face[element[1]]);
|
||||
// 3 element find by template
|
||||
CvPoint templ_v01 = {pTF->ptTempl[element[1]].x - pTF->ptTempl[element[0]].x, pTF->ptTempl[element[1]].y - pTF->ptTempl[element[0]].y};
|
||||
CvPoint templ_v02 = {pTF->ptTempl[element[2]].x - pTF->ptTempl[element[0]].x, pTF->ptTempl[element[2]].y - pTF->ptTempl[element[0]].y};
|
||||
CvPoint prev_v01 = {pTF->face[element[1]].ptCenter.x - pTF->face[element[0]].ptCenter.x, pTF->face[element[1]].ptCenter.y - pTF->face[element[0]].ptCenter.y};
|
||||
CvPoint prev_v02 = {pTF->face[element[2]].ptCenter.x - pTF->face[element[0]].ptCenter.x, pTF->face[element[2]].ptCenter.y - pTF->face[element[0]].ptCenter.y};
|
||||
CvPoint new_v01 = {new_face[element[1]]->ptCenter.x - new_face[element[0]]->ptCenter.x, new_face[element[1]]->ptCenter.y - new_face[element[0]]->ptCenter.y};
|
||||
double templ_d01 = sqrt((double)templ_v01.x*templ_v01.x + templ_v01.y*templ_v01.y);
|
||||
double templ_d02 = sqrt((double)templ_v02.x*templ_v02.x + templ_v02.y*templ_v02.y);
|
||||
double prev_d01 = sqrt((double)prev_v01.x*prev_v01.x + prev_v01.y*prev_v01.y);
|
||||
double prev_d02 = sqrt((double)prev_v02.x*prev_v02.x + prev_v02.y*prev_v02.y);
|
||||
double new_d01 = sqrt((double)new_v01.x*new_v01.x + new_v01.y*new_v01.y);
|
||||
double scale = templ_d01 / new_d01;
|
||||
double new_d02 = templ_d02 / scale;
|
||||
double sin_a = double(prev_v01.x * prev_v02.y - prev_v01.y * prev_v02.x) / (prev_d01 * prev_d02);
|
||||
double cos_a = cos(asin(sin_a));
|
||||
double x = double(new_v01.x) * cos_a - double(new_v01.y) * sin_a;
|
||||
double y = double(new_v01.x) * sin_a + double(new_v01.y) * cos_a;
|
||||
x = x * new_d02 / new_d01;
|
||||
y = y * new_d02 / new_d01;
|
||||
CvPoint new_v02 = {int(x + 0.5), int(y + 0.5)};
|
||||
face[element[2]].iColor = 0;
|
||||
face[element[2]].iEnergy = 0;
|
||||
face[element[2]].nRectsInThis = 0;
|
||||
face[element[2]].nRectsOnBottom = 0;
|
||||
face[element[2]].nRectsOnLeft = 0;
|
||||
face[element[2]].nRectsOnRight = 0;
|
||||
face[element[2]].nRectsOnTop = 0;
|
||||
face[element[2]].ptCenter.x = new_v02.x + new_face[element[0]]->ptCenter.x;
|
||||
face[element[2]].ptCenter.y = new_v02.y + new_face[element[0]]->ptCenter.y;
|
||||
face[element[2]].r.width = int(double(pTF->rTempl[element[2]].width) / (scale) + 0.5);
|
||||
face[element[2]].r.height = int(double(pTF->rTempl[element[2]].height) / (scale) + 0.5);
|
||||
face[element[2]].r.x = face[element[2]].ptCenter.x - (face[element[2]].r.width + 1) / 2;
|
||||
face[element[2]].r.y = face[element[2]].ptCenter.y - (face[element[2]].r.height + 1) / 2;
|
||||
_ASSERT(face[LEYE].r.x + face[LEYE].r.width <= face[REYE].r.x);
|
||||
}
|
||||
return found;
|
||||
} // int ChoiceTrackingFace3(const CvTrackingRect* tr_face, CvTrackingRect* new_face, int& new_energy)
|
||||
|
||||
inline int GetEnergy(CvTrackingRect** ppNew, const CvTrackingRect* pPrev, CvPoint* ptTempl, CvRect* rTempl)
|
||||
{
|
||||
int energy = 0;
|
||||
CvPoint ptNew[NUM_FACE_ELEMENTS];
|
||||
CvPoint ptPrev[NUM_FACE_ELEMENTS];
|
||||
for (int i = 0; i < NUM_FACE_ELEMENTS; i++)
|
||||
{
|
||||
ptNew[i] = ppNew[i]->ptCenter;
|
||||
ptPrev[i] = pPrev[i].ptCenter;
|
||||
energy += ppNew[i]->iEnergy - 2 * ppNew[i]->nRectsInThis;
|
||||
}
|
||||
double dx = 0, dy = 0, scale = 1, rotate = 0;
|
||||
double e_templ = CalculateTransformationLMS3(ptTempl, ptNew, &scale, &rotate, &dx, &dy);
|
||||
double e_prev = CalculateTransformationLMS3_0(ptPrev, ptNew);
|
||||
double w_eye = double(ppNew[LEYE]->r.width + ppNew[REYE]->r.width) * scale / 2.0;
|
||||
double h_eye = double(ppNew[LEYE]->r.height + ppNew[REYE]->r.height) * scale / 2.0;
|
||||
double w_mouth = double(ppNew[MOUTH]->r.width) * scale;
|
||||
double h_mouth = double(ppNew[MOUTH]->r.height) * scale;
|
||||
energy +=
|
||||
int(512.0 * (e_prev + 16.0 * e_templ)) +
|
||||
4 * pow2(ppNew[LEYE]->r.width - ppNew[REYE]->r.width) +
|
||||
4 * pow2(ppNew[LEYE]->r.height - ppNew[REYE]->r.height) +
|
||||
4 * (int)pow(w_eye - double(rTempl[LEYE].width + rTempl[REYE].width) / 2.0, 2) +
|
||||
2 * (int)pow(h_eye - double(rTempl[LEYE].height + rTempl[REYE].height) / 2.0, 2) +
|
||||
1 * (int)pow(w_mouth - double(rTempl[MOUTH].width), 2) +
|
||||
1 * (int)pow(h_mouth - double(rTempl[MOUTH].height), 2) +
|
||||
0;
|
||||
return energy;
|
||||
}
|
||||
|
||||
inline int GetEnergy2(CvTrackingRect** ppNew, const CvTrackingRect* pPrev, CvPoint* ptTempl, CvRect* rTempl, int* element)
|
||||
{
|
||||
CvPoint new_v = {ppNew[element[0]]->ptCenter.x - ppNew[element[1]]->ptCenter.x,
|
||||
ppNew[element[0]]->ptCenter.y - ppNew[element[1]]->ptCenter.y};
|
||||
CvPoint prev_v = {pPrev[element[0]].ptCenter.x - pPrev[element[1]].ptCenter.x,
|
||||
pPrev[element[0]].ptCenter.y - pPrev[element[1]].ptCenter.y};
|
||||
double new_d = sqrt((double)new_v.x*new_v.x + new_v.y*new_v.y);
|
||||
double prev_d = sqrt((double)prev_v.x*prev_v.x + prev_v.y*prev_v.y);
|
||||
double dx = ptTempl[element[0]].x - ptTempl[element[1]].x;
|
||||
double dy = ptTempl[element[0]].y - ptTempl[element[1]].y;
|
||||
double templ_d = sqrt(dx*dx + dy*dy);
|
||||
double scale_templ = new_d / templ_d;
|
||||
double w0 = (double)ppNew[element[0]]->r.width * scale_templ;
|
||||
double h0 = (double)ppNew[element[0]]->r.height * scale_templ;
|
||||
double w1 = (double)ppNew[element[1]]->r.width * scale_templ;
|
||||
double h1 = (double)ppNew[element[1]]->r.height * scale_templ;
|
||||
|
||||
int energy = ppNew[element[0]]->iEnergy + ppNew[element[1]]->iEnergy +
|
||||
- 2 * (ppNew[element[0]]->nRectsInThis - ppNew[element[1]]->nRectsInThis) +
|
||||
(int)pow(w0 - (double)rTempl[element[0]].width, 2) +
|
||||
(int)pow(h0 - (double)rTempl[element[0]].height, 2) +
|
||||
(int)pow(w1 - (double)rTempl[element[1]].width, 2) +
|
||||
(int)pow(h1 - (double)rTempl[element[1]].height, 2) +
|
||||
(int)pow(new_d - prev_d, 2) +
|
||||
0;
|
||||
|
||||
return energy;
|
||||
}
|
||||
|
||||
inline double CalculateTransformationLMS3( CvPoint* pTemplPoints,
|
||||
CvPoint* pSrcPoints,
|
||||
double* pdbAverageScale,
|
||||
double* pdbAverageRotate,
|
||||
double* pdbAverageShiftX,
|
||||
double* pdbAverageShiftY )
|
||||
{
|
||||
// double WS = 0;
|
||||
double dbAverageScale = 1;
|
||||
double dbAverageRotate = 0;
|
||||
double dbAverageShiftX = 0;
|
||||
double dbAverageShiftY = 0;
|
||||
double dbLMS = 0;
|
||||
|
||||
_ASSERT( NULL != pTemplPoints);
|
||||
_ASSERT( NULL != pSrcPoints);
|
||||
|
||||
double dbXt = double(pTemplPoints[0].x + pTemplPoints[1].x + pTemplPoints[2].x) / 3.0;
|
||||
double dbYt = double(pTemplPoints[0].y + pTemplPoints[1].y + pTemplPoints[2].y ) / 3.0;
|
||||
double dbXs = double(pSrcPoints[0].x + pSrcPoints[1].x + pSrcPoints[2].x) / 3.0;
|
||||
double dbYs = double(pSrcPoints[0].y + pSrcPoints[1].y + pSrcPoints[2].y) / 3.0;
|
||||
|
||||
double dbXtXt = double(pow2(pTemplPoints[0].x) + pow2(pTemplPoints[1].x) + pow2(pTemplPoints[2].x)) / 3.0;
|
||||
double dbYtYt = double(pow2(pTemplPoints[0].y) + pow2(pTemplPoints[1].y) + pow2(pTemplPoints[2].y)) / 3.0;
|
||||
|
||||
double dbXsXs = double(pow2(pSrcPoints[0].x) + pow2(pSrcPoints[1].x) + pow2(pSrcPoints[2].x)) / 3.0;
|
||||
double dbYsYs = double(pow2(pSrcPoints[0].y) + pow2(pSrcPoints[1].y) + pow2(pSrcPoints[2].y)) / 3.0;
|
||||
|
||||
double dbXtXs = double(pTemplPoints[0].x * pSrcPoints[0].x +
|
||||
pTemplPoints[1].x * pSrcPoints[1].x +
|
||||
pTemplPoints[2].x * pSrcPoints[2].x) / 3.0;
|
||||
double dbYtYs = double(pTemplPoints[0].y * pSrcPoints[0].y +
|
||||
pTemplPoints[1].y * pSrcPoints[1].y +
|
||||
pTemplPoints[2].y * pSrcPoints[2].y) / 3.0;
|
||||
|
||||
double dbXtYs = double(pTemplPoints[0].x * pSrcPoints[0].y +
|
||||
pTemplPoints[1].x * pSrcPoints[1].y +
|
||||
pTemplPoints[2].x * pSrcPoints[2].y) / 3.0;
|
||||
double dbYtXs = double(pTemplPoints[0].y * pSrcPoints[0].x +
|
||||
pTemplPoints[1].y * pSrcPoints[1].x +
|
||||
pTemplPoints[2].y * pSrcPoints[2].x ) / 3.0;
|
||||
|
||||
dbXtXt -= dbXt * dbXt;
|
||||
dbYtYt -= dbYt * dbYt;
|
||||
|
||||
dbXsXs -= dbXs * dbXs;
|
||||
dbYsYs -= dbYs * dbYs;
|
||||
|
||||
dbXtXs -= dbXt * dbXs;
|
||||
dbYtYs -= dbYt * dbYs;
|
||||
|
||||
dbXtYs -= dbXt * dbYs;
|
||||
dbYtXs -= dbYt * dbXs;
|
||||
|
||||
dbAverageRotate = atan2( dbXtYs - dbYtXs, dbXtXs + dbYtYs );
|
||||
|
||||
double cosR = cos(dbAverageRotate);
|
||||
double sinR = sin(dbAverageRotate);
|
||||
double del = dbXsXs + dbYsYs;
|
||||
if( del != 0 )
|
||||
{
|
||||
dbAverageScale = (double(dbXtXs + dbYtYs) * cosR + double(dbXtYs - dbYtXs) * sinR) / del;
|
||||
dbLMS = dbXtXt + dbYtYt - ((double)pow(dbXtXs + dbYtYs,2) + (double)pow(dbXtYs - dbYtXs,2)) / del;
|
||||
}
|
||||
|
||||
dbAverageShiftX = double(dbXt) - dbAverageScale * (double(dbXs) * cosR + double(dbYs) * sinR);
|
||||
dbAverageShiftY = double(dbYt) - dbAverageScale * (double(dbYs) * cosR - double(dbXs) * sinR);
|
||||
|
||||
if( pdbAverageScale != NULL ) *pdbAverageScale = dbAverageScale;
|
||||
if( pdbAverageRotate != NULL ) *pdbAverageRotate = dbAverageRotate;
|
||||
if( pdbAverageShiftX != NULL ) *pdbAverageShiftX = dbAverageShiftX;
|
||||
if( pdbAverageShiftY != NULL ) *pdbAverageShiftY = dbAverageShiftY;
|
||||
|
||||
_ASSERT(dbLMS >= 0);
|
||||
return dbLMS;
|
||||
}
|
||||
|
||||
inline double CalculateTransformationLMS3_0( CvPoint* pTemplPoints, CvPoint* pSrcPoints)
|
||||
{
|
||||
double dbLMS = 0;
|
||||
|
||||
_ASSERT( NULL != pTemplPoints);
|
||||
_ASSERT( NULL != pSrcPoints);
|
||||
|
||||
double dbXt = double(pTemplPoints[0].x + pTemplPoints[1].x + pTemplPoints[2].x) / 3.0;
|
||||
double dbYt = double(pTemplPoints[0].y + pTemplPoints[1].y + pTemplPoints[2].y ) / 3.0;
|
||||
double dbXs = double(pSrcPoints[0].x + pSrcPoints[1].x + pSrcPoints[2].x) / 3.0;
|
||||
double dbYs = double(pSrcPoints[0].y + pSrcPoints[1].y + pSrcPoints[2].y) / 3.0;
|
||||
|
||||
double dbXtXt = double(pow2(pTemplPoints[0].x) + pow2(pTemplPoints[1].x) + pow2(pTemplPoints[2].x)) / 3.0;
|
||||
double dbYtYt = double(pow2(pTemplPoints[0].y) + pow2(pTemplPoints[1].y) + pow2(pTemplPoints[2].y)) / 3.0;
|
||||
|
||||
double dbXsXs = double(pow2(pSrcPoints[0].x) + pow2(pSrcPoints[1].x) + pow2(pSrcPoints[2].x)) / 3.0;
|
||||
double dbYsYs = double(pow2(pSrcPoints[0].y) + pow2(pSrcPoints[1].y) + pow2(pSrcPoints[2].y)) / 3.0;
|
||||
|
||||
double dbXtXs = double(pTemplPoints[0].x * pSrcPoints[0].x +
|
||||
pTemplPoints[1].x * pSrcPoints[1].x +
|
||||
pTemplPoints[2].x * pSrcPoints[2].x) / 3.0;
|
||||
double dbYtYs = double(pTemplPoints[0].y * pSrcPoints[0].y +
|
||||
pTemplPoints[1].y * pSrcPoints[1].y +
|
||||
pTemplPoints[2].y * pSrcPoints[2].y) / 3.0;
|
||||
|
||||
double dbXtYs = double(pTemplPoints[0].x * pSrcPoints[0].y +
|
||||
pTemplPoints[1].x * pSrcPoints[1].y +
|
||||
pTemplPoints[2].x * pSrcPoints[2].y) / 3.0;
|
||||
double dbYtXs = double(pTemplPoints[0].y * pSrcPoints[0].x +
|
||||
pTemplPoints[1].y * pSrcPoints[1].x +
|
||||
pTemplPoints[2].y * pSrcPoints[2].x ) / 3.0;
|
||||
|
||||
dbXtXt -= dbXt * dbXt;
|
||||
dbYtYt -= dbYt * dbYt;
|
||||
|
||||
dbXsXs -= dbXs * dbXs;
|
||||
dbYsYs -= dbYs * dbYs;
|
||||
|
||||
dbXtXs -= dbXt * dbXs;
|
||||
dbYtYs -= dbYt * dbYs;
|
||||
|
||||
dbXtYs -= dbXt * dbYs;
|
||||
dbYtXs -= dbYt * dbXs;
|
||||
|
||||
double del = dbXsXs + dbYsYs;
|
||||
if( del != 0 )
|
||||
dbLMS = dbXtXt + dbYtYt - ((double)pow(dbXtXs + dbYtYs,2) + (double)pow(dbXtYs - dbYtXs,2)) / del;
|
||||
return dbLMS;
|
||||
}
|
||||
|
||||
@@ -0,0 +1,84 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
CV_IMPL void
|
||||
cvDeInterlace( const CvArr* framearr, CvArr* fieldEven, CvArr* fieldOdd )
|
||||
{
|
||||
CV_FUNCNAME("cvDeInterlace");
|
||||
|
||||
__BEGIN__;
|
||||
|
||||
CvMat frame_stub, *frame = (CvMat*)framearr;
|
||||
CvMat even_stub, *even = (CvMat*)fieldEven;
|
||||
CvMat odd_stub, *odd = (CvMat*)fieldOdd;
|
||||
CvSize size;
|
||||
int y;
|
||||
|
||||
CV_CALL( frame = cvGetMat( frame, &frame_stub ));
|
||||
CV_CALL( even = cvGetMat( even, &even_stub ));
|
||||
CV_CALL( odd = cvGetMat( odd, &odd_stub ));
|
||||
|
||||
if( !CV_ARE_TYPES_EQ( frame, even ) || !CV_ARE_TYPES_EQ( frame, odd ))
|
||||
CV_ERROR( CV_StsUnmatchedFormats, "All the input images must have the same type" );
|
||||
|
||||
if( frame->cols != even->cols || frame->cols != odd->cols ||
|
||||
frame->rows != even->rows*2 || odd->rows != even->rows )
|
||||
CV_ERROR( CV_StsUnmatchedSizes, "Uncorrelated sizes of the input image and output fields" );
|
||||
|
||||
size = cvGetMatSize( even );
|
||||
size.width *= CV_ELEM_SIZE( even->type );
|
||||
|
||||
for( y = 0; y < size.height; y++ )
|
||||
{
|
||||
memcpy( even->data.ptr + even->step*y,
|
||||
frame->data.ptr + frame->step*y*2, size.width );
|
||||
memcpy( odd->data.ptr + even->step*y,
|
||||
frame->data.ptr + frame->step*(y*2+1), size.width );
|
||||
}
|
||||
|
||||
__END__;
|
||||
}
|
||||
|
||||
/* End of file. */
|
||||
|
||||
|
||||
@@ -0,0 +1,629 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
#if 0
|
||||
|
||||
#include <malloc.h>
|
||||
//#include "decomppoly.h"
|
||||
|
||||
#define ZERO_CLOSE 0.00001f
|
||||
#define ONE_CLOSE 0.99999f
|
||||
|
||||
#define CHECK_COLLINEARITY(vec1_x,vec1_y,vec2_x,vec2_y) \
|
||||
if( vec1_x == 0 ) { \
|
||||
if( vec1_y * vec2_y > 0 ) { \
|
||||
return 0; \
|
||||
} \
|
||||
} \
|
||||
else { \
|
||||
if( vec1_x * vec2_x > 0 ) { \
|
||||
return 0; \
|
||||
} \
|
||||
}
|
||||
|
||||
// determines if edge number one lies in counterclockwise
|
||||
// earlier than edge number two
|
||||
inline int icvIsFirstEdgeClosier( int x0,
|
||||
int y0,
|
||||
int x0_end,
|
||||
int y0_end,
|
||||
int x1_end,
|
||||
int y1_end,
|
||||
int x2_end,
|
||||
int y2_end )
|
||||
{
|
||||
int mult, mult1, mult2;
|
||||
int vec0_x, vec0_y;
|
||||
int vec1_x, vec1_y;
|
||||
int vec2_x, vec2_y;
|
||||
|
||||
vec0_x = x0_end - x0;
|
||||
vec0_y = y0_end - y0;
|
||||
vec1_x = x1_end - x0;
|
||||
vec1_y = y1_end - y0;
|
||||
vec2_x = x2_end - x0;
|
||||
vec2_y = y2_end - y0;
|
||||
|
||||
mult1 = vec1_x * vec0_y - vec0_x * vec1_y;
|
||||
mult2 = vec2_x * vec0_y - vec0_x * vec2_y;
|
||||
|
||||
if( mult1 == 0 ) {
|
||||
CHECK_COLLINEARITY( vec0_x, vec0_y, vec1_x, vec1_y );
|
||||
}
|
||||
if( mult2 == 0 ) {
|
||||
CHECK_COLLINEARITY( vec0_x, vec0_y, vec2_x, vec2_y );
|
||||
}
|
||||
if( mult1 > 0 && mult2 < 0 ) {
|
||||
return 1;
|
||||
}
|
||||
if( mult1 < 0 && mult2 > 0 ) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
mult = vec1_x * vec2_y - vec2_x * vec1_y;
|
||||
if( mult == 0 ) {
|
||||
CHECK_COLLINEARITY( vec1_x, vec1_y, vec2_x, vec2_y );
|
||||
}
|
||||
|
||||
if( mult1 > 0 )
|
||||
{
|
||||
if( mult > 0 ) {
|
||||
return -1;
|
||||
}
|
||||
else {
|
||||
return 1;
|
||||
}
|
||||
} // if( mult1 > 0 )
|
||||
else
|
||||
{
|
||||
if( mult1 != 0 ) {
|
||||
if( mult > 0 ) {
|
||||
return 1;
|
||||
}
|
||||
else {
|
||||
return -1;
|
||||
}
|
||||
} // if( mult1 != 0 )
|
||||
else {
|
||||
if( mult2 > 0 ) {
|
||||
return -1;
|
||||
}
|
||||
else {
|
||||
return 1;
|
||||
}
|
||||
} // if( mult1 != 0 ) else
|
||||
|
||||
} // if( mult1 > 0 ) else
|
||||
|
||||
} // icvIsFirstEdgeClosier
|
||||
|
||||
bool icvEarCutTriangulation( CvPoint* contour,
|
||||
int num,
|
||||
int* outEdges,
|
||||
int* numEdges )
|
||||
{
|
||||
int i;
|
||||
int notFoundFlag = 0;
|
||||
int begIndex = -1;
|
||||
int isInternal;
|
||||
int currentNum = num;
|
||||
int index1, index2, index3;
|
||||
int ix0, iy0, ix1, iy1, ix2, iy2;
|
||||
int x1, y1, x2, y2, x3, y3;
|
||||
int dx1, dy1, dx2, dy2;
|
||||
int* pointExist = ( int* )0;
|
||||
int det, det1, det2;
|
||||
float t1, t2;
|
||||
|
||||
(*numEdges) = 0;
|
||||
|
||||
if( num <= 2 ) {
|
||||
return false;
|
||||
}
|
||||
|
||||
pointExist = ( int* )malloc( num * sizeof( int ) );
|
||||
|
||||
for( i = 0; i < num; i ++ ) {
|
||||
pointExist[i] = 1;
|
||||
}
|
||||
|
||||
for( i = 0; i < num; i ++ ) {
|
||||
outEdges[ (*numEdges) * 2 ] = i;
|
||||
if( i != num - 1 ) {
|
||||
outEdges[ (*numEdges) * 2 + 1 ] = i + 1;
|
||||
}
|
||||
else {
|
||||
outEdges[ (*numEdges) * 2 + 1 ] = 0;
|
||||
}
|
||||
(*numEdges) ++;
|
||||
} // for( i = 0; i < num; i ++ )
|
||||
|
||||
// initializing data before while cycle
|
||||
index1 = 0;
|
||||
index2 = 1;
|
||||
index3 = 2;
|
||||
x1 = contour[ index1 ].x;
|
||||
y1 = contour[ index1 ].y;
|
||||
x2 = contour[ index2 ].x;
|
||||
y2 = contour[ index2 ].y;
|
||||
x3 = contour[ index3 ].x;
|
||||
y3 = contour[ index3 ].y;
|
||||
|
||||
while( currentNum > 3 )
|
||||
{
|
||||
dx1 = x2 - x1;
|
||||
dy1 = y2 - y1;
|
||||
dx2 = x3 - x2;
|
||||
dy2 = y3 - y2;
|
||||
if( dx1 * dy2 - dx2 * dy1 < 0 ) // convex condition
|
||||
{
|
||||
// checking for noncrossing edge
|
||||
ix1 = x3 - x1;
|
||||
iy1 = y3 - y1;
|
||||
isInternal = 1;
|
||||
for( i = 0; i < num; i ++ )
|
||||
{
|
||||
if( i != num - 1 ) {
|
||||
ix2 = contour[ i + 1 ].x - contour[ i ].x;
|
||||
iy2 = contour[ i + 1 ].y - contour[ i ].y;
|
||||
}
|
||||
else {
|
||||
ix2 = contour[ 0 ].x - contour[ i ].x;
|
||||
iy2 = contour[ 0 ].y - contour[ i ].y;
|
||||
}
|
||||
ix0 = contour[ i ].x - x1;
|
||||
iy0 = contour[ i ].y - y1;
|
||||
|
||||
det = ix2 * iy1 - ix1 * iy2;
|
||||
det1 = ix2 * iy0 - ix0 * iy2;
|
||||
if( det != 0.0f )
|
||||
{
|
||||
t1 = ( ( float )( det1 ) ) / det;
|
||||
if( t1 > ZERO_CLOSE && t1 < ONE_CLOSE )
|
||||
{
|
||||
det2 = ix1 * iy0 - ix0 * iy1;
|
||||
t2 = ( ( float )( det2 ) ) / det;
|
||||
if( t2 > ZERO_CLOSE && t2 < ONE_CLOSE ) {
|
||||
isInternal = 0;
|
||||
}
|
||||
|
||||
} // if( t1 > ZERO_CLOSE && t1 < ONE_CLOSE )
|
||||
|
||||
} // if( det != 0.0f )
|
||||
|
||||
} // for( i = 0; i < (*numEdges); i ++ )
|
||||
|
||||
if( isInternal )
|
||||
{
|
||||
// this edge is internal
|
||||
notFoundFlag = 0;
|
||||
outEdges[ (*numEdges) * 2 ] = index1;
|
||||
outEdges[ (*numEdges) * 2 + 1 ] = index3;
|
||||
(*numEdges) ++;
|
||||
pointExist[ index2 ] = 0;
|
||||
index2 = index3;
|
||||
x2 = x3;
|
||||
y2 = y3;
|
||||
currentNum --;
|
||||
if( currentNum >= 3 ) {
|
||||
do {
|
||||
index3 ++;
|
||||
if( index3 == num ) {
|
||||
index3 = 0;
|
||||
}
|
||||
} while( !pointExist[ index3 ] );
|
||||
x3 = contour[ index3 ].x;
|
||||
y3 = contour[ index3 ].y;
|
||||
} // if( currentNum >= 3 )
|
||||
|
||||
} // if( isInternal )
|
||||
else {
|
||||
// this edge intersects some other initial edges
|
||||
if( !notFoundFlag ) {
|
||||
notFoundFlag = 1;
|
||||
begIndex = index1;
|
||||
}
|
||||
index1 = index2;
|
||||
x1 = x2;
|
||||
y1 = y2;
|
||||
index2 = index3;
|
||||
x2 = x3;
|
||||
y2 = y3;
|
||||
do {
|
||||
index3 ++;
|
||||
if( index3 == num ) {
|
||||
index3 = 0;
|
||||
}
|
||||
if( index3 == begIndex ) {
|
||||
if( pointExist ) {
|
||||
free( pointExist );
|
||||
}
|
||||
return false;
|
||||
}
|
||||
} while( !pointExist[ index3 ] );
|
||||
x3 = contour[ index3 ].x;
|
||||
y3 = contour[ index3 ].y;
|
||||
} // if( isInternal ) else
|
||||
|
||||
} // if( dx1 * dy2 - dx2 * dy1 < 0 )
|
||||
else
|
||||
{
|
||||
if( !notFoundFlag ) {
|
||||
notFoundFlag = 1;
|
||||
begIndex = index1;
|
||||
}
|
||||
index1 = index2;
|
||||
x1 = x2;
|
||||
y1 = y2;
|
||||
index2 = index3;
|
||||
x2 = x3;
|
||||
y2 = y3;
|
||||
do {
|
||||
index3 ++;
|
||||
if( index3 == num ) {
|
||||
index3 = 0;
|
||||
}
|
||||
if( index3 == begIndex ) {
|
||||
if( pointExist ) {
|
||||
free( pointExist );
|
||||
}
|
||||
return false;
|
||||
}
|
||||
} while( !pointExist[ index3 ] );
|
||||
x3 = contour[ index3 ].x;
|
||||
y3 = contour[ index3 ].y;
|
||||
} // if( dx1 * dy2 - dx2 * dy1 < 0 ) else
|
||||
|
||||
} // while( currentNum > 3 )
|
||||
|
||||
if( pointExist ) {
|
||||
free( pointExist );
|
||||
}
|
||||
|
||||
return true;
|
||||
|
||||
} // icvEarCutTriangulation
|
||||
|
||||
inline bool icvFindTwoNeighbourEdges( CvPoint* contour,
|
||||
int* edges,
|
||||
int numEdges,
|
||||
int vtxIdx,
|
||||
int mainEdgeIdx,
|
||||
int* leftEdgeIdx,
|
||||
int* rightEdgeIdx )
|
||||
{
|
||||
int i;
|
||||
int compRes;
|
||||
int vec0_x, vec0_y;
|
||||
int x0, y0, x0_end, y0_end;
|
||||
int x1_left = 0, y1_left = 0, x1_right = 0, y1_right = 0, x2, y2;
|
||||
|
||||
(*leftEdgeIdx) = -1;
|
||||
(*rightEdgeIdx) = -1;
|
||||
|
||||
if( edges[ mainEdgeIdx * 2 ] == vtxIdx ) {
|
||||
x0 = contour[ vtxIdx ].x;
|
||||
y0 = contour[ vtxIdx ].y;
|
||||
x0_end = contour[ edges[ mainEdgeIdx * 2 + 1 ] ].x;
|
||||
y0_end = contour[ edges[ mainEdgeIdx * 2 + 1 ] ].y;
|
||||
vec0_x = x0_end - x0;
|
||||
vec0_y = y0_end - y0;
|
||||
}
|
||||
else {
|
||||
//x0 = contour[ edges[ mainEdgeIdx * 2 ] ].x;
|
||||
//y0 = contour[ edges[ mainEdgeIdx * 2 ] ].y;
|
||||
//x0_end = contour[ vtxIdx ].x;
|
||||
//y0_end = contour[ vtxIdx ].y;
|
||||
x0 = contour[ vtxIdx ].x;
|
||||
y0 = contour[ vtxIdx ].y;
|
||||
x0_end = contour[ edges[ mainEdgeIdx * 2 ] ].x;
|
||||
y0_end = contour[ edges[ mainEdgeIdx * 2 ] ].y;
|
||||
vec0_x = x0_end - x0;
|
||||
vec0_y = y0_end - y0;
|
||||
}
|
||||
|
||||
for( i = 0; i < numEdges; i ++ )
|
||||
{
|
||||
if( ( i != mainEdgeIdx ) &&
|
||||
( edges[ i * 2 ] == vtxIdx || edges[ i * 2 + 1 ] == vtxIdx ) )
|
||||
{
|
||||
if( (*leftEdgeIdx) == -1 )
|
||||
{
|
||||
(*leftEdgeIdx) = (*rightEdgeIdx) = i;
|
||||
if( edges[ i * 2 ] == vtxIdx ) {
|
||||
x1_left = x1_right = contour[ edges[ i * 2 + 1 ] ].x;
|
||||
y1_left = y1_right = contour[ edges[ i * 2 + 1 ] ].y;
|
||||
}
|
||||
else {
|
||||
x1_left = x1_right = contour[ edges[ i * 2 ] ].x;
|
||||
y1_left = y1_right = contour[ edges[ i * 2 ] ].y;
|
||||
}
|
||||
|
||||
} // if( (*leftEdgeIdx) == -1 )
|
||||
else
|
||||
{
|
||||
if( edges[ i * 2 ] == vtxIdx ) {
|
||||
x2 = contour[ edges[ i * 2 + 1 ] ].x;
|
||||
y2 = contour[ edges[ i * 2 + 1 ] ].y;
|
||||
}
|
||||
else {
|
||||
x2 = contour[ edges[ i * 2 ] ].x;
|
||||
y2 = contour[ edges[ i * 2 ] ].y;
|
||||
}
|
||||
|
||||
compRes = icvIsFirstEdgeClosier( x0,
|
||||
y0, x0_end, y0_end, x1_left, y1_left, x2, y2 );
|
||||
if( compRes == 0 ) {
|
||||
return false;
|
||||
}
|
||||
if( compRes == -1 ) {
|
||||
(*leftEdgeIdx) = i;
|
||||
x1_left = x2;
|
||||
y1_left = y2;
|
||||
} // if( compRes == -1 )
|
||||
else {
|
||||
compRes = icvIsFirstEdgeClosier( x0,
|
||||
y0, x0_end, y0_end, x1_right, y1_right, x2, y2 );
|
||||
if( compRes == 0 ) {
|
||||
return false;
|
||||
}
|
||||
if( compRes == 1 ) {
|
||||
(*rightEdgeIdx) = i;
|
||||
x1_right = x2;
|
||||
y1_right = y2;
|
||||
}
|
||||
|
||||
} // if( compRes == -1 ) else
|
||||
|
||||
} // if( (*leftEdgeIdx) == -1 ) else
|
||||
|
||||
} // if( ( i != mainEdgesIdx ) && ...
|
||||
|
||||
} // for( i = 0; i < numEdges; i ++ )
|
||||
|
||||
return true;
|
||||
|
||||
} // icvFindTwoNeighbourEdges
|
||||
|
||||
bool icvFindReferences( CvPoint* contour,
|
||||
int num,
|
||||
int* outEdges,
|
||||
int* refer,
|
||||
int* numEdges )
|
||||
{
|
||||
int i;
|
||||
int currPntIdx;
|
||||
int leftEdgeIdx, rightEdgeIdx;
|
||||
|
||||
if( icvEarCutTriangulation( contour, num, outEdges, numEdges ) )
|
||||
{
|
||||
for( i = 0; i < (*numEdges); i ++ )
|
||||
{
|
||||
refer[ i * 4 ] = -1;
|
||||
refer[ i * 4 + 1 ] = -1;
|
||||
refer[ i * 4 + 2 ] = -1;
|
||||
refer[ i * 4 + 3 ] = -1;
|
||||
} // for( i = 0; i < (*numEdges); i ++ )
|
||||
|
||||
for( i = 0; i < (*numEdges); i ++ )
|
||||
{
|
||||
currPntIdx = outEdges[ i * 2 ];
|
||||
if( !icvFindTwoNeighbourEdges( contour,
|
||||
outEdges, (*numEdges), currPntIdx,
|
||||
i, &leftEdgeIdx, &rightEdgeIdx ) )
|
||||
{
|
||||
return false;
|
||||
} // if( !icvFindTwoNeighbourEdges( contour, ...
|
||||
else
|
||||
{
|
||||
if( outEdges[ leftEdgeIdx * 2 ] == currPntIdx ) {
|
||||
if( refer[ i * 4 ] == -1 ) {
|
||||
refer[ i * 4 ] = ( leftEdgeIdx << 2 );
|
||||
}
|
||||
}
|
||||
else {
|
||||
if( refer[ i * 4 ] == -1 ) {
|
||||
refer[ i * 4 ] = ( leftEdgeIdx << 2 ) | 2;
|
||||
}
|
||||
}
|
||||
if( outEdges[ rightEdgeIdx * 2 ] == currPntIdx ) {
|
||||
if( refer[ i * 4 + 1 ] == -1 ) {
|
||||
refer[ i * 4 + 1 ] = ( rightEdgeIdx << 2 ) | 3;
|
||||
}
|
||||
}
|
||||
else {
|
||||
if( refer[ i * 4 + 1 ] == -1 ) {
|
||||
refer[ i * 4 + 1 ] = ( rightEdgeIdx << 2 ) | 1;
|
||||
}
|
||||
}
|
||||
|
||||
} // if( !icvFindTwoNeighbourEdges( contour, ... ) else
|
||||
|
||||
currPntIdx = outEdges[ i * 2 + 1 ];
|
||||
if( i == 18 ) {
|
||||
i = i;
|
||||
}
|
||||
if( !icvFindTwoNeighbourEdges( contour,
|
||||
outEdges, (*numEdges), currPntIdx,
|
||||
i, &leftEdgeIdx, &rightEdgeIdx ) )
|
||||
{
|
||||
return false;
|
||||
} // if( !icvFindTwoNeighbourEdges( contour, ...
|
||||
else
|
||||
{
|
||||
if( outEdges[ leftEdgeIdx * 2 ] == currPntIdx ) {
|
||||
if( refer[ i * 4 + 3 ] == -1 ) {
|
||||
refer[ i * 4 + 3 ] = ( leftEdgeIdx << 2 );
|
||||
}
|
||||
}
|
||||
else {
|
||||
if( refer[ i * 4 + 3 ] == -1 ) {
|
||||
refer[ i * 4 + 3 ] = ( leftEdgeIdx << 2 ) | 2;
|
||||
}
|
||||
}
|
||||
if( outEdges[ rightEdgeIdx * 2 ] == currPntIdx ) {
|
||||
if( refer[ i * 4 + 2 ] == -1 ) {
|
||||
refer[ i * 4 + 2 ] = ( rightEdgeIdx << 2 ) | 3;
|
||||
}
|
||||
}
|
||||
else {
|
||||
if( refer[ i * 4 + 2 ] == -1 ) {
|
||||
refer[ i * 4 + 2 ] = ( rightEdgeIdx << 2 ) | 1;
|
||||
}
|
||||
}
|
||||
|
||||
} // if( !icvFindTwoNeighbourEdges( contour, ... ) else
|
||||
|
||||
} // for( i = 0; i < (*numEdges); i ++ )
|
||||
|
||||
} // if( icvEarCutTriangulation( contour, num, outEdges, numEdges ) )
|
||||
else {
|
||||
return false;
|
||||
} // if( icvEarCutTriangulation( contour, num, outEdges, ... ) else
|
||||
|
||||
return true;
|
||||
|
||||
} // icvFindReferences
|
||||
|
||||
void cvDecompPoly( CvContour* cont,
|
||||
CvSubdiv2D** subdiv,
|
||||
CvMemStorage* storage )
|
||||
{
|
||||
int* memory;
|
||||
CvPoint* contour;
|
||||
int* outEdges;
|
||||
int* refer;
|
||||
CvSubdiv2DPoint** pntsPtrs;
|
||||
CvQuadEdge2D** edgesPtrs;
|
||||
int numVtx;
|
||||
int numEdges;
|
||||
int i;
|
||||
CvSeqReader reader;
|
||||
CvPoint2D32f pnt;
|
||||
CvQuadEdge2D* quadEdge;
|
||||
|
||||
numVtx = cont -> total;
|
||||
if( numVtx < 3 ) {
|
||||
return;
|
||||
}
|
||||
|
||||
*subdiv = ( CvSubdiv2D* )0;
|
||||
|
||||
memory = ( int* )malloc( sizeof( int ) * ( numVtx * 2
|
||||
+ numVtx * numVtx * 2 * 5 )
|
||||
+ sizeof( CvQuadEdge2D* ) * ( numVtx * numVtx )
|
||||
+ sizeof( CvSubdiv2DPoint* ) * ( numVtx * 2 ) );
|
||||
contour = ( CvPoint* )memory;
|
||||
outEdges = ( int* )( contour + numVtx );
|
||||
refer = outEdges + numVtx * numVtx * 2;
|
||||
edgesPtrs = ( CvQuadEdge2D** )( refer + numVtx * numVtx * 4 );
|
||||
pntsPtrs = ( CvSubdiv2DPoint** )( edgesPtrs + numVtx * numVtx );
|
||||
|
||||
cvStartReadSeq( ( CvSeq* )cont, &reader, 0 );
|
||||
for( i = 0; i < numVtx; i ++ )
|
||||
{
|
||||
CV_READ_SEQ_ELEM( (contour[ i ]), reader );
|
||||
} // for( i = 0; i < numVtx; i ++ )
|
||||
|
||||
if( !icvFindReferences( contour, numVtx, outEdges, refer, &numEdges ) )
|
||||
{
|
||||
free( memory );
|
||||
return;
|
||||
} // if( !icvFindReferences( contour, numVtx, outEdges, refer, ...
|
||||
|
||||
*subdiv = cvCreateSubdiv2D( CV_SEQ_KIND_SUBDIV2D,
|
||||
sizeof( CvSubdiv2D ),
|
||||
sizeof( CvSubdiv2DPoint ),
|
||||
sizeof( CvQuadEdge2D ),
|
||||
storage );
|
||||
|
||||
for( i = 0; i < numVtx; i ++ )
|
||||
{
|
||||
pnt.x = ( float )contour[ i ].x;
|
||||
pnt.y = ( float )contour[ i ].y;
|
||||
pntsPtrs[ i ] = cvSubdiv2DAddPoint( *subdiv, pnt, 0 );
|
||||
} // for( i = 0; i < numVtx; i ++ )
|
||||
|
||||
for( i = 0; i < numEdges; i ++ )
|
||||
{
|
||||
edgesPtrs[ i ] = ( CvQuadEdge2D* )
|
||||
( cvSubdiv2DMakeEdge( *subdiv ) & 0xfffffffc );
|
||||
} // for( i = 0; i < numEdges; i ++ )
|
||||
|
||||
for( i = 0; i < numEdges; i ++ )
|
||||
{
|
||||
quadEdge = edgesPtrs[ i ];
|
||||
quadEdge -> next[ 0 ] =
|
||||
( ( CvSubdiv2DEdge )edgesPtrs[ refer[ i * 4 ] >> 2 ] )
|
||||
| ( refer[ i * 4 ] & 3 );
|
||||
quadEdge -> next[ 1 ] =
|
||||
( ( CvSubdiv2DEdge )edgesPtrs[ refer[ i * 4 + 1 ] >> 2 ] )
|
||||
| ( refer[ i * 4 + 1 ] & 3 );
|
||||
quadEdge -> next[ 2 ] =
|
||||
( ( CvSubdiv2DEdge )edgesPtrs[ refer[ i * 4 + 2 ] >> 2 ] )
|
||||
| ( refer[ i * 4 + 2 ] & 3 );
|
||||
quadEdge -> next[ 3 ] =
|
||||
( ( CvSubdiv2DEdge )edgesPtrs[ refer[ i * 4 + 3 ] >> 2 ] )
|
||||
| ( refer[ i * 4 + 3 ] & 3 );
|
||||
quadEdge -> pt[ 0 ] = pntsPtrs[ outEdges[ i * 2 ] ];
|
||||
quadEdge -> pt[ 1 ] = ( CvSubdiv2DPoint* )0;
|
||||
quadEdge -> pt[ 2 ] = pntsPtrs[ outEdges[ i * 2 + 1 ] ];
|
||||
quadEdge -> pt[ 3 ] = ( CvSubdiv2DPoint* )0;
|
||||
} // for( i = 0; i < numEdges; i ++ )
|
||||
|
||||
(*subdiv) -> topleft.x = ( float )cont -> rect.x;
|
||||
(*subdiv) -> topleft.y = ( float )cont -> rect.y;
|
||||
(*subdiv) -> bottomright.x =
|
||||
( float )( cont -> rect.x + cont -> rect.width );
|
||||
(*subdiv) -> bottomright.y =
|
||||
( float )( cont -> rect.y + cont -> rect.height );
|
||||
|
||||
free( memory );
|
||||
return;
|
||||
|
||||
} // cvDecompPoly
|
||||
|
||||
#endif
|
||||
|
||||
// End of file decomppoly.cpp
|
||||
|
||||
@@ -0,0 +1 @@
|
||||
// this file is empty but needed for libtool
|
||||
1381
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/src/enmin.cpp
Normal file
1381
测试/单独功能测试/0-DLL测试(实际没有部署)/dll-goal完整版/OpenCV/cvaux/src/enmin.cpp
Normal file
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,268 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
#ifdef WIN32 /* make sure it builds under Linux whenever it is included into Makefile.am or not. */
|
||||
|
||||
//void icvCutContour( CvSeq* current, IplImage* image );
|
||||
CvSeq* icvCutContourRaster( CvSeq* current, CvMemStorage* storage, IplImage* image );
|
||||
|
||||
|
||||
//create lists of segments of all contours from image
|
||||
CvSeq* cvExtractSingleEdges( IplImage* image, //bw image - it's content will be destroyed by cvFindContours
|
||||
CvMemStorage* storage )
|
||||
{
|
||||
CvMemStorage* tmp_storage = cvCreateChildMemStorage( storage );
|
||||
CvSeq* contours = 0;
|
||||
cvFindContours( image, tmp_storage, &contours, sizeof(CvContour), CV_RETR_LIST, CV_CHAIN_APPROX_NONE );
|
||||
cvZero( image );
|
||||
|
||||
//iterate through contours
|
||||
//iterate through tree
|
||||
CvSeq* current = contours;
|
||||
int number = 0;
|
||||
int level = 1;
|
||||
|
||||
CvSeq* output = 0;
|
||||
CvSeq* tail_seq = 0;
|
||||
|
||||
//actually this loop can iterates through tree,
|
||||
//but still we use CV_RETR_LIST it is not useful
|
||||
while( current )
|
||||
{
|
||||
number++;
|
||||
|
||||
//get vertical list of segments for one contour
|
||||
CvSeq* new_seq = icvCutContourRaster( current, storage, image );
|
||||
|
||||
//add this vertical list to horisontal list
|
||||
if( new_seq )
|
||||
{
|
||||
if( tail_seq )
|
||||
{
|
||||
tail_seq->h_next = new_seq;
|
||||
new_seq->h_prev = tail_seq;
|
||||
tail_seq = new_seq;
|
||||
}
|
||||
else
|
||||
{
|
||||
output = tail_seq = new_seq;
|
||||
}
|
||||
}
|
||||
|
||||
//iteration through tree
|
||||
if( current->v_next )
|
||||
{
|
||||
//goto child
|
||||
current = current->v_next;
|
||||
level++;
|
||||
}
|
||||
else
|
||||
{
|
||||
//go parent
|
||||
while( !current->h_next )
|
||||
{
|
||||
current = current->v_prev;
|
||||
level--;
|
||||
if( !level ) break;
|
||||
}
|
||||
|
||||
if( current ) //go brother
|
||||
current = current->h_next;
|
||||
}
|
||||
}
|
||||
|
||||
//free temporary memstorage with initial contours
|
||||
cvReleaseMemStorage( &tmp_storage );
|
||||
|
||||
return output;
|
||||
}
|
||||
|
||||
//makes vertical list of segments for 1 contour
|
||||
CvSeq* icvCutContourRaster( CvSeq* current, CvMemStorage* storage, IplImage* image /*tmp image*/)
|
||||
{
|
||||
//iplSet(image, 0 ); // this can cause double edges if two contours have common edge
|
||||
// for example if object is circle with 1 pixel width
|
||||
// to remove such problem - remove this iplSet
|
||||
|
||||
//approx contour by single edges
|
||||
CvSeqReader reader;
|
||||
CvSeqWriter writer;
|
||||
|
||||
int writing = 0;
|
||||
cvStartReadSeq( current, &reader, 0 );
|
||||
//below line just to avoid warning
|
||||
cvStartWriteSeq( current->flags, sizeof(CvContour), sizeof(CvPoint), storage, &writer );
|
||||
|
||||
CvSeq* output = 0;
|
||||
CvSeq* tail = 0;
|
||||
|
||||
//first pass through contour - compute number of branches at every point
|
||||
int i;
|
||||
for( i = 0; i < current->total; i++ )
|
||||
{
|
||||
CvPoint cur;
|
||||
|
||||
CV_READ_SEQ_ELEM( cur, reader );
|
||||
|
||||
//mark point
|
||||
((uchar*)image->imageData)[image->widthStep * cur.y + cur.x]++;
|
||||
assert( ((uchar*)image->imageData)[image->widthStep * cur.y + cur.x] != 255 );
|
||||
|
||||
}
|
||||
|
||||
//second pass - create separate edges
|
||||
for( i = 0; i < current->total; i++ )
|
||||
{
|
||||
CvPoint cur;
|
||||
|
||||
CV_READ_SEQ_ELEM( cur, reader );
|
||||
|
||||
//get pixel at this point
|
||||
uchar flag = image->imageData[image->widthStep * cur.y + cur.x];
|
||||
if( flag != 255 && flag < 3) //
|
||||
{
|
||||
if(!writing)
|
||||
{
|
||||
cvStartWriteSeq( current->flags, sizeof(CvContour), sizeof(CvPoint), storage, &writer );
|
||||
writing = 1 ;
|
||||
}
|
||||
|
||||
//mark point
|
||||
if( flag < 3 ) ((uchar*)image->imageData)[image->widthStep * cur.y + cur.x] = 255;
|
||||
//add it to another seq
|
||||
CV_WRITE_SEQ_ELEM( cur, writer );
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
//exclude this point from contour
|
||||
if( writing )
|
||||
{
|
||||
CvSeq* newseq = cvEndWriteSeq( &writer );
|
||||
writing = 0;
|
||||
|
||||
if( tail )
|
||||
{
|
||||
tail->v_next = newseq;
|
||||
newseq->v_prev = tail;
|
||||
tail = newseq;
|
||||
}
|
||||
else
|
||||
{
|
||||
output = tail = newseq;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if( writing ) //if were not self intersections
|
||||
{
|
||||
CvSeq* newseq = cvEndWriteSeq( &writer );
|
||||
writing = 0;
|
||||
|
||||
if( tail )
|
||||
{
|
||||
tail->v_next = newseq;
|
||||
newseq->v_prev = tail;
|
||||
tail = newseq;
|
||||
}
|
||||
else
|
||||
{
|
||||
output = tail = newseq;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
return output;
|
||||
|
||||
}
|
||||
|
||||
|
||||
/*void icvCutContour( CvSeq* current, IplImage* image )
|
||||
{
|
||||
//approx contour by single edges
|
||||
CvSeqReader reader;
|
||||
CvSeqReader rev_reader;
|
||||
|
||||
cvStartReadSeq( current, &reader, 0 );
|
||||
|
||||
int64* cur_pt = (int64*)reader.ptr;
|
||||
int64* prev_pt = (int64*)reader.prev_elem;
|
||||
|
||||
//search for point a in aba position
|
||||
for( int i = 0; i < current->total; i++ )
|
||||
{
|
||||
CV_NEXT_SEQ_ELEM( sizeof(int64), reader );
|
||||
|
||||
//compare current reader pos element with old previous
|
||||
if( prev_pt[0] == ((int64*)reader.ptr)[0] )
|
||||
{
|
||||
//return to prev pos
|
||||
CV_PREV_SEQ_ELEM( sizeof(int64), reader );
|
||||
|
||||
|
||||
//this point is end of edge
|
||||
//start going both directions and collect edge
|
||||
cvStartReadSeq( current, &rev_reader, 1 );
|
||||
|
||||
int pos = cvGetSeqReaderPos( &reader );
|
||||
cvSetSeqReaderPos( &rev_reader, pos );
|
||||
|
||||
//walk in both directions
|
||||
while(1);
|
||||
|
||||
|
||||
}
|
||||
int64* cur_pt = (int64*)reader.ptr;
|
||||
int64* prev_pt = (int64*)reader.prev_elem;
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
*/
|
||||
#endif /* WIN32 */
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -0,0 +1,20 @@
|
||||
TARGET := cvaux
|
||||
BINTYPE := DLL
|
||||
SRC_ROOT := ../../cvaux/src
|
||||
INC_ROOT := ../../cvaux/include
|
||||
CXCORE_INC := ../../cxcore/include
|
||||
CV_INC := ../../cv/include
|
||||
CV_SRC := ../../cv/src
|
||||
SRC_DIRS := . ./vs ../include ../../cxcore/include ../../cv/include
|
||||
|
||||
CXXFLAGS := -D"CVAPI_EXPORTS" -I"$(INC_ROOT)" -I"$(SRC_ROOT)" \
|
||||
-I"$(CXCORE_INC)" -I"$(CV_INC)" -I"$(CV_SRC)"
|
||||
|
||||
INCS := cvaux.h cvaux.hpp cvmat.hpp cvvidsurv.hpp cvface.h cvfacedetection.h \
|
||||
cvfacetemplate.h _cvaux.h _cvfacedetection.h _cvvectrack.h _cvvm.h \
|
||||
cv.h cv.hpp cvcompat.h cvtypes.h $(CV_SRC)/_cvmatrix.h \
|
||||
cxcore.h cxcore.hpp cxerror.h cxmisc.h cxtypes.h cvver.h
|
||||
|
||||
LIBS := -lcxcore$(DBG) -lcv$(DBG)
|
||||
|
||||
include ../../_make/make_module_gnu.mak
|
||||
@@ -0,0 +1,60 @@
|
||||
TARGET = cvaux
|
||||
BINTYPE = DLL
|
||||
ROOT = ..\..
|
||||
PCH = _cvaux.h
|
||||
PCH_STARTER = precomp
|
||||
|
||||
OBJS = \
|
||||
$(OBJPATH)/camshift.obj $(OBJPATH)/cv3dtracker.obj $(OBJPATH)/cvaux.obj \
|
||||
$(OBJPATH)/cvauxutils.obj $(OBJPATH)/cvbgfg_acmmm2003.obj $(OBJPATH)/cvbgfg_common.obj \
|
||||
$(OBJPATH)/cvbgfg_gaussmix.obj $(OBJPATH)/cvcalibfilter.obj $(OBJPATH)/cvclique.obj \
|
||||
$(OBJPATH)/cvcorrespond.obj $(OBJPATH)/cvcorrimages.obj $(OBJPATH)/cvcreatehandmask.obj \
|
||||
$(OBJPATH)/cvdpstereo.obj $(OBJPATH)/cveigenobjects.obj $(OBJPATH)/cvepilines.obj \
|
||||
$(OBJPATH)/cvface.obj $(OBJPATH)/cvfacedetection.obj $(OBJPATH)/cvfacetemplate.obj \
|
||||
$(OBJPATH)/cvfindface.obj $(OBJPATH)/cvfindhandregion.obj $(OBJPATH)/cvhmm.obj \
|
||||
$(OBJPATH)/cvhmm1d.obj $(OBJPATH)/cvhmmobs.obj $(OBJPATH)/cvlcm.obj \
|
||||
$(OBJPATH)/cvlee.obj $(OBJPATH)/cvlevmar.obj $(OBJPATH)/cvlevmarprojbandle.obj \
|
||||
$(OBJPATH)/cvlevmartrif.obj $(OBJPATH)/cvlines.obj $(OBJPATH)/cvlmeds.obj \
|
||||
$(OBJPATH)/cvmat.obj $(OBJPATH)/cvmorphcontours.obj $(OBJPATH)/cvmorphing.obj \
|
||||
$(OBJPATH)/cvprewarp.obj $(OBJPATH)/cvscanlines.obj $(OBJPATH)/cvsegment.obj \
|
||||
$(OBJPATH)/cvsubdiv2.obj $(OBJPATH)/cvtexture.obj $(OBJPATH)/cvtrifocal.obj \
|
||||
$(OBJPATH)/cvvecfacetracking.obj $(OBJPATH)/cvvideo.obj $(OBJPATH)/decomppoly.obj \
|
||||
$(OBJPATH)/enmin.obj $(OBJPATH)/extendededges.obj \
|
||||
$(OBJPATH)/bgfg_estimation.obj $(OBJPATH)/blobtrackanalysis.obj \
|
||||
$(OBJPATH)/blobtrackanalysishist.obj $(OBJPATH)/blobtrackanalysisior.obj \
|
||||
$(OBJPATH)/blobtrackanalysistrackdist.obj $(OBJPATH)/blobtrackgen1.obj \
|
||||
$(OBJPATH)/blobtrackgenyml.obj $(OBJPATH)/blobtrackingauto.obj \
|
||||
$(OBJPATH)/blobtrackingcc.obj $(OBJPATH)/blobtrackingccwithcr.obj \
|
||||
$(OBJPATH)/blobtrackingkalman.obj $(OBJPATH)/blobtrackinglist.obj \
|
||||
$(OBJPATH)/blobtrackingmsfg.obj $(OBJPATH)/blobtrackingmsfgs.obj \
|
||||
$(OBJPATH)/blobtrackpostprockalman.obj $(OBJPATH)/blobtrackpostproclinear.obj \
|
||||
$(OBJPATH)/blobtrackpostproclist.obj $(OBJPATH)/enteringblobdetection.obj \
|
||||
$(OBJPATH)/enteringblobdetectionreal.obj $(OBJPATH)/testseq.obj
|
||||
|
||||
INCS = ../include/cvaux.h ../include/cvaux.hpp ../include/cvmat.hpp \
|
||||
../include/cvvidsurv.hpp ./cvface.h ./cvfacedetection.h \
|
||||
./cvfacetemplate.h ./_cvaux.h ./_cvfacedetection.h \
|
||||
./_cvvectrack.h ./_cvvm.h $(ROOT)/cv/include/cv.h \
|
||||
$(ROOT)/cv/include/cv.hpp $(ROOT)/cv/include/cvcompat.h \
|
||||
$(ROOT)/cv/include/cvtypes.h $(ROOT)/cv/src/_cvmatrix.h \
|
||||
$(ROOT)/cxcore/include/cxcore.h $(ROOT)/cxcore/include/cxcore.hpp \
|
||||
$(ROOT)/cxcore/include/cxerror.h $(ROOT)/cxcore/include/cxmisc.h \
|
||||
$(ROOT)/cxcore/include/cxtypes.h $(ROOT)/cxcore/include/cvver.h
|
||||
|
||||
CXXFLAGS_PROJ = /I"." /I"../include" /I"$(ROOT)/cv/include" /I"$(ROOT)/cv/src" /I"$(ROOT)/cxcore/include"
|
||||
LIBS_PROJ = $(LIBPATH)"$(ROOT)/lib" cxcore$(DBG)$(OUT_P_SUFFIX).lib cv$(DBG)$(OUT_P_SUFFIX).lib
|
||||
|
||||
!if "$(MS)" == "bc"
|
||||
SRCPATH = .;.\vs
|
||||
!endif
|
||||
|
||||
!include $(ROOT)/_make/make_module_$(MS).mak
|
||||
|
||||
!if "$(MS)"=="ms"
|
||||
|
||||
# Hack: include all the files from vs subdirectory as well
|
||||
{.\vs}.cpp{$(OBJPATH)}.obj:
|
||||
@-mkdir $(OBJPATH) 2> nul
|
||||
@$(CXX) $(CXXFLAGS)$@ $<
|
||||
|
||||
!endif
|
||||
@@ -0,0 +1,42 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
@@ -0,0 +1,15 @@
|
||||
//{{NO_DEPENDENCIES}}
|
||||
// Microsoft Developer Studio generated include file.
|
||||
// Used by cvaux.rc
|
||||
//
|
||||
|
||||
// Next default values for new objects
|
||||
//
|
||||
#ifdef APSTUDIO_INVOKED
|
||||
#ifndef APSTUDIO_READONLY_SYMBOLS
|
||||
#define _APS_NEXT_RESOURCE_VALUE 101
|
||||
#define _APS_NEXT_COMMAND_VALUE 40001
|
||||
#define _APS_NEXT_CONTROL_VALUE 1000
|
||||
#define _APS_NEXT_SYMED_VALUE 101
|
||||
#endif
|
||||
#endif
|
||||
@@ -0,0 +1,204 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
#include "_cvaux.h"
|
||||
|
||||
//Function cvCreateBGStatModel creates and returns initialized BG model
|
||||
// parameters:
|
||||
// first_frame - frame from video sequence
|
||||
// model_type – type of BG model (CV_BG_MODEL_MOG, CV_BG_MODEL_FGD,…)
|
||||
// parameters - (optional) if NULL the default parameters of the algorithm will be used
|
||||
CvBGStatModel* cvCreateBGStatModel( IplImage* first_frame, int model_type, void* params )
|
||||
{
|
||||
CvBGStatModel* bg_model = NULL;
|
||||
|
||||
if( model_type == CV_BG_MODEL_FGD || model_type == CV_BG_MODEL_FGD_SIMPLE )
|
||||
bg_model = cvCreateFGDStatModel( first_frame, (CvFGDStatModelParams*)params );
|
||||
else if( model_type == CV_BG_MODEL_MOG )
|
||||
bg_model = cvCreateGaussianBGModel( first_frame, (CvGaussBGStatModelParams*)params );
|
||||
|
||||
return bg_model;
|
||||
}
|
||||
|
||||
|
||||
/* FOREGROUND DETECTOR INTERFACE */
|
||||
class CvFGDetectorBase:public CvFGDetector
|
||||
{
|
||||
protected:
|
||||
CvBGStatModel* m_pFG;
|
||||
int m_FGType;
|
||||
void* m_pFGParam; /* foreground params */
|
||||
CvFGDStatModelParams m_ParamFGD;
|
||||
CvGaussBGStatModelParams m_ParamMOG;
|
||||
char* m_SaveName;
|
||||
char* m_LoadName;
|
||||
public:
|
||||
virtual void SaveState(CvFileStorage* )
|
||||
{
|
||||
if( m_FGType == CV_BG_MODEL_FGD || m_FGType == CV_BG_MODEL_FGD_SIMPLE )
|
||||
{
|
||||
if( m_SaveName ) /* File name is not empty */
|
||||
{
|
||||
//cvSaveStatModel(m_SaveName, (CvFGDStatModel*)m_pFG);
|
||||
}
|
||||
}
|
||||
};
|
||||
virtual void LoadState(CvFileStorage* , CvFileNode* )
|
||||
{
|
||||
if( m_FGType == CV_BG_MODEL_FGD || m_FGType == CV_BG_MODEL_FGD_SIMPLE )
|
||||
{
|
||||
if( m_LoadName ) /* File name is not empty */
|
||||
{
|
||||
//cvRestoreStatModel(m_LoadName, (CvFGDStatModel*)m_pFG);
|
||||
}
|
||||
}
|
||||
};
|
||||
CvFGDetectorBase(int type, void* param)
|
||||
{
|
||||
m_pFG = NULL;
|
||||
m_FGType = type;
|
||||
m_pFGParam = param;
|
||||
if( m_FGType == CV_BG_MODEL_FGD || m_FGType == CV_BG_MODEL_FGD_SIMPLE )
|
||||
{
|
||||
if(m_pFGParam)
|
||||
{
|
||||
m_ParamFGD = *(CvFGDStatModelParams*)m_pFGParam;
|
||||
}
|
||||
else
|
||||
{
|
||||
m_ParamFGD.Lc = CV_BGFG_FGD_LC;
|
||||
m_ParamFGD.N1c = CV_BGFG_FGD_N1C;
|
||||
m_ParamFGD.N2c = CV_BGFG_FGD_N2C;
|
||||
m_ParamFGD.Lcc = CV_BGFG_FGD_LCC;
|
||||
m_ParamFGD.N1cc = CV_BGFG_FGD_N1CC;
|
||||
m_ParamFGD.N2cc = CV_BGFG_FGD_N2CC;
|
||||
m_ParamFGD.delta = CV_BGFG_FGD_DELTA;
|
||||
m_ParamFGD.alpha1 = CV_BGFG_FGD_ALPHA_1;
|
||||
m_ParamFGD.alpha2 = CV_BGFG_FGD_ALPHA_2;
|
||||
m_ParamFGD.alpha3 = CV_BGFG_FGD_ALPHA_3;
|
||||
m_ParamFGD.T = CV_BGFG_FGD_T;
|
||||
m_ParamFGD.minArea = CV_BGFG_FGD_MINAREA;
|
||||
m_ParamFGD.is_obj_without_holes = 1;
|
||||
m_ParamFGD.perform_morphing = 1;
|
||||
}
|
||||
AddParam("LC",&m_ParamFGD.Lc);
|
||||
AddParam("alpha1",&m_ParamFGD.alpha1);
|
||||
AddParam("alpha2",&m_ParamFGD.alpha2);
|
||||
AddParam("alpha3",&m_ParamFGD.alpha3);
|
||||
AddParam("N1c",&m_ParamFGD.N1c);
|
||||
AddParam("N2c",&m_ParamFGD.N2c);
|
||||
AddParam("N1cc",&m_ParamFGD.N1cc);
|
||||
AddParam("N2cc",&m_ParamFGD.N2cc);
|
||||
m_SaveName = 0;
|
||||
m_LoadName = 0;
|
||||
AddParam("SaveName",&m_SaveName);
|
||||
AddParam("LoadName",&m_LoadName);
|
||||
AddParam("ObjWithoutHoles",&m_ParamFGD.is_obj_without_holes);
|
||||
AddParam("Morphology",&m_ParamFGD.perform_morphing);
|
||||
}
|
||||
else if( m_FGType == CV_BG_MODEL_MOG )
|
||||
{
|
||||
if(m_pFGParam)
|
||||
{
|
||||
m_ParamMOG = *(CvGaussBGStatModelParams*)m_pFGParam;
|
||||
}
|
||||
else
|
||||
{
|
||||
m_ParamMOG.win_size = CV_BGFG_MOG_WINDOW_SIZE;
|
||||
m_ParamMOG.bg_threshold = CV_BGFG_MOG_BACKGROUND_THRESHOLD;
|
||||
m_ParamMOG.std_threshold = CV_BGFG_MOG_STD_THRESHOLD;
|
||||
m_ParamMOG.weight_init = CV_BGFG_MOG_WEIGHT_INIT;
|
||||
m_ParamMOG.variance_init = CV_BGFG_MOG_SIGMA_INIT*CV_BGFG_MOG_SIGMA_INIT;
|
||||
m_ParamMOG.minArea = CV_BGFG_MOG_MINAREA;
|
||||
m_ParamMOG.n_gauss = CV_BGFG_MOG_NGAUSSIANS;
|
||||
}
|
||||
AddParam("NG",&m_ParamMOG.n_gauss);
|
||||
}
|
||||
|
||||
};
|
||||
~CvFGDetectorBase()
|
||||
{
|
||||
if(m_pFG)cvReleaseBGStatModel( &m_pFG );
|
||||
}
|
||||
void ParamUpdate()
|
||||
{
|
||||
if(m_pFG)cvReleaseBGStatModel( &m_pFG );
|
||||
}
|
||||
|
||||
inline IplImage* GetMask()
|
||||
{
|
||||
return m_pFG?m_pFG->foreground:NULL;
|
||||
};
|
||||
/* process current image */
|
||||
virtual void Process(IplImage* pImg)
|
||||
{
|
||||
if(m_pFG == NULL)
|
||||
{
|
||||
void* param = m_pFGParam;
|
||||
if( m_FGType == CV_BG_MODEL_FGD || m_FGType == CV_BG_MODEL_FGD_SIMPLE )
|
||||
{
|
||||
param = &m_ParamFGD;
|
||||
}
|
||||
else if( m_FGType == CV_BG_MODEL_MOG )
|
||||
{
|
||||
param = &m_ParamMOG;
|
||||
}
|
||||
m_pFG = cvCreateBGStatModel(
|
||||
pImg,
|
||||
m_FGType,
|
||||
param);
|
||||
LoadState(0, 0);
|
||||
}
|
||||
else
|
||||
{
|
||||
cvUpdateBGStatModel( pImg, m_pFG );
|
||||
}
|
||||
};
|
||||
/* release foreground detector */
|
||||
virtual void Release()
|
||||
{
|
||||
SaveState(0);
|
||||
if(m_pFG)cvReleaseBGStatModel( &m_pFG );
|
||||
};
|
||||
};
|
||||
|
||||
CvFGDetector* cvCreateFGDetectorBase(int type, void *param)
|
||||
{
|
||||
return (CvFGDetector*) new CvFGDetectorBase(type, param);
|
||||
}
|
||||
@@ -0,0 +1,127 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
/*======================= FILTER LIST SHELL =====================*/
|
||||
typedef struct DefTrackAnalyser
|
||||
{
|
||||
CvBlob blob;
|
||||
CvBlobTrackAnalysisOne* pFilter;
|
||||
int m_LastFrame;
|
||||
int state;
|
||||
} DefTrackAnalyser;
|
||||
|
||||
class CvBlobTrackAnalysisList : public CvBlobTrackAnalysis
|
||||
{
|
||||
protected:
|
||||
CvBlobTrackAnalysisOne* (*m_CreateAnalysis)();
|
||||
CvBlobSeq m_TrackAnalyserList;
|
||||
int m_Frame;
|
||||
public:
|
||||
CvBlobTrackAnalysisList(CvBlobTrackAnalysisOne* (*create)()):m_TrackAnalyserList(sizeof(DefTrackAnalyser))
|
||||
{
|
||||
m_Frame = 0;
|
||||
m_CreateAnalysis = create;
|
||||
}
|
||||
~CvBlobTrackAnalysisList()
|
||||
{
|
||||
int i;
|
||||
for(i=m_TrackAnalyserList.GetBlobNum();i>0;--i)
|
||||
{
|
||||
DefTrackAnalyser* pF = (DefTrackAnalyser*)m_TrackAnalyserList.GetBlob(i-1);
|
||||
pF->pFilter->Release();
|
||||
}
|
||||
};
|
||||
virtual void AddBlob(CvBlob* pBlob)
|
||||
{
|
||||
DefTrackAnalyser* pF = (DefTrackAnalyser*)m_TrackAnalyserList.GetBlobByID(CV_BLOB_ID(pBlob));
|
||||
if(pF == NULL)
|
||||
{ /* create new filter */
|
||||
DefTrackAnalyser F;
|
||||
F.state = 0;
|
||||
F.blob = pBlob[0];
|
||||
F.m_LastFrame = m_Frame;
|
||||
F.pFilter = m_CreateAnalysis();
|
||||
m_TrackAnalyserList.AddBlob((CvBlob*)&F);
|
||||
pF = (DefTrackAnalyser*)m_TrackAnalyserList.GetBlobByID(CV_BLOB_ID(pBlob));
|
||||
}
|
||||
|
||||
assert(pF);
|
||||
pF->blob = pBlob[0];
|
||||
pF->m_LastFrame = m_Frame;
|
||||
};
|
||||
virtual void Process(IplImage* pImg, IplImage* pFG)
|
||||
{
|
||||
int i;
|
||||
for(i=m_TrackAnalyserList.GetBlobNum();i>0;--i)
|
||||
{
|
||||
DefTrackAnalyser* pF = (DefTrackAnalyser*)m_TrackAnalyserList.GetBlob(i-1);
|
||||
if(pF->m_LastFrame == m_Frame)
|
||||
{/* process */
|
||||
int ID = CV_BLOB_ID(pF);
|
||||
pF->state = pF->pFilter->Process(&(pF->blob), pImg, pFG);
|
||||
CV_BLOB_ID(pF) = ID;
|
||||
}
|
||||
else
|
||||
{/* delete blob filter */
|
||||
pF->pFilter->Release();
|
||||
m_TrackAnalyserList.DelBlob(i-1);
|
||||
}
|
||||
}/* next blob */
|
||||
m_Frame++;
|
||||
};
|
||||
float GetState(int BlobID)
|
||||
{
|
||||
DefTrackAnalyser* pF = (DefTrackAnalyser*)m_TrackAnalyserList.GetBlobByID(BlobID);
|
||||
return pF?pF->state:0.f;
|
||||
};
|
||||
void Release(){delete this;};
|
||||
|
||||
}; /* CvBlobTrackAnalysisList */
|
||||
|
||||
CvBlobTrackAnalysis* cvCreateBlobTrackAnalysisList(CvBlobTrackAnalysisOne* (*create)())
|
||||
{
|
||||
return (CvBlobTrackAnalysis*) new CvBlobTrackAnalysisList(create);
|
||||
}
|
||||
|
||||
/* ======================== Analyser modules ============================= */
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,161 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
/*======================= FILTER LIST SHELL =====================*/
|
||||
#define MAX_ANS 16
|
||||
#define MAX_DESC 1024
|
||||
class CvBlobTrackAnalysisIOR : public CvBlobTrackAnalysis
|
||||
{
|
||||
protected:
|
||||
struct DefAn
|
||||
{
|
||||
char* pName;
|
||||
CvBlobTrackAnalysis* pAn;
|
||||
} m_Ans[MAX_ANS];
|
||||
int m_AnNum;
|
||||
char m_Desc[MAX_DESC];
|
||||
public:
|
||||
CvBlobTrackAnalysisIOR()
|
||||
{
|
||||
m_AnNum = 0;
|
||||
}
|
||||
~CvBlobTrackAnalysisIOR()
|
||||
{
|
||||
};
|
||||
virtual void AddBlob(CvBlob* pBlob)
|
||||
{
|
||||
int i;
|
||||
for(i=0;i<m_AnNum;++i)
|
||||
{
|
||||
m_Ans[i].pAn->AddBlob(pBlob);
|
||||
}/* next analizer */
|
||||
};
|
||||
virtual void Process(IplImage* pImg, IplImage* pFG)
|
||||
{
|
||||
int i;
|
||||
#ifdef _OPENMP
|
||||
#pragma omp parallel for
|
||||
#endif
|
||||
for(i=0;i<m_AnNum;++i)
|
||||
{
|
||||
m_Ans[i].pAn->Process(pImg, pFG);
|
||||
}/* next analizer */
|
||||
};
|
||||
float GetState(int BlobID)
|
||||
{
|
||||
int state = 0;
|
||||
int i;
|
||||
for(i=0;i<m_AnNum;++i)
|
||||
{
|
||||
state |= (m_Ans[i].pAn->GetState(BlobID) > 0.5);
|
||||
}/* next analizer */
|
||||
return (float)state;
|
||||
};
|
||||
|
||||
virtual char* GetStateDesc(int BlobID)
|
||||
{
|
||||
int rest = MAX_DESC-1;
|
||||
int i;
|
||||
m_Desc[0] = 0;
|
||||
for(i=0;i<m_AnNum;++i)
|
||||
{
|
||||
char* str = m_Ans[i].pAn->GetStateDesc(BlobID);
|
||||
if(str && strlen(m_Ans[i].pName) + strlen(str)+4 < (size_t)rest)
|
||||
{
|
||||
strcat(m_Desc,m_Ans[i].pName);
|
||||
strcat(m_Desc,": ");
|
||||
strcat(m_Desc,str);
|
||||
strcat(m_Desc,"\n");
|
||||
rest = MAX_DESC - (int)strlen(m_Desc) - 1;
|
||||
}
|
||||
}/* next analizer */
|
||||
if(m_Desc[0]!=0)return m_Desc;
|
||||
return NULL;
|
||||
};
|
||||
virtual void SetFileName(char* /*DataBaseName*/)
|
||||
{
|
||||
};
|
||||
|
||||
int AddAnalizer(CvBlobTrackAnalysis* pA, char* pName)
|
||||
{
|
||||
if(m_AnNum<MAX_ANS)
|
||||
{
|
||||
//int i;
|
||||
m_Ans[m_AnNum].pName = pName;
|
||||
m_Ans[m_AnNum].pAn = pA;
|
||||
TransferParamsFromChild(m_Ans[m_AnNum].pAn, pName);
|
||||
m_AnNum++;
|
||||
return 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
printf("Can not add track analizer %s! (not more that %d analizers)\n",pName,MAX_ANS);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
void Release()
|
||||
{
|
||||
int i;
|
||||
for(i=0;i<m_AnNum;++i)
|
||||
{
|
||||
m_Ans[i].pAn->Release();
|
||||
}/* next analizer */
|
||||
delete this;
|
||||
};
|
||||
}; /* CvBlobTrackAnalysisIOR */
|
||||
|
||||
CvBlobTrackAnalysis* cvCreateModuleBlobTrackAnalysisIOR()
|
||||
{
|
||||
CvBlobTrackAnalysisIOR* pIOR = new CvBlobTrackAnalysisIOR();
|
||||
CvBlobTrackAnalysis* pA = NULL;
|
||||
|
||||
pA = cvCreateModuleBlobTrackAnalysisHistPVS();
|
||||
pIOR->AddAnalizer(pA, "HIST");
|
||||
|
||||
//pA = (CvBlobTrackAnalysis*)cvCreateModuleBlobTrackAnalysisHeightScale();
|
||||
//pIOR->AddAnalizer(pA, "SCALE");
|
||||
|
||||
return (CvBlobTrackAnalysis*)pIOR;
|
||||
}/* cvCreateCvBlobTrackAnalysisIOR */
|
||||
/* ======================== Analyser modules ============================= */
|
||||
|
||||
@@ -0,0 +1,561 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
typedef struct DefTrackPoint
|
||||
{
|
||||
float x,y,r,vx,vy,v;
|
||||
} DefTrackPoint;
|
||||
|
||||
class DefTrackRec
|
||||
{
|
||||
private:
|
||||
int ID;
|
||||
public:
|
||||
DefTrackRec(int id = 0,int BlobSize = sizeof(DefTrackPoint))
|
||||
{
|
||||
ID = id;
|
||||
m_pMem = cvCreateMemStorage();
|
||||
m_pSeq = cvCreateSeq(0,sizeof(CvSeq),BlobSize,m_pMem);
|
||||
}
|
||||
~DefTrackRec()
|
||||
{
|
||||
cvReleaseMemStorage(&m_pMem);
|
||||
};
|
||||
inline DefTrackPoint* GetPoint(int PointIndex)
|
||||
{
|
||||
return (DefTrackPoint*)cvGetSeqElem(m_pSeq,PointIndex);
|
||||
};
|
||||
inline void DelPoint(int PointIndex)
|
||||
{
|
||||
cvSeqRemove(m_pSeq,PointIndex);
|
||||
};
|
||||
inline void Clear()
|
||||
{
|
||||
cvClearSeq(m_pSeq);
|
||||
};
|
||||
inline void AddPoint(float x, float y, float r)
|
||||
{
|
||||
DefTrackPoint p = {x,y,r,0};
|
||||
int Num = GetPointNum();
|
||||
if(Num > 0)
|
||||
{
|
||||
DefTrackPoint* pPrev = GetPoint(Num-1);
|
||||
float Alpha = 0.8f;
|
||||
float dx = x-pPrev->x;
|
||||
float dy = y-pPrev->y;
|
||||
p.vx = Alpha*dx+(1-Alpha)*pPrev->vx;
|
||||
p.vy = Alpha*dy+(1-Alpha)*pPrev->vy;
|
||||
p.v = Alpha*dx+(1-Alpha)*pPrev->v;
|
||||
}
|
||||
AddPoint(&p);
|
||||
}
|
||||
inline void AddPoint(DefTrackPoint* pB)
|
||||
{/* add point and recal last velocities */
|
||||
int wnd=3;
|
||||
int Num;
|
||||
int i;
|
||||
cvSeqPush(m_pSeq,pB);
|
||||
|
||||
Num = GetPointNum();
|
||||
for(i=MAX(0,Num-wnd-1);i<Num;++i)
|
||||
{/* next updating point */
|
||||
DefTrackPoint* p = GetPoint(i);
|
||||
int j0 = i - wnd;
|
||||
int j1 = i + wnd;
|
||||
|
||||
if(j0<0) j0 = 0;
|
||||
if(j1>=Num)j1=Num-1;
|
||||
|
||||
if(j1>j0)
|
||||
{
|
||||
float dt = (float)(j1-j0);
|
||||
DefTrackPoint* p0 = GetPoint(j0);
|
||||
DefTrackPoint* p1 = GetPoint(j1);
|
||||
p->vx = (p1->x - p0->x) / dt;
|
||||
p->vy = (p1->y - p0->y) / dt;
|
||||
p->v = (float)sqrt(p->vx*p->vx+p->vy*p->vy);
|
||||
}
|
||||
}/* next updating point */
|
||||
|
||||
#if 0
|
||||
if(0)
|
||||
{ /* debug */
|
||||
int i;
|
||||
printf("Blob %d: ",ID);
|
||||
for(i=0;i<GetPointNum();++i)
|
||||
{
|
||||
DefTrackPoint* p = GetPoint(i);
|
||||
printf(",(%.2f,%.2f,%f.2)",p->vx,p->vy,p->v);
|
||||
}
|
||||
printf("\n");
|
||||
}
|
||||
#endif
|
||||
};
|
||||
inline int GetPointNum()
|
||||
{
|
||||
return m_pSeq->total;
|
||||
};
|
||||
private:
|
||||
CvMemStorage* m_pMem;
|
||||
CvSeq* m_pSeq;
|
||||
};
|
||||
|
||||
/* fill array pIdxPairs by pair of index of correspondent blobs */
|
||||
/* return number of pairs */
|
||||
/* pIdxPairs must have size not less that 2*(pSeqNum+pSeqTNum) */
|
||||
/* pTmp is pointer to memory which size is pSeqNum*pSeqTNum*16 */
|
||||
typedef struct DefMatch
|
||||
{
|
||||
int Idx; /* prev best blob index */
|
||||
int IdxT; /* prev best template blob index */
|
||||
double D; /* blob to blob distance sum */
|
||||
}DefMatch;
|
||||
static int cvTrackMatch(DefTrackRec* pSeq, int MaxLen, DefTrackRec* pSeqT, int* pIdxPairs, void* pTmp)
|
||||
{
|
||||
int NumPair = 0;
|
||||
DefMatch* pMT = (DefMatch*)pTmp;
|
||||
int Num = pSeq->GetPointNum();
|
||||
int NumT = pSeqT->GetPointNum();
|
||||
int i,it;
|
||||
int i0=0; /* last point in the track sequence */
|
||||
|
||||
if(MaxLen > 0 && Num > MaxLen)
|
||||
{/* set new point seq len and new last point in this seq */
|
||||
Num = MaxLen;
|
||||
i0 = pSeq->GetPointNum() - Num;
|
||||
}
|
||||
|
||||
for(i=0;i<Num;++i)
|
||||
{ /* for eacj point row */
|
||||
for(it=0;it<NumT;++it)
|
||||
{ /* for each point templet column */
|
||||
DefTrackPoint* pB = pSeq->GetPoint(i+i0);
|
||||
DefTrackPoint* pBT = pSeqT->GetPoint(it);
|
||||
DefMatch* pMT_cur = pMT + i*NumT + it;
|
||||
double dx = pB->x-pBT->x;
|
||||
double dy = pB->y-pBT->y;
|
||||
double D = dx*dx+dy*dy;
|
||||
int DI[3][2] = {{-1,-1},{-1,0},{0,-1}};
|
||||
int iDI;
|
||||
|
||||
pMT_cur->D = D;
|
||||
pMT_cur->Idx = -1;
|
||||
pMT_cur->IdxT = 0;
|
||||
|
||||
if(i==0) continue;
|
||||
|
||||
for(iDI=0;iDI<3;++iDI)
|
||||
{
|
||||
int i_prev = i+DI[iDI][0];
|
||||
int it_prev = it+DI[iDI][1];
|
||||
if(i_prev >= 0 && it_prev>=0)
|
||||
{
|
||||
double D_cur = D+pMT[NumT*i_prev+it_prev].D;
|
||||
if(pMT_cur->D > D_cur || (pMT_cur->Idx<0) )
|
||||
{/* set new best local way */
|
||||
pMT_cur->D = D_cur;
|
||||
pMT_cur->Idx = i_prev;
|
||||
pMT_cur->IdxT = it_prev;
|
||||
}
|
||||
}
|
||||
}/* check next direction */
|
||||
}/* fill next colum from table */
|
||||
}/*fill next row */
|
||||
|
||||
{ /* back tracking */
|
||||
/* find best end in template */
|
||||
int it_best = 0;
|
||||
DefMatch* pMT_best = pMT + (Num-1)*NumT;
|
||||
i = Num-1; /* set current i to last position */
|
||||
for(it=1;it<NumT;++it)
|
||||
{
|
||||
DefMatch* pMT_new = pMT + it + i*NumT;
|
||||
if(pMT_best->D > pMT_new->D)
|
||||
{
|
||||
pMT_best->D = pMT_new->D;
|
||||
it_best = it;
|
||||
}
|
||||
}/* find best end template point */
|
||||
|
||||
/* back tracking whole sequence */
|
||||
for(it = it_best;i>=0 && it>=0;)
|
||||
{
|
||||
DefMatch* pMT_new = pMT + it + i*NumT;
|
||||
pIdxPairs[2*NumPair] = i+i0;
|
||||
pIdxPairs[2*NumPair+1] = it;
|
||||
NumPair++;
|
||||
|
||||
it = pMT_new->IdxT;
|
||||
i = pMT_new->Idx;
|
||||
}
|
||||
}/* end back tracing */
|
||||
|
||||
return NumPair;
|
||||
}/* cvTrackMatch */
|
||||
|
||||
typedef struct DefTrackForDist
|
||||
{
|
||||
CvBlob blob;
|
||||
DefTrackRec* pTrack;
|
||||
int LastFrame;
|
||||
float state;
|
||||
/* for debug */
|
||||
int close;
|
||||
} DefTrackForDist;
|
||||
|
||||
class CvBlobTrackAnalysisTrackDist : public CvBlobTrackAnalysis
|
||||
{
|
||||
/*---------------- internal functions --------------------*/
|
||||
private:
|
||||
char* m_pDebugAVIName; /* for debuf purpose */
|
||||
//CvVideoWriter* m_pDebugAVI; /* for debuf purpose */
|
||||
IplImage* m_pDebugImg; /* for debuf purpose */
|
||||
|
||||
char m_DataFileName[1024];
|
||||
CvBlobSeq m_Tracks;
|
||||
CvBlobSeq m_TrackDataBase;
|
||||
int m_Frame;
|
||||
void* m_pTempData;
|
||||
int m_TempDataSize;
|
||||
int m_TraceLen;
|
||||
float m_AbnormalThreshold;
|
||||
float m_PosThreshold;
|
||||
float m_VelThreshold;
|
||||
inline void* ReallocTempData(int Size)
|
||||
{
|
||||
if(Size <= m_TempDataSize && m_pTempData) return m_pTempData;
|
||||
cvFree(&m_pTempData);
|
||||
m_TempDataSize = 0;
|
||||
m_pTempData = cvAlloc(Size);
|
||||
if(m_pTempData) m_TempDataSize = Size;
|
||||
return m_pTempData;
|
||||
}/* ReallocTempData */
|
||||
public:
|
||||
CvBlobTrackAnalysisTrackDist():m_Tracks(sizeof(DefTrackForDist)),m_TrackDataBase(sizeof(DefTrackForDist))
|
||||
{
|
||||
m_pDebugImg = 0;
|
||||
//m_pDebugAVI = 0;
|
||||
m_Frame = 0;
|
||||
m_pTempData = NULL;
|
||||
m_TempDataSize = 0;
|
||||
|
||||
m_pDebugAVIName = NULL;
|
||||
AddParam("DebugAVI",&m_pDebugAVIName);
|
||||
CommentParam("DebugAVI","Name of AVI file to save images from debug window");
|
||||
|
||||
m_TraceLen = 50;
|
||||
AddParam("TraceLen",&m_TraceLen);
|
||||
CommentParam("TraceLen","Length (in frames) of trajectory part that is used for comparison");
|
||||
|
||||
m_AbnormalThreshold = 0.02f;
|
||||
AddParam("AbnormalThreshold",&m_AbnormalThreshold);
|
||||
CommentParam("AbnormalThreshold","If trajectory is equal with less then <AbnormalThreshold*DataBaseTrackNum> tracks then trajectory is abnormal");
|
||||
|
||||
m_PosThreshold = 1.25;
|
||||
AddParam("PosThreshold",&m_PosThreshold);
|
||||
CommentParam("PosThreshold","Minimal allowd distance in blob width that is allowed");
|
||||
|
||||
m_VelThreshold = 0.5;
|
||||
AddParam("VelThreshold",&m_VelThreshold);
|
||||
CommentParam("VelThreshold","Minimal allowed relative difference between blob speed");
|
||||
|
||||
}/* constructor */
|
||||
~CvBlobTrackAnalysisTrackDist()
|
||||
{
|
||||
int i;
|
||||
for(i=m_Tracks.GetBlobNum();i>0;--i)
|
||||
{
|
||||
DefTrackForDist* pF = (DefTrackForDist*)m_Tracks.GetBlob(i-1);
|
||||
delete pF->pTrack;
|
||||
}
|
||||
if(m_pDebugImg) cvReleaseImage(&m_pDebugImg);
|
||||
//if(m_pDebugAVI) cvReleaseVideoWriter(&m_pDebugAVI);
|
||||
}/* destructor */
|
||||
|
||||
/*----------------- interface --------------------*/
|
||||
virtual void AddBlob(CvBlob* pBlob)
|
||||
{
|
||||
DefTrackForDist* pF = (DefTrackForDist*)m_Tracks.GetBlobByID(CV_BLOB_ID(pBlob));
|
||||
if(pF == NULL)
|
||||
{ /* create new TRack record */
|
||||
DefTrackForDist F;
|
||||
F.state = 0;
|
||||
F.blob = pBlob[0];
|
||||
F.LastFrame = m_Frame;
|
||||
F.pTrack = new DefTrackRec(CV_BLOB_ID(pBlob));
|
||||
m_Tracks.AddBlob((CvBlob*)&F);
|
||||
pF = (DefTrackForDist*)m_Tracks.GetBlobByID(CV_BLOB_ID(pBlob));
|
||||
}
|
||||
|
||||
assert(pF);
|
||||
assert(pF->pTrack);
|
||||
pF->pTrack->AddPoint(pBlob->x,pBlob->y,pBlob->w*0.5f);
|
||||
pF->blob = pBlob[0];
|
||||
pF->LastFrame = m_Frame;
|
||||
};
|
||||
virtual void Process(IplImage* pImg, IplImage* /*pFG*/)
|
||||
{
|
||||
int i;
|
||||
double MinTv = pImg->width/1440.0; /* minimal threshold for speed difference */
|
||||
double MinTv2 = MinTv*MinTv;
|
||||
for(i=m_Tracks.GetBlobNum();i>0;--i)
|
||||
{
|
||||
DefTrackForDist* pF = (DefTrackForDist*)m_Tracks.GetBlob(i-1);
|
||||
pF->state = 0;
|
||||
if(pF->LastFrame == m_Frame || pF->LastFrame+1 == m_Frame)
|
||||
{/* process one blob trajectory */
|
||||
int NumEq = 0;
|
||||
int it;
|
||||
for(it=m_TrackDataBase.GetBlobNum();it>0;--it)
|
||||
{/* check template */
|
||||
DefTrackForDist* pFT = (DefTrackForDist*)m_TrackDataBase.GetBlob(it-1);
|
||||
int Num = pF->pTrack->GetPointNum();
|
||||
int NumT = pFT->pTrack->GetPointNum();
|
||||
int* pPairIdx = (int*)ReallocTempData(sizeof(int)*2*(Num+NumT)+sizeof(DefMatch)*Num*NumT);
|
||||
void* pTmpData = pPairIdx+2*(Num+NumT);
|
||||
int PairNum = 0;
|
||||
int k;
|
||||
int Equal = 1;
|
||||
int UseVel = 0;
|
||||
int UsePos = 0;
|
||||
|
||||
if(i==it) continue;
|
||||
|
||||
/* match track */
|
||||
PairNum = cvTrackMatch( pF->pTrack, m_TraceLen, pFT->pTrack, pPairIdx, pTmpData );
|
||||
Equal = MAX(1,cvRound(PairNum*0.1));
|
||||
|
||||
UseVel = 3*pF->pTrack->GetPointNum() > m_TraceLen;
|
||||
UsePos = 10*pF->pTrack->GetPointNum() > m_TraceLen;
|
||||
|
||||
{ /* check continues */
|
||||
float D;
|
||||
int DI = pPairIdx[0*2+0]-pPairIdx[(PairNum-1)*2+0];
|
||||
int DIt = pPairIdx[0*2+1]-pPairIdx[(PairNum-1)*2+1];
|
||||
if(UseVel && DI != 0)
|
||||
{
|
||||
D = (float)(DI-DIt)/(float)DI;
|
||||
if(fabs(D)>m_VelThreshold)Equal=0;
|
||||
if(fabs(D)>m_VelThreshold*0.5)Equal/=2;
|
||||
}
|
||||
}/* check continues */
|
||||
|
||||
for(k=0;Equal>0 && k<PairNum;++k)
|
||||
{/* compare with threshold */
|
||||
int j = pPairIdx[k*2+0];
|
||||
int jt = pPairIdx[k*2+1];
|
||||
DefTrackPoint* pB = pF->pTrack->GetPoint(j);
|
||||
DefTrackPoint* pBT = pFT->pTrack->GetPoint(jt);
|
||||
double dx = pB->x-pBT->x;
|
||||
double dy = pB->y-pBT->y;
|
||||
double dvx = pB->vx - pBT->vx;
|
||||
double dvy = pB->vy - pBT->vy;
|
||||
//double dv = pB->v - pBT->v;
|
||||
double D = dx*dx+dy*dy;
|
||||
double Td = pBT->r*m_PosThreshold;
|
||||
double dv2 = dvx*dvx+dvy*dvy;
|
||||
double Tv2 = (pBT->vx*pBT->vx+pBT->vy*pBT->vy)*m_VelThreshold*m_VelThreshold;
|
||||
double Tvm = pBT->v*m_VelThreshold;
|
||||
|
||||
|
||||
if(Tv2 < MinTv2) Tv2 = MinTv2;
|
||||
if(Tvm < MinTv) Tvm = MinTv;
|
||||
|
||||
/* check trajectory position */
|
||||
if(UsePos && D > Td*Td)
|
||||
{
|
||||
Equal--;
|
||||
}
|
||||
else
|
||||
/* check trajectory velacity */
|
||||
/* don't consider tails of trajectory becasue its unnstable for velosity calculation */
|
||||
if(UseVel && j>5 && jt>5 && dv2 > Tv2 )
|
||||
{
|
||||
Equal--;
|
||||
}
|
||||
}/* compare with threshold */
|
||||
|
||||
if(Equal>0)
|
||||
{
|
||||
NumEq++;
|
||||
pFT->close++;
|
||||
}
|
||||
}/* next template */
|
||||
|
||||
{ /* calc state */
|
||||
float T = m_TrackDataBase.GetBlobNum() * m_AbnormalThreshold; /* calc threshold */
|
||||
|
||||
if(T>0)
|
||||
{
|
||||
pF->state = (T - NumEq)/(T*0.2f) + 0.5f;
|
||||
}
|
||||
if(pF->state<0)pF->state=0;
|
||||
if(pF->state>1)pF->state=1;
|
||||
|
||||
/*if(0)if(pF->state>0)
|
||||
{// if abnormal blob
|
||||
printf("Abnormal blob(%d) %d < %f, state=%f\n",CV_BLOB_ID(pF),NumEq,T, pF->state);
|
||||
}*/
|
||||
}/* calc state */
|
||||
}/* process one blob trajectory */
|
||||
else
|
||||
{/* move track to trcaks data base */
|
||||
m_TrackDataBase.AddBlob((CvBlob*)pF);
|
||||
m_Tracks.DelBlob(i-1);
|
||||
}
|
||||
}/* next blob */
|
||||
|
||||
|
||||
if(m_Wnd)
|
||||
{/* debug output */
|
||||
int i;
|
||||
|
||||
if(m_pDebugImg==NULL)
|
||||
m_pDebugImg = cvCloneImage(pImg);
|
||||
else
|
||||
cvCopyImage(pImg, m_pDebugImg);
|
||||
|
||||
for(i=m_TrackDataBase.GetBlobNum();i>0;--i)
|
||||
{/* draw all elements from trackdata base */
|
||||
int j;
|
||||
DefTrackForDist* pF = (DefTrackForDist*)m_TrackDataBase.GetBlob(i-1);
|
||||
CvScalar color = CV_RGB(0,0,0);
|
||||
if(!pF->close) continue;
|
||||
if(pF->close)
|
||||
{
|
||||
color = CV_RGB(0,0,255);
|
||||
}
|
||||
else
|
||||
{
|
||||
color = CV_RGB(0,0,128);
|
||||
}
|
||||
|
||||
for(j=pF->pTrack->GetPointNum();j>0;j--)
|
||||
{
|
||||
DefTrackPoint* pB = pF->pTrack->GetPoint(j-1);
|
||||
int r = 0;//MAX(cvRound(pB->r),1);
|
||||
cvCircle(m_pDebugImg, cvPoint(cvRound(pB->x),cvRound(pB->y)), r, color);
|
||||
}
|
||||
pF->close = 0;
|
||||
}/* draw all elements from trackdata base */
|
||||
|
||||
for(i=m_Tracks.GetBlobNum();i>0;--i)
|
||||
{/* draw all elements for all trajectories */
|
||||
DefTrackForDist* pF = (DefTrackForDist*)m_Tracks.GetBlob(i-1);
|
||||
int j;
|
||||
int c = cvRound(pF->state*255);
|
||||
CvScalar color = CV_RGB(c,255-c,0);
|
||||
CvPoint p = cvPointFrom32f(CV_BLOB_CENTER(pF));
|
||||
int x = cvRound(CV_BLOB_RX(pF)), y = cvRound(CV_BLOB_RY(pF));
|
||||
CvSize s = cvSize(MAX(1,x), MAX(1,y));
|
||||
|
||||
cvEllipse( m_pDebugImg,
|
||||
p,
|
||||
s,
|
||||
0, 0, 360,
|
||||
CV_RGB(c,255-c,0), cvRound(1+(0*c)/255) );
|
||||
|
||||
for(j=pF->pTrack->GetPointNum();j>0;j--)
|
||||
{
|
||||
DefTrackPoint* pB = pF->pTrack->GetPoint(j-1);
|
||||
if(pF->pTrack->GetPointNum()-j > m_TraceLen) break;
|
||||
cvCircle(m_pDebugImg, cvPoint(cvRound(pB->x),cvRound(pB->y)), 0, color);
|
||||
}
|
||||
pF->close = 0;
|
||||
}/* draw all elements for all trajectories */
|
||||
|
||||
//cvNamedWindow("Tracks",0);
|
||||
//cvShowImage("Tracks", m_pDebugImg);
|
||||
}/* debug output */
|
||||
|
||||
#if 0
|
||||
if(m_pDebugImg && m_pDebugAVIName)
|
||||
{
|
||||
if(m_pDebugAVI==NULL)
|
||||
{/* create avi file for writing */
|
||||
m_pDebugAVI = cvCreateVideoWriter(
|
||||
m_pDebugAVIName,
|
||||
CV_FOURCC('x','v','i','d'),
|
||||
25,
|
||||
cvSize(m_pDebugImg->width,m_pDebugImg->height));
|
||||
if(m_pDebugAVI == NULL)
|
||||
{
|
||||
printf("WARNING!!! Can not create AVI file %s for writing\n",m_pDebugAVIName);
|
||||
}
|
||||
}/* create avi file for writing */
|
||||
if(m_pDebugAVI)cvWriteFrame( m_pDebugAVI, m_pDebugImg );
|
||||
}/* write debug window to AVI file */
|
||||
#endif
|
||||
m_Frame++;
|
||||
};
|
||||
float GetState(int BlobID)
|
||||
{
|
||||
DefTrackForDist* pF = (DefTrackForDist*)m_Tracks.GetBlobByID(BlobID);
|
||||
return pF?pF->state:0.0f;
|
||||
};
|
||||
/* return 0 if trajectory is normal
|
||||
return >0 if trajectory abnormal */
|
||||
virtual char* GetStateDesc(int BlobID)
|
||||
{
|
||||
if(GetState(BlobID)>0.5) return "abnormal";
|
||||
return NULL;
|
||||
}
|
||||
virtual void SetFileName(char* DataBaseName)
|
||||
{
|
||||
m_DataFileName[0] = 0;
|
||||
if(DataBaseName)
|
||||
{
|
||||
strncpy(m_DataFileName,DataBaseName,1000);
|
||||
strcat(m_DataFileName, ".yml");
|
||||
}
|
||||
};
|
||||
|
||||
virtual void Release(){ delete this; };
|
||||
|
||||
};
|
||||
|
||||
|
||||
|
||||
CvBlobTrackAnalysis* cvCreateModuleBlobTrackAnalysisTrackDist()
|
||||
{return (CvBlobTrackAnalysis*) new CvBlobTrackAnalysisTrackDist;}
|
||||
|
||||
@@ -0,0 +1,171 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
// For Open Source Computer Vision Library
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
typedef struct DefBlobTrack
|
||||
{
|
||||
CvBlob blob;
|
||||
CvBlobSeq* pSeq;
|
||||
int FrameBegin;
|
||||
int FrameLast;
|
||||
int Saved; /* flag */
|
||||
}DefBlobTrack;
|
||||
|
||||
|
||||
static void SaveTrack(DefBlobTrack* pTrack, char* pFileName, int norm = 0)
|
||||
{/* save blob track */
|
||||
int j;
|
||||
FILE* out = NULL;
|
||||
CvBlobSeq* pS = pTrack->pSeq;
|
||||
CvBlob* pB0 = pS?pS->GetBlob(0):NULL;
|
||||
|
||||
if(pFileName == NULL) return;
|
||||
if(pTrack == NULL) return;
|
||||
|
||||
out = fopen(pFileName,"at");
|
||||
if(out == NULL)
|
||||
{
|
||||
printf("Warning! Can not open %s file for track output\n",pFileName);
|
||||
return;
|
||||
}
|
||||
|
||||
fprintf(out,"%d",pTrack->FrameBegin);
|
||||
|
||||
if(pS)for(j=0;j<pS->GetBlobNum();++j)
|
||||
{
|
||||
CvBlob* pB = pS->GetBlob(j);
|
||||
|
||||
fprintf(out,", %.1f, %.1f", CV_BLOB_X(pB),CV_BLOB_Y(pB));
|
||||
if(CV_BLOB_WX(pB0)>0)
|
||||
fprintf(out,", %.2f",CV_BLOB_WX(pB)/(norm?CV_BLOB_WX(pB0):1));
|
||||
if(CV_BLOB_WY(pB0)>0)
|
||||
fprintf(out,", %.2f",CV_BLOB_WY(pB)/(norm?CV_BLOB_WY(pB0):1));
|
||||
}
|
||||
fprintf(out,"\n");
|
||||
fclose(out);
|
||||
pTrack->Saved = 1;
|
||||
}/* save blob track */
|
||||
|
||||
class CvBlobTrackGen1:public CvBlobTrackGen
|
||||
{
|
||||
|
||||
public:
|
||||
CvBlobTrackGen1(int BlobSizeNorm = 0):m_TrackList(sizeof(DefBlobTrack))
|
||||
{
|
||||
m_BlobSizeNorm = BlobSizeNorm;
|
||||
m_Frame = 0;
|
||||
m_pFileName = NULL;
|
||||
};
|
||||
~CvBlobTrackGen1()
|
||||
{
|
||||
int i;
|
||||
for(i=m_TrackList.GetBlobNum();i>0;--i)
|
||||
{
|
||||
DefBlobTrack* pTrack = (DefBlobTrack*)m_TrackList.GetBlob(i-1);
|
||||
if(!pTrack->Saved)
|
||||
{/* save track */
|
||||
SaveTrack(pTrack, m_pFileName, m_BlobSizeNorm);
|
||||
}/* save track */
|
||||
|
||||
/* delete sequence */
|
||||
delete pTrack->pSeq;
|
||||
pTrack->pSeq = NULL;
|
||||
}/* check next track */
|
||||
}/* destructor */
|
||||
|
||||
void SetFileName(char* pFileName){m_pFileName = pFileName;};
|
||||
void AddBlob(CvBlob* pBlob)
|
||||
{
|
||||
DefBlobTrack* pTrack = (DefBlobTrack*)m_TrackList.GetBlobByID(CV_BLOB_ID(pBlob));
|
||||
if(pTrack==NULL)
|
||||
{/* add new track */
|
||||
DefBlobTrack Track;
|
||||
Track.blob = pBlob[0];
|
||||
Track.FrameBegin = m_Frame;
|
||||
Track.pSeq = new CvBlobSeq;
|
||||
Track.Saved = 0;
|
||||
m_TrackList.AddBlob((CvBlob*)&Track);
|
||||
pTrack = (DefBlobTrack*)m_TrackList.GetBlobByID(CV_BLOB_ID(pBlob));
|
||||
}/* add new track */
|
||||
|
||||
assert(pTrack);
|
||||
pTrack->FrameLast = m_Frame;
|
||||
assert(pTrack->pSeq);
|
||||
pTrack->pSeq->AddBlob(pBlob);
|
||||
};
|
||||
void Process(IplImage* /*pImg*/ = NULL, IplImage* /*pFG*/ = NULL)
|
||||
{
|
||||
int i;
|
||||
for(i=m_TrackList.GetBlobNum();i>0;--i)
|
||||
{
|
||||
DefBlobTrack* pTrack = (DefBlobTrack*)m_TrackList.GetBlob(i-1);
|
||||
if(pTrack->FrameLast < m_Frame && !pTrack->Saved)
|
||||
{/* save track */
|
||||
SaveTrack(pTrack, m_pFileName, m_BlobSizeNorm);
|
||||
if(pTrack->Saved)
|
||||
{ /* delete sequence */
|
||||
delete pTrack->pSeq;
|
||||
pTrack->pSeq = NULL;
|
||||
m_TrackList.DelBlob(i-1);
|
||||
}
|
||||
}/* save track */
|
||||
}/* check next track */
|
||||
m_Frame++;
|
||||
}
|
||||
void Release()
|
||||
{
|
||||
delete this;
|
||||
}
|
||||
protected:
|
||||
int m_Frame;
|
||||
char* m_pFileName;
|
||||
CvBlobSeq m_TrackList;
|
||||
int m_BlobSizeNorm;
|
||||
}; /* class CvBlobTrackGen1 */
|
||||
|
||||
|
||||
CvBlobTrackGen* cvCreateModuleBlobTrackGen1()
|
||||
{
|
||||
return (CvBlobTrackGen*) new CvBlobTrackGen1(0);
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,202 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
typedef struct DefBlobTrack
|
||||
{
|
||||
CvBlob blob;
|
||||
CvBlobSeq* pSeq;
|
||||
int FrameBegin;
|
||||
int FrameLast;
|
||||
int Saved; /* flag */
|
||||
}DefBlobTrack;
|
||||
|
||||
class CvBlobTrackGenYML:public CvBlobTrackGen
|
||||
{
|
||||
protected:
|
||||
int m_Frame;
|
||||
char* m_pFileName;
|
||||
CvBlobSeq m_TrackList;
|
||||
CvSize m_Size;
|
||||
|
||||
void SaveAll()
|
||||
{
|
||||
int ObjNum = m_TrackList.GetBlobNum();
|
||||
int i;
|
||||
char video_name[1024];
|
||||
char* struct_name = NULL;
|
||||
CvFileStorage* storage = cvOpenFileStorage(m_pFileName,NULL,CV_STORAGE_WRITE_TEXT);
|
||||
if(storage==NULL)
|
||||
{
|
||||
printf("WARNING!!! Can not open %s file for trajectories writing",m_pFileName);
|
||||
}
|
||||
|
||||
for(i=0;i<1024 && m_pFileName[i]!='.' && m_pFileName[i]!=0;++i)video_name[i]=m_pFileName[i];
|
||||
video_name[i] = 0;
|
||||
for(;i>0;i--)
|
||||
{
|
||||
if(video_name[i-1] == '\\') break;
|
||||
if(video_name[i-1] == '/') break;
|
||||
if(video_name[i-1] == ':') break;
|
||||
}
|
||||
struct_name = video_name + i;
|
||||
|
||||
cvStartWriteStruct(storage, struct_name, CV_NODE_SEQ);
|
||||
for(i=0;i<ObjNum;++i)
|
||||
{
|
||||
char obj_name[1024];
|
||||
DefBlobTrack* pTrack = (DefBlobTrack*)m_TrackList.GetBlob(i);
|
||||
if(pTrack==NULL) continue;
|
||||
sprintf(obj_name,"%s_obj%d",struct_name,i);
|
||||
cvStartWriteStruct(storage, NULL, CV_NODE_MAP);
|
||||
cvWriteInt(storage, "FrameBegin", pTrack->FrameBegin);
|
||||
cvWriteString(storage, "VideoObj", obj_name);
|
||||
cvEndWriteStruct( storage );
|
||||
pTrack->Saved = 1;
|
||||
}
|
||||
cvEndWriteStruct( storage );
|
||||
|
||||
for(i=0;i<ObjNum;++i)
|
||||
{
|
||||
char obj_name[1024];
|
||||
DefBlobTrack* pTrack = (DefBlobTrack*)m_TrackList.GetBlob(i);
|
||||
CvBlobSeq* pSeq = pTrack->pSeq;
|
||||
sprintf(obj_name,"%s_obj%d",struct_name,i);
|
||||
cvStartWriteStruct(storage, obj_name, CV_NODE_MAP);
|
||||
|
||||
{ /* write pos */
|
||||
int j;
|
||||
CvPoint2D32f p;
|
||||
cvStartWriteStruct(storage, "Pos", CV_NODE_SEQ|CV_NODE_FLOW);
|
||||
for(j=0;j<pSeq->GetBlobNum();++j)
|
||||
{
|
||||
CvBlob* pB = pSeq->GetBlob(j);
|
||||
p.x = pB->x/(m_Size.width-1);
|
||||
p.y = pB->y/(m_Size.height-1);
|
||||
cvWriteRawData(storage, &p, 1 ,"ff");
|
||||
}
|
||||
cvEndWriteStruct( storage );
|
||||
}
|
||||
|
||||
{ /* write size */
|
||||
int j;
|
||||
CvPoint2D32f p;
|
||||
cvStartWriteStruct(storage, "Size", CV_NODE_SEQ|CV_NODE_FLOW);
|
||||
for(j=0;j<pSeq->GetBlobNum();++j)
|
||||
{
|
||||
CvBlob* pB = pSeq->GetBlob(j);
|
||||
p.x = pB->w/(m_Size.width-1);
|
||||
p.y = pB->h/(m_Size.height-1);
|
||||
cvWriteRawData(storage, &p, 1 ,"ff");
|
||||
}
|
||||
cvEndWriteStruct( storage );
|
||||
}
|
||||
cvEndWriteStruct( storage );
|
||||
}
|
||||
cvReleaseFileStorage(&storage);
|
||||
}/* Save All */
|
||||
public:
|
||||
CvBlobTrackGenYML():m_TrackList(sizeof(DefBlobTrack))
|
||||
{
|
||||
m_Frame = 0;
|
||||
m_pFileName = NULL;
|
||||
m_Size = cvSize(2,2);
|
||||
};
|
||||
~CvBlobTrackGenYML()
|
||||
{
|
||||
int i;
|
||||
SaveAll();
|
||||
for(i=m_TrackList.GetBlobNum();i>0;--i)
|
||||
{
|
||||
DefBlobTrack* pTrack = (DefBlobTrack*)m_TrackList.GetBlob(i-1);
|
||||
/* delete sequence */
|
||||
delete pTrack->pSeq;
|
||||
pTrack->pSeq = NULL;
|
||||
}/* check next track */
|
||||
}/* destructor */
|
||||
|
||||
void SetFileName(char* pFileName){m_pFileName = pFileName;};
|
||||
void AddBlob(CvBlob* pBlob)
|
||||
{
|
||||
DefBlobTrack* pTrack = (DefBlobTrack*)m_TrackList.GetBlobByID(CV_BLOB_ID(pBlob));
|
||||
if(pTrack==NULL)
|
||||
{/* add new track */
|
||||
DefBlobTrack Track;
|
||||
Track.blob = pBlob[0];
|
||||
Track.FrameBegin = m_Frame;
|
||||
Track.pSeq = new CvBlobSeq;
|
||||
Track.Saved = 0;
|
||||
m_TrackList.AddBlob((CvBlob*)&Track);
|
||||
pTrack = (DefBlobTrack*)m_TrackList.GetBlobByID(CV_BLOB_ID(pBlob));
|
||||
}/* add new track */
|
||||
|
||||
assert(pTrack);
|
||||
pTrack->FrameLast = m_Frame;
|
||||
assert(pTrack->pSeq);
|
||||
pTrack->pSeq->AddBlob(pBlob);
|
||||
};
|
||||
void Process(IplImage* pImg = NULL, IplImage* /*pFG*/ = NULL)
|
||||
{
|
||||
int i;
|
||||
m_Size = cvSize(pImg->width,pImg->height);
|
||||
for(i=m_TrackList.GetBlobNum();i>0;--i)
|
||||
{
|
||||
DefBlobTrack* pTrack = (DefBlobTrack*)m_TrackList.GetBlob(i-1);
|
||||
if(pTrack->FrameLast < m_Frame && !pTrack->Saved)
|
||||
{/* save track */
|
||||
SaveAll();
|
||||
}/* save track */
|
||||
}/* check next track */
|
||||
m_Frame++;
|
||||
}
|
||||
void Release()
|
||||
{
|
||||
delete this;
|
||||
}
|
||||
}; /* class CvBlobTrackGenYML */
|
||||
|
||||
|
||||
CvBlobTrackGen* cvCreateModuleBlobTrackGenYML()
|
||||
{
|
||||
return (CvBlobTrackGen*) new CvBlobTrackGenYML;
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,456 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
/*
|
||||
This file contain simple implementation of BlobTrackerAuto virtual interface
|
||||
This module just connected other low level 3 modules
|
||||
(foreground estimator + BlobDetector + BlobTracker)
|
||||
and some simple code to detect "lost tracking"
|
||||
The track is lost when integral of foreground mask image by blob area has low value
|
||||
*/
|
||||
#include "_cvaux.h"
|
||||
#include <time.h>
|
||||
|
||||
/* list of Blob Detection modules */
|
||||
CvBlobDetector* cvCreateBlobDetectorSimple();
|
||||
|
||||
/* get frequency for each module time working estimation */
|
||||
static double FREQ = 1000*cvGetTickFrequency();
|
||||
|
||||
#if 1
|
||||
#define COUNTNUM 100
|
||||
#define TIME_BEGIN() \
|
||||
{\
|
||||
static double _TimeSum = 0;\
|
||||
static int _Count = 0;\
|
||||
static int _CountBlob = 0;\
|
||||
int64 _TickCount = cvGetTickCount();\
|
||||
|
||||
#define TIME_END(_name_,_BlobNum_) \
|
||||
_Count++;\
|
||||
_CountBlob+=_BlobNum_;\
|
||||
_TimeSum += (cvGetTickCount()-_TickCount)/FREQ;\
|
||||
if(m_TimesFile)if(_Count%COUNTNUM==0)\
|
||||
{ \
|
||||
FILE* out = fopen(m_TimesFile,"at");\
|
||||
if(out)\
|
||||
{\
|
||||
fprintf(out,"ForFrame Frame: %d %s %f on %f blobs\n",_Count,_name_, _TimeSum/COUNTNUM,((float)_CountBlob)/COUNTNUM);\
|
||||
if(_CountBlob>0)fprintf(out,"ForBlob Frame: %d %s - %f\n",_Count,_name_, _TimeSum/_CountBlob);\
|
||||
fclose(out);\
|
||||
}\
|
||||
_TimeSum = 0;\
|
||||
_CountBlob = 0;\
|
||||
}\
|
||||
}
|
||||
#else
|
||||
#define TIME_BEGIN()
|
||||
#define TIME_END(_name_)
|
||||
#endif
|
||||
|
||||
/* special extended blob structure for auto blob tracking */
|
||||
typedef struct CvBlobTrackAuto
|
||||
{
|
||||
CvBlob blob;
|
||||
int BadFrames;
|
||||
}CvBlobTrackAuto;
|
||||
|
||||
class CvBlobTrackerAuto1: public CvBlobTrackerAuto
|
||||
{
|
||||
public:
|
||||
CvBlobTrackerAuto1(CvBlobTrackerAutoParam1* param);
|
||||
~CvBlobTrackerAuto1();
|
||||
CvBlob* GetBlob(int index){return m_BlobList.GetBlob(index);};
|
||||
CvBlob* GetBlobByID(int ID){return m_BlobList.GetBlobByID(ID);};
|
||||
int GetBlobNum(){return m_BlobList.GetBlobNum();};
|
||||
virtual IplImage* GetFGMask(){return m_pFGMask;};
|
||||
float GetState(int BlobID){return m_pBTA?m_pBTA->GetState(BlobID):0;};
|
||||
char* GetStateDesc(int BlobID){return m_pBTA?m_pBTA->GetStateDesc(BlobID):NULL;};
|
||||
/* return 0 if trajectory is normal
|
||||
return >0 if trajectory abnormal */
|
||||
void Process(IplImage* pImg, IplImage* pMask = NULL);
|
||||
void Release(){delete this;};
|
||||
private:
|
||||
IplImage* m_pFGMask;
|
||||
int m_FGTrainFrames;
|
||||
CvFGDetector* m_pFG; /* pointer to foreground mask detector modelu */
|
||||
CvBlobTracker* m_pBT; /* pointer to Blob tracker module */
|
||||
int m_BTDel;
|
||||
int m_BTReal;
|
||||
CvBlobDetector* m_pBD; /* pointer to Blob detector module */
|
||||
int m_BDDel;
|
||||
CvBlobTrackGen* m_pBTGen;
|
||||
CvBlobTrackPostProc* m_pBTPostProc;
|
||||
int m_UsePPData;
|
||||
CvBlobTrackAnalysis* m_pBTA; /* blob trajectory analyser */
|
||||
CvBlobSeq m_BlobList;
|
||||
int m_FrameCount;
|
||||
int m_NextBlobID;
|
||||
char* m_TimesFile;
|
||||
public:
|
||||
virtual void SaveState(CvFileStorage* fs)
|
||||
{
|
||||
cvWriteInt(fs,"FrameCount",m_FrameCount);
|
||||
cvWriteInt(fs,"NextBlobID",m_NextBlobID);
|
||||
m_BlobList.Write(fs,"BlobList");
|
||||
};
|
||||
virtual void LoadState(CvFileStorage* fs, CvFileNode* node)
|
||||
{
|
||||
CvFileNode* BlobListNode = cvGetFileNodeByName(fs,node,"BlobList");
|
||||
m_FrameCount = cvReadIntByName(fs,node, "FrameCount", m_FrameCount);
|
||||
m_NextBlobID = cvReadIntByName(fs,node, "NextBlobID", m_NextBlobID);
|
||||
if(BlobListNode)
|
||||
{
|
||||
m_BlobList.Load(fs,BlobListNode);
|
||||
}
|
||||
};
|
||||
};
|
||||
|
||||
/* Auto Blob tracker creater (sole interface function for this file) */
|
||||
CvBlobTrackerAuto* cvCreateBlobTrackerAuto1(CvBlobTrackerAutoParam1* param)
|
||||
{
|
||||
return (CvBlobTrackerAuto*)new CvBlobTrackerAuto1(param);
|
||||
}
|
||||
|
||||
/* Constructor of auto blob tracker*/
|
||||
CvBlobTrackerAuto1::CvBlobTrackerAuto1(CvBlobTrackerAutoParam1* param):m_BlobList(sizeof(CvBlobTrackAuto))
|
||||
{
|
||||
m_BlobList.AddFormat("i");
|
||||
m_TimesFile = NULL;
|
||||
AddParam("TimesFile",&m_TimesFile);
|
||||
|
||||
m_NextBlobID = 0;
|
||||
m_pFGMask = NULL;
|
||||
m_FrameCount = 0;
|
||||
|
||||
m_FGTrainFrames = param?param->FGTrainFrames:0;
|
||||
m_pFG = param?param->pFG:0;
|
||||
|
||||
m_BDDel = 0;
|
||||
m_pBD = param?param->pBD:NULL;
|
||||
m_BTDel = 0;
|
||||
m_pBT = param?param->pBT:NULL;;
|
||||
m_BTReal = m_pBT?m_pBT->IsModuleName("BlobTrackerReal"):0;
|
||||
|
||||
m_pBTGen = param?param->pBTGen:NULL;
|
||||
|
||||
m_pBTA = param?param->pBTA:NULL;
|
||||
|
||||
m_pBTPostProc = param?param->pBTPP:NULL;
|
||||
m_UsePPData = param?param->UsePPData:0;
|
||||
|
||||
/* create default sub modules */
|
||||
if(m_pBD==NULL)
|
||||
{
|
||||
m_pBD = cvCreateBlobDetectorSimple();
|
||||
m_BDDel = 1;
|
||||
}
|
||||
if(m_pBT==NULL)
|
||||
{
|
||||
m_pBT = cvCreateBlobTrackerMS();
|
||||
m_BTDel = 1;
|
||||
}
|
||||
|
||||
}/* CvBlobTrackerAuto1::CvBlobTrackerAuto1 */
|
||||
|
||||
/* Destructor of auto blob tracker */
|
||||
CvBlobTrackerAuto1::~CvBlobTrackerAuto1()
|
||||
{
|
||||
if(m_BDDel)m_pBD->Release();
|
||||
if(m_BTDel)m_pBT->Release();
|
||||
}/* Destructor of auto blob tracker */
|
||||
|
||||
void CvBlobTrackerAuto1::Process(IplImage* pImg, IplImage* pMask)
|
||||
{
|
||||
int CurBlobNum = 0;
|
||||
int i;
|
||||
IplImage* pFG = pMask;
|
||||
|
||||
/* increase frame counter */
|
||||
m_FrameCount++;
|
||||
|
||||
if(m_TimesFile)
|
||||
{
|
||||
static int64 TickCount = cvGetTickCount();
|
||||
static double TimeSum = 0;
|
||||
static int Count = 0;
|
||||
Count++;
|
||||
if(Count%100==0)
|
||||
{
|
||||
time_t ltime;
|
||||
time( <ime );
|
||||
FILE* out = fopen(m_TimesFile,"at");
|
||||
double Time;
|
||||
TickCount = cvGetTickCount()-TickCount;
|
||||
Time = TickCount/FREQ;
|
||||
if(out){fprintf(out,"- %sFrame: %d ALL_TIME - %f\n",ctime( <ime ),Count,Time/1000);fclose(out);}
|
||||
|
||||
TimeSum = 0;
|
||||
TickCount = cvGetTickCount();
|
||||
}
|
||||
}
|
||||
|
||||
/* update BG model */
|
||||
TIME_BEGIN()
|
||||
if(m_pFG)
|
||||
{/* if FG detector is needed */
|
||||
m_pFG->Process(pImg);
|
||||
pFG = m_pFG->GetMask();
|
||||
}/* if FG detector is needed */
|
||||
TIME_END("FGDetector",-1)
|
||||
m_pFGMask = pFG; /* for external use */
|
||||
|
||||
/*if(m_pFG && m_pFG->GetParam("DebugWnd") == 1)
|
||||
{// debug foreground result
|
||||
IplImage *pFG = m_pFG->GetMask();
|
||||
if(pFG)
|
||||
{
|
||||
cvNamedWindow("FG",0);
|
||||
cvShowImage("FG", pFG);
|
||||
}
|
||||
}*/
|
||||
|
||||
/* track blobs */
|
||||
TIME_BEGIN()
|
||||
if(m_pBT)
|
||||
{
|
||||
int i;
|
||||
m_pBT->Process(pImg, pFG);
|
||||
for(i=m_BlobList.GetBlobNum();i>0;--i)
|
||||
{/* update data of tracked blob list */
|
||||
CvBlob* pB = m_BlobList.GetBlob(i-1);
|
||||
int BlobID = CV_BLOB_ID(pB);
|
||||
int i = m_pBT->GetBlobIndexByID(BlobID);
|
||||
m_pBT->ProcessBlob(i, pB, pImg, pFG);
|
||||
pB->ID = BlobID;
|
||||
}
|
||||
CurBlobNum = m_pBT->GetBlobNum();
|
||||
}
|
||||
TIME_END("BlobTracker",CurBlobNum)
|
||||
|
||||
/* this part should be removed */
|
||||
if(m_BTReal && m_pBT)
|
||||
{/* update blob list (detect new blob for real blob tracker )*/
|
||||
int i;
|
||||
for(i=m_pBT->GetBlobNum();i>0;--i)
|
||||
{/* update data of tracked blob list */
|
||||
CvBlob* pB = m_pBT->GetBlob(i-1);
|
||||
if(pB && m_BlobList.GetBlobByID(CV_BLOB_ID(pB)) == NULL )
|
||||
{
|
||||
CvBlobTrackAuto NewB;
|
||||
NewB.blob = pB[0];
|
||||
NewB.BadFrames = 0;
|
||||
m_BlobList.AddBlob((CvBlob*)&NewB);
|
||||
}
|
||||
}/* next blob */
|
||||
/*delete blobs */
|
||||
for(i=m_BlobList.GetBlobNum();i>0;--i)
|
||||
{/* update data of tracked blob list */
|
||||
CvBlob* pB = m_BlobList.GetBlob(i-1);
|
||||
if(pB && m_pBT->GetBlobByID(CV_BLOB_ID(pB)) == NULL )
|
||||
{
|
||||
m_BlobList.DelBlob(i-1);
|
||||
}
|
||||
}/* next blob */
|
||||
}/* update blob list */
|
||||
|
||||
|
||||
TIME_BEGIN()
|
||||
if(m_pBTPostProc)
|
||||
{/* post processing module */
|
||||
int i;
|
||||
for(i=m_BlobList.GetBlobNum();i>0;--i)
|
||||
{/* update data of tracked blob list */
|
||||
CvBlob* pB = m_BlobList.GetBlob(i-1);
|
||||
m_pBTPostProc->AddBlob(pB);
|
||||
}
|
||||
m_pBTPostProc->Process();
|
||||
|
||||
for(i=m_BlobList.GetBlobNum();i>0;--i)
|
||||
{/* update data of tracked blob list */
|
||||
CvBlob* pB = m_BlobList.GetBlob(i-1);
|
||||
int BlobID = CV_BLOB_ID(pB);
|
||||
CvBlob* pBN = m_pBTPostProc->GetBlobByID(BlobID);
|
||||
|
||||
if(pBN && m_UsePPData && pBN->w >= CV_BLOB_MINW && pBN->h >= CV_BLOB_MINH)
|
||||
{ /* set new data for tracker */
|
||||
m_pBT->SetBlobByID(BlobID, pBN );
|
||||
}
|
||||
|
||||
if(pBN)
|
||||
{/* update blob list by result from postprocessing */
|
||||
pB[0] = pBN[0];
|
||||
}
|
||||
}
|
||||
}/* post processing module */
|
||||
TIME_END("PostProcessing",CurBlobNum)
|
||||
|
||||
/* Blob deleter (experimental and simple)*/
|
||||
TIME_BEGIN()
|
||||
if(pFG)
|
||||
{/* Blob deleter */
|
||||
int i;
|
||||
if(!m_BTReal)for(i=m_BlobList.GetBlobNum();i>0;--i)
|
||||
{/* check all blobs from list */
|
||||
CvBlobTrackAuto* pB = (CvBlobTrackAuto*)(m_BlobList.GetBlob(i-1));
|
||||
int Good = 0;
|
||||
int w=pFG->width;
|
||||
int h=pFG->height;
|
||||
CvRect r = CV_BLOB_RECT(pB);
|
||||
CvMat mat;
|
||||
double aver = 0;
|
||||
double area = CV_BLOB_WX(pB)*CV_BLOB_WY(pB);
|
||||
if(r.x < 0){r.width += r.x;r.x = 0;}
|
||||
if(r.y < 0){r.height += r.y;r.y = 0;}
|
||||
if(r.x+r.width>=w){r.width = w-r.x-1;}
|
||||
if(r.y+r.height>=h){r.height = h-r.y-1;}
|
||||
|
||||
if(r.width > 4 && r.height > 4 && r.x < w && r.y < h &&
|
||||
r.x >=0 && r.y >=0 &&
|
||||
r.x+r.width < w && r.y+r.height < h && area > 0)
|
||||
{
|
||||
aver = cvSum(cvGetSubRect(pFG,&mat,r)).val[0] / area;
|
||||
/* if mask in blob area exists then its blob OK*/
|
||||
if(aver > 0.1*255)Good = 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
pB->BadFrames+=2;
|
||||
}
|
||||
|
||||
if(Good)
|
||||
{
|
||||
pB->BadFrames = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
pB->BadFrames++;
|
||||
}
|
||||
}/* next blob */
|
||||
|
||||
/* check error count */
|
||||
for(i=0;i<m_BlobList.GetBlobNum();++i)
|
||||
{
|
||||
CvBlobTrackAuto* pB = (CvBlobTrackAuto*)m_BlobList.GetBlob(i);
|
||||
if(pB->BadFrames>3)
|
||||
{/* delete such object */
|
||||
/* from tracker */
|
||||
m_pBT->DelBlobByID(CV_BLOB_ID(pB));
|
||||
/* from local list */
|
||||
m_BlobList.DelBlob(i);
|
||||
i--;
|
||||
}
|
||||
}/* check error count for next blob */
|
||||
}/* Blob deleter */
|
||||
TIME_END("BlobDeleter",m_BlobList.GetBlobNum())
|
||||
|
||||
/* Update blobs */
|
||||
TIME_BEGIN()
|
||||
if(m_pBT)
|
||||
m_pBT->Update(pImg, pFG);
|
||||
TIME_END("BlobTrackerUpdate",CurBlobNum)
|
||||
|
||||
/* detect new blob */
|
||||
TIME_BEGIN()
|
||||
if(!m_BTReal && m_pBD && pFG && (m_FrameCount > m_FGTrainFrames) )
|
||||
{/* detect new blob */
|
||||
static CvBlobSeq NewBlobList;
|
||||
CvBlobTrackAuto NewB;
|
||||
|
||||
NewBlobList.Clear();
|
||||
|
||||
if(m_pBD->DetectNewBlob(pImg, pFG, &NewBlobList, &m_BlobList))
|
||||
{/* add new blob to tracker and blob list */
|
||||
int i;
|
||||
IplImage* pMask = pFG;
|
||||
|
||||
/*if(0)if(NewBlobList.GetBlobNum()>0 && pFG )
|
||||
{// erode FG mask (only for FG_0 and MS1||MS2)
|
||||
pMask = cvCloneImage(pFG);
|
||||
cvErode(pFG,pMask,NULL,2);
|
||||
}*/
|
||||
|
||||
for(i=0;i<NewBlobList.GetBlobNum();++i)
|
||||
{
|
||||
CvBlob* pBN = NewBlobList.GetBlob(i);
|
||||
pBN->ID = m_NextBlobID;
|
||||
if(pBN && pBN->w >= CV_BLOB_MINW && pBN->h >= CV_BLOB_MINH)
|
||||
{
|
||||
CvBlob* pB = m_pBT->AddBlob(pBN, pImg, pMask );
|
||||
if(pB)
|
||||
{
|
||||
NewB.blob = pB[0];
|
||||
NewB.BadFrames = 0;
|
||||
m_BlobList.AddBlob((CvBlob*)&NewB);
|
||||
m_NextBlobID++;
|
||||
}
|
||||
}
|
||||
}/* add next blob from list of detected blob */
|
||||
|
||||
if(pMask != pFG) cvReleaseImage(&pMask);
|
||||
|
||||
}/* create and add new blobs and trackers */
|
||||
}/* detect new blob */
|
||||
TIME_END("BlobDetector",-1)
|
||||
|
||||
TIME_BEGIN()
|
||||
if(m_pBTGen)
|
||||
{/* run tracj generator */
|
||||
for(i=m_BlobList.GetBlobNum();i>0;--i)
|
||||
{/* update data of tracked blob list */
|
||||
CvBlob* pB = m_BlobList.GetBlob(i-1);
|
||||
m_pBTGen->AddBlob(pB);
|
||||
}
|
||||
m_pBTGen->Process(pImg, pFG);
|
||||
}/* run tracj generator */
|
||||
TIME_END("TrajectoryGeneration",-1)
|
||||
|
||||
TIME_BEGIN()
|
||||
if(m_pBTA)
|
||||
{/* trajectory analysis module */
|
||||
int i;
|
||||
for(i=m_BlobList.GetBlobNum();i>0;i--)
|
||||
m_pBTA->AddBlob(m_BlobList.GetBlob(i-1));
|
||||
m_pBTA->Process(pImg, pFG);
|
||||
}/* trajectory analysis module */
|
||||
TIME_END("TrackAnalysis",m_BlobList.GetBlobNum())
|
||||
|
||||
}/* CvBlobTrackerAuto1::Process */
|
||||
|
||||
@@ -0,0 +1,529 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
static float CalcAverageMask(CvBlob* pBlob, IplImage* pImgFG )
|
||||
{/* calc summ of mask */
|
||||
double Area, Aver = 0;
|
||||
CvRect r;
|
||||
CvMat mat;
|
||||
|
||||
if(pImgFG==NULL) return 0;
|
||||
|
||||
r.x = cvRound(pBlob->x - pBlob->w*0.5);
|
||||
r.y = cvRound(pBlob->y - pBlob->h*0.5);
|
||||
r.width = cvRound(pBlob->w);
|
||||
r.height = cvRound(pBlob->h);
|
||||
Area = r.width*r.height;
|
||||
if(r.x<0){r.width += r.x;r.x = 0;}
|
||||
if(r.y<0){r.height += r.y;r.y = 0;}
|
||||
if((r.x+r.width)>=pImgFG->width){r.width=pImgFG->width-r.x-1;}
|
||||
if((r.y+r.height)>=pImgFG->height){r.height=pImgFG->height-r.y-1;}
|
||||
if(r.width>0 && r.height>0)
|
||||
{
|
||||
double Sum = cvSum(cvGetSubRect(pImgFG,&mat,r)).val[0]/255.0;
|
||||
assert(Area>0);
|
||||
Aver = Sum/Area;
|
||||
}
|
||||
return (float)Aver;
|
||||
}/* calc summ of mask */
|
||||
|
||||
|
||||
/*============== BLOB TRACKERCC CLASS DECLARATION =============== */
|
||||
typedef struct DefBlobTracker
|
||||
{
|
||||
CvBlob blob;
|
||||
CvBlobTrackPredictor* pPredictor;
|
||||
CvBlob BlobPredict;
|
||||
int Collision;
|
||||
CvBlobSeq* pBlobHyp;
|
||||
float AverFG;
|
||||
}DefBlobTracker;
|
||||
void cvFindBlobsByCCClasters(IplImage* pFG, CvBlobSeq* pBlobs, CvMemStorage* storage);
|
||||
|
||||
class CvBlobTrackerCC : public CvBlobTracker
|
||||
{
|
||||
private:
|
||||
float m_AlphaSize;
|
||||
float m_AlphaPos;
|
||||
float m_Alpha;
|
||||
int m_Collision;
|
||||
int m_ConfidenceType;
|
||||
char* m_ConfidenceTypeStr;
|
||||
CvBlobSeq m_BlobList;
|
||||
CvBlobSeq m_BlobListNew;
|
||||
// int m_LastID;
|
||||
CvMemStorage* m_pMem;
|
||||
int m_ClearHyp;
|
||||
IplImage* m_pImg;
|
||||
IplImage* m_pImgFG;
|
||||
public:
|
||||
CvBlobTrackerCC():m_BlobList(sizeof(DefBlobTracker))
|
||||
{
|
||||
// m_LastID = 0;
|
||||
m_ClearHyp = 0;
|
||||
m_pMem = cvCreateMemStorage();
|
||||
m_Collision = 1; /* if 1 then collistion will be detected and processed */
|
||||
AddParam("Collision",&m_Collision);
|
||||
CommentParam("Collision", "if 1 then collision cases are processed in special way");
|
||||
|
||||
m_AlphaSize = 0.02f;
|
||||
AddParam("AlphaSize",&m_AlphaSize);
|
||||
CommentParam("AlphaSize", "Size update speed (0..1)");
|
||||
|
||||
m_AlphaPos = 1.0f;
|
||||
AddParam("AlphaPos",&m_AlphaPos);
|
||||
CommentParam("AlphaPos", "Pos update speed (0..1)");
|
||||
|
||||
m_Alpha = 0.001f;
|
||||
AddParam("Alpha", &m_Alpha);
|
||||
CommentParam("Alpha","Coefficient for model histogramm updating (0 - hist is not upated)");
|
||||
|
||||
m_ConfidenceType=0;
|
||||
m_ConfidenceTypeStr = "NearestBlob";
|
||||
AddParam("ConfidenceType", &m_ConfidenceTypeStr);
|
||||
CommentParam("ConfidenceType","Type of calculated Confidence (NearestBlob, AverFG, BC)");
|
||||
|
||||
SetModuleName("CC");
|
||||
};
|
||||
~CvBlobTrackerCC()
|
||||
{
|
||||
if(m_pMem)cvReleaseMemStorage(&m_pMem);
|
||||
};
|
||||
|
||||
/* blob functions*/
|
||||
virtual int GetBlobNum() {return m_BlobList.GetBlobNum();};
|
||||
virtual CvBlob* GetBlob(int BlobIndex){return m_BlobList.GetBlob(BlobIndex);};
|
||||
virtual void SetBlob(int BlobIndex, CvBlob* pBlob)
|
||||
{
|
||||
CvBlob* pB = m_BlobList.GetBlob(BlobIndex);
|
||||
if(pB) pB[0] = pBlob[0];
|
||||
};
|
||||
virtual CvBlob* GetBlobByID(int BlobID){return m_BlobList.GetBlobByID(BlobID);};
|
||||
virtual void DelBlob(int BlobIndex)
|
||||
{
|
||||
DefBlobTracker* pBT = (DefBlobTracker*)m_BlobList.GetBlob(BlobIndex);
|
||||
if(pBT==NULL) return;
|
||||
if(pBT->pPredictor)
|
||||
{
|
||||
pBT->pPredictor->Release();
|
||||
}
|
||||
else
|
||||
{
|
||||
printf("WARNING!!! Invalid Predictor in CC tracker");
|
||||
}
|
||||
delete pBT->pBlobHyp;
|
||||
m_BlobList.DelBlob(BlobIndex);
|
||||
};
|
||||
#if 0
|
||||
virtual void DelBlobByID(int BlobID)
|
||||
{
|
||||
DefBlobTracker* pBT = (DefBlobTracker*)m_BlobList.GetBlobByID(BlobID);
|
||||
pBT->pPredictor->Release();
|
||||
delete pBT->pBlobHyp;
|
||||
m_BlobList.DelBlobByID(BlobID);
|
||||
};
|
||||
#endif
|
||||
virtual void Release(){delete this;};
|
||||
|
||||
/* Add new blob to track it and assign to this blob personal ID */
|
||||
/* pBlob - pinter to structure with blob parameters (ID is ignored)*/
|
||||
/* pImg - current image */
|
||||
/* pImgFG - current foreground mask */
|
||||
/* return pointer to new added blob */
|
||||
virtual CvBlob* AddBlob(CvBlob* pB, IplImage* /*pImg*/, IplImage* pImgFG = NULL )
|
||||
{
|
||||
assert(pImgFG); /* this tracker use only foreground mask */
|
||||
DefBlobTracker NewB;
|
||||
NewB.blob = pB[0];
|
||||
// CV_BLOB_ID(&NewB) = m_LastID;
|
||||
NewB.pBlobHyp = new CvBlobSeq;
|
||||
NewB.pPredictor = cvCreateModuleBlobTrackPredictKalman(); /* module for predict position */
|
||||
NewB.pPredictor->Update(pB);
|
||||
NewB.AverFG = pImgFG?CalcAverageMask(pB,pImgFG):0;
|
||||
m_BlobList.AddBlob((CvBlob*)&NewB);
|
||||
return m_BlobList.GetBlob(m_BlobList.GetBlobNum()-1);
|
||||
};
|
||||
virtual void Process(IplImage* pImg, IplImage* pImgFG = NULL)
|
||||
{
|
||||
CvSeq* cnts;
|
||||
CvSeq* cnt;
|
||||
int i;
|
||||
|
||||
m_pImg = pImg;
|
||||
m_pImgFG = pImgFG;
|
||||
|
||||
if(m_BlobList.GetBlobNum() <= 0 ) return;
|
||||
|
||||
/* clear blob list for new blobs */
|
||||
m_BlobListNew.Clear();
|
||||
|
||||
assert(m_pMem);
|
||||
cvClearMemStorage(m_pMem);
|
||||
assert(pImgFG);
|
||||
|
||||
|
||||
/* find CC */
|
||||
#if 0
|
||||
{// by contur clastring
|
||||
cvFindBlobsByCCClasters(pImgFG, &m_BlobListNew, m_pMem);
|
||||
}
|
||||
#else
|
||||
{/* one contour - one blob */
|
||||
IplImage* pBin = cvCloneImage(pImgFG);
|
||||
assert(pBin);
|
||||
cvThreshold(pBin,pBin,128,255,CV_THRESH_BINARY);
|
||||
cvFindContours(pBin, m_pMem, &cnts, sizeof(CvContour), CV_RETR_EXTERNAL);
|
||||
/* process each contours*/
|
||||
for(cnt = cnts;cnt;cnt=cnt->h_next)
|
||||
{
|
||||
CvBlob NewBlob;
|
||||
/* image moments */
|
||||
double M00,X,Y,XX,YY;
|
||||
CvMoments m;
|
||||
CvRect r = ((CvContour*)cnt)->rect;
|
||||
CvMat mat;
|
||||
if(r.height < 3 || r.width < 3) continue;
|
||||
cvMoments( cvGetSubRect(pImgFG,&mat,r), &m, 0 );
|
||||
M00 = cvGetSpatialMoment( &m, 0, 0 );
|
||||
if(M00 <= 0 ) continue;
|
||||
X = cvGetSpatialMoment( &m, 1, 0 )/M00;
|
||||
Y = cvGetSpatialMoment( &m, 0, 1 )/M00;
|
||||
XX = (cvGetSpatialMoment( &m, 2, 0 )/M00) - X*X;
|
||||
YY = (cvGetSpatialMoment( &m, 0, 2 )/M00) - Y*Y;
|
||||
NewBlob = cvBlob(r.x+(float)X,r.y+(float)Y,(float)(4*sqrt(XX)),(float)(4*sqrt(YY)));
|
||||
m_BlobListNew.AddBlob(&NewBlob);
|
||||
}/* next contour */
|
||||
cvReleaseImage(&pBin);
|
||||
}
|
||||
#endif
|
||||
for(i=m_BlobList.GetBlobNum();i>0;--i)
|
||||
{/* predict new blob position */
|
||||
CvBlob* pB=NULL;
|
||||
DefBlobTracker* pBT = (DefBlobTracker*)m_BlobList.GetBlob(i-1);
|
||||
|
||||
/* update predictor by previouse value of blob*/
|
||||
pBT->pPredictor->Update(&(pBT->blob));
|
||||
|
||||
/* predict current position */
|
||||
pB = pBT->pPredictor->Predict();
|
||||
|
||||
if(pB)
|
||||
{
|
||||
pBT->BlobPredict = pB[0];
|
||||
}
|
||||
else
|
||||
{
|
||||
pBT->BlobPredict = pBT->blob;
|
||||
}
|
||||
}/* predict new blob position */
|
||||
|
||||
if(m_Collision)
|
||||
for(i=m_BlobList.GetBlobNum();i>0;--i)
|
||||
{/* predict collision */
|
||||
int Collision = 0;
|
||||
int j;
|
||||
DefBlobTracker* pF = (DefBlobTracker*)m_BlobList.GetBlob(i-1);
|
||||
for(j=m_BlobList.GetBlobNum();j>0;--j)
|
||||
{/* predict collision */
|
||||
CvBlob* pB1;
|
||||
CvBlob* pB2;
|
||||
DefBlobTracker* pF2 = (DefBlobTracker*)m_BlobList.GetBlob(j-1);
|
||||
if(i==j) continue;
|
||||
pB1 = &pF->BlobPredict;
|
||||
pB2 = &pF2->BlobPredict;
|
||||
if( fabs(pB1->x-pB2->x)<0.6*(pB1->w+pB2->w) &&
|
||||
fabs(pB1->y-pB2->y)<0.6*(pB1->h+pB2->h) ) Collision = 1;
|
||||
pB1 = &pF->blob;
|
||||
pB2 = &pF2->blob;
|
||||
if( fabs(pB1->x-pB2->x)<0.6*(pB1->w+pB2->w) &&
|
||||
fabs(pB1->y-pB2->y)<0.6*(pB1->h+pB2->h) ) Collision = 1;
|
||||
if(Collision) break;
|
||||
}/* check next blob to cross current*/
|
||||
pF->Collision = Collision;
|
||||
}/* predict collision */
|
||||
|
||||
for(i=m_BlobList.GetBlobNum();i>0;--i)
|
||||
{/* find a neighbour on cur frame for each blob from prev frame */
|
||||
CvBlob* pB = m_BlobList.GetBlob(i-1);
|
||||
DefBlobTracker* pBT = (DefBlobTracker*)pB;
|
||||
//int BlobID = CV_BLOB_ID(pB);
|
||||
//CvBlob* pBBest = NULL;
|
||||
//double DistBest = -1;
|
||||
//int j;
|
||||
|
||||
if(pBT->pBlobHyp->GetBlobNum()>0)
|
||||
{/* track all hypothesis */
|
||||
int h,hN = pBT->pBlobHyp->GetBlobNum();
|
||||
for(h=0;h<hN;++h)
|
||||
{
|
||||
int j, jN = m_BlobListNew.GetBlobNum();
|
||||
CvBlob* pB = pBT->pBlobHyp->GetBlob(h);
|
||||
int BlobID = CV_BLOB_ID(pB);
|
||||
CvBlob* pBBest = NULL;
|
||||
double DistBest = -1;
|
||||
for(j=0;j<jN;j++)
|
||||
{/* find best CC */
|
||||
double Dist = -1;
|
||||
CvBlob* pBNew = m_BlobListNew.GetBlob(j);
|
||||
double dx = fabs(CV_BLOB_X(pB)-CV_BLOB_X(pBNew));
|
||||
double dy = fabs(CV_BLOB_Y(pB)-CV_BLOB_Y(pBNew));
|
||||
if(dx > 2*CV_BLOB_WX(pB) || dy > 2*CV_BLOB_WY(pB)) continue;
|
||||
|
||||
Dist = sqrt(dx*dx+dy*dy);
|
||||
if(Dist < DistBest || pBBest == NULL)
|
||||
{
|
||||
DistBest = Dist;
|
||||
pBBest = pBNew;
|
||||
}
|
||||
}/* find best CC */
|
||||
if(pBBest)
|
||||
{
|
||||
pB[0] = pBBest[0];
|
||||
CV_BLOB_ID(pB) = BlobID;
|
||||
}
|
||||
else
|
||||
{ /* delete this hypothesis */
|
||||
pBT->pBlobHyp->DelBlob(h);
|
||||
h--;
|
||||
hN--;
|
||||
}
|
||||
}/* next hyp*/
|
||||
}/* track all hypothesis */
|
||||
}/* track next blob */
|
||||
|
||||
m_ClearHyp = 1;
|
||||
|
||||
}/* Process */
|
||||
|
||||
virtual void ProcessBlob(int BlobIndex, CvBlob* pBlob, IplImage* /*pImg*/, IplImage* /*pImgFG*/ = NULL)
|
||||
{
|
||||
int ID = pBlob->ID;
|
||||
CvBlob* pB = m_BlobList.GetBlob(BlobIndex);
|
||||
DefBlobTracker* pBT = (DefBlobTracker*)pB;
|
||||
//CvBlob* pBBest = NULL;
|
||||
//double DistBest = -1;
|
||||
int BlobID;
|
||||
|
||||
if(pB==NULL) return;
|
||||
|
||||
BlobID = pB->ID;
|
||||
|
||||
if(m_Collision && pBT->Collision)
|
||||
{/* tracking in collision */
|
||||
pB[0]=pBT->BlobPredict;
|
||||
CV_BLOB_ID(pB)=BlobID;
|
||||
}/* tracking in collision */
|
||||
else
|
||||
{/* not collision tracking */
|
||||
CvBlob* pBBest = GetNearestBlob(pB);
|
||||
if(pBBest)
|
||||
{
|
||||
float w = pBlob->w*(1-m_AlphaSize)+m_AlphaSize*pBBest->w;
|
||||
float h = pBlob->h*(1-m_AlphaSize)+m_AlphaSize*pBBest->h;
|
||||
float x = pBlob->x*(1-m_AlphaPos)+m_AlphaPos*pBBest->x;
|
||||
float y = pBlob->y*(1-m_AlphaPos)+m_AlphaPos*pBBest->y;
|
||||
pB->w = w;
|
||||
pB->h = h;
|
||||
pB->x = x;
|
||||
pB->y = y;
|
||||
CV_BLOB_ID(pB) = BlobID;
|
||||
}
|
||||
}/* not collision tracking */
|
||||
|
||||
pBlob[0] = pB[0];
|
||||
pBlob->ID = ID;
|
||||
};
|
||||
|
||||
virtual double GetConfidence(int BlobIndex, CvBlob* pBlob, IplImage* /*pImg*/, IplImage* pImgFG = NULL)
|
||||
{
|
||||
/* define koefficients in exp by exp(-XT*K)=VT */
|
||||
static double _KS = -log(0.1)/pow(0.5,2); /* XT = 1, VT = 0.1 - when size is Larger in 2 times Confidence is smoller in 10 times */
|
||||
static double _KP = -log(0.1)/pow(m_pImg->width*0.02,2); /* XT = 0.02*ImgWidth, VT = 0.1*/
|
||||
DefBlobTracker* pBT = (DefBlobTracker*)m_BlobList.GetBlob(BlobIndex);
|
||||
float dx,dy,dw,dh;
|
||||
float dp2,ds2;
|
||||
double W = 1;
|
||||
CvBlob* pBC = GetNearestBlob(pBlob);
|
||||
if(pBC == NULL ) return 0;
|
||||
|
||||
dx = pBC->x-pBlob->x;
|
||||
dy = pBC->y-pBlob->y;
|
||||
dw = (pBC->w-pBlob->w)/pBC->w;
|
||||
dh = (pBC->h-pBlob->h)/pBC->h;
|
||||
|
||||
dp2 = dx*dx+dy*dy;
|
||||
ds2 = dw*dw+dh*dh;
|
||||
|
||||
if(!pBT->Collision)
|
||||
{ /* Confidence for size by nearest blob */
|
||||
W*=exp(-_KS*ds2);
|
||||
}
|
||||
|
||||
if(m_ConfidenceType==0 && !pBT->Collision)
|
||||
{ /* confinence by nearest blob */
|
||||
W*=exp(-_KP*dp2);
|
||||
}
|
||||
|
||||
if(m_ConfidenceType==1 && pBT->AverFG>0)
|
||||
{/* calc summ of mask */
|
||||
float Aver = CalcAverageMask(pBlob, pImgFG );
|
||||
if(Aver < pBT->AverFG)
|
||||
{
|
||||
float diff = 1+0.9f*(Aver-pBT->AverFG)/pBT->AverFG;
|
||||
if(diff < 0.1f) diff = 0.1f;
|
||||
W *= diff;
|
||||
}
|
||||
}/* calc summ of mask */
|
||||
|
||||
if(m_ConfidenceType==2)
|
||||
{/* calc BCoeff */
|
||||
float S = 0.2f;
|
||||
float Aver = CalcAverageMask(pBlob, pImgFG );
|
||||
double B = sqrt(Aver*pBT->AverFG)+sqrt((1-Aver)*(1-pBT->AverFG));
|
||||
|
||||
W *= exp((B-1)/(2*S));
|
||||
}/* calc summ of mask */
|
||||
return W;
|
||||
};
|
||||
|
||||
virtual void UpdateBlob(int BlobIndex, CvBlob* /*pBlob*/, IplImage* /*pImg*/, IplImage* pImgFG = NULL)
|
||||
{
|
||||
DefBlobTracker* pBT = (DefBlobTracker*)m_BlobList.GetBlob(BlobIndex);
|
||||
|
||||
if(pImgFG==NULL || pBT==NULL) return;
|
||||
|
||||
if(!pBT->Collision)
|
||||
{
|
||||
//pBT->AverFG = pBT->AverFG * (1-m_Alpha) + m_Alpha * CalcAverageMask(pBlob,pImgFG);
|
||||
}
|
||||
};
|
||||
|
||||
virtual void ParamUpdate()
|
||||
{
|
||||
char* pCT[3] = {"NearestBlob","AverFG","BC"};
|
||||
int i;
|
||||
|
||||
CvBlobTracker::ParamUpdate();
|
||||
|
||||
for(i=0;i<3;++i)
|
||||
{
|
||||
if(cv_stricmp(m_ConfidenceTypeStr,pCT[i])==0)
|
||||
{
|
||||
m_ConfidenceType = i;
|
||||
}
|
||||
}
|
||||
SetParamStr("ConfidenceType",pCT[m_ConfidenceType]);
|
||||
}
|
||||
/* =============== MULTI HYPOTHESIS INTERFACE ================== */
|
||||
/* return number of position hyposetis of currently tracked blob */
|
||||
virtual int GetBlobHypNum(int BlobIdx)
|
||||
{
|
||||
DefBlobTracker* pBT = (DefBlobTracker*)m_BlobList.GetBlob(BlobIdx);
|
||||
assert(pBT->pBlobHyp);
|
||||
return pBT->pBlobHyp->GetBlobNum();
|
||||
};/* CvBlobtrackerList::GetBlobHypNum() */
|
||||
|
||||
/* return pointer to specified blob hypothesis by index blob */
|
||||
virtual CvBlob* GetBlobHyp(int BlobIndex, int hypothesis)
|
||||
{
|
||||
DefBlobTracker* pBT = (DefBlobTracker*)m_BlobList.GetBlob(BlobIndex);
|
||||
assert(pBT->pBlobHyp);
|
||||
return pBT->pBlobHyp->GetBlob(hypothesis);
|
||||
};/* CvBlobtrackerList::GetBlobHyp() */
|
||||
/* Set new parameters for specified (by index) blob hyp (can be called several times for each hyp )*/
|
||||
virtual void SetBlobHyp(int BlobIndex, CvBlob* pBlob)
|
||||
{
|
||||
if(m_ClearHyp)
|
||||
{/* clear all hypothesis */
|
||||
int b, bN = m_BlobList.GetBlobNum();
|
||||
for(b=0;b<bN;++b)
|
||||
{
|
||||
DefBlobTracker* pBT = (DefBlobTracker*)m_BlobList.GetBlob(b);
|
||||
assert(pBT->pBlobHyp);
|
||||
pBT->pBlobHyp->Clear();
|
||||
}
|
||||
m_ClearHyp = 0;
|
||||
}
|
||||
{/* add hypothesis */
|
||||
DefBlobTracker* pBT = (DefBlobTracker*)m_BlobList.GetBlob(BlobIndex);
|
||||
assert(pBT->pBlobHyp);
|
||||
pBT->pBlobHyp->AddBlob(pBlob);
|
||||
}
|
||||
};
|
||||
|
||||
private:
|
||||
CvBlob* GetNearestBlob(CvBlob* pB)
|
||||
{
|
||||
//DefBlobTracker* pBT = (DefBlobTracker*)pB;
|
||||
CvBlob* pBBest = NULL;
|
||||
double DistBest = -1;
|
||||
int j,BlobID;
|
||||
|
||||
if(pB==NULL) return NULL;
|
||||
|
||||
BlobID = pB->ID;
|
||||
|
||||
for(j=m_BlobListNew.GetBlobNum();j>0;--j)
|
||||
{/* find best CC */
|
||||
double Dist = -1;
|
||||
CvBlob* pBNew = m_BlobListNew.GetBlob(j-1);
|
||||
double dx = fabs(CV_BLOB_X(pB)-CV_BLOB_X(pBNew));
|
||||
double dy = fabs(CV_BLOB_Y(pB)-CV_BLOB_Y(pBNew));
|
||||
if(dx > 2*CV_BLOB_WX(pB) || dy > 2*CV_BLOB_WY(pB)) continue;
|
||||
|
||||
Dist = sqrt(dx*dx+dy*dy);
|
||||
if(Dist < DistBest || pBBest == NULL)
|
||||
{
|
||||
DistBest = Dist;
|
||||
pBBest = pBNew;
|
||||
}
|
||||
}/* find best CC */
|
||||
return pBBest;
|
||||
}; /* GetNearestBlob */
|
||||
|
||||
};
|
||||
|
||||
CvBlobTracker* cvCreateBlobTrackerCC()
|
||||
{
|
||||
return (CvBlobTracker*) new CvBlobTrackerCC;
|
||||
}
|
||||
/*============== BLOB TRACKERCC CLASS DECLARATION =============== */
|
||||
@@ -0,0 +1,451 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
/*============== BLOB TRACKERCC CLASS DECLARATION =============== */
|
||||
typedef struct DefBlobTrackerCR
|
||||
{
|
||||
CvBlob blob;
|
||||
CvBlobTrackPredictor* pPredictor;
|
||||
CvBlob BlobPredict;
|
||||
CvBlob BlobPrev;
|
||||
int Collision;
|
||||
CvBlobSeq* pBlobHyp;
|
||||
CvBlobTrackerOne* pResolver;
|
||||
}DefBlobTrackerCR;
|
||||
void cvFindBlobsByCCClasters(IplImage* pFG, CvBlobSeq* pBlobs, CvMemStorage* storage);
|
||||
class CvBlobTrackerCCCR : public CvBlobTracker
|
||||
{
|
||||
private:
|
||||
float m_AlphaSize;
|
||||
int m_Collision;
|
||||
CvBlobSeq m_BlobList;
|
||||
CvBlobSeq m_BlobListNew;
|
||||
CvMemStorage* m_pMem;
|
||||
CvBlobTrackerOne* (*m_CreateCR)();
|
||||
char m_ModuleName[1024];
|
||||
|
||||
|
||||
public:
|
||||
CvBlobTrackerCCCR(CvBlobTrackerOne* (*CreateCR)(), char* CRName):m_BlobList(sizeof(DefBlobTrackerCR))
|
||||
{
|
||||
m_CreateCR = CreateCR;
|
||||
m_pMem = cvCreateMemStorage();
|
||||
|
||||
m_Collision = 1; /* if 1 then collistion will be detected and processed */
|
||||
|
||||
m_AlphaSize = 0.05f;
|
||||
AddParam("AlphaSize",&m_AlphaSize);
|
||||
CommentParam("AlphaSize", "Size update speed (0..1)");
|
||||
|
||||
strcpy(m_ModuleName, "CC");
|
||||
if(CRName)strcat(m_ModuleName,CRName);
|
||||
SetModuleName(m_ModuleName);
|
||||
|
||||
{
|
||||
CvBlobTrackerOne* pM = m_CreateCR();
|
||||
TransferParamsFromChild(pM,NULL);
|
||||
pM->Release();
|
||||
}
|
||||
SetParam("SizeVar",0);
|
||||
};
|
||||
~CvBlobTrackerCCCR()
|
||||
{
|
||||
if(m_pMem)cvReleaseMemStorage(&m_pMem);
|
||||
};
|
||||
|
||||
/* blob functions*/
|
||||
virtual int GetBlobNum() {return m_BlobList.GetBlobNum();};
|
||||
virtual CvBlob* GetBlob(int BlobIndex){return m_BlobList.GetBlob(BlobIndex);};
|
||||
virtual void SetBlob(int BlobIndex, CvBlob* pBlob)
|
||||
{
|
||||
CvBlob* pB = m_BlobList.GetBlob(BlobIndex);
|
||||
if(pB) pB[0] = pBlob[0];
|
||||
};
|
||||
virtual CvBlob* GetBlobByID(int BlobID){return m_BlobList.GetBlobByID(BlobID);};
|
||||
virtual void DelBlob(int BlobIndex)
|
||||
{
|
||||
DefBlobTrackerCR* pBT = (DefBlobTrackerCR*)m_BlobList.GetBlob(BlobIndex);
|
||||
if(pBT->pResolver)pBT->pResolver->Release();
|
||||
if(pBT->pPredictor)pBT->pPredictor->Release();
|
||||
delete pBT->pBlobHyp;
|
||||
m_BlobList.DelBlob(BlobIndex);
|
||||
};
|
||||
virtual void DelBlobByID(int BlobID)
|
||||
{
|
||||
DefBlobTrackerCR* pBT = (DefBlobTrackerCR*)m_BlobList.GetBlobByID(BlobID);
|
||||
if(pBT->pResolver)pBT->pResolver->Release();
|
||||
if(pBT->pPredictor)pBT->pPredictor->Release();
|
||||
delete pBT->pBlobHyp;
|
||||
m_BlobList.DelBlobByID(BlobID);
|
||||
};
|
||||
virtual void Release(){delete this;};
|
||||
|
||||
/* Add new blob to track it and assign to this blob personal ID */
|
||||
/* pBlob - pinter to structure with blob parameters (ID is ignored)*/
|
||||
/* pImg - current image */
|
||||
/* pImgFG - current foreground mask */
|
||||
/* return pointer to new added blob */
|
||||
virtual CvBlob* AddBlob(CvBlob* pB, IplImage* pImg, IplImage* pImgFG = NULL )
|
||||
{
|
||||
DefBlobTrackerCR NewB;
|
||||
NewB.blob = pB[0];
|
||||
NewB.pBlobHyp = new CvBlobSeq;
|
||||
NewB.pPredictor = cvCreateModuleBlobTrackPredictKalman(); /* module for predict position */
|
||||
NewB.pPredictor->SetParam("DataNoisePos",0.001);
|
||||
NewB.pPredictor->ParamUpdate();
|
||||
NewB.pResolver = NULL;
|
||||
if(m_CreateCR)
|
||||
{
|
||||
NewB.pResolver = m_CreateCR();
|
||||
TransferParamsToChild(NewB.pResolver,NULL);
|
||||
NewB.pResolver->Init(pB, pImg, pImgFG);
|
||||
}
|
||||
m_BlobList.AddBlob((CvBlob*)&NewB);
|
||||
return m_BlobList.GetBlob(m_BlobList.GetBlobNum()-1);
|
||||
};
|
||||
virtual void Process(IplImage* pImg, IplImage* pImgFG = NULL)
|
||||
{
|
||||
CvSeq* cnts;
|
||||
CvSeq* cnt;
|
||||
int i;
|
||||
//CvMat* pMC = NULL;
|
||||
|
||||
if(m_BlobList.GetBlobNum() <= 0 ) return;
|
||||
|
||||
/* clear blob list for new blobs */
|
||||
m_BlobListNew.Clear();
|
||||
|
||||
assert(m_pMem);
|
||||
cvClearMemStorage(m_pMem);
|
||||
assert(pImgFG);
|
||||
|
||||
{/* one contour - one blob */
|
||||
IplImage* pBin = cvCloneImage(pImgFG);
|
||||
assert(pBin);
|
||||
cvThreshold(pBin,pBin,128,255,CV_THRESH_BINARY);
|
||||
cvFindContours(pBin, m_pMem, &cnts, sizeof(CvContour), CV_RETR_EXTERNAL);
|
||||
/* process each contours*/
|
||||
for(cnt = cnts;cnt;cnt=cnt->h_next)
|
||||
{
|
||||
CvBlob NewBlob;
|
||||
/* image moments */
|
||||
double M00,X,Y,XX,YY;
|
||||
CvMoments m;
|
||||
CvRect r = ((CvContour*)cnt)->rect;
|
||||
CvMat mat;
|
||||
if(r.height < 3 || r.width < 3) continue;
|
||||
cvMoments( cvGetSubRect(pImgFG,&mat,r), &m, 0 );
|
||||
M00 = cvGetSpatialMoment( &m, 0, 0 );
|
||||
if(M00 <= 0 ) continue;
|
||||
X = cvGetSpatialMoment( &m, 1, 0 )/M00;
|
||||
Y = cvGetSpatialMoment( &m, 0, 1 )/M00;
|
||||
XX = (cvGetSpatialMoment( &m, 2, 0 )/M00) - X*X;
|
||||
YY = (cvGetSpatialMoment( &m, 0, 2 )/M00) - Y*Y;
|
||||
NewBlob = cvBlob(r.x+(float)X,r.y+(float)Y,(float)(4*sqrt(XX)),(float)(4*sqrt(YY)));
|
||||
m_BlobListNew.AddBlob(&NewBlob);
|
||||
}/* next contour */
|
||||
cvReleaseImage(&pBin);
|
||||
}
|
||||
|
||||
for(i=m_BlobList.GetBlobNum();i>0;--i)
|
||||
{/* predict new blob position */
|
||||
CvBlob* pB = NULL;
|
||||
DefBlobTrackerCR* pBT = (DefBlobTrackerCR*)m_BlobList.GetBlob(i-1);
|
||||
/*update predictor */
|
||||
pBT->pPredictor->Update(&(pBT->blob));
|
||||
pB = pBT->pPredictor->Predict();
|
||||
if(pB)
|
||||
{
|
||||
pBT->BlobPredict = pB[0];
|
||||
}
|
||||
pBT->BlobPrev = pBT->blob;
|
||||
}/* predict new blob position */
|
||||
|
||||
|
||||
if(m_BlobList.GetBlobNum()>0 && m_BlobListNew.GetBlobNum()>0)
|
||||
{/* resolve new blob to old */
|
||||
int i,j;
|
||||
int NOld = m_BlobList.GetBlobNum();
|
||||
int NNew = m_BlobListNew.GetBlobNum();
|
||||
|
||||
for(i=0;i<NOld;i++)
|
||||
{/* set 0 collision and clear all hyp */
|
||||
DefBlobTrackerCR* pF = (DefBlobTrackerCR*)m_BlobList.GetBlob(i);
|
||||
pF->Collision = 0;
|
||||
pF->pBlobHyp->Clear();
|
||||
}/* set 0 collision */
|
||||
|
||||
/* create correspondance records */
|
||||
for(j=0;j<NNew;++j)
|
||||
{
|
||||
CvBlob* pB1 = m_BlobListNew.GetBlob(j);
|
||||
DefBlobTrackerCR* pFLast = NULL;
|
||||
|
||||
for(i=0;i<NOld;i++)
|
||||
{/* check intersection */
|
||||
int Intersection = 0;
|
||||
DefBlobTrackerCR* pF = (DefBlobTrackerCR*)m_BlobList.GetBlob(i);
|
||||
CvBlob* pB2 = &(pF->BlobPredict);
|
||||
if( fabs(pB1->x-pB2->x)<0.5*(pB1->w+pB2->w) &&
|
||||
fabs(pB1->y-pB2->y)<0.5*(pB1->h+pB2->h) ) Intersection = 1;
|
||||
if(Intersection)
|
||||
{
|
||||
if(pFLast)
|
||||
{
|
||||
pF->Collision = pFLast->Collision = 1;
|
||||
}
|
||||
pFLast = pF;
|
||||
pF->pBlobHyp->AddBlob(pB1);
|
||||
}
|
||||
}/* check intersection */
|
||||
}/* check next new blob */
|
||||
}/* resolve new blob to old */
|
||||
|
||||
for(i=m_BlobList.GetBlobNum();i>0;--i)
|
||||
{/* track each blob */
|
||||
CvBlob* pB = m_BlobList.GetBlob(i-1);
|
||||
DefBlobTrackerCR* pBT = (DefBlobTrackerCR*)pB;
|
||||
int BlobID = CV_BLOB_ID(pB);
|
||||
//CvBlob* pBBest = NULL;
|
||||
//double DistBest = -1;
|
||||
int j;
|
||||
|
||||
if(pBT->pResolver)
|
||||
{
|
||||
pBT->pResolver->SetCollision(pBT->Collision);
|
||||
}
|
||||
|
||||
if(pBT->Collision)
|
||||
{/* tracking in collision */
|
||||
if(pBT->pResolver)
|
||||
{
|
||||
pB[0] = pBT->pResolver->Process(&(pBT->BlobPredict),pImg, pImgFG)[0];
|
||||
}
|
||||
}/* tracking in collision */
|
||||
else
|
||||
{/* not collision tracking */
|
||||
CvBlob NewCC = pBT->BlobPredict;
|
||||
if(pBT->pBlobHyp->GetBlobNum()==1)
|
||||
{/* one blob to one CC */
|
||||
NewCC = pBT->pBlobHyp->GetBlob(0)[0];
|
||||
}
|
||||
else
|
||||
{/* one blob several CC */
|
||||
CvBlob* pBBest = NULL;
|
||||
double DistBest = -1;
|
||||
double CMax = 0;
|
||||
for(j=pBT->pBlobHyp->GetBlobNum();j>0;--j)
|
||||
{/* find best CC */
|
||||
CvBlob* pBNew = pBT->pBlobHyp->GetBlob(j-1);
|
||||
if(pBT->pResolver)
|
||||
{/* choose CC by confidence */
|
||||
// double dx = fabs(CV_BLOB_X(pB)-CV_BLOB_X(pBNew));
|
||||
// double dy = fabs(CV_BLOB_Y(pB)-CV_BLOB_Y(pBNew));
|
||||
double C = pBT->pResolver->GetConfidence(pBNew,pImg, pImgFG);
|
||||
if(C > CMax || pBBest == NULL)
|
||||
{
|
||||
CMax = C;
|
||||
pBBest = pBNew;
|
||||
}
|
||||
}
|
||||
else
|
||||
{ /* chose CC by distance */
|
||||
double dx = fabs(CV_BLOB_X(pB)-CV_BLOB_X(pBNew));
|
||||
double dy = fabs(CV_BLOB_Y(pB)-CV_BLOB_Y(pBNew));
|
||||
double Dist = sqrt(dx*dx+dy*dy);
|
||||
if(Dist < DistBest || pBBest == NULL)
|
||||
{
|
||||
DistBest = Dist;
|
||||
pBBest = pBNew;
|
||||
}
|
||||
}
|
||||
}/* find best CC */
|
||||
if(pBBest)
|
||||
NewCC = pBBest[0];
|
||||
}/* one blob several CC */
|
||||
pB->x = NewCC.x;
|
||||
pB->y = NewCC.y;
|
||||
pB->w = (m_AlphaSize)*NewCC.w+(1-m_AlphaSize)*pB->w;
|
||||
pB->h = (m_AlphaSize)*NewCC.h+(1-m_AlphaSize)*pB->h;
|
||||
pBT->pResolver->SkipProcess(&(pBT->BlobPredict),pImg, pImgFG);
|
||||
}/* not collision tracking */
|
||||
|
||||
pBT->pResolver->Update(pB, pImg, pImgFG);
|
||||
|
||||
CV_BLOB_ID(pB)=BlobID;
|
||||
|
||||
}/* track next blob */
|
||||
|
||||
if(m_Wnd)
|
||||
{
|
||||
IplImage* pI = cvCloneImage(pImg);
|
||||
int i;
|
||||
for(i=m_BlobListNew.GetBlobNum();i>0;--i)
|
||||
{/* draw each new CC */
|
||||
CvBlob* pB = m_BlobListNew.GetBlob(i-1);
|
||||
CvPoint p = cvPointFrom32f(CV_BLOB_CENTER(pB));
|
||||
int x = cvRound(CV_BLOB_RX(pB)), y = cvRound(CV_BLOB_RY(pB));
|
||||
CvSize s = cvSize(MAX(1,x), MAX(1,y));
|
||||
//int c = 255;
|
||||
cvEllipse( pI,
|
||||
p,
|
||||
s,
|
||||
0, 0, 360,
|
||||
CV_RGB(255,255,0), 1 );
|
||||
}
|
||||
|
||||
for(i=m_BlobList.GetBlobNum();i>0;--i)
|
||||
{/* draw each new CC */
|
||||
DefBlobTrackerCR* pF = (DefBlobTrackerCR*)m_BlobList.GetBlob(i-1);
|
||||
CvBlob* pB = &(pF->BlobPredict);
|
||||
CvPoint p = cvPointFrom32f(CV_BLOB_CENTER(pB));
|
||||
int x = cvRound(CV_BLOB_RX(pB)), y = cvRound(CV_BLOB_RY(pB));
|
||||
CvSize s = cvSize(MAX(1,x), MAX(1,y));
|
||||
cvEllipse( pI,
|
||||
p,
|
||||
s,
|
||||
0, 0, 360,
|
||||
CV_RGB(0,0,255), 1 );
|
||||
|
||||
pB = &(pF->blob);
|
||||
p = cvPointFrom32f(CV_BLOB_CENTER(pB));
|
||||
x = cvRound(CV_BLOB_RX(pB)); y = cvRound(CV_BLOB_RY(pB));
|
||||
s = cvSize(MAX(1,x), MAX(1,y));
|
||||
cvEllipse( pI,
|
||||
p,
|
||||
s,
|
||||
0, 0, 360,
|
||||
CV_RGB(0,255,0), 1 );
|
||||
}
|
||||
|
||||
//cvNamedWindow("CCwithCR",0);
|
||||
//cvShowImage("CCwithCR",pI);
|
||||
cvReleaseImage(&pI);
|
||||
}
|
||||
|
||||
}/* Process */
|
||||
virtual void SaveState(CvFileStorage* fs)
|
||||
{
|
||||
int b,bN = m_BlobList.GetBlobNum();
|
||||
cvWriteInt(fs,"BlobNum",m_BlobList.GetBlobNum());
|
||||
cvStartWriteStruct(fs,"BlobList",CV_NODE_SEQ);
|
||||
for(b=0;b<bN;++b)
|
||||
{
|
||||
DefBlobTrackerCR* pF = (DefBlobTrackerCR*)m_BlobList.GetBlob(b);
|
||||
cvStartWriteStruct(fs,NULL,CV_NODE_MAP);
|
||||
cvWriteInt(fs,"ID",CV_BLOB_ID(pF));
|
||||
cvStartWriteStruct(fs,"Blob",CV_NODE_SEQ|CV_NODE_FLOW);
|
||||
cvWriteRawData(fs,&(pF->blob),1,"ffffi");
|
||||
cvEndWriteStruct(fs);
|
||||
cvStartWriteStruct(fs,"BlobPredict",CV_NODE_SEQ|CV_NODE_FLOW);
|
||||
cvWriteRawData(fs,&(pF->BlobPredict),1,"ffffi");
|
||||
cvEndWriteStruct(fs);
|
||||
cvStartWriteStruct(fs,"BlobPrev",CV_NODE_SEQ|CV_NODE_FLOW);
|
||||
cvWriteRawData(fs,&(pF->BlobPrev),1,"ffffi");
|
||||
cvEndWriteStruct(fs);
|
||||
pF->pBlobHyp->Write(fs,"BlobHyp");
|
||||
cvWriteInt(fs,"Collision",pF->Collision);
|
||||
|
||||
cvStartWriteStruct(fs,"Predictor",CV_NODE_MAP);
|
||||
pF->pPredictor->SaveState(fs);
|
||||
cvEndWriteStruct(fs);
|
||||
|
||||
cvStartWriteStruct(fs,"Resolver",CV_NODE_MAP);
|
||||
pF->pResolver->SaveState(fs);
|
||||
cvEndWriteStruct(fs);
|
||||
cvEndWriteStruct(fs);
|
||||
}
|
||||
cvEndWriteStruct(fs);
|
||||
}/* SaveState*/
|
||||
|
||||
virtual void LoadState(CvFileStorage* fs, CvFileNode* node)
|
||||
{
|
||||
int b,bN = cvReadIntByName(fs,node,"BlobNum",0);
|
||||
CvFileNode* pBlobListNode = cvGetFileNodeByName(fs,node,"BlobList");
|
||||
if(!CV_NODE_IS_SEQ(pBlobListNode->tag)) return;
|
||||
bN = pBlobListNode->data.seq->total;
|
||||
for(b=0;b<bN;++b)
|
||||
{
|
||||
DefBlobTrackerCR* pF = NULL;
|
||||
CvBlob Blob;
|
||||
CvFileNode* pSeqNode = NULL;
|
||||
CvFileNode* pBlobNode = (CvFileNode*)cvGetSeqElem(pBlobListNode->data.seq,b);
|
||||
assert(pBlobNode);
|
||||
|
||||
Blob.ID = cvReadIntByName(fs,pBlobNode,"ID",0);
|
||||
|
||||
pSeqNode = cvGetFileNodeByName(fs, pBlobNode, "Blob");
|
||||
if(CV_NODE_IS_SEQ(pSeqNode->tag))
|
||||
cvReadRawData( fs, pSeqNode, &Blob, "ffffi" );
|
||||
|
||||
AddBlob(&Blob,NULL,NULL);
|
||||
pF = (DefBlobTrackerCR*)m_BlobList.GetBlobByID(Blob.ID);
|
||||
|
||||
pSeqNode = cvGetFileNodeByName(fs, pBlobNode, "BlobPredict");
|
||||
if(CV_NODE_IS_SEQ(pSeqNode->tag))
|
||||
cvReadRawData( fs, pSeqNode, &pF->BlobPredict, "ffffi" );
|
||||
pSeqNode = cvGetFileNodeByName(fs, pBlobNode, "BlobPrev");
|
||||
if(CV_NODE_IS_SEQ(pSeqNode->tag))
|
||||
cvReadRawData( fs, pSeqNode, &pF->BlobPrev, "ffffi" );
|
||||
pSeqNode = cvGetFileNodeByName(fs, pBlobNode, "BlobHyp");
|
||||
if(pSeqNode)
|
||||
pF->pBlobHyp->Load(fs,pSeqNode);
|
||||
pF->Collision = cvReadIntByName(fs, pBlobNode,"Collision",pF->Collision);
|
||||
|
||||
pSeqNode = cvGetFileNodeByName(fs, pBlobNode, "Predictor");
|
||||
if(pSeqNode)
|
||||
pF->pPredictor->LoadState(fs,pSeqNode);
|
||||
pSeqNode = cvGetFileNodeByName(fs, pBlobNode, "Resolver");
|
||||
if(pSeqNode)
|
||||
pF->pResolver->LoadState(fs,pSeqNode);
|
||||
}/* read next blob */
|
||||
}/* CCwithCR LoadState */
|
||||
|
||||
//void SetCollision(int Collision){m_Collision = Collision;};
|
||||
};
|
||||
|
||||
CvBlobTrackerOne* cvCreateBlobTrackerOneMSPF();
|
||||
CvBlobTracker* cvCreateBlobTrackerCCMSPF()
|
||||
{
|
||||
return (CvBlobTracker*) new CvBlobTrackerCCCR(cvCreateBlobTrackerOneMSPF,"MSPF");
|
||||
}
|
||||
/*============== BLOB TRACKERCC CLASS DECLARATION =============== */
|
||||
@@ -0,0 +1,163 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
/*======================= KALMAN FILTER AS TRACKER =========================*/
|
||||
/* state vector is (x,y,w,h,dx,dy,dw,dh)*/
|
||||
/* mesurment is (x,y,w,h) */
|
||||
/* dinamic matrix A */
|
||||
const float A8[] = { 1, 0, 0, 0, 1, 0, 0, 0,
|
||||
0, 1, 0, 0, 0, 1, 0, 0,
|
||||
0, 0, 1, 0, 0, 0, 1, 0,
|
||||
0, 0, 0, 1, 0, 0, 0, 1,
|
||||
0, 0, 0, 0, 1, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 1, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 1, 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 1};
|
||||
/* measurement matrix H */
|
||||
const float H8[] = { 1, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 1, 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 1, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 1, 0, 0, 0, 0};
|
||||
|
||||
/* matices for zero size velosity */
|
||||
/* dinamic matrix A */
|
||||
const float A6[] = { 1, 0, 0, 0, 1, 0,
|
||||
0, 1, 0, 0, 0, 1,
|
||||
0, 0, 1, 0, 0, 0,
|
||||
0, 0, 0, 1, 0, 0,
|
||||
0, 0, 0, 0, 1, 0,
|
||||
0, 0, 0, 0, 0, 1};
|
||||
/* measurement matrix H */
|
||||
const float H6[] = { 1, 0, 0, 0, 0, 0,
|
||||
0, 1, 0, 0, 0, 0,
|
||||
0, 0, 1, 0, 0, 0,
|
||||
0, 0, 0, 1, 0, 0};
|
||||
|
||||
#define STATE_NUM 6
|
||||
#define A A6
|
||||
#define H H6
|
||||
class CvBlobTrackerOneKalman:public CvBlobTrackerOne
|
||||
{
|
||||
private:
|
||||
CvBlob m_Blob;
|
||||
CvKalman* m_pKalman;
|
||||
int m_Frame;
|
||||
public:
|
||||
CvBlobTrackerOneKalman()
|
||||
{
|
||||
m_Frame = 0;
|
||||
m_pKalman = cvCreateKalman(STATE_NUM,4);
|
||||
memcpy( m_pKalman->transition_matrix->data.fl, A, sizeof(A));
|
||||
memcpy( m_pKalman->measurement_matrix->data.fl, H, sizeof(H));
|
||||
cvSetIdentity( m_pKalman->process_noise_cov, cvRealScalar(1e-5) );
|
||||
cvSetIdentity( m_pKalman->measurement_noise_cov, cvRealScalar(1e-1) );
|
||||
// CV_MAT_ELEM(*m_pKalman->measurement_noise_cov, float, 2,2) *= (float)pow(20,2);
|
||||
// CV_MAT_ELEM(*m_pKalman->measurement_noise_cov, float, 3,3) *= (float)pow(20,2);
|
||||
cvSetIdentity( m_pKalman->error_cov_post, cvRealScalar(1));
|
||||
cvZero(m_pKalman->state_post);
|
||||
cvZero(m_pKalman->state_pre);
|
||||
}
|
||||
~CvBlobTrackerOneKalman()
|
||||
{
|
||||
cvReleaseKalman(&m_pKalman);
|
||||
}
|
||||
virtual void Init(CvBlob* pBlob, IplImage* /*pImg*/, IplImage* /*pImgFG*/ = NULL)
|
||||
{
|
||||
m_Blob = pBlob[0];
|
||||
m_pKalman->state_post->data.fl[0] = CV_BLOB_X(pBlob);
|
||||
m_pKalman->state_post->data.fl[1] = CV_BLOB_Y(pBlob);
|
||||
m_pKalman->state_post->data.fl[2] = CV_BLOB_WX(pBlob);
|
||||
m_pKalman->state_post->data.fl[3] = CV_BLOB_WY(pBlob);
|
||||
}
|
||||
virtual CvBlob* Process(CvBlob* pBlob, IplImage* /*pImg*/, IplImage* /*pImgFG*/ = NULL)
|
||||
{
|
||||
CvBlob* pBlobRes = &m_Blob;
|
||||
float Z[4];
|
||||
CvMat Zmat = cvMat(4,1,CV_32F,Z);
|
||||
m_Blob = pBlob[0];
|
||||
if(m_Frame < 2)
|
||||
{/* first call */
|
||||
m_pKalman->state_post->data.fl[0+4] = CV_BLOB_X(pBlob)-m_pKalman->state_post->data.fl[0];
|
||||
m_pKalman->state_post->data.fl[1+4] = CV_BLOB_Y(pBlob)-m_pKalman->state_post->data.fl[1];
|
||||
if(m_pKalman->DP>6)
|
||||
{
|
||||
m_pKalman->state_post->data.fl[2+4] = CV_BLOB_WX(pBlob)-m_pKalman->state_post->data.fl[2];
|
||||
m_pKalman->state_post->data.fl[3+4] = CV_BLOB_WY(pBlob)-m_pKalman->state_post->data.fl[3];
|
||||
}
|
||||
m_pKalman->state_post->data.fl[0] = CV_BLOB_X(pBlob);
|
||||
m_pKalman->state_post->data.fl[1] = CV_BLOB_Y(pBlob);
|
||||
m_pKalman->state_post->data.fl[2] = CV_BLOB_WX(pBlob);
|
||||
m_pKalman->state_post->data.fl[3] = CV_BLOB_WY(pBlob);
|
||||
memcpy(m_pKalman->state_pre->data.fl,m_pKalman->state_post->data.fl,sizeof(float)*STATE_NUM);
|
||||
}
|
||||
else
|
||||
{/* another call */
|
||||
Z[0] = CV_BLOB_X(pBlob);
|
||||
Z[1] = CV_BLOB_Y(pBlob);
|
||||
Z[2] = CV_BLOB_WX(pBlob);
|
||||
Z[3] = CV_BLOB_WY(pBlob);
|
||||
cvKalmanCorrect(m_pKalman,&Zmat);
|
||||
cvKalmanPredict(m_pKalman,0);
|
||||
cvMatMulAdd(m_pKalman->measurement_matrix, m_pKalman->state_pre, NULL, &Zmat);
|
||||
CV_BLOB_X(pBlobRes) = Z[0];
|
||||
CV_BLOB_Y(pBlobRes) = Z[1];
|
||||
CV_BLOB_WX(pBlobRes) = Z[2];
|
||||
CV_BLOB_WY(pBlobRes) = Z[3];
|
||||
}
|
||||
m_Frame++;
|
||||
return pBlobRes;
|
||||
}
|
||||
virtual void Release()
|
||||
{
|
||||
delete this;
|
||||
}
|
||||
}; /* class CvBlobTrackerOneKalman */
|
||||
|
||||
static CvBlobTrackerOne* cvCreateModuleBlobTrackerOneKalman()
|
||||
{
|
||||
return (CvBlobTrackerOne*) new CvBlobTrackerOneKalman;
|
||||
}
|
||||
|
||||
CvBlobTracker* cvCreateBlobTrackerKalman()
|
||||
{
|
||||
return cvCreateBlobTrackerList(cvCreateModuleBlobTrackerOneKalman);
|
||||
}
|
||||
@@ -0,0 +1,524 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
#define PIX_HIST_BIN_NUM_1 3 //number of bins for classification (not used now)
|
||||
#define PIX_HIST_BIN_NUM_2 5 //number of bins for statistic collection
|
||||
#define PIX_HIST_ALPHA 0.01f //alpha-coefficient for running avarage procedure
|
||||
#define PIX_HIST_DELTA 2 //maximal difference between descriptors(RGB)
|
||||
#define PIX_HIST_COL_QUANTS 64 //quantization level in rgb-space
|
||||
#define PIX_HIST_DELTA_IN_PIX_VAL (PIX_HIST_DELTA * 256 / PIX_HIST_COL_QUANTS) //allowed difference in rgb-space
|
||||
|
||||
//structures for background statistics estimation
|
||||
typedef struct CvPixHistBin{
|
||||
float bin_val;
|
||||
uchar cols[3];
|
||||
}CvPixHistBin;
|
||||
typedef struct CvPixHist{
|
||||
CvPixHistBin bins[PIX_HIST_BIN_NUM_2];
|
||||
}CvPixHist;
|
||||
//class for background statistics estimation
|
||||
class CvBGEstimPixHist
|
||||
{
|
||||
private:
|
||||
CvPixHist* m_PixHists;
|
||||
int m_width;
|
||||
int m_height;
|
||||
|
||||
//function for update color histogram for one pixel
|
||||
void update_hist_elem(int x, int y, uchar* cols )
|
||||
{
|
||||
//find closest bin
|
||||
int dist = 0, min_dist = 2147483647, indx = -1;
|
||||
for( int k = 0; k < PIX_HIST_BIN_NUM_2; k++ ){
|
||||
uchar* hist_cols = m_PixHists[y*m_width+x].bins[k].cols;
|
||||
m_PixHists[y*m_width+x].bins[k].bin_val *= (1-PIX_HIST_ALPHA);
|
||||
int l;
|
||||
for( l = 0; l < 3; l++ ){
|
||||
int val = abs( hist_cols[l] - cols[l] );
|
||||
if( val > PIX_HIST_DELTA_IN_PIX_VAL ) break;
|
||||
dist += val;
|
||||
}
|
||||
if( l == 3 && dist < min_dist ){
|
||||
min_dist = dist;
|
||||
indx = k;
|
||||
}
|
||||
}
|
||||
if( indx < 0 ){//N2th elem in the table is replaced by a new features
|
||||
indx = PIX_HIST_BIN_NUM_2 - 1;
|
||||
m_PixHists[y*m_width+x].bins[indx].bin_val = PIX_HIST_ALPHA;
|
||||
for(int l = 0; l < 3; l++ ){
|
||||
m_PixHists[y*m_width+x].bins[indx].cols[l] = cols[l];
|
||||
}
|
||||
}
|
||||
else {
|
||||
//add vote!
|
||||
m_PixHists[y*m_width+x].bins[indx].bin_val += PIX_HIST_ALPHA;
|
||||
}
|
||||
//re-sort bins by BIN_VAL
|
||||
{
|
||||
int k;
|
||||
for(k = 0; k < indx; k++ ){
|
||||
if( m_PixHists[y*m_width+x].bins[k].bin_val <= m_PixHists[y*m_width+x].bins[indx].bin_val ){
|
||||
CvPixHistBin tmp1, tmp2 = m_PixHists[y*m_width+x].bins[indx];
|
||||
//shift elements
|
||||
for(int l = k; l <= indx; l++ ){
|
||||
tmp1 = m_PixHists[y*m_width+x].bins[l];
|
||||
m_PixHists[y*m_width+x].bins[l] = tmp2;
|
||||
tmp2 = tmp1;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}//void update_hist(...)
|
||||
|
||||
//function for calculation difference between histograms
|
||||
float get_hist_diff(int x1, int y1, int x2, int y2)
|
||||
{
|
||||
float dist = 0;
|
||||
for( int i = 0; i < 3; i++ ){
|
||||
dist += labs(m_PixHists[y1*m_width+x1].bins[0].cols[i] -
|
||||
m_PixHists[y2*m_width+x2].bins[0].cols[i]);
|
||||
}
|
||||
return dist;
|
||||
}
|
||||
|
||||
|
||||
public:
|
||||
IplImage* bg_image;
|
||||
|
||||
CvBGEstimPixHist(CvSize img_size)
|
||||
{
|
||||
m_PixHists = (CvPixHist*)cvAlloc(img_size.width*img_size.height*sizeof(CvPixHist));
|
||||
memset( m_PixHists, 0, img_size.width*img_size.height*sizeof(CvPixHist) );
|
||||
m_width = img_size.width;
|
||||
m_height = img_size.height;
|
||||
|
||||
bg_image = cvCreateImage(img_size, IPL_DEPTH_8U, 3 );
|
||||
}/* constructor */
|
||||
|
||||
~CvBGEstimPixHist()
|
||||
{
|
||||
cvReleaseImage(&bg_image);
|
||||
cvFree(&m_PixHists);
|
||||
}/* destructor */
|
||||
|
||||
|
||||
//function for update histograms and bg_image
|
||||
void update_hists( IplImage* pImg )
|
||||
{
|
||||
for( int i = 0; i < pImg->height; i++ ){
|
||||
for( int j = 0; j < pImg->width; j++ ){
|
||||
update_hist_elem( j, i, ((uchar*)(pImg->imageData))+i*pImg->widthStep+3*j );
|
||||
((uchar*)(bg_image->imageData))[i*bg_image->widthStep+3*j] = m_PixHists[i*m_width+j].bins[0].cols[0];
|
||||
((uchar*)(bg_image->imageData))[i*bg_image->widthStep+3*j+1] = m_PixHists[i*m_width+j].bins[0].cols[1];
|
||||
((uchar*)(bg_image->imageData))[i*bg_image->widthStep+3*j+2] = m_PixHists[i*m_width+j].bins[0].cols[2];
|
||||
}
|
||||
}
|
||||
//cvNamedWindow("RoadMap2",0);
|
||||
//cvShowImage("RoadMap2", bg_image);
|
||||
}
|
||||
};/* CvBGEstimPixHist */
|
||||
|
||||
|
||||
|
||||
/*======================= TRACKER LIST SHELL =====================*/
|
||||
typedef struct DefBlobTrackerL
|
||||
{
|
||||
CvBlob blob;
|
||||
CvBlobTrackerOne* pTracker;
|
||||
int Frame;
|
||||
int Collision;
|
||||
CvBlobTrackPredictor* pPredictor;
|
||||
CvBlob BlobPredict;
|
||||
CvBlobSeq* pBlobHyp;
|
||||
} DefBlobTrackerL;
|
||||
|
||||
class CvBlobTrackerList : public CvBlobTracker
|
||||
{
|
||||
private:
|
||||
CvBlobTrackerOne* (*m_Create)();
|
||||
CvBlobSeq m_BlobTrackerList;
|
||||
// int m_LastID;
|
||||
int m_Collision;
|
||||
int m_ClearHyp;
|
||||
float m_BGImageUsing;
|
||||
CvBGEstimPixHist* m_pBGImage;
|
||||
IplImage* m_pImgFG;
|
||||
IplImage* m_pImgReg; /* mask for multiblob confidence calculation */
|
||||
public:
|
||||
CvBlobTrackerList(CvBlobTrackerOne* (*create)()):m_BlobTrackerList(sizeof(DefBlobTrackerL))
|
||||
{
|
||||
//int i;
|
||||
CvBlobTrackerOne* pM = create();
|
||||
// m_LastID = 0;
|
||||
m_Create = create;
|
||||
m_ClearHyp = 0;
|
||||
m_pImgFG = 0;
|
||||
m_pImgReg = NULL;
|
||||
|
||||
TransferParamsFromChild(pM,NULL);
|
||||
|
||||
pM->Release();
|
||||
|
||||
m_Collision = 1; /* if 1 then collistion will be detected and processed */
|
||||
AddParam("Collision",&m_Collision);
|
||||
CommentParam("Collision", "if 1 then collision cases are processed in special way");
|
||||
|
||||
m_pBGImage = NULL;
|
||||
m_BGImageUsing = 50;
|
||||
AddParam("BGImageUsing", &m_BGImageUsing);
|
||||
CommentParam("BGImageUsing","Weight of using BG image in update hist model (0 - BG dies not use 1 - use)");
|
||||
}
|
||||
~CvBlobTrackerList()
|
||||
{
|
||||
int i;
|
||||
if(m_pBGImage) delete m_pBGImage;
|
||||
if(m_pImgFG) cvReleaseImage(&m_pImgFG);
|
||||
if(m_pImgReg) cvReleaseImage(&m_pImgReg);
|
||||
for(i=m_BlobTrackerList.GetBlobNum();i>0;--i)
|
||||
{
|
||||
m_BlobTrackerList.DelBlob(i-1);
|
||||
}
|
||||
};
|
||||
CvBlob* AddBlob(CvBlob* pBlob, IplImage* pImg, IplImage* pImgFG )
|
||||
{/* create new tracker */
|
||||
DefBlobTrackerL F;
|
||||
F.blob = pBlob[0];
|
||||
// F.blob.ID = m_LastID++;
|
||||
F.pTracker = m_Create();
|
||||
F.pPredictor = cvCreateModuleBlobTrackPredictKalman();
|
||||
F.pBlobHyp = new CvBlobSeq;
|
||||
F.Frame = 0;
|
||||
TransferParamsToChild(F.pTracker,NULL);
|
||||
|
||||
F.pTracker->Init(pBlob,pImg, pImgFG);
|
||||
m_BlobTrackerList.AddBlob((CvBlob*)&F);
|
||||
return m_BlobTrackerList.GetBlob(m_BlobTrackerList.GetBlobNum()-1);
|
||||
};
|
||||
void DelBlob(int BlobIndex)
|
||||
{
|
||||
DefBlobTrackerL* pF = (DefBlobTrackerL*)m_BlobTrackerList.GetBlob(BlobIndex);
|
||||
if(pF == NULL) return;
|
||||
pF->pTracker->Release();
|
||||
pF->pPredictor->Release();
|
||||
delete pF->pBlobHyp;
|
||||
m_BlobTrackerList.DelBlob(BlobIndex);
|
||||
}
|
||||
void DelBlobByID(int BlobID)
|
||||
{
|
||||
DefBlobTrackerL* pF = (DefBlobTrackerL*)m_BlobTrackerList.GetBlobByID(BlobID);
|
||||
if(pF == NULL) return;
|
||||
pF->pTracker->Release();
|
||||
pF->pPredictor->Release();
|
||||
delete pF->pBlobHyp;
|
||||
m_BlobTrackerList.DelBlobByID(BlobID);
|
||||
}
|
||||
|
||||
virtual void Process(IplImage* pImg, IplImage* pImgFG = NULL)
|
||||
{
|
||||
int i;
|
||||
if(pImgFG)
|
||||
{
|
||||
if(m_pImgFG) cvCopyImage(pImgFG,m_pImgFG);
|
||||
else m_pImgFG = cvCloneImage(pImgFG);
|
||||
}
|
||||
|
||||
if(m_pBGImage==NULL && m_BGImageUsing>0)
|
||||
{
|
||||
m_pBGImage = new CvBGEstimPixHist(cvSize(pImg->width,pImg->height));
|
||||
}
|
||||
|
||||
if(m_Collision)
|
||||
for(i=m_BlobTrackerList.GetBlobNum();i>0;--i)
|
||||
{/* update predictor */
|
||||
DefBlobTrackerL* pF = (DefBlobTrackerL*)m_BlobTrackerList.GetBlob(i-1);
|
||||
pF->pPredictor->Update((CvBlob*)pF);
|
||||
}/* update predictor */
|
||||
|
||||
if(m_pBGImage && m_pImgFG)
|
||||
{/* wheighting mask mask */
|
||||
int x,y,yN=pImg->height,xN=pImg->width;
|
||||
IplImage* pImgBG = NULL;
|
||||
m_pBGImage->update_hists(pImg);
|
||||
pImgBG = m_pBGImage->bg_image;
|
||||
for(y=0;y<yN;++y)
|
||||
{
|
||||
unsigned char* pI = (unsigned char*)pImg->imageData + y*pImg->widthStep;
|
||||
unsigned char* pBG = (unsigned char*)pImgBG->imageData + y*pImgBG->widthStep;
|
||||
unsigned char* pFG = (unsigned char*)m_pImgFG->imageData +y*m_pImgFG->widthStep;
|
||||
for(x=0;x<xN;++x)
|
||||
{
|
||||
if(pFG[x])
|
||||
{
|
||||
int D1 = (int)(pI[3*x+0])-(int)(pBG[3*x+0]);
|
||||
int D2 = (int)(pI[3*x+1])-(int)(pBG[3*x+1]);
|
||||
int D3 = (int)(pI[3*x+2])-(int)(pBG[3*x+2]);
|
||||
int DD = D1*D1+D2*D2+D3*D3;
|
||||
double D = sqrt((float)DD);
|
||||
double DW = 25;
|
||||
double W = 1/(exp(-4*(D-m_BGImageUsing)/DW)+1);
|
||||
pFG[x] = (uchar)cvRound(W*255);
|
||||
}
|
||||
}/* next mask pixel */
|
||||
}/* next mask line */
|
||||
/*if(m_Wnd)
|
||||
{
|
||||
cvNamedWindow("BlobList_FGWeight",0);
|
||||
cvShowImage("BlobList_FGWeight",m_pImgFG);
|
||||
}*/
|
||||
}/* wheighting mask mask */
|
||||
|
||||
for(i=m_BlobTrackerList.GetBlobNum();i>0;--i)
|
||||
{/* predict position */
|
||||
DefBlobTrackerL* pF = (DefBlobTrackerL*)m_BlobTrackerList.GetBlob(i-1);
|
||||
CvBlob* pB = pF->pPredictor->Predict();
|
||||
if(pB)
|
||||
{
|
||||
pF->BlobPredict = pB[0];
|
||||
pF->BlobPredict.w = pF->blob.w;
|
||||
pF->BlobPredict.h = pF->blob.h;
|
||||
}
|
||||
}/* predict position */
|
||||
|
||||
if(m_Collision)
|
||||
for(i=m_BlobTrackerList.GetBlobNum();i>0;--i)
|
||||
{/* predict collision */
|
||||
int Collision = 0;
|
||||
int j;
|
||||
DefBlobTrackerL* pF = (DefBlobTrackerL*)m_BlobTrackerList.GetBlob(i-1);
|
||||
for(j=m_BlobTrackerList.GetBlobNum();j>0;--j)
|
||||
{/* predict collision */
|
||||
CvBlob* pB1;
|
||||
CvBlob* pB2;
|
||||
DefBlobTrackerL* pF2 = (DefBlobTrackerL*)m_BlobTrackerList.GetBlob(j-1);
|
||||
if(i==j) continue;
|
||||
pB1 = &pF->BlobPredict;
|
||||
pB2 = &pF2->BlobPredict;
|
||||
if( fabs(pB1->x-pB2->x)<0.5*(pB1->w+pB2->w) &&
|
||||
fabs(pB1->y-pB2->y)<0.5*(pB1->h+pB2->h) ) Collision = 1;
|
||||
pB1 = &pF->blob;
|
||||
pB2 = &pF2->blob;
|
||||
if( fabs(pB1->x-pB2->x)<0.5*(pB1->w+pB2->w) &&
|
||||
fabs(pB1->y-pB2->y)<0.5*(pB1->h+pB2->h) ) Collision = 1;
|
||||
if(Collision) break;
|
||||
}/* check next blob to cross current*/
|
||||
pF->Collision = Collision;
|
||||
pF->pTracker->SetCollision(Collision);
|
||||
}/* predict collision */
|
||||
|
||||
for(i=m_BlobTrackerList.GetBlobNum();i>0;--i)
|
||||
{/* track each blob */
|
||||
DefBlobTrackerL* pF = (DefBlobTrackerL*)m_BlobTrackerList.GetBlob(i-1);
|
||||
if(pF->pBlobHyp->GetBlobNum()>0)
|
||||
{/* track all hypothesis */
|
||||
int h,hN = pF->pBlobHyp->GetBlobNum();
|
||||
for(h=0;h<hN;++h)
|
||||
{
|
||||
CvBlob* pB = pF->pBlobHyp->GetBlob(h);
|
||||
CvBlob* pNewBlob = pF->pTracker->Process(pB,pImg,m_pImgFG);
|
||||
int BlobID = CV_BLOB_ID(pB);
|
||||
if(pNewBlob)
|
||||
{
|
||||
pB[0] = pNewBlob[0];
|
||||
pB->w = MAX(CV_BLOB_MINW,pNewBlob->w);
|
||||
pB->h = MAX(CV_BLOB_MINH,pNewBlob->h);
|
||||
CV_BLOB_ID(pB) = BlobID;
|
||||
}
|
||||
}/* next hyp*/
|
||||
|
||||
}/* track all hypothesis */
|
||||
pF->Frame++;
|
||||
}/* next blob */
|
||||
|
||||
#if 0
|
||||
for(i=m_BlobTrackerList.GetBlobNum();i>0;--i)
|
||||
{/* update predictor */
|
||||
DefBlobTrackerL* pF = (DefBlobTrackerL*)m_BlobTrackerList.GetBlob(i-1);
|
||||
if((m_Collision && !pF->Collision) || !m_Collision)
|
||||
{
|
||||
pF->pPredictor->Update((CvBlob*)pF);
|
||||
}
|
||||
else
|
||||
{/* pravilnyp putem idete tovarischy!!! */
|
||||
pF->pPredictor->Update(&(pF->BlobPredict));
|
||||
}
|
||||
}/* update predictor */
|
||||
#endif
|
||||
m_ClearHyp = 1;
|
||||
};
|
||||
|
||||
|
||||
/* Process on blob (for multi hypothesis tracing) */
|
||||
virtual void ProcessBlob(int BlobIndex, CvBlob* pBlob, IplImage* pImg, IplImage* /*pImgFG*/ = NULL)
|
||||
{
|
||||
int ID = pBlob->ID;
|
||||
DefBlobTrackerL* pF = (DefBlobTrackerL*)m_BlobTrackerList.GetBlob(BlobIndex);
|
||||
CvBlob* pNewBlob = pF->pTracker->Process(pBlob?pBlob:&(pF->blob),pImg,m_pImgFG);
|
||||
if(pNewBlob)
|
||||
{
|
||||
pF->blob = pNewBlob[0];
|
||||
pF->blob.w = MAX(CV_BLOB_MINW,pNewBlob->w);
|
||||
pF->blob.h = MAX(CV_BLOB_MINH,pNewBlob->h);
|
||||
pBlob[0] = pF->blob;
|
||||
}
|
||||
pBlob->ID = ID;
|
||||
};
|
||||
virtual double GetConfidence(int BlobIndex, CvBlob* pBlob, IplImage* pImg, IplImage* pImgFG = NULL)
|
||||
{
|
||||
DefBlobTrackerL* pF = (DefBlobTrackerL*)m_BlobTrackerList.GetBlob(BlobIndex);
|
||||
if(pF==NULL) return 0;
|
||||
if(pF->pTracker==NULL) return 0;
|
||||
return pF->pTracker->GetConfidence(pBlob?pBlob:(&pF->blob), pImg, pImgFG, NULL);
|
||||
};
|
||||
virtual double GetConfidenceList(CvBlobSeq* pBlobList, IplImage* pImg, IplImage* pImgFG = NULL)
|
||||
{
|
||||
double W = 1;
|
||||
int b,bN = pBlobList->GetBlobNum();
|
||||
|
||||
if(m_pImgReg == NULL)
|
||||
{
|
||||
m_pImgReg = cvCreateImage(cvSize(pImg->width,pImg->height),IPL_DEPTH_8U,1);
|
||||
}
|
||||
assert(pImg);
|
||||
|
||||
cvSet(m_pImgReg,cvScalar(255));
|
||||
|
||||
for(b=0;b<bN;++b)
|
||||
{
|
||||
CvBlob* pB = pBlobList->GetBlob(b);
|
||||
DefBlobTrackerL* pF = (DefBlobTrackerL*)m_BlobTrackerList.GetBlobByID(pB->ID);
|
||||
if(pF==NULL || pF->pTracker==NULL) continue;
|
||||
W *= pF->pTracker->GetConfidence(pB, pImg, pImgFG, m_pImgReg );
|
||||
cvEllipse(
|
||||
m_pImgReg,
|
||||
cvPoint(cvRound(pB->x*256),cvRound(pB->y*256)), cvSize(cvRound(pB->w*128),cvRound(pB->h*128)),
|
||||
0, 0, 360,
|
||||
cvScalar(0), CV_FILLED, 8, 8 );
|
||||
// cvNamedWindow("REG",0);
|
||||
// cvShowImage("REG",m_pImgReg);
|
||||
// cvWaitKey(0);
|
||||
}
|
||||
return W;
|
||||
};
|
||||
virtual void UpdateBlob(int BlobIndex, CvBlob* pBlob, IplImage* pImg, IplImage* /*pImgFG*/ = NULL)
|
||||
{
|
||||
DefBlobTrackerL* pF = (DefBlobTrackerL*)m_BlobTrackerList.GetBlob(BlobIndex);
|
||||
if(pF)
|
||||
{
|
||||
pF->pTracker->Update(pBlob?pBlob:&(pF->blob),pImg,m_pImgFG);
|
||||
}
|
||||
};
|
||||
|
||||
int GetBlobNum(){return m_BlobTrackerList.GetBlobNum();};
|
||||
CvBlob* GetBlob(int index){return m_BlobTrackerList.GetBlob(index);};
|
||||
void SetBlob(int BlobIndex, CvBlob* pBlob)
|
||||
{
|
||||
CvBlob* pB = m_BlobTrackerList.GetBlob(BlobIndex);
|
||||
if(pB)
|
||||
{
|
||||
pB[0] = pBlob[0];
|
||||
pB->w = MAX(CV_BLOB_MINW, pBlob->w);
|
||||
pB->h = MAX(CV_BLOB_MINH, pBlob->h);
|
||||
}
|
||||
}
|
||||
|
||||
void Release(){delete this;};
|
||||
|
||||
/* additional functionality */
|
||||
CvBlob* GetBlobByID(int BlobID){return m_BlobTrackerList.GetBlobByID(BlobID);}
|
||||
|
||||
/* =============== MULTI HYPOTHESIS INTERFACE ================== */
|
||||
/* return number of position hyposetis of currently tracked blob */
|
||||
virtual int GetBlobHypNum(int BlobIdx)
|
||||
{
|
||||
DefBlobTrackerL* pF = (DefBlobTrackerL*)m_BlobTrackerList.GetBlob(BlobIdx);
|
||||
assert(pF->pBlobHyp);
|
||||
return pF->pBlobHyp->GetBlobNum();
|
||||
};/* CvBlobtrackerList::GetBlobHypNum() */
|
||||
|
||||
/* return pointer to specified blob hypothesis by index blob */
|
||||
virtual CvBlob* GetBlobHyp(int BlobIndex, int hypothesis)
|
||||
{
|
||||
DefBlobTrackerL* pF = (DefBlobTrackerL*)m_BlobTrackerList.GetBlob(BlobIndex);
|
||||
assert(pF->pBlobHyp);
|
||||
return pF->pBlobHyp->GetBlob(hypothesis);
|
||||
};/* CvBlobtrackerList::GetBlobHyp() */
|
||||
/* Set new parameters for specified (by index) blob hyp (can be called several times for each hyp )*/
|
||||
virtual void SetBlobHyp(int BlobIndex, CvBlob* pBlob)
|
||||
{
|
||||
if(m_ClearHyp)
|
||||
{/* clear all hypothesis */
|
||||
int b, bN = m_BlobTrackerList.GetBlobNum();
|
||||
for(b=0;b<bN;++b)
|
||||
{
|
||||
DefBlobTrackerL* pF = (DefBlobTrackerL*)m_BlobTrackerList.GetBlob(b);
|
||||
assert(pF->pBlobHyp);
|
||||
pF->pBlobHyp->Clear();
|
||||
}
|
||||
m_ClearHyp = 0;
|
||||
}
|
||||
{/* add hypothesis */
|
||||
DefBlobTrackerL* pF = (DefBlobTrackerL*)m_BlobTrackerList.GetBlob(BlobIndex);
|
||||
assert(pF->pBlobHyp);
|
||||
pF->pBlobHyp->AddBlob(pBlob);
|
||||
}
|
||||
}; /*CvBlobtrackerList::SetBlobHyp*/
|
||||
|
||||
private:
|
||||
public:
|
||||
void ParamUpdate()
|
||||
{
|
||||
int i;
|
||||
for(i=m_BlobTrackerList.GetBlobNum();i>0;--i)
|
||||
{
|
||||
DefBlobTrackerL* pF = (DefBlobTrackerL*)m_BlobTrackerList.GetBlob(i-1);
|
||||
TransferParamsToChild(pF->pTracker);
|
||||
pF->pTracker->ParamUpdate();
|
||||
}
|
||||
}
|
||||
}; /* CvBlobTrackerList */
|
||||
|
||||
CvBlobTracker* cvCreateBlobTrackerList(CvBlobTrackerOne* (*create)())
|
||||
{
|
||||
return (CvBlobTracker*) new CvBlobTrackerList(create);
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,420 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
#define SCALE_BASE 1.1
|
||||
#define SCALE_RANGE 2
|
||||
#define SCALE_NUM (2*SCALE_RANGE+1)
|
||||
typedef float DefHistType;
|
||||
#define DefHistTypeMat CV_32F
|
||||
#define HIST_INDEX(_pData) (((_pData)[0]>>m_ByteShift) + (((_pData)[1]>>(m_ByteShift))<<m_BinBit)+((pImgData[2]>>m_ByteShift)<<(m_BinBit*2)))
|
||||
|
||||
void calcKernelEpanechnikov(CvMat* pK)
|
||||
{/* allocate kernel for histogramm creation */
|
||||
int x,y;
|
||||
int w = pK->width;
|
||||
int h = pK->height;
|
||||
float x0 = 0.5f*(w-1);
|
||||
float y0 = 0.5f*(h-1);
|
||||
for(y=0;y<h;++y)for(x=0;x<w;++x)
|
||||
{
|
||||
// float r2 = ((x-x0)*(x-x0)/(x0*x0)+(y-y0)*(y-y0)/(y0*y0));
|
||||
float r2 = ((x-x0)*(x-x0)+(y-y0)*(y-y0))/((x0*x0)+(y0*y0));
|
||||
CV_MAT_ELEM(pK[0],DefHistType, y, x) = (DefHistType)((r2<1)?(1-r2):0);
|
||||
}
|
||||
}/* allocate kernel for histogramm creation */
|
||||
|
||||
class CvBlobTrackerOneMSFGS:public CvBlobTrackerOne
|
||||
{
|
||||
private:
|
||||
/* parameters */
|
||||
float m_FGWeight;
|
||||
float m_Alpha;
|
||||
CvSize m_ObjSize;
|
||||
CvMat* m_KernelHistModel;
|
||||
CvMat* m_KernelHistCandidate;
|
||||
CvSize m_KernelMeanShiftSize;
|
||||
CvMat* m_KernelMeanShiftK[SCALE_NUM];
|
||||
CvMat* m_KernelMeanShiftG[SCALE_NUM];
|
||||
CvMat* m_Weights;
|
||||
int m_BinBit;
|
||||
int m_ByteShift;
|
||||
int m_BinNum;
|
||||
int m_Dim;
|
||||
int m_BinNumTotal;
|
||||
CvMat* m_HistModel;
|
||||
float m_HistModelVolume;
|
||||
CvMat* m_HistCandidate;
|
||||
float m_HistCandidateVolume;
|
||||
CvMat* m_HistTemp;
|
||||
CvBlob m_Blob;
|
||||
void ReAllocHist(int Dim, int BinBit)
|
||||
{
|
||||
m_BinBit = BinBit;
|
||||
m_ByteShift = 8-BinBit;
|
||||
m_Dim = Dim;
|
||||
m_BinNum = (1<<BinBit);
|
||||
m_BinNumTotal = cvRound(pow((double)m_BinNum,(double)m_Dim));
|
||||
if(m_HistModel) cvReleaseMat(&m_HistModel);
|
||||
if(m_HistCandidate) cvReleaseMat(&m_HistCandidate);
|
||||
if(m_HistTemp) cvReleaseMat(&m_HistTemp);
|
||||
m_HistCandidate = cvCreateMat(1, m_BinNumTotal, DefHistTypeMat);
|
||||
m_HistModel = cvCreateMat(1, m_BinNumTotal, DefHistTypeMat);
|
||||
m_HistTemp = cvCreateMat(1, m_BinNumTotal, DefHistTypeMat);
|
||||
cvZero(m_HistCandidate);
|
||||
cvZero(m_HistModel);
|
||||
m_HistModelVolume = 0.0f;
|
||||
m_HistCandidateVolume = 0.0f;
|
||||
}
|
||||
void ReAllocKernel(int w, int h, float sigma=0.4)
|
||||
{
|
||||
double ScaleToObj = sigma*1.39;
|
||||
int kernel_width = cvRound(w/ScaleToObj);
|
||||
int kernel_height = cvRound(h/ScaleToObj);
|
||||
int x,y,s;
|
||||
assert(w>0);
|
||||
assert(h>0);
|
||||
m_ObjSize = cvSize(w,h);
|
||||
m_KernelMeanShiftSize = cvSize(kernel_width,kernel_height);
|
||||
|
||||
|
||||
/* create kernels for histogramm calculation */
|
||||
if(m_KernelHistModel) cvReleaseMat(&m_KernelHistModel);
|
||||
m_KernelHistModel = cvCreateMat(h, w, DefHistTypeMat);
|
||||
calcKernelEpanechnikov(m_KernelHistModel);
|
||||
if(m_KernelHistCandidate) cvReleaseMat(&m_KernelHistCandidate);
|
||||
m_KernelHistCandidate = cvCreateMat(kernel_height, kernel_width, DefHistTypeMat);
|
||||
calcKernelEpanechnikov(m_KernelHistCandidate);
|
||||
|
||||
if(m_Weights) cvReleaseMat(&m_Weights);
|
||||
m_Weights = cvCreateMat(kernel_height, kernel_width, CV_32F);
|
||||
|
||||
for(s=-SCALE_RANGE;s<=SCALE_RANGE;++s)
|
||||
{/* allocate kernwl for meanshifts in space and scale */
|
||||
int si = s+SCALE_RANGE;
|
||||
double cur_sigma = sigma * pow(SCALE_BASE,s);
|
||||
double cur_sigma2 = cur_sigma*cur_sigma;
|
||||
double x0 = 0.5*(kernel_width-1);
|
||||
double y0 = 0.5*(kernel_height-1);
|
||||
if(m_KernelMeanShiftK[si]) cvReleaseMat(&m_KernelMeanShiftK[si]);
|
||||
if(m_KernelMeanShiftG[si]) cvReleaseMat(&m_KernelMeanShiftG[si]);
|
||||
m_KernelMeanShiftK[si] = cvCreateMat(kernel_height, kernel_width, DefHistTypeMat);
|
||||
m_KernelMeanShiftG[si] = cvCreateMat(kernel_height, kernel_width, DefHistTypeMat);
|
||||
for(y=0;y<kernel_height;++y)
|
||||
{
|
||||
DefHistType* pK = (DefHistType*)CV_MAT_ELEM_PTR_FAST( m_KernelMeanShiftK[si][0], y, 0, sizeof(DefHistType) );
|
||||
DefHistType* pG = (DefHistType*)CV_MAT_ELEM_PTR_FAST( m_KernelMeanShiftG[si][0], y, 0, sizeof(DefHistType) );
|
||||
for(x=0;x<kernel_width;++x)
|
||||
{
|
||||
double r2 = ((x-x0)*(x-x0)/(x0*x0)+(y-y0)*(y-y0)/(y0*y0));
|
||||
double sigma12 = cur_sigma2 / 2.56;
|
||||
double sigma22 = cur_sigma2 * 2.56;
|
||||
pK[x] = (DefHistType)(Gaussian2D(r2, sigma12)/sigma12 - Gaussian2D(r2, sigma22)/sigma22);
|
||||
pG[x] = (DefHistType)(Gaussian2D(r2, cur_sigma2/1.6) - Gaussian2D(r2, cur_sigma2*1.6));
|
||||
}
|
||||
}/* next line */
|
||||
}
|
||||
}/* ReallocKernel*/
|
||||
inline double Gaussian2D(double x, double sigma2)
|
||||
{
|
||||
return (exp(-x/(2*sigma2)) / (2*3.1415926535897932384626433832795*sigma2) );
|
||||
}
|
||||
void calcHist(IplImage* pImg, IplImage* pMask, CvPoint Center, CvMat* pKernel, CvMat* pHist, DefHistType* pHistVolume)
|
||||
{
|
||||
int w = pKernel->width;
|
||||
int h = pKernel->height;
|
||||
DefHistType Volume = 0;
|
||||
int x0 = Center.x - w/2;
|
||||
int y0 = Center.y - h/2;
|
||||
int x,y;
|
||||
|
||||
//cvZero(pHist);
|
||||
cvSet(pHist,cvScalar(1.0/m_BinNumTotal)); /* no zero bins, all bins have very small value*/
|
||||
Volume = 1;
|
||||
|
||||
if(m_Dim == 3)
|
||||
{
|
||||
for(y=0;y<h;++y)
|
||||
{
|
||||
unsigned char* pImgData = NULL;
|
||||
unsigned char* pMaskData = NULL;
|
||||
DefHistType* pKernelData = NULL;
|
||||
if((y0+y)>=pImg->height) continue;
|
||||
if((y0+y)<0)continue;
|
||||
pImgData = &CV_IMAGE_ELEM(pImg,unsigned char,y+y0,x0*3);
|
||||
pMaskData = pMask?(&CV_IMAGE_ELEM(pMask,unsigned char,y+y0,x0)):NULL;
|
||||
pKernelData = (DefHistType*)CV_MAT_ELEM_PTR_FAST(pKernel[0],y,0,sizeof(DefHistType));
|
||||
for(x=0;x<w;++x,pImgData+=3)
|
||||
{
|
||||
if((x0+x)>=pImg->width) continue;
|
||||
if((x0+x)<0)continue;
|
||||
if(pMaskData==NULL || pMaskData[x]>128)
|
||||
{
|
||||
DefHistType K = pKernelData[x];
|
||||
int index = HIST_INDEX(pImgData);
|
||||
assert(index >= 0 && index < pHist->cols);
|
||||
Volume += K;
|
||||
((DefHistType*)(pHist->data.ptr))[index] += K;
|
||||
}/* only masked pixels */
|
||||
}/* next column */
|
||||
}/* next row */
|
||||
}/* if m_Dim == 3 */
|
||||
if(pHistVolume)pHistVolume[0] = Volume;
|
||||
};/*calcHist*/
|
||||
double calcBhattacharyya()
|
||||
{
|
||||
cvMul(m_HistCandidate,m_HistModel,m_HistTemp);
|
||||
cvPow(m_HistTemp,m_HistTemp,0.5);
|
||||
return cvSum(m_HistTemp).val[0] / sqrt(m_HistCandidateVolume*m_HistModelVolume);
|
||||
} /* calcBhattacharyyaCoefficient */
|
||||
void calcWeights(IplImage* pImg, IplImage* pImgFG, CvPoint Center)
|
||||
{
|
||||
cvZero(m_Weights);
|
||||
/* calc new pos */
|
||||
if(m_Dim == 3)
|
||||
{
|
||||
int x0 = Center.x - m_KernelMeanShiftSize.width/2;
|
||||
int y0 = Center.y - m_KernelMeanShiftSize.height/2;
|
||||
int x,y;
|
||||
|
||||
assert(m_Weights->width == m_KernelMeanShiftSize.width);
|
||||
assert(m_Weights->height == m_KernelMeanShiftSize.height);
|
||||
|
||||
/*calc shift vector */
|
||||
for(y=0;y<m_KernelMeanShiftSize.height;++y)
|
||||
{
|
||||
unsigned char* pImgData = NULL;
|
||||
unsigned char* pMaskData = NULL;
|
||||
float* pWData = NULL;
|
||||
|
||||
if(y+y0 < 0 || y+y0 >= pImg->height) continue;
|
||||
|
||||
pImgData = &CV_IMAGE_ELEM(pImg,unsigned char,y+y0,x0*3);
|
||||
pMaskData = pImgFG?(&CV_IMAGE_ELEM(pImgFG,unsigned char,y+y0,x0)):NULL;
|
||||
pWData = (float*)CV_MAT_ELEM_PTR_FAST(m_Weights[0],y,0,sizeof(float));
|
||||
|
||||
for(x=0;x<m_KernelMeanShiftSize.width;++x,pImgData+=3)
|
||||
{
|
||||
double V = 0;
|
||||
double HM = 0;
|
||||
double HC = 0;
|
||||
int index;
|
||||
if(x+x0 < 0 || x+x0 >= pImg->width) continue;
|
||||
|
||||
index = HIST_INDEX(pImgData);
|
||||
assert(index >= 0 && index < m_BinNumTotal);
|
||||
|
||||
if(m_HistModelVolume>0)
|
||||
HM = ((DefHistType*)m_HistModel->data.ptr)[index]/m_HistModelVolume;
|
||||
if(m_HistCandidateVolume>0)
|
||||
HC = ((DefHistType*)m_HistCandidate->data.ptr)[index]/m_HistCandidateVolume;
|
||||
|
||||
V = (HC>0)?sqrt(HM / HC):0;
|
||||
V += m_FGWeight*(pMaskData?((pMaskData[x]/255.0f)):0);
|
||||
pWData[x] = (float)MIN(V,100000);
|
||||
}/* next column */
|
||||
}/* next row */
|
||||
}/* if m_Dim == 3 */
|
||||
}/* calcWeights */
|
||||
|
||||
public:
|
||||
CvBlobTrackerOneMSFGS()
|
||||
{
|
||||
int i;
|
||||
m_FGWeight = 0;
|
||||
m_Alpha = 0.0;
|
||||
|
||||
/* add several parameters for external use */
|
||||
AddParam("FGWeight", &m_FGWeight);
|
||||
CommentParam("FGWeight","Weight of FG mask using (0 - mask will not be used for tracking)");
|
||||
AddParam("Alpha", &m_Alpha);
|
||||
CommentParam("Alpha","Coefficient for model histogramm updating (0 - hist is not upated)");
|
||||
|
||||
m_BinBit=0;
|
||||
m_Dim = 0;
|
||||
m_HistModel = NULL;
|
||||
m_HistCandidate = NULL;
|
||||
m_HistTemp = NULL;
|
||||
m_KernelHistModel = NULL;
|
||||
m_KernelHistCandidate = NULL;
|
||||
m_Weights = NULL;
|
||||
for(i=0;i<SCALE_NUM;++i)
|
||||
{
|
||||
m_KernelMeanShiftK[i] = NULL;
|
||||
m_KernelMeanShiftG[i] = NULL;
|
||||
}
|
||||
ReAllocHist(3,5); /* 3D hist, each dim has 2^5 bins*/
|
||||
}
|
||||
~CvBlobTrackerOneMSFGS()
|
||||
{
|
||||
int i;
|
||||
if(m_HistModel) cvReleaseMat(&m_HistModel);
|
||||
if(m_HistCandidate) cvReleaseMat(&m_HistCandidate);
|
||||
if(m_HistTemp) cvReleaseMat(&m_HistTemp);
|
||||
if(m_KernelHistModel) cvReleaseMat(&m_KernelHistModel);
|
||||
for(i=0;i<SCALE_NUM;++i)
|
||||
{
|
||||
if(m_KernelMeanShiftK[i]) cvReleaseMat(&m_KernelMeanShiftK[i]);
|
||||
if(m_KernelMeanShiftG[i]) cvReleaseMat(&m_KernelMeanShiftG[i]);
|
||||
}
|
||||
}
|
||||
/* interface */
|
||||
virtual void Init(CvBlob* pBlobInit, IplImage* pImg, IplImage* pImgFG = NULL)
|
||||
{
|
||||
int w = cvRound(CV_BLOB_WX(pBlobInit));
|
||||
int h = cvRound(CV_BLOB_WY(pBlobInit));
|
||||
if(w<3)w=3;
|
||||
if(h<3)h=3;
|
||||
if(w>pImg->width)w=pImg->width;
|
||||
if(h>pImg->height)h=pImg->height;
|
||||
ReAllocKernel(w,h);
|
||||
calcHist(pImg, pImgFG, cvPointFrom32f(CV_BLOB_CENTER(pBlobInit)), m_KernelHistModel, m_HistModel, &m_HistModelVolume);
|
||||
m_Blob = pBlobInit[0];
|
||||
};
|
||||
virtual CvBlob* Process(CvBlob* pBlobPrev, IplImage* pImg, IplImage* pImgFG = NULL)
|
||||
{
|
||||
int iter;
|
||||
|
||||
if(pBlobPrev)
|
||||
{
|
||||
m_Blob = pBlobPrev[0];
|
||||
}
|
||||
for(iter=0;iter<10;++iter)
|
||||
{
|
||||
// float newx=0,newy=0,sum=0;
|
||||
float dx=0,dy=0,sum=0;
|
||||
int x,y,si;
|
||||
CvPoint Center = cvPoint(cvRound(m_Blob.x),cvRound(m_Blob.y));
|
||||
CvSize Size = cvSize(cvRound(m_Blob.w),cvRound(m_Blob.h));
|
||||
|
||||
if(m_ObjSize.width != Size.width || m_ObjSize.height != Size.height)
|
||||
{ /* realloc kernels */
|
||||
ReAllocKernel(Size.width,Size.height);
|
||||
} /* realloc kernels */
|
||||
|
||||
/* mean shift in coordinate space */
|
||||
calcHist(pImg, NULL, Center, m_KernelHistCandidate, m_HistCandidate, &m_HistCandidateVolume);
|
||||
calcWeights(pImg, pImgFG, Center);
|
||||
for(si=1;si<(SCALE_NUM-1);++si)
|
||||
{
|
||||
CvMat* pKernel = m_KernelMeanShiftK[si];
|
||||
float sdx = 0, sdy=0, ssum=0;
|
||||
int s = si-SCALE_RANGE;
|
||||
float factor = (1.0f-( float(s)/float(SCALE_RANGE) )*( float(s)/float(SCALE_RANGE) ));
|
||||
|
||||
for(y=0;y<m_KernelMeanShiftSize.height;++y)
|
||||
for(x=0;x<m_KernelMeanShiftSize.width;++x)
|
||||
{
|
||||
float W = *(float*)CV_MAT_ELEM_PTR_FAST(m_Weights[0],y,x,sizeof(float));
|
||||
float K = *(float*)CV_MAT_ELEM_PTR_FAST(pKernel[0],y,x,sizeof(float));
|
||||
float KW = K*W;
|
||||
ssum += (float)fabs(KW);
|
||||
sdx += KW*(x-m_KernelMeanShiftSize.width*0.5f);
|
||||
sdy += KW*(y-m_KernelMeanShiftSize.height*0.5f);
|
||||
}/* next pixel */
|
||||
dx += sdx * factor;
|
||||
dy += sdy * factor;
|
||||
sum += ssum * factor;
|
||||
}/* next scale */
|
||||
if(sum > 0)
|
||||
{
|
||||
dx /= sum;
|
||||
dy /= sum;
|
||||
}
|
||||
|
||||
m_Blob.x += dx;
|
||||
m_Blob.y += dy;
|
||||
|
||||
{ /* mean shift in scale space */
|
||||
float news = 0;
|
||||
float sum = 0;
|
||||
float scale;
|
||||
|
||||
Center = cvPoint(cvRound(m_Blob.x),cvRound(m_Blob.y));
|
||||
calcHist(pImg, NULL, Center, m_KernelHistCandidate, m_HistCandidate, &m_HistCandidateVolume);
|
||||
calcWeights(pImg, pImgFG, Center);
|
||||
//cvSet(m_Weights,cvScalar(1));
|
||||
for(si=0; si<SCALE_NUM; si++)
|
||||
{
|
||||
double W = cvDotProduct(m_Weights, m_KernelMeanShiftG[si]);;
|
||||
int s = si-SCALE_RANGE;
|
||||
sum += (float)fabs(W);
|
||||
news += (float)(s*W);
|
||||
}
|
||||
if(sum>0)
|
||||
{
|
||||
news /= sum;
|
||||
}
|
||||
scale = (float)pow((double)SCALE_BASE,(double)news);
|
||||
m_Blob.w *= scale;
|
||||
m_Blob.h *= scale;
|
||||
} /* mean shift in scale space */
|
||||
|
||||
/* check fo finish */
|
||||
if(fabs(dx)<0.1 && fabs(dy)<0.1) break;
|
||||
}/* next iteration */
|
||||
|
||||
if(m_Alpha>0)
|
||||
{/* update hist */
|
||||
double Vol, WM, WC;
|
||||
CvPoint Center = cvPoint(cvRound(m_Blob.x),cvRound(m_Blob.y));
|
||||
calcHist(pImg, pImgFG, Center, m_KernelHistModel, m_HistCandidate, &m_HistCandidateVolume);
|
||||
Vol = 0.5*(m_HistModelVolume + m_HistCandidateVolume);
|
||||
WM = Vol*(1-m_Alpha)/m_HistModelVolume;
|
||||
WC = Vol*(m_Alpha)/m_HistCandidateVolume;
|
||||
cvAddWeighted(m_HistModel, WM, m_HistCandidate,WC,0,m_HistModel);
|
||||
m_HistModelVolume = (float)cvSum(m_HistModel).val[0];
|
||||
}/* update hist */
|
||||
|
||||
return &m_Blob;
|
||||
}; /* Process */
|
||||
virtual void Release(){delete this;};
|
||||
}; /*CvBlobTrackerOneMSFGS*/
|
||||
|
||||
CvBlobTrackerOne* cvCreateBlobTrackerOneMSFGS()
|
||||
{
|
||||
return (CvBlobTrackerOne*) new CvBlobTrackerOneMSFGS;
|
||||
}
|
||||
CvBlobTracker* cvCreateBlobTrackerMSFGS()
|
||||
{
|
||||
return cvCreateBlobTrackerList(cvCreateBlobTrackerOneMSFGS);
|
||||
}
|
||||
|
||||
@@ -0,0 +1,303 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
/*======================= KALMAN FILTER =========================*/
|
||||
/* state vector is (x,y,w,h,dx,dy,dw,dh)*/
|
||||
/* mesurment is (x,y,w,h) */
|
||||
/* dinamic matrix A */
|
||||
const float A8[] = { 1, 0, 0, 0, 1, 0, 0, 0,
|
||||
0, 1, 0, 0, 0, 1, 0, 0,
|
||||
0, 0, 1, 0, 0, 0, 1, 0,
|
||||
0, 0, 0, 1, 0, 0, 0, 1,
|
||||
0, 0, 0, 0, 1, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 1, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 1, 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 1};
|
||||
/* measurement matrix H */
|
||||
const float H8[] = { 1, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 1, 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 1, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 1, 0, 0, 0, 0};
|
||||
|
||||
/* matices for zero size velosity */
|
||||
/* dinamic matrix A */
|
||||
const float A6[] = { 1, 0, 0, 0, 1, 0,
|
||||
0, 1, 0, 0, 0, 1,
|
||||
0, 0, 1, 0, 0, 0,
|
||||
0, 0, 0, 1, 0, 0,
|
||||
0, 0, 0, 0, 1, 0,
|
||||
0, 0, 0, 0, 0, 1};
|
||||
/* measurement matrix H */
|
||||
const float H6[] = { 1, 0, 0, 0, 0, 0,
|
||||
0, 1, 0, 0, 0, 0,
|
||||
0, 0, 1, 0, 0, 0,
|
||||
0, 0, 0, 1, 0, 0};
|
||||
|
||||
#define STATE_NUM 6
|
||||
#define A A6
|
||||
#define H H6
|
||||
|
||||
class CvBlobTrackPostProcKalman:public CvBlobTrackPostProcOne
|
||||
{
|
||||
private:
|
||||
CvBlob m_Blob;
|
||||
CvKalman* m_pKalman;
|
||||
int m_Frame;
|
||||
float m_ModelNoise;
|
||||
float m_DataNoisePos;
|
||||
float m_DataNoiseSize;
|
||||
public:
|
||||
CvBlobTrackPostProcKalman();
|
||||
~CvBlobTrackPostProcKalman();
|
||||
CvBlob* Process(CvBlob* pBlob);
|
||||
void Release();
|
||||
virtual void ParamUpdate();
|
||||
}; /* class CvBlobTrackPostProcKalman */
|
||||
|
||||
|
||||
CvBlobTrackPostProcKalman::CvBlobTrackPostProcKalman()
|
||||
{
|
||||
m_ModelNoise = 1e-6f;
|
||||
m_DataNoisePos = 1e-6f;
|
||||
m_DataNoiseSize = 1e-1f;
|
||||
#if STATE_NUM>6
|
||||
m_DataNoiseSize *= (float)pow(20.,2.);
|
||||
#else
|
||||
m_DataNoiseSize /= (float)pow(20.,2.);
|
||||
#endif
|
||||
|
||||
AddParam("ModelNoise",&m_ModelNoise);
|
||||
AddParam("DataNoisePos",&m_DataNoisePos);
|
||||
AddParam("DataNoiseSize",&m_DataNoiseSize);
|
||||
|
||||
m_Frame = 0;
|
||||
m_pKalman = cvCreateKalman(STATE_NUM,4);
|
||||
memcpy( m_pKalman->transition_matrix->data.fl, A, sizeof(A));
|
||||
memcpy( m_pKalman->measurement_matrix->data.fl, H, sizeof(H));
|
||||
|
||||
cvSetIdentity( m_pKalman->process_noise_cov, cvRealScalar(m_ModelNoise) );
|
||||
cvSetIdentity( m_pKalman->measurement_noise_cov, cvRealScalar(m_DataNoisePos) );
|
||||
CV_MAT_ELEM(*m_pKalman->measurement_noise_cov, float, 2,2) = m_DataNoiseSize;
|
||||
CV_MAT_ELEM(*m_pKalman->measurement_noise_cov, float, 3,3) = m_DataNoiseSize;
|
||||
cvSetIdentity( m_pKalman->error_cov_post, cvRealScalar(1));
|
||||
cvZero(m_pKalman->state_post);
|
||||
cvZero(m_pKalman->state_pre);
|
||||
}
|
||||
CvBlobTrackPostProcKalman::~CvBlobTrackPostProcKalman()
|
||||
{
|
||||
cvReleaseKalman(&m_pKalman);
|
||||
}
|
||||
|
||||
void CvBlobTrackPostProcKalman::ParamUpdate()
|
||||
{
|
||||
cvSetIdentity( m_pKalman->process_noise_cov, cvRealScalar(m_ModelNoise) );
|
||||
cvSetIdentity( m_pKalman->measurement_noise_cov, cvRealScalar(m_DataNoisePos) );
|
||||
CV_MAT_ELEM(*m_pKalman->measurement_noise_cov, float, 2,2) = m_DataNoiseSize;
|
||||
CV_MAT_ELEM(*m_pKalman->measurement_noise_cov, float, 3,3) = m_DataNoiseSize;
|
||||
}
|
||||
CvBlob* CvBlobTrackPostProcKalman::Process(CvBlob* pBlob)
|
||||
{
|
||||
CvBlob* pBlobRes = &m_Blob;
|
||||
float Z[4];
|
||||
CvMat Zmat = cvMat(4,1,CV_32F,Z);
|
||||
m_Blob = pBlob[0];
|
||||
if(m_Frame < 2)
|
||||
{/* first call */
|
||||
m_pKalman->state_post->data.fl[0+4] = CV_BLOB_X(pBlob)-m_pKalman->state_post->data.fl[0];
|
||||
m_pKalman->state_post->data.fl[1+4] = CV_BLOB_Y(pBlob)-m_pKalman->state_post->data.fl[1];
|
||||
if(m_pKalman->DP>6)
|
||||
{
|
||||
m_pKalman->state_post->data.fl[2+4] = CV_BLOB_WX(pBlob)-m_pKalman->state_post->data.fl[2];
|
||||
m_pKalman->state_post->data.fl[3+4] = CV_BLOB_WY(pBlob)-m_pKalman->state_post->data.fl[3];
|
||||
}
|
||||
m_pKalman->state_post->data.fl[0] = CV_BLOB_X(pBlob);
|
||||
m_pKalman->state_post->data.fl[1] = CV_BLOB_Y(pBlob);
|
||||
m_pKalman->state_post->data.fl[2] = CV_BLOB_WX(pBlob);
|
||||
m_pKalman->state_post->data.fl[3] = CV_BLOB_WY(pBlob);
|
||||
}
|
||||
else
|
||||
{/* another call */
|
||||
cvKalmanPredict(m_pKalman,0);
|
||||
Z[0] = CV_BLOB_X(pBlob);
|
||||
Z[1] = CV_BLOB_Y(pBlob);
|
||||
Z[2] = CV_BLOB_WX(pBlob);
|
||||
Z[3] = CV_BLOB_WY(pBlob);
|
||||
cvKalmanCorrect(m_pKalman,&Zmat);
|
||||
cvMatMulAdd(m_pKalman->measurement_matrix, m_pKalman->state_post, NULL, &Zmat);
|
||||
CV_BLOB_X(pBlobRes) = Z[0];
|
||||
CV_BLOB_Y(pBlobRes) = Z[1];
|
||||
// CV_BLOB_WX(pBlobRes) = Z[2];
|
||||
// CV_BLOB_WY(pBlobRes) = Z[3];
|
||||
}
|
||||
m_Frame++;
|
||||
return pBlobRes;
|
||||
}
|
||||
void CvBlobTrackPostProcKalman::Release()
|
||||
{
|
||||
delete this;
|
||||
}
|
||||
|
||||
CvBlobTrackPostProcOne* cvCreateModuleBlobTrackPostProcKalmanOne()
|
||||
{
|
||||
return (CvBlobTrackPostProcOne*) new CvBlobTrackPostProcKalman;
|
||||
}
|
||||
|
||||
CvBlobTrackPostProc* cvCreateModuleBlobTrackPostProcKalman()
|
||||
{
|
||||
return cvCreateBlobTrackPostProcList(cvCreateModuleBlobTrackPostProcKalmanOne);
|
||||
}
|
||||
/*======================= KALMAN FILTER =========================*/
|
||||
|
||||
|
||||
|
||||
/*======================= KALMAN PREDICTOR =========================*/
|
||||
class CvBlobTrackPredictKalman:public CvBlobTrackPredictor
|
||||
{
|
||||
private:
|
||||
CvBlob m_BlobPredict;
|
||||
CvKalman* m_pKalman;
|
||||
int m_Frame;
|
||||
float m_ModelNoise;
|
||||
float m_DataNoisePos;
|
||||
float m_DataNoiseSize;
|
||||
public:
|
||||
CvBlobTrackPredictKalman();
|
||||
~CvBlobTrackPredictKalman();
|
||||
CvBlob* Predict();
|
||||
void Update(CvBlob* pBlob);
|
||||
virtual void ParamUpdate();
|
||||
void Release()
|
||||
{
|
||||
delete this;
|
||||
}
|
||||
}; /* class CvBlobTrackPredictKalman */
|
||||
|
||||
|
||||
void CvBlobTrackPredictKalman::ParamUpdate()
|
||||
{
|
||||
cvSetIdentity( m_pKalman->process_noise_cov, cvRealScalar(m_ModelNoise) );
|
||||
cvSetIdentity( m_pKalman->measurement_noise_cov, cvRealScalar(m_DataNoisePos) );
|
||||
CV_MAT_ELEM(*m_pKalman->measurement_noise_cov, float, 2,2) = m_DataNoiseSize;
|
||||
CV_MAT_ELEM(*m_pKalman->measurement_noise_cov, float, 3,3) = m_DataNoiseSize;
|
||||
}
|
||||
CvBlobTrackPredictKalman::CvBlobTrackPredictKalman()
|
||||
{
|
||||
m_ModelNoise = 1e-6f;
|
||||
m_DataNoisePos = 1e-6f;
|
||||
m_DataNoiseSize = 1e-1f;
|
||||
#if STATE_NUM>6
|
||||
m_DataNoiseSize *= (float)pow(20.,2.);
|
||||
#else
|
||||
m_DataNoiseSize /= (float)pow(20.,2.);
|
||||
#endif
|
||||
|
||||
AddParam("ModelNoise",&m_ModelNoise);
|
||||
AddParam("DataNoisePos",&m_DataNoisePos);
|
||||
AddParam("DataNoiseSize",&m_DataNoiseSize);
|
||||
|
||||
m_Frame = 0;
|
||||
m_pKalman = cvCreateKalman(STATE_NUM,4);
|
||||
memcpy( m_pKalman->transition_matrix->data.fl, A, sizeof(A));
|
||||
memcpy( m_pKalman->measurement_matrix->data.fl, H, sizeof(H));
|
||||
|
||||
cvSetIdentity( m_pKalman->process_noise_cov, cvRealScalar(m_ModelNoise) );
|
||||
cvSetIdentity( m_pKalman->measurement_noise_cov, cvRealScalar(m_DataNoisePos) );
|
||||
CV_MAT_ELEM(*m_pKalman->measurement_noise_cov, float, 2,2) = m_DataNoiseSize;
|
||||
CV_MAT_ELEM(*m_pKalman->measurement_noise_cov, float, 3,3) = m_DataNoiseSize;
|
||||
cvSetIdentity( m_pKalman->error_cov_post, cvRealScalar(1));
|
||||
cvZero(m_pKalman->state_post);
|
||||
cvZero(m_pKalman->state_pre);
|
||||
}
|
||||
CvBlobTrackPredictKalman::~CvBlobTrackPredictKalman()
|
||||
{
|
||||
cvReleaseKalman(&m_pKalman);
|
||||
}
|
||||
CvBlob* CvBlobTrackPredictKalman::Predict()
|
||||
{
|
||||
if(m_Frame >= 2)
|
||||
{
|
||||
cvKalmanPredict(m_pKalman,0);
|
||||
m_BlobPredict.x = m_pKalman->state_pre->data.fl[0];
|
||||
m_BlobPredict.y = m_pKalman->state_pre->data.fl[1];
|
||||
m_BlobPredict.w = m_pKalman->state_pre->data.fl[2];
|
||||
m_BlobPredict.h = m_pKalman->state_pre->data.fl[3];
|
||||
}
|
||||
return &m_BlobPredict;
|
||||
}
|
||||
|
||||
void CvBlobTrackPredictKalman::Update(CvBlob* pBlob)
|
||||
{
|
||||
float Z[4];
|
||||
CvMat Zmat = cvMat(4,1,CV_32F,Z);
|
||||
m_BlobPredict = pBlob[0];
|
||||
if(m_Frame < 2)
|
||||
{/* first call */
|
||||
m_pKalman->state_post->data.fl[0+4] = CV_BLOB_X(pBlob)-m_pKalman->state_post->data.fl[0];
|
||||
m_pKalman->state_post->data.fl[1+4] = CV_BLOB_Y(pBlob)-m_pKalman->state_post->data.fl[1];
|
||||
if(m_pKalman->DP>6)
|
||||
{
|
||||
m_pKalman->state_post->data.fl[2+4] = CV_BLOB_WX(pBlob)-m_pKalman->state_post->data.fl[2];
|
||||
m_pKalman->state_post->data.fl[3+4] = CV_BLOB_WY(pBlob)-m_pKalman->state_post->data.fl[3];
|
||||
}
|
||||
m_pKalman->state_post->data.fl[0] = CV_BLOB_X(pBlob);
|
||||
m_pKalman->state_post->data.fl[1] = CV_BLOB_Y(pBlob);
|
||||
m_pKalman->state_post->data.fl[2] = CV_BLOB_WX(pBlob);
|
||||
m_pKalman->state_post->data.fl[3] = CV_BLOB_WY(pBlob);
|
||||
}
|
||||
else
|
||||
{/* another call */
|
||||
Z[0] = CV_BLOB_X(pBlob);
|
||||
Z[1] = CV_BLOB_Y(pBlob);
|
||||
Z[2] = CV_BLOB_WX(pBlob);
|
||||
Z[3] = CV_BLOB_WY(pBlob);
|
||||
cvKalmanCorrect(m_pKalman,&Zmat);
|
||||
}
|
||||
cvKalmanPredict(m_pKalman,0);
|
||||
m_Frame++;
|
||||
}/* update */
|
||||
|
||||
CvBlobTrackPredictor* cvCreateModuleBlobTrackPredictKalman()
|
||||
{
|
||||
return (CvBlobTrackPredictor*) new CvBlobTrackPredictKalman;
|
||||
}
|
||||
/*======================= KALMAN PREDICTOR =========================*/
|
||||
|
||||
@@ -0,0 +1,119 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
/*======================= TIME AVERAGING FILTER =========================*/
|
||||
#define TIME_WND 5
|
||||
class CvBlobTrackPostProcTimeAver:public CvBlobTrackPostProcOne
|
||||
{
|
||||
protected:
|
||||
CvBlob m_Blob;
|
||||
CvBlob m_pBlobs[TIME_WND];
|
||||
float m_Weights[TIME_WND];
|
||||
int m_Frame;
|
||||
public:
|
||||
CvBlobTrackPostProcTimeAver( int KernelType = 0)
|
||||
{
|
||||
int i;
|
||||
m_Frame = 0;
|
||||
for(i=0;i<TIME_WND;++i)
|
||||
{
|
||||
m_Weights[i] = 1;
|
||||
if(KernelType == 1)
|
||||
{
|
||||
m_Weights[i] = (float)exp((-2.3*i)/(TIME_WND-1)); /* last weight is 0.1 of first weight */
|
||||
}
|
||||
}
|
||||
};
|
||||
~CvBlobTrackPostProcTimeAver(){};
|
||||
CvBlob* Process(CvBlob* pBlob)
|
||||
{
|
||||
float WSum = 0;
|
||||
int i;
|
||||
int index = m_Frame % TIME_WND;
|
||||
int size = MIN((m_Frame+1), TIME_WND);
|
||||
m_pBlobs[index] = pBlob[0];
|
||||
m_Blob.x = m_Blob.y = m_Blob.w = m_Blob.h = 0;
|
||||
|
||||
for(i=0;i<size;++i)
|
||||
{
|
||||
float W = m_Weights[i];
|
||||
int index = (m_Frame - i + TIME_WND) % TIME_WND;
|
||||
m_Blob.x += W*m_pBlobs[index].x;
|
||||
m_Blob.y += W*m_pBlobs[index].y;
|
||||
m_Blob.w += W*m_pBlobs[index].w;
|
||||
m_Blob.h += W*m_pBlobs[index].h;
|
||||
WSum += W;
|
||||
}
|
||||
assert(WSum>0);
|
||||
|
||||
m_Blob.x /= WSum;
|
||||
m_Blob.y /= WSum;
|
||||
m_Blob.w /= WSum;
|
||||
m_Blob.h /= WSum;
|
||||
|
||||
m_Frame++;
|
||||
return &m_Blob;
|
||||
};
|
||||
void Release()
|
||||
{
|
||||
delete this;
|
||||
}
|
||||
}; /* class CvBlobTrackPostProcTimeAver */
|
||||
|
||||
CvBlobTrackPostProcOne* cvCreateModuleBlobTrackPostProcTimeAverRectOne()
|
||||
{
|
||||
return (CvBlobTrackPostProcOne*) new CvBlobTrackPostProcTimeAver(0);
|
||||
}
|
||||
CvBlobTrackPostProcOne* cvCreateModuleBlobTrackPostProcTimeAverExpOne()
|
||||
{
|
||||
return (CvBlobTrackPostProcOne*) new CvBlobTrackPostProcTimeAver(1);
|
||||
}
|
||||
|
||||
CvBlobTrackPostProc* cvCreateModuleBlobTrackPostProcTimeAverRect()
|
||||
{
|
||||
return cvCreateBlobTrackPostProcList(cvCreateModuleBlobTrackPostProcTimeAverRectOne);
|
||||
}
|
||||
CvBlobTrackPostProc* cvCreateModuleBlobTrackPostProcTimeAverExp()
|
||||
{
|
||||
return cvCreateBlobTrackPostProcList(cvCreateModuleBlobTrackPostProcTimeAverExpOne);
|
||||
}
|
||||
/*======================= KALMAN FILTER =========================*/
|
||||
@@ -0,0 +1,125 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
/*======================= FILTER LIST SHELL =====================*/
|
||||
typedef struct DefBlobFilter
|
||||
{
|
||||
CvBlob blob;
|
||||
CvBlobTrackPostProcOne* pFilter;
|
||||
int m_LastFrame;
|
||||
} DefBlobFilter;
|
||||
|
||||
class CvBlobTrackPostProcList : public CvBlobTrackPostProc
|
||||
{
|
||||
protected:
|
||||
CvBlobTrackPostProcOne* (*m_CreatePostProc)();
|
||||
CvBlobSeq m_BlobFilterList;
|
||||
int m_Frame;
|
||||
public:
|
||||
CvBlobTrackPostProcList(CvBlobTrackPostProcOne* (*create)()):m_BlobFilterList(sizeof(DefBlobFilter))
|
||||
{
|
||||
m_Frame = 0;
|
||||
m_CreatePostProc = create;
|
||||
CvBlobTrackPostProcOne* pM = create();
|
||||
TransferParamsFromChild(pM,NULL);
|
||||
pM->Release();
|
||||
}
|
||||
~CvBlobTrackPostProcList()
|
||||
{
|
||||
int i;
|
||||
for(i=m_BlobFilterList.GetBlobNum();i>0;--i)
|
||||
{
|
||||
DefBlobFilter* pF = (DefBlobFilter*)m_BlobFilterList.GetBlob(i-1);
|
||||
pF->pFilter->Release();
|
||||
}
|
||||
};
|
||||
virtual void AddBlob(CvBlob* pBlob)
|
||||
{
|
||||
DefBlobFilter* pF = (DefBlobFilter*)m_BlobFilterList.GetBlobByID(CV_BLOB_ID(pBlob));
|
||||
if(pF == NULL)
|
||||
{ /* create new filter */
|
||||
DefBlobFilter F;
|
||||
F.blob = pBlob[0];
|
||||
F.m_LastFrame = m_Frame;
|
||||
F.pFilter = m_CreatePostProc();
|
||||
TransferParamsToChild(F.pFilter,NULL);
|
||||
m_BlobFilterList.AddBlob((CvBlob*)&F);
|
||||
pF = (DefBlobFilter*)m_BlobFilterList.GetBlobByID(CV_BLOB_ID(pBlob));
|
||||
}
|
||||
|
||||
assert(pF);
|
||||
pF->blob = pBlob[0];
|
||||
pF->m_LastFrame = m_Frame;
|
||||
};
|
||||
virtual void Process()
|
||||
{
|
||||
int i;
|
||||
for(i=m_BlobFilterList.GetBlobNum();i>0;--i)
|
||||
{
|
||||
DefBlobFilter* pF = (DefBlobFilter*)m_BlobFilterList.GetBlob(i-1);
|
||||
if(pF->m_LastFrame == m_Frame)
|
||||
{/* process */
|
||||
int ID = CV_BLOB_ID(pF);
|
||||
pF->blob = *(pF->pFilter->Process(&(pF->blob)));
|
||||
CV_BLOB_ID(pF) = ID;
|
||||
}
|
||||
else
|
||||
{/* delete blob filter */
|
||||
pF->pFilter->Release();
|
||||
m_BlobFilterList.DelBlob(i-1);
|
||||
}
|
||||
}/* next blob */
|
||||
m_Frame++;
|
||||
};
|
||||
int GetBlobNum(){return m_BlobFilterList.GetBlobNum();};
|
||||
CvBlob* GetBlob(int index){return m_BlobFilterList.GetBlob(index);};
|
||||
void Release(){delete this;};
|
||||
|
||||
/* additional functionality */
|
||||
CvBlob* GetBlobByID(int BlobID){return m_BlobFilterList.GetBlobByID(BlobID);}
|
||||
}; /* CvBlobTrackPostProcList */
|
||||
|
||||
CvBlobTrackPostProc* cvCreateBlobTrackPostProcList(CvBlobTrackPostProcOne* (*create)())
|
||||
{
|
||||
return (CvBlobTrackPostProc*) new CvBlobTrackPostProcList(create);
|
||||
}
|
||||
/*======================= FILTER LIST SHELL =====================*/
|
||||
@@ -0,0 +1,991 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
/*
|
||||
This file contain implementation of virtual interface of CvBlobDetector
|
||||
this implementation based on simple algorithm
|
||||
new blob is detected when several successive frames contains connected componets
|
||||
which have uniform motion with not high speed.
|
||||
Also separation from border and already tracked blobs are considered.
|
||||
*/
|
||||
|
||||
//#define USE_OBJECT_DETECTOR
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
static int CompareContour(const void* a, const void* b, void* )
|
||||
{
|
||||
float dx,dy;
|
||||
float h,w,ht,wt;
|
||||
CvPoint2D32f pa,pb;
|
||||
CvRect ra,rb;
|
||||
CvSeq* pCA = *(CvSeq**)a;
|
||||
CvSeq* pCB = *(CvSeq**)b;
|
||||
ra = ((CvContour*)pCA)->rect;
|
||||
rb = ((CvContour*)pCB)->rect;
|
||||
pa.x = ra.x + ra.width*0.5f;
|
||||
pa.y = ra.y + ra.height*0.5f;
|
||||
pb.x = rb.x + rb.width*0.5f;
|
||||
pb.y = rb.y + rb.height*0.5f;
|
||||
w = (ra.width+rb.width)*0.5f;
|
||||
h = (ra.height+rb.height)*0.5f;
|
||||
|
||||
dx = (float)(fabs(pa.x - pb.x)-w);
|
||||
dy = (float)(fabs(pa.y - pb.y)-h);
|
||||
|
||||
//wt = MAX(ra.width,rb.width)*0.1f;
|
||||
wt = 0;
|
||||
ht = MAX(ra.height,rb.height)*0.3f;
|
||||
if(dx < wt && dy < ht) return 1;
|
||||
return 0;
|
||||
}
|
||||
void cvFindBlobsByCCClasters(IplImage* pFG, CvBlobSeq* pBlobs, CvMemStorage* storage)
|
||||
{/* create contours */
|
||||
IplImage* pIB = NULL;
|
||||
CvSeq* cnt = NULL;
|
||||
CvSeq* cnt_list = cvCreateSeq(0,sizeof(CvSeq),sizeof(CvSeq*), storage );
|
||||
CvSeq* clasters = NULL;
|
||||
int claster_cur, claster_num;
|
||||
|
||||
pIB = cvCloneImage(pFG);
|
||||
cvThreshold(pIB,pIB,128,255,CV_THRESH_BINARY);
|
||||
cvFindContours(pIB,storage, &cnt, sizeof(CvContour), CV_RETR_EXTERNAL);
|
||||
cvReleaseImage(&pIB);
|
||||
|
||||
/* create cnt_list*/
|
||||
/* process each contours*/
|
||||
for(;cnt;cnt=cnt->h_next)
|
||||
{
|
||||
cvSeqPush( cnt_list, &cnt);
|
||||
}
|
||||
|
||||
claster_num = cvSeqPartition( cnt_list, storage, &clasters, CompareContour, NULL );
|
||||
|
||||
for(claster_cur=0;claster_cur<claster_num;++claster_cur)
|
||||
{
|
||||
int cnt_cur;
|
||||
CvBlob NewBlob;
|
||||
double M00,X,Y,XX,YY; /* image moments */
|
||||
CvMoments m;
|
||||
CvRect rect_res = cvRect(-1,-1,-1,-1);
|
||||
CvMat mat;
|
||||
|
||||
for(cnt_cur=0;cnt_cur<clasters->total;++cnt_cur)
|
||||
{
|
||||
CvRect rect;
|
||||
CvSeq* cnt;
|
||||
int k = *(int*)cvGetSeqElem( clasters, cnt_cur );
|
||||
if(k!=claster_cur) continue;
|
||||
cnt = *(CvSeq**)cvGetSeqElem( cnt_list, cnt_cur );
|
||||
rect = ((CvContour*)cnt)->rect;
|
||||
|
||||
if(rect_res.height<0)
|
||||
{
|
||||
rect_res = rect;
|
||||
}
|
||||
else
|
||||
{/* unite rects */
|
||||
int x0,x1,y0,y1;
|
||||
x0 = MIN(rect_res.x,rect.x);
|
||||
y0 = MIN(rect_res.y,rect.y);
|
||||
x1 = MAX(rect_res.x+rect_res.width,rect.x+rect.width);
|
||||
y1 = MAX(rect_res.y+rect_res.height,rect.y+rect.height);
|
||||
rect_res.x = x0;
|
||||
rect_res.y = y0;
|
||||
rect_res.width = x1-x0;
|
||||
rect_res.height = y1-y0;
|
||||
}
|
||||
}
|
||||
|
||||
if(rect_res.height < 1 || rect_res.width < 1)
|
||||
{
|
||||
X = 0;
|
||||
Y = 0;
|
||||
XX = 0;
|
||||
YY = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
cvMoments( cvGetSubRect(pFG,&mat,rect_res), &m, 0 );
|
||||
M00 = cvGetSpatialMoment( &m, 0, 0 );
|
||||
if(M00 <= 0 ) continue;
|
||||
X = cvGetSpatialMoment( &m, 1, 0 )/M00;
|
||||
Y = cvGetSpatialMoment( &m, 0, 1 )/M00;
|
||||
XX = (cvGetSpatialMoment( &m, 2, 0 )/M00) - X*X;
|
||||
YY = (cvGetSpatialMoment( &m, 0, 2 )/M00) - Y*Y;
|
||||
}
|
||||
NewBlob = cvBlob(rect_res.x+(float)X,rect_res.y+(float)Y,(float)(4*sqrt(XX)),(float)(4*sqrt(YY)));
|
||||
pBlobs->AddBlob(&NewBlob);
|
||||
}/* next cluster */
|
||||
|
||||
#if 0
|
||||
{// debug info
|
||||
IplImage* pI = cvCreateImage(cvSize(pFG->width,pFG->height),IPL_DEPTH_8U,3);
|
||||
cvZero(pI);
|
||||
for(claster_cur=0;claster_cur<claster_num;++claster_cur)
|
||||
{
|
||||
int cnt_cur;
|
||||
CvScalar color = CV_RGB(rand()%256,rand()%256,rand()%256);
|
||||
for(cnt_cur=0;cnt_cur<clasters->total;++cnt_cur)
|
||||
{
|
||||
CvSeq* cnt;
|
||||
int k = *(int*)cvGetSeqElem( clasters, cnt_cur );
|
||||
if(k!=claster_cur) continue;
|
||||
cnt = *(CvSeq**)cvGetSeqElem( cnt_list, cnt_cur );
|
||||
cvDrawContours( pI, cnt, color, color, 0, 1, 8);
|
||||
|
||||
}
|
||||
CvBlob* pB = pBlobs->GetBlob(claster_cur);
|
||||
int x = cvRound(CV_BLOB_RX(pB)), y = cvRound(CV_BLOB_RY(pB));
|
||||
cvEllipse( pI,
|
||||
cvPointFrom32f(CV_BLOB_CENTER(pB)),
|
||||
cvSize(MAX(1,x), MAX(1,y)),
|
||||
0, 0, 360,
|
||||
color, 1 );
|
||||
}
|
||||
cvNamedWindow( "Clusters", 0);
|
||||
cvShowImage( "Clusters",pI );
|
||||
|
||||
cvReleaseImage(&pI);
|
||||
|
||||
}/* debug info */
|
||||
#endif
|
||||
}/* cvFindBlobsByCCClasters */
|
||||
|
||||
/* simple blob detector */
|
||||
/* numer of successive frame to analyse */
|
||||
#define EBD_FRAME_NUM 5
|
||||
class CvBlobDetectorSimple:public CvBlobDetector
|
||||
{
|
||||
public:
|
||||
CvBlobDetectorSimple();
|
||||
~CvBlobDetectorSimple();
|
||||
int DetectNewBlob(IplImage* pImg, IplImage* pFGMask, CvBlobSeq* pNewBlobList, CvBlobSeq* pOldBlobList);
|
||||
void Release(){delete this;};
|
||||
protected:
|
||||
IplImage* m_pMaskBlobNew;
|
||||
IplImage* m_pMaskBlobExist;
|
||||
/* lists of connected components detected on previouse frames */
|
||||
CvBlobSeq* m_pBlobLists[EBD_FRAME_NUM];
|
||||
};
|
||||
|
||||
/* Blob detector creator (sole interface function for this file) */
|
||||
CvBlobDetector* cvCreateBlobDetectorSimple(){return new CvBlobDetectorSimple;};
|
||||
|
||||
/* Constructor of BlobDetector */
|
||||
CvBlobDetectorSimple::CvBlobDetectorSimple()
|
||||
{
|
||||
int i = 0;
|
||||
m_pMaskBlobNew = NULL;
|
||||
m_pMaskBlobExist = NULL;
|
||||
for(i=0;i<EBD_FRAME_NUM;++i)m_pBlobLists[i] = NULL;
|
||||
}
|
||||
|
||||
/* destructor of BlobDetector*/
|
||||
CvBlobDetectorSimple::~CvBlobDetectorSimple()
|
||||
{
|
||||
int i;
|
||||
if(m_pMaskBlobExist) cvReleaseImage(&m_pMaskBlobExist);
|
||||
if(m_pMaskBlobNew) cvReleaseImage(&m_pMaskBlobNew);
|
||||
for(i=0;i<EBD_FRAME_NUM;++i)delete m_pBlobLists[i];
|
||||
}/* cvReleaseBlobDetector */
|
||||
|
||||
/* cvDetectNewBlobs return 1 and fill blob pNewBlob by blob parameters if new blob is detected */
|
||||
int CvBlobDetectorSimple::DetectNewBlob(IplImage* /*pImg*/, IplImage* pFGMask, CvBlobSeq* pNewBlobList, CvBlobSeq* pOldBlobList)
|
||||
{
|
||||
int res = 0;
|
||||
CvSize S = cvSize(pFGMask->width,pFGMask->height);
|
||||
if(m_pMaskBlobNew == NULL ) m_pMaskBlobNew = cvCreateImage(S,IPL_DEPTH_8U,1);
|
||||
if(m_pMaskBlobExist == NULL ) m_pMaskBlobExist = cvCreateImage(S,IPL_DEPTH_8U,1);
|
||||
|
||||
/* shift blob list */
|
||||
{
|
||||
int i;
|
||||
if(m_pBlobLists[0]) delete m_pBlobLists[0];
|
||||
for(i=1;i<EBD_FRAME_NUM;++i)m_pBlobLists[i-1]=m_pBlobLists[i];
|
||||
m_pBlobLists[EBD_FRAME_NUM-1] = new CvBlobSeq;
|
||||
}/* shift blob list */
|
||||
|
||||
/* create exist blob mask */
|
||||
cvCopy(pFGMask, m_pMaskBlobNew);
|
||||
|
||||
/* create contours and add new blobs to blob list */
|
||||
{/* create blobs */
|
||||
CvBlobSeq Blobs;
|
||||
CvMemStorage* storage = cvCreateMemStorage();
|
||||
|
||||
#if 1
|
||||
{/* glue contours */
|
||||
cvFindBlobsByCCClasters(m_pMaskBlobNew, &Blobs, storage );
|
||||
}/* glue contours */
|
||||
#else
|
||||
{ /**/
|
||||
IplImage* pIB = cvCloneImage(m_pMaskBlobNew);
|
||||
CvSeq* cnts = NULL;
|
||||
CvSeq* cnt = NULL;
|
||||
cvThreshold(pIB,pIB,128,255,CV_THRESH_BINARY);
|
||||
cvFindContours(pIB,storage, &cnts, sizeof(CvContour), CV_RETR_EXTERNAL);
|
||||
/* process each contours*/
|
||||
for(cnt = cnts;cnt;cnt=cnt->h_next)
|
||||
{
|
||||
CvBlob NewBlob;
|
||||
/* image moments */
|
||||
double M00,X,Y,XX,YY;
|
||||
CvMoments m;
|
||||
CvRect r = ((CvContour*)cnt)->rect;
|
||||
CvMat mat;
|
||||
if(r.height < S.height*0.02 || r.width < S.width*0.02) continue;
|
||||
cvMoments( cvGetSubRect(m_pMaskBlobNew,&mat,r), &m, 0 );
|
||||
M00 = cvGetSpatialMoment( &m, 0, 0 );
|
||||
if(M00 <= 0 ) continue;
|
||||
X = cvGetSpatialMoment( &m, 1, 0 )/M00;
|
||||
Y = cvGetSpatialMoment( &m, 0, 1 )/M00;
|
||||
XX = (cvGetSpatialMoment( &m, 2, 0 )/M00) - X*X;
|
||||
YY = (cvGetSpatialMoment( &m, 0, 2 )/M00) - Y*Y;
|
||||
NewBlob = cvBlob(r.x+(float)X,r.y+(float)Y,(float)(4*sqrt(XX)),(float)(4*sqrt(YY)));
|
||||
Blobs.AddBlob(&NewBlob);
|
||||
}/* next contour */
|
||||
cvReleaseImage(&pIB);
|
||||
}/* one contour - one blob */
|
||||
#endif
|
||||
|
||||
{/* Delete small and intersected blobs */
|
||||
int i;
|
||||
for(i=Blobs.GetBlobNum();i>0;i--)
|
||||
{
|
||||
CvBlob* pB = Blobs.GetBlob(i-1);
|
||||
|
||||
if(pB->h < S.height*0.02 || pB->w < S.width*0.02)
|
||||
{
|
||||
Blobs.DelBlob(i-1);
|
||||
continue;
|
||||
}
|
||||
if(pOldBlobList)
|
||||
{
|
||||
int j;
|
||||
for(j=pOldBlobList->GetBlobNum();j>0;j--)
|
||||
{
|
||||
CvBlob* pBOld = pOldBlobList->GetBlob(j-1);
|
||||
if((fabs(pBOld->x-pB->x) < (CV_BLOB_RX(pBOld)+CV_BLOB_RX(pB))) &&
|
||||
(fabs(pBOld->y-pB->y) < (CV_BLOB_RY(pBOld)+CV_BLOB_RY(pB))))
|
||||
{/* intersection is present, delete blob from list*/
|
||||
Blobs.DelBlob(i-1);
|
||||
break;
|
||||
}
|
||||
}/* checl next old blob */
|
||||
}/*if pOldBlobList */
|
||||
}/* check next blob */
|
||||
}/* Delete small and intersected blobs */
|
||||
|
||||
{/* bubble sort blobs by size */
|
||||
int N = Blobs.GetBlobNum();
|
||||
int i,j;
|
||||
for(i=1;i<N;++i)
|
||||
{
|
||||
for(j=i;j>0;--j)
|
||||
{
|
||||
CvBlob temp;
|
||||
float AreaP, AreaN;
|
||||
CvBlob* pP = Blobs.GetBlob(j-1);
|
||||
CvBlob* pN = Blobs.GetBlob(j);
|
||||
AreaP = CV_BLOB_WX(pP)*CV_BLOB_WY(pP);
|
||||
AreaN = CV_BLOB_WX(pN)*CV_BLOB_WY(pN);
|
||||
if(AreaN < AreaP)break;
|
||||
temp = pN[0];
|
||||
pN[0] = pP[0];
|
||||
pP[0] = temp;
|
||||
}
|
||||
}
|
||||
/* copy only first 10 blobs */
|
||||
for(i=0;i<MIN(N,10);++i)
|
||||
{
|
||||
m_pBlobLists[EBD_FRAME_NUM-1]->AddBlob(Blobs.GetBlob(i));
|
||||
}
|
||||
}/* sort blobs by size */
|
||||
cvReleaseMemStorage(&storage);
|
||||
}/* create Blobs */
|
||||
|
||||
/* analize blob list to find best blob trajectory */
|
||||
{/* analize blob list to find best blob trajectory */
|
||||
int Count = 0;
|
||||
int pBLIndex[EBD_FRAME_NUM];
|
||||
int pBL_BEST[EBD_FRAME_NUM];
|
||||
int i;
|
||||
int finish = 0;
|
||||
double BestError = -1;
|
||||
int Good = 1;
|
||||
for(i=0;i<EBD_FRAME_NUM;++i)
|
||||
{
|
||||
pBLIndex[i] = 0;
|
||||
pBL_BEST[i] = 0;
|
||||
}
|
||||
|
||||
/* check configuration exist */
|
||||
for(i=0;Good && (i<EBD_FRAME_NUM);++i)
|
||||
if(m_pBlobLists[i] == NULL || m_pBlobLists[i]->GetBlobNum() == 0)
|
||||
Good = 0;
|
||||
|
||||
if(Good)
|
||||
do{/* for each configuration */
|
||||
CvBlob* pBL[EBD_FRAME_NUM];
|
||||
int Good = 1;
|
||||
double Error = 0;
|
||||
CvBlob* pBNew = m_pBlobLists[EBD_FRAME_NUM-1]->GetBlob(pBLIndex[EBD_FRAME_NUM-1]);
|
||||
for(i=0;i<EBD_FRAME_NUM;++i)pBL[i] = m_pBlobLists[i]->GetBlob(pBLIndex[i]);
|
||||
|
||||
Count++;
|
||||
|
||||
/* check intersection last blob with existed */
|
||||
if(Good && pOldBlobList)
|
||||
{ /* check intersection last blob with existed */
|
||||
int k;
|
||||
for(k=pOldBlobList->GetBlobNum();k>0;--k)
|
||||
{
|
||||
CvBlob* pBOld = pOldBlobList->GetBlob(k-1);
|
||||
if((fabs(pBOld->x-pBNew->x) < (CV_BLOB_RX(pBOld)+CV_BLOB_RX(pBNew))) &&
|
||||
(fabs(pBOld->y-pBNew->y) < (CV_BLOB_RY(pBOld)+CV_BLOB_RY(pBNew))))
|
||||
Good = 0;
|
||||
}
|
||||
}/* check intersection last blob with existed */
|
||||
|
||||
/* check distance to image border */
|
||||
if(Good)
|
||||
{ /* check distance to image border */
|
||||
CvBlob* pB = pBNew;
|
||||
float dx = MIN(pB->x,S.width-pB->x)/CV_BLOB_RX(pB);
|
||||
float dy = MIN(pB->y,S.height-pB->y)/CV_BLOB_RY(pB);
|
||||
|
||||
if(dx < 1.1 || dy < 1.1) Good = 0;
|
||||
}/* check distance to image border */
|
||||
|
||||
/* check uniform moveing */
|
||||
if(Good)
|
||||
{/* check uniform moveing */
|
||||
int N = EBD_FRAME_NUM;
|
||||
float sum[2] = {0,0};
|
||||
float jsum[2] = {0,0};
|
||||
float a[2],b[2]; /* estimated parameters of moving x(t) = a*t+b*/
|
||||
int j;
|
||||
|
||||
for(j=0;j<N;++j)
|
||||
{
|
||||
float x = pBL[j]->x;
|
||||
float y = pBL[j]->y;
|
||||
sum[0] += x;
|
||||
jsum[0] += j*x;
|
||||
sum[1] += y;
|
||||
jsum[1] += j*y;
|
||||
}
|
||||
a[0] = 6*((1-N)*sum[0]+2*jsum[0])/(N*(N*N-1));
|
||||
b[0] = -2*((1-2*N)*sum[0]+3*jsum[0])/(N*(N+1));
|
||||
a[1] = 6*((1-N)*sum[1]+2*jsum[1])/(N*(N*N-1));
|
||||
b[1] = -2*((1-2*N)*sum[1]+3*jsum[1])/(N*(N+1));
|
||||
for(j=0;j<N;++j)
|
||||
{
|
||||
Error +=
|
||||
pow(a[0]*j+b[0]-pBL[j]->x,2)+
|
||||
pow(a[1]*j+b[1]-pBL[j]->y,2);
|
||||
}
|
||||
Error = sqrt(Error/N);
|
||||
if( Error > S.width*0.01 ||
|
||||
fabs(a[0])>S.width*0.1 ||
|
||||
fabs(a[1])>S.height*0.1)
|
||||
Good = 0;
|
||||
}/* check configuration */
|
||||
|
||||
|
||||
/* new best trajectory */
|
||||
if(Good && (BestError == -1 || BestError > Error))
|
||||
{/* new best trajectory */
|
||||
for(i=0;i<EBD_FRAME_NUM;++i)
|
||||
{
|
||||
pBL_BEST[i] = pBLIndex[i];
|
||||
}
|
||||
BestError = Error;
|
||||
}/* new best trajectory */
|
||||
|
||||
/* set next configuration */
|
||||
for(i=0;i<EBD_FRAME_NUM;++i)
|
||||
{
|
||||
pBLIndex[i]++;
|
||||
if(pBLIndex[i] != m_pBlobLists[i]->GetBlobNum()) break;
|
||||
pBLIndex[i]=0;
|
||||
}/* next time shift */
|
||||
if(i==EBD_FRAME_NUM)finish=1;
|
||||
}while(!finish); /* check next time configuration of connected components */
|
||||
|
||||
#if 0
|
||||
{/**/
|
||||
printf("BlobDetector configurations = %d [",Count);
|
||||
int i;
|
||||
for(i=0;i<EBD_FRAME_NUM;++i)
|
||||
{
|
||||
printf("%d,",m_pBlobLists[i]?m_pBlobLists[i]->GetBlobNum():0);
|
||||
}
|
||||
printf("]\n");
|
||||
|
||||
}
|
||||
#endif
|
||||
|
||||
if(BestError != -1)
|
||||
{/* put new blob to output and delete from blob list */
|
||||
CvBlob* pNewBlob = m_pBlobLists[EBD_FRAME_NUM-1]->GetBlob(pBL_BEST[EBD_FRAME_NUM-1]);
|
||||
pNewBlobList->AddBlob(pNewBlob);
|
||||
for(i=0;i<EBD_FRAME_NUM;++i)
|
||||
{/* remove blob from each list */
|
||||
m_pBlobLists[i]->DelBlob(pBL_BEST[i]);
|
||||
}/* remove blob from each list */
|
||||
res = 1;
|
||||
}/* put new blob to output and delete from blob list */
|
||||
}/* analize blod list to find best blob trajectory */
|
||||
|
||||
return res;
|
||||
}/* cvDetectNewBlob */
|
||||
|
||||
|
||||
|
||||
|
||||
/* simple blob detector2 */
|
||||
/* numer of successive frame to analyse */
|
||||
#define SEQ_SIZE_MAX 30
|
||||
#define SEQ_NUM 1000
|
||||
typedef struct
|
||||
{
|
||||
int size;
|
||||
CvBlob* pBlobs[SEQ_SIZE_MAX];
|
||||
} DefSeq;
|
||||
class CvBlobDetectorCC:public CvBlobDetector
|
||||
{
|
||||
public:
|
||||
CvBlobDetectorCC();
|
||||
~CvBlobDetectorCC();
|
||||
int DetectNewBlob(IplImage* pImg, IplImage* pFGMask, CvBlobSeq* pNewBlobList, CvBlobSeq* pOldBlobList);
|
||||
void Release(){delete this;};
|
||||
virtual void ParamUpdate()
|
||||
{
|
||||
if(SEQ_SIZE<1)SEQ_SIZE=1;
|
||||
if(SEQ_SIZE>SEQ_SIZE_MAX)SEQ_SIZE=SEQ_SIZE_MAX;
|
||||
|
||||
#ifdef USE_OBJECT_DETECTOR
|
||||
if( m_param_split_detector_file_name )
|
||||
{
|
||||
m_split_detector = new CvObjectDetector();
|
||||
if( !m_split_detector->Load( m_param_split_detector_file_name ) )
|
||||
{
|
||||
delete m_split_detector;
|
||||
m_split_detector = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
m_min_window_size = m_split_detector->GetMinWindowSize();
|
||||
m_max_border = m_split_detector->GetMaxBorderSize();
|
||||
}
|
||||
}
|
||||
#endif
|
||||
}
|
||||
private:
|
||||
/* lists of connected components detected on previouse frames */
|
||||
CvBlobSeq* m_pBlobLists[SEQ_SIZE_MAX];
|
||||
DefSeq m_TrackSeq[SEQ_NUM];
|
||||
int m_TrackNum;
|
||||
float m_HMin;
|
||||
float m_WMin;
|
||||
float m_MinDistToBorder;
|
||||
int m_Clastering;
|
||||
int SEQ_SIZE;
|
||||
|
||||
/* if not 0 then the detector is loaded from the specified file
|
||||
and it is applied for splitting blobs which actually correspond
|
||||
to groups of objects */
|
||||
char* m_param_split_detector_file_name;
|
||||
float m_param_roi_scale;
|
||||
int m_param_only_roi;
|
||||
|
||||
CvObjectDetector* m_split_detector;
|
||||
CvSize m_min_window_size;
|
||||
int m_max_border;
|
||||
|
||||
CvBlobSeq m_detected_blob_seq;
|
||||
CvSeq* m_roi_seq;
|
||||
|
||||
CvBlobSeq m_debug_blob_seq;
|
||||
};
|
||||
|
||||
/* Blob detector creator (sole interface function for this file) */
|
||||
CvBlobDetector* cvCreateBlobDetectorCC(){return new CvBlobDetectorCC;}
|
||||
|
||||
/* Constructor of BlobDetector */
|
||||
CvBlobDetectorCC::CvBlobDetectorCC() :
|
||||
m_split_detector(0),
|
||||
m_detected_blob_seq(sizeof(CvDetectedBlob)),
|
||||
m_roi_seq(0),
|
||||
m_debug_blob_seq(sizeof(CvDetectedBlob))
|
||||
{
|
||||
/*CvDrawShape shapes[] =
|
||||
{
|
||||
{ CvDrawShape::RECT, {{255,255,255}} },
|
||||
{ CvDrawShape::RECT, {{0,0,255}} },
|
||||
{ CvDrawShape::ELLIPSE, {{0,255,0}} }
|
||||
};
|
||||
int num_shapes = sizeof(shapes) / sizeof(shapes[0]);*/
|
||||
|
||||
int i = 0;
|
||||
SEQ_SIZE = 10;
|
||||
AddParam("Latency",&SEQ_SIZE);
|
||||
for(i=0;i<SEQ_SIZE_MAX;++i)m_pBlobLists[i] = NULL;
|
||||
for(i=0;i<SEQ_NUM;++i)m_TrackSeq[i].size = 0;
|
||||
m_TrackNum = 0;
|
||||
|
||||
m_HMin = 0.02f;
|
||||
m_WMin = 0.01f;
|
||||
AddParam("HMin",&m_HMin);
|
||||
AddParam("WMin",&m_WMin);
|
||||
m_MinDistToBorder = 1.1f;
|
||||
AddParam("MinDistToBorder",&m_MinDistToBorder);
|
||||
CommentParam("MinDistToBorder","Minimal allowed distance from blob center to image border in blob sizes");
|
||||
|
||||
m_Clastering=1;
|
||||
AddParam("Clastering",&m_Clastering);
|
||||
CommentParam("Clastering","Minimal allowed distance from blob center to image border in blob sizes");
|
||||
|
||||
m_param_split_detector_file_name = 0;
|
||||
#ifdef USE_OBJECT_DETECTOR
|
||||
AddParam("Detector", &m_param_split_detector_file_name);
|
||||
CommentParam("Detector", "Detector file name");
|
||||
#endif
|
||||
|
||||
m_param_roi_scale = 1.5F;
|
||||
AddParam("ROIScale", &m_param_roi_scale);
|
||||
CommentParam("ROIScale", "Determines the size of search window around a blob");
|
||||
|
||||
m_param_only_roi = 1;
|
||||
AddParam("OnlyROI", &m_param_only_roi);
|
||||
CommentParam("OnlyROI", "Shows the whole debug image (0) or only ROIs where the detector was applied (1)");
|
||||
|
||||
m_min_window_size = cvSize(0,0);
|
||||
m_max_border = 0;
|
||||
m_roi_seq = cvCreateSeq( 0, sizeof(*m_roi_seq), sizeof(CvRect), cvCreateMemStorage() );
|
||||
|
||||
SetModuleName("BD_CC");
|
||||
|
||||
}
|
||||
|
||||
/* destructor of BlobDetector*/
|
||||
CvBlobDetectorCC::~CvBlobDetectorCC()
|
||||
{
|
||||
int i;
|
||||
for(i=0;i<SEQ_SIZE_MAX;++i)
|
||||
{
|
||||
if(m_pBlobLists[i])
|
||||
delete m_pBlobLists[i];
|
||||
}
|
||||
|
||||
if( m_roi_seq )
|
||||
{
|
||||
cvReleaseMemStorage( &m_roi_seq->storage );
|
||||
m_roi_seq = 0;
|
||||
}
|
||||
//cvDestroyWindow( "EnteringBlobDetectionDebug" );
|
||||
}/* cvReleaseBlobDetector */
|
||||
|
||||
|
||||
/* cvDetectNewBlobs return 1 and fill blob pNewBlob by blob parameters if new blob is detected */
|
||||
int CvBlobDetectorCC::DetectNewBlob(IplImage* /*pImg*/, IplImage* pFGMask, CvBlobSeq* pNewBlobList, CvBlobSeq* pOldBlobList)
|
||||
{
|
||||
int res = 0;
|
||||
CvSize S = cvSize(pFGMask->width,pFGMask->height);
|
||||
|
||||
/* shift blob list */
|
||||
{
|
||||
int i;
|
||||
if(m_pBlobLists[SEQ_SIZE-1]) delete m_pBlobLists[SEQ_SIZE-1];
|
||||
for(i=SEQ_SIZE-1;i>0;--i)m_pBlobLists[i]=m_pBlobLists[i-1];
|
||||
m_pBlobLists[0] = new CvBlobSeq;
|
||||
}/* shift blob list */
|
||||
|
||||
/* create contours and add new blobs to blob list */
|
||||
{/* create blobs */
|
||||
CvBlobSeq Blobs;
|
||||
CvMemStorage* storage = cvCreateMemStorage();
|
||||
|
||||
if(m_Clastering)
|
||||
{/* glue contours */
|
||||
cvFindBlobsByCCClasters(pFGMask, &Blobs, storage );
|
||||
}/* glue contours */
|
||||
else
|
||||
{ /**/
|
||||
IplImage* pIB = cvCloneImage(pFGMask);
|
||||
CvSeq* cnts = NULL;
|
||||
CvSeq* cnt = NULL;
|
||||
cvThreshold(pIB,pIB,128,255,CV_THRESH_BINARY);
|
||||
cvFindContours(pIB,storage, &cnts, sizeof(CvContour), CV_RETR_EXTERNAL);
|
||||
/* process each contours*/
|
||||
for(cnt = cnts;cnt;cnt=cnt->h_next)
|
||||
{
|
||||
CvBlob NewBlob;
|
||||
/* image moments */
|
||||
double M00,X,Y,XX,YY;
|
||||
CvMoments m;
|
||||
CvRect r = ((CvContour*)cnt)->rect;
|
||||
CvMat mat;
|
||||
if(r.height < S.height*m_HMin || r.width < S.width*m_WMin) continue;
|
||||
cvMoments( cvGetSubRect(pFGMask,&mat,r), &m, 0 );
|
||||
M00 = cvGetSpatialMoment( &m, 0, 0 );
|
||||
if(M00 <= 0 ) continue;
|
||||
X = cvGetSpatialMoment( &m, 1, 0 )/M00;
|
||||
Y = cvGetSpatialMoment( &m, 0, 1 )/M00;
|
||||
XX = (cvGetSpatialMoment( &m, 2, 0 )/M00) - X*X;
|
||||
YY = (cvGetSpatialMoment( &m, 0, 2 )/M00) - Y*Y;
|
||||
NewBlob = cvBlob(r.x+(float)X,r.y+(float)Y,(float)(4*sqrt(XX)),(float)(4*sqrt(YY)));
|
||||
Blobs.AddBlob(&NewBlob);
|
||||
}/* next contour */
|
||||
cvReleaseImage(&pIB);
|
||||
}/* one contour - one blob */
|
||||
|
||||
{/* Delete small and intersected blobs */
|
||||
int i;
|
||||
for(i=Blobs.GetBlobNum();i>0;i--)
|
||||
{
|
||||
CvBlob* pB = Blobs.GetBlob(i-1);
|
||||
|
||||
if(pB->h < S.height*m_HMin || pB->w < S.width*m_WMin)
|
||||
{
|
||||
Blobs.DelBlob(i-1);
|
||||
continue;
|
||||
}
|
||||
if(pOldBlobList)
|
||||
{
|
||||
int j;
|
||||
for(j=pOldBlobList->GetBlobNum();j>0;j--)
|
||||
{
|
||||
CvBlob* pBOld = pOldBlobList->GetBlob(j-1);
|
||||
if((fabs(pBOld->x-pB->x) < (CV_BLOB_RX(pBOld)+CV_BLOB_RX(pB))) &&
|
||||
(fabs(pBOld->y-pB->y) < (CV_BLOB_RY(pBOld)+CV_BLOB_RY(pB))))
|
||||
{/* intersection is present, delete blob from list*/
|
||||
Blobs.DelBlob(i-1);
|
||||
break;
|
||||
}
|
||||
}/* checl next old blob */
|
||||
}/*if pOldBlobList */
|
||||
}/* check next blob */
|
||||
}/* Delete small and intersected blobs */
|
||||
|
||||
{/* bubble sort blobs by size */
|
||||
int N = Blobs.GetBlobNum();
|
||||
int i,j;
|
||||
for(i=1;i<N;++i)
|
||||
{
|
||||
for(j=i;j>0;--j)
|
||||
{
|
||||
CvBlob temp;
|
||||
float AreaP, AreaN;
|
||||
CvBlob* pP = Blobs.GetBlob(j-1);
|
||||
CvBlob* pN = Blobs.GetBlob(j);
|
||||
AreaP = CV_BLOB_WX(pP)*CV_BLOB_WY(pP);
|
||||
AreaN = CV_BLOB_WX(pN)*CV_BLOB_WY(pN);
|
||||
if(AreaN < AreaP)break;
|
||||
temp = pN[0];
|
||||
pN[0] = pP[0];
|
||||
pP[0] = temp;
|
||||
}
|
||||
}
|
||||
/* copy only first 10 blobs */
|
||||
for(i=0;i<MIN(N,10);++i)
|
||||
{
|
||||
m_pBlobLists[0]->AddBlob(Blobs.GetBlob(i));
|
||||
}
|
||||
}/* sort blobs by size */
|
||||
cvReleaseMemStorage(&storage);
|
||||
}/* create Blobs */
|
||||
|
||||
{/* shift each track */
|
||||
int j;
|
||||
for(j=0;j<m_TrackNum;++j)
|
||||
{
|
||||
int i;
|
||||
DefSeq* pTrack = m_TrackSeq+j;
|
||||
for(i=SEQ_SIZE-1;i>0;--i)pTrack->pBlobs[i]=pTrack->pBlobs[i-1];
|
||||
pTrack->pBlobs[0] = NULL;
|
||||
if(pTrack->size == SEQ_SIZE)pTrack->size--;
|
||||
}
|
||||
}/* shift each track */
|
||||
|
||||
/* analize blob list to find best blob trajectory */
|
||||
{/* analize blob list to find best blob trajectory */
|
||||
double BestError = -1;
|
||||
int BestTrack = -1;;
|
||||
CvBlobSeq* pNewBlobs = m_pBlobLists[0];
|
||||
int i;
|
||||
int NewTrackNum = 0;
|
||||
for(i=pNewBlobs->GetBlobNum();i>0;--i)
|
||||
{
|
||||
CvBlob* pBNew = pNewBlobs->GetBlob(i-1);
|
||||
int j;
|
||||
int AsignedTrack = 0;
|
||||
for(j=0;j<m_TrackNum;++j)
|
||||
{
|
||||
double dx,dy;
|
||||
DefSeq* pTrack = m_TrackSeq+j;
|
||||
CvBlob* pLastBlob = pTrack->size>0?pTrack->pBlobs[1]:NULL;
|
||||
if(pLastBlob == NULL) continue;
|
||||
dx = fabs(CV_BLOB_X(pLastBlob)-CV_BLOB_X(pBNew));
|
||||
dy = fabs(CV_BLOB_Y(pLastBlob)-CV_BLOB_Y(pBNew));
|
||||
if(dx > 2*CV_BLOB_WX(pLastBlob) || dy > 2*CV_BLOB_WY(pLastBlob)) continue;
|
||||
AsignedTrack++;
|
||||
if(pTrack->pBlobs[0]==NULL)
|
||||
{/*fill existed track */
|
||||
pTrack->pBlobs[0] = pBNew;
|
||||
pTrack->size++;
|
||||
}
|
||||
else if((m_TrackNum+NewTrackNum)<SEQ_NUM)
|
||||
{ /* duplicate existed track */
|
||||
m_TrackSeq[m_TrackNum+NewTrackNum] = pTrack[0];
|
||||
m_TrackSeq[m_TrackNum+NewTrackNum].pBlobs[0] = pBNew;
|
||||
NewTrackNum++;
|
||||
}
|
||||
}/* next track */
|
||||
|
||||
if(AsignedTrack==0 && (m_TrackNum+NewTrackNum)<SEQ_NUM )
|
||||
{/* init new track */
|
||||
m_TrackSeq[m_TrackNum+NewTrackNum].size = 1;
|
||||
m_TrackSeq[m_TrackNum+NewTrackNum].pBlobs[0] = pBNew;
|
||||
NewTrackNum++;
|
||||
}
|
||||
}/* next new blob */
|
||||
|
||||
m_TrackNum += NewTrackNum;
|
||||
|
||||
/* check each track */
|
||||
for(i=0;i<m_TrackNum;++i)
|
||||
{
|
||||
int Good = 1;
|
||||
DefSeq* pTrack = m_TrackSeq+i;
|
||||
CvBlob* pBNew = pTrack->pBlobs[0];
|
||||
if(pTrack->size != SEQ_SIZE) continue;
|
||||
if(pBNew == NULL ) continue;
|
||||
|
||||
/* check intersection last blob with existed */
|
||||
if(Good && pOldBlobList)
|
||||
{ /* check intersection last blob with existed */
|
||||
int k;
|
||||
for(k=pOldBlobList->GetBlobNum();k>0;--k)
|
||||
{
|
||||
CvBlob* pBOld = pOldBlobList->GetBlob(k-1);
|
||||
if((fabs(pBOld->x-pBNew->x) < (CV_BLOB_RX(pBOld)+CV_BLOB_RX(pBNew))) &&
|
||||
(fabs(pBOld->y-pBNew->y) < (CV_BLOB_RY(pBOld)+CV_BLOB_RY(pBNew))))
|
||||
Good = 0;
|
||||
}
|
||||
}/* check intersection last blob with existed */
|
||||
|
||||
/* check distance to image border */
|
||||
if(Good)
|
||||
{ /* check distance to image border */
|
||||
float dx = MIN(pBNew->x,S.width-pBNew->x)/CV_BLOB_RX(pBNew);
|
||||
float dy = MIN(pBNew->y,S.height-pBNew->y)/CV_BLOB_RY(pBNew);
|
||||
if(dx < m_MinDistToBorder || dy < m_MinDistToBorder) Good = 0;
|
||||
}/* check distance to image border */
|
||||
|
||||
/* check uniform moveing */
|
||||
if(Good)
|
||||
{/* check uniform moveing */
|
||||
double Error = 0;
|
||||
int N = pTrack->size;
|
||||
CvBlob** pBL = pTrack->pBlobs;
|
||||
float sum[2] = {0,0};
|
||||
float jsum[2] = {0,0};
|
||||
float a[2],b[2]; /* estimated parameters of moving x(t) = a*t+b*/
|
||||
int j;
|
||||
|
||||
for(j=0;j<N;++j)
|
||||
{
|
||||
float x = pBL[j]->x;
|
||||
float y = pBL[j]->y;
|
||||
sum[0] += x;
|
||||
jsum[0] += j*x;
|
||||
sum[1] += y;
|
||||
jsum[1] += j*y;
|
||||
}
|
||||
a[0] = 6*((1-N)*sum[0]+2*jsum[0])/(N*(N*N-1));
|
||||
b[0] = -2*((1-2*N)*sum[0]+3*jsum[0])/(N*(N+1));
|
||||
a[1] = 6*((1-N)*sum[1]+2*jsum[1])/(N*(N*N-1));
|
||||
b[1] = -2*((1-2*N)*sum[1]+3*jsum[1])/(N*(N+1));
|
||||
for(j=0;j<N;++j)
|
||||
{
|
||||
Error +=
|
||||
pow(a[0]*j+b[0]-pBL[j]->x,2)+
|
||||
pow(a[1]*j+b[1]-pBL[j]->y,2);
|
||||
}
|
||||
Error = sqrt(Error/N);
|
||||
if( Error > S.width*0.01 ||
|
||||
fabs(a[0])>S.width*0.1 ||
|
||||
fabs(a[1])>S.height*0.1)
|
||||
Good = 0;
|
||||
|
||||
/* new best trajectory */
|
||||
if(Good && (BestError == -1 || BestError > Error))
|
||||
{/* new best trajectory */
|
||||
BestTrack = i;
|
||||
BestError = Error;
|
||||
}/* new best trajectory */
|
||||
}/* check uniform moveing */
|
||||
}/* next track */
|
||||
|
||||
#if 0
|
||||
{/**/
|
||||
printf("BlobDetector configurations = %d [",m_TrackNum);
|
||||
int i;
|
||||
for(i=0;i<SEQ_SIZE;++i)
|
||||
{
|
||||
printf("%d,",m_pBlobLists[i]?m_pBlobLists[i]->GetBlobNum():0);
|
||||
}
|
||||
printf("]\n");
|
||||
|
||||
}
|
||||
#endif
|
||||
|
||||
if(BestTrack >= 0)
|
||||
{/* put new blob to output and delete from blob list */
|
||||
assert(m_TrackSeq[BestTrack].size == SEQ_SIZE);
|
||||
assert(m_TrackSeq[BestTrack].pBlobs[0]);
|
||||
pNewBlobList->AddBlob(m_TrackSeq[BestTrack].pBlobs[0]);
|
||||
m_TrackSeq[BestTrack].pBlobs[0] = NULL;
|
||||
m_TrackSeq[BestTrack].size--;
|
||||
res = 1;
|
||||
}/* put new blob to output and mark in blob list to delete*/
|
||||
}/* analize blod list to find best blob trajectory */
|
||||
|
||||
{/* delete bad tracks */
|
||||
int i;
|
||||
for(i=m_TrackNum-1;i>=0;--i)
|
||||
{/* delete bad tracks */
|
||||
if(m_TrackSeq[i].pBlobs[0]) continue;
|
||||
if(m_TrackNum>0)
|
||||
m_TrackSeq[i] = m_TrackSeq[--m_TrackNum];
|
||||
}/* delete bad tracks */
|
||||
}
|
||||
|
||||
#ifdef USE_OBJECT_DETECTOR
|
||||
if( m_split_detector && pNewBlobList->GetBlobNum() > 0 )
|
||||
{
|
||||
int num_new_blobs = pNewBlobList->GetBlobNum();
|
||||
int i = 0;
|
||||
|
||||
if( m_roi_seq ) cvClearSeq( m_roi_seq );
|
||||
m_debug_blob_seq.Clear();
|
||||
for( i = 0; i < num_new_blobs; ++i )
|
||||
{
|
||||
CvBlob* b = pNewBlobList->GetBlob(i);
|
||||
CvMat roi_stub;
|
||||
CvMat* roi_mat = 0;
|
||||
CvMat* scaled_roi_mat = 0;
|
||||
|
||||
CvDetectedBlob d_b = cvDetectedBlob( CV_BLOB_X(b), CV_BLOB_Y(b), CV_BLOB_WX(b), CV_BLOB_WY(b), 0 );
|
||||
m_debug_blob_seq.AddBlob(&d_b);
|
||||
|
||||
float scale = m_param_roi_scale * m_min_window_size.height / CV_BLOB_WY(b);
|
||||
|
||||
float b_width = MAX(CV_BLOB_WX(b), m_min_window_size.width / scale)
|
||||
+ (m_param_roi_scale - 1.0F) * (m_min_window_size.width / scale)
|
||||
+ 2.0F * m_max_border / scale;
|
||||
float b_height = CV_BLOB_WY(b) * m_param_roi_scale + 2.0F * m_max_border / scale;
|
||||
|
||||
CvRect roi = cvRectIntersection( cvRect( cvFloor(CV_BLOB_X(b) - 0.5F*b_width),
|
||||
cvFloor(CV_BLOB_Y(b) - 0.5F*b_height),
|
||||
cvCeil(b_width), cvCeil(b_height) ),
|
||||
cvRect( 0, 0, pImg->width, pImg->height ) );
|
||||
if( roi.width <= 0 || roi.height <= 0 )
|
||||
continue;
|
||||
|
||||
if( m_roi_seq ) cvSeqPush( m_roi_seq, &roi );
|
||||
|
||||
roi_mat = cvGetSubRect( pImg, &roi_stub, roi );
|
||||
scaled_roi_mat = cvCreateMat( cvCeil(scale*roi.height), cvCeil(scale*roi.width), CV_8UC3 );
|
||||
cvResize( roi_mat, scaled_roi_mat );
|
||||
|
||||
m_detected_blob_seq.Clear();
|
||||
m_split_detector->Detect( scaled_roi_mat, &m_detected_blob_seq );
|
||||
cvReleaseMat( &scaled_roi_mat );
|
||||
|
||||
for( int k = 0; k < m_detected_blob_seq.GetBlobNum(); ++k )
|
||||
{
|
||||
CvDetectedBlob* b = (CvDetectedBlob*) m_detected_blob_seq.GetBlob(k);
|
||||
|
||||
/* scale and shift each detected blob back to the original image coordinates */
|
||||
CV_BLOB_X(b) = CV_BLOB_X(b) / scale + roi.x;
|
||||
CV_BLOB_Y(b) = CV_BLOB_Y(b) / scale + roi.y;
|
||||
CV_BLOB_WX(b) /= scale;
|
||||
CV_BLOB_WY(b) /= scale;
|
||||
|
||||
CvDetectedBlob d_b = cvDetectedBlob( CV_BLOB_X(b), CV_BLOB_Y(b), CV_BLOB_WX(b), CV_BLOB_WY(b), 1,
|
||||
b->response );
|
||||
m_debug_blob_seq.AddBlob(&d_b);
|
||||
}
|
||||
|
||||
if( m_detected_blob_seq.GetBlobNum() > 1 )
|
||||
{
|
||||
/*
|
||||
* Split blob
|
||||
* The original blob is replaced by the first detected blob,
|
||||
* remaining detected blobs are added to the end of the sequence
|
||||
*/
|
||||
CvBlob* first_b = m_detected_blob_seq.GetBlob(0);
|
||||
CV_BLOB_X(b) = CV_BLOB_X(first_b); CV_BLOB_Y(b) = CV_BLOB_Y(first_b);
|
||||
CV_BLOB_WX(b) = CV_BLOB_WX(first_b); CV_BLOB_WY(b) = CV_BLOB_WY(first_b);
|
||||
|
||||
for( int j = 1; j < m_detected_blob_seq.GetBlobNum(); ++j )
|
||||
{
|
||||
CvBlob* detected_b = m_detected_blob_seq.GetBlob(j);
|
||||
pNewBlobList->AddBlob(detected_b);
|
||||
}
|
||||
}
|
||||
} /* for each new blob */
|
||||
for( i = 0; i < pNewBlobList->GetBlobNum(); ++i )
|
||||
{
|
||||
CvBlob* b = pNewBlobList->GetBlob(i);
|
||||
CvDetectedBlob d_b = cvDetectedBlob( CV_BLOB_X(b), CV_BLOB_Y(b), CV_BLOB_WX(b), CV_BLOB_WY(b), 2 );
|
||||
m_debug_blob_seq.AddBlob(&d_b);
|
||||
}
|
||||
} // if( m_split_detector )
|
||||
#endif
|
||||
|
||||
return res;
|
||||
}/* cvDetectNewBlob */
|
||||
|
||||
|
||||
@@ -0,0 +1,158 @@
|
||||
/*M///////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
|
||||
//
|
||||
// By downloading, copying, installing or using the software you agree to this license.
|
||||
// If you do not agree to this license, do not download, install,
|
||||
// copy or use the software.
|
||||
//
|
||||
//
|
||||
// Intel License Agreement
|
||||
//
|
||||
// Copyright (C) 2000, Intel Corporation, all rights reserved.
|
||||
// Third party copyrights are property of their respective owners.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without modification,
|
||||
// are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistribution's of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Redistribution's in binary form must reproduce the above copyright notice,
|
||||
// this list of conditions and the following disclaimer in the documentation
|
||||
// and/or other materials provided with the distribution.
|
||||
//
|
||||
// * The name of Intel Corporation may not be used to endorse or promote products
|
||||
// derived from this software without specific prior written permission.
|
||||
//
|
||||
// This software is provided by the copyright holders and contributors "as is" and
|
||||
// any express or implied warranties, including, but not limited to, the implied
|
||||
// warranties of merchantability and fitness for a particular purpose are disclaimed.
|
||||
// In no event shall the Intel Corporation or contributors be liable for any direct,
|
||||
// indirect, incidental, special, exemplary, or consequential damages
|
||||
// (including, but not limited to, procurement of substitute goods or services;
|
||||
// loss of use, data, or profits; or business interruption) however caused
|
||||
// and on any theory of liability, whether in contract, strict liability,
|
||||
// or tort (including negligence or otherwise) arising in any way out of
|
||||
// the use of this software, even if advised of the possibility of such damage.
|
||||
//
|
||||
//M*/
|
||||
|
||||
/*
|
||||
This file contain implementation of virtual interface of CvBlobDetector
|
||||
this implementation based on simple algorithm
|
||||
new blob is detected when several successive frames contains connected componets
|
||||
which have uniform motion with not high speed.
|
||||
Also separation from border and already tracked blobs are considered.
|
||||
*/
|
||||
|
||||
#include "_cvaux.h"
|
||||
|
||||
/* blob detector based on real data (groundtruth data)*/
|
||||
class CvBlobDetectorReal:public CvBlobDetector
|
||||
{
|
||||
protected:
|
||||
CvTestSeq* m_pTestSeq;
|
||||
CvBlobSeq m_DetectedBlobs;
|
||||
CvMemStorage* m_pMem;
|
||||
public:
|
||||
CvBlobDetectorReal(CvTestSeq* pTestSeq)
|
||||
{
|
||||
m_pTestSeq = pTestSeq;
|
||||
m_pMem = cvCreateMemStorage(0);
|
||||
}
|
||||
/* destructor of BlobDetector*/
|
||||
~CvBlobDetectorReal()
|
||||
{
|
||||
if(m_pMem) cvReleaseMemStorage(&m_pMem);
|
||||
}/* cvReleaseBlobDetector */
|
||||
|
||||
/* cvDetectNewBlobs return 1 and fill blob pNewBlob by blob parameters if new blob is detected */
|
||||
int DetectNewBlob(IplImage* /*pImg*/, IplImage* /*pFGMask*/, CvBlobSeq* pNewBlobList, CvBlobSeq* /*pOldBlobList*/)
|
||||
{
|
||||
int i;
|
||||
int TestObjNum;
|
||||
IplImage* pMask = NULL;
|
||||
IplImage* pMaskCopy = NULL;
|
||||
CvSeq* cnts = NULL;
|
||||
|
||||
if(m_pTestSeq==NULL) return 0;
|
||||
TestObjNum = cvTestSeqGetObjectNum(m_pTestSeq);
|
||||
pMask = cvTestSeqGetFGMask(m_pTestSeq);
|
||||
if(pMask == NULL) return 0;
|
||||
pMaskCopy = cvCloneImage(pMask);
|
||||
assert(pMaskCopy);
|
||||
|
||||
cvClearMemStorage(m_pMem);
|
||||
cvFindContours( pMaskCopy, m_pMem, &cnts, sizeof(CvContour), CV_RETR_EXTERNAL);
|
||||
cvReleaseImage(&pMaskCopy);
|
||||
|
||||
for(i=0;i<TestObjNum;++i)
|
||||
{/* check each object */
|
||||
CvPoint2D32f RealPos;
|
||||
CvPoint2D32f RealSize;
|
||||
int RealPosFlag = cvTestSeqGetObjectPos(m_pTestSeq,i,&RealPos);
|
||||
int RealSizeFlag = cvTestSeqGetObjectSize(m_pTestSeq,i,&RealSize);
|
||||
|
||||
if(!RealPosFlag) continue;
|
||||
if(m_DetectedBlobs.GetBlobByID(i)) continue;
|
||||
|
||||
if(RealSizeFlag)
|
||||
{ /* real size is know */
|
||||
float W2 = RealSize.x * 0.5f;
|
||||
float H2 = RealSize.y * 0.5f;
|
||||
if( RealPos.x > W2 && RealPos.x < (pMask->width-W2) &&
|
||||
RealPos.y > H2 && RealPos.y < (pMask->height-H2) )
|
||||
{ /* yes !! we found new blob, Let's add it to list */
|
||||
CvBlob NewBlob;
|
||||
NewBlob.x = RealPos.x;
|
||||
NewBlob.y = RealPos.y;
|
||||
NewBlob.w = RealSize.x;
|
||||
NewBlob.h = RealSize.y;
|
||||
NewBlob.ID = i;
|
||||
m_DetectedBlobs.AddBlob(&NewBlob);
|
||||
pNewBlobList->AddBlob(&NewBlob);
|
||||
}
|
||||
}/* real size is know */
|
||||
else
|
||||
{
|
||||
CvSeq* cnt;
|
||||
if(m_DetectedBlobs.GetBlobByID(i)) continue;
|
||||
for(cnt=cnts;cnt;cnt=cnt->h_next)
|
||||
{
|
||||
//CvBlob* pNewBlob = NULL;
|
||||
CvBlob NewBlob;
|
||||
CvRect r = cvBoundingRect( cnt );
|
||||
float x = RealPos.x - r.x;
|
||||
float y = RealPos.y - r.y;
|
||||
|
||||
if(x<0 || x > r.width || y < 0 || y > r.height ) continue;
|
||||
if( r.x <= 1 ||
|
||||
r.y <= 1 ||
|
||||
r.x + r.width >= pMask->width - 2 ||
|
||||
r.y + r.height >= pMask->height - 2 ) continue;
|
||||
|
||||
/* yes !! we found new blob, Let's add it to list */
|
||||
NewBlob.x = RealPos.x;
|
||||
NewBlob.y = RealPos.y;
|
||||
NewBlob.w = (float)r.width;
|
||||
NewBlob.h = (float)r.height;
|
||||
NewBlob.ID = i;
|
||||
m_DetectedBlobs.AddBlob(&NewBlob);
|
||||
pNewBlobList->AddBlob(&NewBlob);
|
||||
}
|
||||
}/* check new blob entrance */
|
||||
}/* check next object */
|
||||
|
||||
return pNewBlobList->GetBlobNum();
|
||||
}/* cvDetectNewBlob */
|
||||
void Release(){delete this;};
|
||||
};
|
||||
|
||||
/* Blob detector creator */
|
||||
CvBlobDetector* cvCreateBlobDetectorReal(CvTestSeq* pTestSeq){return new CvBlobDetectorReal(pTestSeq);}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user