[shotwell/wip/phako/enhanced-faces: 7/136] Updated facedetect binary to use DBus, WIP



commit 08c893a2795e8af6223b9f4c65001b29c113fb56
Author: NarendraMA <narendra_m_a yahoo com>
Date:   Wed Jun 27 21:37:47 2018 +0530

    Updated facedetect binary to use DBus, WIP

 facedetect/facedetect-opencv.cpp        |  44 +++++++++
 facedetect/meson.build                  |  10 +-
 facedetect/org.gnome.ShotwellFaces1.xml |  52 ++++++++++
 facedetect/shotwell-facedetect.cpp      | 166 +++++++++++---------------------
 facedetect/shotwell-facedetect.hpp      |  26 +++++
 5 files changed, 184 insertions(+), 114 deletions(-)
---
diff --git a/facedetect/facedetect-opencv.cpp b/facedetect/facedetect-opencv.cpp
new file mode 100644
index 00000000..fd6394a0
--- /dev/null
+++ b/facedetect/facedetect-opencv.cpp
@@ -0,0 +1,44 @@
+#include "shotwell-facedetect.hpp"
+
+using namespace std;
+using namespace cv;
+
+vector<FaceRect> detectFaces(String inputName, String cascadeName, double scale) {
+       CascadeClassifier cascade;
+       if (!cascade.load(cascadeName)) {
+               cout << "error;Could not load classifier cascade. Filename: \"" << cascadeName << "\"" << 
endl;
+       }
+
+       if (inputName.empty()) {
+               cout << "error;You must specify the file to process." << endl;
+       }
+
+       Mat img = imread(inputName, 1);
+       if (img.empty()) {
+               cout << "error;Could not load the file to process. Filename: \"" << inputName << "\"" << endl;
+       }
+    
+    Mat gray;
+    cvtColor(img, gray, CV_BGR2GRAY);
+
+    Mat smallImg(cvRound(img.rows / scale), cvRound(img.cols / scale), CV_8UC1);
+    Size smallImgSize = smallImg.size();
+
+    resize(gray, smallImg, smallImgSize, 0, 0, INTER_LINEAR);
+    equalizeHist(smallImg, smallImg);
+
+    vector<Rect> faces;
+    cascade.detectMultiScale(smallImg, faces, 1.1, 2, CV_HAAR_SCALE_IMAGE, Size(30, 30));
+
+    vector<FaceRect> scaled;
+    for (vector<Rect>::const_iterator r = faces.begin(); r != faces.end(); r++) {
+        FaceRect i;
+        i.x = (float) r->x / smallImgSize.width;
+        i.y = (float) r->y / smallImgSize.height;
+        i.width = (float) r->width / smallImgSize.width;
+        i.height = (float) r->height / smallImgSize.height;
+        scaled.push_back(i);
+    }
+
+    return scaled;
+}
diff --git a/facedetect/meson.build b/facedetect/meson.build
index 6724abcb..f1931e37 100644
--- a/facedetect/meson.build
+++ b/facedetect/meson.build
@@ -1,10 +1,16 @@
+gnome = import('gnome')
 subproject = ('facedetect')
 add_languages('cpp')
 facedetect_dep = dependency('opencv', version : ['>= 2.3.0'], required : true)
+gio_unix = dependency('gio-unix-2.0', required : true)
+gdbus_src = gnome.gdbus_codegen('dbus-interface',
+  sources: 'org.gnome.ShotwellFaces1.xml',
+  interface_prefix : 'org.gnome.')
 executable('shotwell-facedetect',
-           'shotwell-facedetect.cpp',
-           dependencies : facedetect_dep,
+           'shotwell-facedetect.cpp', 'facedetect-opencv.cpp', gdbus_src,
+           dependencies : [facedetect_dep, gio, gio_unix],
            install : true,
+           include_directories: config_incdir,
            install_dir : join_paths(get_option('libexecdir'), 'shotwell'))
 install_data('facedetect-haarcascade.xml',
               install_dir : join_paths(get_option('datadir'), 'shotwell'))
diff --git a/facedetect/org.gnome.ShotwellFaces1.xml b/facedetect/org.gnome.ShotwellFaces1.xml
new file mode 100644
index 00000000..b621f56f
--- /dev/null
+++ b/facedetect/org.gnome.ShotwellFaces1.xml
@@ -0,0 +1,52 @@
+<!DOCTYPE node PUBLIC
+'-//freedesktop//DTD D-BUS Object Introspection 1.0//EN'
+'http://www.freedesktop.org/standards/dbus/1.0/introspect.dtd'>
+<node>
+  <!--
+      org.gnome.Shotwell.Faces1:
+      @short_description: Face detection/recognition
+  -->
+  <interface name="org.gnome.Shotwell.Faces1">
+    <!--
+        DetectFaces
+        @image: Image file to run face detection on
+        @cascade: Cascade XML file
+        @scale: Scaling to apply on image
+        Returns an array of face bounding boxes (x,y,w,h) in dimensionless units
+    -->
+    <method name="DetectFaces">
+      <arg type="s" name="image" direction="in" />
+      <arg type="s" name="cascade" direction="in" />
+      <arg type="d" name="scale" direction="in" />
+      <arg type="a(dddd)" name="faces" direction="out" />
+    </method>
+
+    <!--
+        TrainFaces
+        @images: List of image files with a face in it
+        @labels: List of labels for each face
+        @model: File name to save model in
+        Returns non-zero on any error
+    -->
+    <method name="TrainFaces">
+      <arg type="as" name="images" direction="in" />
+      <arg type="as" name="labels" direction="in" />
+      <arg type="s" name="model" direction="in" />
+      <arg type="y" name="status" direction="out" />
+    </method>
+
+    <!--
+        RecogniseFace
+        @image: Image of face to recognise
+        @model: File name to read model from
+        @threshold: Probability threshold
+        Returns array of (label, probability) pairs 
+    -->
+    <method name="RecogniseFace">
+      <arg type="s" name="image" direction="in" />
+      <arg type="s" name="model" direction="in" />
+      <arg type="d" name="threshold" direction="in" />
+      <arg type="a(sd)" name="labels" direction="out" />
+    </method>
+  </interface>
+</node>
diff --git a/facedetect/shotwell-facedetect.cpp b/facedetect/shotwell-facedetect.cpp
index 378a9059..9f3f52f2 100644
--- a/facedetect/shotwell-facedetect.cpp
+++ b/facedetect/shotwell-facedetect.cpp
@@ -2,133 +2,75 @@
  *
  * Copyright 2011 Valentín Barros Puertas <valentin(at)sanva(dot)net>
  * Copyright 2018 Ricardo Fantin da Costa <ricardofantin(at)gmail(dot)com>
+ * Copyright 2018 Narendra A <narendra_m_a(at)yahoo(dot)com>
  * 
  * This software is licensed under the GNU LGPL (version 2.1 or later).
  * See the COPYING file in this distribution.
  */
 
-#include "opencv2/objdetect/objdetect.hpp"
-#include "opencv2/highgui/highgui.hpp"
-#include "opencv2/imgproc/imgproc.hpp"
-
-#include <iostream>
-#include <stdio.h>
+#include "shotwell-facedetect.hpp"
+#include "dbus-interface.h"
 
 using namespace std;
 using namespace cv;
 
-void help() {
-
-       cout <<
-               "Usage:" << endl <<
-               "./facedetect --cascade=<cascade_path> "
-               "--scale=<image scale greater or equal to 1, try 1.3 for example> "
-               "filename" << endl << endl <<
-               "Example:" << endl <<
-               "./facedetect --cascade=\"./data/haarcascades/haarcascade_frontalface_alt.xml\" "
-               "--scale=1.3 ./photo.jpg" << endl << endl <<
-               "Using OpenCV version " << CV_VERSION << endl;
-
+// DBus binding functions
+static gboolean on_handle_detect_faces(ShotwellFaces1 *object,
+                                       GDBusMethodInvocation *invocation,
+                                       const gchar *arg_image,
+                                       const gchar *arg_cascade,
+                                       gdouble arg_scale) {
+    GVariantBuilder *builder;
+    GVariant *faces;
+    vector<FaceRect> rects = 
+        detectFaces(arg_image, arg_cascade, arg_scale);
+    // Construct return value
+    builder = g_variant_builder_new(G_VARIANT_TYPE ("a(dddd)"));
+    for (vector<FaceRect>::const_iterator r = rects.begin(); r != rects.end(); r++) {
+        GVariant *rect = g_variant_new("(dddd)", r->x, r->y, r->width, r->height);
+        g_variant_builder_add(builder, "(dddd)", rect);
+    }
+    faces = g_variant_new("a(dddd)", builder);
+    g_variant_builder_unref (builder);
+    // Call return
+    shotwell_faces1_complete_detect_faces(object, invocation,
+                                          faces);
+    g_free(faces);
+    return TRUE;
 }
 
-void detectFaces(Mat &img, CascadeClassifier &cascade, double scale) {
-  UMat uimg, gray;
-  img.copyTo(uimg);
-  cvtColor(uimg, gray, CV_BGR2GRAY);
-
-  UMat smallImg(cvRound(img.rows / scale), cvRound(img.cols / scale), CV_8UC1);
-  Size smallImgSize = smallImg.size();
-
-  resize(gray, smallImg, smallImgSize, 0, 0, INTER_LINEAR);
-  equalizeHist(smallImg, smallImg);
-
-  vector<Rect> faces;
-  cascade.detectMultiScale(smallImg, faces, 1.1, 2, CV_HAAR_SCALE_IMAGE, Size(30, 30));
-
-  int i = 0;
-  for (vector<Rect>::const_iterator r = faces.begin(); r != faces.end(); r++, i++) {
-
-    printf(
-           "face;x=%f&y=%f&width=%f&height=%f\n",
-           (float) r->x / smallImgSize.width,
-           (float) r->y / smallImgSize.height,
-           (float) r->width / smallImgSize.width,
-           (float) r->height / smallImgSize.height
-           );
-
-  }
-
+gboolean on_handle_train_faces(ShotwellFaces1 *object,
+                               GDBusMethodInvocation *invocation,
+                               const gchar *const *arg_images,
+                               const gchar *const *arg_labels,
+                               const gchar *arg_model) {
+    return TRUE;
 }
 
-int main(int argc, const char** argv) {
-
-       const std::string scaleOpt = "--scale=";
-       size_t scaleOptLen = scaleOpt.length();
-       const std::string cascadeOpt = "--cascade=";
-       size_t cascadeOptLen = cascadeOpt.length();
-
-       std::string cascadeName, inputName;
-       double scale = 1;
-
-       for (int i = 1; i < argc; i++) {
-
-               if (cascadeOpt.compare(0, cascadeOptLen, argv[i], cascadeOptLen) == 0) {
-
-                       cascadeName.assign(argv[i] + cascadeOptLen);
-
-               } else if (scaleOpt.compare(0, scaleOptLen, argv[i], scaleOptLen) == 0) {
-
-                       if (!sscanf(argv[i] + scaleOpt.length(), "%lf", &scale) || scale < 1)
-                               scale = 1;
-
-               } else if (argv[i][0] == '-') {
-
-                       cout << "warning;Unknown option " << argv[i] << endl;
-
-               } else
-                       inputName.assign(argv[i]);
-
-       }
-
-       if (cascadeName.empty()) {
-
-               cout << "error;You must specify the cascade." << endl;
-               help();
-
-               return -1;
-
-       }
-
-       CascadeClassifier cascade;
-
-       if (!cascade.load(cascadeName)) {
-
-               cout << "error;Could not load classifier cascade. Filename: \"" << cascadeName << "\"" << 
endl;
-
-               return -1;
-       }
-
-       if (inputName.empty()) {
-
-               cout << "error;You must specify the file to process." << endl;
-               help();
-
-               return -1;
-
-       }
-
-       Mat image = imread(inputName, 1);
-
-       if (image.empty()) {
-
-               cout << "error;Could not load the file to process. Filename: \"" << inputName << "\"" << endl;
-
-               return -1;
+gboolean on_handle_recognise_face(ShotwellFaces1 *object,
+                                  GDBusMethodInvocation *invocation,
+                                  const gchar *arg_image,
+                                  const gchar *arg_model,
+                                  gdouble arg_threshold) {
+    return TRUE;
+}
 
-       }
+static void on_name_acquired(GDBusConnection *connection,
+                             const gchar *name, gpointer user_data) {
+    ShotwellFaces1 *interface;
+    GError *error;
+    interface = shotwell_faces1_skeleton_new();
+    g_signal_connect(interface, "handle-detect-faces", G_CALLBACK (on_handle_detect_faces), NULL);
+    error = NULL;
+    !g_dbus_interface_skeleton_export(G_DBUS_INTERFACE_SKELETON(interface), connection, 
"/org/gnome/shotwell/faces", &error);
+}
 
-       detectFaces(image, cascade, scale);
+int main() {
+       GMainLoop *loop;
+       loop = g_main_loop_new (NULL, FALSE);
+       g_bus_own_name(G_BUS_TYPE_SESSION, "org.gnome.shotwell.faces", G_BUS_NAME_OWNER_FLAGS_NONE, NULL,
+                   on_name_acquired, NULL, NULL, NULL);
+       g_main_loop_run (loop);
 
        return 0;
-
 }
diff --git a/facedetect/shotwell-facedetect.hpp b/facedetect/shotwell-facedetect.hpp
new file mode 100644
index 00000000..d861eded
--- /dev/null
+++ b/facedetect/shotwell-facedetect.hpp
@@ -0,0 +1,26 @@
+/* 
+ * Copyright 2018 Narendra A (narendra_m_a(at)yahoo dot com)
+ * 
+ * This software is licensed under the GNU LGPL (version 2.1 or later).
+ * See the COPYING file in this distribution.
+ *
+ * Header file for facedetect/recognition routines
+ */
+
+#include "opencv2/objdetect/objdetect.hpp"
+#include "opencv2/highgui/highgui.hpp"
+#include "opencv2/imgproc/imgproc.hpp"
+
+#include <iostream>
+#include <stdio.h>
+
+typedef struct {
+    float x, y, width, height;
+} FaceRect;
+
+using namespace std;
+using namespace cv;
+
+vector<FaceRect> detectFaces(String inputName, String cascadeName, double scale);
+int trainFaces(vector<String> images, vector<String> labels, String modelFile);
+vector<pair<String, double>> recogniseFace(String image, String modelFile);


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]