[cheese/capsrework: 3/9] Move caps retrieving stuff into CheeseCameraDevice
- From: Filippo Argiolas <fargiolas src gnome org>
- To: svn-commits-list gnome org
- Cc:
- Subject: [cheese/capsrework: 3/9] Move caps retrieving stuff into CheeseCameraDevice
- Date: Sun, 13 Dec 2009 20:08:45 +0000 (UTC)
commit 277e0b97ef5a71f3dfae09c74b33cbb9382ef57c
Author: Filippo Argiolas <filippo argiolas gmail com>
Date: Sun Dec 13 18:11:01 2009 +0100
Move caps retrieving stuff into CheeseCameraDevice
Caps are device specific so it makes sense to retrieve them directly in
CheeseCameraDevice. Make CheeseCameraDevice string properties CONSTRUCT_ONLY.
libcheese/cheese-camera-device-monitor.c | 13 ++--
libcheese/cheese-camera-device.c | 101 +++++++++++++++++-----
libcheese/cheese-camera-device.h | 2 +
libcheese/cheese-camera.c | 136 ++++++-----------------------
libcheese/cheese-camera.h | 2 +-
5 files changed, 114 insertions(+), 140 deletions(-)
---
diff --git a/libcheese/cheese-camera-device-monitor.c b/libcheese/cheese-camera-device-monitor.c
index 0bb869a..6743407 100644
--- a/libcheese/cheese-camera-device-monitor.c
+++ b/libcheese/cheese-camera-device-monitor.c
@@ -152,13 +152,12 @@ cheese_camera_device_monitor_added (CheeseCameraDeviceMonitor *monitor,
g_print ("\n");
- device = cheese_camera_device_new ();
- g_object_set (G_OBJECT (device),
- "device-id", g_udev_device_get_property (udevice, "DEVPATH"),
- "device-file", device_file,
- "name", product_name,
- "src", gstreamer_src,
- NULL);
+ device = g_object_new (CHEESE_TYPE_CAMERA_DEVICE,
+ "device-id", g_udev_device_get_property (udevice, "DEVPATH"),
+ "device-file", device_file,
+ "name", product_name,
+ "src", gstreamer_src,
+ NULL);
g_signal_emit (monitor, monitor_signals[ADDED], 0, device);
}
diff --git a/libcheese/cheese-camera-device.c b/libcheese/cheese-camera-device.c
index ac9a91f..a0afa8f 100644
--- a/libcheese/cheese-camera-device.c
+++ b/libcheese/cheese-camera-device.c
@@ -46,8 +46,7 @@ enum
PROP_NAME,
PROP_FILE,
PROP_ID,
- PROP_SRC,
- PROP_CAPS
+ PROP_SRC
};
typedef struct
@@ -233,6 +232,75 @@ cheese_webcam_device_update_format_table (CheeseCameraDevice *device)
}
static void
+cheese_camera_device_get_caps (CheeseCameraDevice *device)
+{
+ CheeseCameraDevicePrivate *priv =
+ CHEESE_CAMERA_DEVICE_GET_PRIVATE (device);
+
+ gchar *pipeline_desc;
+ GstElement *pipeline;
+ GstStateChangeReturn ret;
+ GstMessage *msg;
+ GstBus *bus;
+ GError *err = NULL;
+
+ pipeline_desc = g_strdup_printf ("%s name=source device=%s ! fakesink",
+ priv->src, priv->device);
+ pipeline = gst_parse_launch (pipeline_desc, &err);
+ if ((pipeline != NULL) && (err == NULL))
+ {
+ /* Start the pipeline and wait for max. 10 seconds for it to start up */
+ gst_element_set_state (pipeline, GST_STATE_READY);
+ ret = gst_element_get_state (pipeline, NULL, NULL, 10 * GST_SECOND);
+
+ /* Check if any error messages were posted on the bus */
+ bus = gst_element_get_bus (pipeline);
+ msg = gst_bus_poll (bus, GST_MESSAGE_ERROR, 0);
+ gst_object_unref (bus);
+
+ if ((msg == NULL) && (ret == GST_STATE_CHANGE_SUCCESS))
+ {
+ GstElement *src;
+ GstPad *pad;
+ char *name;
+ GstCaps *caps;
+
+ src = gst_bin_get_by_name (GST_BIN (pipeline), "source");
+
+ g_object_get (G_OBJECT (src), "device-name", &name, NULL);
+ if (name == NULL)
+ name = "Unknown";
+
+ g_print ("Device: %s (%s)\n", name, priv->device);
+ pad = gst_element_get_pad (src, "src");
+ caps = gst_pad_get_caps (pad);
+ priv->caps = cheese_webcam_device_filter_caps (device, caps, supported_formats);
+ cheese_webcam_device_update_format_table (device);
+
+ gst_object_unref (pad);
+ gst_caps_unref (caps);
+ }
+ gst_element_set_state (pipeline, GST_STATE_NULL);
+ gst_object_unref (pipeline);
+ }
+
+ if (err)
+ g_error_free (err);
+
+ g_free (pipeline_desc);
+}
+
+static void
+cheese_camera_device_constructed (GObject *object)
+{
+ CheeseCameraDevice *device = CHEESE_CAMERA_DEVICE (object);
+
+ cheese_camera_device_get_caps (device);
+
+ G_OBJECT_CLASS (cheese_camera_device_parent_class)->finalize (object);
+}
+
+static void
cheese_camera_device_get_property (GObject *object, guint prop_id, GValue *value, GParamSpec *pspec)
{
CheeseCameraDevice *device = CHEESE_CAMERA_DEVICE (object);
@@ -252,9 +320,6 @@ cheese_camera_device_get_property (GObject *object, guint prop_id, GValue *value
case PROP_SRC:
g_value_set_string (value, priv->src);
break;
- case PROP_CAPS:
- gst_value_set_caps (value, priv->caps);
- break;
default:
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
break;
@@ -267,7 +332,6 @@ cheese_camera_device_set_property (GObject *object, guint prop_id, const GValue
CheeseCameraDevice *device = CHEESE_CAMERA_DEVICE (object);
CheeseCameraDevicePrivate *priv =
CHEESE_CAMERA_DEVICE_GET_PRIVATE (device);
- const GstCaps *new_caps;
switch (prop_id) {
case PROP_NAME:
@@ -286,14 +350,6 @@ cheese_camera_device_set_property (GObject *object, guint prop_id, const GValue
g_free (priv->src);
priv->src = g_value_dup_string (value);
break;
- case PROP_CAPS:
- new_caps = gst_value_get_caps (value);
- if (new_caps != NULL) {
- gst_caps_unref (priv->caps);
- priv->caps = cheese_webcam_device_filter_caps (device, new_caps, supported_formats);
- cheese_webcam_device_update_format_table (device);
- }
- break;
default:
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
break;
@@ -314,6 +370,8 @@ cheese_camera_device_finalize (GObject *object)
gst_caps_unref (priv->caps);
free_format_list (device);
+
+ G_OBJECT_CLASS (cheese_camera_device_parent_class)->finalize (object);
}
static void
@@ -324,32 +382,27 @@ cheese_camera_device_class_init (CheeseCameraDeviceClass *klass)
object_class->finalize = cheese_camera_device_finalize;
object_class->get_property = cheese_camera_device_get_property;
object_class->set_property = cheese_camera_device_set_property;
+ object_class->constructed = cheese_camera_device_constructed;
g_object_class_install_property (object_class, PROP_NAME,
g_param_spec_string ("name",
NULL, NULL, NULL,
- G_PARAM_READWRITE));
+ G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY));
g_object_class_install_property (object_class, PROP_FILE,
g_param_spec_string ("device-file",
NULL, NULL, NULL,
- G_PARAM_READWRITE));
+ G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY));
g_object_class_install_property (object_class, PROP_ID,
g_param_spec_string ("device-id",
NULL, NULL, NULL,
- G_PARAM_READWRITE));
+ G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY));
g_object_class_install_property (object_class, PROP_SRC,
g_param_spec_string ("src",
NULL, NULL, NULL,
- G_PARAM_READWRITE));
- g_object_class_install_property (object_class, PROP_CAPS,
- g_param_spec_boxed ("caps",
- NULL, NULL,
- GST_TYPE_CAPS,
- G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
-
+ G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY));
g_type_class_add_private (klass, sizeof (CheeseCameraDevicePrivate));
}
diff --git a/libcheese/cheese-camera-device.h b/libcheese/cheese-camera-device.h
index fedf547..444db3a 100644
--- a/libcheese/cheese-camera-device.h
+++ b/libcheese/cheese-camera-device.h
@@ -56,6 +56,8 @@ typedef struct
GType cheese_video_format_get_type (void) G_GNUC_CONST;
+GType cheese_camera_device_get_type (void) G_GNUC_CONST;
+
CheeseCameraDevice *cheese_camera_device_new (void);
GstCaps *cheese_camera_device_get_caps_for_format (CheeseCameraDevice *device,
CheeseVideoFormat *format);
diff --git a/libcheese/cheese-camera.c b/libcheese/cheese-camera.c
index aab40b9..6cbd846 100644
--- a/libcheese/cheese-camera.c
+++ b/libcheese/cheese-camera.c
@@ -42,8 +42,6 @@ G_DEFINE_TYPE (CheeseCamera, cheese_camera, G_TYPE_OBJECT)
#define CHEESE_CAMERA_ERROR cheese_camera_error_quark ()
-#define MIN_DEFAULT_RATE 15.0
-
enum CheeseCameraError
{
CHEESE_CAMERA_ERROR_UNKNOWN,
@@ -87,7 +85,7 @@ typedef struct
int x_resolution;
int y_resolution;
int selected_device;
- CheeseVideoFormat *current_format;
+ CheeseVideoFormat *default_format;
guint eos_timeout_id;
} CheeseCameraPrivate;
@@ -320,67 +318,6 @@ cheese_camera_get_video_devices_from_udev (CheeseCamera *camera)
}
static void
-cheese_camera_get_camera_device_data (CheeseCamera *camera,
- CheeseCameraDevice *device)
-{
- char *pipeline_desc;
- GstElement *pipeline;
- GstStateChangeReturn ret;
- GstMessage *msg;
- GstBus *bus;
- gchar *src;
- gchar *devpath;
- GError *err = NULL;
-
- g_object_get (G_OBJECT (device), "device-file", &devpath, "src", &src, NULL);
-
- pipeline_desc = g_strdup_printf ("%s name=source device=%s ! fakesink",
- src, devpath);
- pipeline = gst_parse_launch (pipeline_desc, &err);
- if ((pipeline != NULL) && (err == NULL))
- {
- /* Start the pipeline and wait for max. 10 seconds for it to start up */
- gst_element_set_state (pipeline, GST_STATE_READY);
- ret = gst_element_get_state (pipeline, NULL, NULL, 10 * GST_SECOND);
-
- /* Check if any error messages were posted on the bus */
- bus = gst_element_get_bus (pipeline);
- msg = gst_bus_poll (bus, GST_MESSAGE_ERROR, 0);
- gst_object_unref (bus);
-
- if ((msg == NULL) && (ret == GST_STATE_CHANGE_SUCCESS))
- {
- GstElement *src;
- GstPad *pad;
- char *name;
- GstCaps *caps;
-
- src = gst_bin_get_by_name (GST_BIN (pipeline), "source");
-
- g_object_get (G_OBJECT (src), "device-name", &name, NULL);
- if (name == NULL)
- name = "Unknown";
-
- g_print ("Device: %s (%s)\n", name, devpath);
- pad = gst_element_get_pad (src, "src");
- caps = gst_pad_get_caps (pad);
- g_object_set (G_OBJECT (device), "caps", caps, NULL);
-
- gst_object_unref (pad);
- gst_caps_unref (caps);
- }
- gst_element_set_state (pipeline, GST_STATE_NULL);
- gst_object_unref (pipeline);
- }
- if (err)
- g_error_free (err);
-
- g_free (pipeline_desc);
- g_free (devpath);
- g_free (src);
-}
-
-static void
cheese_camera_create_fake_format (CheeseCamera *camera, CheeseCameraDevice *device)
{
// CheeseCameraPrivate *priv = CHEESE_CAMERA_GET_PRIVATE (camera);
@@ -395,7 +332,7 @@ cheese_camera_create_fake_format (CheeseCamera *camera, CheeseCameraDevice *devi
30, 1,
NULL);
- g_object_set (G_OBJECT (device), "caps", caps, NULL);
+// g_object_set (G_OBJECT (device), "caps", caps, NULL);
}
static void
@@ -407,13 +344,6 @@ cheese_camera_detect_camera_devices (CheeseCamera *camera)
cheese_camera_get_video_devices_from_udev (camera);
- g_print ("Probing supported video formats...\n");
- for (i = 0; i < priv->num_camera_devices; i++)
- {
- cheese_camera_get_camera_device_data (camera, g_ptr_array_index (priv->camera_devices, i));
- g_print ("\n");
- }
-
if (priv->num_camera_devices == 0)
cheese_camera_create_fake_format (camera, g_ptr_array_index (priv->camera_devices, 0));
}
@@ -455,53 +385,28 @@ cheese_camera_create_camera_source_bin (CheeseCamera *camera)
}
}
- /* Use the previously set resolution from gconf if it is set and the
- * camera supports it. */
- CheeseVideoFormat *format = g_new0 (CheeseVideoFormat, 1);
- format->width = priv->x_resolution;
- format->height = priv->y_resolution;
- GstCaps *caps = cheese_camera_device_get_caps_for_format (selected_camera, format);
- g_free (format);
-
- if (gst_caps_is_empty (caps))
- {
- g_warning ("CAPS_ARE_EMPTY");
- gst_caps_unref (caps);
- format = cheese_camera_device_get_best_format (selected_camera);
- caps = cheese_camera_device_get_caps_for_format (selected_camera, format);
- if (gst_caps_is_empty (caps)) {
- g_warning ("CAPS_ARE_STILL_EMPTY");
- gst_caps_unref (caps);
- goto fallback;
- }
- }
-
camera_input = g_strdup_printf (
"%s name=video_source device=%s ! capsfilter name=capsfilter ! identity",
cheese_camera_device_get_src (selected_camera),
cheese_camera_device_get_device_file (selected_camera));
- g_print ("%s\n", camera_input);
-
priv->camera_source_bin = gst_parse_bin_from_description (camera_input,
TRUE, &err);
-
g_free (camera_input);
if (priv->camera_source_bin == NULL) {
- gst_caps_unref (caps);
goto fallback;
}
priv->video_source = gst_bin_get_by_name (GST_BIN (priv->camera_source_bin), "video_source");
priv->capsfilter = gst_bin_get_by_name (GST_BIN (priv->camera_source_bin), "capsfilter");
- g_object_set (G_OBJECT (priv->capsfilter), "caps", caps, NULL);
- gst_caps_unref (caps);
-
}
return TRUE;
+
+/* FIXME: get rid of videotest stuff and set problem page when
+ * something fails, see cheese-video-widget */
fallback:
if (err != NULL)
{
@@ -1122,7 +1027,7 @@ cheese_camera_set_property (GObject *object, guint prop_id, const GValue *value,
priv->device_name = g_value_dup_string (value);
break;
case PROP_FORMAT:
- cheese_camera_set_video_format (self, g_value_get_boxed (value));
+ cheese_camera_set_video_format (self, g_value_dup_boxed (value));
break;
default:
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
@@ -1217,6 +1122,7 @@ cheese_camera_init (CheeseCamera *camera)
priv->camera_devices = NULL;
priv->device_name = NULL;
priv->photo_handler_signal_id = 0;
+ priv->current_format = NULL;
}
CheeseCamera *
@@ -1346,11 +1252,11 @@ cheese_camera_is_playing (CheeseCamera *camera)
return priv->pipeline_is_playing;
}
-void
+gboolean
cheese_camera_set_video_format (CheeseCamera *camera, CheeseVideoFormat *format)
{
-#if 0
CheeseCameraPrivate *priv = CHEESE_CAMERA_GET_PRIVATE (camera);
+ CheeseCameraDevice *device = g_ptr_array_index (priv->camera_devices, priv->selected_device);
GstCaps *caps;
if ((format->width == priv->current_format->width) &&
@@ -1358,7 +1264,21 @@ cheese_camera_set_video_format (CheeseCamera *camera, CheeseVideoFormat *format)
goto out;
}
- caps = cheese_camera_device_get_caps_for_format (selected_camera, format);
+ caps = cheese_camera_device_get_caps_for_format (device, format);
+
+ if (gst_caps_is_empty (caps))
+ {
+ g_warning ("CAPS_ARE_EMPTY");
+ gst_caps_unref (caps);
+ format = g_slice_new (CheeseVideoFormat);
+ format = cheese_camera_device_get_best_format (device);
+ caps = cheese_camera_device_get_caps_for_format (device, format);
+ if (gst_caps_is_empty (caps)) {
+ g_warning ("CAPS_ARE_STILL_EMPTY");
+ gst_caps_unref (caps);
+ return FALSE;
+ }
+ }
if (cheese_camera_is_playing (camera)) {
/* shouldn't this be done async? */
@@ -1368,11 +1288,11 @@ cheese_camera_set_video_format (CheeseCamera *camera, CheeseVideoFormat *format)
} else {
g_object_set (priv->capsfilter, "caps", caps, NULL);
}
+
out:
- if (G_LIKELY (priv->current_format) != NULL) {
- g_free (priv->current_format);
- }
-#endif
+ g_boxed_free (CHEESE_TYPE_VIDEO_FORMAT, priv->current_format);
+ priv->current_format = format;
+ return TRUE;
}
const CheeseVideoFormat *
diff --git a/libcheese/cheese-camera.h b/libcheese/cheese-camera.h
index 3ed45d0..60cbc87 100644
--- a/libcheese/cheese-camera.h
+++ b/libcheese/cheese-camera.h
@@ -91,7 +91,7 @@ void cheese_camera_set_device_by_dev_file (CheeseCamera *camera, c
void cheese_camera_set_device_by_dev_udi (CheeseCamera *camera, char *udi);
gboolean cheese_camera_switch_camera_device (CheeseCamera *camera);
GList * cheese_camera_get_video_formats (CheeseCamera *camera);
-void cheese_camera_set_video_format (CheeseCamera *camera,
+gboolean cheese_camera_set_video_format (CheeseCamera *camera,
CheeseVideoFormat *format);
void cheese_camera_get_balance_property_range (CheeseCamera *camera,
gchar *property,
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]