Branch data Line data Source code
1 : : /* GIO - GLib Input, Output and Streaming Library
2 : : *
3 : : * Copyright © 2013 Canonical Limited
4 : : *
5 : : * SPDX-License-Identifier: LGPL-2.1-or-later
6 : : *
7 : : * This library is free software; you can redistribute it and/or
8 : : * modify it under the terms of the GNU Lesser General Public
9 : : * License as published by the Free Software Foundation; either
10 : : * version 2.1 of the License, or (at your option) any later version.
11 : : *
12 : : * This library is distributed in the hope that it will be useful,
13 : : * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 : : * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 : : * Lesser General Public License for more details.
16 : : *
17 : : * You should have received a copy of the GNU Lesser General
18 : : * Public License along with this library; if not, see <http://www.gnu.org/licenses/>.
19 : : *
20 : : * Author: Ryan Lortie <desrt@desrt.ca>
21 : : */
22 : :
23 : : #include "config.h"
24 : :
25 : : #include "gbytesicon.h"
26 : : #include "gbytes.h"
27 : : #include "gicon.h"
28 : : #include "glibintl.h"
29 : : #include "gloadableicon.h"
30 : : #include "gmemoryinputstream.h"
31 : : #include "gtask.h"
32 : : #include "gioerror.h"
33 : :
34 : :
35 : : /**
36 : : * GBytesIcon:
37 : : *
38 : : * `GBytesIcon` specifies an image held in memory in a common format (usually
39 : : * PNG) to be used as icon.
40 : : *
41 : : * Since: 2.38
42 : : */
43 : :
44 : : typedef GObjectClass GBytesIconClass;
45 : :
46 : : struct _GBytesIcon
47 : : {
48 : : GObject parent_instance;
49 : :
50 : : GBytes *bytes;
51 : : };
52 : :
53 : : enum
54 : : {
55 : : PROP_0,
56 : : PROP_BYTES
57 : : };
58 : :
59 : : static void g_bytes_icon_icon_iface_init (GIconIface *iface);
60 : : static void g_bytes_icon_loadable_icon_iface_init (GLoadableIconIface *iface);
61 : 34 : G_DEFINE_TYPE_WITH_CODE (GBytesIcon, g_bytes_icon, G_TYPE_OBJECT,
62 : : G_IMPLEMENT_INTERFACE (G_TYPE_ICON, g_bytes_icon_icon_iface_init)
63 : : G_IMPLEMENT_INTERFACE (G_TYPE_LOADABLE_ICON, g_bytes_icon_loadable_icon_iface_init))
64 : :
65 : : static void
66 : 2 : g_bytes_icon_get_property (GObject *object,
67 : : guint prop_id,
68 : : GValue *value,
69 : : GParamSpec *pspec)
70 : : {
71 : 2 : GBytesIcon *icon = G_BYTES_ICON (object);
72 : :
73 : 2 : switch (prop_id)
74 : : {
75 : 2 : case PROP_BYTES:
76 : 2 : g_value_set_boxed (value, icon->bytes);
77 : 2 : break;
78 : :
79 : 0 : default:
80 : 0 : G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
81 : : }
82 : 2 : }
83 : :
84 : : static void
85 : 4 : g_bytes_icon_set_property (GObject *object,
86 : : guint prop_id,
87 : : const GValue *value,
88 : : GParamSpec *pspec)
89 : : {
90 : 4 : GBytesIcon *icon = G_BYTES_ICON (object);
91 : :
92 : 4 : switch (prop_id)
93 : : {
94 : 4 : case PROP_BYTES:
95 : 4 : icon->bytes = g_value_dup_boxed (value);
96 : 4 : break;
97 : :
98 : 0 : default:
99 : 0 : G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
100 : : }
101 : 4 : }
102 : :
103 : : static void
104 : 4 : g_bytes_icon_finalize (GObject *object)
105 : : {
106 : : GBytesIcon *icon;
107 : :
108 : 4 : icon = G_BYTES_ICON (object);
109 : :
110 : 4 : g_bytes_unref (icon->bytes);
111 : :
112 : 4 : G_OBJECT_CLASS (g_bytes_icon_parent_class)->finalize (object);
113 : 4 : }
114 : :
115 : : static void
116 : 3 : g_bytes_icon_class_init (GBytesIconClass *klass)
117 : : {
118 : 3 : GObjectClass *gobject_class = G_OBJECT_CLASS (klass);
119 : :
120 : 3 : gobject_class->get_property = g_bytes_icon_get_property;
121 : 3 : gobject_class->set_property = g_bytes_icon_set_property;
122 : 3 : gobject_class->finalize = g_bytes_icon_finalize;
123 : :
124 : : /**
125 : : * GBytesIcon:bytes:
126 : : *
127 : : * The bytes containing the icon.
128 : : */
129 : 3 : g_object_class_install_property (gobject_class, PROP_BYTES,
130 : : g_param_spec_boxed ("bytes", NULL, NULL,
131 : : G_TYPE_BYTES,
132 : : G_PARAM_CONSTRUCT_ONLY | G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
133 : 3 : }
134 : :
135 : : static void
136 : 4 : g_bytes_icon_init (GBytesIcon *bytes)
137 : : {
138 : 4 : }
139 : :
140 : : /**
141 : : * g_bytes_icon_new:
142 : : * @bytes: a #GBytes.
143 : : *
144 : : * Creates a new icon for a bytes.
145 : : *
146 : : * This cannot fail, but loading and interpreting the bytes may fail later on
147 : : * (for example, if g_loadable_icon_load() is called) if the image is invalid.
148 : : *
149 : : * Returns: (transfer full) (type GBytesIcon): a #GIcon for the given
150 : : * @bytes.
151 : : *
152 : : * Since: 2.38
153 : : **/
154 : : GIcon *
155 : 3 : g_bytes_icon_new (GBytes *bytes)
156 : : {
157 : 3 : g_return_val_if_fail (bytes != NULL, NULL);
158 : :
159 : 3 : return g_object_new (G_TYPE_BYTES_ICON, "bytes", bytes, NULL);
160 : : }
161 : :
162 : : /**
163 : : * g_bytes_icon_get_bytes:
164 : : * @icon: a #GIcon.
165 : : *
166 : : * Gets the #GBytes associated with the given @icon.
167 : : *
168 : : * Returns: (transfer none): a #GBytes.
169 : : *
170 : : * Since: 2.38
171 : : **/
172 : : GBytes *
173 : 1 : g_bytes_icon_get_bytes (GBytesIcon *icon)
174 : : {
175 : 1 : g_return_val_if_fail (G_IS_BYTES_ICON (icon), NULL);
176 : :
177 : 1 : return icon->bytes;
178 : : }
179 : :
180 : : static guint
181 : 4 : g_bytes_icon_hash (GIcon *icon)
182 : : {
183 : 4 : GBytesIcon *bytes_icon = G_BYTES_ICON (icon);
184 : :
185 : 4 : return g_bytes_hash (bytes_icon->bytes);
186 : : }
187 : :
188 : : static gboolean
189 : 2 : g_bytes_icon_equal (GIcon *icon1,
190 : : GIcon *icon2)
191 : : {
192 : 2 : GBytesIcon *bytes1 = G_BYTES_ICON (icon1);
193 : 2 : GBytesIcon *bytes2 = G_BYTES_ICON (icon2);
194 : :
195 : 2 : return g_bytes_equal (bytes1->bytes, bytes2->bytes);
196 : : }
197 : :
198 : : static GVariant *
199 : 1 : g_bytes_icon_serialize (GIcon *icon)
200 : : {
201 : 1 : GBytesIcon *bytes_icon = G_BYTES_ICON (icon);
202 : :
203 : 1 : return g_variant_new ("(sv)", "bytes",
204 : : g_variant_new_from_bytes (G_VARIANT_TYPE_BYTESTRING, bytes_icon->bytes, TRUE));
205 : : }
206 : :
207 : : static void
208 : 3 : g_bytes_icon_icon_iface_init (GIconIface *iface)
209 : : {
210 : 3 : iface->hash = g_bytes_icon_hash;
211 : 3 : iface->equal = g_bytes_icon_equal;
212 : 3 : iface->serialize = g_bytes_icon_serialize;
213 : 3 : }
214 : :
215 : : static GInputStream *
216 : 1 : g_bytes_icon_load (GLoadableIcon *icon,
217 : : int size,
218 : : char **type,
219 : : GCancellable *cancellable,
220 : : GError **error)
221 : : {
222 : 1 : GBytesIcon *bytes_icon = G_BYTES_ICON (icon);
223 : :
224 : 1 : if (type)
225 : 0 : *type = NULL;
226 : :
227 : 1 : return g_memory_input_stream_new_from_bytes (bytes_icon->bytes);
228 : : }
229 : :
230 : : static void
231 : 1 : g_bytes_icon_load_async (GLoadableIcon *icon,
232 : : int size,
233 : : GCancellable *cancellable,
234 : : GAsyncReadyCallback callback,
235 : : gpointer user_data)
236 : : {
237 : 1 : GBytesIcon *bytes_icon = G_BYTES_ICON (icon);
238 : : GTask *task;
239 : :
240 : 1 : task = g_task_new (icon, cancellable, callback, user_data);
241 : 1 : g_task_set_source_tag (task, g_bytes_icon_load_async);
242 : 1 : g_task_return_pointer (task, g_memory_input_stream_new_from_bytes (bytes_icon->bytes), g_object_unref);
243 : 1 : g_object_unref (task);
244 : 1 : }
245 : :
246 : : static GInputStream *
247 : 1 : g_bytes_icon_load_finish (GLoadableIcon *icon,
248 : : GAsyncResult *res,
249 : : char **type,
250 : : GError **error)
251 : : {
252 : 1 : g_return_val_if_fail (g_task_is_valid (res, icon), NULL);
253 : :
254 : 1 : if (type)
255 : 0 : *type = NULL;
256 : :
257 : 1 : return g_task_propagate_pointer (G_TASK (res), error);
258 : : }
259 : :
260 : : static void
261 : 3 : g_bytes_icon_loadable_icon_iface_init (GLoadableIconIface *iface)
262 : : {
263 : 3 : iface->load = g_bytes_icon_load;
264 : 3 : iface->load_async = g_bytes_icon_load_async;
265 : 3 : iface->load_finish = g_bytes_icon_load_finish;
266 : 3 : }
|