1 /*
2 * Clutter.
3 *
4 * An OpenGL based 'interactive canvas' library.
5 *
6 * Authored By Matthew Allum <mallum@openedhand.com>
7 * Jorn Baayen <jorn@openedhand.com>
8 * Emmanuele Bassi <ebassi@openedhand.com>
9 *
10 * Copyright (C) 2006 OpenedHand
11 *
12 * This library is free software; you can redistribute it and/or
13 * modify it under the terms of the GNU Lesser General Public
14 * License as published by the Free Software Foundation; either
15 * version 2 of the License, or (at your option) any later version.
16 *
17 * This library is distributed in the hope that it will be useful,
18 * but WITHOUT ANY WARRANTY; without even the implied warranty of
19 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
20 * Lesser General Public License for more details.
21 *
22 * You should have received a copy of the GNU Lesser General Public
23 * License along with this library. If not, see <http://www.gnu.org/licenses/>.
24 */
25
26 #ifdef HAVE_CONFIG_H
27 #include "clutter-build-config.h"
28 #endif
29
30 #define CLUTTER_DISABLE_DEPRECATION_WARNINGS
31
32 #include "deprecated/clutter-actor.h"
33 #include "clutter-alpha.h"
34 #include "clutter-behaviour.h"
35 #include "clutter-behaviour-depth.h"
36 #include "clutter-enum-types.h"
37 #include "clutter-main.h"
38 #include "clutter-debug.h"
39 #include "clutter-private.h"
40
41 /**
42 * SECTION:clutter-behaviour-depth
43 * @Title: ClutterBehaviourDepth
44 * @short_description: A behaviour controlling the Z position
45 * @Deprecated: 1.6: Use clutter_actor_animate() instead
46 *
47 * #ClutterBehaviourDepth is a simple #ClutterBehaviour controlling the
48 * depth of a set of actors between a start and end depth.
49 *
50 * #ClutterBehaviourDepth is available since Clutter 0.4.
51 *
52 * Deprecated: 1.6: Use the #ClutterActor:depth property and
53 * clutter_actor_animate(), or #ClutterAnimator, or #ClutterState
54 * instead.
55 */
56
57 struct _ClutterBehaviourDepthPrivate
58 {
59 gint depth_start;
60 gint depth_end;
61 };
62
63 enum
64 {
65 PROP_0,
66
67 PROP_DEPTH_START,
68 PROP_DEPTH_END
69 };
70
G_DEFINE_TYPE_WITH_PRIVATE(ClutterBehaviourDepth,clutter_behaviour_depth,CLUTTER_TYPE_BEHAVIOUR)71 G_DEFINE_TYPE_WITH_PRIVATE (ClutterBehaviourDepth,
72 clutter_behaviour_depth,
73 CLUTTER_TYPE_BEHAVIOUR)
74
75 static void
76 alpha_notify_foreach (ClutterBehaviour *behaviour,
77 ClutterActor *actor,
78 gpointer user_data)
79 {
80 clutter_actor_set_depth (actor, GPOINTER_TO_INT (user_data));
81 }
82
83 static void
clutter_behaviour_depth_alpha_notify(ClutterBehaviour * behaviour,gdouble alpha_value)84 clutter_behaviour_depth_alpha_notify (ClutterBehaviour *behaviour,
85 gdouble alpha_value)
86 {
87 ClutterBehaviourDepthPrivate *priv;
88 gint depth;
89
90 priv = CLUTTER_BEHAVIOUR_DEPTH (behaviour)->priv;
91
92 /* Need to create factor as to avoid borking signedness */
93 depth = (alpha_value * (priv->depth_end - priv->depth_start))
94 + priv->depth_start;
95
96 CLUTTER_NOTE (ANIMATION, "alpha: %.4f, depth: %d", alpha_value, depth);
97
98 clutter_behaviour_actors_foreach (behaviour,
99 alpha_notify_foreach,
100 GINT_TO_POINTER (depth));
101 }
102
103 static void
clutter_behaviour_depth_applied(ClutterBehaviour * behaviour,ClutterActor * actor)104 clutter_behaviour_depth_applied (ClutterBehaviour *behaviour,
105 ClutterActor *actor)
106 {
107 ClutterBehaviourDepth *depth = CLUTTER_BEHAVIOUR_DEPTH (behaviour);
108
109 clutter_actor_set_depth (actor, depth->priv->depth_start);
110 }
111
112 static void
clutter_behaviour_depth_set_property(GObject * gobject,guint prop_id,const GValue * value,GParamSpec * pspec)113 clutter_behaviour_depth_set_property (GObject *gobject,
114 guint prop_id,
115 const GValue *value,
116 GParamSpec *pspec)
117 {
118 ClutterBehaviourDepth *depth = CLUTTER_BEHAVIOUR_DEPTH (gobject);
119
120 switch (prop_id)
121 {
122 case PROP_DEPTH_START:
123 depth->priv->depth_start = g_value_get_int (value);
124 break;
125 case PROP_DEPTH_END:
126 depth->priv->depth_end = g_value_get_int (value);
127 break;
128 default:
129 G_OBJECT_WARN_INVALID_PROPERTY_ID (gobject, prop_id, pspec);
130 break;
131 }
132 }
133
134 static void
clutter_behaviour_depth_get_property(GObject * gobject,guint prop_id,GValue * value,GParamSpec * pspec)135 clutter_behaviour_depth_get_property (GObject *gobject,
136 guint prop_id,
137 GValue *value,
138 GParamSpec *pspec)
139 {
140 ClutterBehaviourDepth *depth = CLUTTER_BEHAVIOUR_DEPTH (gobject);
141
142 switch (prop_id)
143 {
144 case PROP_DEPTH_START:
145 g_value_set_int (value, depth->priv->depth_start);
146 break;
147 case PROP_DEPTH_END:
148 g_value_set_int (value, depth->priv->depth_end);
149 break;
150 default:
151 G_OBJECT_WARN_INVALID_PROPERTY_ID (gobject, prop_id, pspec);
152 break;
153 }
154 }
155
156 static void
clutter_behaviour_depth_class_init(ClutterBehaviourDepthClass * klass)157 clutter_behaviour_depth_class_init (ClutterBehaviourDepthClass *klass)
158 {
159 GObjectClass *gobject_class = G_OBJECT_CLASS (klass);
160 ClutterBehaviourClass *behaviour_class = CLUTTER_BEHAVIOUR_CLASS (klass);
161
162 gobject_class->set_property = clutter_behaviour_depth_set_property;
163 gobject_class->get_property = clutter_behaviour_depth_get_property;
164
165 behaviour_class->alpha_notify = clutter_behaviour_depth_alpha_notify;
166 behaviour_class->applied = clutter_behaviour_depth_applied;
167
168 /**
169 * ClutterBehaviourDepth:depth-start:
170 *
171 * Start depth level to apply to the actors.
172 *
173 * Since: 0.4
174 *
175 * Deprecated: 1.6
176 */
177 g_object_class_install_property (gobject_class,
178 PROP_DEPTH_START,
179 g_param_spec_int ("depth-start",
180 P_("Start Depth"),
181 P_("Initial depth to apply"),
182 G_MININT, G_MAXINT, 0,
183 CLUTTER_PARAM_READWRITE));
184 /**
185 * ClutterBehaviourDepth:depth-end:
186 *
187 * End depth level to apply to the actors.
188 *
189 * Since: 0.4
190 *
191 * Deprecated: 1.6
192 */
193 g_object_class_install_property (gobject_class,
194 PROP_DEPTH_END,
195 g_param_spec_int ("depth-end",
196 P_("End Depth"),
197 P_("Final depth to apply"),
198 G_MININT, G_MAXINT, 0,
199 CLUTTER_PARAM_READWRITE));
200 }
201
202 static void
clutter_behaviour_depth_init(ClutterBehaviourDepth * depth)203 clutter_behaviour_depth_init (ClutterBehaviourDepth *depth)
204 {
205 depth->priv = clutter_behaviour_depth_get_instance_private (depth);
206 }
207
208 /**
209 * clutter_behaviour_depth_new:
210 * @alpha: (allow-none): a #ClutterAlpha instance, or %NULL
211 * @depth_start: initial value of the depth
212 * @depth_end: final value of the depth
213 *
214 * Creates a new #ClutterBehaviourDepth which can be used to control
215 * the ClutterActor:depth property of a set of #ClutterActor<!-- -->s.
216 *
217 * If @alpha is not %NULL, the #ClutterBehaviour will take ownership
218 * of the #ClutterAlpha instance. In the case when @alpha is %NULL,
219 * it can be set later with clutter_behaviour_set_alpha().
220 *
221 * Return value: (transfer full): the newly created behaviour
222 *
223 * Since: 0.4
224 *
225 * Deprecated: 1.6
226 */
227 ClutterBehaviour *
clutter_behaviour_depth_new(ClutterAlpha * alpha,gint depth_start,gint depth_end)228 clutter_behaviour_depth_new (ClutterAlpha *alpha,
229 gint depth_start,
230 gint depth_end)
231 {
232 g_return_val_if_fail (alpha == NULL || CLUTTER_IS_ALPHA (alpha), NULL);
233
234 return g_object_new (CLUTTER_TYPE_BEHAVIOUR_DEPTH,
235 "alpha", alpha,
236 "depth-start", depth_start,
237 "depth-end", depth_end,
238 NULL);
239 }
240
241 /**
242 * clutter_behaviour_depth_set_bounds:
243 * @behaviour: a #ClutterBehaviourDepth
244 * @depth_start: initial value of the depth
245 * @depth_end: final value of the depth
246 *
247 * Sets the boundaries of the @behaviour.
248 *
249 * Since: 0.6
250 *
251 * Deprecated: 1.6
252 */
253 void
clutter_behaviour_depth_set_bounds(ClutterBehaviourDepth * behaviour,gint depth_start,gint depth_end)254 clutter_behaviour_depth_set_bounds (ClutterBehaviourDepth *behaviour,
255 gint depth_start,
256 gint depth_end)
257 {
258 ClutterBehaviourDepthPrivate *priv;
259
260 g_return_if_fail (CLUTTER_IS_BEHAVIOUR_DEPTH (behaviour));
261
262 priv = behaviour->priv;
263
264 g_object_freeze_notify (G_OBJECT (behaviour));
265
266 if (priv->depth_start != depth_start)
267 {
268 priv->depth_start = depth_start;
269 g_object_notify (G_OBJECT (behaviour), "depth-start");
270 }
271
272 if (priv->depth_end != depth_end)
273 {
274 priv->depth_end = depth_end;
275 g_object_notify (G_OBJECT (behaviour), "depth-end");
276 }
277
278 g_object_thaw_notify (G_OBJECT (behaviour));
279 }
280
281 /**
282 * clutter_behaviour_depth_get_bounds:
283 * @behaviour: a #ClutterBehaviourDepth
284 * @depth_start: (out): return location for the initial depth value, or %NULL
285 * @depth_end: (out): return location for the final depth value, or %NULL
286 *
287 * Gets the boundaries of the @behaviour
288 *
289 * Since: 0.6
290 *
291 * Deprecated: 1.6
292 */
293 void
clutter_behaviour_depth_get_bounds(ClutterBehaviourDepth * behaviour,gint * depth_start,gint * depth_end)294 clutter_behaviour_depth_get_bounds (ClutterBehaviourDepth *behaviour,
295 gint *depth_start,
296 gint *depth_end)
297 {
298 g_return_if_fail (CLUTTER_IS_BEHAVIOUR_DEPTH (behaviour));
299
300 if (depth_start)
301 *depth_start = behaviour->priv->depth_start;
302
303 if (depth_end)
304 *depth_end = behaviour->priv->depth_end;
305 }
306