1 // SPDX-License-Identifier: GPL-2.0-or-later
2 /*
3 * Copyright (C) 2007 MenTaLguY <mental@rydia.net>
4 * Abhishek Sharma
5 *
6 * Released under GNU GPL v2+, read the file 'COPYING' for more information.
7 */
8
9 #include "style-subject.h"
10
11 #include "desktop.h"
12 #include "desktop-style.h"
13 #include "selection.h"
14
15 #include "xml/sp-css-attr.h"
16
17 namespace Inkscape {
18 namespace UI {
19 namespace Widget {
20
StyleSubject()21 StyleSubject::StyleSubject() : _desktop(nullptr) {
22 }
23
~StyleSubject()24 StyleSubject::~StyleSubject() {
25 setDesktop(nullptr);
26 }
27
setDesktop(SPDesktop * desktop)28 void StyleSubject::setDesktop(SPDesktop *desktop) {
29 if (desktop != _desktop) {
30 if (desktop) {
31 GC::anchor(desktop);
32 }
33 if (_desktop) {
34 GC::release(_desktop);
35 }
36 _desktop = desktop;
37 _afterDesktopSwitch(desktop);
38 _emitChanged();
39 }
40 }
41
42 StyleSubject::Selection::Selection() = default;
43
44 StyleSubject::Selection::~Selection() = default;
45
_getSelection() const46 Inkscape::Selection *StyleSubject::Selection::_getSelection() const {
47 SPDesktop *desktop = getDesktop();
48 if (desktop) {
49 return desktop->getSelection();
50 } else {
51 return nullptr;
52 }
53 }
54
list()55 std::vector<SPObject*> StyleSubject::Selection::list() {
56 Inkscape::Selection *selection = _getSelection();
57 if(selection) {
58 return std::vector<SPObject *>(selection->objects().begin(), selection->objects().end());
59 }
60
61 return std::vector<SPObject*>();
62 }
63
getBounds(SPItem::BBoxType type)64 Geom::OptRect StyleSubject::Selection::getBounds(SPItem::BBoxType type) {
65 Inkscape::Selection *selection = _getSelection();
66 if (selection) {
67 return selection->bounds(type);
68 } else {
69 return Geom::OptRect();
70 }
71 }
72
queryStyle(SPStyle * query,int property)73 int StyleSubject::Selection::queryStyle(SPStyle *query, int property) {
74 SPDesktop *desktop = getDesktop();
75 if (desktop) {
76 return sp_desktop_query_style(desktop, query, property);
77 } else {
78 return QUERY_STYLE_NOTHING;
79 }
80 }
81
_afterDesktopSwitch(SPDesktop * desktop)82 void StyleSubject::Selection::_afterDesktopSwitch(SPDesktop *desktop) {
83 _sel_changed.disconnect();
84 _subsel_changed.disconnect();
85 _sel_modified.disconnect();
86 if (desktop) {
87 _subsel_changed = desktop->connectToolSubselectionChanged(sigc::hide(sigc::mem_fun(*this, &Selection::_emitChanged)));
88 Inkscape::Selection *selection = desktop->getSelection();
89 if (selection) {
90 _sel_changed = selection->connectChanged(sigc::hide(sigc::mem_fun(*this, &Selection::_emitChanged)));
91 _sel_modified = selection->connectModified(sigc::mem_fun(*this, &Selection::_emitModified));
92 }
93 }
94 }
95
setCSS(SPCSSAttr * css)96 void StyleSubject::Selection::setCSS(SPCSSAttr *css) {
97 SPDesktop *desktop = getDesktop();
98 if (desktop) {
99 sp_desktop_set_style(desktop, css);
100 }
101 }
102
CurrentLayer()103 StyleSubject::CurrentLayer::CurrentLayer() {
104 _element = nullptr;
105 }
106
107 StyleSubject::CurrentLayer::~CurrentLayer() = default;
108
_setLayer(SPObject * layer)109 void StyleSubject::CurrentLayer::_setLayer(SPObject *layer) {
110 _layer_release.disconnect();
111 _layer_modified.disconnect();
112 if (_element) {
113 sp_object_unref(_element, nullptr);
114 }
115 _element = layer;
116 if (layer) {
117 sp_object_ref(layer, nullptr);
118 _layer_release = layer->connectRelease(sigc::hide(sigc::bind(sigc::mem_fun(*this, &CurrentLayer::_setLayer), (SPObject *)nullptr)));
119 _layer_modified = layer->connectModified(sigc::hide(sigc::hide(sigc::mem_fun(*this, &CurrentLayer::_emitChanged))));
120 }
121 _emitChanged();
122 }
123
_getLayer() const124 SPObject *StyleSubject::CurrentLayer::_getLayer() const {
125 return _element;
126 }
127
_getLayerSList() const128 SPObject *StyleSubject::CurrentLayer::_getLayerSList() const {
129 return _element;
130
131 }
132
list()133 std::vector<SPObject*> StyleSubject::CurrentLayer::list(){
134 std::vector<SPObject*> list;
135 list.push_back(_element);
136 return list;
137 }
138
getBounds(SPItem::BBoxType type)139 Geom::OptRect StyleSubject::CurrentLayer::getBounds(SPItem::BBoxType type) {
140 SPObject *layer = _getLayer();
141 if (layer && SP_IS_ITEM(layer)) {
142 return SP_ITEM(layer)->desktopBounds(type);
143 } else {
144 return Geom::OptRect();
145 }
146 }
147
queryStyle(SPStyle * query,int property)148 int StyleSubject::CurrentLayer::queryStyle(SPStyle *query, int property) {
149 std::vector<SPItem*> list;
150 SPObject* i=_getLayerSList();
151 if (i) {
152 list.push_back((SPItem*)i);
153 return sp_desktop_query_style_from_list(list, query, property);
154 } else {
155 return QUERY_STYLE_NOTHING;
156 }
157 }
158
setCSS(SPCSSAttr * css)159 void StyleSubject::CurrentLayer::setCSS(SPCSSAttr *css) {
160 SPObject *layer = _getLayer();
161 if (layer) {
162 sp_desktop_apply_css_recursive(layer, css, true);
163 }
164 }
165
_afterDesktopSwitch(SPDesktop * desktop)166 void StyleSubject::CurrentLayer::_afterDesktopSwitch(SPDesktop *desktop) {
167 _layer_switched.disconnect();
168 if (desktop) {
169 _layer_switched = desktop->connectCurrentLayerChanged(sigc::mem_fun(*this, &CurrentLayer::_setLayer));
170 _setLayer(desktop->currentLayer());
171 } else {
172 _setLayer(nullptr);
173 }
174 }
175
176 }
177 }
178 }
179
180 /*
181 Local Variables:
182 mode:c++
183 c-file-style:"stroustrup"
184 c-file-offsets:((innamespace . 0)(inline-open . 0)(case-label . +))
185 indent-tabs-mode:nil
186 fill-column:99
187 End:
188 */
189 // vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=8:softtabstop=4:fileencoding=utf-8:textwidth=99 :
190