42#include <boost/range/adaptor/reversed.hpp>
43#include <glibmm/main.h>
44#include <glibmm/miscutils.h>
113 document_filename(nullptr),
114 document_base(nullptr),
115 document_name(nullptr),
117 object_id_counter(1),
118 _router(
std::make_unique<
Avoid::Router>(
Avoid::PolyLineRouting|
Avoid::OrthogonalRouting)),
119 current_persp3d(nullptr),
120 current_persp3d_impl(nullptr),
121 _activexmltree(nullptr)
125 _event_log = std::make_unique<Inkscape::EventLog>(
this);
126 _selection = std::make_unique<Inkscape::Selection>(
this);
129 sigc::hide(sigc::bind(
130 sigc::ptr_fun(&DocumentUndo::resetKey),
this)));
156 _page_manager = std::make_unique<Inkscape::PageManager>(
this);
157 _cms_manager = std::make_unique<Inkscape::Colors::DocumentCMS>(
this);
171 DocumentUndo::clearRedo(
this);
172 DocumentUndo::clearUndo(
this);
242 return cast<SPNamedView>(nv);
255 std::vector<Persp3D*> plist;
257 for (
auto & i : plist) {
276 if (
auto p = cast<Persp3D>(&
c)) {
277 list.emplace_back(p);
313 for (
auto page : pages) {
322 g_return_if_fail(
object !=
nullptr);
323 g_return_if_fail(object->
document ==
this);
333 for (
auto object : objects) {
334 object->collectOrphan();
342 char const *filename,
343 char const *document_base,
344 char const *document_name,
348 auto document = std::make_unique<SPDocument>();
354 document->rdoc =
rdoc;
355 document->rroot =
rroot;
356 document->_parent_document =
parent;
358 if (document->document_filename){
359 g_free(document->document_filename);
360 document->document_filename =
nullptr;
362 if (document->document_base){
363 g_free(document->document_base);
364 document->document_base =
nullptr;
366 if (document->document_name){
367 g_free(document->document_name);
368 document->document_name =
nullptr;
374 document->document_filename = filename? g_strdup(filename) : NULL;
383 document->document_base =
nullptr;
390 document->root = cast<SPRoot>(rootObj);
392 if (document->root ==
nullptr) {
410 auto nv = document->getNamedView();
413 nv->setDefaultAttribute(
"pagecolor",
"/template/base/pagecolor",
"#ffffff");
414 nv->setDefaultAttribute(
"bordercolor",
"/template/base/bordercolor",
"");
415 nv->setDefaultAttribute(
"borderopacity",
"/template/base/borderopacity",
"");
416 nv->setDefaultAttribute(
"inkscape:showpageshadow",
"/template/base/pageshadow",
"2");
417 nv->setDefaultAttribute(
"inkscape:pageopacity",
"/template/base/pageopacity",
"0.0");
418 nv->setDefaultAttribute(
"inkscape:pagecheckerboard",
"/template/base/pagecheckerboard",
"0");
419 nv->setDefaultAttribute(
"inkscape:deskcolor",
"/template/base/deskcolor",
"#d1d1d1");
423 if (document->root->width.isAbsolute()) {
424 nv->setDefaultAttribute(
"inkscape:document-units",
"", document->root->width.getUnit());
425 }
else if (document->root->height.isAbsolute()) {
426 nv->setDefaultAttribute(
"inkscape:document-units",
"", document->root->height.getUnit());
430 if (!document->root->defs) {
434 g_assert(document->root->defs);
447 if (!document->getCurrentPersp3D()) {
450 document->setCurrentPersp3DImpl(persp_impl);
453 DocumentUndo::setUndoSensitive(document.get(),
true);
461 document->root->inkscape.getVersion().isInsideRangeInclusive(lowest_version, {0, 92})) {
466 if (document->root->inkscape.getVersion().isInsideRangeInclusive(lowest_version, {0, 92})) {
471 if (document->root->inkscape.getVersion().isInsideRangeInclusive(lowest_version, {1, 0})) {
476 if (document->root->inkscape.getVersion().isInsideRangeInclusive(lowest_version, {1, 1})) {
481 if (document->root->inkscape.getVersion().isInsideRangeInclusive(lowest_version, {1, 2})) {
486 std::string version = document->root->inkscape.getVersion().str();
487 if (version.size() > 4) {
489 if (version ==
"1.3.1") {
490 document->getRoot()->updateRepr(SP_OBJECT_CHILD_MODIFIED_FLAG);
494 if (!(INKSCAPE.use_gui()) &&
495 document->root->inkscape.getVersion().isInsideRangeInclusive(lowest_version, {0, 92})) {
527 doc->_original_document =
this;
540 g_warning(
"Error on rebase_doc: no file.");
546 rebase(new_xmldoc, keep_namedview);
548 g_warning(
"Error on rebase_doc: The file could not be parsed.");
567 if (new_xmldoc ==
nullptr)
569 g_warning(
"Error on rebase_doc: NULL pointer input.");
578 if (!g_strcmp0(
child->name(),
"sodipodi:namedview") && keep_namedview) {
587 if (!g_strcmp0(
child->name(),
"sodipodi:namedview") && keep_namedview) {
597 origin_xmldoc->
root()->
setAttribute(g_quark_to_string(iter.key), iter.value);
610 g_warning(
"Error on rebase_doc: NULL file");
623 for (
auto doc =
this; doc; doc = doc->_parent_document) {
625 if (
auto ret = doc->_searchForChild(filename, avoid)) {
632 auto const path = Glib::path_is_absolute(filename)
636 auto doc =
createNewDoc(path.c_str(),
false,
false,
this);
651 if (
auto ret =
c->_searchForChild(filename, avoid)) {
679 if (
rdoc ==
nullptr)
return nullptr;
683 if (strcmp(
rroot->
name(),
"svg:svg") != 0)
return nullptr;
725 if (std::strcmp(
rdoc->
root()->
name(),
"svg:svg") != 0) {
744 return nv->getDisplayUnit();
746 return UnitTable::get().getUnit(
"px");
751 if (scaleX <= 0 || scaleY <= 0) {
752 g_warning(
"%s: Invalid scale, has to be positive: %f, %f", __func__, scaleX, scaleY);
777 double scale_x = 1.0;
778 double scale_y = 1.0;
798 bool transform_stroke = prefs->
getBool(
"/options/transform/stroke",
true);
799 bool transform_rectcorners = prefs->
getBool(
"/options/transform/rectcorners",
true);
800 bool transform_pattern = prefs->
getBool(
"/options/transform/pattern",
true);
801 bool transform_gradient = prefs->
getBool(
"/options/transform/gradient",
true);
803 prefs->
setBool(
"/options/transform/stroke",
true);
804 prefs->
setBool(
"/options/transform/rectcorners",
true);
805 prefs->
setBool(
"/options/transform/pattern",
true);
806 prefs->
setBool(
"/options/transform/gradient",
true);
811 prefs->
setBool(
"/options/transform/stroke", transform_stroke);
812 prefs->
setBool(
"/options/transform/rectcorners", transform_rectcorners);
813 prefs->
setBool(
"/options/transform/pattern", transform_pattern);
814 prefs->
setBool(
"/options/transform/gradient", transform_gradient);
821 auto const &unit_table = UnitTable::get();
825 gdouble old_width_converted;
838 gdouble old_height_converted;
859 auto const &unit_table = UnitTable::get();
876 auto const &unit_table = UnitTable::get();
880 gdouble old_width_converted;
898 auto const &unit_table = UnitTable::get();
915 auto const &unit_table = UnitTable::get();
919 gdouble old_height_converted;
989 return page->getDesktopRect();
1005 auto const &unit_table = UnitTable::get();
1006 Unit const *nv_units = unit_table.getUnit(
"px");
1032 nv->translateGuides(gadget_translation);
1037 Quantity(Quantity::convert(rect.
height(),
"px", nv_units), nv_units));
1042 nv->translateGrids(gadget_translation);
1046 nv->scrollAllDesktops(-tr_x, -tr_y_gadgets *
yaxisdir());
1052 if (this->document_base) {
1053 g_free(this->document_base);
1054 this->document_base =
nullptr;
1063 gchar *new_document_base =
nullptr;
1064 gchar *new_document_name =
nullptr;
1065 gchar *new_document_filename =
nullptr;
1072 new_document_filename = g_strdup(filename);
1075 new_document_base = g_path_get_dirname(new_document_filename);
1076 new_document_name = g_path_get_basename(new_document_filename);
1078 new_document_name = g_strdup_printf(_(
"Unnamed document %d"), ++
doc_count);
1079 new_document_base =
nullptr;
1080 new_document_filename =
nullptr;
1092 bool use_sodipodi_absref = prefs->
getBool(
"/options/svgoutput/usesodipodiabsref",
false);
1096 if (strncmp(new_document_name,
"ink_ext_XXXXXX", 14))
1097 repr->
setAttribute(
"sodipodi:docname", new_document_name);
1135 GQuark idq = g_quark_from_string(
id);
1138 if(object->
getId()) {
1141 auto ret =
iddef.emplace(
id,
object);
1142 g_assert(ret.second);
1144 auto it =
iddef.find(
id);
1145 g_assert(it !=
iddef.end());
1151 if (!pos->second.empty()) {
1152 pos->second.emit(
object);
1161 if (
iddef.empty())
return nullptr;
1163 if (
auto rv =
iddef.find(
id); rv !=
iddef.end()) {
1176 if (!
id ||
iddef.empty())
return nullptr;
1178 if (
auto rv =
iddef.find(
id); rv !=
iddef.end()) {
1191 if (
iddef.empty())
return nullptr;
1192 auto id = href.substr(1);
1198 if (!href || href[0] ==
'\0')
return nullptr;
1207 if (
auto const temp =
parent->getAttribute(
"class")) {
1208 std::istringstream classes(temp);
1209 Glib::ustring token;
1210 while (classes >> token) {
1212 if (classes.str() ==
" ") {
1216 if (token == klass) {
1217 objects.emplace_back(
parent);
1231 if (klass.empty())
return {};
1232 std::vector<SPObject*> objects;
1239 std::vector<SPObject*> &objects,
1244 Glib::ustring prefixed =
custom ?
"inkscape:" :
"svg:";
1245 prefixed += element;
1246 if (
parent->getRepr()->name() == prefixed) {
1247 objects.emplace_back(
parent);
1258 if (element.empty())
return {};
1259 std::vector<SPObject*> objects;
1266 std::vector<SPObject*> &objects)
1272 objects.push_back(
parent);
1284 if (selector.empty())
return {};
1286 static CRSelEng *sel_eng =
nullptr;
1293 std::vector<SPObject*> objects;
1294 for (
auto cur = cr_selector; cur; cur = cur->next) {
1295 if (cur->simple_sel) {
1306 auto result = std::string(prefix);
1307 auto const prefix_len =
result.size();
1325 auto ret =
reprdef.emplace(repr,
object);
1326 g_assert(ret.second);
1329 g_assert(it !=
reprdef.end());
1337 if (!repr)
return nullptr;
1339 return it ==
reprdef.end() ? nullptr : it->second;
1350 std::vector<Glib::ustring> document_languages;
1355 gchar *rdf_language_stripped = g_strstrip(g_strdup(rdf_language));
1356 if (strcmp(rdf_language_stripped,
"") != 0) {
1357 document_languages.emplace_back(rdf_language_stripped);
1359 g_free(rdf_language_stripped);
1367 if (document_languages.empty()) {
1368 return parent_languages;
1372 std::move(parent_languages.begin(), parent_languages.end(),
1373 std::back_insert_iterator(document_languages));
1376 return document_languages;
1382 const gchar *
const * names = g_get_language_names();
1383 for (
int i=0; names[i]; i++) {
1384 document_languages.emplace_back(names[i]);
1387 return document_languages;
1421 if (!
root)
return false;
1432 if (!
root)
return 0;
1436 if (nv->is_y_axis_down()) {
1460 nv->fix_guidelines();
1461 nv->updateViewPort();
1463 for (
auto&
child : nv->children) {
1464 child.requestDisplayUpdate(SP_OBJECT_MODIFIED_FLAG);
1502 for (
unsigned int pass = 1; pass <= 2; ++pass) {
1506 g_warning(
"More than 32 iteration while updating document '%s'",
document_filename);
1520 _router->processTransaction();
1554 _router->processTransaction();
1586 SPGroup *group,
unsigned int dkey,
1589 bool take_hidden =
false,
1590 bool take_insensitive =
false,
1591 bool take_groups =
true,
1592 bool enter_groups =
false,
1593 bool enter_layers =
true)
1595 g_return_val_if_fail(group, s);
1598 if (
auto item = cast<SPItem>(&o)) {
1607 if (
auto childgroup = cast<SPGroup>(
item)) {
1608 bool is_layer = childgroup->effectiveLayerMode(dkey) ==
SPGroup::LAYER;
1609 if ((enter_layers && is_layer) || (enter_groups)) {
1610 s =
find_items_in_area(s, childgroup, dkey, area,
test, take_hidden, take_insensitive, take_groups, enter_groups, enter_layers);
1612 if (!take_groups || (enter_layers && is_layer)) {
1617 if (box &&
test(area, *box)) {
1632 std::optional<bool> outline;
1635 if (
auto item = cast<SPItem>(&
c)) {
1638 if (
auto cid = di->drawing().getCanvasItemDrawing()) {
1639 auto canvas = cid->get_canvas();
1640 outline = canvas->canvas_point_in_outline_zone(p - canvas->get_pos());
1644 if (std::find(list.begin(), list.end(),
item) != list.end()) {
1650 if (
auto group = cast<SPGroup>(
item)) {
1664 if (!is<SPItem>(&o)) {
1668 if (is<SPGroup>(&o) && (cast<SPGroup>(&o)->effectiveLayerMode(dkey) ==
SPGroup::LAYER || into_groups)) {
1671 auto child = cast<SPItem>(&o);
1672 if (!active_only ||
child->isVisibleAndUnlocked(dkey)) {
1687 auto const key = (key_t{dkey} << 2) | (into_groups << 1) | active_only;
1709 std::optional<bool> outline;
1711 std::vector<SPItem*>
result;
1713 bool seen_upto = !upto;
1714 for (
auto node : nodes) {
1721 if (
auto di =
node->get_arenaitem(dkey)) {
1723 if (
auto cid = di->drawing().getCanvasItemDrawing()) {
1724 auto canvas = cid->get_canvas();
1725 outline = canvas->canvas_point_in_outline_zone(p - canvas->get_pos());
1730 if (--items_count == 0) {
1743 if (
items.empty()) {
1746 return items.back();
1756 std::optional<bool> outline;
1758 for (
auto &
c : boost::adaptors::reverse(group->
children)) {
1759 if (
auto group = cast<SPGroup>(&
c)) {
1766 if (
auto cid = di->drawing().getCanvasItemDrawing()) {
1767 auto canvas = cid->get_canvas();
1768 outline = canvas->canvas_point_in_outline_zone(p - canvas->get_pos());
1787std::vector<SPItem*>
SPDocument::getItemsInBox(
unsigned int dkey,
Geom::Rect const &box,
bool take_hidden,
bool take_insensitive,
bool take_groups,
bool enter_groups,
bool enter_layers)
const
1789 std::vector<SPItem*> x;
1806 std::vector<SPItem*> x;
1812 std::vector<SPItem*>
result;
1818 gdouble saved_delta = prefs->
getDouble(
"/options/cursortolerance/value", 1.0);
1819 prefs->
setDouble(
"/options/cursortolerance/value", 0.25);
1828 size_t item_counter = 0;
1829 for(
auto point : points) {
1837 if(item_counter ==
limit){
1838 prefs->
setDouble(
"/options/cursortolerance/value", saved_delta);
1846 prefs->
setDouble(
"/options/cursortolerance/value", saved_delta);
1852 bool const into_groups,
SPItem *upto)
const
1866 g_return_val_if_fail(
key !=
nullptr,
false);
1867 g_return_val_if_fail(*
key !=
'\0',
false);
1868 g_return_val_if_fail(
object !=
nullptr,
false);
1874 g_return_val_if_fail(std::find(rlist.begin(),rlist.end(),
object) == rlist.end(),
false);
1885 if (object->
getId() || is<SPGroup>(
object) || is<SPPage>(
object)) {
1899 g_return_val_if_fail(
key !=
nullptr,
false);
1900 g_return_val_if_fail(*
key !=
'\0',
false);
1901 g_return_val_if_fail(
object !=
nullptr,
false);
1907 g_return_val_if_fail(!rlist.empty(),
false);
1909 g_return_val_if_fail(it != rlist.end(),
false);
1923 std::vector<SPObject *> emptyset;
1924 g_return_val_if_fail(
key !=
nullptr, emptyset);
1925 g_return_val_if_fail(*
key !=
'\0', emptyset);
1970 if (is<SPDefs>(obj)) {
1973 def.requestOrphanCollection();
1991 unsigned int newend =
start;
1993 unsigned int iterations = 0;
2004 }
while (iterations < 100 && newend <
end);
2007 return start - newend;
2035 for (
auto & defsNode : defsNodes) {
2080 std::string DuplicateDefString =
"RESERVED_FOR_INKSCAPE_DUPLICATE_DEF";
2088 Glib::ustring defid = def->attribute(
"id");
2089 if( defid.find( DuplicateDefString ) != Glib::ustring::npos )
break;
2094 auto s_gr = cast<SPGradient>(src);
2095 auto s_lpeobj = cast<LivePathEffectObject>(src);
2096 if (src && (s_gr || s_lpeobj)) {
2098 auto t_gr = cast<SPGradient>(&trg);
2099 if (src != &trg && s_gr && t_gr) {
2100 if (s_gr->isEquivalent(t_gr)) {
2102 Glib::ustring newid = trg.getId();
2103 if (newid != defid) {
2106 gchar *longid = g_strdup_printf(
"%s_%9.9d", DuplicateDefString.c_str(), stagger++);
2107 def->setAttribute(
"id", longid);
2112 auto t_lpeobj = cast<LivePathEffectObject>(&trg);
2113 if (src != &trg && s_lpeobj && t_lpeobj) {
2114 if (t_lpeobj->is_similar(s_lpeobj)) {
2116 Glib::ustring newid = trg.getId();
2117 if (newid != defid) {
2120 gchar *longid = g_strdup_printf(
"%s_%9.9d", DuplicateDefString.c_str(), stagger++);
2121 def->setAttribute(
"id", longid);
2133 Glib::ustring defid = def->attribute(
"id");
2134 if( defid.find( DuplicateDefString ) != Glib::ustring::npos )
continue;
2136 auto s_lpeobj = cast<LivePathEffectObject>(src);
2137 auto s_gr = cast<SPGradient>(src);
2138 if (src && (s_gr || s_lpeobj)) {
2141 auto t_gr = cast<SPGradient>(trg);
2142 if (trg && (src != trg) && s_gr && t_gr) {
2143 Glib::ustring newid = trg->
getId();
2144 if (newid.find(DuplicateDefString) != Glib::ustring::npos)
2146 if (t_gr && s_gr->isEquivalent(t_gr)) {
2150 gchar *longid = g_strdup_printf(
"%s_%9.9d", DuplicateDefString.c_str(), stagger++);
2151 laterDef->setAttribute(
"id", longid);
2156 auto t_lpeobj = cast<LivePathEffectObject>(trg);
2157 if (trg && (src != trg) && s_lpeobj && t_lpeobj) {
2158 Glib::ustring newid = trg->
getId();
2159 if (newid.find(DuplicateDefString) != Glib::ustring::npos)
2161 if (t_lpeobj->is_similar(s_lpeobj)) {
2165 gchar *longid = g_strdup_printf(
"%s_%9.9d", DuplicateDefString.c_str(), stagger++);
2166 laterDef->setAttribute(
"id", longid);
2180 Glib::ustring defid = def->attribute(
"id");
2181 if( defid.find( DuplicateDefString ) != Glib::ustring::npos )
continue;
2183 bool duplicate =
false;
2189 if (src && is<SPSymbol>(src)) {
2192 size_t pos =
id.find(
"_inkscape_duplicate" );
2193 if( pos != Glib::ustring::npos ) {
2200 if (is<SPSymbol>(&trg) && src != &trg) {
2201 Glib::ustring id2 = trg.getRepr()->attribute(
"id");
2203 if( !
id.compare( id2 ) ) {
2263 SPDocument::IDChangedSignal::slot_type slot)
2269 SPDocument::ResourcesChangedSignal::slot_type slot)
2294 static guint
const flags = SP_OBJECT_MODIFIED_FLAG | SP_OBJECT_CHILD_MODIFIED_FLAG | SP_OBJECT_PARENT_MODIFIED_FLAG;
2331 g_assert(inject_into);
2337 _parent->set_reference_document(
nullptr);
2342 return nv->get_origin_follows_page();
void add_actions_edit_document(SPDocument *document)
Authors: Sushant A A sushant.co19@gmail.com
void add_document_actions_effect(SPDocument *doc)
Authors: Sushant A A sushant.co19@gmail.com
void add_actions_pages(SPDocument *doc)
void add_actions_processing(SPDocument *doc)
void add_actions_undo_document(SPDocument *document)
Actions for Undo/Redo tied to document.
3x3 matrix representing an affine transformation.
static CRect from_xywh(Coord x, Coord y, Coord w, Coord h)
Create rectangle from origin and dimensions.
C right() const
Return rightmost coordinate of the rectangle (+X is to the right).
bool contains(GenericRect< C > const &r) const
Check whether the rectangle includes all points in the given rectangle.
bool intersects(GenericRect< C > const &r) const
Check whether the rectangles have any common points.
C top() const
Return top coordinate of the rectangle (+Y is downwards).
void setMax(CPoint const &p)
Set the lower right point of the rectangle.
C left() const
Return leftmost coordinate of the rectangle (+X is to the right).
C height() const
Get the vertical extent of the rectangle.
C width() const
Get the horizontal extent of the rectangle.
CPoint min() const
Get the corner of the rectangle with smallest coordinate values.
C bottom() const
Return bottom coordinate of the rectangle (+Y is downwards).
CPoint max() const
Get the corner of the rectangle with largest coordinate values.
Axis-aligned rectangle that can be empty.
Two-dimensional point that doubles as a vector.
Axis aligned, non-empty rectangle.
void add(UndoStackObserver &observer)
Add an UndoStackObserver.
void remove(UndoStackObserver &observer)
Remove an UndoStackObserver.
RAII-style mechanism for creating a temporary undo-insensitive context.
SPObject * layerForObject(SPObject *object)
Return layer that contains object.
SPGroup * currentLayer() const
Returns current top layer.
Preference storage class.
bool getBool(Glib::ustring const &pref_path, bool def=false)
Retrieve a Boolean value.
double getDouble(Glib::ustring const &pref_path, double def=0.0, Glib::ustring const &unit="")
Retrieve a floating point value.
static Preferences * get()
Access the singleton Preferences object.
void setDouble(Glib::ustring const &pref_path, double value)
Set a floating point value.
void setBool(Glib::ustring const &pref_path, bool value)
Set a Boolean value.
Observes changes made to the undo and redo stacks.
static double convert(double from_dist, Unit const *from, Unit const *to)
Convert distances.
Interface for refcounted XML nodes.
virtual Node * next()=0
Get the next sibling of this node.
virtual void addChild(Node *child, Node *after)=0
Insert another node as a child of this node.
virtual void appendChild(Node *child)=0
Append a node as the last child of this node.
virtual char const * name() const =0
Get the name of the element node.
virtual const AttributeVector & attributeList() const =0
Get a list of the node's attributes.
void addChildAtPos(Node *child, unsigned pos)
Insert another node as a child of this node.
void setAttribute(Util::const_char_ptr key, Util::const_char_ptr value)
Change an attribute of this node.
virtual Node * duplicate(Document *doc) const =0
Create a duplicate of this node.
virtual Node * firstChild()=0
Get the first child of this node.
virtual void mergeFrom(Node const *src, char const *key, bool extension=false, bool clean=false)=0
Merge all children of another node with the current.
virtual char const * attribute(char const *key) const =0
Get the string representation of a node's attribute.
void removeAttribute(Inkscape::Util::const_char_ptr key)
Remove an attribute of this node.
virtual void removeChild(Node *child)=0
Remove a child of this node.
virtual Node * lastChild()=0
Get the last child of this node.
virtual Node * root()=0
Get the root node of this node's document.
static Persp3D * document_first_persp(SPDocument *document)
To do: update description of desktop.
Inkscape::LayerManager & layerManager()
Typed SVG document implementation.
bool get_origin_follows_page()
std::vector< SPObject * > _collection_queue
Orphans.
void scaleContentBy(Geom::Scale const &delta)
Scale the content, used by file-update and document properties when modifying the the document's view...
void setDocumentFilename(char const *filename)
A filename, or NULL.
CRCascade * style_cascade
static std::unique_ptr< SPDocument > createDoc(Inkscape::XML::Document *rdoc, char const *filename, char const *base, char const *name, bool keepalive, SPDocument *parent=nullptr)
std::vector< SPObject * > getObjectsByClass(Glib::ustring const &klass) const
void prunePages(const std::string &page_nums, bool invert=false)
Remove pages in bulk using the integer range format "1,2,3-4" etc.
std::vector< std::unique_ptr< SPDocument > > _child_documents
void setCurrentPersp3D(Persp3D *const persp)
Inkscape::XML::Document * rdoc
Our Inkscape::XML::Document.
const Geom::Affine & doc2dt() const
Document to desktop coordinate transformation.
void importDefs(SPDocument *source)
Paste SVG defs from the document retrieved from the clipboard or imported document into the active do...
bool removeResource(char const *key, SPObject *object)
Inkscape::XML::Event * partial
SPDocument::ModifiedSignal modified_signal
std::vector< SPItem * > getItemsAtPoints(unsigned const key, std::vector< Geom::Point > points, bool all_layers=true, bool topmost_only=true, size_t limit=0, bool active_only=true) const
Glib::RefPtr< Gio::SimpleActionGroup > action_group
std::map< std::string, std::vector< SPObject * > > resources
static int get_new_doc_number()
void _emitModified(unsigned int object_modified_tag=0)
static std::unique_ptr< SPDocument > createNewDocFromMem(std::span< char const > buffer, bool keepalive, std::string const &filename="")
void setWidthAndHeight(const Inkscape::Util::Quantity &width, const Inkscape::Util::Quantity &height, bool changeSize=true)
SPRoot * getRoot()
Returns our SPRoot.
static SPItem * getItemFromListAtPointBottom(unsigned int dkey, SPGroup *group, const std::vector< SPItem * > &list, Geom::Point const &p, bool take_insensitive=false)
Returns the bottommost item from the list which is at the point, or NULL if none.
SPDocument::CommitSignal commit_signal
double update_desktop_affine()
Update desktop transform after Y-axis orientation change.
std::unique_ptr< SPDocument > copy() const
Create a copy of the document, useful for modifying during save & export.
SPDocument * get_reference_document()
sigc::connection connectResourcesChanged(char const *key, SPDocument::ResourcesChangedSignal::slot_type slot)
std::string generate_unique_id(char const *prefix)
Generate a document-wide unique id.
bool addResource(char const *key, SPObject *object)
bool idle_handler()
An idle handler to update the document.
std::unique_ptr< Inkscape::Colors::DocumentCMS > _cms_manager
SPObject * getObjectById(std::string const &id) const
sigc::signal< void()> destroySignal
void setWidth(const Inkscape::Util::Quantity &width, bool changeSize=true)
void _importDefsNode(SPDocument *source, Inkscape::XML::Node *defs, Inkscape::XML::Node *target_defs)
char * document_base
To be used for resolving relative hrefs.
SPDocument * _parent_document
SPDocument::FilenameSetSignal filename_set_signal
Inkscape::CompositeUndoStackObserver undoStackObservers
void setModifiedSinceSave(bool const modified=true)
Indicate to the user if the document has been modified since the last save by displaying a "*" in fro...
void setupViewport(SPItemCtx *ctx)
void fitToRect(Geom::Rect const &rect, bool with_margins=false)
Given a Geom::Rect that may, for example, correspond to the bbox of an object, this function fits the...
Inkscape::Util::Quantity getWidth() const
void process_pending_resource_changes()
void addUndoObserver(Inkscape::UndoStackObserver &observer)
Add the observer to the document's undo listener The caller is in charge of freeing any memory alloca...
sigc::connection connectSavedOrModified(sigc::slot< void()> &&slot)
std::deque< SPItem * > const & get_flat_item_list(unsigned int dkey, bool into_groups, bool active_only) const
Turn the SVG DOM into a cached flat list of nodes that can be searched from top-down.
std::unique_ptr< Inkscape::PageManager > _page_manager
std::vector< SPObject * > const getResourceList(char const *key)
Geom::Point getDimensions() const
sigc::connection _desktop_activated_connection
bool rerouting_handler()
An idle handler to reroute connectors in the document.
Persp3D * current_persp3d
Currently 'active' perspective (to which, e.g., newly created boxes are attached)
sigc::connection connectBeforeCommit(BeforeCommitSignal::slot_type slot)
Geom::Rect getViewBox() const
std::vector< SPItem * > getItemsPartiallyInBox(unsigned int dkey, Geom::Rect const &box, bool take_hidden=false, bool take_insensitive=false, bool take_groups=true, bool enter_groups=false, bool enter_layers=true) const
Get items whose bounding box overlaps with given area.
Inkscape::XML::Node * getReprRoot()
Geom::OptRect preferredBounds() const
std::unique_ptr< Inkscape::Selection > _selection
Geom::OptRect pageBounds()
Returns the position of the selected page or the preferredBounds()
SPDocument::BeforeCommitSignal before_commit_signal
SPDocument::ReconstructionStart _reconstruction_start_signal
sigc::connection connectModified(ModifiedSignal::slot_type slot)
sigc::signal< void(double)> _y_axis_flipped
unsigned int vacuumDocument()
Remove unused definitions etc.
void setHeight(const Inkscape::Util::Quantity &height, bool changeSize=true)
sigc::connection modified_connection
void getPerspectivesInDefs(std::vector< Persp3D * > &list) const
void setDocumentBase(char const *document_base)
To be used for resolving relative hrefs.
ResourcesChangedSignalMap resources_changed_signals
void emitReconstructionFinish()
bool has_yaxis_orientation_changed()
Detect Y-axis orientation change.
double yaxisdir() const
"1" if the desktop Y-axis points down, "-1" if it points up.
std::vector< SPItem * > getItemsInBox(unsigned int dkey, Geom::Rect const &box, bool take_hidden=false, bool take_insensitive=false, bool take_groups=true, bool enter_groups=false, bool enter_layers=true) const
Return list of items, contained in box.
void bindObjectToId(char const *id, SPObject *object)
std::queue< GQuark > pending_resource_changes
bool modified_since_autosave
void removeUndoObserver(Inkscape::UndoStackObserver &observer)
bool _updateDocument(int flags, unsigned int object_modified_tag=0)
Tries to update the document state based on the modified and "update required" flags,...
bool keepalive
false if temporary document (e.g. to generate a PNG for display in a dialog).
SPDefs * getDefs()
Return the main defs object for the document.
SPDocument * createChildDoc(std::string const &filename)
Fetches a document and attaches it to the current document as a child href.
std::map< unsigned long, std::deque< SPItem * > > _node_cache
void set_origin_follows_page(bool on)
std::vector< SPObject * > getObjectsByElement(Glib::ustring const &element, bool custom=false) const
char * document_filename
A filename, or NULL.
static std::unique_ptr< SPDocument > createNewDoc(char const *filename, bool keepalive, bool make_new=false, SPDocument *parent=nullptr)
Fetches document from filename, or creates new, if NULL; public document appears in document list.
Inkscape::XML::Document * getReprDoc()
Our Inkscape::XML::Document.
sigc::connection connectReconstructionFinish(ReconstructionFinish::slot_type slot)
SPDocument * _searchForChild(std::string const &filename, SPDocument const *avoid=nullptr)
sigc::signal< void()> _saved_or_modified_signal
unsigned long object_id_counter
void rebase(Inkscape::XML::Document *new_xmldoc, bool keep_namedview=true)
SPDocument::ReconstructionFinish _reconstruction_finish_signal
Inkscape::ConsoleOutputUndoObserver console_output_undo_observer
void bindObjectToRepr(Inkscape::XML::Node *repr, SPObject *object)
void setDocumentScale(const double scaleX, const double scaleY)
Sets document scale (by changing viewBox)
char * document_name
basename or other human-readable label for the document.
std::vector< Glib::ustring > getLanguages() const
Returns preferred document languages (from most to least preferred)
std::unique_ptr< Inkscape::EventLog > _event_log
void queueForOrphanCollection(SPObject *object)
sigc::connection connectFilenameSet(FilenameSetSignal::slot_type slot)
void do_change_filename(char const *const filename, bool const rebase)
int ensureUpToDate(unsigned int object_modified_tag=0)
Repeatedly works on getting the document updated, since sometimes it takes more than one pass to get ...
std::unique_ptr< Avoid::Router > _router
SPDocument * _ref_document
bool is_yaxisdown() const
True if the desktop Y-axis points down, false if it points up.
SPObject * getObjectByHref(std::string const &href) const
SPObject * getObjectByRepr(Inkscape::XML::Node *repr) const
void set_reference_document(SPDocument *document)
Set the reference document object.
IDChangedSignalMap id_changed_signals
Dictionary of signals for id changes.
sigc::connection connectIdChanged(const char *id, IDChangedSignal::slot_type slot)
sigc::connection connectReconstructionStart(ReconstructionStart::slot_type slot, bool first=false)
SPNamedView * getNamedView()
Get the namedview for this document, creates it if it's not found.
void changeFilenameAndHrefs(char const *filename)
Changes the base, name and filename members of document, and updates any relative hrefs in the docume...
Persp3D * getCurrentPersp3D()
Geom::Scale getDocumentScale(bool computed=true) const
Returns document scale as defined by width/height (in pixels) and viewBox (real world to user-units).
void setViewBox()
Set default viewbox calculated from document properties.
SPItem * getGroupAtPoint(unsigned int key, Geom::Point const &p) const
Inkscape::Util::Quantity getHeight() const
void setPages(bool enabled)
void SPDocument::initialize_current_persp3d() { this->current_persp3d = Persp3D::document_first_persp...
void emitReconstructionStart()
std::map< std::string, SPObject * > iddef
sigc::connection connectCommit(CommitSignal::slot_type slot)
Inkscape::XML::Node * rroot
Root element of Inkscape::XML::Document.
sigc::connection connectDestroy(sigc::signal< void()>::slot_type slot)
Inkscape::XML::Node * getReprNamedView()
SPItem * getItemAtPoint(unsigned int key, Geom::Point const &p, bool into_groups, SPItem *upto=nullptr) const
sigc::connection rerouting_connection
Inkscape::Util::Unit const * getDisplayUnit()
guaranteed not to return nullptr
Persp3DImpl * current_persp3d_impl
std::vector< SPObject * > getObjectsBySelector(Glib::ustring const &selector) const
std::map< Inkscape::XML::Node *, SPObject * > reprdef
void scaleChildItemsRec(Geom::Scale const &sc, Geom::Point const &p, bool noRecurse)
void translateChildItems(Geom::Translate const &tr)
LayerMode effectiveLayerMode(unsigned int display_key) const
Base class for visual SVG elements.
Geom::OptRect documentVisualBounds() const
Get item's visual bbox in document coordinate system.
Inkscape::DrawingItem * get_arenaitem(unsigned key) const
Return the arenaitem corresponding to the given item in the display with the given key.
bool isVisibleAndUnlocked() const
void set_origin_follows_page(bool on)
bool is_y_axis_down() const
SPObject is an abstract base class of all of the document nodes at the SVG document level.
void setAttribute(Inkscape::Util::const_char_ptr key, Inkscape::Util::const_char_ptr value)
void invoke_build(SPDocument *document, Inkscape::XML::Node *repr, unsigned int cloned)
void updateDisplay(SPCtx *ctx, unsigned int flags)
Updates the object's display immediately.
void emitModified(unsigned int flags)
Emits the MODIFIED signal with the object's flags.
char const * getId() const
Returns the objects current ID string.
Inkscape::XML::Node * updateRepr(unsigned int flags=SP_OBJECT_WRITE_EXT)
Updates the object's repr based on the object's state.
Inkscape::XML::Node * getRepr()
Returns the XML representation of tree.
void releaseReferences()
Cleans up an SPObject, releasing its references and requesting that references to it be released.
SPDefs * defs
Primary <defs> element where we put new defs (patterns, gradients etc.).
NodeObserver const * observer
void cr_cascade_unref(CRCascade *a_this)
CRCascade * cr_cascade_new(CRStyleSheet *a_author_sheet, CRStyleSheet *a_user_sheet, CRStyleSheet *a_ua_sheet)
The declaration of the CRSelEng class.
typedefG_BEGIN_DECLS struct _CRSelEng CRSelEng
CRSelEng * cr_sel_eng_new(CRNodeIface const *)
enum CRStatus cr_sel_eng_matches_node(CRSelEng *a_this, CRSimpleSel *a_sel, CRXMLNodePtr a_node, gboolean *a_result)
The declaration file of the CRSelector file.
CRSelector * cr_selector_parse_from_buf(const guchar *a_char_buf, enum CREncoding a_enc)
void cr_selector_destroy(CRSelector *a_this)
TODO: insert short description here.
Editable view implementation.
static char const *const parent
char * prepend_current_dir_if_relative(gchar const *uri)
TODO: insert short description here.
TODO: insert short description here.
static std::vector< SPItem * > & find_items_in_area(std::vector< SPItem * > &s, SPGroup *group, unsigned int dkey, Geom::Rect const &area, bool(*test)(Geom::Rect const &, Geom::Rect const &), bool take_hidden=false, bool take_insensitive=false, bool take_groups=true, bool enter_groups=false, bool enter_layers=true)
Return a vector list of items in a given area.
static unsigned int count_objects_recursive(SPObject *obj, unsigned int count)
static void _getObjectsByElementRecursive(Glib::ustring const &element, SPObject *parent, std::vector< SPObject * > &objects, bool custom)
static void _getObjectsBySelectorRecursive(SPObject *parent, CRSelEng *sel_eng, CRSimpleSel *simple_sel, std::vector< SPObject * > &objects)
static unsigned long next_serial
constexpr auto SP_DOCUMENT_UPDATE_PRIORITY
static void _getObjectsByClassRecursive(Glib::ustring const &klass, SPObject *parent, std::vector< SPObject * > &objects)
static void vacuum_document_recursive(SPObject *obj)
Remove unused definitions etc.
static bool is_within(Geom::Rect const &area, Geom::Rect const &box)
bool sp_no_convert_text_baseline_spacing
constexpr auto SP_DOCUMENT_REROUTING_PRIORITY
static std::vector< SPItem * > find_items_at_point(std::deque< SPItem * > const &nodes, unsigned dkey, Geom::Point const &p, int items_count=0, SPItem *upto=nullptr)
Returns the items from the descendants of group (recursively) which are at the point p,...
static bool overlaps(Geom::Rect const &area, Geom::Rect const &box)
void _build_flat_item_list(std::deque< SPItem * > &cache, SPGroup *group, unsigned int dkey, bool into_groups, bool active_only)
static SPItem * find_group_at_point(unsigned dkey, SPGroup *group, Geom::Point const &p)
Returns the topmost non-layer group from the descendants of group which is at point p,...
static SPItem * find_item_at_point(std::deque< SPItem * > const &nodes, unsigned dkey, Geom::Point const &p, SPItem *upto=nullptr)
static unsigned int objects_in_document(SPDocument *document)
Count the number of objects in a given document recursively using the count_objects_recursive helper ...
bool sp_no_convert_text_baseline_spacing
void sp_repr_free_log(Inkscape::XML::Event *log)
void sp_file_fix_feComposite(SPObject *o)
void sp_file_convert_text_baseline_spacing(SPDocument *doc)
void sp_file_convert_font_name(SPDocument *doc)
void sp_file_convert_dpi(SPDocument *doc)
void sp_file_fix_osb(SPObject *o)
void sp_file_fix_empty_lines(SPDocument *doc)
void change_def_references(SPObject *from_obj, SPObject *to_obj)
void prevent_id_clashes(SPDocument *imported_doc, SPDocument *current_doc, bool from_clipboard)
This function resolves ID clashes between the document being imported and the current open document: ...
TODO: insert short description here.
Inkscape::XML::Node * node
Inkscape - An SVG editor.
void inkscape_unref(Inkscape::Application &in)
void inkscape_ref(Inkscape::Application &in)
void shift(T &a, T &b, T const &c)
libavoid: Object-avoiding orthogonal and polyline connector routing library.
@ segmentPenalty
This penalty is applied for each segment in the connector path beyond the first.
Affine identity()
Create an identity matrix.
static R & release(R &r)
Decrements the reference count of a anchored object.
Miscellaneous supporting code.
CRNodeIface const croco_node_iface
Interface for XML nodes used by libcroco.
void rebase_hrefs(Inkscape::XML::Node *rootxml, gchar const *const old_base, gchar const *const new_base, bool const spns)
Change relative hrefs in current root XML node (faster than full document generation)
@ ELEMENT_NODE
Regular element node, e.g. <group />.
static cairo_user_data_key_t key
struct rdf_work_entity_t * rdf_find_entity(gchar const *name)
Retrieves a known RDF/Work entity by name.
void rdf_set_defaults(SPDocument *doc)
const gchar * rdf_get_work_entity(SPDocument const *doc, struct rdf_work_entity_t *entity)
Retrieves a known RDF/Work entity's contents from the document XML by name.
TODO: insert short description here.
Document * sp_repr_read_file(const gchar *filename, const gchar *default_ns, bool xinclude)
Reads XML from a file, and returns the Document.
Document * sp_repr_read_mem(const gchar *buffer, gint length, const gchar *default_ns)
Reads and parses XML from a buffer, returning it as an Document.
std::vector< Inkscape::XML::Node const * > sp_repr_lookup_name_many(Inkscape::XML::Node const *repr, gchar const *name, gint maxdepth)
Inkscape::XML::Node const * sp_repr_lookup_name(Inkscape::XML::Node const *repr, gchar const *name, gint maxdepth)
Inkscape::XML::Document * sp_repr_document_new(char const *rootname)
Returns new document having as first child a node named rootname.
Contains the interface for the Router class.
Inkscape::XML::SimpleDocument - generic XML document implementation.
void sp_lpe_item_update_patheffect(SPLPEItem *lpeitem, bool wholetree, bool write, bool with_satellites)
Calls any registered handlers for the update_patheffect action.
Base class for live path effect items.
void invert(const double v[16], double alpha[16])
SPObject * sp_object_unref(SPObject *object, SPObject *owner)
Decrease reference count of object, with possible debugging and finalization.
SPObject * sp_object_ref(SPObject *object, SPObject *owner)
Increase reference count of object, with possible debugging.
SPRoot: SVG <svg> implementation.
Interface for XML documents.
virtual Node * createElement(char const *name)=0
static std::string get_type_string(Inkscape::XML::Node const &node)
~install_reference_document()
install_reference_document(SPDocument *inject_into, SPDocument *reference)
static SPObject * createObject(std::string const &id)
Contains transformations to document/viewport and the viewport size.
Geom::Affine i2doc
Item to document transformation.
Geom::Affine i2vp
Item to viewport transformation.
Geom::Rect viewport
Viewport size.
The abstraction of a css2 simple selection list as defined by the right part of the "selector" produc...