#include "frontends/font_metrics.h"
#include "frontends/nullpainter.h"
+#include "frontends/LyXView.h"
+#include "frontends/WorkArea.h"
#include "frontends/Painter.h"
#include "insets/insettext.h"
#include <boost/crc.hpp>
+using lyx::frontend::Painter;
+using lyx::frontend::NullPainter;
+using lyx::char_type;
using lyx::pos_type;
using lyx::pit_type;
namespace {
+/// Flag: do a full redraw of inside text of inset
+/// Working variable indicating a full screen refresh
+bool refreshInside;
+
/**
* A class used for painting an individual row of text.
*/
void paintForeignMark(double orig_x, LyXFont const & font, int desc = 0);
void paintHebrewComposeChar(lyx::pos_type & vpos, LyXFont const & font);
void paintArabicComposeChar(lyx::pos_type & vpos, LyXFont const & font);
- void paintChars(lyx::pos_type & vpos, LyXFont font,
- bool hebrew, bool arabic);
+ void paintChars(lyx::pos_type & vpos, LyXFont font,
+ bool hebrew, bool arabic);
int paintAppendixStart(int y);
void paintFromPos(lyx::pos_type & vpos);
void paintInset(lyx::pos_type const pos, LyXFont const & font);
pi.ltr_pos = (text_.bidi.level(pos) % 2 == 0);
pi.erased_ = erased_ || isDeletedText(par_, pos);
theCoords.insets().add(inset, int(x_), yo_);
- InsetBase * in = const_cast<InsetBase *>(inset);
+ InsetText const * const in = inset->asTextInset();
// non-wide insets are painted completely. Recursive
- bool tmp = bv_.repaintAll();
- if (!in->asTextInset() || !static_cast<InsetText*>(in)->Wide()) {
- bv_.repaintAll(true);
+ bool tmp = refreshInside;
+ if (!in || !in->Wide()) {
+ refreshInside = true;
lyxerr[Debug::PAINTING] << endl << "Paint inset fully" << endl;
}
- if (bv_.repaintAll())
+ if (refreshInside)
inset->drawSelection(pi, int(x_), yo_);
inset->draw(pi, int(x_), yo_);
- bv_.repaintAll(tmp);
+ refreshInside = tmp;
x_ += inset->width();
}
string str;
// first char
- char c = par_.getChar(pos);
+ char_type c = par_.getChar(pos);
str += c;
++vpos;
for (pos_type i = pos - 1; i >= 0; --i) {
c = par_.getChar(i);
- if (!Encodings::IsComposeChar_hebrew(c)) {
- if (IsPrintableNonspace(c)) {
+ if (!Encodings::isComposeChar_hebrew(c)) {
+ if (isPrintableNonspace(c)) {
int const width2 =
text_.singleWidth(par_, i, c, text_.getFont(par_, i));
// dalet / resh
string str;
// first char
- char c = par_.getChar(pos);
+ char_type c = par_.getChar(pos);
c = par_.transformChar(c, pos);
str += c;
++vpos;
for (pos_type i = pos - 1; i >= 0; --i) {
c = par_.getChar(i);
- if (!Encodings::IsComposeChar_arabic(c)) {
- if (IsPrintableNonspace(c)) {
- int const width2 =
+ if (!Encodings::isComposeChar_arabic(c)) {
+ if (isPrintableNonspace(c)) {
+ int const width2 =
text_.singleWidth(par_, i, c, text_.getFont(par_, i));
dx = (width2 - width) / 2;
}
}
-void RowPainter::paintChars(pos_type & vpos, LyXFont font,
+void RowPainter::paintChars(pos_type & vpos, LyXFont font,
bool hebrew, bool arabic)
{
pos_type pos = text_.bidi.vis2log(vpos);
pos_type const end = row_.endpos();
FontSpan const font_span = par_.fontSpan(pos);
- Change::Type const prev_change = par_.lookupChange(pos);
+ Change::Type const prev_change = par_.lookupChange(pos).type;
// first character
string str;
if (prev_change != par_.lookupChange(pos))
break;
- char c = par_.getChar(pos);
+ char_type c = par_.getChar(pos);
- if (!IsPrintableNonspace(c))
+ if (!isPrintableNonspace(c))
break;
- if (arabic && Encodings::IsComposeChar_arabic(c))
+ if (arabic && Encodings::isComposeChar_arabic(c))
break;
- if (hebrew && Encodings::IsComposeChar_hebrew(c))
+ if (hebrew && Encodings::isComposeChar_hebrew(c))
break;
if (arabic)
}
// usual characters, no insets
- char const c = par_.getChar(pos);
+ char_type const c = par_.getChar(pos);
// special case languages
std::string const & lang = orig_font.language()->lang();
// draw as many chars as we can
if ((!hebrew && !arabic)
- || (hebrew && !Encodings::IsComposeChar_hebrew(c))
- || (arabic && !Encodings::IsComposeChar_arabic(c))) {
+ || (hebrew && !Encodings::isComposeChar_hebrew(c))
+ || (arabic && !Encodings::isComposeChar_arabic(c))) {
paintChars(vpos, orig_font, hebrew, arabic);
} else if (hebrew) {
paintHebrewComposeChar(vpos, orig_font);
bool is_struckout = false;
int last_strikeout_x = 0;
- // Use font span to speed things up, see below
+ // Use font span to speed things up, see below
FontSpan font_span;
LyXFont font;
}
-bool CursorOnRow(PainterInfo & pi, pit_type const pit,
+bool CursorOnRow(PainterInfo & pi, pit_type const pit,
RowList::const_iterator rit, LyXText const & text)
{
// Is there a cursor on this row (or inside inset on row)
CursorSlice const & sl = cur[d];
if (sl.text() == &text
&& sl.pit() == pit
- && sl.pos() >= rit->pos()
+ && sl.pos() >= rit->pos()
&& sl.pos() <= rit->endpos())
return true;
}
}
-bool innerCursorOnRow(PainterInfo & pi, pit_type pit,
+bool innerCursorOnRow(PainterInfo & pi, pit_type pit,
RowList::const_iterator rit, LyXText const & text)
{
// Is there a cursor inside an inset on this row, and is this inset
for (lyx::size_type d = 0; d < cur.depth(); d++) {
CursorSlice const & sl = cur[d];
if (sl.text() == &text
- && sl.pit() == pit
+ && sl.pit() == pit
&& sl.pos() == rit->pos())
return d < cur.depth() - 1;
}
lyx::size_type rowno(0);
for (RowList::const_iterator rit = rb; rit != re; ++rit, ++rowno) {
y += rit->ascent();
- // Allow setting of bv->repaintAll() for nested insets in
+ // Allow setting of refreshInside for nested insets in
// this row only
- bool tmp = pi.base.bv->repaintAll();
+ bool tmp = refreshInside;
// Row signature; has row changed since last paint?
lyx::size_type const row_sig = calculateRowSignature(*rit, par, x, y);
bool row_has_changed = par.rowSignature()[rowno] != row_sig;
-
+
bool cursor_on_row = CursorOnRow(pi, pit, rit, text);
bool in_inset_alone_on_row = innerCursorOnRow(pi, pit, rit,
text);
// If this is the only object on the row, we can make it wide
for (pos_type i = rit->pos() ; i != rit->endpos(); ++i) {
- InsetBase* in
- = const_cast<InsetBase*>(par.getInset(i));
- if (in && in->asTextInset()) {
- static_cast<InsetText*>(in)->Wide()
- = in_inset_alone_on_row &&
- static_cast<InsetText*>(in)->Tall();
+ InsetBase const * const in = par.getInset(i);
+ if (in) {
+ InsetText const * const t = in->asTextInset();
+ if (t)
+ t->Wide() = in_inset_alone_on_row;
}
}
- // If selection is on, the current row signature differs
- // from cache, or cursor is inside an inset _on this row_,
+ // If selection is on, the current row signature differs
+ // from cache, or cursor is inside an inset _on this row_,
// then paint the row
if (repaintAll || row_has_changed || cursor_on_row) {
// Add to row signature cache
bool const inside = (y + rit->descent() >= 0
&& y - rit->ascent() < ww);
RowPainter rp(inside ? pi : nullpi, text, pit, *rit, x, y);
- // Clear background of this row
+ // Clear background of this row
// (if paragraph background was not cleared)
- if (!repaintAll &&
+ if (!repaintAll &&
(!in_inset_alone_on_row || row_has_changed)) {
- pi.pain.fillRectangle(( rowno ? 0 : x - 10 ), y - rit->ascent(),
- pi.base.bv->workWidth(), rit->height(),
+ pi.pain.fillRectangle(x, y - rit->ascent(),
+ text.maxwidth_, rit->height(),
text.backgroundColor());
// If outer row has changed, force nested
// insets to repaint completely
if (row_has_changed)
- pi.base.bv->repaintAll(true);
+ refreshInside = true;
}
-
+
// Instrumentation for testing row cache (see also
// 12 lines lower):
if (text.isMainText())
- lyxerr[Debug::PAINTING] << "#";
+ lyxerr[Debug::PAINTING] << "#";
else
- lyxerr[Debug::PAINTING] << "[" <<
+ lyxerr[Debug::PAINTING] << "[" <<
repaintAll << row_has_changed <<
cursor_on_row << "]";
rp.paintAppendix();
}
y += rit->descent();
// Restore, see above
- pi.base.bv->repaintAll(tmp);
+ refreshInside = tmp;
}
lyxerr[Debug::PAINTING] << "." << endl;
}
void paintText(BufferView const & bv, ViewMetricsInfo const & vi)
{
- Painter & pain = bv.painter();
+ Painter & pain = bv.owner()->workArea()->getPainter();
LyXText * const text = bv.text();
bool const select = bv.cursor().selection();
PainterInfo pi(const_cast<BufferView *>(&bv), pain);
// Should the whole screen, including insets, be refreshed?
- bool repaintAll(select || !vi.singlepar);
-
+ bool repaintAll = select || !vi.singlepar;
+
if (repaintAll) {
// Clear background (if not delegated to rows)
pain.fillRectangle(0, vi.y1, bv.workWidth(), vi.y2 - vi.y1,
int yy = vi.y1;
// draw contents
for (pit_type pit = vi.p1; pit <= vi.p2; ++pit) {
- bv.repaintAll(repaintAll);
+ refreshInside = repaintAll;
Paragraph const & par = text->getPar(pit);
yy += par.ascent();
paintPar(pi, *bv.text(), pit, 0, yy, repaintAll);
if (vi.p1 > 0) {
text->redoParagraph(vi.p1 - 1);
- theCoords.parPos()[bv.text()][vi.p1 - 1] =
+ theCoords.parPos()[bv.text()][vi.p1 - 1] =
Point(0, vi.y1 - text->getPar(vi.p1 - 1).descent());
}
if (vi.p2 < lyx::pit_type(text->paragraphs().size()) - 1) {
text->redoParagraph(vi.p2 + 1);
- theCoords.parPos()[bv.text()][vi.p2 + 1] =
+ theCoords.parPos()[bv.text()][vi.p2 + 1] =
Point(0, vi.y2 + text->getPar(vi.p2 + 1).ascent());
}
y -= text.getPar(0).ascent();
// This flag can not be set from within same inset:
- bool repaintAll = pi.base.bv->repaintAll();
+ bool repaintAll = refreshInside;
for (int pit = 0; pit < int(text.paragraphs().size()); ++pit) {
y += text.getPar(pit).ascent();
paintPar(pi, text, pit, x, y, repaintAll);