diff options
| -rw-r--r-- | src/desktop-style.cpp | 240 | ||||
| -rw-r--r-- | src/display/nr-svgfonts.cpp | 132 | ||||
| -rw-r--r-- | src/extension/internal/cairo-renderer.cpp | 164 | ||||
| -rw-r--r-- | src/extension/internal/latex-text-renderer.cpp | 100 | ||||
| -rw-r--r-- | src/extension/internal/latex-text-renderer.h | 12 | ||||
| -rw-r--r-- | src/helper/pixbuf-ops.cpp | 15 | ||||
| -rw-r--r-- | src/libnrtype/Layout-TNG.h | 1 | ||||
| -rw-r--r-- | src/object-snapper.cpp | 44 | ||||
| -rw-r--r-- | src/selection-describer.cpp | 77 | ||||
| -rw-r--r-- | src/sp-flowregion.cpp | 62 | ||||
| -rw-r--r-- | src/sp-flowtext.cpp | 167 | ||||
| -rw-r--r-- | src/sp-flowtext.h | 8 | ||||
| -rw-r--r-- | src/sp-item.cpp | 183 | ||||
| -rw-r--r-- | src/sp-use.cpp | 109 | ||||
| -rw-r--r-- | src/sp-use.h | 5 | ||||
| -rw-r--r-- | src/ui/dialog/clonetiler.cpp | 22 | ||||
| -rw-r--r-- | src/ui/dialog/find.cpp | 93 | ||||
| -rw-r--r-- | src/ui/dialog/livepatheffect-editor.cpp | 127 | ||||
| -rw-r--r-- | src/ui/dialog/symbols.cpp | 22 |
19 files changed, 921 insertions, 662 deletions
diff --git a/src/desktop-style.cpp b/src/desktop-style.cpp index 15dc339cf..30869d87d 100644 --- a/src/desktop-style.cpp +++ b/src/desktop-style.cpp @@ -49,6 +49,24 @@ #include "box3d-side.h" #include <2geom/math-utils.h> +namespace { + +bool isTextualItem(SPObject const *obj) +{ + bool isTextual = dynamic_cast<SPText const *>(obj) // + || dynamic_cast<SPFlowtext const *>(obj) // + || dynamic_cast<SPTSpan const *>(obj) // + || dynamic_cast<SPTRef const *>(obj) // + || dynamic_cast<SPTextPath const *>(obj) // + || dynamic_cast<SPFlowdiv const *>(obj) // + || dynamic_cast<SPFlowpara const *>(obj) // + || dynamic_cast<SPFlowtspan const *>(obj); + + return isTextual; +} + +} // namespace + /** * Set color on selection on desktop. */ @@ -89,8 +107,10 @@ void sp_desktop_apply_css_recursive(SPObject *o, SPCSSAttr *css, bool skip_lines) { // non-items should not have style - if (!SP_IS_ITEM(o)) + SPItem *item = dynamic_cast<SPItem *>(o); + if (!item) { return; + } // 1. tspans with role=line are not regular objects in that they are not supposed to have style of their own, // but must always inherit from the parent text. Same for textPath. @@ -100,22 +120,24 @@ sp_desktop_apply_css_recursive(SPObject *o, SPCSSAttr *css, bool skip_lines) // it, be it clone or not; it's just styleless shape (because that's how Inkscape does // flowtext). + SPTSpan *tspan = dynamic_cast<SPTSpan *>(o); + if (!(skip_lines - && ((SP_IS_TSPAN(o) && SP_TSPAN(o)->role == SP_TSPAN_ROLE_LINE) - || SP_IS_FLOWDIV(o) - || SP_IS_FLOWPARA(o) - || SP_IS_TEXTPATH(o)) + && ((tspan && tspan->role == SP_TSPAN_ROLE_LINE) + || dynamic_cast<SPFlowdiv *>(o) + || dynamic_cast<SPFlowpara *>(o) + || dynamic_cast<SPTextPath *>(o)) && !o->getAttribute("style")) && - !(SP_IS_FLOWREGION(o) || - SP_IS_FLOWREGIONEXCLUDE(o) || - (SP_IS_USE(o) && + !(dynamic_cast<SPFlowregionbreak *>(o) || + dynamic_cast<SPFlowregionExclude *>(o) || + (dynamic_cast<SPUse *>(o) && o->parent && - (SP_IS_FLOWREGION(o->parent) || - SP_IS_FLOWREGIONEXCLUDE(o->parent) - ) - ) - ) + (dynamic_cast<SPFlowregion *>(o->parent) || + dynamic_cast<SPFlowregionExclude *>(o->parent) + ) + ) + ) ) { SPCSSAttr *css_set = sp_repr_css_attr_new(); @@ -123,7 +145,7 @@ sp_desktop_apply_css_recursive(SPObject *o, SPCSSAttr *css, bool skip_lines) // Scale the style by the inverse of the accumulated parent transform in the paste context. { - Geom::Affine const local(SP_ITEM(o)->i2doc_affine()); + Geom::Affine const local(item->i2doc_affine()); double const ex(local.descrim()); if ( ( ex != 0. ) && ( ex != 1. ) ) { @@ -137,8 +159,9 @@ sp_desktop_apply_css_recursive(SPObject *o, SPCSSAttr *css, bool skip_lines) } // setting style on child of clone spills into the clone original (via shared repr), don't do it! - if (SP_IS_USE(o)) + if (dynamic_cast<SPUse *>(o)) { return; + } for ( SPObject *child = o->firstChild() ; child ; child = child->getNext() ) { if (sp_repr_css_property(css, "opacity", NULL) != NULL) { @@ -212,11 +235,10 @@ sp_desktop_set_style(SPDesktop *desktop, SPCSSAttr *css, bool change, bool write css_no_text = sp_css_attr_unset_text(css_no_text); for (GSList const *i = desktop->selection->itemList(); i != NULL; i = i->next) { + SPItem *item = reinterpret_cast<SPItem *>(i->data); // If not text, don't apply text attributes (can a group have text attributes? Yes! FIXME) - if ( SP_IS_TEXT(i->data) || SP_IS_FLOWTEXT(i->data) - || SP_IS_TSPAN(i->data) || SP_IS_TREF(i->data) || SP_IS_TEXTPATH(i->data) - || SP_IS_FLOWDIV(i->data) || SP_IS_FLOWPARA(i->data) || SP_IS_FLOWTSPAN(i->data)) { + if (isTextualItem(item)) { // If any font property has changed, then we have written out the font // properties in longhand and we need to remove the 'font' shorthand. @@ -224,11 +246,11 @@ sp_desktop_set_style(SPDesktop *desktop, SPCSSAttr *css, bool change, bool write sp_repr_css_unset_property(css, "font"); } - sp_desktop_apply_css_recursive(SP_OBJECT(i->data), css, true); + sp_desktop_apply_css_recursive(item, css, true); } else { - sp_desktop_apply_css_recursive(SP_OBJECT(i->data), css_no_text, true); + sp_desktop_apply_css_recursive(item, css_no_text, true); } } @@ -427,16 +449,17 @@ stroke_average_width (GSList const *objects) int n_notstroked = 0; for (GSList const *l = objects; l != NULL; l = l->next) { - if (!SP_IS_ITEM (l->data)) + SPObject *obj = reinterpret_cast<SPObject *>(l->data); + SPItem *item = dynamic_cast<SPItem *>(obj); + if (!item) { continue; + } - Geom::Affine i2dt = SP_ITEM(l->data)->i2dt_affine(); - - SPObject *object = SP_OBJECT(l->data); + Geom::Affine i2dt = item->i2dt_affine(); - double width = object->style->stroke_width.computed * i2dt.descrim(); + double width = item->style->stroke_width.computed * i2dt.descrim(); - if ( object->style->stroke.isNone() || IS_NAN(width)) { + if ( item->style->stroke.isNone() || IS_NAN(width)) { ++n_notstroked; // do not count nonstroked objects continue; } else { @@ -493,7 +516,10 @@ objects_query_fillstroke (GSList *objects, SPStyle *style_res, bool const isfill bool same_color = true; for (GSList const *i = objects; i != NULL; i = i->next) { - SPObject *obj = SP_OBJECT (i->data); + SPObject *obj = reinterpret_cast<SPObject *>(i->data); + if (!obj) { + continue; + } SPStyle *style = obj->style; if (!style) { continue; @@ -504,9 +530,9 @@ objects_query_fillstroke (GSList *objects, SPStyle *style_res, bool const isfill // We consider paint "effectively set" for anything within text hierarchy SPObject *parent = obj->parent; bool paint_effectively_set = - paint->set || (SP_IS_TEXT(parent) || SP_IS_TEXTPATH(parent) || SP_IS_TSPAN(parent) - || SP_IS_FLOWTEXT(parent) || SP_IS_FLOWDIV(parent) || SP_IS_FLOWPARA(parent) - || SP_IS_FLOWTSPAN(parent) || SP_IS_FLOWLINE(parent)); + paint->set || (dynamic_cast<SPText *>(parent) || dynamic_cast<SPTextPath *>(parent) || dynamic_cast<SPTSpan *>(parent) + || dynamic_cast<SPFlowtext *>(parent) || dynamic_cast<SPFlowdiv *>(parent) || dynamic_cast<SPFlowpara *>(parent) + || dynamic_cast<SPFlowtspan *>(parent) || dynamic_cast<SPFlowline*>(parent)); // 1. Bail out with QUERY_STYLE_MULTIPLE_DIFFERENT if necessary @@ -518,38 +544,45 @@ objects_query_fillstroke (GSList *objects, SPStyle *style_res, bool const isfill if (paint_res->set && paint->set && paint_res->isPaintserver()) { // both previous paint and this paint were a server, see if the servers are compatible - SPPaintServer *server_res = isfill? SP_STYLE_FILL_SERVER (style_res) : SP_STYLE_STROKE_SERVER (style_res); - SPPaintServer *server = isfill? SP_STYLE_FILL_SERVER (style) : SP_STYLE_STROKE_SERVER (style); + SPPaintServer *server_res = isfill ? style_res->getFillPaintServer() : style_res->getStrokePaintServer(); + SPPaintServer *server = isfill ? style->getFillPaintServer() : style->getStrokePaintServer(); - if (SP_IS_LINEARGRADIENT (server_res)) { - - if (!SP_IS_LINEARGRADIENT(server)) + SPLinearGradient *linear_res = dynamic_cast<SPLinearGradient *>(server_res); + SPRadialGradient *radial_res = linear_res ? NULL : dynamic_cast<SPRadialGradient *>(server_res); + SPPattern *pattern_res = (linear_res || radial_res) ? NULL : dynamic_cast<SPPattern *>(server_res); + if (linear_res) { + SPLinearGradient *linear = dynamic_cast<SPLinearGradient *>(server); + if (!linear) { return QUERY_STYLE_MULTIPLE_DIFFERENT; // different kind of server + } - SPGradient *vector = SP_GRADIENT(server)->getVector(); - SPGradient *vector_res = SP_GRADIENT(server_res)->getVector(); - if (vector_res != vector) + SPGradient *vector = linear->getVector(); + SPGradient *vector_res = linear_res->getVector(); + if (vector_res != vector) { return QUERY_STYLE_MULTIPLE_DIFFERENT; // different gradient vectors - - } else if (SP_IS_RADIALGRADIENT (server_res)) { - - if (!SP_IS_RADIALGRADIENT(server)) + } + } else if (radial_res) { + SPRadialGradient *radial = dynamic_cast<SPRadialGradient *>(server); + if (!radial) { return QUERY_STYLE_MULTIPLE_DIFFERENT; // different kind of server + } - SPGradient *vector = SP_GRADIENT(server)->getVector(); - SPGradient *vector_res = SP_GRADIENT(server_res)->getVector(); - if (vector_res != vector) + SPGradient *vector = radial->getVector(); + SPGradient *vector_res = radial_res->getVector(); + if (vector_res != vector) { return QUERY_STYLE_MULTIPLE_DIFFERENT; // different gradient vectors - - } else if (SP_IS_PATTERN (server_res)) { - - if (!SP_IS_PATTERN(server)) + } + } else if (pattern_res) { + SPPattern *pattern = dynamic_cast<SPPattern *>(server); + if (!pattern) { return QUERY_STYLE_MULTIPLE_DIFFERENT; // different kind of server + } - SPPattern *pat = pattern_getroot (SP_PATTERN (server)); - SPPattern *pat_res = pattern_getroot (SP_PATTERN (server_res)); - if (pat_res != pat) + SPPattern *pat = pattern_getroot (pattern); + SPPattern *pat_res = pattern_getroot (pattern_res); + if (pat_res != pat) { return QUERY_STYLE_MULTIPLE_DIFFERENT; // different pattern roots + } } } @@ -667,7 +700,10 @@ objects_query_opacity (GSList *objects, SPStyle *style_res) for (GSList const *i = objects; i != NULL; i = i->next) { - SPObject *obj = SP_OBJECT (i->data); + SPObject *obj = reinterpret_cast<SPObject *>(i->data); + if (!obj) { + continue; + } SPStyle *style = obj->style; if (!style) { continue; @@ -720,8 +756,12 @@ objects_query_strokewidth (GSList *objects, SPStyle *style_res) int n_stroked = 0; for (GSList const *i = objects; i != NULL; i = i->next) { - SPObject *obj = SP_OBJECT (i->data); - if (!SP_IS_ITEM(obj)) { + SPObject *obj = reinterpret_cast<SPObject *>(i->data); + if (!obj) { + continue; + } + SPItem *item = dynamic_cast<SPItem *>(obj); + if (!item) { continue; } SPStyle *style = obj->style; @@ -740,7 +780,7 @@ objects_query_strokewidth (GSList *objects, SPStyle *style_res) noneSet &= style->stroke.isNone(); - Geom::Affine i2d = SP_ITEM(obj)->i2dt_affine(); + Geom::Affine i2d = item->i2dt_affine(); double sw = style->stroke_width.computed * i2d.descrim(); if (!IS_NAN(sw)) { @@ -790,8 +830,8 @@ objects_query_miterlimit (GSList *objects, SPStyle *style_res) bool same_ml = true; for (GSList const *i = objects; i != NULL; i = i->next) { - SPObject *obj = SP_OBJECT (i->data); - if (!SP_IS_ITEM(obj)) { + SPObject *obj = reinterpret_cast<SPObject *>(i->data); + if (!dynamic_cast<SPItem *>(obj)) { continue; } SPStyle *style = obj->style; @@ -849,8 +889,8 @@ objects_query_strokecap (GSList *objects, SPStyle *style_res) int n_stroked = 0; for (GSList const *i = objects; i != NULL; i = i->next) { - SPObject *obj = SP_OBJECT (i->data); - if (!SP_IS_ITEM(obj)) { + SPObject *obj = reinterpret_cast<SPObject *>(i->data); + if (!dynamic_cast<SPItem *>(obj)) { continue; } SPStyle *style = obj->style; @@ -903,8 +943,8 @@ objects_query_strokejoin (GSList *objects, SPStyle *style_res) int n_stroked = 0; for (GSList const *i = objects; i != NULL; i = i->next) { - SPObject *obj = SP_OBJECT (i->data); - if (!SP_IS_ITEM(obj)) { + SPObject *obj = reinterpret_cast<SPObject *>(i->data); + if (!dynamic_cast<SPItem *>(obj)) { continue; } SPStyle *style = obj->style; @@ -966,11 +1006,9 @@ objects_query_fontnumbers (GSList *objects, SPStyle *style_res) int no_size = 0; for (GSList const *i = objects; i != NULL; i = i->next) { - SPObject *obj = SP_OBJECT (i->data); + SPObject *obj = reinterpret_cast<SPObject *>(i->data); - if (!SP_IS_TEXT(obj) && !SP_IS_FLOWTEXT(obj) - && !SP_IS_TSPAN(obj) && !SP_IS_TREF(obj) && !SP_IS_TEXTPATH(obj) - && !SP_IS_FLOWDIV(obj) && !SP_IS_FLOWPARA(obj) && !SP_IS_FLOWTSPAN(obj)) { + if (!isTextualItem(obj)) { continue; } @@ -980,7 +1018,9 @@ objects_query_fontnumbers (GSList *objects, SPStyle *style_res) } texts ++; - double dummy = style->font_size.computed * Geom::Affine(SP_ITEM(obj)->i2dt_affine()).descrim(); + SPItem *item = dynamic_cast<SPItem *>(obj); + g_assert(item != NULL); + double dummy = style->font_size.computed * Geom::Affine(item->i2dt_affine()).descrim(); if (!IS_NAN(dummy)) { size += dummy; /// \todo FIXME: we assume non-% units here } else { @@ -1085,12 +1125,11 @@ objects_query_fontstyle (GSList *objects, SPStyle *style_res) int texts = 0; for (GSList const *i = objects; i != NULL; i = i->next) { - SPObject *obj = SP_OBJECT (i->data); + SPObject *obj = reinterpret_cast<SPObject *>(i->data); - if (!SP_IS_TEXT(obj) && !SP_IS_FLOWTEXT(obj) - && !SP_IS_TSPAN(obj) && !SP_IS_TREF(obj) && !SP_IS_TEXTPATH(obj) - && !SP_IS_FLOWDIV(obj) && !SP_IS_FLOWPARA(obj) && !SP_IS_FLOWTSPAN(obj)) + if (!isTextualItem(obj)) { continue; + } SPStyle *style = obj->style; if (!style) { @@ -1155,11 +1194,9 @@ objects_query_baselines (GSList *objects, SPStyle *style_res) int texts = 0; for (GSList const *i = objects; i != NULL; i = i->next) { - SPObject *obj = SP_OBJECT (i->data); + SPObject *obj = reinterpret_cast<SPObject *>(i->data); - if (!SP_IS_TEXT(obj) && !SP_IS_FLOWTEXT(obj) - && !SP_IS_TSPAN(obj) && !SP_IS_TREF(obj) && !SP_IS_TEXTPATH(obj) - && !SP_IS_FLOWDIV(obj) && !SP_IS_FLOWPARA(obj) && !SP_IS_FLOWTSPAN(obj)) { + if (!isTextualItem(obj)) { continue; } @@ -1245,12 +1282,10 @@ objects_query_fontfamily (GSList *objects, SPStyle *style_res) style_res->font_family.set = FALSE; for (GSList const *i = objects; i != NULL; i = i->next) { - SPObject *obj = SP_OBJECT (i->data); + SPObject *obj = reinterpret_cast<SPObject *>(i->data); // std::cout << " " << reinterpret_cast<SPObject*>(i->data)->getId() << std::endl; - if (!SP_IS_TEXT(obj) && !SP_IS_FLOWTEXT(obj) - && !SP_IS_TSPAN(obj) && !SP_IS_TREF(obj) && !SP_IS_TEXTPATH(obj) - && !SP_IS_FLOWDIV(obj) && !SP_IS_FLOWPARA(obj) && !SP_IS_FLOWTSPAN(obj)) { + if (!isTextualItem(obj)) { continue; } @@ -1303,12 +1338,10 @@ objects_query_fontspecification (GSList *objects, SPStyle *style_res) style_res->font_specification.set = FALSE; for (GSList const *i = objects; i != NULL; i = i->next) { - SPObject *obj = SP_OBJECT (i->data); + SPObject *obj = reinterpret_cast<SPObject *>(i->data); // std::cout << " " << reinterpret_cast<SPObject*>(i->data)->getId() << std::endl; - if (!SP_IS_TEXT(obj) && !SP_IS_FLOWTEXT(obj) - && !SP_IS_TSPAN(obj) && !SP_IS_TREF(obj) && !SP_IS_TEXTPATH(obj) - && !SP_IS_FLOWDIV(obj) && !SP_IS_FLOWPARA(obj) && !SP_IS_FLOWTSPAN(obj)) { + if (!isTextualItem(obj)) { continue; } @@ -1363,9 +1396,12 @@ objects_query_blend (GSList *objects, SPStyle *style_res) guint items = 0; for (GSList const *i = objects; i != NULL; i = i->next) { - SPObject *obj = SP_OBJECT (i->data); + SPObject *obj = reinterpret_cast<SPObject *>(i->data); + if (!obj) { + continue; + } SPStyle *style = obj->style; - if (!style || !SP_IS_ITEM(obj)) { + if (!style || !dynamic_cast<SPItem *>(obj)) { continue; } @@ -1378,14 +1414,14 @@ objects_query_blend (GSList *objects, SPStyle *style_res) // determine whether filter is simple (blend and/or blur) or complex for(SPObject *primitive_obj = style->getFilter()->children; - primitive_obj && SP_IS_FILTER_PRIMITIVE(primitive_obj); + primitive_obj && dynamic_cast<SPFilterPrimitive *>(primitive_obj); primitive_obj = primitive_obj->next) { - SPFilterPrimitive *primitive = SP_FILTER_PRIMITIVE(primitive_obj); - if(SP_IS_FEBLEND(primitive)) + SPFilterPrimitive *primitive = dynamic_cast<SPFilterPrimitive *>(primitive_obj); + if (dynamic_cast<SPFeBlend *>(primitive)) { ++blendcount; - else if(SP_IS_GAUSSIANBLUR(primitive)) + } else if (dynamic_cast<SPGaussianBlur *>(primitive)) { ++blurcount; - else { + } else { blurcount = complex_filter; break; } @@ -1394,10 +1430,10 @@ objects_query_blend (GSList *objects, SPStyle *style_res) // simple filter if(blurcount == 1 || blendcount == 1) { for(SPObject *primitive_obj = style->getFilter()->children; - primitive_obj && SP_IS_FILTER_PRIMITIVE(primitive_obj); + primitive_obj && dynamic_cast<SPFilterPrimitive *>(primitive_obj); primitive_obj = primitive_obj->next) { - if(SP_IS_FEBLEND(primitive_obj)) { - SPFeBlend *spblend = SP_FEBLEND(primitive_obj); + SPFeBlend *spblend = dynamic_cast<SPFeBlend *>(primitive_obj); + if (spblend) { blend = spblend->blend_mode; } } @@ -1450,16 +1486,20 @@ objects_query_blur (GSList *objects, SPStyle *style_res) guint items = 0; for (GSList const *i = objects; i != NULL; i = i->next) { - SPObject *obj = SP_OBJECT (i->data); + SPObject *obj = reinterpret_cast<SPObject *>(i->data); + if (!obj) { + continue; + } SPStyle *style = obj->style; if (!style) { continue; } - if (!SP_IS_ITEM(obj)) { + SPItem *item = dynamic_cast<SPItem *>(obj); + if (!item) { continue; } - Geom::Affine i2d = SP_ITEM(obj)->i2dt_affine(); + Geom::Affine i2d = item->i2dt_affine(); items ++; @@ -1468,12 +1508,12 @@ objects_query_blur (GSList *objects, SPStyle *style_res) //cycle through filter primitives SPObject *primitive_obj = style->getFilter()->children; while (primitive_obj) { - if (SP_IS_FILTER_PRIMITIVE(primitive_obj)) { - SPFilterPrimitive *primitive = SP_FILTER_PRIMITIVE(primitive_obj); + SPFilterPrimitive *primitive = dynamic_cast<SPFilterPrimitive *>(primitive_obj); + if (primitive) { //if primitive is gaussianblur - if(SP_IS_GAUSSIANBLUR(primitive)) { - SPGaussianBlur * spblur = SP_GAUSSIANBLUR(primitive); + SPGaussianBlur * spblur = dynamic_cast<SPGaussianBlur *>(primitive); + if (spblur) { float num = spblur->stdDeviation.getNumber(); float dummy = num * i2d.descrim(); if (!IS_NAN(dummy)) { diff --git a/src/display/nr-svgfonts.cpp b/src/display/nr-svgfonts.cpp index 84b4bd080..011f51977 100644 --- a/src/display/nr-svgfonts.cpp +++ b/src/display/nr-svgfonts.cpp @@ -4,6 +4,7 @@ * * Authors: * Felipe C. da S. Sanches <juca@members.fsf.org> + * Jon A. Cruz <jon@joncruz.org> * * Copyright (C) 2008 Felipe C. da S. Sanches * @@ -32,9 +33,9 @@ #include "sp-font.h" #include "sp-glyph-kerning.h" -//*************************// +// ************************// // UserFont Implementation // -//*************************// +// ************************// // I wrote this binding code because Cairomm does not yet support userfonts. I have moved this code to cairomm and sent them a patch. // Once Cairomm incorporate the UserFonts binding, this code should be removed from inkscape and Cairomm API should be used. @@ -111,16 +112,38 @@ unsigned int size_of_substring(const char* substring, gchar* str){ return 0; } -//TODO: in these macros, verify what happens when using unicode strings. -#define Match_VKerning_Rule ((SP_VKERN(node))->u1->contains(previous_unicode[0])\ - || (SP_VKERN(node))->g1->contains(previous_glyph_name)) &&\ - ((SP_VKERN(node))->u2->contains(this->glyphs[i]->unicode[0])\ - || (SP_VKERN(node))->g2->contains(this->glyphs[i]->glyph_name.c_str())) -#define Match_HKerning_Rule ((SP_HKERN(node))->u1->contains(previous_unicode[0])\ - || (SP_HKERN(node))->g1->contains(previous_glyph_name)) &&\ - ((SP_HKERN(node))->u2->contains(this->glyphs[i]->unicode[0])\ - || (SP_HKERN(node))->g2->contains(this->glyphs[i]->glyph_name.c_str())) +namespace { + +//TODO: in these functions, verify what happens when using unicode strings. + +bool MatchVKerningRule(SPVkern const *vkern, + SPGlyph *glyph, + char const *previous_unicode, + gchar const *previous_glyph_name) +{ + bool value = (vkern->u1->contains(previous_unicode[0]) + || vkern->g1->contains(previous_glyph_name)) + && (vkern->u2->contains(glyph->unicode[0]) + || vkern->g2->contains(glyph->glyph_name.c_str())); + + return value; +} + +bool MatchHKerningRule(SPHkern const *hkern, + SPGlyph *glyph, + char const *previous_unicode, + gchar const *previous_glyph_name) +{ + bool value = (hkern->u1->contains(previous_unicode[0]) + || hkern->g1->contains(previous_glyph_name)) + && (hkern->u2->contains(glyph->unicode[0]) + || hkern->g2->contains(glyph->glyph_name.c_str())); + + return value; +} + +} // namespace cairo_status_t SvgFont::scaled_font_text_to_glyphs (cairo_scaled_font_t */*scaled_font*/, @@ -182,11 +205,13 @@ SvgFont::scaled_font_text_to_glyphs (cairo_scaled_font_t */*scaled_font*/, if ( (len = size_of_substring(this->glyphs[i]->unicode.c_str(), _utf8)) ){ for(SPObject* node = this->font->children;previous_unicode && node;node=node->next){ //apply glyph kerning if appropriate - if (SP_IS_HKERN(node) && is_horizontal_text && Match_HKerning_Rule ){ - x -= ((SP_HKERN(node))->k / 1000.0);//TODO: use here the height of the font + SPHkern *hkern = dynamic_cast<SPHkern *>(node); + if (hkern && is_horizontal_text && MatchHKerningRule(hkern, this->glyphs[i], previous_unicode, previous_glyph_name) ){ + x -= (hkern->k / 1000.0);//TODO: use here the height of the font } - if (SP_IS_VKERN(node) && !is_horizontal_text && Match_VKerning_Rule ){ - y -= ((SP_VKERN(node))->k / 1000.0);//TODO: use here the "height" of the font + SPVkern *vkern = dynamic_cast<SPVkern *>(node); + if (vkern && !is_horizontal_text && MatchVKerningRule(vkern, this->glyphs[i], previous_unicode, previous_glyph_name) ){ + y -= (vkern->k / 1000.0);//TODO: use here the "height" of the font } } previous_unicode = const_cast<char*>(this->glyphs[i]->unicode.c_str());//used for kerning checking @@ -246,9 +271,8 @@ SvgFont::glyph_modified(SPObject* /* blah */, unsigned int /* bleh */){ Geom::PathVector SvgFont::flip_coordinate_system(SPFont* spfont, Geom::PathVector pathv){ double units_per_em = 1000; - SPObject* obj; - for (obj = (SP_OBJECT(spfont))->children; obj; obj=obj->next){ - if (SP_IS_FONTFACE(obj)){ + for (SPObject *obj = spfont->children; obj; obj = obj->next){ + if (dynamic_cast<SPFontFace *>(obj)) { //XML Tree being directly used here while it shouldn't be. sp_repr_get_double(obj->getRepr(), "units_per_em", &units_per_em); } @@ -275,19 +299,21 @@ SvgFont::scaled_font_render_glyph (cairo_scaled_font_t */*scaled_font*/, if (glyph > this->glyphs.size()) return CAIRO_STATUS_SUCCESS;//TODO: this is an error! - SPObject* node; - if (glyph == this->glyphs.size()){ - if (!this->missingglyph) return CAIRO_STATUS_SUCCESS; - node = SP_OBJECT(this->missingglyph); + SPObject *node = NULL; + if (glyph == glyphs.size()){ + if (!missingglyph) { + return CAIRO_STATUS_SUCCESS; + } + node = missingglyph; } else { - node = SP_OBJECT(this->glyphs[glyph]); + node = glyphs[glyph]; } - if (!SP_IS_GLYPH(node) && !SP_IS_MISSING_GLYPH(node)) { + if (!dynamic_cast<SPGlyph *>(node) && !dynamic_cast<SPMissingGlyph *>(node)) { return CAIRO_STATUS_SUCCESS; // FIXME: is this the right code to return? } - SPFont* spfont = SP_FONT(node->parent); + SPFont* spfont = dynamic_cast<SPFont *>(node->parent); if (!spfont) { return CAIRO_STATUS_SUCCESS; // FIXME: is this the right code to return? } @@ -296,36 +322,48 @@ SvgFont::scaled_font_render_glyph (cairo_scaled_font_t */*scaled_font*/, // or using the d attribute of a glyph node. // pathv stores the path description from the d attribute: Geom::PathVector pathv; - if (SP_IS_GLYPH(node) && (SP_GLYPH(node))->d) { - pathv = sp_svg_read_pathv((SP_GLYPH(node))->d); - pathv = flip_coordinate_system(spfont, pathv); - this->render_glyph_path(cr, &pathv); - } else if (SP_IS_MISSING_GLYPH(node) && (SP_MISSING_GLYPH(node))->d) { - pathv = sp_svg_read_pathv((SP_MISSING_GLYPH(node))->d); + + SPGlyph *glyphNode = dynamic_cast<SPGlyph *>(node); + if (glyphNode && glyphNode->d) { + pathv = sp_svg_read_pathv(glyphNode->d); pathv = flip_coordinate_system(spfont, pathv); - this->render_glyph_path(cr, &pathv); + render_glyph_path(cr, &pathv); + } else { + SPMissingGlyph *missing = dynamic_cast<SPMissingGlyph *>(node); + if (missing && missing->d) { + pathv = sp_svg_read_pathv(missing->d); + pathv = flip_coordinate_system(spfont, pathv); + render_glyph_path(cr, &pathv); + } } if (node->hasChildren()){ //render the SVG described on this glyph's child nodes. for(node = node->children; node; node=node->next){ - if (SP_IS_PATH(node)){ - pathv = (SP_SHAPE(node))->_curve->get_pathvector(); - pathv = flip_coordinate_system(spfont, pathv); - this->render_glyph_path(cr, &pathv); + { + SPPath *path = dynamic_cast<SPPath *>(node); + if (path) { + pathv = path->_curve->get_pathvector(); + pathv = flip_coordinate_system(spfont, pathv); + render_glyph_path(cr, &pathv); + } } - if (SP_IS_OBJECTGROUP(node)){ + if (dynamic_cast<SPObjectGroup *>(node)) { g_warning("TODO: svgfonts: render OBJECTGROUP"); } - if (SP_IS_USE(node)){ - SPItem* item = SP_USE(node)->ref->getObject(); - if (SP_IS_PATH(item)){ - pathv = (SP_SHAPE(item))->_curve->get_pathvector(); + SPUse *use = dynamic_cast<SPUse *>(node); + if (use) { + SPItem* item = use->ref->getObject(); + SPPath *path = dynamic_cast<SPPath *>(item); + if (path) { + SPShape *shape = dynamic_cast<SPShape *>(item); + g_assert(shape != NULL); + pathv = shape->_curve->get_pathvector(); pathv = flip_coordinate_system(spfont, pathv); this->render_glyph_path(cr, &pathv); } - glyph_modified_connection = (SP_OBJECT(item))->connectModified(sigc::mem_fun(*this, &SvgFont::glyph_modified)); + glyph_modified_connection = item->connectModified(sigc::mem_fun(*this, &SvgFont::glyph_modified)); } } } @@ -337,11 +375,13 @@ cairo_font_face_t* SvgFont::get_font_face(){ if (!this->userfont) { for(SPObject* node = this->font->children;node;node=node->next){ - if (SP_IS_GLYPH(node)){ - this->glyphs.push_back(SP_GLYPH(node)); + SPGlyph *glyph = dynamic_cast<SPGlyph *>(node); + if (glyph) { + glyphs.push_back(glyph); } - if (SP_IS_MISSING_GLYPH(node)){ - this->missingglyph=SP_MISSING_GLYPH(node); + SPMissingGlyph *missing = dynamic_cast<SPMissingGlyph *>(node); + if (missing) { + missingglyph = missing; } } this->userfont = new UserFont(this); diff --git a/src/extension/internal/cairo-renderer.cpp b/src/extension/internal/cairo-renderer.cpp index 1d9bb09d0..5a9a28ef9 100644 --- a/src/extension/internal/cairo-renderer.cpp +++ b/src/extension/internal/cairo-renderer.cpp @@ -147,13 +147,13 @@ Here comes the rendering part which could be put into the 'render' methods of SP /* The below functions are copy&pasted plus slightly modified from *_invoke_print functions. */ static void sp_item_invoke_render(SPItem *item, CairoRenderContext *ctx); -static void sp_group_render(SPItem *item, CairoRenderContext *ctx); -static void sp_use_render(SPItem *item, CairoRenderContext *ctx); -static void sp_shape_render(SPItem *item, CairoRenderContext *ctx); -static void sp_text_render(SPItem *item, CairoRenderContext *ctx); -static void sp_flowtext_render(SPItem *item, CairoRenderContext *ctx); -static void sp_image_render(SPItem *item, CairoRenderContext *ctx); -static void sp_symbol_render(SPItem *item, CairoRenderContext *ctx); +static void sp_group_render(SPGroup *group, CairoRenderContext *ctx); +static void sp_use_render(SPUse *use, CairoRenderContext *ctx); +static void sp_shape_render(SPShape *shape, CairoRenderContext *ctx); +static void sp_text_render(SPText *text, CairoRenderContext *ctx); +static void sp_flowtext_render(SPFlowtext *flowtext, CairoRenderContext *ctx); +static void sp_image_render(SPImage *image, CairoRenderContext *ctx); +static void sp_symbol_render(SPSymbol *symbol, CairoRenderContext *ctx); static void sp_asbitmap_render(SPItem *item, CairoRenderContext *ctx); static void sp_shape_render_invoke_marker_rendering(SPMarker* marker, Geom::Affine tr, SPStyle* style, CairoRenderContext *ctx) @@ -179,17 +179,15 @@ static void sp_shape_render_invoke_marker_rendering(SPMarker* marker, Geom::Affi } } -static void sp_shape_render (SPItem *item, CairoRenderContext *ctx) +static void sp_shape_render(SPShape *shape, CairoRenderContext *ctx) { - SPShape *shape = SP_SHAPE(item); - if (!shape->_curve) { return; } - Geom::OptRect pbox = item->geometricBounds(); + Geom::OptRect pbox = shape->geometricBounds(); - SPStyle* style = item->style; + SPStyle* style = shape->style; Geom::PathVector const & pathv = shape->_curve->get_pathvector(); if (pathv.empty()) { @@ -201,7 +199,7 @@ static void sp_shape_render (SPItem *item, CairoRenderContext *ctx) // START marker for (int i = 0; i < 2; i++) { // SP_MARKER_LOC and SP_MARKER_LOC_START if ( shape->_marker[i] ) { - SPMarker* marker = SP_MARKER (shape->_marker[i]); + SPMarker* marker = shape->_marker[i]; Geom::Affine tr; if (marker->orient_mode == MARKER_ORIENT_AUTO) { tr = sp_shape_marker_get_transform_at_start(pathv.begin()->front()); @@ -216,7 +214,7 @@ static void sp_shape_render (SPItem *item, CairoRenderContext *ctx) // MID marker for (int i = 0; i < 3; i += 2) { // SP_MARKER_LOC and SP_MARKER_LOC_MID if ( !shape->_marker[i] ) continue; - SPMarker* marker = SP_MARKER (shape->_marker[i]); + SPMarker* marker = shape->_marker[i]; for(Geom::PathVector::const_iterator path_it = pathv.begin(); path_it != pathv.end(); ++path_it) { // START position if ( path_it != pathv.begin() @@ -268,7 +266,7 @@ static void sp_shape_render (SPItem *item, CairoRenderContext *ctx) // END marker for (int i = 0; i < 4; i += 3) { // SP_MARKER_LOC and SP_MARKER_LOC_END if ( shape->_marker[i] ) { - SPMarker* marker = SP_MARKER (shape->_marker[i]); + SPMarker* marker = shape->_marker[i]; /* Get reference to last curve in the path. * For moveto-only path, this returns the "closing line segment". */ @@ -291,26 +289,25 @@ static void sp_shape_render (SPItem *item, CairoRenderContext *ctx) } } -static void sp_group_render(SPItem *item, CairoRenderContext *ctx) +static void sp_group_render(SPGroup *group, CairoRenderContext *ctx) { - SPGroup *group = SP_GROUP(item); CairoRenderer *renderer = ctx->getRenderer(); TRACE(("sp_group_render opacity: %f\n", SP_SCALE24_TO_FLOAT(item->style->opacity.value))); GSList *l = g_slist_reverse(group->childList(false)); while (l) { - SPObject *o = SP_OBJECT (l->data); - if (SP_IS_ITEM(o)) { - renderer->renderItem (ctx, SP_ITEM (o)); + SPObject *o = reinterpret_cast<SPObject *>(l->data); + SPItem *item = dynamic_cast<SPItem *>(o); + if (item) { + renderer->renderItem(ctx, item); } l = g_slist_remove (l, o); } } -static void sp_use_render(SPItem *item, CairoRenderContext *ctx) +static void sp_use_render(SPUse *use, CairoRenderContext *ctx) { bool translated = false; - SPUse *use = SP_USE(item); CairoRenderer *renderer = ctx->getRenderer(); if ((use->x._set && use->x.computed != 0) || (use->y._set && use->y.computed != 0)) { @@ -320,8 +317,8 @@ static void sp_use_render(SPItem *item, CairoRenderContext *ctx) translated = true; } - if (use->child && SP_IS_ITEM(use->child)) { - renderer->renderItem(ctx, SP_ITEM(use->child)); + if (use->child) { + renderer->renderItem(ctx, use->child); } if (translated) { @@ -329,30 +326,27 @@ static void sp_use_render(SPItem *item, CairoRenderContext *ctx) } } -static void sp_text_render(SPItem *item, CairoRenderContext *ctx) +static void sp_text_render(SPText *text, CairoRenderContext *ctx) { - SPText *group = SP_TEXT (item); - group->layout.showGlyphs(ctx); + text->layout.showGlyphs(ctx); } -static void sp_flowtext_render(SPItem *item, CairoRenderContext *ctx) +static void sp_flowtext_render(SPFlowtext *flowtext, CairoRenderContext *ctx) { - SPFlowtext *group = SP_FLOWTEXT(item); - group->layout.showGlyphs(ctx); + flowtext->layout.showGlyphs(ctx); } -static void sp_image_render(SPItem *item, CairoRenderContext *ctx) +static void sp_image_render(SPImage *image, CairoRenderContext *ctx) { - SPImage *image; - int w, h; - - image = SP_IMAGE (item); - - if (!image->pixbuf) return; - if ((image->width.computed <= 0.0) || (image->height.computed <= 0.0)) return; + if (!image->pixbuf) { + return; + } + if ((image->width.computed <= 0.0) || (image->height.computed <= 0.0)) { + return; + } - w = image->pixbuf->width(); - h = image->pixbuf->height(); + int w = image->pixbuf->width(); + int h = image->pixbuf->height(); double x = image->x.computed; double y = image->y.computed; @@ -372,12 +366,11 @@ static void sp_image_render(SPItem *item, CairoRenderContext *ctx) Geom::Scale s(width / (double)w, height / (double)h); Geom::Affine t(s * tp); - ctx->renderImage (image->pixbuf, t, item->style); + ctx->renderImage(image->pixbuf, t, image->style); } -static void sp_symbol_render(SPItem *item, CairoRenderContext *ctx) +static void sp_symbol_render(SPSymbol *symbol, CairoRenderContext *ctx) { - SPSymbol *symbol = SP_SYMBOL(item); if (!symbol->cloned) { return; } @@ -412,7 +405,7 @@ static void sp_symbol_render(SPItem *item, CairoRenderContext *ctx) ctx->transform(vb2user); } - sp_group_render(item, ctx); + sp_group_render(symbol, ctx); ctx->popState(); } @@ -524,34 +517,56 @@ static void sp_item_invoke_render(SPItem *item, CairoRenderContext *ctx) SPStyle* style = item->style; if((ctx->getFilterToBitmap() == TRUE) && (style->filter.set != 0)) { - return sp_asbitmap_render(item, ctx); + sp_asbitmap_render(item, ctx); } - if (SP_IS_ROOT(item)) { + SPRoot *root = dynamic_cast<SPRoot *>(item); + if (root) { TRACE(("root\n")); - return sp_root_render(SP_ROOT(item), ctx); - } else if (SP_IS_SYMBOL(item)) { - TRACE(("symbol\n")); - return sp_symbol_render(item, ctx); - } else if (SP_IS_GROUP(item)) { - TRACE(("group\n")); - return sp_group_render(item, ctx); - } else if (SP_IS_SHAPE(item)) { - TRACE(("shape\n")); - return sp_shape_render(item, ctx); - } else if (SP_IS_USE(item)) { - TRACE(("use begin---\n")); - sp_use_render(item, ctx); - TRACE(("---use end\n")); - } else if (SP_IS_TEXT(item)) { - TRACE(("text\n")); - return sp_text_render(item, ctx); - } else if (SP_IS_FLOWTEXT(item)) { - TRACE(("flowtext\n")); - return sp_flowtext_render(item, ctx); - } else if (SP_IS_IMAGE(item)) { - TRACE(("image\n")); - return sp_image_render(item, ctx); + sp_root_render(root, ctx); + } else { + SPSymbol *symbol = dynamic_cast<SPSymbol *>(item); + if (symbol) { + TRACE(("symbol\n")); + sp_symbol_render(symbol, ctx); + } else { + SPGroup *group = dynamic_cast<SPGroup *>(item); + if (group) { + TRACE(("group\n")); + sp_group_render(group, ctx); + } else { + SPShape *shape = dynamic_cast<SPShape *>(item); + if (shape) { + TRACE(("shape\n")); + sp_shape_render(shape, ctx); + } else { + SPUse *use = dynamic_cast<SPUse *>(item); + if (use) { + TRACE(("use begin---\n")); + sp_use_render(use, ctx); + TRACE(("---use end\n")); + } else { + SPText *text = dynamic_cast<SPText *>(item); + if (text) { + TRACE(("text\n")); + sp_text_render(text, ctx); + } else { + SPFlowtext *flowtext = dynamic_cast<SPFlowtext *>(item); + if (flowtext) { + TRACE(("flowtext\n")); + sp_flowtext_render(flowtext, ctx); + } else { + SPImage *image = dynamic_cast<SPImage *>(item); + if (image) { + TRACE(("image\n")); + sp_image_render(image, ctx); + } + } + } + } + } + } + } } } @@ -571,8 +586,9 @@ CairoRenderer::setStateForItem(CairoRenderContext *ctx, SPItem const *item) // This is so because we use the image's/(flow)text's transform for positioning // instead of explicitly specifying it and letting the renderer do the // transformation before rendering the item. - if (SP_IS_TEXT(item) || SP_IS_FLOWTEXT(item) || SP_IS_IMAGE(item)) + if (dynamic_cast<SPText const *>(item) || dynamic_cast<SPFlowtext const *>(item) || dynamic_cast<SPImage const *>(item)) { state->parent_has_userspace = TRUE; + } TRACE(("setStateForItem opacity: %f\n", state->opacity)); } @@ -700,8 +716,8 @@ CairoRenderer::applyClipPath(CairoRenderContext *ctx, SPClipPath const *cp) TRACE(("BEGIN clip\n")); SPObject const *co = cp; for ( SPObject const *child = co->firstChild() ; child; child = child->getNext() ) { - if (SP_IS_ITEM(child)) { - SPItem const *item = SP_ITEM(child); + SPItem const *item = dynamic_cast<SPItem const *>(child); + if (item) { // combine transform of the item in clippath and the item using clippath: Geom::Affine tempmat = item->transform * ctx->getCurrentState()->item_transform; @@ -759,8 +775,8 @@ CairoRenderer::applyMask(CairoRenderContext *ctx, SPMask const *mask) TRACE(("BEGIN mask\n")); SPObject const *co = mask; for ( SPObject const *child = co->firstChild() ; child; child = child->getNext() ) { - if (SP_IS_ITEM(child)) { - SPItem const *item = SP_ITEM(child); + SPItem const *item = dynamic_cast<SPItem const *>(child); + if (item) { // TODO fix const correctness: renderItem(ctx, const_cast<SPItem*>(item)); } diff --git a/src/extension/internal/latex-text-renderer.cpp b/src/extension/internal/latex-text-renderer.cpp index 398c9f061..ab0733848 100644 --- a/src/extension/internal/latex-text-renderer.cpp +++ b/src/extension/internal/latex-text-renderer.cpp @@ -66,7 +66,8 @@ latex_render_document_text_to_file( SPDocument *doc, gchar const *filename, bool pageBoundingBox = true; if (exportId && strcmp(exportId, "")) { // we want to export the given item only - base = SP_ITEM(doc->getObjectById(exportId)); + base = dynamic_cast<SPItem *>(doc->getObjectById(exportId)); + g_assert(base != NULL); pageBoundingBox = exportCanvas; } else { @@ -225,26 +226,22 @@ LaTeXTextRenderer::writePostamble() fprintf(_stream, "%s", postamble); } -void -LaTeXTextRenderer::sp_group_render(SPItem *item) +void LaTeXTextRenderer::sp_group_render(SPGroup *group) { - SPGroup *group = SP_GROUP(item); - GSList *l = g_slist_reverse(group->childList(false)); while (l) { - SPObject *o = SP_OBJECT (l->data); - if (SP_IS_ITEM(o)) { - renderItem (SP_ITEM (o)); + SPObject *o = reinterpret_cast<SPObject *>(l->data); + SPItem *item = dynamic_cast<SPItem *>(o); + if (item) { + renderItem(item); } l = g_slist_remove (l, o); } } -void -LaTeXTextRenderer::sp_use_render(SPItem *item) +void LaTeXTextRenderer::sp_use_render(SPUse *use) { bool translated = false; - SPUse *use = SP_USE(item); if ((use->x._set && use->x.computed != 0) || (use->y._set && use->y.computed != 0)) { Geom::Affine tp(Geom::Translate(use->x.computed, use->y.computed)); @@ -252,8 +249,9 @@ LaTeXTextRenderer::sp_use_render(SPItem *item) translated = true; } - if (use->child && SP_IS_ITEM(use->child)) { - renderItem(SP_ITEM(use->child)); + SPItem *childItem = dynamic_cast<SPItem *>(use->child); + if (childItem) { + renderItem(childItem); } if (translated) { @@ -261,16 +259,14 @@ LaTeXTextRenderer::sp_use_render(SPItem *item) } } -void -LaTeXTextRenderer::sp_text_render(SPItem *item) +void LaTeXTextRenderer::sp_text_render(SPText *textobj) { // Only PDFLaTeX supports importing a single page of a graphics file, // so only PDF backend gets interleaved text/graphics if (_pdflatex && _omittext_state == GRAPHIC_ON_TOP) _omittext_state = NEW_PAGE_ON_GRAPHIC; - SPText *textobj = SP_TEXT (item); - SPStyle *style = item->style; + SPStyle *style = textobj->style; // get position and alignment // Align vertically on the baseline of the font (retreived from the anchor point) @@ -312,7 +308,7 @@ LaTeXTextRenderer::sp_text_render(SPItem *item) } // get rotation - Geom::Affine i2doc = item->i2doc_affine(); + Geom::Affine i2doc = textobj->i2doc_affine(); Geom::Affine wotransl = i2doc.withoutTranslation(); double degrees = -180/M_PI * Geom::atan2(wotransl.xAxis()); bool has_rotation = !Geom::are_near(degrees,0.); @@ -336,11 +332,11 @@ LaTeXTextRenderer::sp_text_render(SPItem *item) // Walk through all spans in the text object. // Write span strings to LaTeX, associated with font weight and style. - Inkscape::Text::Layout const &layout = *(te_get_layout (item)); + Inkscape::Text::Layout const &layout = *(te_get_layout (textobj)); for (Inkscape::Text::Layout::iterator li = layout.begin(), le = layout.end(); li != le; li.nextStartOfSpan()) { - SPStyle const &spanstyle = *(sp_te_style_at_position (item, li)); + SPStyle const &spanstyle = *(sp_te_style_at_position (textobj, li)); bool is_bold = false, is_italic = false, is_oblique = false; if (spanstyle.font_weight.computed == SP_CSS_FONT_WEIGHT_500 || @@ -367,7 +363,7 @@ LaTeXTextRenderer::sp_text_render(SPItem *item) Inkscape::Text::Layout::iterator ln = li; ln.nextStartOfSpan(); - Glib::ustring uspanstr = sp_te_get_string_multiline (item, li, ln); + Glib::ustring uspanstr = sp_te_get_string_multiline (textobj, li, ln); const gchar *spanstr = uspanstr.c_str(); if (!spanstr) { continue; @@ -394,8 +390,7 @@ LaTeXTextRenderer::sp_text_render(SPItem *item) fprintf(_stream, "%s", os.str().c_str()); } -void -LaTeXTextRenderer::sp_flowtext_render(SPItem * item) +void LaTeXTextRenderer::sp_flowtext_render(SPFlowtext *flowtext) { /* Flowtext is possible by using a minipage! :) @@ -407,16 +402,15 @@ Flowing in rectangle is possible, not in arb shape. if (_pdflatex && _omittext_state == GRAPHIC_ON_TOP) _omittext_state = NEW_PAGE_ON_GRAPHIC; - SPFlowtext *flowtext = SP_FLOWTEXT(item); - SPStyle *style = item->style; + SPStyle *style = flowtext->style; SPItem *frame_item = flowtext->get_frame(NULL); - if (!frame_item || !SP_IS_RECT(frame_item)) { + SPRect *frame = dynamic_cast<SPRect *>(frame_item); + if (!frame_item || !frame) { g_warning("LaTeX export: non-rectangular flowed text shapes are not supported, skipping text."); return; // don't know how to handle non-rect frames yet. is quite uncommon for latex users i think } - SPRect *frame = SP_RECT(frame_item); Geom::Rect framebox = frame->getRect() * transform(); // get position and alignment @@ -460,7 +454,7 @@ Flowing in rectangle is possible, not in arb shape. } // get rotation - Geom::Affine i2doc = item->i2doc_affine(); + Geom::Affine i2doc = flowtext->i2doc_affine(); Geom::Affine wotransl = i2doc.withoutTranslation(); double degrees = -180/M_PI * Geom::atan2(wotransl.xAxis()); bool has_rotation = !Geom::are_near(degrees,0.); @@ -485,11 +479,11 @@ Flowing in rectangle is possible, not in arb shape. // Walk through all spans in the text object. // Write span strings to LaTeX, associated with font weight and style. - Inkscape::Text::Layout const &layout = *(te_get_layout (item)); + Inkscape::Text::Layout const &layout = *(te_get_layout(flowtext)); for (Inkscape::Text::Layout::iterator li = layout.begin(), le = layout.end(); li != le; li.nextStartOfSpan()) { - SPStyle const &spanstyle = *(sp_te_style_at_position (item, li)); + SPStyle const &spanstyle = *(sp_te_style_at_position(flowtext, li)); bool is_bold = false, is_italic = false, is_oblique = false; if (spanstyle.font_weight.computed == SP_CSS_FONT_WEIGHT_500 || @@ -516,7 +510,7 @@ Flowing in rectangle is possible, not in arb shape. Inkscape::Text::Layout::iterator ln = li; ln.nextStartOfSpan(); - Glib::ustring uspanstr = sp_te_get_string_multiline (item, li, ln); + Glib::ustring uspanstr = sp_te_get_string_multiline(flowtext, li, ln); const gchar *spanstr = uspanstr.c_str(); if (!spanstr) { continue; @@ -558,22 +552,36 @@ LaTeXTextRenderer::sp_item_invoke_render(SPItem *item) return; } - if (SP_IS_ROOT(item)) { - return sp_root_render(SP_ROOT(item)); - } else if (SP_IS_GROUP(item)) { - return sp_group_render(item); - } else if (SP_IS_USE(item)) { - sp_use_render(item); - } else if (SP_IS_TEXT(item)) { - return sp_text_render(item); - } else if (SP_IS_FLOWTEXT(item)) { - return sp_flowtext_render(item); + SPRoot *root = dynamic_cast<SPRoot *>(item); + if (root) { + sp_root_render(root); } else { - // Only PDFLaTeX supports importing a single page of a graphics file, - // so only PDF backend gets interleaved text/graphics - if (_pdflatex && (_omittext_state == EMPTY || _omittext_state == NEW_PAGE_ON_GRAPHIC)) - writeGraphicPage(); - _omittext_state = GRAPHIC_ON_TOP; + SPGroup *group = dynamic_cast<SPGroup *>(item); + if (group) { + sp_group_render(group); + } else { + SPUse *use = dynamic_cast<SPUse *>(item); + if (use) { + sp_use_render(use); + } else { + SPText *text = dynamic_cast<SPText *>(item); + if (text) { + sp_text_render(text); + } else { + SPFlowtext *flowtext = dynamic_cast<SPFlowtext *>(item); + if (flowtext) { + sp_flowtext_render(flowtext); + } else { + // Only PDFLaTeX supports importing a single page of a graphics file, + // so only PDF backend gets interleaved text/graphics + if (_pdflatex && (_omittext_state == EMPTY || _omittext_state == NEW_PAGE_ON_GRAPHIC)) { + writeGraphicPage(); + } + _omittext_state = GRAPHIC_ON_TOP; + } + } + } + } } } diff --git a/src/extension/internal/latex-text-renderer.h b/src/extension/internal/latex-text-renderer.h index 77d12bc61..b9563b53b 100644 --- a/src/extension/internal/latex-text-renderer.h +++ b/src/extension/internal/latex-text-renderer.h @@ -23,6 +23,10 @@ class SPItem; class SPRoot; +class SPGroup; +class SPUse; +class SPText; +class SPFlowtext; namespace Inkscape { namespace Extension { @@ -73,10 +77,10 @@ protected: void sp_item_invoke_render(SPItem *item); void sp_root_render(SPRoot *item); - void sp_group_render(SPItem *item); - void sp_use_render(SPItem *item); - void sp_text_render(SPItem *item); - void sp_flowtext_render(SPItem *item); + void sp_group_render(SPGroup *group); + void sp_use_render(SPUse *use); + void sp_text_render(SPText *text); + void sp_flowtext_render(SPFlowtext *flowtext); }; } /* namespace Internal */ diff --git a/src/helper/pixbuf-ops.cpp b/src/helper/pixbuf-ops.cpp index acb2be4da..9639096fb 100644 --- a/src/helper/pixbuf-ops.cpp +++ b/src/helper/pixbuf-ops.cpp @@ -34,20 +34,21 @@ #include "helper/pixbuf-ops.h" -// TODO look for copy-n-past duplication of this function: +// TODO look for copy-n-paste duplication of this function: /** * Hide all items that are not listed in list, recursively, skipping groups and defs. */ static void hide_other_items_recursively(SPObject *o, GSList *list, unsigned dkey) { - if ( SP_IS_ITEM(o) - && !SP_IS_DEFS(o) - && !SP_IS_ROOT(o) - && !SP_IS_GROUP(o) - && !SP_IS_USE(o) + SPItem *item = dynamic_cast<SPItem *>(o); + if ( item + && !dynamic_cast<SPDefs *>(item) + && !dynamic_cast<SPRoot *>(item) + && !dynamic_cast<SPGroup *>(item) + && !dynamic_cast<SPUse *>(item) && !g_slist_find(list, o) ) { - SP_ITEM(o)->invoke_hide(dkey); + item->invoke_hide(dkey); } // recurse diff --git a/src/libnrtype/Layout-TNG.h b/src/libnrtype/Layout-TNG.h index efb5ebc24..fd5bbfaef 100644 --- a/src/libnrtype/Layout-TNG.h +++ b/src/libnrtype/Layout-TNG.h @@ -481,6 +481,7 @@ public: from a call to appendText() then the optional \a text_iterator parameter is set to point to the actual character, otherwise \a text_iterator is unaltered. */ + // TODO FIXME a void* cookie is a very unsafe design, and C++ makes it unnecessary. void getSourceOfCharacter(iterator const &it, void **source_cookie, Glib::ustring::iterator *text_iterator = NULL) const; /** For latin text, the left side of the character, on the baseline */ diff --git a/src/object-snapper.cpp b/src/object-snapper.cpp index 2b29814b0..338f91463 100644 --- a/src/object-snapper.cpp +++ b/src/object-snapper.cpp @@ -91,7 +91,8 @@ void Inkscape::ObjectSnapper::_findCandidates(SPObject* parent, for ( SPObject *o = parent->firstChild(); o; o = o->getNext() ) { g_assert(dt != NULL); - if (SP_IS_ITEM(o) && !(dt->itemIsHidden(SP_ITEM(o)) && !clip_or_mask)) { + SPItem *item = dynamic_cast<SPItem *>(o); + if (item && !(dt->itemIsHidden(item) && !clip_or_mask)) { // Snapping to items in a locked layer is allowed // Don't snap to hidden objects, unless they're a clipped path or a mask /* See if this item is on the ignore list */ @@ -104,23 +105,22 @@ void Inkscape::ObjectSnapper::_findCandidates(SPObject* parent, } if (it == NULL || i == it->end()) { - SPItem *item = SP_ITEM(o); if (item) { if (!clip_or_mask) { // cannot clip or mask more than once // The current item is not a clipping path or a mask, but might // still be the subject of clipping or masking itself ; if so, then // we should also consider that path or mask for snapping to - SPObject *obj = SP_OBJECT(item->clip_ref ? item->clip_ref->getObject() : NULL); + SPObject *obj = item->clip_ref ? item->clip_ref->getObject() : NULL; if (obj && _snapmanager->snapprefs.isTargetSnappable(SNAPTARGET_PATH_CLIP)) { _findCandidates(obj, it, false, bbox_to_snap, true, item->i2doc_affine()); } - obj = SP_OBJECT(item->mask_ref ? item->mask_ref->getObject() : NULL); + obj = item->mask_ref ? item->mask_ref->getObject() : NULL; if (obj && _snapmanager->snapprefs.isTargetSnappable(SNAPTARGET_PATH_MASK)) { _findCandidates(obj, it, false, bbox_to_snap, true, item->i2doc_affine()); } } - if (SP_IS_GROUP(o)) { + if (dynamic_cast<SPGroup *>(item)) { _findCandidates(o, it, false, bbox_to_snap, clip_or_mask, additional_affine); } else { Geom::OptRect bbox_of_item; @@ -197,8 +197,10 @@ void Inkscape::ObjectSnapper::_collectNodes(SnapSourceType const &t, for (std::vector<SnapCandidateItem>::const_iterator i = _candidates->begin(); i != _candidates->end(); ++i) { //Geom::Affine i2doc(Geom::identity()); SPItem *root_item = (*i).item; - if (SP_IS_USE((*i).item)) { - root_item = SP_USE((*i).item)->root(); + + SPUse *use = dynamic_cast<SPUse *>((*i).item); + if (use) { + root_item = use->root(); } g_return_if_fail(root_item); @@ -382,9 +384,10 @@ void Inkscape::ObjectSnapper::_collectPaths(Geom::Point /*p*/, Geom::Affine i2doc(Geom::identity()); SPItem *root_item = NULL; /* We might have a clone at hand, so make sure we get the root item */ - if (SP_IS_USE((*i).item)) { - i2doc = SP_USE((*i).item)->get_root_transform(); - root_item = SP_USE((*i).item)->root(); + SPUse *use = dynamic_cast<SPUse *>((*i).item); + if (use) { + i2doc = use->get_root_transform(); + root_item = use->root(); g_return_if_fail(root_item); } else { i2doc = (*i).item->i2doc_affine(); @@ -396,7 +399,7 @@ void Inkscape::ObjectSnapper::_collectPaths(Geom::Point /*p*/, //Add the item's path to snap to if (_snapmanager->snapprefs.isTargetSnappable(SNAPTARGET_PATH, SNAPTARGET_PATH_INTERSECTION, SNAPTARGET_TEXT_BASELINE)) { if (p_is_other || p_is_a_node || (!_snapmanager->snapprefs.getStrictSnapping() && p_is_a_bbox)) { - if (SP_IS_TEXT(root_item) || SP_IS_FLOWTEXT(root_item)) { + if (dynamic_cast<SPText *>(root_item) || dynamic_cast<SPFlowtext *>(root_item)) { if (_snapmanager->snapprefs.isTargetSnappable(SNAPTARGET_TEXT_BASELINE)) { // Snap to the text baseline Text::Layout const *layout = te_get_layout(static_cast<SPItem *>(root_item)); @@ -411,15 +414,17 @@ void Inkscape::ObjectSnapper::_collectPaths(Geom::Point /*p*/, // the CPU, so we'll only snap to paths having no more than 500 nodes // This also leads to a lag of approx. 500 msec (in my lousy test set-up). bool very_complex_path = false; - if (SP_IS_PATH(root_item)) { - very_complex_path = SP_PATH(root_item)->nodesInPath() > 500; + SPPath *path = dynamic_cast<SPPath *>(root_item); + if (path) { + very_complex_path = path->nodesInPath() > 500; } if (!very_complex_path && root_item && _snapmanager->snapprefs.isTargetSnappable(SNAPTARGET_PATH, SNAPTARGET_PATH_INTERSECTION)) { SPCurve *curve = NULL; - if (SP_IS_SHAPE(root_item)) { - curve = SP_SHAPE(root_item)->getCurve(); - }/* else if (SP_IS_TEXT(root_item) || SP_IS_FLOWTEXT(root_item)) { + SPShape *shape = dynamic_cast<SPShape *>(root_item); + if (shape) { + curve = shape->getCurve(); + }/* else if (dynamic_cast<SPText *>(root_item) || dynamic_cast<SPFlowtext *>(root_item)) { curve = te_get_layout(root_item)->convertToCurves(); }*/ if (curve) { @@ -711,10 +716,11 @@ void Inkscape::ObjectSnapper::freeSnap(IntermSnapResults &isr, * That path must not be ignored however when snapping to the paths, so we add it here * manually when applicable */ - SPPath *path = NULL; + SPPath const *path = NULL; if (it != NULL) { - if (it->size() == 1 && SP_IS_PATH(*it->begin())) { - path = SP_PATH(*it->begin()); + SPPath const *tmpPath = dynamic_cast<SPPath const *>(*it->begin()); + if ((it->size() == 1) && tmpPath) { + path = tmpPath; } // else: *it->begin() might be a SPGroup, e.g. when editing a LPE of text that has been converted to a group of paths // as reported in bug #356743. In that case we can just ignore it, i.e. not snap to this item } diff --git a/src/selection-describer.cpp b/src/selection-describer.cpp index 1cb96fed0..f7814fd57 100644 --- a/src/selection-describer.cpp +++ b/src/selection-describer.cpp @@ -5,6 +5,7 @@ * MenTaLguY <mental@rydia.net> * bulia byak <buliabyak@users.sf.net> * Abhishek Sharma + * Jon A. Cruz <jon@joncruz.org> * * Copyright (C) 2004-2006 Authors * @@ -46,11 +47,14 @@ char* collect_terms (GSList *items) bool first = true; for (GSList *i = (GSList *)items; i != NULL; i = i->next) { - const char *term = SP_ITEM(i->data)->displayName(); - if (term != NULL && g_slist_find (check, term) == NULL) { - check = g_slist_prepend (check, (void *) term); - ss << (first ? "" : ", ") << "<b>" << term << "</b>"; - first = false; + SPItem *item = dynamic_cast<SPItem *>(reinterpret_cast<SPObject *>(i->data)); + if (item) { + const char *term = item->displayName(); + if (term != NULL && g_slist_find (check, term) == NULL) { + check = g_slist_prepend (check, (void *) term); + ss << (first ? "" : ", ") << "<b>" << term << "</b>"; + first = false; + } } } return g_strdup(ss.str().c_str()); @@ -62,10 +66,13 @@ static int count_terms (GSList *items) GSList *check = NULL; int count=0; for (GSList *i = (GSList *)items; i != NULL; i = i->next) { - const char *term = SP_ITEM(i->data)->displayName(); - if (term != NULL && g_slist_find (check, term) == NULL) { - check = g_slist_prepend (check, (void *) term); - count++; + SPItem *item = dynamic_cast<SPItem *>(reinterpret_cast<SPObject *>(i->data)); + if (item) { + const char *term = item->displayName(); + if (term != NULL && g_slist_find (check, term) == NULL) { + check = g_slist_prepend (check, (void *) term); + count++; + } } } return count; @@ -76,8 +83,10 @@ static int count_filtered (GSList *items) { int count=0; for (GSList *i = items; i != NULL; i = i->next) { - SPItem *item = SP_ITEM(i->data); - count += item->isFiltered(); + SPItem *item = dynamic_cast<SPItem *>(reinterpret_cast<SPObject *>((i->data))); + if (item) { + count += item->isFiltered(); + } } return count; } @@ -118,7 +127,8 @@ void SelectionDescriber::_updateMessageFromSelection(Inkscape::Selection *select if (!items) { // no items _context.set(Inkscape::NORMAL_MESSAGE, _when_nothing); } else { - SPItem *item = SP_ITEM(items->data); + SPItem *item = dynamic_cast<SPItem *>(reinterpret_cast<SPObject *>(items->data)); + g_assert(item != NULL); SPObject *layer = selection->layers()->layerForObject(item); SPObject *root = selection->layers()->currentRoot(); @@ -181,30 +191,41 @@ void SelectionDescriber::_updateMessageFromSelection(Inkscape::Selection *select if (!items->next) { // one item char *item_desc = item->detailedDescription(); - if (SP_IS_USE(item) && SP_IS_SYMBOL(item->firstChild())) { + bool isUse = dynamic_cast<SPUse *>(item) != NULL; + if (isUse && dynamic_cast<SPSymbol *>(item->firstChild())) { _context.setF(Inkscape::NORMAL_MESSAGE, "%s%s. %s. %s.", item_desc, in_phrase, _("Convert symbol to group to edit"), _when_selected); - } else if (SP_IS_SYMBOL(item)) { + } else if (dynamic_cast<SPSymbol *>(item)) { _context.setF(Inkscape::NORMAL_MESSAGE, "%s%s. %s.", item_desc, in_phrase, _("Remove from symbols tray to edit symbol")); - } else if (SP_IS_USE(item) || (SP_IS_OFFSET(item) && SP_OFFSET(item)->sourceHref)) { - _context.setF(Inkscape::NORMAL_MESSAGE, "%s%s. %s. %s.", - item_desc, in_phrase, - _("Use <b>Shift+D</b> to look up original"), _when_selected); - } else if (SP_IS_TEXT_TEXTPATH(item)) { - _context.setF(Inkscape::NORMAL_MESSAGE, "%s%s. %s. %s.", - item_desc, in_phrase, - _("Use <b>Shift+D</b> to look up path"), _when_selected); - } else if (SP_IS_FLOWTEXT(item) && !SP_FLOWTEXT(item)->has_internal_frame()) { - _context.setF(Inkscape::NORMAL_MESSAGE, "%s%s. %s. %s.", - item_desc, in_phrase, - _("Use <b>Shift+D</b> to look up frame"), _when_selected); } else { - _context.setF(Inkscape::NORMAL_MESSAGE, "%s%s. %s.", - item_desc, in_phrase, _when_selected); + SPOffset *offset = (isUse) ? NULL : dynamic_cast<SPOffset *>(item); + if (isUse || (offset && offset->sourceHref)) { + _context.setF(Inkscape::NORMAL_MESSAGE, "%s%s. %s. %s.", + item_desc, in_phrase, + _("Use <b>Shift+D</b> to look up original"), _when_selected); + } else { + SPText *text = dynamic_cast<SPText *>(item); + if (text && text->firstChild() && dynamic_cast<SPText *>(text->firstChild())) { + _context.setF(Inkscape::NORMAL_MESSAGE, "%s%s. %s. %s.", + item_desc, in_phrase, + _("Use <b>Shift+D</b> to look up path"), _when_selected); + } else { + SPFlowtext *flowtext = dynamic_cast<SPFlowtext *>(item); + if (flowtext && !flowtext->has_internal_frame()) { + _context.setF(Inkscape::NORMAL_MESSAGE, "%s%s. %s. %s.", + item_desc, in_phrase, + _("Use <b>Shift+D</b> to look up frame"), _when_selected); + } else { + _context.setF(Inkscape::NORMAL_MESSAGE, "%s%s. %s.", + item_desc, in_phrase, _when_selected); + } + } + } } + g_free(item_desc); } else { // multiple items int objcount = g_slist_length((GSList *)items); diff --git a/src/sp-flowregion.cpp b/src/sp-flowregion.cpp index 32d3b0f60..580945d74 100644 --- a/src/sp-flowregion.cpp +++ b/src/sp-flowregion.cpp @@ -85,12 +85,14 @@ void SPFlowregion::update(SPCtx *ctx, unsigned int flags) { l = g_slist_reverse(l); while (l) { - SPObject *child = SP_OBJECT(l->data); + SPObject *child = reinterpret_cast<SPObject *>(l->data); + g_assert(child != NULL); l = g_slist_remove(l, child); + SPItem *item = dynamic_cast<SPItem *>(child); if (childflags || (child->uflags & (SP_OBJECT_MODIFIED_FLAG | SP_OBJECT_CHILD_MODIFIED_FLAG))) { - if (SP_IS_ITEM (child)) { - SPItem const &chi = *SP_ITEM(child); + if (item) { + SPItem const &chi = *item; cctx.i2doc = chi.transform * ictx->i2doc; cctx.i2vp = chi.transform * ictx->i2vp; child->updateDisplay((SPCtx *)&cctx, childflags); @@ -138,7 +140,8 @@ void SPFlowregion::modified(guint flags) { l = g_slist_reverse(l); while (l) { - SPObject *child = SP_OBJECT(l->data); + SPObject *child = reinterpret_cast<SPObject *>(l->data); + g_assert(child != NULL); l = g_slist_remove(l, child); if (flags || (child->mflags & (SP_OBJECT_MODIFIED_FLAG | SP_OBJECT_CHILD_MODIFIED_FLAG))) { @@ -157,7 +160,7 @@ Inkscape::XML::Node *SPFlowregion::write(Inkscape::XML::Document *xml_doc, Inksc GSList *l = NULL; for ( SPObject *child = this->firstChild() ; child; child = child->getNext() ) { - if ( !SP_IS_TITLE(child) && !SP_IS_DESC(child) ) { + if ( !dynamic_cast<SPTitle *>(child) && !dynamic_cast<SPDesc *>(child) ) { Inkscape::XML::Node *crepr = child->updateRepr(xml_doc, NULL, flags); if (crepr) { @@ -174,7 +177,7 @@ Inkscape::XML::Node *SPFlowregion::write(Inkscape::XML::Document *xml_doc, Inksc } else { for ( SPObject *child = this->firstChild() ; child; child = child->getNext() ) { - if ( !SP_IS_TITLE(child) && !SP_IS_DESC(child) ) { + if ( !dynamic_cast<SPTitle *>(child) && !dynamic_cast<SPDesc *>(child) ) { child->updateRepr(flags); } } @@ -240,12 +243,14 @@ void SPFlowregionExclude::update(SPCtx *ctx, unsigned int flags) { l = g_slist_reverse (l); while (l) { - SPObject *child = SP_OBJECT(l->data); + SPObject *child = reinterpret_cast<SPObject *>(l->data); + g_assert(child != NULL); l = g_slist_remove(l, child); if (flags || (child->uflags & (SP_OBJECT_MODIFIED_FLAG | SP_OBJECT_CHILD_MODIFIED_FLAG))) { - if (SP_IS_ITEM (child)) { - SPItem const &chi = *SP_ITEM(child); + SPItem *item = dynamic_cast<SPItem *>(child); + if (item) { + SPItem const &chi = *item; cctx.i2doc = chi.transform * ictx->i2doc; cctx.i2vp = chi.transform * ictx->i2vp; child->updateDisplay((SPCtx *)&cctx, flags); @@ -290,7 +295,8 @@ void SPFlowregionExclude::modified(guint flags) { l = g_slist_reverse (l); while (l) { - SPObject *child = SP_OBJECT(l->data); + SPObject *child = reinterpret_cast<SPObject *>(l->data); + g_assert(child != NULL); l = g_slist_remove(l, child); if (flags || (child->mflags & (SP_OBJECT_MODIFIED_FLAG | SP_OBJECT_CHILD_MODIFIED_FLAG))) { @@ -363,20 +369,28 @@ static void GetDest(SPObject* child,Shape **computed) SPCurve *curve=NULL; Geom::Affine tr_mat; - SPObject* u_child=child; - if ( SP_IS_USE(u_child) ) { - u_child=SP_USE(u_child)->child; - tr_mat = SP_ITEM(u_child)->getRelativeTransform(child->parent); - } else { - tr_mat = SP_ITEM(u_child)->transform; - } - if ( SP_IS_SHAPE (u_child) ) { - if (!(SP_SHAPE(u_child)->_curve)) - SP_SHAPE (u_child)->set_shape (); - curve = SP_SHAPE (u_child)->getCurve (); - } else if ( SP_IS_TEXT (u_child) ) { - curve = SP_TEXT (u_child)->getNormalizedBpath (); - } + SPObject* u_child = child; + SPItem *item = dynamic_cast<SPItem *>(u_child); + g_assert(item != NULL); + SPUse *use = dynamic_cast<SPUse *>(item); + if ( use ) { + u_child = use->child; + tr_mat = use->getRelativeTransform(child->parent); + } else { + tr_mat = item->transform; + } + SPShape *shape = dynamic_cast<SPShape *>(u_child); + if ( shape ) { + if (!(shape->_curve)) { + shape->set_shape(); + } + curve = shape->getCurve(); + } else { + SPText *text = dynamic_cast<SPText *>(u_child); + if ( text ) { + curve = text->getNormalizedBpath(); + } + } if ( curve ) { Path* temp=new Path; diff --git a/src/sp-flowtext.cpp b/src/sp-flowtext.cpp index 72fe86daf..766026980 100644 --- a/src/sp-flowtext.cpp +++ b/src/sp-flowtext.cpp @@ -86,12 +86,14 @@ void SPFlowtext::update(SPCtx* ctx, unsigned int flags) { l = g_slist_reverse(l); while (l) { - SPObject *child = SP_OBJECT(l->data); + SPObject *child = reinterpret_cast<SPObject *>(l->data); + g_assert(child != NULL); l = g_slist_remove(l, child); if (childflags || (child->uflags & (SP_OBJECT_MODIFIED_FLAG | SP_OBJECT_CHILD_MODIFIED_FLAG))) { - if (SP_IS_ITEM(child)) { - SPItem const &chi = *SP_ITEM(child); + SPItem *item = dynamic_cast<SPItem *>(child); + if (item) { + SPItem const &chi = *item; cctx.i2doc = chi.transform * ictx->i2doc; cctx.i2vp = chi.transform * ictx->i2vp; child->updateDisplay((SPCtx *)&cctx, childflags); @@ -129,19 +131,18 @@ void SPFlowtext::modified(unsigned int flags) { // FIXME: the below stanza is copied over from sp_text_modified, consider factoring it out if (flags & ( SP_OBJECT_STYLE_MODIFIED_FLAG )) { - SPFlowtext *text = SP_FLOWTEXT(this); - Geom::OptRect pbox = text->geometricBounds(); + Geom::OptRect pbox = geometricBounds(); - for (SPItemView* v = text->display; v != NULL; v = v->next) { + for (SPItemView* v = display; v != NULL; v = v->next) { Inkscape::DrawingGroup *g = dynamic_cast<Inkscape::DrawingGroup *>(v->arenaitem); - text->_clearFlow(g); - g->setStyle(this->style); - text->layout.show(g, pbox); + _clearFlow(g); + g->setStyle(style); + layout.show(g, pbox); } } for ( SPObject *o = this->firstChild() ; o ; o = o->getNext() ) { - if (SP_IS_FLOWREGION(o)) { + if (dynamic_cast<SPFlowregion *>(o)) { region = o; break; } @@ -231,7 +232,7 @@ Inkscape::XML::Node* SPFlowtext::write(Inkscape::XML::Document* doc, Inkscape::X for (SPObject *child = this->firstChild() ; child ; child = child->getNext() ) { Inkscape::XML::Node *c_repr = NULL; - if ( SP_IS_FLOWDIV(child) || SP_IS_FLOWPARA(child) || SP_IS_FLOWREGION(child) || SP_IS_FLOWREGIONEXCLUDE(child)) { + if ( dynamic_cast<SPFlowdiv *>(child) || dynamic_cast<SPFlowpara *>(child) || dynamic_cast<SPFlowregion *>(child) || dynamic_cast<SPFlowregionExclude *>(child)) { c_repr = child->updateRepr(doc, NULL, flags); } @@ -247,7 +248,7 @@ Inkscape::XML::Node* SPFlowtext::write(Inkscape::XML::Document* doc, Inkscape::X } } else { for (SPObject *child = this->firstChild() ; child ; child = child->getNext() ) { - if ( SP_IS_FLOWDIV(child) || SP_IS_FLOWPARA(child) || SP_IS_FLOWREGION(child) || SP_IS_FLOWREGIONEXCLUDE(child) ) { + if ( dynamic_cast<SPFlowdiv *>(child) || dynamic_cast<SPFlowpara *>(child) || dynamic_cast<SPFlowregion *>(child) || dynamic_cast<SPFlowregionExclude *>(child)) { child->updateRepr(flags); } } @@ -285,7 +286,7 @@ void SPFlowtext::print(SPPrintContext *ctx) { } const char* SPFlowtext::displayName() const { - if (SP_FLOWTEXT(this)->has_internal_frame()) { + if (has_internal_frame()) { return _("Flowed Text"); } else { return _("Linked Flowed Text"); @@ -293,7 +294,6 @@ const char* SPFlowtext::displayName() const { } gchar* SPFlowtext::description() const { - Inkscape::Text::Layout const &layout = SP_FLOWTEXT(this)->layout; int const nChars = layout.iteratorToCharIndex(layout.end()); char const *trunc = (layout.inputTruncated()) ? _(" [truncated]") : ""; @@ -346,12 +346,17 @@ void SPFlowtext::_buildLayoutInput(SPObject *root, Shape const *exclusion_shape, Inkscape::Text::Layout::OptionalTextTagAttrs pi; bool with_indent = false; - if (SP_IS_FLOWPARA(root)) { + if (dynamic_cast<SPFlowpara *>(root)) { // emulate par-indent with the first char's kern SPObject *t = root; - for ( ; t != NULL && !SP_IS_FLOWTEXT(t); t = t->parent){}; - if (SP_IS_FLOWTEXT(t)) { - double indent = SP_FLOWTEXT(t)->par_indent; + SPFlowtext *ft = NULL; + while (t && !ft) { + ft = dynamic_cast<SPFlowtext *>(t); + t = t->parent; + } + + if (ft) { + double indent = ft->par_indent; if (indent != 0) { with_indent = true; SVGLength sl; @@ -363,7 +368,7 @@ void SPFlowtext::_buildLayoutInput(SPObject *root, Shape const *exclusion_shape, } if (*pending_line_break_object) { - if (SP_IS_FLOWREGIONBREAK(*pending_line_break_object)) { + if (dynamic_cast<SPFlowregionbreak *>(*pending_line_break_object)) { layout.appendControlCode(Inkscape::Text::Layout::SHAPE_BREAK, *pending_line_break_object); } else { layout.appendControlCode(Inkscape::Text::Layout::PARAGRAPH_BREAK, *pending_line_break_object); @@ -372,9 +377,10 @@ void SPFlowtext::_buildLayoutInput(SPObject *root, Shape const *exclusion_shape, } for (SPObject *child = root->firstChild() ; child ; child = child->getNext() ) { - if (SP_IS_STRING(child)) { + SPString *str = dynamic_cast<SPString *>(child); + if (str) { if (*pending_line_break_object) { - if (SP_IS_FLOWREGIONBREAK(*pending_line_break_object)) + if (dynamic_cast<SPFlowregionbreak *>(*pending_line_break_object)) layout.appendControlCode(Inkscape::Text::Layout::SHAPE_BREAK, *pending_line_break_object); else { layout.appendControlCode(Inkscape::Text::Layout::PARAGRAPH_BREAK, *pending_line_break_object); @@ -382,31 +388,35 @@ void SPFlowtext::_buildLayoutInput(SPObject *root, Shape const *exclusion_shape, *pending_line_break_object = NULL; } if (with_indent) { - layout.appendText(SP_STRING(child)->string, root->style, child, &pi); + layout.appendText(str->string, root->style, child, &pi); } else { - layout.appendText(SP_STRING(child)->string, root->style, child); + layout.appendText(str->string, root->style, child); } - } else if (SP_IS_FLOWREGION(child)) { - std::vector<Shape*> const &computed = SP_FLOWREGION(child)->computed; - for (std::vector<Shape*>::const_iterator it = computed.begin() ; it != computed.end() ; ++it) { - shapes->push_back(Shape()); - if (exclusion_shape->hasEdges()) { - shapes->back().Booleen(*it, const_cast<Shape*>(exclusion_shape), bool_op_diff); - } else { - shapes->back().Copy(*it); + } else { + SPFlowregion *region = dynamic_cast<SPFlowregion *>(child); + if (region) { + std::vector<Shape*> const &computed = region->computed; + for (std::vector<Shape*>::const_iterator it = computed.begin() ; it != computed.end() ; ++it) { + shapes->push_back(Shape()); + if (exclusion_shape->hasEdges()) { + shapes->back().Booleen(*it, const_cast<Shape*>(exclusion_shape), bool_op_diff); + } else { + shapes->back().Copy(*it); + } + layout.appendWrapShape(&shapes->back()); } - layout.appendWrapShape(&shapes->back()); } - } - //XML Tree is being directly used while it shouldn't be. - else if (!SP_IS_FLOWREGIONEXCLUDE(child) && !sp_repr_is_meta_element(child->getRepr())) { - _buildLayoutInput(child, exclusion_shape, shapes, pending_line_break_object); + //Xml Tree is being directly used while it shouldn't be. + else if (!dynamic_cast<SPFlowregionExclude *>(child) && !sp_repr_is_meta_element(child->getRepr())) { + _buildLayoutInput(child, exclusion_shape, shapes, pending_line_break_object); + } } } - if (SP_IS_FLOWDIV(root) || SP_IS_FLOWPARA(root) || SP_IS_FLOWREGIONBREAK(root) || SP_IS_FLOWLINE(root)) { - if (!root->hasChildren()) + if (dynamic_cast<SPFlowdiv *>(root) || dynamic_cast<SPFlowpara *>(root) || dynamic_cast<SPFlowregionbreak *>(root) || dynamic_cast<SPFlowline *>(root)) { + if (!root->hasChildren()) { layout.appendText("", root->style, root); + } *pending_line_break_object = root; } } @@ -418,16 +428,13 @@ Shape* SPFlowtext::_buildExclusionShape() const for (SPObject *child = children ; child ; child = child->getNext() ) { // RH: is it right that this shouldn't be recursive? - if ( SP_IS_FLOWREGIONEXCLUDE(child) ) { - SPFlowregionExclude *c_child = SP_FLOWREGIONEXCLUDE(child); - - if ( c_child->computed && c_child->computed->hasEdges() ) { - if (shape->hasEdges()) { - shape_temp->Booleen(shape, c_child->computed, bool_op_union); - std::swap(shape, shape_temp); - } else { - shape->Copy(c_child->computed); - } + SPFlowregionExclude *c_child = dynamic_cast<SPFlowregionExclude *>(child); + if ( c_child && c_child->computed && c_child->computed->hasEdges() ) { + if (shape->hasEdges()) { + shape_temp->Booleen(shape, c_child->computed, bool_op_union); + std::swap(shape, shape_temp); + } else { + shape->Copy(c_child->computed); } } } @@ -514,24 +521,23 @@ Inkscape::XML::Node *SPFlowtext::getAsText() sp_repr_set_svg_double(line_tspan, "y", anchor_point[Geom::Y]); } - SPObject *source_obj = 0; void *rawptr = 0; Glib::ustring::iterator span_text_start_iter; this->layout.getSourceOfCharacter(it, &rawptr, &span_text_start_iter); - source_obj = SP_OBJECT (rawptr); - gchar *style_text = sp_style_write_difference((SP_IS_STRING(source_obj) ? source_obj->parent : source_obj)->style, this->style); + SPObject *source_obj = reinterpret_cast<SPObject *>(rawptr); + gchar *style_text = sp_style_write_difference((dynamic_cast<SPString *>(source_obj) ? source_obj->parent : source_obj)->style, this->style); if (style_text && *style_text) { span_tspan->setAttribute("style", style_text); g_free(style_text); } - if (SP_IS_STRING(source_obj)) { - Glib::ustring *string = &SP_STRING(source_obj)->string; - SPObject *span_end_obj = 0; + SPString *str = dynamic_cast<SPString *>(source_obj); + if (str) { + Glib::ustring *string = &(str->string); // TODO fixme: dangerous, unsafe premature-optimization void *rawptr = 0; Glib::ustring::iterator span_text_end_iter; this->layout.getSourceOfCharacter(it_span_end, &rawptr, &span_text_end_iter); - span_end_obj = SP_OBJECT(rawptr); + SPObject *span_end_obj = reinterpret_cast<SPObject *>(rawptr); if (span_end_obj != source_obj) { if (it_span_end == this->layout.end()) { span_text_end_iter = span_text_start_iter; @@ -562,13 +568,19 @@ Inkscape::XML::Node *SPFlowtext::getAsText() return repr; } -SPItem *SPFlowtext::get_frame(SPItem *after) +SPItem const *SPFlowtext::get_frame(SPItem const *after) const +{ + SPItem *item = const_cast<SPFlowtext *>(this)->get_frame(after); + return item; +} + +SPItem *SPFlowtext::get_frame(SPItem const *after) { SPItem *frame = 0; SPObject *region = 0; for (SPObject *o = firstChild() ; o ; o = o->getNext() ) { - if (SP_IS_FLOWREGION(o)) { + if (dynamic_cast<SPFlowregion *>(o)) { region = o; break; } @@ -578,29 +590,31 @@ SPItem *SPFlowtext::get_frame(SPItem *after) bool past = false; for (SPObject *o = region->firstChild() ; o ; o = o->getNext() ) { - if (SP_IS_ITEM(o)) { + SPItem *item = dynamic_cast<SPItem *>(o); + if (item) { if ( (after == NULL) || past ) { - frame = SP_ITEM(o); + frame = item; } else { - if (SP_ITEM(o) == after) { + if (item == after) { past = true; } } } } - if ( frame && SP_IS_USE(frame) ) { - frame = SP_USE(frame)->get_original(); + SPUse *use = dynamic_cast<SPUse *>(frame); + if ( use ) { + frame = use->get_original(); } } return frame; } -bool SPFlowtext::has_internal_frame() +bool SPFlowtext::has_internal_frame() const { - SPItem *frame = get_frame(NULL); + SPItem const *frame = get_frame(NULL); - return (frame && this->isAncestorOf(frame) && SP_IS_RECT(frame)); + return (frame && isAncestorOf(frame) && dynamic_cast<SPRect const *>(frame)); } @@ -611,19 +625,21 @@ SPItem *create_flowtext_with_internal_frame (SPDesktop *desktop, Geom::Point p0, Inkscape::XML::Document *xml_doc = doc->getReprDoc(); Inkscape::XML::Node *root_repr = xml_doc->createElement("svg:flowRoot"); root_repr->setAttribute("xml:space", "preserve"); // we preserve spaces in the text objects we create - SPItem *ft_item = SP_ITEM(desktop->currentLayer()->appendChildRepr(root_repr)); + SPItem *ft_item = dynamic_cast<SPItem *>(desktop->currentLayer()->appendChildRepr(root_repr)); + g_assert(ft_item != NULL); SPObject *root_object = doc->getObjectByRepr(root_repr); - g_assert(SP_IS_FLOWTEXT(root_object)); + g_assert(dynamic_cast<SPFlowtext *>(root_object) != NULL); Inkscape::XML::Node *region_repr = xml_doc->createElement("svg:flowRegion"); root_repr->appendChild(region_repr); SPObject *region_object = doc->getObjectByRepr(region_repr); - g_assert(SP_IS_FLOWREGION(region_object)); + g_assert(dynamic_cast<SPFlowregion *>(region_object) != NULL); Inkscape::XML::Node *rect_repr = xml_doc->createElement("svg:rect"); // FIXME: use path!!! after rects are converted to use path region_repr->appendChild(rect_repr); - SPRect *rect = SP_RECT(doc->getObjectByRepr(rect_repr)); + SPRect *rect = dynamic_cast<SPRect *>(doc->getObjectByRepr(rect_repr)); + g_assert(rect != NULL); p0 *= desktop->dt2doc(); p1 *= desktop->dt2doc(); @@ -642,7 +658,7 @@ SPItem *create_flowtext_with_internal_frame (SPDesktop *desktop, Geom::Point p0, Inkscape::XML::Node *para_repr = xml_doc->createElement("svg:flowPara"); root_repr->appendChild(para_repr); SPObject *para_object = doc->getObjectByRepr(para_repr); - g_assert(SP_IS_FLOWPARA(para_object)); + g_assert(dynamic_cast<SPFlowpara *>(para_object) != NULL); Inkscape::XML::Node *text = xml_doc->createTextNode(""); para_repr->appendChild(text); @@ -652,7 +668,10 @@ SPItem *create_flowtext_with_internal_frame (SPDesktop *desktop, Geom::Point p0, Inkscape::GC::release(para_repr); Inkscape::GC::release(rect_repr); - ft_item->transform = SP_ITEM(desktop->currentLayer())->i2doc_affine().inverse(); + + SPItem *item = dynamic_cast<SPItem *>(desktop->currentLayer()); + g_assert(item != NULL); + ft_item->transform = item->i2doc_affine().inverse(); return ft_item; } @@ -675,14 +694,14 @@ Geom::Affine SPFlowtext::set_transform (Geom::Affine const &xform) SPObject *region = NULL; for ( SPObject *o = this->firstChild() ; o ; o = o->getNext() ) { - if (SP_IS_FLOWREGION(o)) { + if (dynamic_cast<SPFlowregion *>(o)) { region = o; break; } } if (region) { - if (SP_IS_RECT(region->firstChild())) { - SPRect *rect = SP_RECT(region->firstChild()); + SPRect *rect = dynamic_cast<SPRect *>(region->firstChild()); + if (rect) { rect->set_i2d_affine(xform * rect->i2dt_affine()); rect->doWriteTransform(rect->getRepr(), rect->transform, NULL, true); } diff --git a/src/sp-flowtext.h b/src/sp-flowtext.h index 743d55030..9e6046469 100644 --- a/src/sp-flowtext.h +++ b/src/sp-flowtext.h @@ -31,9 +31,13 @@ public: but losing the automatic wrapping ability. */ Inkscape::XML::Node *getAsText(); - SPItem *get_frame(SPItem *after); + // TODO check if these should return SPRect instead of SPItem - bool has_internal_frame(); + SPItem *get_frame(SPItem const *after); + + SPItem const *get_frame(SPItem const *after) const; + + bool has_internal_frame() const; //semiprivate: (need to be accessed by the C-style functions still) Inkscape::Text::Layout layout; diff --git a/src/sp-item.cpp b/src/sp-item.cpp index ebb08e3d8..73347fc4e 100644 --- a/src/sp-item.cpp +++ b/src/sp-item.cpp @@ -130,7 +130,8 @@ bool SPItem::isVisibleAndUnlocked(unsigned display_key) const { bool SPItem::isLocked() const { for (SPObject const *o = this; o != NULL; o = o->parent) { - if (SP_IS_ITEM(o) && !(SP_ITEM(o)->sensitive)) { + SPItem const *item = dynamic_cast<SPItem const *>(o); + if (item && !(item->sensitive)) { return true; } } @@ -185,14 +186,17 @@ guint32 SPItem::highlight_color() const { { return atoi(_highlightColor) | 0x00000000; } - else if (parent && parent != this && SP_IS_ITEM(parent)) - { - return SP_ITEM(parent)->highlight_color(); - } - else - { - static Inkscape::Preferences *prefs = Inkscape::Preferences::get(); - return prefs->getInt("/tools/nodes/highlight_color", 0xff0000ff) | 0x00000000; + else { + SPItem const *item = dynamic_cast<SPItem const *>(parent); + if (parent && (parent != this) && item) + { + return item->highlight_color(); + } + else + { + static Inkscape::Preferences *prefs = Inkscape::Preferences::get(); + return prefs->getInt("/tools/nodes/highlight_color", 0xff0000ff) | 0x00000000; + } } } @@ -209,8 +213,9 @@ void SPItem::resetEvaluated() { requestDisplayUpdate(SP_OBJECT_MODIFIED_FLAG | SP_OBJECT_STYLE_MODIFIED_FLAG); } } if ( StatusSet == _evaluated_status ) { - if (SP_IS_SWITCH(parent)) { - SP_SWITCH(parent)->resetChildEvaluated(); + SPSwitch *switchItem = dynamic_cast<SPSwitch *>(parent); + if (switchItem) { + switchItem->resetChildEvaluated(); } } } @@ -306,7 +311,7 @@ SPItem::scaleCenter(Geom::Scale const &sc) { namespace { bool is_item(SPObject const &object) { - return SP_IS_ITEM(&object); + return dynamic_cast<SPItem const *>(&object) != NULL; } } @@ -566,20 +571,23 @@ void SPItem::clip_ref_changed(SPObject *old_clip, SPObject *clip, SPItem *item) SPItemView *v; /* Hide clippath */ for (v = item->display; v != NULL; v = v->next) { - SP_CLIPPATH(old_clip)->hide(v->arenaitem->key()); + SPClipPath *oldPath = dynamic_cast<SPClipPath *>(old_clip); + g_assert(oldPath != NULL); + oldPath->hide(v->arenaitem->key()); } } - if (SP_IS_CLIPPATH(clip)) { + SPClipPath *clipPath = dynamic_cast<SPClipPath *>(clip); + if (clipPath) { Geom::OptRect bbox = item->geometricBounds(); for (SPItemView *v = item->display; v != NULL; v = v->next) { if (!v->arenaitem->key()) { v->arenaitem->setKey(SPItem::display_key_new(3)); } - Inkscape::DrawingItem *ai = SP_CLIPPATH(clip)->show( + Inkscape::DrawingItem *ai = clipPath->show( v->arenaitem->drawing(), v->arenaitem->key()); v->arenaitem->setClip(ai); - SP_CLIPPATH(clip)->setBBox(v->arenaitem->key(), bbox); + clipPath->setBBox(v->arenaitem->key(), bbox); clip->requestDisplayUpdate(SP_OBJECT_MODIFIED_FLAG); } } @@ -590,34 +598,37 @@ void SPItem::mask_ref_changed(SPObject *old_mask, SPObject *mask, SPItem *item) if (old_mask) { /* Hide mask */ for (SPItemView *v = item->display; v != NULL; v = v->next) { - SP_MASK(old_mask)->sp_mask_hide(v->arenaitem->key()); + SPMask *maskItem = dynamic_cast<SPMask *>(old_mask); + g_assert(maskItem != NULL); + maskItem->sp_mask_hide(v->arenaitem->key()); } } - if (SP_IS_MASK(mask)) { + SPMask *maskItem = dynamic_cast<SPMask *>(mask); + if (maskItem) { Geom::OptRect bbox = item->geometricBounds(); for (SPItemView *v = item->display; v != NULL; v = v->next) { if (!v->arenaitem->key()) { v->arenaitem->setKey(SPItem::display_key_new(3)); } - Inkscape::DrawingItem *ai = SP_MASK(mask)->sp_mask_show( + Inkscape::DrawingItem *ai = maskItem->sp_mask_show( v->arenaitem->drawing(), v->arenaitem->key()); v->arenaitem->setMask(ai); - SP_MASK(mask)->sp_mask_set_bbox(v->arenaitem->key(), bbox); + maskItem->sp_mask_set_bbox(v->arenaitem->key(), bbox); mask->requestDisplayUpdate(SP_OBJECT_MODIFIED_FLAG); } } } void SPItem::fill_ps_ref_changed(SPObject *old_ps, SPObject *ps, SPItem *item) { - SPPaintServer *old_fill_ps = SP_PAINT_SERVER(old_ps); + SPPaintServer *old_fill_ps = dynamic_cast<SPPaintServer *>(old_ps); if (old_fill_ps) { for (SPItemView *v =item->display; v != NULL; v = v->next) { old_fill_ps->hide(v->arenaitem->key()); } } - SPPaintServer *new_fill_ps = SP_PAINT_SERVER(ps); + SPPaintServer *new_fill_ps = dynamic_cast<SPPaintServer *>(ps); if (new_fill_ps) { Geom::OptRect bbox = item->geometricBounds(); for (SPItemView *v = item->display; v != NULL; v = v->next) { @@ -635,14 +646,14 @@ void SPItem::fill_ps_ref_changed(SPObject *old_ps, SPObject *ps, SPItem *item) { } void SPItem::stroke_ps_ref_changed(SPObject *old_ps, SPObject *ps, SPItem *item) { - SPPaintServer *old_stroke_ps = SP_PAINT_SERVER(old_ps); + SPPaintServer *old_stroke_ps = dynamic_cast<SPPaintServer *>(old_ps); if (old_stroke_ps) { for (SPItemView *v =item->display; v != NULL; v = v->next) { old_stroke_ps->hide(v->arenaitem->key()); } } - SPPaintServer *new_stroke_ps = SP_PAINT_SERVER(ps); + SPPaintServer *new_stroke_ps = dynamic_cast<SPPaintServer *>(ps); if (new_stroke_ps) { Geom::OptRect bbox = item->geometricBounds(); for (SPItemView *v = item->display; v != NULL; v = v->next) { @@ -731,7 +742,7 @@ Inkscape::XML::Node* SPItem::write(Inkscape::XML::Document *xml_doc, Inkscape::X if (flags & SP_OBJECT_WRITE_BUILD) { GSList *l = NULL; for (SPObject *child = object->firstChild(); child != NULL; child = child->next ) { - if (SP_IS_TITLE(child) || SP_IS_DESC(child)) { + if (dynamic_cast<SPTitle *>(child) || dynamic_cast<SPDesc *>(child)) { Inkscape::XML::Node *crepr = child->updateRepr(xml_doc, NULL, flags); if (crepr) { l = g_slist_prepend (l, crepr); @@ -745,7 +756,7 @@ Inkscape::XML::Node* SPItem::write(Inkscape::XML::Document *xml_doc, Inkscape::X } } else { for (SPObject *child = object->firstChild() ; child != NULL; child = child->next ) { - if (SP_IS_TITLE(child) || SP_IS_DESC(child)) { + if (dynamic_cast<SPTitle *>(child) || dynamic_cast<SPDesc *>(child)) { child->updateRepr(flags); } } @@ -821,13 +832,14 @@ Geom::OptRect SPItem::visualBounds(Geom::Affine const &transform) const Geom::OptRect bbox; - if ( style && style->filter.href && style->getFilter() && SP_IS_FILTER(style->getFilter())) { + + SPFilter *filter = (style && style->filter.href) ? dynamic_cast<SPFilter *>(style->getFilter()) : NULL; + if ( filter ) { // call the subclass method // CPPIFY //bbox = this->bbox(Geom::identity(), SPItem::VISUAL_BBOX); bbox = const_cast<SPItem*>(this)->bbox(Geom::identity(), SPItem::GEOMETRIC_BBOX); // see LP Bug 1229971 - SPFilter *filter = SP_FILTER(style->getFilter()); // default filer area per the SVG spec: SVGLength x, y, w, h; Geom::Point minp, maxp; @@ -874,8 +886,10 @@ Geom::OptRect SPItem::visualBounds(Geom::Affine const &transform) const bbox = const_cast<SPItem*>(this)->bbox(transform, SPItem::VISUAL_BBOX); } if (clip_ref->getObject()) { - SP_ITEM(clip_ref->getOwner())->bbox_valid = FALSE; // LP Bug 1349018 - bbox.intersectWith(SP_CLIPPATH(clip_ref->getObject())->geometricBounds(transform)); + SPItem *ownerItem = dynamic_cast<SPItem *>(clip_ref->getOwner()); + g_assert(ownerItem != NULL); + ownerItem->bbox_valid = FALSE; // LP Bug 1349018 + bbox.intersectWith(clip_ref->getObject()->geometricBounds(transform)); } return bbox; @@ -955,7 +969,7 @@ unsigned int SPItem::pos_in_parent() const { return pos; } - if (SP_IS_ITEM(iter)) { + if (dynamic_cast<SPItem *>(iter)) { pos++; } } @@ -997,10 +1011,11 @@ void SPItem::getSnappoints(std::vector<Inkscape::SnapCandidatePoint> &p, Inkscap if (*o) { // obj is a group object, the children are the actual clippers for (SPObject *child = (*o)->children ; child ; child = child->next) { - if (SP_IS_ITEM(child)) { + SPItem *item = dynamic_cast<SPItem *>(child); + if (item) { std::vector<Inkscape::SnapCandidatePoint> p_clip_or_mask; // Please note the recursive call here! - SP_ITEM(child)->getSnappoints(p_clip_or_mask, snapprefs); + item->getSnappoints(p_clip_or_mask, snapprefs); // Take into account the transformation of the item being clipped or masked for (std::vector<Inkscape::SnapCandidatePoint>::const_iterator p_orig = p_clip_or_mask.begin(); p_orig != p_clip_or_mask.end(); ++p_orig) { // All snappoints are in desktop coordinates, but the item's transformation is @@ -1122,7 +1137,7 @@ Inkscape::DrawingItem *SPItem::invoke_show(Inkscape::Drawing &drawing, unsigned ai->setClip(ac); // Update bbox, in case the clip uses bbox units - SP_CLIPPATH(cp)->setBBox(clip_key, item_bbox); + cp->setBBox(clip_key, item_bbox); cp->requestDisplayUpdate(SP_OBJECT_MODIFIED_FLAG); } if (mask_ref->getObject()) { @@ -1138,7 +1153,7 @@ Inkscape::DrawingItem *SPItem::invoke_show(Inkscape::Drawing &drawing, unsigned ai->setMask(ac); // Update bbox, in case the mask uses bbox units - SP_MASK(mask)->sp_mask_set_bbox(mask_key, item_bbox); + mask->sp_mask_set_bbox(mask_key, item_bbox); mask->requestDisplayUpdate(SP_OBJECT_MODIFIED_FLAG); } @@ -1226,8 +1241,9 @@ void SPItem::adjust_pattern(Geom::Affine const &postmul, bool set, PatternTransf bool fill = (pt == TRANSFORM_FILL || pt == TRANSFORM_BOTH); if (fill && style && (style->fill.isPaintserver())) { SPObject *server = style->getFillPaintServer(); - if ( SP_IS_PATTERN(server) ) { - SPPattern *pattern = sp_pattern_clone_if_necessary(this, SP_PATTERN(server), "fill"); + SPPattern *serverPatt = dynamic_cast<SPPattern *>(server); + if ( serverPatt ) { + SPPattern *pattern = sp_pattern_clone_if_necessary(this, serverPatt, "fill"); sp_pattern_transform_multiply(pattern, postmul, set); } } @@ -1235,8 +1251,9 @@ void SPItem::adjust_pattern(Geom::Affine const &postmul, bool set, PatternTransf bool stroke = (pt == TRANSFORM_STROKE || pt == TRANSFORM_BOTH); if (stroke && style && (style->stroke.isPaintserver())) { SPObject *server = style->getStrokePaintServer(); - if ( SP_IS_PATTERN(server) ) { - SPPattern *pattern = sp_pattern_clone_if_necessary(this, SP_PATTERN(server), "stroke"); + SPPattern *serverPatt = dynamic_cast<SPPattern *>(server); + if ( serverPatt ) { + SPPattern *pattern = sp_pattern_clone_if_necessary(this, serverPatt, "stroke"); sp_pattern_transform_multiply(pattern, postmul, set); } } @@ -1246,7 +1263,8 @@ void SPItem::adjust_gradient( Geom::Affine const &postmul, bool set ) { if ( style && style->fill.isPaintserver() ) { SPPaintServer *server = style->getFillPaintServer(); - if ( SP_IS_GRADIENT(server) ) { + SPGradient *serverGrad = dynamic_cast<SPGradient *>(server); + if ( serverGrad ) { /** * \note Bbox units for a gradient are generally a bad idea because @@ -1257,7 +1275,7 @@ void SPItem::adjust_gradient( Geom::Affine const &postmul, bool set ) * \todo FIXME: convert back to bbox units after transforming with * the item, so as to preserve the original units. */ - SPGradient *gradient = sp_gradient_convert_to_userspace( SP_GRADIENT(server), this, "fill" ); + SPGradient *gradient = sp_gradient_convert_to_userspace( serverGrad, this, "fill" ); sp_gradient_transform_multiply( gradient, postmul, set ); } @@ -1265,8 +1283,9 @@ void SPItem::adjust_gradient( Geom::Affine const &postmul, bool set ) if ( style && style->stroke.isPaintserver() ) { SPPaintServer *server = style->getStrokePaintServer(); - if ( SP_IS_GRADIENT(server) ) { - SPGradient *gradient = sp_gradient_convert_to_userspace( SP_GRADIENT(server), this, "stroke"); + SPGradient *serverGrad = dynamic_cast<SPGradient *>(server); + if ( serverGrad ) { + SPGradient *gradient = sp_gradient_convert_to_userspace( serverGrad, this, "stroke"); sp_gradient_transform_multiply( gradient, postmul, set ); } } @@ -1318,10 +1337,11 @@ void SPItem::adjust_stroke_width_recursive(double expansion) adjust_stroke (expansion); // A clone's child is the ghost of its original - we must not touch it, skip recursion - if ( !SP_IS_USE(this) ) { + if ( !dynamic_cast<SPUse *>(this) ) { for ( SPObject *o = children; o; o = o->getNext() ) { - if (SP_IS_ITEM(o)) { - SP_ITEM(o)->adjust_stroke_width_recursive(expansion); + SPItem *item = dynamic_cast<SPItem *>(o); + if (item) { + item->adjust_stroke_width_recursive(expansion); } } } @@ -1332,10 +1352,11 @@ void SPItem::freeze_stroke_width_recursive(bool freeze) freeze_stroke_width = freeze; // A clone's child is the ghost of its original - we must not touch it, skip recursion - if ( !SP_IS_USE(this) ) { + if ( !dynamic_cast<SPUse *>(this) ) { for ( SPObject *o = children; o; o = o->getNext() ) { - if (SP_IS_ITEM(o)) { - SP_ITEM(o)->freeze_stroke_width_recursive(freeze); + SPItem *item = dynamic_cast<SPItem *>(o); + if (item) { + item->freeze_stroke_width_recursive(freeze); } } } @@ -1347,13 +1368,16 @@ void SPItem::freeze_stroke_width_recursive(bool freeze) static void sp_item_adjust_rects_recursive(SPItem *item, Geom::Affine advertized_transform) { - if (SP_IS_RECT (item)) { - SP_RECT(item)->compensateRxRy(advertized_transform); + SPRect *rect = dynamic_cast<SPRect *>(item); + if (rect) { + rect->compensateRxRy(advertized_transform); } for (SPObject *o = item->children; o != NULL; o = o->next) { - if (SP_IS_ITEM(o)) - sp_item_adjust_rects_recursive(SP_ITEM(o), advertized_transform); + SPItem *item = dynamic_cast<SPItem *>(o); + if (item) { + sp_item_adjust_rects_recursive(item, advertized_transform); + } } } @@ -1368,12 +1392,13 @@ void SPItem::adjust_paint_recursive (Geom::Affine advertized_transform, Geom::Af // Within text, we do not fork gradients, and so must not recurse to avoid double compensation; // also we do not recurse into clones, because a clone's child is the ghost of its original - // we must not touch it - if (!(this && (SP_IS_TEXT(this) || SP_IS_USE(this)))) { + if (!(this && (dynamic_cast<SPText *>(this) || dynamic_cast<SPUse *>(this)))) { for (SPObject *o = children; o != NULL; o = o->next) { - if (SP_IS_ITEM(o)) { + SPItem *item = dynamic_cast<SPItem *>(o); + if (item) { // At the level of the transformed item, t_ancestors is identity; // below it, it is the accmmulated chain of transforms from this level to the top level - SP_ITEM(o)->adjust_paint_recursive (advertized_transform, t_item * t_ancestors, is_pattern); + item->adjust_paint_recursive (advertized_transform, t_item * t_ancestors, is_pattern); } } } @@ -1392,20 +1417,18 @@ void SPItem::adjust_paint_recursive (Geom::Affine advertized_transform, Geom::Af void SPItem::adjust_livepatheffect (Geom::Affine const &postmul, bool set) { - if ( SP_IS_LPE_ITEM(this) ) { - SPLPEItem *lpeitem = SP_LPE_ITEM (this); - if ( lpeitem->hasPathEffect() ) { - lpeitem->forkPathEffectsIfNecessary(); - - // now that all LPEs are forked_if_necessary, we can apply the transform - PathEffectList effect_list = lpeitem->getEffectList(); - for (PathEffectList::iterator it = effect_list.begin(); it != effect_list.end(); ++it) - { - LivePathEffectObject *lpeobj = (*it)->lpeobject; - if (lpeobj && lpeobj->get_lpe()) { - Inkscape::LivePathEffect::Effect * effect = lpeobj->get_lpe(); - effect->transform_multiply(postmul, set); - } + SPLPEItem *lpeitem = dynamic_cast<SPLPEItem *>(this); + if ( lpeitem && lpeitem->hasPathEffect() ) { + lpeitem->forkPathEffectsIfNecessary(); + + // now that all LPEs are forked_if_necessary, we can apply the transform + PathEffectList effect_list = lpeitem->getEffectList(); + for (PathEffectList::iterator it = effect_list.begin(); it != effect_list.end(); ++it) + { + LivePathEffectObject *lpeobj = (*it)->lpeobject; + if (lpeobj && lpeobj->get_lpe()) { + Inkscape::LivePathEffect::Effect * effect = lpeobj->get_lpe(); + effect->transform_multiply(postmul, set); } } } @@ -1480,7 +1503,7 @@ void SPItem::doWriteTransform(Inkscape::XML::Node *repr, Geom::Affine const &tra // onSetTransform cannot be pure due to the fact that not all visible Items are transformable. if ( // run the object's set_transform (i.e. embed transform) only if: - SP_IS_TEXT_TEXTPATH(this) || + (dynamic_cast<SPText *>(this) && firstChild() && dynamic_cast<SPTextPath *>(firstChild())) || (!preserve && // user did not chose to preserve all transforms (!clip_ref || !clip_ref->getObject()) && // the object does not have a clippath (!mask_ref || !mask_ref->getObject()) && // the object does not have a mask @@ -1551,11 +1574,14 @@ Geom::Affine i2anc_affine(SPObject const *object, SPObject const *const ancestor g_return_val_if_fail(object != NULL, ret); /* stop at first non-renderable ancestor */ - while ( object != ancestor && SP_IS_ITEM(object) ) { - if (SP_IS_ROOT(object)) { - ret *= SP_ROOT(object)->c2p; + while ( object != ancestor && dynamic_cast<SPItem const *>(object) ) { + SPRoot const *root = dynamic_cast<SPRoot const *>(object); + if (root) { + ret *= root->c2p; } else { - ret *= SP_ITEM(object)->transform; + SPItem const *item = dynamic_cast<SPItem const *>(object); + g_assert(item != NULL); + ret *= item->transform; } object = object->parent; } @@ -1619,7 +1645,7 @@ Geom::Affine SPItem::dt2i_affine() const SPItemView *SPItem::sp_item_view_new_prepend(SPItemView *list, SPItem *item, unsigned flags, unsigned key, Inkscape::DrawingItem *drawing_item) { g_assert(item != NULL); - g_assert(SP_IS_ITEM(item)); + g_assert(dynamic_cast<SPItem *>(item) != NULL); g_assert(drawing_item != NULL); SPItemView *new_view = g_new(SPItemView, 1); @@ -1677,8 +1703,9 @@ SPItem *sp_item_first_item_child(SPObject *obj) { SPItem *child = 0; for ( SPObject *iter = obj->firstChild() ; iter ; iter = iter->next ) { - if ( SP_IS_ITEM(iter) ) { - child = SP_ITEM(iter); + SPItem *tmp = dynamic_cast<SPItem *>(iter); + if ( tmp ) { + child = tmp; break; } } diff --git a/src/sp-use.cpp b/src/sp-use.cpp index e3fcd252a..2bd6757ff 100644 --- a/src/sp-use.cpp +++ b/src/sp-use.cpp @@ -50,10 +50,17 @@ namespace { } SPUse::SPUse() - : SPItem() - , child(NULL) - , href(NULL) - , ref(new SPUseReference(this)) + : SPItem(), + child(NULL), + x(), + y(), + width(), + height(), + href(NULL), + ref(new SPUseReference(this)), + _delete_connection(), + _changed_connection(), + _transformed_connection() { this->x.unset(); this->y.unset(); @@ -179,14 +186,23 @@ Inkscape::XML::Node* SPUse::write(Inkscape::XML::Document *xml_doc, Inkscape::XM g_free(uri_string); } - if (SP_IS_SHAPE(this->child)) { - SP_SHAPE(this->child)->set_shape(); // evaluate SPCurve of child - } else if (SP_IS_TEXT(this->child)) { - SP_TEXT(this->child)->rebuildLayout(); // refresh Layout, LP Bug 1339305 - } else if (SP_IS_FLOWTEXT(this->child)) { - if (SP_IS_FLOWREGION(SP_FLOWTEXT(this->child)->firstChild())) - SP_FLOWREGION(SP_FLOWTEXT(this->child)->firstChild())->UpdateComputed(); - SP_FLOWTEXT(this->child)->rebuildLayout(); + SPShape *shape = dynamic_cast<SPShape *>(child); + if (shape) { + shape->set_shape(); // evaluate SPCurve of child + } else { + SPText *text = dynamic_cast<SPText *>(child); + if (text) { + text->rebuildLayout(); // refresh Layout, LP Bug 1339305 + } else { + SPFlowtext *flowtext = dynamic_cast<SPFlowtext *>(child); + if (flowtext) { + SPFlowregion *flowregion = dynamic_cast<SPFlowregion *>(flowtext->firstChild()); + if (flowregion) { + flowregion->UpdateComputed(); + } + flowtext->rebuildLayout(); + } + } } return repr; @@ -223,18 +239,18 @@ void SPUse::print(SPPrintContext* ctx) { } const char* SPUse::displayName() const { - if (this->child && SP_IS_SYMBOL( this->child )) { + if (dynamic_cast<SPSymbol *>(child)) { return _("Symbol"); + } else { + return _("Clone"); } - - return _("Clone"); } gchar* SPUse::description() const { - if (this->child) { - if( SP_IS_SYMBOL( this->child ) ) { - if (this->child->title()) { - return g_strdup_printf(_("called %s"), Glib::Markup::escape_text(Glib::ustring( g_dpgettext2(NULL, "Symbol", this->child->title()))).c_str()); + if (child) { + if ( dynamic_cast<SPSymbol *>(child) ) { + if (child->title()) { + return g_strdup_printf(_("called %s"), Glib::Markup::escape_text(Glib::ustring( g_dpgettext2(NULL, "Symbol", child->title()))).c_str()); } else { return g_strdup_printf(_("called %s"), _("Unnamed Symbol")); } @@ -302,12 +318,10 @@ void SPUse::hide(unsigned int key) { SPItem *SPUse::root() { SPItem *orig = this->child; - while (orig && SP_IS_USE(orig)) { - orig = SP_USE(orig)->child; - } - - if (!orig) { - return NULL; + SPUse *use = dynamic_cast<SPUse *>(orig); + while (orig && use) { + orig = use->child; + use = dynamic_cast<SPUse *>(orig); } return orig; @@ -325,13 +339,16 @@ int SPUse::cloneDepth() const { unsigned depth = 1; SPItem *orig = this->child; - while (orig && SP_IS_USE(orig)) { + while (orig && dynamic_cast<SPUse *>(orig)) { ++depth; - orig = SP_USE(orig)->child; + orig = dynamic_cast<SPUse *>(orig)->child; } - if (!orig) return -1; - return depth; + if (!orig) { + return -1; + } else { + return depth; + } } /** @@ -345,9 +362,9 @@ Geom::Affine SPUse::get_root_transform() { GSList *chain = NULL; chain = g_slist_prepend(chain, this); - while (SP_IS_USE(orig)) { + while (dynamic_cast<SPUse *>(orig)) { chain = g_slist_prepend(chain, orig); - orig = SP_USE(orig)->child; + orig = dynamic_cast<SPUse *>(orig)->child; } chain = g_slist_prepend(chain, orig); @@ -357,14 +374,13 @@ Geom::Affine SPUse::get_root_transform() { Geom::Affine t(Geom::identity()); for (GSList *i = chain; i != NULL; i = i->next) { - SPItem *i_tem = SP_ITEM(i->data); + SPItem *i_tem = reinterpret_cast<SPItem *>(i->data); // "An additional transformation translate(x,y) is appended to the end (i.e., // right-side) of the transform attribute on the generated 'g', where x and y // represent the values of the x and y attributes on the 'use' element." - http://www.w3.org/TR/SVG11/struct.html#UseElement - if (SP_IS_USE(i_tem)) { - SPUse *i_use = SP_USE(i_tem); - + SPUse *i_use = dynamic_cast<SPUse *>(i_tem); + if (i_use) { if ((i_use->x._set && i_use->x.computed != 0) || (i_use->y._set && i_use->y.computed != 0)) { t = t * Geom::Translate(i_use->x._set ? i_use->x.computed : 0, i_use->y._set ? i_use->y.computed : 0); } @@ -405,7 +421,7 @@ void SPUse::move_compensate(Geom::Affine const *mp) { } // never compensate uses which are used in flowtext - if (this->parent && SP_IS_FLOWREGION(this->parent)) { + if (parent && dynamic_cast<SPFlowregion *>(parent)) { return; } @@ -462,8 +478,9 @@ void SPUse::href_changed() { SPObject* obj = SPFactory::instance().createObject(NodeTraits::get_type_string(*childrepr)); - if (SP_IS_ITEM(obj)) { - this->child = SP_ITEM(obj); + SPItem *item = dynamic_cast<SPItem *>(obj); + if (item) { + child = item; this->attach(this->child, this->lastChild()); sp_object_unref(this->child, this); @@ -495,8 +512,8 @@ void SPUse::href_changed() { void SPUse::delete_self() { // always delete uses which are used in flowtext - if (this->parent && SP_IS_FLOWREGION(this->parent)) { - this->deleteObject(); + if (parent && dynamic_cast<SPFlowregion *>(parent)) { + deleteObject(); return; } @@ -547,9 +564,10 @@ void SPUse::update(SPCtx *ctx, unsigned flags) { sp_object_ref(this->child); if (childflags || (this->child->uflags & (SP_OBJECT_MODIFIED_FLAG | SP_OBJECT_CHILD_MODIFIED_FLAG))) { - SPItem const &chi = *SP_ITEM(this->child); - cctx.i2doc = chi.transform * ictx->i2doc; - cctx.i2vp = chi.transform * ictx->i2vp; + SPItem const *chi = dynamic_cast<SPItem const *>(child); + g_assert(chi != NULL); + cctx.i2doc = chi->transform * ictx->i2doc; + cctx.i2vp = chi->transform * ictx->i2vp; this->child->updateDisplay((SPCtx *)&cctx, childflags); } @@ -621,7 +639,7 @@ SPItem *SPUse::unlink() { Inkscape::XML::Node *copy = NULL; - if (SP_IS_SYMBOL(orig)) { // make a group, copy children + if (dynamic_cast<SPSymbol *>(orig)) { // make a group, copy children copy = xml_doc->createElement("svg:g"); for (Inkscape::XML::Node *child = orig->getRepr()->firstChild() ; child != NULL; child = child->next()) { @@ -669,7 +687,8 @@ SPItem *SPUse::unlink() { this->setSuccessor(unlinked); sp_object_unref(this, NULL); - SPItem *item = SP_ITEM(unlinked); + SPItem *item = dynamic_cast<SPItem *>(unlinked); + g_assert(item != NULL); // Set the accummulated transform. { diff --git a/src/sp-use.h b/src/sp-use.h index 97385b986..81e4391aa 100644 --- a/src/sp-use.h +++ b/src/sp-use.h @@ -6,7 +6,9 @@ * * Authors: * Lauris Kaplinski <lauris@kaplinski.com> + * Jon A. Cruz <jon@joncruz.org> * + * Copyright (C) 1999-2014 Authors * Copyright (C) 1999-2002 Lauris Kaplinski * Copyright (C) 2000-2001 Ximian, Inc. * @@ -20,9 +22,6 @@ #include "sp-item.h" #include "enums.h" -#define SP_USE(obj) (dynamic_cast<SPUse*>((SPObject*)obj)) -#define SP_IS_USE(obj) (dynamic_cast<const SPUse*>((SPObject*)obj) != NULL) - class SPUseReference; class SPUse : public SPItem { diff --git a/src/ui/dialog/clonetiler.cpp b/src/ui/dialog/clonetiler.cpp index 5ef885ab2..d1a675735 100644 --- a/src/ui/dialog/clonetiler.cpp +++ b/src/ui/dialog/clonetiler.cpp @@ -1,5 +1,6 @@ -/** @file +/** + * @file * Clone tiling dialog */ /* Authors: @@ -2002,7 +2003,7 @@ bool CloneTiler::clonetiler_is_a_clone_of(SPObject *tile, SPObject *obj) id_href = g_strdup_printf("#%s", obj_repr->attribute("id")); } - if (SP_IS_USE(tile) && + if (dynamic_cast<SPUse *>(tile) && tile->getRepr()->attribute("xlink:href") && (!id_href || !strcmp(id_href, tile->getRepr()->attribute("xlink:href"))) && tile->getRepr()->attribute("inkscape:tiled-clone-of") && @@ -2025,8 +2026,10 @@ void CloneTiler::clonetiler_trace_hide_tiled_clones_recursively(SPObject *from) return; for (SPObject *o = from->firstChild(); o != NULL; o = o->next) { - if (SP_IS_ITEM(o) && clonetiler_is_a_clone_of (o, NULL)) - SP_ITEM(o)->invoke_hide(trace_visionkey); // FIXME: hide each tiled clone's original too! + SPItem *item = dynamic_cast<SPItem *>(o); + if (item && clonetiler_is_a_clone_of(o, NULL)) { + item->invoke_hide(trace_visionkey); // FIXME: hide each tiled clone's original too! + } clonetiler_trace_hide_tiled_clones_recursively (o); } } @@ -2160,7 +2163,9 @@ void CloneTiler::clonetiler_remove(GtkWidget */*widget*/, GtkWidget *dlg, bool d } } for (GSList *i = to_delete; i; i = i->next) { - SP_OBJECT(i->data)->deleteObject(); + SPObject *obj = reinterpret_cast<SPObject *>(i->data); + g_assert(obj != NULL); + obj->deleteObject(); } g_slist_free (to_delete); @@ -2330,7 +2335,7 @@ void CloneTiler::clonetiler_apply(GtkWidget */*widget*/, GtkWidget *dlg) bool invert_picked = prefs->getBool(prefs_path + "invert_picked"); double gamma_picked = prefs->getDoubleLimited(prefs_path + "gamma_picked", 0, -10, 10); - SPItem *item = SP_IS_ITEM(obj) ? SP_ITEM(obj) : 0; + SPItem *item = dynamic_cast<SPItem *>(obj); if (dotrace) { clonetiler_trace_setup (sp_desktop_document(desktop), 1.0, item); } @@ -2621,9 +2626,10 @@ void CloneTiler::clonetiler_apply(GtkWidget */*widget*/, GtkWidget *dlg) if (center_set) { SPObject *clone_object = sp_desktop_document(desktop)->getObjectByRepr(clone); - if (clone_object && SP_IS_ITEM(clone_object)) { + SPItem *item = dynamic_cast<SPItem *>(clone_object); + if (clone_object && item) { clone_object->requestDisplayUpdate(SP_OBJECT_MODIFIED_FLAG); - SP_ITEM(clone_object)->setCenter(desktop->doc2dt(new_center)); + item->setCenter(desktop->doc2dt(new_center)); clone_object->updateRepr(); } } diff --git a/src/ui/dialog/find.cpp b/src/ui/dialog/find.cpp index 1a4823e4a..1a7832688 100644 --- a/src/ui/dialog/find.cpp +++ b/src/ui/dialog/find.cpp @@ -241,7 +241,7 @@ Find::Find() Inkscape::Selection *selection = sp_desktop_selection (SP_ACTIVE_DESKTOP); SPItem *item = selection->singleItem(); if (item) { - if (SP_IS_TEXT(item) || SP_IS_FLOWTEXT(item)) { + if (dynamic_cast<SPText *>(item) || dynamic_cast<SPFlowtext *>(item)) { gchar *str; str = sp_te_get_string_multiline (item); entry_find.getEntry()->set_text(str); @@ -343,7 +343,7 @@ bool Find::item_text_match (SPItem *item, const gchar *find, bool exact, bool ca return false; } - if (SP_IS_TEXT(item) || SP_IS_FLOWTEXT(item)) { + if (dynamic_cast<SPText *>(item) || dynamic_cast<SPFlowtext *>(item)) { const gchar *item_text = sp_te_get_string_multiline (item); if (item_text == NULL) { return false; @@ -388,7 +388,7 @@ bool Find::item_id_match (SPItem *item, const gchar *id, bool exact, bool casema return false; } - if (SP_IS_STRING(item)) { // SPStrings have "on demand" ids which are useless for searching + if (dynamic_cast<SPString *>(item)) { // SPStrings have "on demand" ids which are useless for searching return false; } @@ -561,11 +561,14 @@ GSList *Find::filter_fields (GSList *l, bool exact, bool casematch) if (check_searchin_text.get_active()) { for (GSList *i = in; i != NULL; i = i->next) { - if (item_text_match (SP_ITEM(i->data), text, exact, casematch)) { + SPObject *obj = reinterpret_cast<SPObject *>(i->data); + SPItem *item = dynamic_cast<SPItem *>(obj); + g_assert(item != NULL); + if (item_text_match(item, text, exact, casematch)) { if (!g_slist_find(out, i->data)) { out = g_slist_prepend (out, i->data); if (_action_replace) { - item_text_match (SP_ITEM(i->data), text, exact, casematch, _action_replace); + item_text_match(item, text, exact, casematch, _action_replace); } } } @@ -581,11 +584,13 @@ GSList *Find::filter_fields (GSList *l, bool exact, bool casematch) if (ids) { for (GSList *i = in; i != NULL; i = i->next) { - if (item_id_match (SP_ITEM(i->data), text, exact, casematch)) { + SPObject *obj = reinterpret_cast<SPObject *>(i->data); + SPItem *item = dynamic_cast<SPItem *>(obj); + if (item_id_match(item, text, exact, casematch)) { if (!g_slist_find(out, i->data)) { out = g_slist_prepend (out, i->data); if (_action_replace) { - item_id_match (SP_ITEM(i->data), text, exact, casematch, _action_replace); + item_id_match(item, text, exact, casematch, _action_replace); } } } @@ -595,12 +600,15 @@ GSList *Find::filter_fields (GSList *l, bool exact, bool casematch) if (style) { for (GSList *i = in; i != NULL; i = i->next) { - if (item_style_match (SP_ITEM(i->data), text, exact, casematch)) { + SPObject *obj = reinterpret_cast<SPObject *>(i->data); + SPItem *item = dynamic_cast<SPItem *>(obj); + g_assert(item != NULL); + if (item_style_match(item, text, exact, casematch)) { if (!g_slist_find(out, i->data)) if (!g_slist_find(out, i->data)) { out = g_slist_prepend (out, i->data); if (_action_replace) { - item_style_match (SP_ITEM(i->data), text, exact, casematch, _action_replace); + item_style_match(item, text, exact, casematch, _action_replace); } } } @@ -610,11 +618,14 @@ GSList *Find::filter_fields (GSList *l, bool exact, bool casematch) if (attrname) { for (GSList *i = in; i != NULL; i = i->next) { - if (item_attr_match (SP_ITEM(i->data), text, exact, casematch)) { + SPObject *obj = reinterpret_cast<SPObject *>(i->data); + SPItem *item = dynamic_cast<SPItem *>(obj); + g_assert(item != NULL); + if (item_attr_match(item, text, exact, casematch)) { if (!g_slist_find(out, i->data)) { out = g_slist_prepend (out, i->data); if (_action_replace) { - item_attr_match (SP_ITEM(i->data), text, exact, casematch, _action_replace); + item_attr_match(item, text, exact, casematch, _action_replace); } } } @@ -624,11 +635,14 @@ GSList *Find::filter_fields (GSList *l, bool exact, bool casematch) if (attrvalue) { for (GSList *i = in; i != NULL; i = i->next) { - if (item_attrvalue_match (SP_ITEM(i->data), text, exact, casematch)) { + SPObject *obj = reinterpret_cast<SPObject *>(i->data); + SPItem *item = dynamic_cast<SPItem *>(obj); + g_assert(item != NULL); + if (item_attrvalue_match(item, text, exact, casematch)) { if (!g_slist_find(out, i->data)) { out = g_slist_prepend (out, i->data); if (_action_replace) { - item_attrvalue_match (SP_ITEM(i->data), text, exact, casematch, _action_replace); + item_attrvalue_match(item, text, exact, casematch, _action_replace); } } } @@ -638,11 +652,14 @@ GSList *Find::filter_fields (GSList *l, bool exact, bool casematch) if (font) { for (GSList *i = in; i != NULL; i = i->next) { - if (item_font_match (SP_ITEM(i->data), text, exact, casematch)) { + SPObject *obj = reinterpret_cast<SPObject *>(i->data); + SPItem *item = dynamic_cast<SPItem *>(obj); + g_assert(item != NULL); + if (item_font_match(item, text, exact, casematch)) { if (!g_slist_find(out, i->data)) { out = g_slist_prepend (out, i->data); if (_action_replace) { - item_font_match (SP_ITEM(i->data), text, exact, casematch, _action_replace); + item_font_match(item, text, exact, casematch, _action_replace); } } } @@ -661,34 +678,34 @@ bool Find::item_type_match (SPItem *item) { bool all =check_alltypes.get_active(); - if ( SP_IS_RECT(item)) { + if ( dynamic_cast<SPRect *>(item)) { return ( all ||check_rects.get_active()); - } else if (SP_IS_GENERICELLIPSE(item)) { + } else if (dynamic_cast<SPGenericEllipse *>(item)) { return ( all || check_ellipses.get_active()); - } else if (SP_IS_STAR(item) || SP_IS_POLYGON(item)) { + } else if (dynamic_cast<SPStar *>(item) || dynamic_cast<SPPolygon *>(item)) { return ( all || check_stars.get_active()); - } else if (SP_IS_SPIRAL(item)) { + } else if (dynamic_cast<SPSpiral *>(item)) { return ( all || check_spirals.get_active()); - } else if (SP_IS_PATH(item) || SP_IS_LINE(item) || SP_IS_POLYLINE(item)) { + } else if (dynamic_cast<SPPath *>(item) || dynamic_cast<SPLine *>(item) || dynamic_cast<SPPolyLine *>(item)) { return (all || check_paths.get_active()); - } else if (SP_IS_TEXT(item) || SP_IS_TSPAN(item) || SP_IS_TREF(item) || SP_IS_STRING(item)) { + } else if (dynamic_cast<SPText *>(item) || dynamic_cast<SPTSpan *>(item) || dynamic_cast<SPTRef *>(item) || dynamic_cast<SPString *>(item)) { return (all || check_texts.get_active()); - } else if (SP_IS_GROUP(item) && !desktop->isLayer(item) ) { // never select layers! + } else if (dynamic_cast<SPGroup *>(item) && !desktop->isLayer(item) ) { // never select layers! return (all || check_groups.get_active()); - } else if (SP_IS_USE(item)) { + } else if (dynamic_cast<SPUse *>(item)) { return (all || check_clones.get_active()); - } else if (SP_IS_IMAGE(item)) { + } else if (dynamic_cast<SPImage *>(item)) { return (all || check_images.get_active()); - } else if (SP_IS_OFFSET(item)) { + } else if (dynamic_cast<SPOffset *>(item)) { return (all || check_offsets.get_active()); } @@ -699,7 +716,10 @@ GSList *Find::filter_types (GSList *l) { GSList *n = NULL; for (GSList *i = l; i != NULL; i = i->next) { - if (item_type_match (SP_ITEM(i->data))) { + SPObject *obj = reinterpret_cast<SPObject *>(i->data); + SPItem *item = dynamic_cast<SPItem *>(obj); + g_assert(item != NULL); + if (item_type_match(item)) { n = g_slist_prepend (n, i->data); } } @@ -716,7 +736,7 @@ GSList *Find::filter_list (GSList *l, bool exact, bool casematch) GSList *Find::all_items (SPObject *r, GSList *l, bool hidden, bool locked) { - if (SP_IS_DEFS(r)) { + if (dynamic_cast<SPDefs *>(r)) { return l; // we're not interested in items in defs } @@ -725,8 +745,8 @@ GSList *Find::all_items (SPObject *r, GSList *l, bool hidden, bool locked) } for (SPObject *child = r->firstChild(); child; child = child->getNext()) { - if (SP_IS_ITEM(child) && !child->cloned && !desktop->isLayer(SP_ITEM(child))) { - SPItem *item = reinterpret_cast<SPItem *>(child); + SPItem *item = dynamic_cast<SPItem *>(child); + if (item && !child->cloned && !desktop->isLayer(item)) { if ((hidden || !desktop->itemIsHidden(item)) && (locked || !item->isLocked())) { l = g_slist_prepend (l, child); } @@ -739,16 +759,18 @@ GSList *Find::all_items (SPObject *r, GSList *l, bool hidden, bool locked) GSList *Find::all_selection_items (Inkscape::Selection *s, GSList *l, SPObject *ancestor, bool hidden, bool locked) { for (GSList *i = (GSList *) s->itemList(); i != NULL; i = i->next) { - if (SP_IS_ITEM (i->data) && !reinterpret_cast<SPItem *>(i->data)->cloned && !desktop->isLayer(SP_ITEM(i->data))) { - SPItem *item = reinterpret_cast<SPItem *>(i->data); + SPObject *obj = reinterpret_cast<SPObject *>(i->data); + SPItem *item = dynamic_cast<SPItem *>(obj); + g_assert(item != NULL); + if (item && !item->cloned && !desktop->isLayer(item)) { if (!ancestor || ancestor->isAncestorOf(item)) { if ((hidden || !desktop->itemIsHidden(item)) && (locked || !item->isLocked())) { l = g_slist_prepend (l, i->data); } } } - if (!ancestor || ancestor->isAncestorOf(SP_OBJECT (i->data))) { - l = all_items (SP_OBJECT (i->data), l, hidden, locked); + if (!ancestor || ancestor->isAncestorOf(item)) { + l = all_items(item, l, hidden, locked); } } return l; @@ -831,7 +853,10 @@ void Find::onAction() Inkscape::Selection *selection = sp_desktop_selection (desktop); selection->clear(); selection->setList(n); - scroll_to_show_item (desktop, SP_ITEM(n->data)); + SPObject *obj = reinterpret_cast<SPObject *>(n->data); + SPItem *item = dynamic_cast<SPItem *>(obj); + g_assert(item != NULL); + scroll_to_show_item(desktop, item); if (_action_replace) { DocumentUndo::done(sp_desktop_document(desktop), SP_VERB_CONTEXT_TEXT, _("Replace text or property")); diff --git a/src/ui/dialog/livepatheffect-editor.cpp b/src/ui/dialog/livepatheffect-editor.cpp index 9a569725c..eb3857ee7 100644 --- a/src/ui/dialog/livepatheffect-editor.cpp +++ b/src/ui/dialog/livepatheffect-editor.cpp @@ -295,9 +295,8 @@ LivePathEffectEditor::onSelectionChanged(Inkscape::Selection *sel) if ( sel && !sel->isEmpty() ) { SPItem *item = sel->singleItem(); if ( item ) { - if ( SP_IS_LPE_ITEM(item) ) { - SPLPEItem *lpeitem = SP_LPE_ITEM(item); - + SPLPEItem *lpeitem = dynamic_cast<SPLPEItem *>(item); + if ( lpeitem ) { effect_list_reload(lpeitem); current_lpeitem = lpeitem; @@ -318,25 +317,28 @@ LivePathEffectEditor::onSelectionChanged(Inkscape::Selection *sel) button_up.set_sensitive(false); button_down.set_sensitive(false); } - } else if ( SP_IS_USE(item) ) { - // test whether linked object is supported by the CLONE_ORIGINAL LPE - SPItem *orig = SP_USE(item)->get_original(); - if ( SP_IS_SHAPE(orig) || - SP_IS_TEXT(orig) ) - { - // Note that an SP_USE cannot have an LPE applied, so we only need to worry about the "add effect" case. - set_sensitize_all(true); - showText(_("Click add button to convert clone")); - button_remove.set_sensitive(false); - button_up.set_sensitive(false); - button_down.set_sensitive(false); + } else { + SPUse *use = dynamic_cast<SPUse *>(item); + if ( use ) { + // test whether linked object is supported by the CLONE_ORIGINAL LPE + SPItem *orig = use->get_original(); + if ( dynamic_cast<SPShape *>(orig) || + dynamic_cast<SPText *>(orig) ) + { + // Note that an SP_USE cannot have an LPE applied, so we only need to worry about the "add effect" case. + set_sensitize_all(true); + showText(_("Click add button to convert clone")); + button_remove.set_sensitive(false); + button_up.set_sensitive(false); + button_down.set_sensitive(false); + } else { + showText(_("Select a path or shape")); + set_sensitize_all(false); + } } else { showText(_("Select a path or shape")); set_sensitize_all(false); } - } else { - showText(_("Select a path or shape")); - set_sensitize_all(false); } } else { showText(_("Only one item can be selected")); @@ -423,7 +425,7 @@ LivePathEffectEditor::onAdd() if ( sel && !sel->isEmpty() ) { SPItem *item = sel->singleItem(); if (item) { - if ( SP_IS_LPE_ITEM(item) ) { + if ( dynamic_cast<SPLPEItem *>(item) ) { // show effectlist dialog using Inkscape::UI::Dialog::LivePathEffectAdd; LivePathEffectAdd::show(current_desktop); @@ -439,7 +441,7 @@ LivePathEffectEditor::onAdd() } // If item is a SPRect, convert it to path first: - if ( SP_IS_RECT(item) ) { + if ( dynamic_cast<SPRect *>(item) ) { sp_selected_path_to_curves(sel, current_desktop, false); item = sel->singleItem(); // get new item } @@ -451,41 +453,43 @@ LivePathEffectEditor::onAdd() lpe_list_locked = false; onSelectionChanged(sel); - } - else if ( SP_IS_USE(item) ) { - // item is a clone. do not show effectlist dialog. - // convert to path, apply CLONE_ORIGINAL LPE, link it to the cloned path - - // test whether linked object is supported by the CLONE_ORIGINAL LPE - SPItem *orig = SP_USE(item)->get_original(); - if ( SP_IS_SHAPE(orig) || - SP_IS_TEXT(orig) ) - { - // select original - sel->set(orig); - - // delete clone but remember its id and transform - gchar *id = g_strdup(item->getRepr()->attribute("id")); - gchar *transform = g_strdup(item->getRepr()->attribute("transform")); - item->deleteObject(false); - item = NULL; - - // run sp_selection_clone_original_path_lpe - sp_selection_clone_original_path_lpe(current_desktop); - SPItem *new_item = sel->singleItem(); - new_item->getRepr()->setAttribute("id", id); - new_item->getRepr()->setAttribute("transform", transform); - g_free(id); - g_free(transform); - - /// \todo Add the LPE stack of the original path? - - SPDocument *doc = current_desktop->doc(); - DocumentUndo::done(doc, SP_VERB_DIALOG_LIVE_PATH_EFFECT, - _("Create and apply Clone original path effect")); - - lpe_list_locked = false; - onSelectionChanged(sel); + } else { + SPUse *use = dynamic_cast<SPUse *>(item); + if ( use ) { + // item is a clone. do not show effectlist dialog. + // convert to path, apply CLONE_ORIGINAL LPE, link it to the cloned path + + // test whether linked object is supported by the CLONE_ORIGINAL LPE + SPItem *orig = use->get_original(); + if ( dynamic_cast<SPShape *>(orig) || + dynamic_cast<SPText *>(orig) ) + { + // select original + sel->set(orig); + + // delete clone but remember its id and transform + gchar *id = g_strdup(item->getRepr()->attribute("id")); + gchar *transform = g_strdup(item->getRepr()->attribute("transform")); + item->deleteObject(false); + item = NULL; + + // run sp_selection_clone_original_path_lpe + sp_selection_clone_original_path_lpe(current_desktop); + SPItem *new_item = sel->singleItem(); + new_item->getRepr()->setAttribute("id", id); + new_item->getRepr()->setAttribute("transform", transform); + g_free(id); + g_free(transform); + + /// \todo Add the LPE stack of the original path? + + SPDocument *doc = current_desktop->doc(); + DocumentUndo::done(doc, SP_VERB_DIALOG_LIVE_PATH_EFFECT, + _("Create and apply Clone original path effect")); + + lpe_list_locked = false; + onSelectionChanged(sel); + } } } } @@ -498,13 +502,14 @@ LivePathEffectEditor::onRemove() Inkscape::Selection *sel = _getSelection(); if ( sel && !sel->isEmpty() ) { SPItem *item = sel->singleItem(); - if ( item && SP_IS_LPE_ITEM(item) ) { - SP_LPE_ITEM(item)->removeCurrentPathEffect(false); + SPLPEItem *lpeitem = dynamic_cast<SPLPEItem *>(item); + if ( lpeitem ) { + lpeitem->removeCurrentPathEffect(false); DocumentUndo::done( sp_desktop_document(current_desktop), SP_VERB_DIALOG_LIVE_PATH_EFFECT, _("Remove path effect") ); - effect_list_reload(SP_LPE_ITEM(item)); + effect_list_reload(lpeitem); } } @@ -515,7 +520,8 @@ void LivePathEffectEditor::onUp() Inkscape::Selection *sel = _getSelection(); if ( sel && !sel->isEmpty() ) { SPItem *item = sel->singleItem(); - if ( SPLPEItem *lpeitem = SP_LPE_ITEM(item) ) { + SPLPEItem *lpeitem = dynamic_cast<SPLPEItem *>(item); + if ( lpeitem ) { lpeitem->upCurrentPathEffect(); DocumentUndo::done( sp_desktop_document(current_desktop), SP_VERB_DIALOG_LIVE_PATH_EFFECT, @@ -531,7 +537,8 @@ void LivePathEffectEditor::onDown() Inkscape::Selection *sel = _getSelection(); if ( sel && !sel->isEmpty() ) { SPItem *item = sel->singleItem(); - if ( SPLPEItem *lpeitem = SP_LPE_ITEM(item) ) { + SPLPEItem *lpeitem = dynamic_cast<SPLPEItem *>(item); + if ( lpeitem ) { lpeitem->downCurrentPathEffect(); DocumentUndo::done( sp_desktop_document(current_desktop), SP_VERB_DIALOG_LIVE_PATH_EFFECT, diff --git a/src/ui/dialog/symbols.cpp b/src/ui/dialog/symbols.cpp index a9cf8d068..a17a03861 100644 --- a/src/ui/dialog/symbols.cpp +++ b/src/ui/dialog/symbols.cpp @@ -298,8 +298,7 @@ SymbolsDialog::SymbolsDialog( gchar const* prefsPath ) : // This might need to be a global variable so setTargetDesktop can modify it SPDefs *defs = currentDocument->getDefs(); - sigc::connection defsModifiedConn = (SP_OBJECT(defs))->connectModified( - sigc::mem_fun(*this, &SymbolsDialog::defsModified)); + sigc::connection defsModifiedConn = defs->connectModified(sigc::mem_fun(*this, &SymbolsDialog::defsModified)); instanceConns.push_back(defsModifiedConn); sigc::connection selectionChangedConn = currentDesktop->selection->connectChanged( @@ -658,11 +657,11 @@ GSList* SymbolsDialog::symbols_in_doc_recursive (SPObject *r, GSList *l) g_return_val_if_fail(r != NULL, l); // Stop multiple counting of same symbol - if( SP_IS_USE(r) ) { + if ( dynamic_cast<SPUse *>(r) ) { return l; } - if( SP_IS_SYMBOL(r) ) { + if ( dynamic_cast<SPSymbol *>(r) ) { l = g_slist_prepend (l, r); } @@ -684,7 +683,7 @@ GSList* SymbolsDialog::symbols_in_doc( SPDocument* symbolDocument ) { GSList* SymbolsDialog::use_in_doc_recursive (SPObject *r, GSList *l) { - if( SP_IS_USE(r) ) { + if ( dynamic_cast<SPUse *>(r) ) { l = g_slist_prepend (l, r); } @@ -709,8 +708,9 @@ gchar const* SymbolsDialog::style_from_use( gchar const* id, SPDocument* documen gchar const* style = 0; GSList* l = use_in_doc( document ); for( ; l != NULL; l = l->next ) { - SPObject* use = SP_OBJECT(l->data); - if( SP_IS_USE( use ) ) { + SPObject *obj = reinterpret_cast<SPObject *>(l->data); + SPUse *use = dynamic_cast<SPUse *>(obj); + if ( use ) { gchar const *href = use->getRepr()->attribute("xlink:href"); if( href ) { Glib::ustring href2(href); @@ -730,8 +730,9 @@ void SymbolsDialog::add_symbols( SPDocument* symbolDocument ) { GSList* l = symbols_in_doc( symbolDocument ); for( ; l != NULL; l = l->next ) { - SPObject* symbol = SP_OBJECT(l->data); - if (SP_IS_SYMBOL(symbol)) { + SPObject *obj = reinterpret_cast<SPObject *>(l->data); + SPSymbol *symbol = dynamic_cast<SPSymbol *>(obj); + if (symbol) { add_symbol( symbol ); } } @@ -820,7 +821,8 @@ SymbolsDialog::draw_symbol(SPObject *symbol) previewDocument->getRoot()->requestDisplayUpdate(SP_OBJECT_MODIFIED_FLAG); previewDocument->ensureUpToDate(); - SPItem *item = SP_ITEM(object_temp); + SPItem *item = dynamic_cast<SPItem *>(object_temp); + g_assert(item != NULL); unsigned psize = SYMBOL_ICON_SIZES[pack_size]; Glib::RefPtr<Gdk::Pixbuf> pixbuf(NULL); |
