1 // SPDX-License-Identifier: GPL-2.0-or-later
2 #ifndef SEEN_SP_CLIPPATH_H
3 #define SEEN_SP_CLIPPATH_H
4 
5 /*
6  * SVG <clipPath> implementation
7  *
8  * Authors:
9  *   Lauris Kaplinski <lauris@kaplinski.com>
10  *   Abhishek Sharma
11  *   Jon A. Cruz <jon@joncruz.org>
12  *
13  * Copyright (C) 2001-2002 authors
14  * Copyright (C) 2001 Ximian, Inc.
15  *
16  * Released under GNU GPL v2+, read the file 'COPYING' for more information.
17  */
18 
19 #include <cstdio>
20 #include "sp-object-group.h"
21 #include "display/drawing.h"
22 #include "display/drawing-group.h"
23 #include "uri-references.h"
24 #include "xml/node.h"
25 
26 #define SP_CLIPPATH(obj) (dynamic_cast<SPClipPath*>((SPObject*)obj))
27 #define SP_IS_CLIPPATH(obj) (dynamic_cast<const SPClipPath*>((SPObject*)obj) != NULL)
28 
29 namespace Inkscape {
30 
31 class Drawing;
32 class DrawingItem;
33 
34 } // namespace Inkscape
35 
36 
37 struct SPClipPathView {
38     SPClipPathView *next;
39     unsigned int key;
40     Inkscape::DrawingItem *arenaitem;
41     Geom::OptRect bbox;
42 };
43 
44 class SPClipPath : public SPObjectGroup {
45 public:
46 	SPClipPath();
47 	~SPClipPath() override;
48 
49     class Reference;
50 
51     unsigned int clipPathUnits_set : 1;
52     unsigned int clipPathUnits : 1;
53 
54     SPClipPathView *display;
55     static char const *create(std::vector<Inkscape::XML::Node*> &reprs, SPDocument *document);
56     //static GType sp_clippath_get_type(void);
57 
58     Inkscape::DrawingItem *show(Inkscape::Drawing &drawing, unsigned int key);
59     void hide(unsigned int key);
60 
61     void setBBox(unsigned int key, Geom::OptRect const &bbox);
62     Geom::OptRect geometricBounds(Geom::Affine const &transform);
63 
64 protected:
65     void build(SPDocument* doc, Inkscape::XML::Node* repr) override;
66 	void release() override;
67 
68 	void child_added(Inkscape::XML::Node* child, Inkscape::XML::Node* ref) override;
69 
70 	void set(SPAttr key, char const* value) override;
71 
72 	void update(SPCtx* ctx, unsigned int flags) override;
73 	void modified(unsigned int flags) override;
74 
75 	Inkscape::XML::Node* write(Inkscape::XML::Document* doc, Inkscape::XML::Node* repr, unsigned int flags) override;
76 };
77 
78 
79 class SPClipPathReference : public Inkscape::URIReference {
80 public:
SPClipPathReference(SPObject * obj)81     SPClipPathReference(SPObject *obj) : URIReference(obj) {}
getObject()82     SPClipPath *getObject() const {
83         return static_cast<SPClipPath *>(URIReference::getObject());
84     }
85 
86 protected:
87     /**
88      * If the owner element of this reference (the element with <... clippath="...">)
89      * is a child of the clippath it refers to, return false.
90      * \return false if obj is not a clippath or if obj is a parent of this
91      *         reference's owner element.  True otherwise.
92      */
_acceptObject(SPObject * obj)93     bool _acceptObject(SPObject *obj) const override {
94         if (!SP_IS_CLIPPATH(obj)) {
95             return false;
96         }
97         SPObject * const owner = this->getOwner();
98         if (!URIReference::_acceptObject(obj)) {
99             //XML Tree being used directly here while it shouldn't be...
100             Inkscape::XML::Node * const owner_repr = owner->getRepr();
101             //XML Tree being used directly here while it shouldn't be...
102             Inkscape::XML::Node * const obj_repr = obj->getRepr();
103             char const * owner_name = "";
104             char const * owner_clippath = "";
105             char const * obj_name = "";
106             char const * obj_id = "";
107             if (owner_repr != nullptr) {
108                 owner_name = owner_repr->name();
109                 owner_clippath = owner_repr->attribute("clippath");
110             }
111             if (obj_repr != nullptr) {
112                 obj_name = obj_repr->name();
113                 obj_id = obj_repr->attribute("id");
114             }
115             printf("WARNING: Ignoring recursive clippath reference "
116                       "<%s clippath=\"%s\"> in <%s id=\"%s\">",
117                       owner_name, owner_clippath,
118                       obj_name, obj_id);
119             return false;
120         }
121         return true;
122     }
123 };
124 
125 #endif // SEEN_SP_CLIPPATH_H
126 
127 /*
128   Local Variables:
129   mode:c++
130   c-file-style:"stroustrup"
131   c-file-offsets:((innamespace . 0)(inline-open . 0)(case-label . +))
132   indent-tabs-mode:nil
133   fill-column:99
134   End:
135 */
136 // vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=8:softtabstop=4:fileencoding=utf-8:textwidth=99 :
137