Some performance tunning opportunity of cheese



Hi All:
I created one patch for your basic/quick review.
You can give me some guide line how to process it.

Details:
Cheese doesn’t perform well on my netbook, after some tries; I’d like discuss some opportunity with you.

0. Rob suggest me use gconf key for customized options, it has been reflected in the attached patch.

1. ALSA or PulseAudio

Gconfaudiosrc is default to PulseAudio on my platform, however if I use ALSA directly, it will reduce CPU consummation. 

For example, for audio only recording, Gst pipeline with PulseAudio src consumes 50%CPU, while with ALSA src consumes 30% CPU.

Should we add some options(man through UI) to let user select ALSA as audio src?

2. Vorbis vs FLAC

   If I use flacenc instead of vorbisenc, %CPU could decrease to 8% based on ALSA

   Should we add flac as a option for audio recording?

3. (max) fps, cheese always try to use the highest fps (no higher than 30) of camera. 

However, it doesn’t make sense for most web-camera, you can’t see difference of 15fps or 30fps. 

Should we add some option for it, or use 15 instead?

4. cheese on my netbook lack of a/v sync, 

but when I add ‘do-timestamp’ for both audio and video src, and let audio src ‘provide-clock’. It will be ok for a/v sync.

Do you think it is a valid change?

5. there is also some preview latency on my netbook.

   When I add queue in the audio/video encode pipeline, it will be much better.

6. video sink ‘sync=false’

   Set ‘sync=false’ of video sink also benefits preview latency.

7. video effect is insteresting, it also add some startup time for pipeline status change.

When there is no video effect selected, we can optimize pipeline to reduce ~3s for Gst pipeline startup.

When there is only rgb or yuv based effect, we can also optimized pipleline to reduce ~3s pipeline startup

8. cheese will query camera capability during each launch time.

    However, in most case we don’t change the device, if we try to add some policy to save the capability for once (when the hw changed), and load the capabiltiy when hw hasn’t changed, it could reduce launch time ~3s

 

Your comments are welcome


-----Original Message-----
From: cheese-list-bounces gnome org [mailto:cheese-list-bounces gnome org] On Behalf Of Zhao, Halley
Sent: 2010年1月9日 9:22
To: Stefan Kost
Cc: 'cheese-list gnome org'; Guo, Young
Subject: RE: some performance tunning opportunity of cheese

For still image, I think we do not need timestamp.
For view-finding, the 'sync=false' of video sink could also ignore the timestamp. 
Is it right?

-----Original Message-----
From: Stefan Kost [mailto:ensonic hora-obscura de] 
Sent: 2010年1月8日 17:56
To: Zhao, Halley
Cc: 'cheese-list gnome org'; Guo, Young
Subject: Re: some performance tunning opportunity of cheese

Stefan Kost wrote:
> Zhao, Halley wrote:
>   
>> Hi all:
>>
>>
>>     
>> 4. cheese on my netbook lack of a/v sync,
>>
>> but when I add ‘do-timestamp’ for both audio and video src, and let
>> audio src ‘provide-clock’. It will be ok for a/v sync.
>>
>> Do you think it is a valid change?
>>
>>     
> ‘provide-clock’ for the source imho makes sense when recording audio.
> Are you sure setting "do-timestamp" makes a difference?
>
>   
erm, its not as easy as that. The audiosrc is not running for still
images or viewfinder (atleast not in camerabin). Using "provide-clock"
would cause the clock to change while the pipline runs (unless we keep
the audiosrc running all the time).

Stefan
_______________________________________________
Cheese-list mailing list
Cheese-list gnome org
http://mail.gnome.org/mailman/listinfo/cheese-list
diff --git a/libcheese/cheese-camera.c b/libcheese/cheese-camera.c
index 00577d2..fd7745a 100644
--- a/libcheese/cheese-camera.c
+++ b/libcheese/cheese-camera.c
@@ -34,6 +34,7 @@
 
 #include "cheese-camera.h"
 #include "cheese-camera-device-monitor.h"
+#include "cheese-gconf.h"
 
 G_DEFINE_TYPE (CheeseCamera, cheese_camera, G_TYPE_OBJECT)
 
@@ -43,7 +44,22 @@ G_DEFINE_TYPE (CheeseCamera, cheese_camera, G_TYPE_OBJECT)
 
 #define MIN_DEFAULT_RATE 15.0
 
-static void find_highest_framerate (CheeseVideoFormat *format);
+static void find_highest_framerate (CheeseVideoFormat *format, CheeseCamera *camera);
+#define g_print printf
+
+#define __AUDIO_SRC_PROVIDE_CLOCK        1
+#define __AUDIO_SRC_DO_TIMESTAMP         1
+#define __VIDEO_SRC_DO_TIMESTAMP         1
+
+#define __TWO_QUEUES_FOR_AUDIO           1 // this need be open, samos need two queues for audio record
+
+#define __VIDEO_ENCODE_QUEUE             1
+
+#define __GET_DEVICE_DATA_FROM_FILE      1
+
+#define __VIDEO_SINK_SYNC_FALSE          1
+
+#define VIDEO_SCALE_MODE                 0 //nearest
 
 enum CheeseCameraError
 {
@@ -91,7 +107,15 @@ typedef struct
   CheeseVideoFormat *current_format;
 
   guint eos_timeout_id;
-} CheeseCameraPrivate;
+  
+  CheeseGConf *gconf;
+  int highest_fps_numerator;
+  int highest_fps_denominator;
+  char* audio_src_name;
+  char* audio_src_device_name;
+  char* audio_encode_name;
+  int video_scale_mode;
+ } CheeseCameraPrivate;
 
 enum
 {
@@ -383,13 +407,13 @@ cheese_camera_get_supported_framerates (CheeseVideoFormat *video_format, GstStru
 
 static void
 cheese_camera_add_video_format (CheeseCameraDevice *camera_device,
-                                CheeseVideoFormat *video_format, GstStructure *format_structure)
+                                CheeseVideoFormat *video_format, GstStructure *format_structure, CheeseCamera *camera)
 {
   int    i;
   gchar *resolution;
 
   cheese_camera_get_supported_framerates (video_format, format_structure);
-  find_highest_framerate (video_format);
+  find_highest_framerate (video_format, camera);
 
   g_print ("%s %d x %d num_framerates %d\n", video_format->mimetype, video_format->width,
            video_format->height, video_format->num_framerates);
@@ -445,7 +469,7 @@ cheese_resolution_compare (gconstpointer _a, gconstpointer _b)
 }
 
 static void
-cheese_camera_get_supported_video_formats (CheeseCameraDevice *camera_device, GstCaps *caps)
+cheese_camera_get_supported_video_formats (CheeseCameraDevice *camera_device, GstCaps *caps, CheeseCamera *camera)
 {
   int i;
   int num_structures;
@@ -477,7 +501,7 @@ cheese_camera_get_supported_video_formats (CheeseCameraDevice *camera_device, Gs
       video_format.mimetype = g_strdup (gst_structure_get_name (structure));
       gst_structure_get_int (structure, "width", &(video_format.width));
       gst_structure_get_int (structure, "height", &(video_format.height));
-      cheese_camera_add_video_format (camera_device, &video_format, structure);
+      cheese_camera_add_video_format (camera_device, &video_format, structure, camera);
     }
     else if (GST_VALUE_HOLDS_INT_RANGE (width))
     {
@@ -501,7 +525,7 @@ cheese_camera_get_supported_video_formats (CheeseCameraDevice *camera_device, Gs
         video_format.mimetype = g_strdup (gst_structure_get_name (structure));
         video_format.width    = cur_width;
         video_format.height   = cur_height;
-        cheese_camera_add_video_format (camera_device, &video_format, structure);
+        cheese_camera_add_video_format (camera_device, &video_format, structure, camera);
         cur_width  *= 2;
         cur_height *= 2;
       }
@@ -515,7 +539,7 @@ cheese_camera_get_supported_video_formats (CheeseCameraDevice *camera_device, Gs
         video_format.mimetype = g_strdup (gst_structure_get_name (structure));
         video_format.width    = cur_width;
         video_format.height   = cur_height;
-        cheese_camera_add_video_format (camera_device, &video_format, structure);
+        cheese_camera_add_video_format (camera_device, &video_format, structure, camera);
         cur_width  /= 2;
         cur_height /= 2;
       }
@@ -542,6 +566,100 @@ cheese_camera_get_supported_video_formats (CheeseCameraDevice *camera_device, Gs
   }
 }
 
+static gchar* cheese_camera_device_data_file_name (CheeseCameraDevice *camera_device)
+{
+  gchar** str_v;
+  int i;
+  gchar* file_name;
+  gchar* hiden;
+
+  str_v = g_strsplit(camera_device->id, "/", 255);
+  
+  for (i = 0; str_v[i] != NULL; i++);
+   
+  hiden = g_strdup_printf(".%s", str_v[i-1]);
+  file_name = g_strjoin(G_DIR_SEPARATOR_S, g_get_home_dir(), hiden, NULL);
+  
+  g_strfreev(str_v);
+  g_free(hiden);
+  return file_name;
+}
+
+static gboolean cheese_camera_device_data_file_older_than (GFile *file, guint days)
+{
+  struct tm* clock, *clock_now;
+  struct stat attrib;
+  time_t now;
+  gchar *file_path;
+  gint data_year, data_month, data_day, data_sec;
+
+  file_path = g_file_get_path(file);
+  
+  stat(file_path, &attrib);
+  g_free(file_path);
+  clock = gmtime(&(attrib.st_ctime));
+  data_year = clock->tm_year;
+  data_month = clock->tm_mon;
+  data_day = clock->tm_mday;
+  data_sec = clock->tm_sec;
+  
+  time(&now);
+  clock_now = gmtime(&now);
+  
+  if (data_year != clock_now->tm_year || data_month != clock_now->tm_mon || (clock_now->tm_mday - data_day >= days))
+    return TRUE;
+
+  //g_print("clock info is %d %d %d %d\n", data_year, data_month, data_day, data_sec);
+  //g_print("clock now is %d %d %d %d\n", clock_now->tm_year, clock_now->tm_mon, clock_now->tm_mday, clock_now->tm_sec);
+  return FALSE;
+}
+
+static gboolean cheese_camera_device_data_file_valid(CheeseCameraDevice *camera_device, GFile *file)
+{
+  if (!g_file_query_exists(file, NULL)) {
+    g_print("%s file does not exist\n", g_file_get_path(file));
+    return FALSE;
+  }
+  
+  if (cheese_camera_device_data_file_older_than(file, 1))
+    return FALSE;
+
+  return TRUE;  
+}
+
+static void cheese_camera_device_data_to_file(CheeseCameraDevice *camera_device, GstCaps *caps, GFile *file)
+{
+  GFileOutputStream *output_stream;
+  gchar *caps_string;
+  gsize bytes_written;  
+
+  caps_string =  gst_caps_to_string(caps);
+  output_stream = g_file_replace (file, NULL, FALSE, G_FILE_CREATE_NONE, NULL, NULL);
+  g_output_stream_write_all (output_stream, caps_string, strlen(caps_string) + 1, &bytes_written, NULL, NULL);
+  g_output_stream_close(output_stream, NULL, NULL);
+  
+  g_free(caps_string);
+}
+
+static void cheese_camera_device_data_from_file(CheeseCameraDevice *camera_device, GFile *file, CheeseCamera *camera)
+{
+#define CAPS_LENGTH 4096
+  GFileInputStream *input_stream;
+  gchar caps_string[CAPS_LENGTH];
+  GstCaps *caps;
+  gsize bytes_read;
+  
+  input_stream = g_file_read(file, NULL, NULL);
+  g_input_stream_read_all(input_stream, caps_string, CAPS_LENGTH, &bytes_read, NULL, NULL);
+
+  if (bytes_read >= CAPS_LENGTH)
+    g_warning("Caps info stored in file is too huge\n");
+
+  caps = gst_caps_from_string(caps_string);
+  cheese_camera_get_supported_video_formats (camera_device, caps, camera);
+  gst_caps_unref(caps);
+}
+
 static void
 cheese_camera_get_camera_device_data (CheeseCamera       *camera,
                                       CheeseCameraDevice *camera_device)
@@ -553,6 +671,17 @@ cheese_camera_get_camera_device_data (CheeseCamera       *camera,
   GstMessage          *msg;
   GstBus              *bus;
 
+#if __GET_DEVICE_DATA_FROM_FILE
+  gchar* device_data_file = cheese_camera_device_data_file_name(camera_device);
+  GFile *file = g_file_new_for_path(device_data_file);
+  g_free(device_data_file);
+
+  if (cheese_camera_device_data_file_valid(camera_device, file)) {
+    g_print("Get device data from file\n");
+    cheese_camera_device_data_from_file(camera_device, file, camera);
+  }
+  else
+#endif
   {
     pipeline_desc = g_strdup_printf ("%s name=source device=%s ! fakesink",
                                      camera_device->gstreamer_src,
@@ -587,7 +716,10 @@ cheese_camera_get_camera_device_data (CheeseCamera       *camera,
         pad  = gst_element_get_pad (src, "src");
         caps = gst_pad_get_caps (pad);
         gst_object_unref (pad);
-        cheese_camera_get_supported_video_formats (camera_device, caps);
+        cheese_camera_get_supported_video_formats (camera_device, caps, camera);
+        #if __GET_DEVICE_DATA_FROM_FILE
+        cheese_camera_device_data_to_file(camera_device, caps, file);
+        #endif
         gst_caps_unref (caps);
       }
       gst_element_set_state (pipeline, GST_STATE_NULL);
@@ -614,8 +746,8 @@ cheese_camera_create_fake_format (CheeseCamera *camera, CheeseCameraDevice *devi
   format.height                    = 240;
   format.num_framerates            = 1;
   format.framerates                = g_new0 (CheeseFramerate, 1);
-  format.framerates[0].numerator   = 30;
-  format.framerates[0].denominator = 1;
+  format.framerates[0].numerator   = priv->highest_fps_numerator;
+  format.framerates[0].denominator = priv->highest_fps_denominator;
 
   g_array_append_val (device->video_formats, format);
   priv->current_format = &format;
@@ -642,26 +774,48 @@ cheese_camera_detect_camera_devices (CheeseCamera *camera)
 }
 
 static void
-find_highest_framerate (CheeseVideoFormat *format)
+find_highest_framerate (CheeseVideoFormat *format, CheeseCamera *camera)
 {
+  CheeseCameraPrivate *priv       = CHEESE_CAMERA_GET_PRIVATE (camera);
   int framerate_numerator;
   int framerate_denominator;
   int i;
 
-  /* Select the highest framerate up to 30 Hz*/
+  /* Select the highest framerate up to highest_fps_numerator/highest_fps_denominator Hz*/
   framerate_numerator   = 1;
   framerate_denominator = 1;
   for (i = 0; i < format->num_framerates; i++)
   {
     float framerate = format->framerates[i].numerator / format->framerates[i].denominator;
     if (framerate > ((float) framerate_numerator / framerate_denominator)
-        && framerate <= 30)
+        && framerate <= ((float)priv->highest_fps_numerator/priv->highest_fps_denominator))
     {
       framerate_numerator   = format->framerates[i].numerator;
       framerate_denominator = format->framerates[i].denominator;
     }
   }
 
+  if(framerate_numerator == 1 && framerate_denominator == 1)
+  {
+    // we doesn't find a fps which is <=15; so select the lowest one
+    g_print("not find a fps <=%f\n",(float)priv->highest_fps_numerator/priv->highest_fps_denominator);
+    if(format->num_framerates > 0)
+    {
+      framerate_numerator   = format->framerates[0].numerator;
+      framerate_denominator = format->framerates[0].denominator;
+    }
+
+    for (i = 0; i < format->num_framerates; i++)
+    {
+      float framerate = format->framerates[i].numerator / format->framerates[i].denominator;
+      if (framerate < ((float) framerate_numerator / framerate_denominator))
+      {
+        framerate_numerator   = format->framerates[i].numerator;
+        framerate_denominator = format->framerates[i].denominator;
+      }
+    }
+  }
+
   format->highest_framerate.numerator   = framerate_numerator;
   format->highest_framerate.denominator = framerate_denominator;
 }
@@ -763,6 +917,9 @@ cheese_camera_create_camera_source_bin (CheeseCamera *camera)
   }
 
   priv->video_source = gst_bin_get_by_name (GST_BIN (priv->camera_source_bin), "video_source");
+#if __VIDEO_SRC_DO_TIMESTAMP
+  g_object_set(priv->video_source, "do_timestamp", 1, NULL);
+#endif
   priv->capsfilter   = gst_bin_get_by_name (GST_BIN (priv->camera_source_bin), "capsfilter");
   return TRUE;
 
@@ -882,6 +1039,10 @@ cheese_camera_create_video_display_bin (CheeseCamera *camera, GError **error)
     cheese_camera_set_error_element_not_found (error, "gconfvideosink");
   }
 
+#if __VIDEO_SINK_SYNC_FALSE
+  g_object_set(video_sink, "sync", FALSE, NULL);
+#endif
+
   if (error != NULL && *error != NULL)
     return FALSE;
 
@@ -972,21 +1133,40 @@ cheese_camera_create_video_save_bin (CheeseCamera *camera, GError **error)
 
   priv->video_save_bin = gst_bin_new ("video_save_bin");
 
-  if ((priv->audio_source = gst_element_factory_make ("gconfaudiosrc", "audio_source")) == NULL)
+  if ((priv->audio_source = gst_element_factory_make (priv->audio_src_name, "audio_source")) == NULL)
   {
-    cheese_camera_set_error_element_not_found (error, "gconfaudiosrc");
+    cheese_camera_set_error_element_not_found (error, priv->audio_src_name);
   }
+  if(priv->audio_src_device_name)
+  {
+    g_object_set(priv->audio_source, "device", priv->audio_src_device_name, NULL);
+  }
+#if __AUDIO_SRC_PROVIDE_CLOCK
+  // it is default on already.
+  g_object_set(priv->audio_source, "provide-clock", 1, NULL);
+#endif
+
+#if __AUDIO_SRC_DO_TIMESTAMP
+  g_object_set(priv->audio_source, "do-timestamp", 1, NULL);
+#endif
   if ((audio_queue = gst_element_factory_make ("queue", "audio_queue")) == NULL)
   {
     cheese_camera_set_error_element_not_found (error, "queue");
   }
+#if __TWO_QUEUES_FOR_AUDIO
+  GstElement *audio_queue1 = NULL;
+  if ((audio_queue1 = gst_element_factory_make ("queue", "audio_queue1")) == NULL)
+  {
+    cheese_camera_set_error_element_not_found (error, "queue");
+  }
+#endif
   if ((audio_convert = gst_element_factory_make ("audioconvert", "audio_convert")) == NULL)
   {
     cheese_camera_set_error_element_not_found (error, "audioconvert");
   }
-  if ((audio_enc = gst_element_factory_make ("vorbisenc", "audio_enc")) == NULL)
+  if ((audio_enc = gst_element_factory_make (priv->audio_encode_name, "audio_enc")) == NULL)
   {
-    cheese_camera_set_error_element_not_found (error, "vorbisenc");
+    cheese_camera_set_error_element_not_found (error, priv->audio_encode_name);
   }
 
   if ((video_save_csp = gst_element_factory_make ("ffmpegcolorspace", "video_save_csp")) == NULL)
@@ -1013,7 +1193,7 @@ cheese_camera_create_video_save_bin (CheeseCamera *camera, GError **error)
   else
   {
     /* Use bilinear scaling */
-    g_object_set (video_save_scale, "method", 1, NULL);
+    g_object_set (video_save_scale, "method", priv->video_scale_mode, NULL);
   }
 
   if ((mux = gst_element_factory_make ("oggmux", "mux")) == NULL)
@@ -1044,12 +1224,28 @@ cheese_camera_create_video_save_bin (CheeseCamera *camera, GError **error)
   gst_element_add_pad (priv->video_save_bin, gst_ghost_pad_new ("sink", pad));
   gst_object_unref (GST_OBJECT (pad));
 
-
+#if __TWO_QUEUES_FOR_AUDIO
+  gst_bin_add(GST_BIN(priv->video_save_bin), audio_queue1);
+  ok = gst_element_link_many (priv->audio_source, audio_queue, audio_convert, 
+                              audio_enc, audio_queue1, mux, priv->video_file_sink, NULL);
+  
+#else
   ok = gst_element_link_many (priv->audio_source, audio_queue, audio_convert,
                               audio_enc, mux, priv->video_file_sink, NULL);
-
+#endif
   ok &= gst_element_link_many (video_save_csp, video_save_rate, video_enc, NULL);
+#if !__VIDEO_ENCODE_QUEUE
   ok &= gst_element_link (video_enc, mux);
+#else
+  GstElement *video_enc_queue = NULL;
+  if ((video_enc_queue = gst_element_factory_make ("queue", "video-enc-queue")) == NULL)
+  {
+    cheese_camera_set_error_element_not_found (error, "queue");
+  }
+  ok &= gst_bin_add(GST_BIN(priv->video_save_bin), video_enc_queue);
+  ok &= gst_element_link (video_enc, video_enc_queue);
+  ok &= gst_element_link (video_enc_queue, mux);
+#endif
 
   if (!ok)
     g_error ("Unable to create video save pipeline");
@@ -1171,46 +1367,73 @@ cheese_camera_change_effect_filter (CheeseCamera *camera, GstElement *new_filter
 void
 cheese_camera_set_effect (CheeseCamera *camera, CheeseCameraEffect effect)
 {
-  GString    *rgb_effects_str = g_string_new ("");
-  GString    *yuv_effects_str = g_string_new ("");
-  char       *effects_pipeline_desc;
-  int         i;
   GstElement *effect_filter;
-  GError     *err = NULL;
 
-  for (i = 0; i < NUM_EFFECTS; i++)
+  if (effect != CHEESE_CAMERA_EFFECT_NO_EFFECT)
   {
-    if (effect & EFFECT_TO_PIPELINE_DESC[i].effect)
+    GString    *rgb_effects_str = g_string_new ("");
+    GString    *yuv_effects_str = g_string_new ("");
+    char       *effects_pipeline_desc;
+    int         i;
+    GError     *err = NULL;
+
+    for (i = 0; i < NUM_EFFECTS; i++)
     {
-      if (EFFECT_TO_PIPELINE_DESC[i].colorspace == RGB)
-      {
-        g_string_append (rgb_effects_str, EFFECT_TO_PIPELINE_DESC[i].pipeline_desc);
-        g_string_append (rgb_effects_str, " ! ");
-      }
-      else
+      if (effect & EFFECT_TO_PIPELINE_DESC[i].effect)
       {
-        g_string_append (yuv_effects_str, " ! ");
-        g_string_append (yuv_effects_str, EFFECT_TO_PIPELINE_DESC[i].pipeline_desc);
+        if (EFFECT_TO_PIPELINE_DESC[i].colorspace == RGB)
+        {
+          if (rgb_effects_str->len !=0)
+            g_string_append (rgb_effects_str, " ! ");
+          g_string_append (rgb_effects_str, EFFECT_TO_PIPELINE_DESC[i].pipeline_desc);
+        }
+        else
+        {
+          g_string_append (yuv_effects_str, " ! ");
+          g_string_append (yuv_effects_str, EFFECT_TO_PIPELINE_DESC[i].pipeline_desc);
+        }
       }
     }
+    if ((rgb_effects_str->len !=0) && (yuv_effects_str->len !=0)) 
+    {
+      effects_pipeline_desc = g_strconcat ("ffmpegcolorspace ! ",
+                                           rgb_effects_str->str,
+                                           " ! ffmpegcolorspace ",
+                                           yuv_effects_str->str,
+                                           NULL);
+    }
+    else if (rgb_effects_str->len !=0)
+    {
+      effects_pipeline_desc = g_strconcat ("ffmpegcolorspace ! ",
+                                           rgb_effects_str->str,
+                                           NULL);
+    }
+    else if (yuv_effects_str->len !=0)
+    {
+      effects_pipeline_desc = g_strconcat ("ffmpegcolorspace",
+                                           yuv_effects_str->str,
+                                           NULL);
+    }
+    else
+      g_assert_not_reached ();
+		
+    effect_filter = gst_parse_bin_from_description (effects_pipeline_desc, TRUE, &err);
+    if (!effect_filter || (err != NULL))
+    {
+      g_error_free (err);
+      g_error ("ERROR effect_filter\n");
+    }
+	
+    g_free (effects_pipeline_desc);
+    g_string_free (rgb_effects_str, TRUE);
+    g_string_free (yuv_effects_str, TRUE);
   }
-  effects_pipeline_desc = g_strconcat ("ffmpegcolorspace ! ",
-                                       rgb_effects_str->str,
-                                       "ffmpegcolorspace",
-                                       yuv_effects_str->str,
-                                       NULL);
-
-  effect_filter = gst_parse_bin_from_description (effects_pipeline_desc, TRUE, &err);
-  if (!effect_filter || (err != NULL))
-  {
-    g_error_free (err);
-    g_error ("ERROR effect_filter\n");
+  else
+  {//effect == CHEESE_CAMERA_EFFECT_NO_EFFECT
+    effect_filter = gst_element_factory_make ("identity", "effect");
   }
+ 
   cheese_camera_change_effect_filter (camera, effect_filter);
-
-  g_free (effects_pipeline_desc);
-  g_string_free (rgb_effects_str, TRUE);
-  g_string_free (yuv_effects_str, TRUE);
 }
 
 void
@@ -1329,6 +1552,11 @@ cheese_camera_finalize (GObject *object)
   /* Free CheeseCameraDevice array */
   g_ptr_array_free (priv->camera_devices, TRUE);
 
+  g_free(priv->audio_src_name);
+  if (priv->audio_src_device_name) g_free(priv->audio_src_device_name);
+  g_free(priv->audio_encode_name);
+  g_object_unref(priv->gconf);
+
   G_OBJECT_CLASS (cheese_camera_parent_class)->finalize (object);
 }
 
@@ -1472,6 +1700,39 @@ cheese_camera_init (CheeseCamera *camera)
   priv->camera_devices          = NULL;
   priv->device_name             = NULL;
   priv->photo_handler_signal_id = 0;
+
+  priv->gconf               = cheese_gconf_new ();
+  g_object_get (priv->gconf,
+                "gconf_prop_highest_fps_numerator", &(priv->highest_fps_numerator),
+                "gconf_prop_highest_fps_denominator", &(priv->highest_fps_denominator),
+                "gconf_prop_audio_src_name", &(priv->audio_src_name),
+                "gconf_prop_audio_src_device_name", &(priv->audio_src_device_name),
+                "gconf_prop_audio_encode_name", &(priv->audio_encode_name),
+                "gconf_prop_video_scale_mode", &(priv->video_scale_mode),
+                NULL);
+  g_print("highest_fps_numerator: %d,\thighest_fps_denominator: %d,\tvideo_scale_mode: %d\n",
+              priv->highest_fps_numerator, priv->highest_fps_denominator,priv->video_scale_mode);
+  if(priv->audio_src_name) g_print(" priv->audio_src_name: %s\n",priv->audio_src_name);
+  if(priv->audio_src_device_name) g_print(" priv->audio_src_device_name: %s\n",priv->audio_src_device_name);
+  if(priv->audio_encode_name) g_print("priv->audio_encode_name : %s\n",priv->audio_encode_name);
+
+  if(!priv->highest_fps_numerator || !priv->highest_fps_denominator)
+  {
+     priv->highest_fps_numerator =30;
+     priv->highest_fps_denominator = 1;
+  }
+  if(priv->video_scale_mode <0 || priv->video_scale_mode >=3)
+  {
+     priv->video_scale_mode = 1;
+  }
+  if(!priv->audio_src_name)  
+  {
+    priv->audio_src_name = g_strdup("gconfaudiosrc");
+  }
+  if(!priv->audio_encode_name)
+  {
+    priv->audio_encode_name = g_strdup("vorbisenc");
+  }
 }
 
 CheeseCamera *
diff --git a/libcheese/cheese-gconf.c b/libcheese/cheese-gconf.c
index c039d89..28bed9e 100644
--- a/libcheese/cheese-gconf.c
+++ b/libcheese/cheese-gconf.c
@@ -187,6 +187,36 @@ cheese_gconf_get_property (GObject *object, guint prop_id, GValue *value,
                                                     CHEESE_GCONF_PREFIX "/burst_repeat",
                                                     NULL));
       break;
+    case GCONF_PROP_HIGHEST_FPS_NUMERATOR:
+        g_value_set_int (value, gconf_client_get_int (priv->client,
+                                                      CHEESE_GCONF_PREFIX "/highest_fps_numerator",
+                                                      NULL));
+      break;  
+    case GCONF_PROP_HIGHEST_FPS_DENOMINATOR:
+      g_value_set_int (value, gconf_client_get_int (priv->client,
+                                                    CHEESE_GCONF_PREFIX "/highest_fps_denominator",
+                                                    NULL));
+      break;
+    case GCONF_PROP_ADUIO_SRC_NAME:
+      g_value_set_string (value, gconf_client_get_string (priv->client,
+                                                          CHEESE_GCONF_PREFIX "/audio_src_name",
+                                                          NULL));
+      break;
+    case GCONF_PROP_AUDIO_SRC_DEVICE_NAME:
+      g_value_set_string (value, gconf_client_get_string (priv->client,
+                                                          CHEESE_GCONF_PREFIX "/audio_src_device_name",
+                                                          NULL));
+      break;
+    case GCONF_PROP_AUDIO_ENCODE_NAME:
+      g_value_set_string (value, gconf_client_get_string (priv->client,
+                                                          CHEESE_GCONF_PREFIX "/audio_encode_name",
+                                                          NULL));
+      break;
+    case GCONF_PROP_VIDEO_SCALE_MODE:
+      g_value_set_int (value, gconf_client_get_int (priv->client,
+                                                    CHEESE_GCONF_PREFIX "/video_scale_mode",
+                                                    NULL));
+      break;
     default:
       G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
       break;
@@ -332,6 +362,43 @@ cheese_gconf_set_property (GObject *object, guint prop_id, const GValue *value,
                             g_value_get_int (value),
                             NULL);
       break;
+    case GCONF_PROP_HIGHEST_FPS_NUMERATOR:
+      gconf_client_set_int (priv->client,
+                            CHEESE_GCONF_PREFIX "/highest_fps_numerator",
+                            g_value_get_int (value),
+                            NULL);
+      break;
+    case GCONF_PROP_HIGHEST_FPS_DENOMINATOR:
+      gconf_client_set_int (priv->client,
+                            CHEESE_GCONF_PREFIX "/highest_fps_denominator",
+                            g_value_get_int (value),
+                            NULL);
+      break;
+    case GCONF_PROP_ADUIO_SRC_NAME:
+      gconf_client_set_string (priv->client,
+                               CHEESE_GCONF_PREFIX "/audio_src_name",
+                               g_value_get_string (value),
+                               NULL);
+      break;
+    case GCONF_PROP_AUDIO_SRC_DEVICE_NAME:
+      gconf_client_set_string (priv->client,
+                               CHEESE_GCONF_PREFIX "/audio_src_device_name",
+                               g_value_get_string (value),
+                               NULL);
+      break;
+    case GCONF_PROP_AUDIO_ENCODE_NAME:
+      gconf_client_set_string (priv->client,
+                               CHEESE_GCONF_PREFIX "/audio_encode_name",
+                               g_value_get_string (value),
+                               NULL);
+      break;
+    case GCONF_PROP_VIDEO_SCALE_MODE:
+      gconf_client_set_int (priv->client,
+                            CHEESE_GCONF_PREFIX "/video_scale_mode",
+                            g_value_get_int (value),
+                            NULL);
+      break;
+
     default:
       G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
       break;
@@ -478,6 +545,48 @@ cheese_gconf_class_init (CheeseGConfClass *klass)
                                                      G_MAXINT,
                                                      4,
                                                      G_PARAM_READWRITE));
+  g_object_class_install_property (object_class, GCONF_PROP_HIGHEST_FPS_NUMERATOR,
+                                   g_param_spec_int ("gconf_prop_highest_fps_numerator",
+                                                     NULL,
+                                                     NULL,
+                                                     1,
+                                                     G_MAXINT,
+                                                     4,
+                                                     G_PARAM_READWRITE));
+  g_object_class_install_property (object_class, GCONF_PROP_HIGHEST_FPS_DENOMINATOR,
+                                   g_param_spec_int ("gconf_prop_highest_fps_denominator",
+                                                     NULL,
+                                                     NULL,
+                                                     1,
+                                                     G_MAXINT,
+                                                     4,
+                                                     G_PARAM_READWRITE));
+  g_object_class_install_property (object_class, GCONF_PROP_ADUIO_SRC_NAME,
+                                   g_param_spec_string ("gconf_prop_audio_src_name",
+                                                        NULL,
+                                                        NULL,
+                                                        "",
+                                                        G_PARAM_READWRITE));
+  g_object_class_install_property (object_class, GCONF_PROP_AUDIO_SRC_DEVICE_NAME,
+                                   g_param_spec_string ("gconf_prop_audio_src_device_name",
+                                                        NULL,
+                                                        NULL,
+                                                        "",
+                                                        G_PARAM_READWRITE));
+  g_object_class_install_property (object_class, GCONF_PROP_AUDIO_ENCODE_NAME,
+                                   g_param_spec_string ("gconf_prop_audio_encode_name",
+                                                        NULL,
+                                                        NULL,
+                                                        "",
+                                                        G_PARAM_READWRITE));
+  g_object_class_install_property (object_class, GCONF_PROP_VIDEO_SCALE_MODE,
+                                   g_param_spec_int ("gconf_prop_video_scale_mode",
+                                                     NULL,
+                                                     NULL,
+                                                     1,
+                                                     G_MAXINT,
+                                                     4,
+                                                     G_PARAM_READWRITE));
 
   g_type_class_add_private (klass, sizeof (CheeseGConfPrivate));
 }
diff --git a/libcheese/cheese-gconf.h b/libcheese/cheese-gconf.h
index 9b9b308..e6bfc0c 100644
--- a/libcheese/cheese-gconf.h
+++ b/libcheese/cheese-gconf.h
@@ -56,7 +56,13 @@ enum
   GCONF_PROP_ENABLE_DELETE,
   GCONF_PROP_WIDE_MODE,
   GCONF_PROP_BURST_DELAY,
-  GCONF_PROP_BURST_REPEAT
+  GCONF_PROP_BURST_REPEAT,
+  GCONF_PROP_HIGHEST_FPS_NUMERATOR,
+  GCONF_PROP_HIGHEST_FPS_DENOMINATOR,
+  GCONF_PROP_ADUIO_SRC_NAME,
+  GCONF_PROP_AUDIO_SRC_DEVICE_NAME,
+  GCONF_PROP_AUDIO_ENCODE_NAME,
+  GCONF_PROP_VIDEO_SCALE_MODE
 };
 
 GType        cheese_gconf_get_type (void);
diff --git a/src/cheese-window.c b/src/cheese-window.c
index 3e01b56..4ae788d 100644
--- a/src/cheese-window.c
+++ b/src/cheese-window.c
@@ -2066,9 +2066,10 @@ setup_camera (CheeseWindow *cheese_window)
   g_signal_connect (cheese_window->camera, "video-saved",
                     G_CALLBACK (cheese_window_video_saved_cb), cheese_window);
 
-  cheese_camera_set_effect (cheese_window->camera,
-                            cheese_effect_chooser_get_selection (CHEESE_EFFECT_CHOOSER (cheese_window->effect_chooser)));
-
+  CheeseCameraEffect effect = cheese_effect_chooser_get_selection (CHEESE_EFFECT_CHOOSER (cheese_window->effect_chooser));
+  if(CHEESE_CAMERA_EFFECT_NO_EFFECT != effect) {
+    cheese_camera_set_effect (cheese_window->camera, effect);
+  }
   cheese_camera_set_balance_property (cheese_window->camera, "brightness", brightness);
   cheese_camera_set_balance_property (cheese_window->camera, "contrast", contrast);
   cheese_camera_set_balance_property (cheese_window->camera, "saturation", saturation);


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