]> git.ipfire.org Git - thirdparty/util-linux.git/blob - libsmartcols/src/column.c
Merge branch 'scols_fl_wrap' of https://github.com/ignatenkobrain/util-linux
[thirdparty/util-linux.git] / libsmartcols / src / column.c
1 /*
2 * column.c - functions for table handling at the column level
3 *
4 * Copyright (C) 2014 Ondrej Oprala <ooprala@redhat.com>
5 * Copyright (C) 2014 Karel Zak <kzak@redhat.com>
6 *
7 * This file may be redistributed under the terms of the
8 * GNU Lesser General Public License.
9 */
10
11 /**
12 * SECTION: column
13 * @title: Column
14 * @short_description: defines output columns formats, headers, etc.
15 *
16 * An API to access and modify per-column data and information.
17 */
18
19
20 #include <stdlib.h>
21 #include <unistd.h>
22 #include <string.h>
23 #include <ctype.h>
24
25 #include "smartcolsP.h"
26
27 /**
28 * scols_new_column:
29 *
30 * Allocates space for a new column.
31 *
32 * Returns: a pointer to a new struct libscols_cell instance, NULL in case of an ENOMEM error.
33 */
34 struct libscols_column *scols_new_column(void)
35 {
36 struct libscols_column *cl;
37
38 cl = calloc(1, sizeof(*cl));
39 if (!cl)
40 return NULL;
41 DBG(COL, ul_debugobj(cl, "alloc"));
42 cl->refcount = 1;
43 INIT_LIST_HEAD(&cl->cl_columns);
44 return cl;
45 }
46
47 /**
48 * scols_ref_column:
49 * @cl: a pointer to a struct libscols_column instance
50 *
51 * Increases the refcount of @cl.
52 */
53 void scols_ref_column(struct libscols_column *cl)
54 {
55 if (cl)
56 cl->refcount++;
57 }
58
59 /**
60 * scols_unref_column:
61 * @cl: a pointer to a struct libscols_column instance
62 *
63 * Decreases the refcount of @cl. When the count falls to zero, the instance
64 * is automatically deallocated.
65 */
66 void scols_unref_column(struct libscols_column *cl)
67 {
68 if (cl && --cl->refcount <= 0) {
69 DBG(COL, ul_debugobj(cl, "dealloc"));
70 list_del(&cl->cl_columns);
71 scols_reset_cell(&cl->header);
72 free(cl->color);
73 free(cl);
74 }
75 }
76
77 /**
78 * scols_copy_column:
79 * @cl: a pointer to a struct libscols_column instance
80 *
81 * Creates a new column and copies @cl's data over to it.
82 *
83 * Returns: a pointer to a new struct libscols_column instance.
84 */
85 struct libscols_column *scols_copy_column(const struct libscols_column *cl)
86 {
87 struct libscols_column *ret;
88
89 if (!cl)
90 return NULL;
91 ret = scols_new_column();
92 if (!ret)
93 return NULL;
94
95 DBG(COL, ul_debugobj((void *) cl, "copy to %p", ret));
96
97 if (scols_column_set_color(ret, cl->color))
98 goto err;
99 if (scols_cell_copy_content(&ret->header, &cl->header))
100 goto err;
101
102 ret->width = cl->width;
103 ret->width_min = cl->width_min;
104 ret->width_max = cl->width_max;
105 ret->width_avg = cl->width_avg;
106 ret->width_hint = cl->width_hint;
107 ret->flags = cl->flags;
108 ret->is_extreme = cl->is_extreme;
109
110 return ret;
111 err:
112 scols_unref_column(ret);
113 return NULL;
114 }
115
116 /**
117 * scols_column_set_whint:
118 * @cl: a pointer to a struct libscols_column instance
119 * @whint: a width hint
120 *
121 * Sets the width hint of column @cl to @whint.
122 *
123 * Returns: 0, a negative value in case of an error.
124 */
125 int scols_column_set_whint(struct libscols_column *cl, double whint)
126 {
127 if (!cl)
128 return -EINVAL;
129
130 cl->width_hint = whint;
131 return 0;
132 }
133
134 /**
135 * scols_column_get_whint:
136 * @cl: a pointer to a struct libscols_column instance
137 *
138 * Returns: The width hint of column @cl, a negative value in case of an error.
139 */
140 double scols_column_get_whint(struct libscols_column *cl)
141 {
142 assert(cl);
143 return cl ? cl->width_hint : -EINVAL;
144 }
145
146 /**
147 * scols_column_set_flags:
148 * @cl: a pointer to a struct libscols_column instance
149 * @flags: a flag mask
150 *
151 * Sets the flags of @cl to @flags.
152 *
153 * Returns: 0, a negative value in case of an error.
154 */
155 int scols_column_set_flags(struct libscols_column *cl, int flags)
156 {
157 if (!cl)
158 return -EINVAL;
159
160 if (cl->table) {
161 if (!(cl->flags & SCOLS_FL_TREE) && (flags & SCOLS_FL_TREE))
162 cl->table->ntreecols++;
163 else if ((cl->flags & SCOLS_FL_TREE) && !(flags & SCOLS_FL_TREE))
164 cl->table->ntreecols--;
165 }
166
167 cl->flags = flags;
168 return 0;
169 }
170
171 /**
172 * scols_column_get_flags:
173 * @cl: a pointer to a struct libscols_column instance
174 *
175 * Returns: The flag mask of @cl, a negative value in case of an error.
176 */
177 int scols_column_get_flags(struct libscols_column *cl)
178 {
179 assert(cl);
180 return cl ? cl->flags : -EINVAL;
181 }
182
183 /**
184 * scols_column_get_header:
185 * @cl: a pointer to a struct libscols_column instance
186 *
187 * Returns: A pointer to a struct libscols_cell instance, representing the
188 * header info of column @cl or NULL in case of an error.
189 */
190 struct libscols_cell *scols_column_get_header(struct libscols_column *cl)
191 {
192 return cl ? &cl->header : NULL;
193 }
194
195 /**
196 * scols_column_set_color:
197 * @cl: a pointer to a struct libscols_column instance
198 * @color: color name or ESC sequence
199 *
200 * The default color for data cells and column header.
201 *
202 * If you want to set header specific color then use scols_column_get_header()
203 * and scols_cell_set_color().
204 *
205 * If you want to set data cell specific color the use scols_line_get_cell() +
206 * scols_cell_set_color().
207 *
208 * Returns: 0, a negative value in case of an error.
209 */
210 int scols_column_set_color(struct libscols_column *cl, const char *color)
211 {
212 char *p = NULL;
213
214 if (!cl)
215 return -EINVAL;
216 if (color) {
217 if (isalpha(*color)) {
218 color = color_sequence_from_colorname(color);
219
220 if (!color)
221 return -EINVAL;
222 }
223 p = strdup(color);
224 if (!p)
225 return -ENOMEM;
226 }
227
228 free(cl->color);
229 cl->color = p;
230 return 0;
231 }
232
233 /**
234 * scols_column_get_color:
235 * @cl: a pointer to a struct libscols_column instance
236 *
237 * Returns: The current color setting of the column @cl.
238 */
239 const char *scols_column_get_color(struct libscols_column *cl)
240 {
241 assert(cl);
242 return cl ? cl->color : NULL;
243 }
244
245
246 /**
247 * scols_column_set_cmpfunc:
248 * @cl: column
249 * @cmp: pointer to compare function
250 * @data: private data for cmp function
251 *
252 * Returns: 0, a negative value in case of an error.
253 */
254 int scols_column_set_cmpfunc(struct libscols_column *cl,
255 int (*cmp)(struct libscols_cell *,
256 struct libscols_cell *,
257 void *),
258 void *data)
259 {
260 if (!cl)
261 return -EINVAL;
262
263 cl->cmpfunc = cmp;
264 cl->cmpfunc_data = data;
265 return 0;
266 }
267
268 /**
269 * scols_column_is_hidden:
270 * @cl: a pointer to a struct libscols_column instance
271 *
272 * Gets the value of @cl's flag hidden.
273 *
274 * Returns: hidden flag value, negative value in case of an error.
275 *
276 * Since: 2.27
277 */
278 int scols_column_is_hidden(struct libscols_column *cl)
279 {
280 if (!cl)
281 return -EINVAL;
282 return cl->flags & SCOLS_FL_HIDDEN;
283 }
284
285 /**
286 * scols_column_is_trunc:
287 * @cl: a pointer to a struct libscols_column instance
288 *
289 * Gets the value of @cl's flag trunc.
290 *
291 * Returns: trunc flag value, negative value in case of an error.
292 */
293 int scols_column_is_trunc(struct libscols_column *cl)
294 {
295 if (!cl)
296 return -EINVAL;
297 return cl->flags & SCOLS_FL_TRUNC;
298 }
299 /**
300 * scols_column_is_tree:
301 * @cl: a pointer to a struct libscols_column instance
302 *
303 * Gets the value of @cl's flag tree.
304 *
305 * Returns: tree flag value, negative value in case of an error.
306 */
307 int scols_column_is_tree(struct libscols_column *cl)
308 {
309 if (!cl)
310 return -EINVAL;
311 return cl->flags & SCOLS_FL_TREE;
312 }
313 /**
314 * scols_column_is_right:
315 * @cl: a pointer to a struct libscols_column instance
316 *
317 * Gets the value of @cl's flag right.
318 *
319 * Returns: right flag value, negative value in case of an error.
320 */
321 int scols_column_is_right(struct libscols_column *cl)
322 {
323 if (!cl)
324 return -EINVAL;
325 return cl->flags & SCOLS_FL_RIGHT;
326 }
327 /**
328 * scols_column_is_strict_width:
329 * @cl: a pointer to a struct libscols_column instance
330 *
331 * Gets the value of @cl's flag strict_width.
332 *
333 * Returns: strict_width flag value, negative value in case of an error.
334 */
335 int scols_column_is_strict_width(struct libscols_column *cl)
336 {
337 if (!cl)
338 return -EINVAL;
339 return cl->flags & SCOLS_FL_STRICTWIDTH;
340 }
341 /**
342 * scols_column_is_noextremes:
343 * @cl: a pointer to a struct libscols_column instance
344 *
345 * Gets the value of @cl's flag no_extremes.
346 *
347 * Returns: no_extremes flag value, negative value in case of an error.
348 */
349 int scols_column_is_noextremes(struct libscols_column *cl)
350 {
351 if (!cl)
352 return -EINVAL;
353 return cl->flags & SCOLS_FL_NOEXTREMES;
354 }
355 /**
356 * scols_column_is_wrap:
357 * @cl: a pointer to a struct libscols_column instance
358 *
359 * Gets the value of @cl's flag wrap.
360 *
361 * Returns: wrap flag value, negative value in case of an error.
362 */
363 int scols_column_is_wrap(struct libscols_column *cl)
364 {
365 if (!cl)
366 return -EINVAL;
367 return cl->flags & SCOLS_FL_WRAP;
368 }