Skip to content

Commit

Permalink
Scroll faster (#5560)
Browse files Browse the repository at this point in the history
* make it go fast

* even faster!

* better mouseclick handling and now we can drag the data in editmode too!

* clean up
  • Loading branch information
JorisGoosen authored Jun 13, 2024
1 parent 1b8538f commit 5535a4a
Show file tree
Hide file tree
Showing 8 changed files with 143 additions and 124 deletions.
5 changes: 3 additions & 2 deletions Common/timers.cpp
Original file line number Diff line number Diff line change
@@ -1,8 +1,9 @@
#include "timers.h"

#ifdef PROFILE_JASP
#include <iostream>

#include <algorithm>
#include <iostream>
#include <vector>
static std::map<std::string, boost::timer::cpu_timer *> * timers = nullptr;

boost::timer::cpu_timer * _getTimer(std::string timerName)
Expand Down
3 changes: 0 additions & 3 deletions Desktop/components/JASP/Widgets/DataTableView.qml
Original file line number Diff line number Diff line change
Expand Up @@ -81,9 +81,6 @@ FocusScope
cacheItems: true //!ribbonModel.dataMode
maxColWidth: 250 * jaspTheme.uiScale
expandDataSet: ribbonModel.dataMode

doubleClickWorkaround: !ribbonModel.dataMode
//flickableInteractive: !ribbonModel.dataMode
onDoubleClicked: __myRoot.doubleClicked()

function showPopupMenu(fromItem, globalPos, rowIndex, columnIndex)
Expand Down
2 changes: 1 addition & 1 deletion Desktop/components/JASP/Widgets/DataTableViewEdit.qml
Original file line number Diff line number Diff line change
Expand Up @@ -192,7 +192,7 @@ Item
anchors.fill: parent
acceptedButtons: Qt.RightButton

onPressed: (mouse) =>
onClicked: (mouse) =>
{
if(mouse.buttons & Qt.RightButton)
dataTableView.showPopupMenu(editItemRoot, mapToGlobal(mouse.x, mouse.y), rowIndex, columnIndex);
Expand Down
2 changes: 1 addition & 1 deletion Desktop/components/JASP/Widgets/DataTableViewItem.qml
Original file line number Diff line number Diff line change
Expand Up @@ -85,7 +85,7 @@ Item
toolTipTimeOut: 10000
toolTipDelay: 400

onPressed: (mouse) =>
onClicked: (mouse) =>
{
if(ribbonModel.dataMode)
{
Expand Down
75 changes: 8 additions & 67 deletions Desktop/components/JASP/Widgets/JASPDataView.qml
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,6 @@ FocusScope
property string toolTip: ""
property alias cursorShape: wheelCatcher.cursorShape
property alias mouseArea: wheelCatcher
property bool doubleClickWorkaround: true
property alias isMainDataViewer: theView.mainData
readonly property alias editCoordinates: theView.editCoordinates

Expand Down Expand Up @@ -52,6 +51,9 @@ FocusScope
readonly property real flickableHeight: myFlickable.height

property real contentFlickSize: 100


signal doubleClicked()

Keys.onUpPressed: (event) => { budgeUp(); event.accepted = true; }
Keys.onLeftPressed: (event) => { budgeLeft(); event.accepted = true; }
Expand Down Expand Up @@ -121,6 +123,7 @@ FocusScope
contentHeight: theView.height
contentWidth: theView.width


DataSetView
{
z: -10
Expand All @@ -147,79 +150,17 @@ FocusScope
onSelectionBudgesRight: __JASPDataViewRoot.budgeRight()
}
}
/*

MouseArea
{
id: wheelCatcher
anchors.fill: myFlickable
acceptedButtons: Qt.NoButton
acceptedButtons: Qt.LeftButton
cursorShape: Qt.PointingHandCursor
z: 1000
z: -1000
onDoubleClicked: __JASPDataViewRoot.doubleClicked()
}
*/

signal doubleClicked()

JASPMouseAreaToolTipped
{
id: wheelCatcher
z: 1000
anchors.fill: myFlickable
anchors.leftMargin: theView.rowNumberWidth
anchors.topMargin: theView.headerHeight

toolTipText: __JASPDataViewRoot.doubleClickWorkaround ? qsTr("Double click to edit data") : ""

acceptedButtons: __JASPDataViewRoot.doubleClickWorkaround ? Qt.LeftButton : Qt.NoButton
dragging: myFlickable.dragging
//hoverEnabled: !flickableInteractive

property real lastTimeClicked: -1
property real doubleClickTime: 400

onPressed: (mouse)=>
{
//console.log("doubleclick workaround pressed")
if(!__JASPDataViewRoot.doubleClickWorkaround)
{
mouse.accepted = false;
return;
}

var curTime = new Date().getTime()

if(lastTimeClicked === -1 || curTime - lastTimeClicked > doubleClickTime)
{
// console.log("doubleclick workaround pressed set time")
lastTimeClicked = curTime
mouse.accepted = false
}
else
{
// console.log("doubleclick workaround activated")
lastTimeClicked = -1
__JASPDataViewRoot.doubleClicked()
}
}

onWheel: (wheel)=>
{
if(wheel.angleDelta.y == 120)
{
if(wheel.modifiers & Qt.ShiftModifier) horiScroller.scrollUp()
else vertiScroller.scrollUp()
}
else if(wheel.angleDelta.y == -120)
{
if(wheel.modifiers & Qt.ShiftModifier) horiScroller.scrollDown()
else vertiScroller.scrollDown()
}
else
wheel.accepted = false;
}
}

JASPScrollBar
{
id: vertiScroller;
Expand Down
4 changes: 1 addition & 3 deletions Desktop/components/JASP/Widgets/LabelEditorWindow.qml
Original file line number Diff line number Diff line change
Expand Up @@ -43,9 +43,7 @@ FocusScope
expandDataSet: false
toolTip: qsTr("Edit the labels here or choose which values should be filtered out.")
mouseArea.enabled: false
mouseArea.visible: false
//flickableInteractive: false
doubleClickWorkaround: false
mouseArea.visible: false

Binding
{
Expand Down
166 changes: 122 additions & 44 deletions Desktop/qquick/datasetview.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -247,7 +247,7 @@ void DataSetView::calculateCellSizesAndClear(bool clearStorage)
_storedLineFlags.clear();
_storedDisplayText.clear();

storeAllItems();
storeAllItems();

//if(clearStorage)
// clearCaches();
Expand Down Expand Up @@ -299,8 +299,8 @@ void DataSetView::calculateCellSizesAndClear(bool clearStorage)

void DataSetView::viewportChangedDelayed()
{
_delayViewportChangedTimer->start();
//viewportChanged();
//_delayViewportChangedTimer->start();
viewportChanged();
}

void DataSetView::viewportChanged()
Expand All @@ -318,7 +318,7 @@ void DataSetView::viewportChanged()
#endif

determineCurrentViewPortIndices();
storeAllItems();
storeOutOfViewItems();
buildNewLinesAndCreateNewItems();

JASPTIMER_RESUME(DataSetView::updateCalledForRender);
Expand Down Expand Up @@ -358,8 +358,8 @@ void DataSetView::determineCurrentViewPortIndices()
if(_currentViewportColMax == -1)
_currentViewportColMax = _model->columnCount();

_currentViewportColMin = std::max(0, std::min(_model->columnCount(), _currentViewportColMin - _viewportMargin));
_currentViewportColMax = std::max(0, std::min(_model->columnCount(), _currentViewportColMax + _viewportMargin));
_currentViewportColMin = std::max(0, std::min(_model->columnCount(), _currentViewportColMin - _viewportMargin));
_currentViewportColMax = std::max(0, std::min(_model->columnCount(), _currentViewportColMax + _viewportMargin));

_currentViewportRowMin = std::max(0, std::min(_model->rowCount(), qRound(leftTop.y() / _dataRowsMaxHeight) - (1 + _viewportMargin)));
_currentViewportRowMax = std::max(0, std::min(_model->rowCount(), qRound(rightBottom.y() / _dataRowsMaxHeight) + (1 + _viewportMargin)));
Expand All @@ -374,44 +374,122 @@ void DataSetView::determineCurrentViewPortIndices()

void DataSetView::storeAllItems()
{
JASPTIMER_SCOPE(DataSetView::storeAllItems);

for(auto & subVec : _cellTextItems)
{
for(auto & intTextItem : subVec.second)
{
if(intTextItem.second)
{
intTextItem.second->item->setVisible(false);

if (_cacheItems) _textItemStorage.push(intTextItem.second);
else delete intTextItem.second;
}
}
subVec.second.clear();
}

_cellTextItems.clear();

for(auto & intItem : _columnHeaderItems)
{
intItem.second->item->setVisible(false);

if (_cacheItems) _columnHeaderStorage.push(intItem.second);
else delete intItem.second;
}

_columnHeaderItems.clear();

for(auto & intItem : _rowNumberItems)
{
intItem.second->item->setVisible(false);

if (_cacheItems) _rowNumberStorage.push(intItem.second);
else delete intItem.second;
}

_rowNumberItems.clear();
JASPTIMER_SCOPE(DataSetView::storeAllItems);

for(auto & subVec : _cellTextItems)
{
for(auto & intTextItem : subVec.second)
{
if(intTextItem.second)
{
intTextItem.second->item->setVisible(false);

if (_cacheItems) _textItemStorage.push(intTextItem.second);
else delete intTextItem.second;
}
}
subVec.second.clear();
}

_cellTextItems.clear();

for(auto & intItem : _columnHeaderItems)
{
intItem.second->item->setVisible(false);

if (_cacheItems) _columnHeaderStorage.push(intItem.second);
else delete intItem.second;
}

_columnHeaderItems.clear();

for(auto & intItem : _rowNumberItems)
{
intItem.second->item->setVisible(false);

if (_cacheItems) _rowNumberStorage.push(intItem.second);
else delete intItem.second;
}

_rowNumberItems.clear();
}

void DataSetView::storeOutOfViewItems()
{
JASPTIMER_SCOPE(DataSetView::storeOutOfViewItems);

{
ItemCxsByColRow cleanList;

for(auto & subVec : _cellTextItems)
{
for(auto & intTextItem : subVec.second)
{
if(intTextItem.second)
{
int col = subVec.first,
row = intTextItem.first;

if(col < _currentViewportColMin || col > _currentViewportColMax || row < _currentViewportRowMin || row > _currentViewportRowMax)
{
intTextItem.second->item->setVisible(false);

if (_cacheItems) _textItemStorage.push(intTextItem.second);
else delete intTextItem.second;
}
else
{
cleanList[col][row] = intTextItem.second;
}
}
}
}

_cellTextItems = cleanList ;
}

{
ItemCxsByIndex cleanList;

for(auto & intItem : _columnHeaderItems)
{
int col = intItem.first;

if(col < _currentViewportColMin || col > _currentViewportColMax)
{
intItem.second->item->setVisible(false);

if (_cacheItems) _columnHeaderStorage.push(intItem.second);
else delete intItem.second;
}
else
cleanList[col] = intItem.second;
}

_columnHeaderItems = cleanList;
}


{
ItemCxsByIndex cleanList;

for(auto & intItem : _rowNumberItems)
{
int row = intItem.first;

if(row < _currentViewportRowMin || row > _currentViewportRowMax)
{
intItem.second->item->setVisible(false);

if (_cacheItems) _rowNumberStorage.push(intItem.second);
else delete intItem.second;
}
else
cleanList[row] = intItem.second;
}

_rowNumberItems = cleanList;
}
}

void DataSetView::addLine(float x0, float y0, float x1, float y1)
Expand Down
10 changes: 7 additions & 3 deletions Desktop/qquick/datasetview.h
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,9 @@ struct ItemContextualized
QQmlContext * context = nullptr;
};

typedef std::map<int, std::map<int, ItemContextualized *>> ItemCxsByColRow;
typedef std::map<int, ItemContextualized *> ItemCxsByIndex;

/// Custom QQuickItem to render data tables witch caching and only displaying the necessary cells and lines
/// Supports scaling the data into millions of columns and rows without any noticable slowdowns (the model could slow it down though)
/// Contains custom rendering code for the lines to make sure they are always a single pixel wide.
Expand Down Expand Up @@ -275,7 +278,8 @@ public slots:
void _copy(QPoint where, bool clear);
void calculateCellSizesAndClear(bool clearStorage);
void determineCurrentViewPortIndices();
void storeAllItems();
void storeAllItems();
void storeOutOfViewItems();
void buildNewLinesAndCreateNewItems();
void columnIndexSelectedApply(int columnIndex, std::function<void (int)> applyThis);
void columnIndexSelectedApply(int columnIndex, std::function<void (intset)> applyThis);
Expand Down Expand Up @@ -321,9 +325,9 @@ public slots:
std::stack<ItemContextualized*> _textItemStorage,
_rowNumberStorage,
_columnHeaderStorage;
std::map<int, ItemContextualized *> _rowNumberItems,
ItemCxsByIndex _rowNumberItems,
_columnHeaderItems;
std::map<int, std::map<int, ItemContextualized *>> _cellTextItems; //[col][row]
ItemCxsByColRow _cellTextItems; //[col][row]
std::vector<float> _lines;
QQuickItem * _leftTopItem = nullptr,
* _extraColumnItem = nullptr,
Expand Down

0 comments on commit 5535a4a

Please sign in to comment.