1 /* ATK - Accessibility Toolkit
2 * Copyright 2001, 2002, 2003 Sun Microsystems Inc.
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 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
16 * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
17 * Boston, MA 02111-1307, USA.
23 #include <glib/gi18n-lib.h>
26 #include "atkmarshal.h"
27 #include "atk-enum-types.h"
28 #include "atkprivate.h"
32 * @Short_description: The ATK interface implemented by valuators and
33 * components which display or select a value from a bounded range of
37 * #AtkValue should be implemented for components which either display
38 * a value from a bounded range, or which allow the user to specify a
39 * value from a bounded range, or both. For instance, most sliders and
40 * range controls, as well as dials, should have #AtkObject
41 * representations which implement #AtkValue on the component's
42 * behalf. #AtKValues may be read-only, in which case attempts to
43 * alter the value return would fail.
45 * <refsect1 id="current-value-text">
46 * <title>On the subject of current value text</title>
48 * In addition to providing the current value, implementors can
49 * optionally provide an end-user-consumable textual description
50 * associated with this value. This description should be included
51 * when the numeric value fails to convey the full, on-screen
52 * representation seen by users.
56 * <title>Password strength</title>
57 * A password strength meter whose value changes as the user types
58 * their new password. Red is used for values less than 4.0, yellow
59 * for values between 4.0 and 7.0, and green for values greater than
60 * 7.0. In this instance, value text should be provided by the
61 * implementor. Appropriate value text would be "weak", "acceptable,"
62 * and "strong" respectively.
65 * A level bar whose value changes to reflect the battery charge. The
66 * color remains the same regardless of the charge and there is no
67 * on-screen text reflecting the fullness of the battery. In this
68 * case, because the position within the bar is the only indication
69 * the user has of the current charge, value text should not be
70 * provided by the implementor.
72 * <refsect2 id="implementor-notes">
73 * <title>Implementor Notes</title>
75 * Implementors should bear in mind that assistive technologies will
76 * likely prefer the value text provided over the numeric value when
77 * presenting a widget's value. As a result, strings not intended for
78 * end users should not be exposed in the value text, and strings
79 * which are exposed should be localized. In the case of widgets which
80 * display value text on screen, for instance through a separate label
81 * in close proximity to the value-displaying widget, it is still
82 * expected that implementors will expose the value text using the
87 * #AtkValue should NOT be implemented for widgets whose displayed
88 * value is not reflective of a meaningful amount. For instance, a
89 * progress pulse indicator whose value alternates between 0.0 and 1.0
90 * to indicate that some process is still taking place should not
91 * implement #AtkValue because the current value does not reflect
92 * progress towards completion.
97 * <refsect1 id="ranges">
98 * <title>On the subject of ranges</title>
100 * In addition to providing the minimum and maximum values,
101 * implementors can optionally provide details about subranges
102 * associated with the widget. These details should be provided by the
103 * implementor when both of the following are communicated visually to
107 * <listitem>The existence of distinct ranges such as "weak",
108 * "acceptable", and "strong" indicated by color, bar tick marks,
109 * and/or on-screen text.</listitem>
110 * <listitem>Where the current value stands within a given subrange,
111 * for instance illustrating progression from very "weak" towards
112 * nearly "acceptable" through changes in shade and/or position on
113 * the bar within the "weak" subrange.</listitem>
116 * If both of the above do not apply to the widget, it should be
117 * sufficient to expose the numeric value, along with the value text
118 * if appropriate, to make the widget accessible.
121 * <refsect2 id="ranges-implementor-notes">
122 * <title>Implementor Notes</title>
124 * If providing subrange details is deemed necessary, all possible
125 * values of the widget are expected to fall within one of the
126 * subranges defined by the implementor.
131 * <refsect1 id="localization">
132 * <title>On the subject of localization of end-user-consumable text
135 * Because value text and subrange descriptors are human-consumable,
136 * implementors are expected to provide localized strings which can be
137 * directly presented to end users via their assistive technology. In
138 * order to simplify this for implementors, implementors can use
139 * atk_value_type_get_localized_name() with the following
140 * already-localized constants for commonly-needed values can be used:
144 * <listitem>ATK_VALUE_VERY_WEAK</listitem>
145 * <listitem>ATK_VALUE_WEAK</listitem>
146 * <listitem>ATK_VALUE_ACCEPTABLE</listitem>
147 * <listitem>ATK_VALUE_STRONG</listitem>
148 * <listitem>ATK_VALUE_VERY_STRONG</listitem>
149 * <listitem>ATK_VALUE_VERY_LOW</listitem>
150 * <listitem>ATK_VALUE_LOW</listitem>
151 * <listitem>ATK_VALUE_MEDIUM</listitem>
152 * <listitem>ATK_VALUE_HIGH</listitem>
153 * <listitem>ATK_VALUE_VERY_HIGH</listitem>
154 * <listitem>ATK_VALUE_VERY_BAD</listitem>
155 * <listitem>ATK_VALUE_BAD</listitem>
156 * <listitem>ATK_VALUE_GOOD</listitem>
157 * <listitem>ATK_VALUE_VERY_GOOD</listitem>
158 * <listitem>ATK_VALUE_BEST</listitem>
159 * <listitem>ATK_VALUE_SUBSUBOPTIMAL</listitem>
160 * <listitem>ATK_VALUE_SUBOPTIMAL</listitem>
161 * <listitem>ATK_VALUE_OPTIMAL</listitem>
164 * Proposals for additional constants, along with their use cases,
165 * should be submitted to the GNOME Accessibility Team.
169 * <refsect1 id="changes">
170 * <title>On the subject of changes</title>
172 * Note that if there is a textual description associated with the new
173 * numeric value, that description should be included regardless of
174 * whether or not it has also changed.
179 static GPtrArray *value_type_names = NULL;
186 /* These are listed here for extraction by intltool */
188 /* Translators: This string describes a range within value-related
189 * widgets such as a password-strength meter. Note that what such a
190 * widget presents is controlled by application developers. Thus
191 * assistive technologies such as screen readers are expected to
192 * present this string alone or as a token in a list.
195 /* Translators: This string describes a range within value-related
196 * widgets such as a password-strength meter. Note that what such a
197 * widget presents is controlled by application developers. Thus
198 * assistive technologies such as screen readers are expected to
199 * present this string alone or as a token in a list.
202 /* Translators: This string describes a range within value-related
203 * widgets such as a password-strength meter. Note that what such a
204 * widget presents is controlled by application developers. Thus
205 * assistive technologies such as screen readers are expected to
206 * present this string alone or as a token in a list.
209 /* Translators: This string describes a range within value-related
210 * widgets such as a password-strength meter. Note that what such a
211 * widget presents is controlled by application developers. Thus
212 * assistive technologies such as screen readers are expected to
213 * present this string alone or as a token in a list.
216 /* Translators: This string describes a range within value-related
217 * widgets such as a password-strength meter. Note that what such a
218 * widget presents is controlled by application developers. Thus
219 * assistive technologies such as screen readers are expected to
220 * present this string alone or as a token in a list.
223 /* Translators: This string describes a range within value-related
224 * widgets such as a volume slider. Note that what such a widget
225 * presents (e.g. temperature, volume, price) is controlled by
226 * application developers. Thus assistive technologies such as screen
227 * readers are expected to present this string alone or as a token in
231 /* Translators: This string describes a range within value-related
232 * widgets such as a volume slider. Note that what such a widget
233 * presents (e.g. temperature, volume, price) is controlled by
234 * application developers. Thus assistive technologies such as screen
235 * readers are expected to present this string alone or as a token in
239 /* Translators: This string describes a range within value-related
240 * widgets such as a volume slider. Note that what such a widget
241 * presents (e.g. temperature, volume, price) is controlled by
242 * application developers. Thus assistive technologies such as screen
243 * readers are expected to present this string alone or as a token in
247 /* Translators: This string describes a range within value-related
248 * widgets such as a volume slider. Note that what such a widget
249 * presents (e.g. temperature, volume, price) is controlled by
250 * application developers. Thus assistive technologies such as screen
251 * readers are expected to present this string alone or as a token in
255 /* Translators: This string describes a range within value-related
256 * widgets such as a hard drive usage. Note that what such a widget
257 * presents (e.g. hard drive usage, network traffic) is controlled by
258 * application developers. Thus assistive technologies such as screen
259 * readers are expected to present this string alone or as a token in
263 /* Translators: This string describes a range within value-related
264 * widgets such as a hard drive usage. Note that what such a widget
265 * presents (e.g. hard drive usage, network traffic) is controlled by
266 * application developers. Thus assistive technologies such as screen
267 * readers are expected to present this string alone or as a token in
271 /* Translators: This string describes a range within value-related
272 * widgets such as a hard drive usage. Note that what such a widget
273 * presents (e.g. hard drive usage, network traffic) is controlled by
274 * application developers. Thus assistive technologies such as screen
275 * readers are expected to present this string alone or as a token in
279 /* Translators: This string describes a range within value-related
280 * widgets such as a hard drive usage. Note that what such a widget
281 * presents (e.g. hard drive usage, network traffic) is controlled by
282 * application developers. Thus assistive technologies such as screen
283 * readers are expected to present this string alone or as a token in
287 /* Translators: This string describes a range within value-related
288 * widgets such as a hard drive usage. Note that what such a widget
289 * presents (e.g. hard drive usage, network traffic) is controlled by
290 * application developers. Thus assistive technologies such as screen
291 * readers are expected to present this string alone or as a token in
297 static void atk_value_base_init (AtkValueIface *class);
299 static guint atk_value_signals[LAST_SIGNAL] = {0};
302 atk_value_get_type (void)
304 static GType type = 0;
309 sizeof (AtkValueIface),
310 (GBaseInitFunc) atk_value_base_init,
311 (GBaseFinalizeFunc) NULL,
315 type = g_type_register_static (G_TYPE_INTERFACE, "AtkValue", &tinfo, 0);
322 atk_value_base_init (AtkValueIface *class)
324 static gboolean initialized = FALSE;
328 * AtkValue::value-changed:
329 * @atkvalue: the object on which the signal was emitted.
330 * @value: the new value in a numerical form.
331 * @text: human readable text alternative (also called
332 * description) of this object. NULL if not available.
334 * The 'value-changed' signal is emitted when the current value
335 * that represent the object changes. @value is the numerical
336 * representation of this new value. @text is the human
337 * readable text alternative of @value, and can be NULL if it is
338 * not available. Note that if there is a textual description
339 * associated with the new numeric value, that description
340 * should be included regardless of whether or not it has also
343 * Example: a password meter whose value changes as the user
344 * types their new password. Appropiate value text would be
345 * "weak", "acceptable" and "strong".
349 atk_value_signals[VALUE_CHANGED] =
350 g_signal_new ("value_changed",
354 (GSignalAccumulator) NULL, NULL,
355 atk_marshal_VOID__DOUBLE_STRING,
357 2, G_TYPE_DOUBLE, G_TYPE_STRING);
364 * atk_value_get_current_value:
365 * @obj: a GObject instance that implements AtkValueIface
366 * @value: a #GValue representing the current accessible value
368 * Gets the value of this object.
370 * Deprecated: Since 2.12. Use atk_value_get_value_and_text()
374 atk_value_get_current_value (AtkValue *obj,
377 AtkValueIface *iface;
379 g_return_if_fail (value != NULL);
380 g_return_if_fail (ATK_IS_VALUE (obj));
382 iface = ATK_VALUE_GET_IFACE (obj);
384 if (iface->get_current_value)
386 if (G_IS_VALUE (value))
387 g_value_unset (value);
389 memset (value, 0, sizeof (*value));
391 (iface->get_current_value) (obj, value);
396 * atk_value_get_maximum_value:
397 * @obj: a GObject instance that implements AtkValueIface
398 * @value: a #GValue representing the maximum accessible value
400 * Gets the maximum value of this object.
402 * Deprecated: Since 2.12. Use atk_value_get_range() instead.
405 atk_value_get_maximum_value (AtkValue *obj,
408 AtkValueIface *iface;
410 g_return_if_fail (value != NULL);
411 g_return_if_fail (ATK_IS_VALUE (obj));
413 iface = ATK_VALUE_GET_IFACE (obj);
415 if (iface->get_maximum_value)
417 if (G_IS_VALUE (value))
418 g_value_unset (value);
420 memset (value, 0, sizeof (*value));
422 (iface->get_maximum_value) (obj, value);
427 * atk_value_get_minimum_value:
428 * @obj: a GObject instance that implements AtkValueIface
429 * @value: a #GValue representing the minimum accessible value
431 * Gets the minimum value of this object.
433 * Deprecated: Since 2.12. Use atk_value_get_range() instead.
436 atk_value_get_minimum_value (AtkValue *obj,
439 AtkValueIface *iface;
441 g_return_if_fail (value != NULL);
442 g_return_if_fail (ATK_IS_VALUE (obj));
444 iface = ATK_VALUE_GET_IFACE (obj);
446 if (iface->get_minimum_value)
448 if (G_IS_VALUE (value))
449 g_value_unset (value);
451 memset (value, 0, sizeof (*value));
453 (iface->get_minimum_value) (obj, value);
458 * atk_value_get_minimum_increment:
459 * @obj: a GObject instance that implements AtkValueIface
460 * @value: a #GValue representing the minimum increment by which the accessible value may be changed
462 * Gets the minimum increment by which the value of this object may be changed. If zero,
463 * the minimum increment is undefined, which may mean that it is limited only by the
464 * floating point precision of the platform.
468 * Deprecated: Since 2.12. Use atk_value_get_increment() instead.
471 atk_value_get_minimum_increment (AtkValue *obj,
474 AtkValueIface *iface;
476 g_return_if_fail (value != NULL);
477 g_return_if_fail (ATK_IS_VALUE (obj));
479 iface = ATK_VALUE_GET_IFACE (obj);
481 if (iface->get_minimum_increment)
483 if (G_IS_VALUE (value))
484 g_value_unset (value);
486 memset (value, 0, sizeof (*value));
488 (iface->get_minimum_increment) (obj, value);
493 * atk_value_set_current_value:
494 * @obj: a GObject instance that implements AtkValueIface
495 * @value: a #GValue which is the desired new accessible value.
497 * Sets the value of this object.
499 * Returns: %TRUE if new value is successfully set, %FALSE otherwise.
501 * Deprecated: Since 2.12. Use atk_value_set_value() instead.
504 atk_value_set_current_value (AtkValue *obj,
507 AtkValueIface *iface;
509 g_return_val_if_fail (ATK_IS_VALUE (obj), FALSE);
510 g_return_val_if_fail (G_IS_VALUE (value), FALSE);
512 iface = ATK_VALUE_GET_IFACE (obj);
514 if (iface->set_current_value)
515 return (iface->set_current_value) (obj, value);
522 * atk_value_get_value_and_text:
523 * @obj: a GObject instance that implements AtkValueIface
524 * @value: (out): address of #gdouble to put the current value of @obj
525 * @text: (out) (allow-none): address of #gchar to put the human
526 * readable text alternative for @value
528 * Gets the current value and the human readable text alternative of
529 * @obj. @text is a newly created string, that must be freed by the
530 * caller. Can be NULL if not descriptor is available.
536 atk_value_get_value_and_text (AtkValue *obj,
540 AtkValueIface *iface;
542 g_return_if_fail (ATK_IS_VALUE (obj));
544 iface = ATK_VALUE_GET_IFACE (obj);
546 if (iface->get_value_and_text)
548 (iface->get_value_and_text) (obj, value, text);
553 * atk_value_get_range:
554 * @obj: a GObject instance that implements AtkValueIface
556 * Gets the range of this object.
558 * Returns: (nullable) (transfer full): a newly allocated #AtkRange
559 * that represents the minimum, maximum and descriptor (if available)
560 * of @obj. NULL if that range is not defined.
565 atk_value_get_range (AtkValue *obj)
567 AtkValueIface *iface;
569 g_return_val_if_fail (ATK_IS_VALUE (obj), NULL);
571 iface = ATK_VALUE_GET_IFACE (obj);
573 if (iface->get_range)
575 return (iface->get_range) (obj);
582 * atk_value_get_increment:
583 * @obj: a GObject instance that implements AtkValueIface
585 * Gets the minimum increment by which the value of this object may be
586 * changed. If zero, the minimum increment is undefined, which may
587 * mean that it is limited only by the floating point precision of the
590 * Return value: the minimum increment by which the value of this
591 * object may be changed. zero if undefined.
596 atk_value_get_increment (AtkValue *obj)
598 AtkValueIface *iface;
600 g_return_val_if_fail (ATK_IS_VALUE (obj), 0);
602 iface = ATK_VALUE_GET_IFACE (obj);
604 if (iface->get_increment)
606 return (iface->get_increment) (obj);
614 * atk_value_get_sub_ranges:
615 * @obj: a GObject instance that implements AtkValueIface
617 * Gets the list of subranges defined for this object. See #AtkValue
618 * introduction for examples of subranges and when to expose them.
620 * Returns: (element-type AtkRange) (transfer full): an #GSList of
621 * #AtkRange which each of the subranges defined for this object. Free
622 * the returns list with g_slist_free().
627 atk_value_get_sub_ranges (AtkValue *obj)
629 AtkValueIface *iface;
631 g_return_val_if_fail (ATK_IS_VALUE (obj), NULL);
633 iface = ATK_VALUE_GET_IFACE (obj);
635 if (iface->get_sub_ranges)
637 return (iface->get_sub_ranges) (obj);
644 * atk_value_set_value:
645 * @obj: a GObject instance that implements AtkValueIface
646 * @new_value: a double which is the desired new accessible value.
648 * Sets the value of this object.
650 * This method is intended to provide a way to change the value of the
651 * object. In any case, it is possible that the value can't be
652 * modified (ie: a read-only component). If the value changes due this
653 * call, it is possible that the text could change, and will trigger
654 * an #AtkValue::value-changed signal emission.
656 * Note for implementors: the deprecated atk_value_set_current_value()
657 * method returned TRUE or FALSE depending if the value was assigned
658 * or not. In the practice several implementors were not able to
659 * decide it, and returned TRUE in any case. For that reason it is not
660 * required anymore to return if the value was properly assigned or
666 atk_value_set_value (AtkValue *obj,
667 const gdouble new_value)
669 AtkValueIface *iface;
671 g_return_if_fail (ATK_IS_VALUE (obj));
673 iface = ATK_VALUE_GET_IFACE (obj);
675 if (iface->set_value)
677 (iface->set_value) (obj, new_value);
682 initialize_value_type_names ()
684 GTypeClass *enum_class;
685 GEnumValue *enum_value;
687 gchar *value_type_name = NULL;
689 if (value_type_names)
692 value_type_names = g_ptr_array_new ();
693 enum_class = g_type_class_ref (ATK_TYPE_VALUE_TYPE);
694 if (!G_IS_ENUM_CLASS(enum_class))
697 for (i = 0; i < ATK_VALUE_LAST_DEFINED; i++)
699 enum_value = g_enum_get_value (G_ENUM_CLASS (enum_class), i);
700 value_type_name = g_strdup (enum_value->value_nick);
701 _compact_name (value_type_name);
702 g_ptr_array_add (value_type_names, value_type_name);
705 g_type_class_unref (enum_class);
709 * atk_value_type_get_name:
710 * @role: The #AtkValueType whose name is required
712 * Gets the description string describing the #AtkValueType @value_type.
714 * Returns: the string describing the #AtkValueType
717 atk_value_type_get_name (AtkValueType value_type)
719 g_return_val_if_fail (value_type >= 0, NULL);
721 if (!value_type_names)
722 initialize_value_type_names ();
724 if (value_type < value_type_names->len)
725 return g_ptr_array_index (value_type_names, value_type);
731 * atk_value_type_get_localized_name:
732 * @value_type: The #AtkValueType whose localized name is required
734 * Gets the localized description string describing the #AtkValueType @value_type.
736 * Returns: the localized string describing the #AtkValueType
739 atk_value_type_get_localized_name (AtkValueType value_type)
741 _gettext_initialization ();
743 return dgettext (GETTEXT_PACKAGE, atk_value_type_get_name (value_type));