Get rid of ParagraphMetrics::insetDimension

We already have a CoordCache of insets dimensions. It is not necessary
to store the same information in two places.

Give a name to CoordCache tables types to improve code readability.

Remove ParagraphMetrics::singleWidth, which is not used anymore.
This commit is contained in:
Jean-Marc Lasgouttes 2015-10-12 16:11:58 +02:00
parent e181a881db
commit 26eb5092fb
9 changed files with 37 additions and 93 deletions

View File

@ -33,14 +33,14 @@ is acted on.
** Buffer::change issues
When calling Buffer::changed outside of bv::processUpdateFlags,
how do we now that the update strategy is set correctly? It is
how do we know that the update strategy is set correctly? It is
possible to reset the strategy at the end of bv::draw. What would be
a good value? NoScreenUpdate?
On a related note, what is the semantics of a call to
Buffer::changed(false)? What does the caller mean?
** How to avoid redraw with FitCursor when the cursor is already OK?
** How to avoid redraw with FitCursor when the cursor is already OK?
In this case, we invoke Buffer::change(false) with drawing disabled
and NoScreenUpdate strategy.
@ -60,15 +60,9 @@ cursor.
* Proposals
** get rid of pm::insetDimension.
The information contained there is already in bv::coordCache.
Effect: only code simplification.
** set inset position during metrics phase
This implies to set inset positions relative to outer isnet during
This implies to set inset positions relative to outer inset during
metrics phase and then in a second loop to descend into insets and
update positions correctly.
@ -95,14 +89,13 @@ expensive for large files. This would though help scrolling.
* Description of current drawing mechanism
** Two phase drawing
** Two stage drawing
There are two parts to drawing the work area:
+ the metrics phase computes the size of insets and breaks the
paragraphs into rows. It stores the dimension of insets (both
normal and math) in bv::coordCache, and the size of normal
insets in pm::insetDimension.
normal and math) in bv::coordCache.
+ the drawing phase draws the contents and caches the inset
positions. Since the caching of positions is useful in itself,
@ -110,7 +103,6 @@ There are two parts to drawing the work area:
thing we want is to cache inset positions
(Painter::setDrawingEnabled).
The machinery is controlled via bv::processUpdateFlags. This method is
called at the end of bv::mouseEventDispatch and in
GuiApplication::dispatch, via the updateCurrentView method. There are

View File

@ -2847,8 +2847,7 @@ Point BufferView::coordOffset(DocIterator const & dit) const
// FIXME (Abdel 23/09/2007): this is a bit messy because of the
// elimination of Inset::dim_ cache. This coordOffset() method needs
// to be rewritten in light of the new design.
Dimension const & dim = parMetrics(dit[i - 1].text(),
dit[i - 1].pit()).insetDimension(&sl.inset());
Dimension const & dim = coordCache().getInsets().dim(&sl.inset());
lastw = dim.wid;
} else {
Dimension const dim = sl.inset().dimension(*this);

View File

@ -42,7 +42,7 @@ void CoordCache::clear()
void CoordCache::dump() const
{
LYXERR0("InsetCache contains:");
CoordCacheBase<Inset>::cache_type::const_iterator it =
CoordCache::Insets::cache_type::const_iterator it =
getInsets().data_.begin();
for (; it != getInsets().data_.end(); ++it) {
// Warning: it is not guaranteed that inset is a valid pointer

View File

@ -167,10 +167,10 @@ private:
* All points cached in this cache are only valid between subsequent
* updates. (x,y) == (0,0) is the upper left screen corner, x increases
* to the right, y increases downwords.
* The dimension part is built in BufferView::updateMetrics() and the
* The dimension part is built in BufferView::updateMetrics() and the
* diverse Inset::metrics() calls.
* The individual points are added at drawing time in
* BufferView::updateMetrics(). The math inset position are cached in
* BufferView::draw(). The math inset position are cached in
* the diverse InsetMathXXX::draw() calls and the in-text inset position
* are cached in RowPainter::paintInset().
* FIXME: For mathed, it would be nice if the insets did not saves their
@ -182,19 +182,21 @@ public:
void clear();
/// A map from MathData to position on the screen
CoordCacheBase<MathData> & arrays() { return arrays_; }
CoordCacheBase<MathData> const & getArrays() const { return arrays_; }
typedef CoordCacheBase<MathData> Arrays;
Arrays & arrays() { return arrays_; }
Arrays const & getArrays() const { return arrays_; }
/// A map from insets to positions on the screen
CoordCacheBase<Inset> & insets() { return insets_; }
CoordCacheBase<Inset> const & getInsets() const { return insets_; }
typedef CoordCacheBase<Inset> Insets;
Insets & insets() { return insets_; }
Insets const & getInsets() const { return insets_; }
/// Dump the contents of the cache to lyxerr in debugging form
void dump() const;
private:
/// MathDatas
CoordCacheBase<MathData> arrays_;
Arrays arrays_;
// All insets
CoordCacheBase<Inset> insets_;
Insets insets_;
};
} // namespace lyx

View File

@ -119,24 +119,6 @@ void ParagraphMetrics::setPosition(int position)
}
Dimension const & ParagraphMetrics::insetDimension(Inset const * inset) const
{
InsetDims::const_iterator it = inset_dims_.find(inset);
if (it != inset_dims_.end())
return it->second;
static Dimension dummy;
return dummy;
}
void ParagraphMetrics::setInsetDimension(Inset const * inset,
Dimension const & dim)
{
inset_dims_[inset] = dim;
}
Row & ParagraphMetrics::getRow(pos_type pos, bool boundary)
{
LBUFERR(!rows().empty());
@ -212,25 +194,6 @@ int ParagraphMetrics::rightMargin(BufferView const & bv) const
}
int ParagraphMetrics::singleWidth(pos_type pos, Font const & font) const
{
// The most special cases are handled first.
if (Inset const * inset = par_->getInset(pos))
return insetDimension(inset).wid;
char_type const c = par_->getChar(pos);
if (c == '\t')
return 4 * theFontMetrics(font).width(' ');
// Note that this function is only called in
// RowPainter::paintText, and only used for characters that do
// not require handling of compose chars or ligatures. It can
// therefore be kept simple.
return theFontMetrics(font).width(c);
}
bool ParagraphMetrics::hfillExpansion(Row const & row, pos_type pos) const
{
if (!par_->isHfill(pos))

View File

@ -78,8 +78,6 @@ public:
RowList const & rows() const { return rows_; }
///
int rightMargin(BufferView const & bv) const;
///
int singleWidth(pos_type pos, Font const & Font) const;
/// dump some information to lyxerr
void dump() const;
@ -94,11 +92,6 @@ public:
int position() const { return position_; }
void setPosition(int position);
///
Dimension const & insetDimension(Inset const * inset) const;
///
void setInsetDimension(Inset const *, Dimension const & dim);
private:
///
int position_;
@ -108,10 +101,6 @@ private:
Dimension dim_;
///
Paragraph const * par_;
typedef std::map<Inset const *, Dimension> InsetDims;
///
InsetDims inset_dims_;
};
} // namespace lyx

View File

@ -139,7 +139,7 @@ void RowPainter::paintInset(Inset const * inset, Font const & font,
inset->drawSelection(pi_, x1, yo_);
inset->draw(pi_, x1, yo_);
Dimension const & dim = pm_.insetDimension(inset);
Dimension const & dim = pi_.base.bv->coordCache().insets().dim(inset);
paintForeignMark(x_, font.language(), dim.descent());

View File

@ -400,6 +400,7 @@ bool TextMetrics::redoParagraph(pit_type const pit)
// redo insets
Font const bufferfont = buffer.params().getFont();
CoordCache::Insets & insetCache = bv_->coordCache().insets();
InsetList::const_iterator ii = par.insetList().begin();
InsetList::const_iterator iend = par.insetList().end();
for (; ii != iend; ++ii) {
@ -425,9 +426,8 @@ bool TextMetrics::redoParagraph(pit_type const pit)
MacroContext mc(&buffer, parPos);
MetricsInfo mi(bv_, font.fontInfo(), w, mc);
ii->inset->metrics(mi, dim);
Dimension const & old_dim = pm.insetDimension(ii->inset);
if (old_dim != dim) {
pm.setInsetDimension(ii->inset, dim);
if (!insetCache.has(ii->inset) || insetCache.dim(ii->inset) != dim) {
insetCache.add(ii->inset, dim);
changed = true;
}
}
@ -621,6 +621,7 @@ void TextMetrics::computeRowMetrics(pit_type const pit,
&& (body_pos > endpos || !par.isLineSeparator(body_pos - 1)))
body_pos = 0;
ParagraphMetrics & pm = par_metrics_[pit];
CoordCache::Insets & insetCache = bv_->coordCache().insets();
Row::iterator cit = row.begin();
Row::iterator const cend = row.end();
for ( ; cit != cend; ++cit) {
@ -635,8 +636,7 @@ void TextMetrics::computeRowMetrics(pit_type const pit,
else
cit->dim.wid = 5;
// Cache the inset dimension.
bv_->coordCache().insets().add(cit->inset, cit->dim);
pm.setInsetDimension(cit->inset, cit->dim);
insetCache.add(cit->inset, cit->dim);
}
}
@ -778,7 +778,6 @@ void TextMetrics::breakRow(Row & row, int const right_margin, pit_type const pit
return;
}
ParagraphMetrics const & pm = par_metrics_[pit];
ParagraphList const & pars = text_->paragraphs();
#if 0
@ -804,7 +803,7 @@ void TextMetrics::breakRow(Row & row, int const right_margin, pit_type const pit
// The most special cases are handled first.
if (par.isInset(i)) {
Inset const * ins = par.getInset(i);
Dimension dim = pm.insetDimension(ins);
Dimension dim = bv_->coordCache().insets().dim(ins);
row.add(i, ins, dim, *fi, par.lookupChange(i));
} else if (c == ' ' && i + 1 == body_pos) {
// There is a space at i, but it should not be
@ -929,12 +928,12 @@ void TextMetrics::setRowHeight(Row & row, pit_type const pit,
int maxdesc = int(fontmetrics.maxDescent() * spacing_val);
// insets may be taller
ParagraphMetrics const & pm = par_metrics_[pit];
CoordCache::Insets const & insetCache = bv_->coordCache().getInsets();
Row::const_iterator cit = row.begin();
Row::const_iterator cend = row.end();
for ( ; cit != cend; ++cit) {
if (cit->inset) {
Dimension const & dim = pm.insetDimension(cit->inset);
Dimension const & dim = insetCache.dim(cit->inset);
maxasc = max(maxasc, dim.ascent());
maxdesc = max(maxdesc, dim.descent());
}
@ -1327,9 +1326,9 @@ Inset * TextMetrics::editXY(Cursor & cur, int x, int y,
if (edited == inset && cur.pos() == it->pos) {
// non-editable inset, set cursor after the inset if x is
// nearer to that position (bug 9628)
ParagraphMetrics const & pm = par_metrics_[pit];
Dimension const & dim = pm.insetDimension(inset);
Point p = bv_->coordCache().getInsets().xy(inset);
CoordCache::Insets const & insetCache = bv_->coordCache().getInsets();
Dimension const & dim = insetCache.dim(inset);
Point p = insetCache.xy(inset);
bool const is_rtl = text_->isRTL(text_->getPar(pit));
if (is_rtl) {
// "in front of" == "right of"
@ -1389,7 +1388,7 @@ void TextMetrics::setCursorFromCoordinates(Cursor & cur, int const x, int const
InsetList::InsetTable * TextMetrics::checkInsetHit(pit_type pit, int x, int y)
{
Paragraph const & par = text_->paragraphs()[pit];
ParagraphMetrics const & pm = par_metrics_[pit];
CoordCache::Insets const & insetCache = bv_->coordCache().getInsets();
LYXERR(Debug::DEBUG, "x: " << x << " y: " << y << " pit: " << pit);
@ -1400,13 +1399,13 @@ InsetList::InsetTable * TextMetrics::checkInsetHit(pit_type pit, int x, int y)
LYXERR(Debug::DEBUG, "examining inset " << inset);
if (!bv_->coordCache().getInsets().has(inset)) {
if (!insetCache.has(inset)) {
LYXERR(Debug::DEBUG, "inset has no cached position");
return 0;
}
Dimension const & dim = pm.insetDimension(inset);
Point p = bv_->coordCache().getInsets().xy(inset);
Dimension const & dim = insetCache.dim(inset);
Point p = insetCache.xy(inset);
LYXERR(Debug::DEBUG, "xo: " << p.x_ << "..." << p.x_ + dim.wid
<< " yo: " << p.y_ - dim.asc << "..." << p.y_ + dim.des);

View File

@ -266,7 +266,7 @@ void MathData::metrics(MetricsInfo & mi, Dimension & dim) const
dim.asc = 0;
dim.wid = 0;
Dimension d;
CoordCacheBase<Inset> & coords = mi.base.bv->coordCache().insets();
CoordCache::Insets & coords = mi.base.bv->coordCache().insets();
for (pos_type i = 0, n = size(); i != n; ++i) {
MathAtom const & at = operator[](i);
at->metrics(mi, d);
@ -318,7 +318,7 @@ void MathData::draw(PainterInfo & pi, int x, int y) const
if (inlineCompletionPos.inMathed())
inlineCompletionData = &inlineCompletionPos.cell();
CoordCacheBase<Inset> & coords = pi.base.bv->coordCache().insets();
CoordCache::Insets & coords = pi.base.bv->coordCache().insets();
for (size_t i = 0, n = size(); i != n; ++i) {
MathAtom const & at = operator[](i);
coords.add(at.nucleus(), x, y);
@ -850,7 +850,7 @@ int MathData::pos2x(BufferView const * bv, size_type pos, int glue) const
{
int x = 0;
size_type target = min(pos, size());
CoordCacheBase<Inset> const & coords = bv->coordCache().getInsets();
CoordCache::Insets const & coords = bv->coordCache().getInsets();
for (size_type i = 0; i < target; ++i) {
const_iterator it = begin() + i;
if ((*it)->getChar() == ' ')
@ -874,7 +874,7 @@ MathData::size_type MathData::x2pos(BufferView const * bv, int targetx, int glue
const_iterator it = begin();
int lastx = 0;
int currx = 0;
CoordCacheBase<Inset> const & coords = bv->coordCache().getInsets();
CoordCache::Insets const & coords = bv->coordCache().getInsets();
// find first position after targetx
for (; currx < targetx && it != end(); ++it) {
lastx = currx;