mirror of
https://gitlab.gnome.org/GNOME/glib.git
synced 2025-02-02 17:26:17 +01:00
parent
e298f1a078
commit
4411023462
@ -45,6 +45,7 @@ content_files = [
|
|||||||
"floating-refs.md",
|
"floating-refs.md",
|
||||||
"boxed.md",
|
"boxed.md",
|
||||||
"enum-types.md",
|
"enum-types.md",
|
||||||
|
"gvalue.md",
|
||||||
]
|
]
|
||||||
content_images = [
|
content_images = [
|
||||||
]
|
]
|
||||||
|
108
docs/reference/gobject/gvalue.md
Normal file
108
docs/reference/gobject/gvalue.md
Normal file
@ -0,0 +1,108 @@
|
|||||||
|
Title: Generic value container
|
||||||
|
|
||||||
|
# Generic value container
|
||||||
|
|
||||||
|
The [`struct@GObject.Value`] structure is basically a variable container
|
||||||
|
that consists of a type identifier and a specific value of that type. The
|
||||||
|
type identifier within a `GValue` structure always determines the type of the
|
||||||
|
associated value.
|
||||||
|
|
||||||
|
To create an undefined `GValue` structure, simply create a zero-filled
|
||||||
|
GValue structure. To initialize the `GValue`, use the
|
||||||
|
[`method@GObject.Value.init`] function. A `GValue` cannot be used until it
|
||||||
|
is initialized.
|
||||||
|
|
||||||
|
Once you have finished using a `GValue`, you must call
|
||||||
|
[`method@GObject.Value.unset`] to ensure that all the resources associated
|
||||||
|
with the `GValue` are freed.
|
||||||
|
|
||||||
|
The basic type operations (such as freeing and copying) are determined by
|
||||||
|
the [`struct@GObject.TypeValueTable`] associated with the type ID stored in
|
||||||
|
the `GValue`. Other `GValue` operations (such as converting values between
|
||||||
|
types) are provided by this interface.
|
||||||
|
|
||||||
|
The code in the example program below demonstrates `GValue`'s features:
|
||||||
|
|
||||||
|
```c
|
||||||
|
#include <glib-object.h>
|
||||||
|
|
||||||
|
static void
|
||||||
|
int2string (const GValue *src_value,
|
||||||
|
GValue *dest_value)
|
||||||
|
{
|
||||||
|
if (g_value_get_int (src_value) == 42)
|
||||||
|
g_value_set_static_string (dest_value, "An important number");
|
||||||
|
else
|
||||||
|
g_value_set_static_string (dest_value, "What's that?");
|
||||||
|
}
|
||||||
|
|
||||||
|
int
|
||||||
|
main (int argc,
|
||||||
|
char *argv[])
|
||||||
|
{
|
||||||
|
// GValues must be initialized
|
||||||
|
GValue a = G_VALUE_INIT;
|
||||||
|
GValue b = G_VALUE_INIT;
|
||||||
|
const char *message;
|
||||||
|
|
||||||
|
// The GValue starts empty
|
||||||
|
g_assert (!G_VALUE_HOLDS_STRING (&a));
|
||||||
|
|
||||||
|
// Put a string in it
|
||||||
|
g_value_init (&a, G_TYPE_STRING);
|
||||||
|
g_assert (G_VALUE_HOLDS_STRING (&a));
|
||||||
|
g_value_set_static_string (&a, "Hello, world!");
|
||||||
|
g_printf ("%s\n", g_value_get_string (&a));
|
||||||
|
|
||||||
|
// Reset it to its pristine state
|
||||||
|
g_value_unset (&a);
|
||||||
|
|
||||||
|
// It can then be reused for another type
|
||||||
|
g_value_init (&a, G_TYPE_INT);
|
||||||
|
g_value_set_int (&a, 42);
|
||||||
|
|
||||||
|
// Attempt to transform it into a GValue of type STRING
|
||||||
|
g_value_init (&b, G_TYPE_STRING);
|
||||||
|
|
||||||
|
// An INT is transformable to a STRING
|
||||||
|
g_assert (g_value_type_transformable (G_TYPE_INT, G_TYPE_STRING));
|
||||||
|
|
||||||
|
g_value_transform (&a, &b);
|
||||||
|
g_printf ("%s\n", g_value_get_string (&b));
|
||||||
|
|
||||||
|
// Attempt to transform it again using a custom transform function
|
||||||
|
g_value_register_transform_func (G_TYPE_INT, G_TYPE_STRING, int2string);
|
||||||
|
g_value_transform (&a, &b);
|
||||||
|
g_printf ("%s\n", g_value_get_string (&b));
|
||||||
|
|
||||||
|
g_value_unset (&b);
|
||||||
|
g_value_unset (&a);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
For letting a `GValue` own (and memory manage) arbitrary types or pointers,
|
||||||
|
they need to become a [boxed type](boxed.html). The example below shows how
|
||||||
|
the pointer `mystruct` of type `MyStruct` is used as a [boxed type](boxed.html).
|
||||||
|
|
||||||
|
```c
|
||||||
|
typedef struct { ... } MyStruct;
|
||||||
|
G_DEFINE_BOXED_TYPE (MyStruct, my_struct, my_struct_copy, my_struct_free)
|
||||||
|
|
||||||
|
// These two lines normally go in a public header. By GObject convention,
|
||||||
|
// the naming scheme is NAMESPACE_TYPE_NAME:
|
||||||
|
#define MY_TYPE_STRUCT (my_struct_get_type ())
|
||||||
|
GType my_struct_get_type (void);
|
||||||
|
|
||||||
|
void
|
||||||
|
foo (void)
|
||||||
|
{
|
||||||
|
GValue *value = g_new0 (GValue, 1);
|
||||||
|
g_value_init (value, MY_TYPE_STRUCT);
|
||||||
|
g_value_set_boxed (value, mystruct);
|
||||||
|
// [... your code ....]
|
||||||
|
g_value_unset (value);
|
||||||
|
g_free (value);
|
||||||
|
}
|
||||||
|
```
|
@ -74,6 +74,7 @@ expand_content_files = [
|
|||||||
'boxed.md',
|
'boxed.md',
|
||||||
'enum-types.md',
|
'enum-types.md',
|
||||||
'floating-refs.md',
|
'floating-refs.md',
|
||||||
|
'gvalue.md',
|
||||||
]
|
]
|
||||||
|
|
||||||
gobject_gir = meson.current_source_dir() / 'GObject-2.0.gir'
|
gobject_gir = meson.current_source_dir() / 'GObject-2.0.gir'
|
||||||
|
116
gobject/gvalue.c
116
gobject/gvalue.c
@ -31,122 +31,6 @@
|
|||||||
#include "gtype-private.h"
|
#include "gtype-private.h"
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* SECTION:generic_values
|
|
||||||
* @short_description: A polymorphic type that can hold values of any
|
|
||||||
* other type
|
|
||||||
* @see_also: The fundamental types which all support #GValue
|
|
||||||
* operations and thus can be used as a type initializer for
|
|
||||||
* g_value_init() are defined by a separate interface. See the
|
|
||||||
* [standard values API][gobject-Standard-Parameter-and-Value-Types]
|
|
||||||
* for details
|
|
||||||
* @title: Generic values
|
|
||||||
*
|
|
||||||
* The #GValue structure is basically a variable container that consists
|
|
||||||
* of a type identifier and a specific value of that type.
|
|
||||||
*
|
|
||||||
* The type identifier within a #GValue structure always determines the
|
|
||||||
* type of the associated value.
|
|
||||||
*
|
|
||||||
* To create an undefined #GValue structure, simply create a zero-filled
|
|
||||||
* #GValue structure. To initialize the #GValue, use the g_value_init()
|
|
||||||
* function. A #GValue cannot be used until it is initialized. Before
|
|
||||||
* destruction you must always use g_value_unset() to make sure allocated
|
|
||||||
* memory is freed.
|
|
||||||
*
|
|
||||||
* The basic type operations (such as freeing and copying) are determined
|
|
||||||
* by the #GTypeValueTable associated with the type ID stored in the #GValue.
|
|
||||||
* Other #GValue operations (such as converting values between types) are
|
|
||||||
* provided by this interface.
|
|
||||||
*
|
|
||||||
* The code in the example program below demonstrates #GValue's
|
|
||||||
* features.
|
|
||||||
*
|
|
||||||
* |[<!-- language="C" -->
|
|
||||||
* #include <glib-object.h>
|
|
||||||
*
|
|
||||||
* static void
|
|
||||||
* int2string (const GValue *src_value,
|
|
||||||
* GValue *dest_value)
|
|
||||||
* {
|
|
||||||
* if (g_value_get_int (src_value) == 42)
|
|
||||||
* g_value_set_static_string (dest_value, "An important number");
|
|
||||||
* else
|
|
||||||
* g_value_set_static_string (dest_value, "What's that?");
|
|
||||||
* }
|
|
||||||
*
|
|
||||||
* int
|
|
||||||
* main (int argc,
|
|
||||||
* char *argv[])
|
|
||||||
* {
|
|
||||||
* // GValues must be initialized
|
|
||||||
* GValue a = G_VALUE_INIT;
|
|
||||||
* GValue b = G_VALUE_INIT;
|
|
||||||
* const gchar *message;
|
|
||||||
*
|
|
||||||
* // The GValue starts empty
|
|
||||||
* g_assert (!G_VALUE_HOLDS_STRING (&a));
|
|
||||||
*
|
|
||||||
* // Put a string in it
|
|
||||||
* g_value_init (&a, G_TYPE_STRING);
|
|
||||||
* g_assert (G_VALUE_HOLDS_STRING (&a));
|
|
||||||
* g_value_set_static_string (&a, "Hello, world!");
|
|
||||||
* g_printf ("%s\n", g_value_get_string (&a));
|
|
||||||
*
|
|
||||||
* // Reset it to its pristine state
|
|
||||||
* g_value_unset (&a);
|
|
||||||
*
|
|
||||||
* // It can then be reused for another type
|
|
||||||
* g_value_init (&a, G_TYPE_INT);
|
|
||||||
* g_value_set_int (&a, 42);
|
|
||||||
*
|
|
||||||
* // Attempt to transform it into a GValue of type STRING
|
|
||||||
* g_value_init (&b, G_TYPE_STRING);
|
|
||||||
*
|
|
||||||
* // An INT is transformable to a STRING
|
|
||||||
* g_assert (g_value_type_transformable (G_TYPE_INT, G_TYPE_STRING));
|
|
||||||
*
|
|
||||||
* g_value_transform (&a, &b);
|
|
||||||
* g_printf ("%s\n", g_value_get_string (&b));
|
|
||||||
*
|
|
||||||
* // Attempt to transform it again using a custom transform function
|
|
||||||
* g_value_register_transform_func (G_TYPE_INT, G_TYPE_STRING, int2string);
|
|
||||||
* g_value_transform (&a, &b);
|
|
||||||
* g_printf ("%s\n", g_value_get_string (&b));
|
|
||||||
* return 0;
|
|
||||||
* }
|
|
||||||
* ]|
|
|
||||||
*
|
|
||||||
* See also [gobject-Standard-Parameter-and-Value-Types] for more information on
|
|
||||||
* validation of #GValue.
|
|
||||||
*
|
|
||||||
* For letting a #GValue own (and memory manage) arbitrary types or pointers,
|
|
||||||
* they need to become a [boxed type][gboxed]. The example below shows how
|
|
||||||
* the pointer `mystruct` of type `MyStruct` is used as a [boxed type][gboxed].
|
|
||||||
*
|
|
||||||
* |[<!-- language="C" -->
|
|
||||||
* typedef struct { ... } MyStruct;
|
|
||||||
* G_DEFINE_BOXED_TYPE (MyStruct, my_struct, my_struct_copy, my_struct_free)
|
|
||||||
*
|
|
||||||
* // These two lines normally go in a public header. By GObject convention,
|
|
||||||
* // the naming scheme is NAMESPACE_TYPE_NAME:
|
|
||||||
* #define MY_TYPE_STRUCT (my_struct_get_type ())
|
|
||||||
* GType my_struct_get_type (void);
|
|
||||||
*
|
|
||||||
* void
|
|
||||||
* foo ()
|
|
||||||
* {
|
|
||||||
* GValue *value = g_new0 (GValue, 1);
|
|
||||||
* g_value_init (value, MY_TYPE_STRUCT);
|
|
||||||
* g_value_set_boxed (value, mystruct);
|
|
||||||
* // [... your code ....]
|
|
||||||
* g_value_unset (value);
|
|
||||||
* g_free (value);
|
|
||||||
* }
|
|
||||||
* ]|
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
/* --- typedefs & structures --- */
|
/* --- typedefs & structures --- */
|
||||||
typedef struct {
|
typedef struct {
|
||||||
GType src_type;
|
GType src_type;
|
||||||
|
Loading…
Reference in New Issue
Block a user