Cleanup and simplify WorkArea code

Rename cursor to caret to in order to avoid ambiguity. The caret is
now the blinking thing only.

Remove unused header contents, and some not so useful methods.

No intended change of behavior.
This commit is contained in:
Jean-Marc Lasgouttes 2017-07-22 01:19:45 +02:00
parent e7fdce0b5a
commit 1a7e342652
7 changed files with 152 additions and 223 deletions

View File

@ -65,8 +65,8 @@ FindAndReplaceWidget::FindAndReplaceWidget(GuiView & view)
replace_work_area_->setFrameStyle(QFrame::StyledPanel); replace_work_area_->setFrameStyle(QFrame::StyledPanel);
// We don't want two cursors blinking. // We don't want two cursors blinking.
find_work_area_->stopBlinkingCursor(); find_work_area_->stopBlinkingCaret();
replace_work_area_->stopBlinkingCursor(); replace_work_area_->stopBlinkingCaret();
} }

View File

@ -122,7 +122,6 @@
#include <X11/Xatom.h> #include <X11/Xatom.h>
#include <X11/Xlib.h> #include <X11/Xlib.h>
#include <QX11Info> #include <QX11Info>
#undef CursorShape
#undef None #undef None
#elif defined(QPA_XCB) #elif defined(QPA_XCB)
#include <xcb/xcb.h> #include <xcb/xcb.h>
@ -1439,7 +1438,7 @@ void GuiApplication::updateCurrentView(FuncRequest const & cmd, DispatchResult &
theSelection().haveSelection(bv->cursor().selection()); theSelection().haveSelection(bv->cursor().selection());
// update gui // update gui
current_view_->restartCursor(); current_view_->restartCaret();
} }
if (dr.needMessageUpdate()) { if (dr.needMessageUpdate()) {
// Some messages may already be translated, so we cannot use _() // Some messages may already be translated, so we cannot use _()
@ -2158,7 +2157,7 @@ void GuiApplication::processKeySym(KeySymbol const & keysym, KeyModifier state)
if (!keysym.isOK()) if (!keysym.isOK())
LYXERR(Debug::KEY, "Empty kbd action (probably composing)"); LYXERR(Debug::KEY, "Empty kbd action (probably composing)");
if (current_view_) if (current_view_)
current_view_->restartCursor(); current_view_->restartCaret();
return; return;
} }
@ -2218,7 +2217,7 @@ void GuiApplication::processKeySym(KeySymbol const & keysym, KeyModifier state)
if (!isPrintable(encoded_last_key)) { if (!isPrintable(encoded_last_key)) {
LYXERR(Debug::KEY, "Non-printable character! Omitting."); LYXERR(Debug::KEY, "Non-printable character! Omitting.");
if (current_view_) if (current_view_)
current_view_->restartCursor(); current_view_->restartCaret();
return; return;
} }
// The following modifier check is not needed on Mac. // The following modifier check is not needed on Mac.
@ -2240,7 +2239,7 @@ void GuiApplication::processKeySym(KeySymbol const & keysym, KeyModifier state)
{ {
if (current_view_) { if (current_view_) {
current_view_->message(_("Unknown function.")); current_view_->message(_("Unknown function."));
current_view_->restartCursor(); current_view_->restartCaret();
} }
return; return;
} }
@ -2255,7 +2254,7 @@ void GuiApplication::processKeySym(KeySymbol const & keysym, KeyModifier state)
LYXERR(Debug::KEY, "Unknown Action and not isText() -- giving up"); LYXERR(Debug::KEY, "Unknown Action and not isText() -- giving up");
if (current_view_) { if (current_view_) {
current_view_->message(_("Unknown function.")); current_view_->message(_("Unknown function."));
current_view_->restartCursor(); current_view_->restartCaret();
} }
return; return;
} }

View File

@ -4345,13 +4345,13 @@ Buffer const * GuiView::updateInset(Inset const * inset)
} }
void GuiView::restartCursor() void GuiView::restartCaret()
{ {
/* When we move around, or type, it's nice to be able to see /* When we move around, or type, it's nice to be able to see
* the cursor immediately after the keypress. * the caret immediately after the keypress.
*/ */
if (d.current_work_area_) if (d.current_work_area_)
d.current_work_area_->startBlinkingCursor(); d.current_work_area_->startBlinkingCaret();
// Take this occasion to update the other GUI elements. // Take this occasion to update the other GUI elements.
updateDialogs(); updateDialogs();
@ -4420,7 +4420,7 @@ void GuiView::resetDialogs()
// Now update controls with current buffer. // Now update controls with current buffer.
guiApp->setCurrentView(this); guiApp->setCurrentView(this);
restoreLayout(); restoreLayout();
restartCursor(); restartCaret();
} }

View File

@ -116,7 +116,7 @@ public:
/// \return true if the \c FuncRequest has been dispatched. /// \return true if the \c FuncRequest has been dispatched.
void dispatch(FuncRequest const & cmd, DispatchResult & dr); void dispatch(FuncRequest const & cmd, DispatchResult & dr);
void restartCursor(); void restartCaret();
/// Update the completion popup and the inline completion state. /// Update the completion popup and the inline completion state.
/// If \c start is true, then a new completion might be started. /// If \c start is true, then a new completion might be started.
/// If \c keep is true, an active completion will be kept active /// If \c keep is true, an active completion will be kept active

View File

@ -22,6 +22,7 @@
#include "GuiPainter.h" #include "GuiPainter.h"
#include "GuiView.h" #include "GuiView.h"
#include "Menus.h" #include "Menus.h"
#include "qt_helpers.h"
#include "Buffer.h" #include "Buffer.h"
#include "BufferList.h" #include "BufferList.h"
@ -36,7 +37,6 @@
#include "LyX.h" #include "LyX.h"
#include "LyXRC.h" #include "LyXRC.h"
#include "LyXVC.h" #include "LyXVC.h"
#include "qt_helpers.h"
#include "Text.h" #include "Text.h"
#include "TextMetrics.h" #include "TextMetrics.h"
#include "version.h" #include "version.h"
@ -46,7 +46,6 @@
#include "support/convert.h" #include "support/convert.h"
#include "support/debug.h" #include "support/debug.h"
#include "support/gettext.h"
#include "support/lassert.h" #include "support/lassert.h"
#include "support/TempFile.h" #include "support/TempFile.h"
@ -68,7 +67,6 @@
#include <QMenu> #include <QMenu>
#include <QPainter> #include <QPainter>
#include <QPalette> #include <QPalette>
#include <QPixmapCache>
#include <QScrollBar> #include <QScrollBar>
#include <QStyleOption> #include <QStyleOption>
#include <QStylePainter> #include <QStylePainter>
@ -77,8 +75,6 @@
#include <QToolTip> #include <QToolTip>
#include <QMenuBar> #include <QMenuBar>
#include "support/bind.h"
#include <cmath> #include <cmath>
#include <iostream> #include <iostream>
@ -130,17 +126,15 @@ mouse_button::state q_motion_state(Qt::MouseButtons state)
namespace frontend { namespace frontend {
class CursorWidget { class CaretWidget {
public: public:
CursorWidget() : rtl_(false), l_shape_(false), completable_(false), CaretWidget() : rtl_(false), l_shape_(false), completable_(false),
show_(false), x_(0), cursor_width_(0) x_(0), caret_width_(0)
{ {}
recomputeWidth();
}
void draw(QPainter & painter) void draw(QPainter & painter)
{ {
if (!show_ || !rect_.isValid()) if (!rect_.isValid())
return; return;
int y = rect_.top(); int y = rect_.top();
@ -149,7 +143,7 @@ public:
int bot = rect_.bottom(); int bot = rect_.bottom();
// draw vertical line // draw vertical line
painter.fillRect(x_, y, cursor_width_, rect_.height(), color_); painter.fillRect(x_, y, caret_width_, rect_.height(), color_);
// draw RTL/LTR indication // draw RTL/LTR indication
painter.setPen(color_); painter.setPen(color_);
@ -157,7 +151,7 @@ public:
if (rtl_) if (rtl_)
painter.drawLine(x_, bot, x_ - l, bot); painter.drawLine(x_, bot, x_ - l, bot);
else else
painter.drawLine(x_, bot, x_ + cursor_width_ + r, bot); painter.drawLine(x_, bot, x_ + caret_width_ + r, bot);
} }
// draw completion triangle // draw completion triangle
@ -168,8 +162,8 @@ public:
painter.drawLine(x_ - 1, m - d, x_ - 1 - d, m); painter.drawLine(x_ - 1, m - d, x_ - 1 - d, m);
painter.drawLine(x_ - 1, m + d, x_ - 1 - d, m); painter.drawLine(x_ - 1, m + d, x_ - 1 - d, m);
} else { } else {
painter.drawLine(x_ + cursor_width_, m - d, x_ + cursor_width_ + d, m); painter.drawLine(x_ + caret_width_, m - d, x_ + caret_width_ + d, m);
painter.drawLine(x_ + cursor_width_, m + d, x_ + cursor_width_ + d, m); painter.drawLine(x_ + caret_width_, m + d, x_ + caret_width_ + d, m);
} }
} }
} }
@ -203,17 +197,12 @@ public:
r = max(r, TabIndicatorWidth); r = max(r, TabIndicatorWidth);
} }
// compute overall rectangle caret_width_ = lyxrc.cursor_width
rect_ = QRect(x - l, y, cursor_width_ + r + l, h);
}
void show(bool set_show = true) { show_ = set_show; }
void hide() { show_ = false; }
int cursorWidth() const { return cursor_width_; }
void recomputeWidth() {
cursor_width_ = lyxrc.cursor_width
? lyxrc.cursor_width ? lyxrc.cursor_width
: 1 + int((lyxrc.currentZoom + 50) / 200.0); : 1 + int((lyxrc.currentZoom + 50) / 200.0);
// compute overall rectangle
rect_ = QRect(x - l, y, caret_width_ + r + l, h);
} }
QRect const & rect() { return rect_; } QRect const & rect() { return rect_; }
@ -226,15 +215,13 @@ private:
/// triangle to show that a completion is available /// triangle to show that a completion is available
bool completable_; bool completable_;
/// ///
bool show_;
///
QColor color_; QColor color_;
/// rectangle, possibly with l_shape and completion triangle /// rectangle, possibly with l_shape and completion triangle
QRect rect_; QRect rect_;
/// x position (were the vertical line is drawn) /// x position (were the vertical line is drawn)
int x_; int x_;
/// the width of the vertical blinking bar
int cursor_width_; int caret_width_;
}; };
@ -247,12 +234,34 @@ SyntheticMouseEvent::SyntheticMouseEvent()
GuiWorkArea::Private::Private(GuiWorkArea * parent) GuiWorkArea::Private::Private(GuiWorkArea * parent)
: p(parent), buffer_view_(0), lyx_view_(0), : p(parent), buffer_view_(0), lyx_view_(0),
cursor_visible_(false), cursor_(0), caret_(0), caret_visible_(false),
need_resize_(false), schedule_redraw_(false), preedit_lines_(1), need_resize_(false), schedule_redraw_(false), preedit_lines_(1),
pixel_ratio_(1.0), pixel_ratio_(1.0),
completer_(new GuiCompleter(p, p)), dialog_mode_(false), shell_escape_(false), completer_(new GuiCompleter(p, p)), dialog_mode_(false), shell_escape_(false),
read_only_(false), clean_(true), externally_modified_(false) read_only_(false), clean_(true), externally_modified_(false)
{ {
int const time = QApplication::cursorFlashTime() / 2;
if (time > 0) {
caret_timeout_.setInterval(time);
caret_timeout_.start();
} else {
// let's initialize this just to be safe
caret_timeout_.setInterval(500);
}
}
GuiWorkArea::Private::~Private()
{
// If something is wrong with the buffer, we can ignore it safely
try {
buffer_view_->buffer().workAreaManager().remove(p);
} catch(...) {}
delete buffer_view_;
delete caret_;
// Completer has a QObject parent and is thus automatically destroyed.
// See #4758.
// delete completer_;
} }
@ -285,23 +294,18 @@ double GuiWorkArea::pixelRatio() const
void GuiWorkArea::init() void GuiWorkArea::init()
{ {
// Setup the signals // Setup the signals
connect(&d->cursor_timeout_, SIGNAL(timeout()), connect(&d->caret_timeout_, SIGNAL(timeout()),
this, SLOT(toggleCursor())); this, SLOT(toggleCaret()));
int const time = QApplication::cursorFlashTime() / 2; // This connection is closed at the same time as this is destroyed.
if (time > 0) { d->synthetic_mouse_event_.timeout.timeout.connect([this](){
d->cursor_timeout_.setInterval(time); generateSyntheticMouseEvent();
d->cursor_timeout_.start(); });
} else {
// let's initialize this just to be safe
d->cursor_timeout_.setInterval(500);
}
// With Qt4.5 a mouse event will happen before the first paint event // With Qt4.5 a mouse event will happen before the first paint event
// so make sure that the buffer view has an up to date metrics. // so make sure that the buffer view has an up to date metrics.
d->buffer_view_->resize(viewport()->width(), viewport()->height()); d->buffer_view_->resize(viewport()->width(), viewport()->height());
d->cursor_ = new frontend::CursorWidget(); d->caret_ = new frontend::CaretWidget();
d->cursor_->hide();
setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff); setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
setAcceptDrops(true); setAcceptDrops(true);
@ -310,63 +314,33 @@ void GuiWorkArea::init()
setFrameStyle(QFrame::NoFrame); setFrameStyle(QFrame::NoFrame);
updateWindowTitle(); updateWindowTitle();
//viewport()->setAutoFillBackground(false); d->updateCursorShape();
// We don't need double-buffering nor SystemBackground on
// the viewport because we have our own backing pixmap. // we paint our own background
//viewport()->setAttribute(Qt::WA_NoSystemBackground);
viewport()->setAttribute(Qt::WA_OpaquePaintEvent); viewport()->setAttribute(Qt::WA_OpaquePaintEvent);
setFocusPolicy(Qt::StrongFocus); setFocusPolicy(Qt::StrongFocus);
d->setCursorShape(Qt::IBeamCursor);
// This connection is closed at the same time as this is destroyed.
d->synthetic_mouse_event_.timeout.timeout.connect([this](){
generateSyntheticMouseEvent();
});
LYXERR(Debug::GUI, "viewport width: " << viewport()->width() LYXERR(Debug::GUI, "viewport width: " << viewport()->width()
<< " viewport height: " << viewport()->height()); << " viewport height: " << viewport()->height());
// Enables input methods for asian languages. // Enables input methods for asian languages.
// Must be set when creating custom text editing widgets. // Must be set when creating custom text editing widgets.
setAttribute(Qt::WA_InputMethodEnabled, true); setAttribute(Qt::WA_InputMethodEnabled, true);
d->dialog_mode_ = false;
} }
GuiWorkArea::~GuiWorkArea() GuiWorkArea::~GuiWorkArea()
{ {
// If something is wrong with the buffer, we can ignore it safely
try {
d->buffer_view_->buffer().workAreaManager().remove(this);
} catch(...) {}
delete d->buffer_view_;
delete d->cursor_;
// Completer has a QObject parent and is thus automatically destroyed.
// See #4758.
// delete completer_;
delete d; delete d;
} }
Qt::CursorShape GuiWorkArea::cursorShape() const
{
return viewport()->cursor().shape();
}
void GuiWorkArea::Private::setCursorShape(Qt::CursorShape shape)
{
p->viewport()->setCursor(shape);
}
void GuiWorkArea::Private::updateCursorShape() void GuiWorkArea::Private::updateCursorShape()
{ {
setCursorShape(buffer_view_->clickableInset() bool const clickable = buffer_view_ && buffer_view_->clickableInset();
? Qt::PointingHandCursor : Qt::IBeamCursor); p->viewport()->setCursor(clickable ? Qt::PointingHandCursor
: Qt::IBeamCursor);
} }
@ -433,14 +407,14 @@ BufferView const & GuiWorkArea::bufferView() const
} }
void GuiWorkArea::stopBlinkingCursor() void GuiWorkArea::stopBlinkingCaret()
{ {
d->cursor_timeout_.stop(); d->caret_timeout_.stop();
d->hideCursor(); d->hideCaret();
} }
void GuiWorkArea::startBlinkingCursor() void GuiWorkArea::startBlinkingCaret()
{ {
// do not show the cursor if the view is busy // do not show the cursor if the view is busy
if (view().busy()) if (view().busy())
@ -453,14 +427,23 @@ void GuiWorkArea::startBlinkingCursor()
if (!d->buffer_view_->cursorInView(p, h)) if (!d->buffer_view_->cursorInView(p, h))
return; return;
d->showCursor(); d->showCaret();
//we're not supposed to cache this value. //we're not supposed to cache this value.
int const time = QApplication::cursorFlashTime() / 2; int const time = QApplication::cursorFlashTime() / 2;
if (time <= 0) if (time <= 0)
return; return;
d->cursor_timeout_.setInterval(time); d->caret_timeout_.setInterval(time);
d->cursor_timeout_.start(); d->caret_timeout_.start();
}
void GuiWorkArea::toggleCaret()
{
if (d->caret_visible_)
d->hideCaret();
else
d->showCaret();
} }
@ -482,9 +465,9 @@ void GuiWorkArea::redraw(bool update_metrics)
// update cursor position, because otherwise it has to wait until // update cursor position, because otherwise it has to wait until
// the blinking interval is over // the blinking interval is over
if (d->cursor_visible_) { if (d->caret_visible_) {
d->hideCursor(); d->hideCaret();
d->showCursor(); d->showCaret();
} }
LYXERR(Debug::WORKAREA, "WorkArea::redraw screen"); LYXERR(Debug::WORKAREA, "WorkArea::redraw screen");
@ -522,9 +505,9 @@ void GuiWorkArea::processKeySym(KeySymbol const & key, KeyModifier mod)
} }
// In order to avoid bad surprise in the middle of an operation, // In order to avoid bad surprise in the middle of an operation,
// we better stop the blinking cursor... // we better stop the blinking caret...
// the cursor gets restarted in GuiView::restartCursor() // the cursor gets restarted in GuiView::restartCaret()
stopBlinkingCursor(); stopBlinkingCaret();
guiApp->processKeySym(key, mod); guiApp->processKeySym(key, mod);
} }
@ -544,7 +527,7 @@ void GuiWorkArea::Private::dispatch(FuncRequest const & cmd)
// In order to avoid bad surprise in the middle of an operation, we better stop // In order to avoid bad surprise in the middle of an operation, we better stop
// the blinking cursor. // the blinking cursor.
if (notJustMovingTheMouse) if (notJustMovingTheMouse)
p->stopBlinkingCursor(); p->stopBlinkingCaret();
buffer_view_->mouseEventDispatch(cmd); buffer_view_->mouseEventDispatch(cmd);
@ -565,7 +548,7 @@ void GuiWorkArea::Private::dispatch(FuncRequest const & cmd)
lyx_view_->clearMessage(); lyx_view_->clearMessage();
// Show the cursor immediately after any operation // Show the cursor immediately after any operation
p->startBlinkingCursor(); p->startBlinkingCaret();
} }
updateCursorShape(); updateCursorShape();
@ -576,16 +559,16 @@ void GuiWorkArea::Private::resizeBufferView()
{ {
// WARNING: Please don't put any code that will trigger a repaint here! // WARNING: Please don't put any code that will trigger a repaint here!
// We are already inside a paint event. // We are already inside a paint event.
p->stopBlinkingCursor(); p->stopBlinkingCaret();
// Warn our container (GuiView). // Warn our container (GuiView).
p->busy(true); p->busy(true);
Point point; Point point;
int h = 0; int h = 0;
buffer_view_->cursorPosAndHeight(point, h); buffer_view_->cursorPosAndHeight(point, h);
bool const cursor_in_view = buffer_view_->cursorInView(point, h); bool const caret_in_view = buffer_view_->cursorInView(point, h);
buffer_view_->resize(p->viewport()->width(), p->viewport()->height()); buffer_view_->resize(p->viewport()->width(), p->viewport()->height());
if (cursor_in_view) if (caret_in_view)
buffer_view_->scrollToCursor(); buffer_view_->scrollToCursor();
p->viewport()->update(); p->viewport()->update();
@ -601,19 +584,19 @@ void GuiWorkArea::Private::resizeBufferView()
// We might be resizing even if the focus is on another widget so we only // We might be resizing even if the focus is on another widget so we only
// restart the cursor if we have the focus. // restart the cursor if we have the focus.
if (p->hasFocus()) if (p->hasFocus())
QTimer::singleShot(50, p, SLOT(startBlinkingCursor())); QTimer::singleShot(50, p, SLOT(startBlinkingCaret()));
} }
void GuiWorkArea::Private::showCursor() void GuiWorkArea::Private::showCaret()
{ {
if (cursor_visible_) if (caret_visible_)
return; return;
Point p; Point point;
int h = 0; int h = 0;
buffer_view_->cursorPosAndHeight(p, h); buffer_view_->cursorPosAndHeight(point, h);
if (!buffer_view_->cursorInView(p, h)) if (!buffer_view_->cursorInView(point, h))
return; return;
// RTL or not RTL // RTL or not RTL
@ -636,34 +619,39 @@ void GuiWorkArea::Private::showCursor()
&& completer_->completionAvailable() && completer_->completionAvailable()
&& !completer_->popupVisible() && !completer_->popupVisible()
&& !completer_->inlineVisible(); && !completer_->inlineVisible();
cursor_visible_ = true; caret_visible_ = true;
cursor_->recomputeWidth();
//int cur_x = buffer_view_->getPos(cur).x_; //int cur_x = buffer_view_->getPos(cur).x_;
// We may have decided to slide the cursor row so that cursor // We may have decided to slide the cursor row so that cursor
// is visible. // is visible.
p.x_ -= buffer_view_->horizScrollOffset(); point.x_ -= buffer_view_->horizScrollOffset();
showCursor(p.x_, p.y_, h, l_shape, isrtl, completable); caret_->update(point.x_, point.y_, h, l_shape, isrtl, completable);
if (schedule_redraw_) {
// This happens when a graphic conversion is finished. As we don't know
// the size of the new graphics, it's better the update everything.
// We can't use redraw() here because this would trigger a infinite
// recursive loop with showCaret().
buffer_view_->resize(p->viewport()->width(), p->viewport()->height());
p->viewport()->update();
updateScrollbar();
schedule_redraw_ = false;
return;
}
p->viewport()->update(caret_->rect());
} }
void GuiWorkArea::Private::hideCursor() void GuiWorkArea::Private::hideCaret()
{ {
if (!cursor_visible_) if (!caret_visible_)
return; return;
cursor_visible_ = false; caret_visible_ = false;
removeCursor(); //if (!qApp->focusWidget())
} p->viewport()->update(caret_->rect());
void GuiWorkArea::toggleCursor()
{
if (d->cursor_visible_)
d->hideCursor();
else
d->showCursor();
} }
@ -686,7 +674,7 @@ void GuiWorkArea::Private::updateScrollbar()
void GuiWorkArea::scrollTo(int value) void GuiWorkArea::scrollTo(int value)
{ {
stopBlinkingCursor(); stopBlinkingCaret();
d->buffer_view_->scrollDocView(value, true); d->buffer_view_->scrollDocView(value, true);
if (lyxrc.cursor_follows_scrollbar) { if (lyxrc.cursor_follows_scrollbar) {
@ -695,7 +683,7 @@ void GuiWorkArea::scrollTo(int value)
d->lyx_view_->updateLayoutList(); d->lyx_view_->updateLayoutList();
} }
// Show the cursor immediately after any operation. // Show the cursor immediately after any operation.
startBlinkingCursor(); startBlinkingCaret();
// FIXME QT5 // FIXME QT5
#ifdef Q_WS_X11 #ifdef Q_WS_X11
QApplication::syncX(); QApplication::syncX();
@ -801,7 +789,7 @@ void GuiWorkArea::focusInEvent(QFocusEvent * e)
d->lyx_view_->currentWorkArea()->bufferView().buffer().updateBuffer(); d->lyx_view_->currentWorkArea()->bufferView().buffer().updateBuffer();
} }
startBlinkingCursor(); startBlinkingCaret();
QAbstractScrollArea::focusInEvent(e); QAbstractScrollArea::focusInEvent(e);
} }
@ -809,7 +797,7 @@ void GuiWorkArea::focusInEvent(QFocusEvent * e)
void GuiWorkArea::focusOutEvent(QFocusEvent * e) void GuiWorkArea::focusOutEvent(QFocusEvent * e)
{ {
LYXERR(Debug::DEBUG, "GuiWorkArea::focusOutEvent(): " << this << endl); LYXERR(Debug::DEBUG, "GuiWorkArea::focusOutEvent(): " << this << endl);
stopBlinkingCursor(); stopBlinkingCaret();
QAbstractScrollArea::focusOutEvent(e); QAbstractScrollArea::focusOutEvent(e);
} }
@ -1163,53 +1151,21 @@ void GuiWorkArea::paintEvent(QPaintEvent * ev)
if (d->needResize()) { if (d->needResize()) {
d->resizeBufferView(); d->resizeBufferView();
if (d->cursor_visible_) { if (d->caret_visible_) {
d->hideCursor(); d->hideCaret();
d->showCursor(); d->showCaret();
} }
} }
GuiPainter pain(viewport(), pixelRatio()); GuiPainter pain(viewport(), pixelRatio());
d->buffer_view_->draw(pain, d->cursor_visible_); d->buffer_view_->draw(pain, d->caret_visible_);
if (d->cursor_visible_) if (d->caret_visible_)
d->cursor_->draw(pain); d->caret_->draw(pain);
ev->accept(); ev->accept();
} }
void GuiWorkArea::Private::showCursor(int x, int y, int h,
bool l_shape, bool rtl, bool completable)
{
if (schedule_redraw_) {
// This happens when a graphic conversion is finished. As we don't know
// the size of the new graphics, it's better the update everything.
// We can't use redraw() here because this would trigger a infinite
// recursive loop with showCursor().
buffer_view_->resize(p->viewport()->width(), p->viewport()->height());
p->viewport()->update();
updateScrollbar();
schedule_redraw_ = false;
// Show the cursor immediately after the update.
hideCursor();
p->toggleCursor();
return;
}
cursor_->update(x, y, h, l_shape, rtl, completable);
cursor_->show();
p->viewport()->update(cursor_->rect());
}
void GuiWorkArea::Private::removeCursor()
{
cursor_->hide();
//if (!qApp->focusWidget())
p->viewport()->update(cursor_->rect());
}
void GuiWorkArea::inputMethodEvent(QInputMethodEvent * e) void GuiWorkArea::inputMethodEvent(QInputMethodEvent * e)
{ {
//FIXME Broken Feature !! //FIXME Broken Feature !!
@ -1236,9 +1192,9 @@ void GuiWorkArea::inputMethodEvent(QInputMethodEvent * e)
// Hide the cursor during the kana-kanji transformation. // Hide the cursor during the kana-kanji transformation.
if (preedit_string.empty()) if (preedit_string.empty())
startBlinkingCursor(); startBlinkingCaret();
else else
stopBlinkingCursor(); stopBlinkingCaret();
// last_width : for checking if last preedit string was/wasn't empty. // last_width : for checking if last preedit string was/wasn't empty.
// FIXME THREAD && FIXME // FIXME THREAD && FIXME
@ -1256,8 +1212,8 @@ void GuiWorkArea::inputMethodEvent(QInputMethodEvent * e)
FontInfo font = d->buffer_view_->cursor().getFont().fontInfo(); FontInfo font = d->buffer_view_->cursor().getFont().fontInfo();
FontMetrics const & fm = theFontMetrics(font); FontMetrics const & fm = theFontMetrics(font);
int height = fm.maxHeight(); int height = fm.maxHeight();
int cur_x = d->cursor_->rect().left(); int cur_x = d->caret_->rect().left();
int cur_y = d->cursor_->rect().bottom(); int cur_y = d->caret_->rect().bottom();
// redraw area of preedit string. // redraw area of preedit string.
viewport()->update(0, cur_y - height, viewport()->width(), viewport()->update(0, cur_y - height, viewport()->width(),
@ -1277,7 +1233,7 @@ void GuiWorkArea::inputMethodEvent(QInputMethodEvent * e)
// get attributes of input method cursor. // get attributes of input method cursor.
// cursor_pos : cursor position in preedit string. // cursor_pos : cursor position in preedit string.
size_t cursor_pos = 0; size_t cursor_pos = 0;
bool cursor_is_visible = false; bool caret_is_visible = false;
for (int i = 0; i != att.size(); ++i) { for (int i = 0; i != att.size(); ++i) {
if (att.at(i).type == QInputMethodEvent::Cursor) { if (att.at(i).type == QInputMethodEvent::Cursor) {
cursor_pos = att.at(i).start; cursor_pos = att.at(i).start;
@ -1364,7 +1320,7 @@ QVariant GuiWorkArea::inputMethodQuery(Qt::InputMethodQuery query) const
// this is the CJK-specific composition window position and // this is the CJK-specific composition window position and
// the context menu position when the menu key is pressed. // the context menu position when the menu key is pressed.
case Qt::ImMicroFocus: case Qt::ImMicroFocus:
cur_r = d->cursor_->rect(); cur_r = d->caret_->rect();
if (d->preedit_lines_ != 1) if (d->preedit_lines_ != 1)
cur_r.moveLeft(10); cur_r.moveLeft(10);
cur_r.moveBottom(cur_r.bottom() cur_r.moveBottom(cur_r.bottom()
@ -1491,7 +1447,7 @@ QSize EmbeddedWorkArea::sizeHint () const
void EmbeddedWorkArea::disable() void EmbeddedWorkArea::disable()
{ {
stopBlinkingCursor(); stopBlinkingCaret();
if (view().currentWorkArea() != this) if (view().currentWorkArea() != this)
return; return;
// No problem if currentMainWorkArea() is 0 (setCurrentWorkArea() // No problem if currentMainWorkArea() is 0 (setCurrentWorkArea()

View File

@ -26,10 +26,6 @@ class QDropEvent;
class QToolButton; class QToolButton;
class QWidget; class QWidget;
#ifdef CursorShape
#undef CursorShape
#endif
namespace lyx { namespace lyx {
class Buffer; class Buffer;
@ -83,8 +79,6 @@ public:
/// ///
GuiCompleter & completer(); GuiCompleter & completer();
Qt::CursorShape cursorShape() const;
/// Return the GuiView this workArea belongs to /// Return the GuiView this workArea belongs to
GuiView const & view() const; GuiView const & view() const;
GuiView & view(); GuiView & view();
@ -94,9 +88,9 @@ public:
public Q_SLOTS: public Q_SLOTS:
/// ///
void stopBlinkingCursor(); void stopBlinkingCaret();
/// ///
void startBlinkingCursor(); void startBlinkingCaret();
Q_SIGNALS: Q_SIGNALS:
/// ///
@ -116,7 +110,7 @@ private Q_SLOTS:
/// timer to limit triple clicks /// timer to limit triple clicks
void doubleClickTimeout(); void doubleClickTimeout();
/// toggle the cursor's visibility /// toggle the cursor's visibility
void toggleCursor(); void toggleCaret();
/// close this work area. /// close this work area.
/// Slot for Buffer::closing signal. /// Slot for Buffer::closing signal.
void close(); void close();

View File

@ -13,30 +13,13 @@
#define WORKAREA_PRIVATE_H #define WORKAREA_PRIVATE_H
#include "FuncRequest.h" #include "FuncRequest.h"
#include "LyXRC.h"
#include "support/FileName.h" #include "support/FileName.h"
#include "support/Timeout.h" #include "support/Timeout.h"
#include <QMouseEvent> #include <QMouseEvent>
#include <QImage>
#include <QPixmap>
#include <QTimer> #include <QTimer>
class QContextMenuEvent;
class QDragEnterEvent;
class QDropEvent;
class QKeyEvent;
class QPaintEvent;
class QResizeEvent;
class QToolButton;
class QWheelEvent;
class QWidget;
#ifdef CursorShape
#undef CursorShape
#endif
namespace lyx { namespace lyx {
class Buffer; class Buffer;
@ -86,34 +69,30 @@ public:
/** /**
* Implementation of the work area (buffer view GUI) * Implementation of the work area (buffer view GUI)
*/ */
class CursorWidget; class CaretWidget;
struct GuiWorkArea::Private struct GuiWorkArea::Private
{ {
///
Private(GuiWorkArea *); Private(GuiWorkArea *);
///
~Private();
/// ///
void resizeBufferView(); void resizeBufferView();
/// paint the cursor and store the background
void showCursor(int x, int y, int h,
bool l_shape, bool rtl, bool completable);
/// hide the cursor
void removeCursor();
/// ///
void dispatch(FuncRequest const & cmd0); void dispatch(FuncRequest const & cmd0);
/// hide the visible cursor, if it is visible /// hide the visible cursor, if it is visible
void hideCursor(); void hideCaret();
/// show the cursor if it is not visible /// show the cursor if it is not visible
void showCursor(); void showCaret();
/// Set the range and value of the scrollbar and connect to its valueChanged /// Set the range and value of the scrollbar and connect to its valueChanged
/// signal. /// signal.
void updateScrollbar(); void updateScrollbar();
/// Change the cursor when the mouse hovers over a clickable inset /// Change the cursor when the mouse hovers over a clickable inset
void updateCursorShape(); void updateCursorShape();
///
void setCursorShape(Qt::CursorShape shape);
bool needResize() const { bool needResize() const {
return need_resize_ || p->pixelRatio() != pixel_ratio_; return need_resize_ || p->pixelRatio() != pixel_ratio_;
@ -125,18 +104,19 @@ struct GuiWorkArea::Private
BufferView * buffer_view_; BufferView * buffer_view_;
/// ///
GuiView * lyx_view_; GuiView * lyx_view_;
/// is the cursor currently displayed
bool cursor_visible_;
/// ///
QTimer cursor_timeout_; CaretWidget * caret_;
/// is the cursor currently displayed
bool caret_visible_;
///
QTimer caret_timeout_;
/// ///
SyntheticMouseEvent synthetic_mouse_event_; SyntheticMouseEvent synthetic_mouse_event_;
/// ///
DoubleClick dc_event_; DoubleClick dc_event_;
///
CursorWidget * cursor_;
/// ///
bool need_resize_; bool need_resize_;
/// ///