From 4d084ce019c8cc0ee85758ed674a8a89a1f979c5 Mon Sep 17 00:00:00 2001 From: Takashi Sakamoto Date: Mon, 18 Nov 2019 13:22:44 +0900 Subject: [PATCH] ctl: elem_info_enum: add properties and constructor --- src/ctl/alsactl.map | 1 + src/ctl/elem-info-enum.c | 109 ++++++++++++++++++++++++++++++++++- src/ctl/elem-info-enum.h | 6 ++ tests/alsactl-elem-info-enum | 9 ++- 4 files changed, 121 insertions(+), 4 deletions(-) diff --git a/src/ctl/alsactl.map b/src/ctl/alsactl.map index f4b688e..8cbfa4f 100644 --- a/src/ctl/alsactl.map +++ b/src/ctl/alsactl.map @@ -39,6 +39,7 @@ ALSA_GOBJECT_0_0_0 { "alsactl_elem_info_int_new"; "alsactl_elem_info_enum_get_type"; + "alsactl_elem_info_enum_new"; local: *; }; diff --git a/src/ctl/elem-info-enum.c b/src/ctl/elem-info-enum.c index 2e47598..8a28d69 100644 --- a/src/ctl/elem-info-enum.c +++ b/src/ctl/elem-info-enum.c @@ -1,14 +1,119 @@ // SPDX-License-Identifier: LGPL-3.0-or-later #include "elem-info-enum.h" +#include "privates.h" -G_DEFINE_TYPE(ALSACtlElemInfoEnum, alsactl_elem_info_enum, ALSACTL_TYPE_ELEM_INFO) +struct _ALSACtlElemInfoEnumPrivate { + const gchar **labels; // should have sentinel member with NULL value. +}; +G_DEFINE_TYPE_WITH_PRIVATE(ALSACtlElemInfoEnum, alsactl_elem_info_enum, ALSACTL_TYPE_ELEM_INFO) + +enum ctl_elem_info_enum_prop_type { + CTL_ELEM_INFO_ENUM_PROP_VALUE_COUNT = 1, + CTL_ELEM_INFO_ENUM_PROP_LABELS, + CTL_ELEM_INFO_ENUM_PROP_COUNT, +}; +static GParamSpec *ctl_elem_info_enum_props[CTL_ELEM_INFO_ENUM_PROP_COUNT] = { NULL, }; + +static void ctl_elem_info_enum_finalize(GObject *obj) +{ + ALSACtlElemInfoEnum *self = ALSACTL_ELEM_INFO_ENUM(obj); + ALSACtlElemInfoEnumPrivate *priv = + alsactl_elem_info_enum_get_instance_private(self); + + g_strfreev((gchar **)priv->labels); + + G_OBJECT_CLASS(alsactl_elem_info_enum_parent_class)->finalize(obj); +} + +static void ctl_elem_info_enum_set_property(GObject *obj, guint id, + const GValue *val, GParamSpec *spec) +{ + ALSACtlElemInfoEnum *self = ALSACTL_ELEM_INFO_ENUM(obj); + ALSACtlElemInfoEnumPrivate *priv = + alsactl_elem_info_enum_get_instance_private(self); + ALSACtlElemInfo *parent = ALSACTL_ELEM_INFO(obj); + struct snd_ctl_elem_info *info; + + ctl_elem_info_refer_private(parent, &info); + + switch (id) { + case CTL_ELEM_INFO_ENUM_PROP_VALUE_COUNT: + info->count = g_value_get_uint(val); + break; + case CTL_ELEM_INFO_ENUM_PROP_LABELS: + g_strfreev((gchar **)priv->labels); + priv->labels = (const gchar **)g_strdupv(g_value_get_boxed(val)); + break; + default: + G_OBJECT_WARN_INVALID_PROPERTY_ID(obj, id, spec); + break; + } +} + +static void ctl_elem_info_enum_get_property(GObject *obj, guint id, + GValue *val, GParamSpec *spec) +{ + ALSACtlElemInfoEnum *self = ALSACTL_ELEM_INFO_ENUM(obj); + ALSACtlElemInfoEnumPrivate *priv = + alsactl_elem_info_enum_get_instance_private(self); + + ALSACtlElemInfo *parent = ALSACTL_ELEM_INFO(obj); + struct snd_ctl_elem_info *info; + + ctl_elem_info_refer_private(parent, &info); + + switch (id) { + case CTL_ELEM_INFO_ENUM_PROP_VALUE_COUNT: + g_value_set_uint(val, info->count); + break; + case CTL_ELEM_INFO_ENUM_PROP_LABELS: + g_value_set_boxed(val, priv->labels); + break; + default: + G_OBJECT_WARN_INVALID_PROPERTY_ID(obj, id, spec); + break; + } +} static void alsactl_elem_info_enum_class_init(ALSACtlElemInfoEnumClass *klass) { - return; + GObjectClass *gobject_class = G_OBJECT_CLASS(klass); + + gobject_class->finalize = ctl_elem_info_enum_finalize; + gobject_class->set_property = ctl_elem_info_enum_set_property; + gobject_class->get_property = ctl_elem_info_enum_get_property; + + ctl_elem_info_enum_props[CTL_ELEM_INFO_ENUM_PROP_VALUE_COUNT] = + g_param_spec_uint("value-count", "value-count", + "The number of members as value of this element", + 0, G_MAXUINT, + 0, + G_PARAM_READWRITE); + + ctl_elem_info_enum_props[CTL_ELEM_INFO_ENUM_PROP_LABELS] = + g_param_spec_boxed("labels", "labels", + "The list of labels for this element", + G_TYPE_STRV, + G_PARAM_READWRITE); + + g_object_class_install_properties(gobject_class, + CTL_ELEM_INFO_ENUM_PROP_COUNT, ctl_elem_info_enum_props); } static void alsactl_elem_info_enum_init(ALSACtlElemInfoEnum *self) { return; } + +/** + * alsactl_elem_info_enum_new: + * + * Allocate and return an instance of ALSACtlElemInfoEnum. + * + * Returns: (transfer full): A #ALSACtlElemInfoEnum. + */ +ALSACtlElemInfoEnum *alsactl_elem_info_enum_new() +{ + return g_object_new(ALSACTL_TYPE_ELEM_INFO_ENUM, + "type", ALSACTL_ELEM_TYPE_ENUMERATED, NULL); +} diff --git a/src/ctl/elem-info-enum.h b/src/ctl/elem-info-enum.h index 4ffee53..ac757d2 100644 --- a/src/ctl/elem-info-enum.h +++ b/src/ctl/elem-info-enum.h @@ -33,9 +33,12 @@ G_BEGIN_DECLS typedef struct _ALSACtlElemInfoEnum ALSACtlElemInfoEnum; typedef struct _ALSACtlElemInfoEnumClass ALSACtlElemInfoEnumClass; +typedef struct _ALSACtlElemInfoEnumPrivate ALSACtlElemInfoEnumPrivate; struct _ALSACtlElemInfoEnum { ALSACtlElemInfo parent_instance; + + ALSACtlElemInfoEnumPrivate *priv; }; struct _ALSACtlElemInfoEnumClass { @@ -43,6 +46,9 @@ struct _ALSACtlElemInfoEnumClass { }; GType alsactl_elem_info_enum_get_type(void) G_GNUC_CONST; + +ALSACtlElemInfoEnum *alsactl_elem_info_enum_new(); + G_END_DECLS #endif diff --git a/tests/alsactl-elem-info-enum b/tests/alsactl-elem-info-enum index 00a8536..9dae1e7 100644 --- a/tests/alsactl-elem-info-enum +++ b/tests/alsactl-elem-info-enum @@ -10,8 +10,13 @@ gi.require_version('ALSACtl', '0.0') from gi.repository import ALSACtl target = ALSACtl.ElemInfoEnum() -props = () -methods = () +props = ( + 'value-count', + 'labels', +) +methods = ( + 'new', +) signals = () if not test(target, props, methods, signals): -- 2.47.3