This commit fixes a crash when accessing a math inset. This was due to an invalid CursorSlice::text() null pointer accessed in InsetMathNest::cursorPos():

CoordCache & coord_cache = sl.text()->bv()->coordCache();

As you can see, I used this indirection to access the BufferView::CoordCache(). Bad luck, the passed CursorSlice was not completely valid inside a mathed inset, hence the crash. My solution is to pass BufferView to InsetBase::cursorPos() and all its derivative.

* InsetBase::cursorPos(): pass BufferView const &

* bufferview_funcs::coordOffset(): ditto.




git-svn-id: svn://svn.lyx.org/lyx/lyx-devel/trunk@15356 a592a061-630c-0410-9148-cb99ea01b6c8
This commit is contained in:
Abdelrazak Younes 2006-10-17 16:23:27 +00:00
parent 52bd213992
commit 4cc7a7708e
21 changed files with 47 additions and 36 deletions

View File

@ -608,7 +608,7 @@ void BufferView::center()
bot.text()->redoParagraph(pit);
Paragraph const & par = bot.text()->paragraphs()[pit];
anchor_ref_ = pit;
offset_ref_ = bv_funcs::coordOffset(cursor_, cursor_.boundary()).y_
offset_ref_ = bv_funcs::coordOffset(*this, cursor_, cursor_.boundary()).y_
+ par.ascent() - height_ / 2;
}

View File

@ -156,7 +156,8 @@ bool string2font(string const & data, LyXFont & font, bool & toggle)
// the next two should probably go elsewhere
// this give the position relative to (0, baseline) of outermost
// paragraph
Point coordOffset(DocIterator const & dit, bool boundary)
Point coordOffset(BufferView const & bv, DocIterator const & dit,
bool boundary)
{
int x = 0;
int y = 0;
@ -166,7 +167,7 @@ Point coordOffset(DocIterator const & dit, bool boundary)
CursorSlice const & sl = dit[i];
int xx = 0;
int yy = 0;
sl.inset().cursorPos(sl, boundary && ((i+1) == dit.depth()), xx, yy);
sl.inset().cursorPos(bv, sl, boundary && ((i+1) == dit.depth()), xx, yy);
x += xx;
y += yy;
//lyxerr << "LCursor::getPos, i: "
@ -215,7 +216,7 @@ Point getPos(BufferView & bv, DocIterator const & dit, bool boundary)
//lyxerr << "cursor out of view" << std::endl;
return Point(-1, -1);
}
Point p = coordOffset(dit, boundary); // offset from outer paragraph
Point p = coordOffset(bv, dit, boundary); // offset from outer paragraph
p.y_ += it->second.y_;
return p;
}

View File

@ -52,7 +52,7 @@ enum CurStatus {
CurStatus status(BufferView const * bv, DocIterator const & dit);
lyx::Point coordOffset(DocIterator const & dit, bool boundary);
lyx::Point coordOffset(BufferView const & bv, DocIterator const & dit, bool boundary);
/// Moves cursor to the next inset with one of the given codes.
void gotoInset(BufferView * bv, std::vector<InsetBase_code> const & codes,

View File

@ -101,7 +101,7 @@ namespace {
int yo;
InsetBase const * inset = &it.inset();
Point o = c.bv().coordCache().getInsets().xy(inset);
inset->cursorPos(it.top(), c.boundary(), xo, yo);
inset->cursorPos(c.bv(), it.top(), c.boundary(), xo, yo);
// Convert to absolute
xo += o.x_;
yo += o.y_;

View File

@ -269,7 +269,8 @@ void InsetBase::markErased(bool)
{}
void InsetBase::cursorPos(CursorSlice const &, bool, int & x, int & y) const
void InsetBase::cursorPos(BufferView const & bv, CursorSlice const &,
bool, int & x, int & y) const
{
lyxerr << "InsetBase::cursorPos called directly" << std::endl;
x = 100;

View File

@ -124,8 +124,8 @@ public:
/// do we cover screen position x/y?
virtual bool covers(BufferView & bv, int x, int y) const;
/// get the screen positions of the cursor (see note in cursor.C)
virtual void cursorPos(CursorSlice const & sl, bool boundary,
int & x, int & y) const;
virtual void cursorPos(BufferView const & bv,
CursorSlice const & sl, bool boundary, int & x, int & y) const;
/// is this an inset that can be moved into?
virtual bool isActive() const { return nargs() > 0; }

View File

@ -81,10 +81,10 @@ docstring const InsetCaption::editMessage() const
}
void InsetCaption::cursorPos
(CursorSlice const & sl, bool boundary, int & x, int & y) const
void InsetCaption::cursorPos(BufferView const & bv,
CursorSlice const & sl, bool boundary, int & x, int & y) const
{
InsetText::cursorPos(sl, boundary, x, y);
InsetText::cursorPos(bv, sl, boundary, x, y);
x += labelwidth_;
}

View File

@ -35,8 +35,8 @@ public:
///
virtual lyx::docstring const editMessage() const;
///
virtual void cursorPos
(CursorSlice const & sl, bool boundary, int & x, int & y) const;
virtual void cursorPos(BufferView const & bv,
CursorSlice const & sl, bool boundary, int & x, int & y) const;
///
bool descendable() const { return true; }
///

View File

@ -211,12 +211,12 @@ void InsetCollapsable::drawSelection(PainterInfo & pi, int x, int y) const
}
void InsetCollapsable::cursorPos
(CursorSlice const & sl, bool boundary, int & x, int & y) const
void InsetCollapsable::cursorPos(BufferView const & bv,
CursorSlice const & sl, bool boundary, int & x, int & y) const
{
BOOST_ASSERT(status() != Collapsed);
InsetText::cursorPos(sl, boundary, x, y);
InsetText::cursorPos(bv, sl, boundary, x, y);
if (status() == Open) {
if (openinlined_)

View File

@ -55,7 +55,8 @@ public:
///
void drawSelection(PainterInfo & pi, int x, int y) const;
/// return x,y of given position relative to the inset's baseline
void cursorPos(CursorSlice const & sl, bool boundary, int & x, int & y) const;
void cursorPos(BufferView const & bv, CursorSlice const & sl,
bool boundary, int & x, int & y) const;
///
bool hitButton(FuncRequest const &) const;
///

View File

@ -1117,10 +1117,10 @@ shared_ptr<InsetText> InsetTabular::cell(idx_type idx)
}
void InsetTabular::cursorPos
(CursorSlice const & sl, bool boundary, int & x, int & y) const
void InsetTabular::cursorPos(BufferView const & bv,
CursorSlice const & sl, bool boundary, int & x, int & y) const
{
cell(sl.idx())->cursorPos(sl, boundary, x, y);
cell(sl.idx())->cursorPos(bv, sl, boundary, x, y);
// y offset correction
int const row = tabular.row_of_cell(sl.idx());

View File

@ -97,7 +97,8 @@ public:
///
Code lyxCode() const { return InsetBase::TABULAR_CODE; }
/// get offset of this cursor slice relative to our upper left corner
void cursorPos(CursorSlice const & sl, bool boundary, int & x, int & y) const;
void cursorPos(BufferView const & bv, CursorSlice const & sl,
bool boundary, int & x, int & y) const;
///
bool tabularFeatures(LCursor & cur, std::string const & what);
///

View File

@ -301,8 +301,8 @@ void InsetText::validate(LaTeXFeatures & features) const
}
void InsetText::cursorPos
(CursorSlice const & sl, bool boundary, int & x, int & y) const
void InsetText::cursorPos(BufferView const & bv,
CursorSlice const & sl, bool boundary, int & x, int & y) const
{
x = text_.cursorX(sl, boundary) + border_;
y = text_.cursorY(sl, boundary);

View File

@ -73,7 +73,8 @@ public:
void validate(LaTeXFeatures & features) const;
/// return x,y of given position relative to the inset's baseline
void cursorPos(CursorSlice const & sl, bool boundary, int & x, int & y) const;
void cursorPos(BufferView const & bv, CursorSlice const & sl,
bool boundary, int & x, int & y) const;
///
Code lyxCode() const { return TEXT_CODE; }
///

View File

@ -102,8 +102,8 @@ LyXText * InsetMathMBox::getText(int) const
}
void InsetMathMBox::cursorPos
(CursorSlice const & sl, bool boundary, int & x, int & y) const
void InsetMathMBox::cursorPos(BufferView const & bv,
CursorSlice const & sl, bool boundary, int & x, int & y) const
{
x = text_.cursorX(sl, boundary);
y = text_.cursorY(sl, boundary);

View File

@ -41,7 +41,8 @@ public:
///
LyXText * getText(int) const;
///
void cursorPos(CursorSlice const & sl, bool boundary, int & x, int & y) const;
void cursorPos(BufferView const & bv, CursorSlice const & sl,
bool boundary, int & x, int & y) const;
protected:
virtual void doDispatch(LCursor & cur, FuncRequest & cmd);

View File

@ -48,12 +48,12 @@ string MathMacro::name() const
}
void MathMacro::cursorPos(CursorSlice const & sl, bool boundary, int & x,
int & y) const
void MathMacro::cursorPos(BufferView const & bv,
CursorSlice const & sl, bool boundary, int & x, int & y) const
{
// We may have 0 arguments, but InsetMathNest requires at least one.
if (nargs() > 0)
InsetMathNest::cursorPos(sl, boundary, x, y);
InsetMathNest::cursorPos(bv, sl, boundary, x, y);
}

View File

@ -33,7 +33,8 @@ public:
///
void metrics(MetricsInfo & mi, Dimension & dim) const;
/// get cursor position
void cursorPos(CursorSlice const & sl, bool boundary, int & x, int & y) const;
void cursorPos(BufferView const & bv, CursorSlice const & sl,
bool boundary, int & x, int & y) const;
///
InsetBase * editXY(LCursor & cur, int x, int y);
///

View File

@ -98,8 +98,9 @@ MathArray const & InsetMathNest::cell(idx_type i) const
}
void InsetMathNest::cursorPos(CursorSlice const & sl, bool /*boundary*/,
int & x, int & y) const
void InsetMathNest::cursorPos(BufferView const & bv,
CursorSlice const & sl, bool /*boundary*/,
int & x, int & y) const
{
// FIXME: This is a hack. Ideally, the coord cache should not store
// absolute positions, but relative ones. This would mean to call
@ -110,7 +111,7 @@ void InsetMathNest::cursorPos(CursorSlice const & sl, bool /*boundary*/,
// absolute again when actually drawing the cursor. What a mess.
BOOST_ASSERT(ptr_cmp(&sl.inset(), this));
MathArray const & ar = sl.cell();
CoordCache & coord_cache = sl.text()->bv()->coordCache();
CoordCache const & coord_cache = bv.coordCache();
if (!coord_cache.getArrays().has(&ar)) {
// this can (semi-)legally happen if we just created this cell
// and it never has been drawn before. So don't ASSERT.

View File

@ -37,7 +37,8 @@ public:
/// identifies NestInsets
InsetMathNest const * asNestInset() const { return this; }
/// get cursor position
void cursorPos(CursorSlice const & sl, bool boundary, int & x, int & y) const;
void cursorPos(BufferView const & bv, CursorSlice const & sl,
bool boundary, int & x, int & y) const;
///
void edit(LCursor & cur, bool left);
///

View File

@ -15,6 +15,8 @@
#include "support/docstring.h"
#include <string>
class PainterInfo;
class LyXFont;
class Dimension;