Coverage Report

Created: 2026-02-10 07:39

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/poppler/glib/poppler-layer.cc
Line
Count
Source
1
/* poppler-layer.cc: glib interface to poppler
2
 *
3
 * Copyright (C) 2008 Carlos Garcia Campos <carlosgc@gnome.org>
4
 * Copyright (C) 2025 Albert Astals Cid <aacid@kde.org>
5
 *
6
 * This program is free software; you can redistribute it and/or modify
7
 * it under the terms of the GNU General Public License as published by
8
 * the Free Software Foundation; either version 2, or (at your option)
9
 * any later version.
10
 *
11
 * This program is distributed in the hope that it will be useful,
12
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14
 * GNU General Public License for more details.
15
 *
16
 * You should have received a copy of the GNU General Public License
17
 * along with this program; if not, write to the Free Software
18
 * Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA.
19
 */
20
21
#include "poppler-layer.h"
22
#include "poppler-private.h"
23
24
/**
25
 * SECTION:poppler-layer
26
 * @short_description: Layers
27
 * @title: PopplerLayer
28
 */
29
30
struct _PopplerLayerClass
31
{
32
    GObjectClass parent_class;
33
};
34
using PopplerLayerClass = _PopplerLayerClass;
35
36
0
G_DEFINE_TYPE(PopplerLayer, poppler_layer, G_TYPE_OBJECT)
37
0
38
0
static void poppler_layer_finalize(GObject *object)
39
0
{
40
0
    PopplerLayer *poppler_layer = POPPLER_LAYER(object);
41
42
0
    if (poppler_layer->document) {
43
0
        g_object_unref(poppler_layer->document);
44
0
        poppler_layer->document = nullptr;
45
0
    }
46
47
0
    if (poppler_layer->title) {
48
0
        g_free(poppler_layer->title);
49
0
        poppler_layer->title = nullptr;
50
0
    }
51
0
    poppler_layer->layer = nullptr;
52
0
    poppler_layer->rbgroup = nullptr;
53
54
0
    G_OBJECT_CLASS(poppler_layer_parent_class)->finalize(object);
55
0
}
56
57
0
static void poppler_layer_init(PopplerLayer * /*layer*/) { }
58
59
static void poppler_layer_class_init(PopplerLayerClass *klass)
60
0
{
61
0
    GObjectClass *gobject_class = G_OBJECT_CLASS(klass);
62
63
0
    gobject_class->finalize = poppler_layer_finalize;
64
0
}
65
66
PopplerLayer *_poppler_layer_new(PopplerDocument *document, Layer *layer, GList *rbgroup)
67
0
{
68
0
    PopplerLayer *poppler_layer;
69
0
    const GooString *layer_name;
70
71
0
    g_return_val_if_fail(POPPLER_IS_DOCUMENT(document), NULL);
72
0
    g_return_val_if_fail(layer != nullptr, NULL);
73
74
0
    poppler_layer = POPPLER_LAYER(g_object_new(POPPLER_TYPE_LAYER, nullptr));
75
76
0
    poppler_layer->document = (PopplerDocument *)g_object_ref(document);
77
0
    poppler_layer->layer = layer;
78
0
    poppler_layer->rbgroup = rbgroup;
79
0
    layer_name = layer->oc->getName();
80
0
    poppler_layer->title = layer_name ? _poppler_goo_string_to_utf8(layer_name) : nullptr;
81
82
0
    return poppler_layer;
83
0
}
84
85
/**
86
 * poppler_layer_get_title:
87
 * @layer: a #PopplerLayer
88
 *
89
 * Returns the name of the layer suitable for
90
 * presentation as a title in a viewer's GUI
91
 *
92
 * Return value: a string containing the title of the layer
93
 *
94
 * Since: 0.12
95
 **/
96
const gchar *poppler_layer_get_title(PopplerLayer *poppler_layer)
97
0
{
98
0
    g_return_val_if_fail(POPPLER_IS_LAYER(poppler_layer), NULL);
99
100
0
    return poppler_layer->title;
101
0
}
102
103
/**
104
 * poppler_layer_is_visible:
105
 * @layer: a #PopplerLayer
106
 *
107
 * Returns whether @layer is visible
108
 *
109
 * Return value: %TRUE if @layer is visible
110
 *
111
 * Since: 0.12
112
 **/
113
gboolean poppler_layer_is_visible(PopplerLayer *poppler_layer)
114
0
{
115
0
    g_return_val_if_fail(POPPLER_IS_LAYER(poppler_layer), FALSE);
116
117
0
    return poppler_layer->layer->oc->getState() == OptionalContentGroup::On;
118
0
}
119
120
/**
121
 * poppler_layer_show:
122
 * @layer: a #PopplerLayer
123
 *
124
 * Shows @layer
125
 *
126
 * Since: 0.12
127
 **/
128
void poppler_layer_show(PopplerLayer *poppler_layer)
129
0
{
130
0
    GList *l;
131
0
    Layer *layer;
132
133
0
    g_return_if_fail(POPPLER_IS_LAYER(poppler_layer));
134
135
0
    layer = poppler_layer->layer;
136
137
0
    if (layer->oc->getState() == OptionalContentGroup::On) {
138
0
        return;
139
0
    }
140
141
0
    layer->oc->setState(OptionalContentGroup::On);
142
143
0
    for (l = poppler_layer->rbgroup; l && l->data; l = g_list_next(l)) {
144
0
        auto *oc = (OptionalContentGroup *)l->data;
145
146
0
        if (oc != layer->oc) {
147
0
            oc->setState(OptionalContentGroup::Off);
148
0
        }
149
0
    }
150
0
}
151
152
/**
153
 * poppler_layer_hide:
154
 * @layer: a #PopplerLayer
155
 *
156
 * Hides @layer. If @layer is the parent of other nested layers,
157
 * such layers will be also hidden and will be blocked until @layer
158
 * is shown again
159
 *
160
 * Since: 0.12
161
 **/
162
void poppler_layer_hide(PopplerLayer *poppler_layer)
163
0
{
164
0
    Layer *layer;
165
166
0
    g_return_if_fail(POPPLER_IS_LAYER(poppler_layer));
167
168
0
    layer = poppler_layer->layer;
169
170
0
    if (layer->oc->getState() == OptionalContentGroup::Off) {
171
0
        return;
172
0
    }
173
174
0
    layer->oc->setState(OptionalContentGroup::Off);
175
0
}
176
177
/**
178
 * poppler_layer_is_parent:
179
 * @layer: a #PopplerLayer
180
 *
181
 * Returns whether @layer is parent of other nested layers.
182
 *
183
 * Return value: %TRUE if @layer is a parent layer
184
 *
185
 * Since: 0.12
186
 **/
187
gboolean poppler_layer_is_parent(PopplerLayer *poppler_layer)
188
0
{
189
0
    g_return_val_if_fail(POPPLER_IS_LAYER(poppler_layer), FALSE);
190
191
0
    return poppler_layer->layer->kids != nullptr;
192
0
}
193
194
/**
195
 * poppler_layer_get_radio_button_group_id:
196
 * @layer: a #PopplerLayer
197
 *
198
 * Returns the numeric ID the radio button group associated with @layer.
199
 *
200
 * Return value: the ID of the radio button group associated with @layer,
201
 * or 0 if the layer is not associated to any radio button group
202
 *
203
 * Since: 0.12
204
 **/
205
gint poppler_layer_get_radio_button_group_id(PopplerLayer *poppler_layer)
206
0
{
207
0
    g_return_val_if_fail(POPPLER_IS_LAYER(poppler_layer), FALSE);
208
209
0
    return GPOINTER_TO_INT(poppler_layer->rbgroup);
210
0
}