From 9f1c113eb98e7898f14502c69d8e3f7c35664c11 Mon Sep 17 00:00:00 2001 From: mathog <> Date: Thu, 21 May 2015 10:23:01 -0700 Subject: patch bug 1294784 (bzr r14167) --- src/display/drawing-text.cpp | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) (limited to 'src/display') diff --git a/src/display/drawing-text.cpp b/src/display/drawing-text.cpp index e20a7ff2a..3928ad796 100644 --- a/src/display/drawing-text.cpp +++ b/src/display/drawing-text.cpp @@ -367,7 +367,7 @@ void DrawingText::decorateStyle(DrawingContext &dc, double vextent, double xphas /* returns scaled line thickness */ void DrawingText::decorateItem(DrawingContext &dc, double phase_length, bool under) { - if (_nrstyle.font_size < 1.0e-32)return; // would cause a divide by zero and nothing would be visible anyway + if ( _nrstyle.font_size <= 1.0e-32 )return; // might cause a divide by zero or overflow and nothing would be visible anyway double tsp_width_adj = _nrstyle.tspan_width / _nrstyle.font_size; double tsp_asc_adj = _nrstyle.ascender / _nrstyle.font_size; double tsp_size_adj = (_nrstyle.ascender + _nrstyle.descender) / _nrstyle.font_size; @@ -381,6 +381,7 @@ void DrawingText::decorateItem(DrawingContext &dc, double phase_length, bool und Geom::Point p2; // All lines must be the same thickness, in combinations, line_through trumps underline double thickness = final_underline_thickness; + if ( thickness <= 1.0e-32 )return; // might cause a divide by zero or overflow and nothing would be visible anyway dc.setTolerance(0.5); // Is this really necessary... could effect dots. if( under ) { -- cgit v1.2.3 From 40093a750e66acc37ade5dad2a6fca96ae3ebb37 Mon Sep 17 00:00:00 2001 From: Jabier Arraiza Cenoz Date: Fri, 29 May 2015 20:44:00 +0200 Subject: Alex Valavanis fix for a compiling bug (bzr r14186) --- src/display/sp-canvas.h | 1 + 1 file changed, 1 insertion(+) (limited to 'src/display') diff --git a/src/display/sp-canvas.h b/src/display/sp-canvas.h index 48c3de2fc..65b06ade8 100644 --- a/src/display/sp-canvas.h +++ b/src/display/sp-canvas.h @@ -23,6 +23,7 @@ #endif #include +#include #include #include <2geom/affine.h> #include <2geom/rect.h> -- cgit v1.2.3 From 3d556ac8b9ff5cb1574f7cc873707e2bc008cc00 Mon Sep 17 00:00:00 2001 From: mathog <> Date: Mon, 1 Jun 2015 16:00:24 -0700 Subject: patch for bug 1283194 (bzr r14192) --- src/display/drawing-text.cpp | 25 ++++++++++++++++++++----- 1 file changed, 20 insertions(+), 5 deletions(-) (limited to 'src/display') diff --git a/src/display/drawing-text.cpp b/src/display/drawing-text.cpp index 3928ad796..a3ca7173a 100644 --- a/src/display/drawing-text.cpp +++ b/src/display/drawing-text.cpp @@ -91,9 +91,24 @@ unsigned DrawingGlyphs::_updateItem(Geom::IntRect const &/*area*/, UpdateContext if (_transform) { scale_bigbox /= _transform->descrim(); } + - Geom::Rect bigbox(Geom::Point(-_width*scale_bigbox*0.1, _asc*scale_bigbox*1.1),Geom::Point(_width*scale_bigbox, -_dsc*scale_bigbox*1.1)); - Geom::Rect b = bigbox * ctx.ctm; + /* Because there can be text decorations the bounding box must correspond in Y to a little above the glyph's ascend + and a little below its descend. This leaves room for overline and underline. The left and right sides + come from the glyph's bounding box. Note that the initial direction of ascender is positive down in Y, and + this flips after the transform is applied. So change the sign on descender. 1.1 provides a little extra space + above and below the max/min y positions of the letters to place the text decorations.*/ + + Geom::Rect b; + if(_drawable){ + Geom::OptRect tiltb = bounds_exact(*_font->PathVector(_glyph)); + Geom::Rect bigbox(Geom::Point(tiltb->left(),-_dsc*scale_bigbox*1.1),Geom::Point(tiltb->right(),_asc*scale_bigbox*1.1)); + b = bigbox * ctx.ctm; + } + else { // Fallback, spaces mostly + Geom::Rect bigbox(Geom::Point(0.0, -_dsc*scale_bigbox*1.1),Geom::Point(_width*scale_bigbox, _asc*scale_bigbox*1.1)); + b = bigbox * ctx.ctm; + } /* The pick box matches the characters as best as it can, leaving no extra space above or below @@ -108,11 +123,11 @@ unsigned DrawingGlyphs::_updateItem(Geom::IntRect const &/*area*/, UpdateContext if(_drawable){ pb = bounds_exact_transformed(*_font->PathVector(_glyph), ctx.ctm); } - if(!pb){ // Fallback + if(!pb){ // Fallback, spaces mostly Geom::Rect pbigbox(Geom::Point(0.0, _asc*scale_bigbox*0.66),Geom::Point(_width*scale_bigbox, 0.0)); pb = pbigbox * ctx.ctm; } - + #if 0 /* FIXME if this is commented out then not even an approximation of pick on decorations */ /* adjust the pick box up or down to include the decorations. @@ -214,7 +229,7 @@ DrawingText::addComponent(font_instance *font, int glyph, Geom::Affine const &tr ng->setGlyph(font, glyph, trans); if(font->PathVector(glyph)){ ng->_drawable = true; } else { ng->_drawable = false; } - ng->_width = width; // only used when _drawable = false + ng->_width = width; // used especially when _drawable = false, otherwise, it is the advance of the font ng->_asc = ascent; // of font, not of this one character ng->_dsc = descent; // of font, not of this one character ng->_pl = phase_length; // used for phase of dots, dashes, and wavy -- cgit v1.2.3 From e90dafdefd3ea63ca7c4f1e070eb367ec4d54e5c Mon Sep 17 00:00:00 2001 From: Diederik van Lierop Date: Fri, 12 Jun 2015 23:50:13 +0200 Subject: Make the behavior of the snap indicator fully transparent, such that all events are sent to the items or canvas as intended Fixed bugs: - https://launchpad.net/bugs/1420301 (bzr r14201) --- src/display/snap-indicator.cpp | 15 +++++++++++++++ src/display/sp-canvas-item.h | 7 ++++++- src/display/sp-canvas.cpp | 30 ++++++++---------------------- 3 files changed, 29 insertions(+), 23 deletions(-) (limited to 'src/display') diff --git a/src/display/snap-indicator.cpp b/src/display/snap-indicator.cpp index 8c0c8163f..926b35599 100644 --- a/src/display/snap-indicator.cpp +++ b/src/display/snap-indicator.cpp @@ -258,6 +258,19 @@ SnapIndicator::set_new_snaptarget(Inkscape::SnappedPoint const &p, bool pre_snap const int timeout_val = 4000; + // The snap indicator will be deleted after some time-out, and sp_canvas_item_dispose + // will be called. This will set canvas->current_item to NULL if the snap indicator was + // the current item, after which any events will go to the root handler instead of any + // item handler. Dragging an object which has just snapped might therefore not be possible + // without selecting / repicking it again. To avoid this, we make sure here that the + // snap indicator will never be picked, and will therefore never be the current item. + // Reported bugs: + // - scrolling when hovering above a pre-snap indicator won't work (for example) + // (https://bugs.launchpad.net/inkscape/+bug/522335/comments/8) + // - dragging doesn't work without repicking + // (https://bugs.launchpad.net/inkscape/+bug/1420301/comments/15) + SP_CTRL(canvasitem)->pickable = false; + SP_CTRL(canvasitem)->moveto(p.getPoint()); _snaptarget = _desktop->add_temporary_canvasitem(canvasitem, timeout_val); _snaptarget_is_presnap = pre_snap; @@ -282,6 +295,7 @@ SnapIndicator::set_new_snaptarget(Inkscape::SnappedPoint const &p, bool pre_snap SPCanvasItem *canvas_tooltip = sp_canvastext_new(_desktop->getTempGroup(), _desktop, tooltip_pos, tooltip_str); sp_canvastext_set_fontsize(SP_CANVASTEXT(canvas_tooltip), fontsize); + SP_CANVASTEXT(canvas_tooltip)->pickable = false; // See the extensive comment above SP_CANVASTEXT(canvas_tooltip)->rgba = 0xffffffff; SP_CANVASTEXT(canvas_tooltip)->outline = false; SP_CANVASTEXT(canvas_tooltip)->background = true; @@ -306,6 +320,7 @@ SnapIndicator::set_new_snaptarget(Inkscape::SnappedPoint const &p, bool pre_snap SP_CTRLRECT(box)->setRectangle(*bbox); SP_CTRLRECT(box)->setColor(pre_snap ? 0x7f7f7fff : 0xff0000ff, 0, 0); SP_CTRLRECT(box)->setDashed(true); + SP_CTRLRECT(box)->pickable = false; // See the extensive comment above sp_canvas_item_move_to_z(box, 0); _snaptarget_bbox = _desktop->add_temporary_canvasitem(box, timeout_val); } diff --git a/src/display/sp-canvas-item.h b/src/display/sp-canvas-item.h index 3b7b7bd4f..3e9e085a0 100644 --- a/src/display/sp-canvas-item.h +++ b/src/display/sp-canvas-item.h @@ -69,7 +69,12 @@ struct SPCanvasItem { gboolean visible; gboolean need_update; gboolean need_affine; - + + // If true, then SPCanvasGroup::point() and sp_canvas_item_invoke_point() will calculate + // the distance to the pointer, such that this item can be picked in pickCurrentItem() + // Only if an item can be picked, then it can be set as current_item and receive events! + bool pickable; + bool in_destruction; }; diff --git a/src/display/sp-canvas.cpp b/src/display/sp-canvas.cpp index 305b0950a..5efc4ce86 100644 --- a/src/display/sp-canvas.cpp +++ b/src/display/sp-canvas.cpp @@ -375,6 +375,7 @@ sp_canvas_item_init(SPCanvasItem *item) // used for rubberbanding, path outline, etc. item->visible = TRUE; item->in_destruction = false; + item->pickable = true; } SPCanvasItem *sp_canvas_item_new(SPCanvasGroup *parent, GType type, gchar const *first_arg_name, ...) @@ -728,7 +729,6 @@ bool sp_canvas_item_is_visible(SPCanvasItem *item) return item->visible; } - /** * Sets visible flag on item and requests a redraw. */ @@ -1009,21 +1009,21 @@ double SPCanvasGroup::point(SPCanvasItem *item, Geom::Point p, SPCanvasItem **ac if ((child->x1 <= x2) && (child->y1 <= y2) && (child->x2 >= x1) && (child->y2 >= y1)) { SPCanvasItem *point_item = NULL; // cater for incomplete item implementations - int has_point; - if (child->visible && SP_CANVAS_ITEM_GET_CLASS(child)->point) { + int pickable; + if (child->visible && child->pickable && SP_CANVAS_ITEM_GET_CLASS(child)->point) { dist = sp_canvas_item_invoke_point(child, p, &point_item); - has_point = TRUE; + pickable = TRUE; } else { - has_point = FALSE; + pickable = FALSE; } - // This metric should be improved, because in case of (partly) overlapping items we will now + // TODO: This metric should be improved, because in case of (partly) overlapping items we will now // always select the last one that has been added to the group. We could instead select the one // of which the center is the closest, for example. One can then move to the center // of the item to be focused, and have that one selected. Of course this will only work if the // centers are not coincident, but at least it's better than what we have now. // See the extensive comment in Inkscape::SelTrans::_updateHandles() - if (has_point && point_item && ((int) (dist + 0.5) <= item->canvas->close_enough)) { + if (pickable && point_item && ((int) (dist + 0.5) <= item->canvas->close_enough)) { best = dist; *actual_item = point_item; } @@ -1480,20 +1480,6 @@ int SPCanvasImpl::emitEvent(SPCanvas *canvas, GdkEvent *event) if (canvas->grabbed_item && !is_descendant (canvas->current_item, canvas->grabbed_item)) { item = canvas->grabbed_item; } else { - // Make sure that current_item is up-to-date. If a snap indicator was just deleted, then - // sp_canvas_item_dispose has been called and there is no current_item specified. We need - // that though because otherwise we don't know where to send this event to, leading to a - // lost event. We can't wait for idle events to have current_item updated, we need it now! - // Otherwise, scrolling when hovering above a pre-snap indicator won't work (for example) - // See this bug report: https://bugs.launchpad.net/inkscape/+bug/522335/comments/8 - if (canvas->need_repick && !canvas->in_repick && event->type == GDK_SCROLL) { - // To avoid side effects, we'll only do this for scroll events, because this is the - // only thing we want to fix here. An example of a reported side effect is that - // otherwise selection of nodes in the node editor by dragging a rectangle using a - // tablet will break - canvas->need_repick = FALSE; - pickCurrentItem(canvas, reinterpret_cast(event)); - } item = canvas->current_item; } @@ -1527,7 +1513,7 @@ int SPCanvasImpl::pickCurrentItem(SPCanvas *canvas, GdkEvent *event) { int button_down = 0; - if (!canvas->root) // canvas may have already be destroyed by closing desktop durring interrupted display! + if (!canvas->root) // canvas may have already be destroyed by closing desktop during interrupted display! return FALSE; int retval = FALSE; -- cgit v1.2.3