Skip to content

Commit

Permalink
Corrected broken sort order of numerical columns when using distance …
Browse files Browse the repository at this point in the history
…search #1060
  • Loading branch information
albar965 committed Nov 13, 2023
1 parent 94e0b1a commit 66bab2e
Show file tree
Hide file tree
Showing 3 changed files with 29 additions and 4 deletions.
5 changes: 5 additions & 0 deletions src/search/sqlmodel.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -672,6 +672,11 @@ QVariant SqlModel::defaultDataHandler(int, int, const Column *, const QVariant&,
return QVariant();
}

QVariant SqlModel::rawData(const QModelIndex& index) const
{
return index.isValid() ? QSqlQueryModel::data(index, Qt::DisplayRole) : QVariant();
}

QVariant SqlModel::data(const QModelIndex& index, int role) const
{
if(!index.isValid())
Expand Down
5 changes: 4 additions & 1 deletion src/search/sqlmodel.h
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*****************************************************************************
* Copyright 2015-2020 Alexander Barthel alex@littlenavmap.org
* Copyright 2015-2023 Alexander Barthel alex@littlenavmap.org
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
Expand Down Expand Up @@ -144,6 +144,9 @@ class SqlModel :
/* Fetch and format data for display */
virtual QVariant data(const QModelIndex& index, int role = Qt::DisplayRole) const override;

/* Fetch data without any converts for display role */
QVariant rawData(const QModelIndex& index) const;

/*
* Sets a data callback that is called for each table cell and the given item data roles.
* @param func callback function or method. Use std::bind to create callbacks to non static methods.
Expand Down
23 changes: 20 additions & 3 deletions src/search/sqlproxymodel.cpp
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*****************************************************************************
* Copyright 2015-2020 Alexander Barthel alex@littlenavmap.org
* Copyright 2015-2023 Alexander Barthel alex@littlenavmap.org
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
Expand Down Expand Up @@ -123,6 +123,10 @@ QVariant SqlProxyModel::headerData(int section, Qt::Orientation orientation, int
/* Defines greater and lower than for sorting of the two columns distance and heading */
bool SqlProxyModel::lessThan(const QModelIndex& sourceLeft, const QModelIndex& sourceRight) const
{
// These types can be converted to long long and compared
const static QSet<QVariant::Type> NUMERIC_TYPES({QVariant::Bool, QVariant::Int, QVariant::UInt, QVariant::LongLong, QVariant::ULongLong,
QVariant::Date, QVariant::Time, QVariant::DateTime});

QString leftCol = sourceSqlModel->getColumnName(sourceLeft.column());
QString rightCol = sourceSqlModel->getColumnName(sourceRight.column());

Expand All @@ -141,8 +145,21 @@ bool SqlProxyModel::lessThan(const QModelIndex& sourceLeft, const QModelIndex& s
return headingLeft < headingRight;
}
else
// Let the model do the sorting for other columns
return QSortFilterProxyModel::lessThan(sourceLeft, sourceRight);
{
// Get unmodified (converted to strings) raw data
QVariant leftData = sourceSqlModel->rawData(sourceLeft);
QVariant rightData = sourceSqlModel->rawData(sourceRight);

if(leftData.type() == QVariant::Double && rightData.type() == QVariant::Double)
// Compare float and double numerically
return leftData.toDouble() < rightData.toDouble();
else if(NUMERIC_TYPES.contains(leftData.type()) && NUMERIC_TYPES.contains(rightData.type()))
// Compare bool, int to long long numerically
return leftData.toLongLong() < rightData.toLongLong();
else
// Let the model do the sorting for other columns
return QSortFilterProxyModel::lessThan(sourceLeft, sourceRight);
}
}

/* Returns the formatted data for the "distance" and "heading" column */
Expand Down

0 comments on commit 66bab2e

Please sign in to comment.