2 * Copyright (C) 2007 Benjamin Otte <otte@gnome.org>
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.
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY 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.
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,
17 * Boston, MA 02110-1301 USA
24 #include "swfdec_video_movie.h"
25 #include "swfdec_as_strings.h"
26 #include "swfdec_debug.h"
27 #include "swfdec_player_internal.h"
28 #include "swfdec_resource.h"
29 #include "swfdec_renderer_internal.h"
30 #include "swfdec_utils.h"
31 #include "swfdec_video_provider.h"
32 #include "swfdec_video_video_provider.h"
34 G_DEFINE_TYPE (SwfdecVideoMovie
, swfdec_video_movie
, SWFDEC_TYPE_MOVIE
)
37 swfdec_video_movie_update_extents (SwfdecMovie
*movie
,
40 SwfdecVideo
*org
= SWFDEC_VIDEO (movie
->graphic
);
41 SwfdecRect rect
= { 0, 0,
42 SWFDEC_TWIPS_SCALE_FACTOR
* org
->width
,
43 SWFDEC_TWIPS_SCALE_FACTOR
* org
->height
};
45 swfdec_rect_union (extents
, extents
, &rect
);
49 swfdec_video_movie_render (SwfdecMovie
*mov
, cairo_t
*cr
,
50 const SwfdecColorTransform
*trans
)
52 SwfdecVideoMovie
*movie
= SWFDEC_VIDEO_MOVIE (mov
);
53 cairo_surface_t
*surface
;
56 if (movie
->provider
== NULL
|| movie
->clear
)
59 surface
= swfdec_video_provider_get_image (movie
->provider
,
60 swfdec_renderer_get (cr
), &width
, &height
);
64 (mov
->original_extents
.x1
- mov
->original_extents
.x0
)
66 (mov
->original_extents
.y1
- mov
->original_extents
.y0
)
68 cairo_set_source_surface (cr
, surface
, 0.0, 0.0);
70 cairo_surface_destroy (surface
);
74 swfdec_video_movie_new_image (SwfdecVideoProvider
*provider
, SwfdecVideoMovie
*movie
)
77 swfdec_movie_invalidate_last (SWFDEC_MOVIE (movie
));
81 swfdec_video_movie_dispose (GObject
*object
)
83 SwfdecVideoMovie
*movie
= SWFDEC_VIDEO_MOVIE (object
);
85 if (movie
->provider
) {
86 g_signal_handlers_disconnect_by_func (movie
->provider
,
87 swfdec_video_movie_new_image
, movie
);
88 g_object_unref (movie
->provider
);
89 movie
->provider
= NULL
;
92 G_OBJECT_CLASS (swfdec_video_movie_parent_class
)->dispose (object
);
96 swfdec_video_movie_set_ratio (SwfdecMovie
*movie
)
98 SwfdecVideoMovie
*video
= SWFDEC_VIDEO_MOVIE (movie
);
101 swfdec_video_provider_set_ratio (video
->provider
, movie
->original_ratio
);
105 swfdec_video_movie_get_variable (SwfdecAsObject
*object
, SwfdecAsObject
*orig
,
106 const char *variable
, SwfdecAsValue
*val
, guint
*flags
)
108 guint version
= swfdec_gc_object_get_context (object
)->version
;
109 SwfdecVideoMovie
*video
;
111 video
= SWFDEC_VIDEO_MOVIE (object
);
113 if (swfdec_strcmp (version
, variable
, SWFDEC_AS_STR_width
) == 0) {
115 if (video
->provider
) {
116 w
= swfdec_video_provider_get_width (video
->provider
);
120 SWFDEC_AS_VALUE_SET_INT (val
, w
);
122 } else if (swfdec_strcmp (version
, variable
, SWFDEC_AS_STR_height
) == 0) {
124 if (video
->provider
) {
125 h
= swfdec_video_provider_get_height (video
->provider
);
129 SWFDEC_AS_VALUE_SET_INT (val
, h
);
131 } else if (swfdec_strcmp (version
, variable
, SWFDEC_AS_STR_deblocking
) == 0) {
132 SWFDEC_STUB ("Video.deblocking (get)");
133 SWFDEC_AS_VALUE_SET_NUMBER (val
, 0);
135 } else if (swfdec_strcmp (version
, variable
, SWFDEC_AS_STR_smoothing
) == 0) {
136 SWFDEC_STUB ("Video.smoothing (get)");
137 SWFDEC_AS_VALUE_SET_BOOLEAN (val
, FALSE
);
140 return SWFDEC_AS_OBJECT_CLASS (swfdec_video_movie_parent_class
)->get (
141 object
, orig
, variable
, val
, flags
);
146 swfdec_video_movie_set_variable (SwfdecAsObject
*object
, const char *variable
,
147 const SwfdecAsValue
*val
, guint flags
)
149 guint version
= swfdec_gc_object_get_context (object
)->version
;
151 if (swfdec_strcmp (version
, variable
, SWFDEC_AS_STR_deblocking
) == 0) {
152 SWFDEC_STUB ("Video.deblocking (set)");
153 } else if (swfdec_strcmp (version
, variable
, SWFDEC_AS_STR_smoothing
) == 0) {
154 SWFDEC_STUB ("Video.smoothing (set)");
156 SWFDEC_AS_OBJECT_CLASS (swfdec_video_movie_parent_class
)->set (object
,
157 variable
, val
, flags
);
162 swfdec_video_movie_foreach_variable (SwfdecAsObject
*object
, SwfdecAsVariableForeach func
, gpointer data
)
164 const char *native_variables
[] = { SWFDEC_AS_STR_width
, SWFDEC_AS_STR_height
,
165 SWFDEC_AS_STR_smoothing
, SWFDEC_AS_STR_deblocking
, NULL
};
168 for (i
= 0; native_variables
[i
] != NULL
; i
++) {
170 swfdec_as_object_get_variable (object
, native_variables
[i
], &val
);
171 if (!func (object
, native_variables
[i
], &val
, 0, data
))
175 return SWFDEC_AS_OBJECT_CLASS (swfdec_video_movie_parent_class
)->foreach (
180 swfdec_video_movie_invalidate (SwfdecMovie
*movie
, const cairo_matrix_t
*matrix
, gboolean last
)
182 SwfdecVideo
*org
= SWFDEC_VIDEO (movie
->graphic
);
183 SwfdecRect rect
= { 0, 0,
184 SWFDEC_TWIPS_SCALE_FACTOR
* org
->width
,
185 SWFDEC_TWIPS_SCALE_FACTOR
* org
->height
};
187 swfdec_rect_transform (&rect
, &rect
, matrix
);
188 swfdec_player_invalidate (SWFDEC_PLAYER (swfdec_gc_object_get_context (movie
)), &rect
);
192 swfdec_video_movie_constructor (GType type
, guint n_construct_properties
,
193 GObjectConstructParam
*construct_properties
)
199 object
= G_OBJECT_CLASS (swfdec_video_movie_parent_class
)->constructor (type
,
200 n_construct_properties
, construct_properties
);
202 movie
= SWFDEC_MOVIE (object
);
203 swfdec_as_object_set_constructor (SWFDEC_AS_OBJECT (movie
), movie
->resource
->sandbox
->Video
);
205 video
= SWFDEC_VIDEO (movie
->graphic
);
207 if (video
->n_frames
> 0) {
208 SwfdecVideoProvider
*provider
= swfdec_video_video_provider_new (video
);
209 swfdec_video_movie_set_provider (SWFDEC_VIDEO_MOVIE (movie
), provider
);
210 g_object_unref (provider
);
217 swfdec_video_movie_class_init (SwfdecVideoMovieClass
* g_class
)
219 GObjectClass
*object_class
= G_OBJECT_CLASS (g_class
);
220 SwfdecAsObjectClass
*asobject_class
= SWFDEC_AS_OBJECT_CLASS (g_class
);
221 SwfdecMovieClass
*movie_class
= SWFDEC_MOVIE_CLASS (g_class
);
223 object_class
->constructor
= swfdec_video_movie_constructor
;
224 object_class
->dispose
= swfdec_video_movie_dispose
;
226 asobject_class
->get
= swfdec_video_movie_get_variable
;
227 asobject_class
->set
= swfdec_video_movie_set_variable
;
228 asobject_class
->foreach
= swfdec_video_movie_foreach_variable
;
230 movie_class
->update_extents
= swfdec_video_movie_update_extents
;
231 movie_class
->render
= swfdec_video_movie_render
;
232 movie_class
->invalidate
= swfdec_video_movie_invalidate
;
233 movie_class
->set_ratio
= swfdec_video_movie_set_ratio
;
237 swfdec_video_movie_init (SwfdecVideoMovie
* video_movie
)
242 swfdec_video_movie_set_provider (SwfdecVideoMovie
*movie
,
243 SwfdecVideoProvider
*provider
)
245 g_return_if_fail (SWFDEC_IS_VIDEO_MOVIE (movie
));
246 g_return_if_fail (provider
== NULL
|| SWFDEC_IS_VIDEO_PROVIDER (provider
));
248 if (provider
== movie
->provider
)
252 g_object_ref (provider
);
253 g_signal_connect (provider
, "new-image",
254 G_CALLBACK (swfdec_video_movie_new_image
), movie
);
257 if (movie
->provider
) {
258 g_signal_handlers_disconnect_by_func (movie
->provider
,
259 swfdec_video_movie_new_image
, movie
);
260 g_object_unref (movie
->provider
);
263 movie
->provider
= provider
;
264 swfdec_movie_invalidate_last (SWFDEC_MOVIE (movie
));
268 swfdec_video_movie_clear (SwfdecVideoMovie
*movie
)
270 g_return_if_fail (SWFDEC_IS_VIDEO_MOVIE (movie
));
273 swfdec_movie_invalidate_last (SWFDEC_MOVIE (movie
));