#include "dolphinviewautoscroller.h"
#include <QAbstractItemView>
-#include <QCoreApplication>
+#include <QApplication>
#include <QCursor>
#include <QEvent>
#include <QMouseEvent>
DolphinViewAutoScroller::DolphinViewAutoScroller(QAbstractItemView* parent) :
QObject(parent),
m_rubberBandSelection(false),
+ m_keyPressed(false),
+ m_initializedTimestamp(false),
m_horizontalScrollInc(0),
m_verticalScrollInc(0),
m_itemView(parent),
- m_timer(0)
+ m_timer(0),
+ m_timestamp()
{
m_itemView->setAutoScroll(false);
m_itemView->viewport()->installEventFilter(this);
+ m_itemView->installEventFilter(this);
m_timer = new QTimer(this);
m_timer->setSingleShot(false);
return m_timer->isActive();
}
+void DolphinViewAutoScroller::handleCurrentIndexChange(const QModelIndex& current,
+ const QModelIndex& previous)
+{
+ // When the autoscroller is inactive and a key has been pressed, it must be
+ // assured that the current item stays visible. The check whether the previous
+ // item is valid is important because of #197951. The keypress check is done
+ // because of #199833.
+ if (current.isValid() && (previous.isValid() || m_keyPressed) && !isActive()) {
+ m_itemView->scrollTo(current);
+ }
+}
+
bool DolphinViewAutoScroller::eventFilter(QObject* watched, QEvent* event)
{
if (watched == m_itemView->viewport()) {
stopAutoScroll();
break;
+ default:
+ break;
+ }
+ } else if (watched == m_itemView) {
+ switch (event->type()) {
+ case QEvent::KeyPress:
+ m_keyPressed = true;
+ break;
+
+ case QEvent::KeyRelease:
+ m_keyPressed = false;
+ break;
+
default:
break;
}
void DolphinViewAutoScroller::scrollViewport()
{
+ if (m_timestamp.elapsed() < QApplication::startDragTime()) {
+ return;
+ }
+
QScrollBar* verticalScrollBar = m_itemView->verticalScrollBar();
if (verticalScrollBar != 0) {
const int value = verticalScrollBar->value();
// update the rubberband.
QWidget* viewport = m_itemView->viewport();
const QPoint pos = viewport->mapFromGlobal(QCursor::pos());
- QMouseEvent event(QEvent::MouseMove, pos, Qt::LeftButton, Qt::LeftButton, Qt::NoModifier);
+ QMouseEvent event(QEvent::MouseMove, pos, Qt::LeftButton, Qt::LeftButton, QApplication::keyboardModifiers());
QCoreApplication::sendEvent(viewport, &event);
}
}
m_itemView->horizontalScrollBar()->isVisible();
if (!verticalScrolling && !horizontalScrolling) {
// no scrollbars are shown at all, so no autoscrolling is necessary
+ stopAutoScroll();
return;
}
if (m_timer->isActive()) {
if ((m_horizontalScrollInc == 0) && (m_verticalScrollInc == 0)) {
- m_timer->stop();
+ stopAutoScroll();
}
} else if ((m_horizontalScrollInc != 0) || (m_verticalScrollInc != 0)) {
+ if (!m_initializedTimestamp) {
+ m_initializedTimestamp = true;
+ m_timestamp.start();
+ }
m_timer->start();
}
}
m_timer->stop();
m_horizontalScrollInc = 0;
m_verticalScrollInc = 0;
+ m_initializedTimestamp = false;
}
int DolphinViewAutoScroller::calculateScrollIncrement(int cursorPos, int rangeSize) const