~ubuntu-branches/ubuntu/lucid/psimedia/lucid-proposed

« back to all changes in this revision

Viewing changes to gstprovider/gstelements/videomaxrate/videomaxrate.c

  • Committer: Bazaar Package Importer
  • Author(s): Ivan Borzenkov
  • Date: 2009-07-18 16:51:30 UTC
  • Revision ID: james.westby@ubuntu.com-20090718165130-7aetrkp6zivus4lk
Tags: upstream-1.0.3
ImportĀ upstreamĀ versionĀ 1.0.3

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/*
 
2
 * Copyright (C) 2008  Barracuda Networks, Inc.
 
3
 *
 
4
 * This library is free software; you can redistribute it and/or
 
5
 * modify it under the terms of the GNU Lesser General Public
 
6
 * License as published by the Free Software Foundation; either
 
7
 * version 2.1 of the License, or (at your option) any later version.
 
8
 *
 
9
 * This library is distributed in the hope that it will be useful,
 
10
 * but WITHANY WARRANTY; without even the implied warranty of
 
11
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 
12
 * Lesser General Public License for more details.
 
13
 *
 
14
 * You should have received a copy of the GNU Lesser General Public
 
15
 * License along with this library; if not, write to the Free Software
 
16
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
 
17
 * 02110-1301  USA
 
18
 *
 
19
 */
 
20
 
 
21
#include "videomaxrate.h"
 
22
 
 
23
static const GstElementDetails videomaxrate_details =
 
24
GST_ELEMENT_DETAILS ("Video maximum rate adjuster",
 
25
    "Filter/Effect/Video",
 
26
    "Drops extra frames",
 
27
    "Justin Karneges <justin@affinix.com>");
 
28
 
 
29
static GstStaticPadTemplate gst_videomaxrate_src_template =
 
30
    GST_STATIC_PAD_TEMPLATE ("src",
 
31
    GST_PAD_SRC,
 
32
    GST_PAD_ALWAYS,
 
33
    GST_STATIC_CAPS ("video/x-raw-yuv; video/x-raw-rgb")
 
34
    );
 
35
 
 
36
static GstStaticPadTemplate gst_videomaxrate_sink_template =
 
37
    GST_STATIC_PAD_TEMPLATE ("sink",
 
38
    GST_PAD_SINK,
 
39
    GST_PAD_ALWAYS,
 
40
    GST_STATIC_CAPS ("video/x-raw-yuv; video/x-raw-rgb")
 
41
    );
 
42
 
 
43
static gboolean gst_videomaxrate_sink_event (GstPad *pad, GstEvent *event);
 
44
static GstCaps *gst_videomaxrate_transform_caps (GstBaseTransform *trans,
 
45
    GstPadDirection direction, GstCaps *caps);
 
46
static gboolean gst_videomaxrate_set_caps (GstBaseTransform *trans,
 
47
    GstCaps *incaps, GstCaps *outcaps);
 
48
static GstFlowReturn gst_videomaxrate_transform_ip (GstBaseTransform *trans,
 
49
    GstBuffer *buf);
 
50
 
 
51
GST_BOILERPLATE (GstVideoMaxRate, gst_videomaxrate, GstBaseTransform,
 
52
    GST_TYPE_BASE_TRANSFORM);
 
53
 
 
54
static void
 
55
gst_videomaxrate_base_init (gpointer gclass)
 
56
{
 
57
  GstElementClass *element_class = GST_ELEMENT_CLASS (gclass);
 
58
 
 
59
  gst_element_class_set_details (element_class, &videomaxrate_details);
 
60
 
 
61
  gst_element_class_add_pad_template (element_class,
 
62
      gst_static_pad_template_get (&gst_videomaxrate_sink_template));
 
63
  gst_element_class_add_pad_template (element_class,
 
64
      gst_static_pad_template_get (&gst_videomaxrate_src_template));
 
65
}
 
66
 
 
67
static void
 
68
gst_videomaxrate_class_init (GstVideoMaxRateClass *klass)
 
69
{
 
70
  GstBaseTransformClass *base_class;
 
71
  base_class = (GstBaseTransformClass *)klass;
 
72
 
 
73
  base_class->transform_caps = gst_videomaxrate_transform_caps;
 
74
  base_class->set_caps = gst_videomaxrate_set_caps;
 
75
  base_class->transform_ip = gst_videomaxrate_transform_ip;
 
76
}
 
77
 
 
78
static void
 
79
gst_videomaxrate_init (GstVideoMaxRate *videomaxrate,
 
80
    GstVideoMaxRateClass *gclass)
 
81
{
 
82
  (void)gclass;
 
83
 
 
84
  videomaxrate->to_rate_numerator = -1;
 
85
  videomaxrate->to_rate_denominator = -1;
 
86
  videomaxrate->have_last_ts = FALSE;
 
87
 
 
88
  gst_pad_set_event_function (GST_BASE_TRANSFORM_SINK_PAD (videomaxrate),
 
89
      gst_videomaxrate_sink_event);
 
90
}
 
91
 
 
92
gboolean
 
93
gst_videomaxrate_sink_event (GstPad *pad, GstEvent *event)
 
94
{
 
95
  GstVideoMaxRate *videomaxrate;
 
96
  gboolean ret;
 
97
 
 
98
  videomaxrate = (GstVideoMaxRate *)gst_pad_get_parent (pad);
 
99
  switch (GST_EVENT_TYPE(event)) {
 
100
    case GST_EVENT_NEWSEGMENT:
 
101
    case GST_EVENT_FLUSH_STOP:
 
102
      videomaxrate->have_last_ts = FALSE;
 
103
      break;
 
104
    default:
 
105
      break;
 
106
  }
 
107
 
 
108
  ret = gst_pad_push_event (GST_BASE_TRANSFORM_SRC_PAD (videomaxrate), event);
 
109
 
 
110
  gst_object_unref (videomaxrate);
 
111
  return ret;
 
112
}
 
113
 
 
114
GstCaps *
 
115
gst_videomaxrate_transform_caps (GstBaseTransform *trans,
 
116
    GstPadDirection direction, GstCaps *caps)
 
117
{
 
118
  GstCaps *ret;
 
119
  GstStructure *structure;
 
120
 
 
121
  (void)trans;
 
122
  (void)direction;
 
123
 
 
124
  /* this function is always called with a simple caps */
 
125
  g_return_val_if_fail (GST_CAPS_IS_SIMPLE (caps), NULL);
 
126
 
 
127
  ret = gst_caps_copy (caps);
 
128
 
 
129
  /* set the framerate as a range */
 
130
  structure = gst_structure_copy (gst_caps_get_structure (ret, 0));
 
131
  gst_structure_set (structure, "framerate", GST_TYPE_FRACTION_RANGE, 0, 1,
 
132
      G_MAXINT, 1, NULL);
 
133
  gst_caps_merge_structure (ret, gst_structure_copy (structure));
 
134
  gst_structure_free (structure);
 
135
 
 
136
  return ret;
 
137
}
 
138
 
 
139
gboolean
 
140
gst_videomaxrate_set_caps (GstBaseTransform *trans, GstCaps *incaps,
 
141
    GstCaps *outcaps)
 
142
{
 
143
  GstVideoMaxRate *videomaxrate;
 
144
  GstStructure *cs;
 
145
  gint numerator, denominator;
 
146
 
 
147
  videomaxrate = (GstVideoMaxRate *)trans;
 
148
  (void)incaps;
 
149
 
 
150
  // keep track of the outbound framerate
 
151
  cs = gst_caps_get_structure (outcaps, 0);
 
152
  if (!gst_structure_get_fraction (cs, "framerate", &numerator, &denominator))
 
153
    return FALSE;
 
154
 
 
155
  videomaxrate->to_rate_numerator = numerator;
 
156
  videomaxrate->to_rate_denominator = denominator;
 
157
 
 
158
  return TRUE;
 
159
}
 
160
 
 
161
GstFlowReturn
 
162
gst_videomaxrate_transform_ip (GstBaseTransform *trans, GstBuffer *buf)
 
163
{
 
164
  GstVideoMaxRate *videomaxrate;
 
165
  GstClockTime ts;
 
166
 
 
167
  videomaxrate = (GstVideoMaxRate *)trans;
 
168
  ts = GST_BUFFER_TIMESTAMP (buf);
 
169
 
 
170
  /* drop frames if they exceed our output rate */
 
171
  if (videomaxrate->have_last_ts) {
 
172
    if (ts < videomaxrate->last_ts + gst_util_uint64_scale (1,
 
173
            videomaxrate->to_rate_denominator * GST_SECOND,
 
174
            videomaxrate->to_rate_numerator)) {
 
175
      return GST_BASE_TRANSFORM_FLOW_DROPPED;
 
176
    }
 
177
  }
 
178
 
 
179
  videomaxrate->last_ts = ts;
 
180
  videomaxrate->have_last_ts = TRUE;
 
181
  return GST_FLOW_OK;
 
182
}