Code

Eliminate remaining sources of empty NR::Rects
authormental <mental@users.sourceforge.net>
Sun, 11 Mar 2007 21:23:04 +0000 (21:23 +0000)
committermental <mental@users.sourceforge.net>
Sun, 11 Mar 2007 21:23:04 +0000 (21:23 +0000)
13 files changed:
src/display/sp-canvas.cpp
src/libnr/nr-convex-hull.h
src/libnrtype/FontInstance.cpp
src/libnrtype/Layout-TNG-OutIter.cpp
src/libnrtype/Layout-TNG-Output.cpp
src/libnrtype/Layout-TNG.h
src/libnrtype/RasterFont.cpp
src/libnrtype/font-instance.h
src/selection.cpp
src/sp-conn-end.cpp
src/ui/dialog/align-and-distribute.cpp
src/ui/dialog/align-and-distribute.h
src/widgets/font-selector.cpp

index 75ffeed846cb82c530a7133d855be596c36e8e0d..559515e037773df3ad107cae6b2996a378f40b38 100644 (file)
@@ -744,11 +744,16 @@ sp_canvas_group_update (SPCanvasItem *item, NR::Matrix const &affine, unsigned i
         }
     }
 
-    NR::Rect const &bounds = corners.bounds();
-    item->x1 = bounds.min()[NR::X];
-    item->y1 = bounds.min()[NR::Y];
-    item->x2 = bounds.max()[NR::X];
-    item->y2 = bounds.max()[NR::Y];
+    NR::Maybe<NR::Rect> const bounds = corners.bounds();
+    if (bounds) {
+        item->x1 = bounds->min()[NR::X];
+        item->y1 = bounds->min()[NR::Y];
+        item->x2 = bounds->max()[NR::X];
+        item->y2 = bounds->max()[NR::Y];
+    } else {
+        item->x1 = item->x2 = corners.midpoint()[NR::X];
+        item->y1 = item->y2 = corners.midpoint()[NR::Y];
+    }
 }
 
 /**
index 28cde376d7339dcd63cebc7e9c451f2756239b69..fef885f005ac862afc3c72672804667b7a80183d 100644 (file)
@@ -17,31 +17,49 @@ namespace NR {
 
 class ConvexHull {
 public:
-       explicit ConvexHull(Point const &p) : _bounds(p, p) {}
+       explicit ConvexHull(Point const &p)
+    : _initial(p) {}
 
     Point midpoint() const {
-        return _bounds.midpoint();
+        if (_bounds) {
+            return _bounds->midpoint();
+        } else {
+            return _initial;
+        }
     }
 
        void add(Point const &p) {
-               _bounds.expandTo(p);
+        if (_bounds) {
+                   _bounds->expandTo(p);
+        } else if ( p != _initial ) {
+            _bounds = Rect(_initial, p);
+        }
        }
        void add(Rect const &p) {
                // Note that this is a hack.  when convexhull actually works
                // you will need to add all four points.
-               _bounds.expandTo(p.min());
-               _bounds.expandTo(p.max());
+               if (_bounds) {
+            _bounds = union_bounds(*_bounds, p);
+        } else {
+            _bounds = p;
+            _bounds->expandTo(_initial);
+        }
        }
        void add(ConvexHull const &h) {
-               _bounds.expandTo(h._bounds);
+        if (h._bounds) {
+            add(*h._bounds);
+        } else {
+            add(h._initial);
+        }
        }
-               
-       Rect const &bounds() const {
+
+       Maybe<Rect> const &bounds() const {
                return _bounds;
        }
        
 private:
-       Rect _bounds;
+    Point _initial;
+       Maybe<Rect> _bounds;
 };
 
 } /* namespace NR */
index 574a76f628c9f236c7fe0206799207b2988144c3..419a631a571e205cbe1838370350fbdefbda1d29 100644 (file)
@@ -611,7 +611,7 @@ bool font_instance::FontSlope(double &run, double &rise)
        return true;
 }
 
-NR::Rect font_instance::BBox(int glyph_id)
+NR::Maybe<NR::Rect> font_instance::BBox(int glyph_id)
 {
        int no=-1;
        if ( id_to_no.find(glyph_id) == id_to_no.end() ) {
@@ -624,11 +624,13 @@ NR::Rect font_instance::BBox(int glyph_id)
        } else {
                no=id_to_no[glyph_id];
        }
-       if ( no < 0 ) return NR::Rect(NR::Point(0,0),NR::Point(0,0));
-       NR::Point rmin(glyphs[no].bbox[0],glyphs[no].bbox[1]);
-       NR::Point rmax(glyphs[no].bbox[2],glyphs[no].bbox[3]);
-       NR::Rect  res(rmin,rmax);
-       return res;
+       if ( no < 0 ) {
+            return NR::Nothing();
+        } else {
+           NR::Point rmin(glyphs[no].bbox[0],glyphs[no].bbox[1]);
+           NR::Point rmax(glyphs[no].bbox[2],glyphs[no].bbox[3]);
+           return NR::Rect(rmin, rmax);
+        }
 }
 
 Path* font_instance::Outline(int glyph_id,Path* copyInto)
index 8c525084e99991131fad2f3ab71aab4fb4b9d88f..167352bd3d7c2e8d3bd33c49a9dff1b933058138 100755 (executable)
@@ -201,7 +201,7 @@ Layout::iterator Layout::sourceToIterator(void *source_cookie) const
     return sourceToIterator(source_cookie, Glib::ustring::const_iterator(std::string::const_iterator(NULL)));
 }
 
-NR::Rect Layout::glyphBoundingBox(iterator const &it, double *rotation) const
+NR::Maybe<NR::Rect> Layout::glyphBoundingBox(iterator const &it, double *rotation) const
 {
    if (rotation) *rotation = _glyphs[it._glyph_index].rotation;
    return _glyphs[it._glyph_index].span(this).font->BBox(_glyphs[it._glyph_index].glyph);
index 5152909f814ab3a8cb0c8c63c6a1afabd339e35d..68d7752c30af2c516fb178d5f342761ce5e92d96 100755 (executable)
@@ -113,20 +113,22 @@ void Layout::getBoundingBox(NRRect *bounding_box, NR::Matrix const &transform, i
         _getGlyphTransformMatrix(glyph_index, &glyph_matrix);
         NR::Matrix total_transform = glyph_matrix;
         total_transform *= transform;
-        NR::Rect glyph_rect = _glyphs[glyph_index].span(this).font->BBox(_glyphs[glyph_index].glyph);
-        NR::Point bmi = glyph_rect.min(), bma = glyph_rect.max();
-        NR::Point tlp(bmi[0],bmi[1]), trp(bma[0],bmi[1]), blp(bmi[0],bma[1]), brp(bma[0],bma[1]);
-        tlp *= total_transform;
-        trp *= total_transform;
-        blp *= total_transform;
-        brp *= total_transform;
-        glyph_rect = NR::Rect(tlp,trp);
-        glyph_rect.expandTo(blp);
-        glyph_rect.expandTo(brp);
-        if ( (glyph_rect.min())[0] < bounding_box->x0 ) bounding_box->x0=(glyph_rect.min())[0];
-        if ( (glyph_rect.max())[0] > bounding_box->x1 ) bounding_box->x1=(glyph_rect.max())[0];
-        if ( (glyph_rect.min())[1] < bounding_box->y0 ) bounding_box->y0=(glyph_rect.min())[1];
-        if ( (glyph_rect.max())[1] > bounding_box->y1 ) bounding_box->y1=(glyph_rect.max())[1];
+        NR::Maybe<NR::Rect> glyph_rect = _glyphs[glyph_index].span(this).font->BBox(_glyphs[glyph_index].glyph);
+        if (glyph_rect) {
+            NR::Point bmi = glyph_rect->min(), bma = glyph_rect->max();
+            NR::Point tlp(bmi[0],bmi[1]), trp(bma[0],bmi[1]), blp(bmi[0],bma[1]), brp(bma[0],bma[1]);
+            tlp *= total_transform;
+            trp *= total_transform;
+            blp *= total_transform;
+            brp *= total_transform;
+            *glyph_rect = NR::Rect(tlp,trp);
+            glyph_rect->expandTo(blp);
+            glyph_rect->expandTo(brp);
+            if ( (glyph_rect->min())[0] < bounding_box->x0 ) bounding_box->x0=(glyph_rect->min())[0];
+            if ( (glyph_rect->max())[0] > bounding_box->x1 ) bounding_box->x1=(glyph_rect->max())[0];
+            if ( (glyph_rect->min())[1] < bounding_box->y0 ) bounding_box->y0=(glyph_rect->min())[1];
+            if ( (glyph_rect->max())[1] > bounding_box->y1 ) bounding_box->y1=(glyph_rect->max())[1];
+        }
     }
 }
 
index 48b01eae5f14ff10e5a7a0c50b12ad639bdf34f4..3eed1fc43d2eb67aa728e19a9d2605c7dd888592 100755 (executable)
@@ -443,7 +443,7 @@ public:
     /** Returns the bounding box of the given glyph, and its rotation.
     The centre of rotation is the horizontal centre of the box at the
     text baseline. */
-    NR::Rect glyphBoundingBox(iterator const &it, double *rotation) const;
+    NR::Maybe<NR::Rect> glyphBoundingBox(iterator const &it, double *rotation) const;
 
     /** Returns the zero-based line number of the character pointed to by
     \a it. */
index 68ecb2e4d9e71fc9085051b7bb6f8577afe180a8..c9af6621f36f8d83be4438be543569d87ebb4186 100644 (file)
@@ -107,20 +107,24 @@ void           raster_font::BBox(int glyph_id,NRRect *area)
 {
        area->x0=area->y0=area->x1=area->y1=0;
        if ( daddy == NULL ) return;
-       NR::Rect  res=daddy->BBox(glyph_id);
-       NR::Point bmi=res.min(),bma=res.max();
-       NR::Point tlp(bmi[0],bmi[1]),trp(bma[0],bmi[1]),blp(bmi[0],bma[1]),brp(bma[0],bma[1]);
-       tlp=tlp*style.transform;
-       trp=trp*style.transform;
-       blp=blp*style.transform;
-       brp=brp*style.transform;
-       res=NR::Rect(tlp,trp);
-       res.expandTo(blp);
-       res.expandTo(brp);
-       area->x0=(res.min())[0];
-       area->y0=(res.min())[1];
-       area->x1=(res.max())[0];
-       area->y1=(res.max())[1];
+       NR::Maybe<NR::Rect> res=daddy->BBox(glyph_id);
+       if (res) {
+               NR::Point bmi=res->min(),bma=res->max();
+               NR::Point tlp(bmi[0],bmi[1]),trp(bma[0],bmi[1]),blp(bmi[0],bma[1]),brp(bma[0],bma[1]);
+               tlp=tlp*style.transform;
+               trp=trp*style.transform;
+               blp=blp*style.transform;
+               brp=brp*style.transform;
+               *res=NR::Rect(tlp,trp);
+               res->expandTo(blp);
+               res->expandTo(brp);
+               area->x0=(res->min())[0];
+               area->y0=(res->min())[1];
+               area->x1=(res->max())[0];
+               area->y1=(res->max())[1];
+       } else {
+               nr_rect_d_set_empty(area);
+       }
 }
 
 void           raster_font::LoadRasterGlyph(int glyph_id)
index ec58ce1d783abe8f88d3a333a4b9510e43ba56c3..4bec0203d21f1e03d214aad798c677e56e97dafe 100644 (file)
@@ -12,6 +12,7 @@
 #include <libnrtype/nrtype-forward.h>
 #include <libnrtype/font-style.h>
 #include <livarot/livarot-forward.h>
+#include "libnr/nr-rect.h"
 
 // the font_instance are the template of several raster_font; they provide metrics and outlines
 // that are drawn by the raster_font, so the raster_font needs info relative to the way the 
@@ -77,7 +78,7 @@ public:
     bool                 FontMetrics(double &ascent, double &descent, double &leading);
     bool                 FontSlope(double &run, double &rise);
                                 // for generating slanted cursors for oblique fonts
-    NR::Rect             BBox(int glyph_id);
+    NR::Maybe<NR::Rect>             BBox(int glyph_id);
 
                // creates a rasterfont for the given style
     raster_font*         RasterFont(NR::Matrix const &trs, double stroke_width,
index c6b307c3b0ddd0918411f374e2852f560e0988ed..201661eecc89345575aede6f4195c8ce66ef1efb 100644 (file)
@@ -380,24 +380,28 @@ std::vector<NR::Point> Selection::getSnapPoints() const {
 
 std::vector<NR::Point> Selection::getSnapPointsConvexHull() const {
     GSList const *items = const_cast<Selection *>(this)->itemList();
+
     std::vector<NR::Point> p;
     for (GSList const *iter = items; iter != NULL; iter = iter->next) {
        sp_item_snappoints(SP_ITEM(iter->data), SnapPointsIter(p));
     }
 
-    std::vector<NR::Point>::iterator i;
-    NR::ConvexHull cvh(*(p.begin()));
-    for (i = p.begin(); i != p.end(); i++) {
-       // these are the points we get back
-       cvh.add(*i);
-    }
+    std::vector<NR::Point> pHull;
+    if (!p.empty()) {
+        std::vector<NR::Point>::iterator i;
+        NR::ConvexHull cvh(p.front());
+        for (i = p.begin(); i != p.end(); i++) {
+            // these are the points we get back
+            cvh.add(*i);
+        }
 
-    NR::Rect rHull = cvh.bounds();
-    std::vector<NR::Point> pHull(4);
-    pHull[0] = rHull.corner(0);
-    pHull[1] = rHull.corner(1);
-    pHull[2] = rHull.corner(2);
-    pHull[3] = rHull.corner(3);
+        NR::Maybe<NR::Rect> rHull = cvh.bounds();
+        if (rHull) {
+            for ( unsigned i = 0 ; i < 4 ; ++i ) {
+                pHull.push_back(rHull->corner(i));
+            }
+        }
+    }
 
     return pHull;
 }
index 7a8a60dd088dde3f5fdb94c16f48b1b3db13905b..dd64975262b2a430806f673b167ecd8bd98822de 100644 (file)
@@ -71,12 +71,14 @@ sp_conn_end_move_compensate(NR::Matrix const *mp, SPItem *moved_item,
         };
         for (unsigned h = 0; h < 2; ++h) {
             NR::Maybe<NR::Rect> bbox = h2attItem[h]->getBounds(NR::identity());
-            if (bbox) {
-                h2bbox_icoordsys[h] = *bbox;
-            } else {
-                // FIXME
-                h2bbox_icoordsys[h] = NR::Rect(NR::Point(0, 0), NR::Point(0, 0));
+            if (!bbox) {
+                if (updatePathRepr) {
+                    path->requestDisplayUpdate(SP_OBJECT_MODIFIED_FLAG);
+                    path->updateRepr();
+                }
+                return;
             }
+            h2bbox_icoordsys[h] = *bbox;
             h2i2anc[h] = i2anc_affine(h2attItem[h], ancestor);
             h2endPt_icoordsys[h] = h2bbox_icoordsys[h].midpoint();
         }
@@ -112,13 +114,15 @@ sp_conn_end_move_compensate(NR::Matrix const *mp, SPItem *moved_item,
         NR::Rect otherpt_rect = NR::Rect(other_endpt, other_endpt);
         NR::Rect h2bbox_icoordsys[2] = { otherpt_rect, otherpt_rect };
         NR::Maybe<NR::Rect> bbox = h2attItem[ind]->getBounds(NR::identity());
-        if (bbox) {
-            h2bbox_icoordsys[ind] = *bbox;
-        } else {
-            // FIXME
-            h2bbox_icoordsys[ind] = NR::Rect(NR::Point(0, 0), NR::Point(0, 0));
+        if (!bbox) {
+            if (updatePathRepr) {
+                path->requestDisplayUpdate(SP_OBJECT_MODIFIED_FLAG);
+                path->updateRepr();
+            }
+            return;
         }
 
+        h2bbox_icoordsys[ind] = *bbox;
         h2i2anc = i2anc_affine(h2attItem[ind], ancestor);
         h2endPt_icoordsys[ind] = h2bbox_icoordsys[ind].midpoint();
 
index 7c5908e5853ff654df4232544547bc48e417de4b..34fa910ccd710199ea8d4ab700c1ead725bd4bb2 100644 (file)
@@ -602,9 +602,8 @@ private :
         // This bbox is cached between calls to randomize, so that there's no growth nor shrink
         // nor drift on sequential randomizations. Discard cache on global (or better active
         // desktop's) selection_change signal.
-        if (!_dialog.randomize_bbox_set) {
+        if (!_dialog.randomize_bbox) {
             _dialog.randomize_bbox = *sel_bbox;
-            _dialog.randomize_bbox_set = true;
         }
 
         // see comment in ActionAlign above
@@ -619,10 +618,10 @@ private :
             NR::Maybe<NR::Rect> item_box = sp_item_bbox_desktop (*it);
             if (item_box) {
                 // find new center, staying within bbox 
-                double x = _dialog.randomize_bbox.min()[NR::X] + item_box->extent(NR::X)/2 +
-                    g_random_double_range (0, _dialog.randomize_bbox.extent(NR::X) - item_box->extent(NR::X));
-                double y = _dialog.randomize_bbox.min()[NR::Y] + item_box->extent(NR::Y)/2 +
-                    g_random_double_range (0, _dialog.randomize_bbox.extent(NR::Y) - item_box->extent(NR::Y));
+                double x = _dialog.randomize_bbox->min()[NR::X] + item_box->extent(NR::X)/2 +
+                    g_random_double_range (0, _dialog.randomize_bbox->extent(NR::X) - item_box->extent(NR::X));
+                double y = _dialog.randomize_bbox->min()[NR::Y] + item_box->extent(NR::Y)/2 +
+                    g_random_double_range (0, _dialog.randomize_bbox->extent(NR::Y) - item_box->extent(NR::Y));
                 // displacement is the new center minus old:
                 NR::Point t = NR::Point (x, y) - 0.5*(item_box->max() + item_box->min());
                 sp_item_move_rel(*it, NR::translate(t));
@@ -767,7 +766,7 @@ void on_tool_changed(Inkscape::Application *inkscape, SPEventContext *context, A
 
 void on_selection_changed(Inkscape::Application *inkscape, Inkscape::Selection *selection, AlignAndDistribute *daad)
 {
-    daad->randomize_bbox_set = false;
+    daad->randomize_bbox = NR::Nothing();
 }
 
 /////////////////////////////////////////////////////////
@@ -777,7 +776,7 @@ void on_selection_changed(Inkscape::Application *inkscape, Inkscape::Selection *
 
 AlignAndDistribute::AlignAndDistribute() 
     : Dialog ("dialogs.align", SP_VERB_DIALOG_ALIGN_DISTRIBUTE),
-      randomize_bbox (NR::Point (0, 0), NR::Point (0, 0)),
+      randomize_bbox(NR::Nothing()),
       _alignFrame(_("Align")),
       _distributeFrame(_("Distribute")),
       _removeOverlapFrame(_("Remove overlaps")),
@@ -941,8 +940,7 @@ AlignAndDistribute::AlignAndDistribute()
 
     // Connect to the global selection change, to invalidate cached randomize_bbox
     g_signal_connect (G_OBJECT (INKSCAPE), "change_selection", G_CALLBACK (on_selection_changed), this);
-    randomize_bbox = NR::Rect (NR::Point (0, 0), NR::Point (0, 0));
-    randomize_bbox_set = false;
+    randomize_bbox = NR::Nothing();
 
     show_all_children();
 
index 69fc176736aae8a6785114d047436574e0ff8520..6d22071f3a532b148e9a0a5b69ebb11a577090dc 100644 (file)
@@ -65,9 +65,7 @@ public:
     std::list<SPItem *>::iterator find_master(std::list <SPItem *> &list, bool horizontal);
     void setMode(bool nodeEdit);
 
-    NR::Rect randomize_bbox;
-    bool randomize_bbox_set;
-
+    NR::Maybe<NR::Rect> randomize_bbox;
 
 protected:
 
index 4c84eeb24269d769b284492356a9d4980b34cae6..bb155fc7c6470e1f22b756dda398006e9dc99372 100644 (file)
@@ -626,11 +626,13 @@ static gint sp_font_preview_expose(GtkWidget *widget, GdkEventExpose *event)
                         hpos[len] = base_pt[0];
                         len++;
                         if ( curF ) {
-                            NR::Rect nbbox = curF->BBox(str_text->glyph_text[i].gl);
-                            bbox.x0 = MIN(bbox.x0, base_pt[NR::X] + theSize * (nbbox.min())[0]);
-                            bbox.y0 = MIN(bbox.y0, base_pt[NR::Y] - theSize * (nbbox.max())[1]);
-                            bbox.x1 = MAX(bbox.x1, base_pt[NR::X] + theSize * (nbbox.max())[0]);
-                            bbox.y1 = MAX(bbox.y1, base_pt[NR::Y] - theSize * (nbbox.min())[1]);
+                            NR::Maybe<NR::Rect> nbbox = curF->BBox(str_text->glyph_text[i].gl);
+                            if (nbbox) {
+                                bbox.x0 = MIN(bbox.x0, base_pt[NR::X] + theSize * (nbbox->min())[0]);
+                                bbox.y0 = MIN(bbox.y0, base_pt[NR::Y] - theSize * (nbbox->max())[1]);
+                                bbox.x1 = MAX(bbox.x1, base_pt[NR::X] + theSize * (nbbox->max())[0]);
+                                bbox.y1 = MAX(bbox.y1, base_pt[NR::Y] - theSize * (nbbox->min())[1]);
+                            }
                         }
                     }
                     if ( curF ) {