pgLab/pglab/ColumnTableModel.cpp
eelke c324daa75b The global function for getting a typename from an oid now supports passing the typmod of a column.
This is used by the list of columns for a table. Works for char, varchar, text and numeric.
2017-12-19 19:33:22 +01:00

190 lines
4.2 KiB
C++

#include "ColumnTableModel.h"
#include "PgDatabaseCatalog.h"
#include "PgAttribute.h"
#include "PgAttributeContainer.h"
#include "PgType.h"
#include "PgTypeContainer.h"
#include "PgIndexContainer.h"
#include "ScopeGuard.h"
#include <QBrush>
void ColumnTableModel::setData(std::shared_ptr<const PgDatabaseCatalog> cat, const PgClass &table)
{
beginResetModel();
SCOPE_EXIT { endResetModel(); };
m_table = table;
m_catalog = cat;
m_columns = cat->attributes()->getColumnsForRelation(table.oid);
// hide system columns
auto si = table.hasoids
? std::remove_if(m_columns.begin(), m_columns.end(),
[](PgAttribute &e) { return e.num <= 0 && e.name != "oid"; })
: std::remove_if(m_columns.begin(), m_columns.end(),
[](PgAttribute &e) { return e.num <= 0; });
// move columns to end and remove them
m_columns.erase(si, m_columns.end());
// sort remaining columns by order in table
std::sort(m_columns.begin(), m_columns.end(),
[] (auto &l, auto &r) -> bool { return l.num < r.num; });
m_indexes = m_catalog->indexes()->getIndexesForTable(table.oid);
std::sort(m_indexes.begin(), m_indexes.end(),
[] (const auto &l, const auto &r) -> bool
{
return l.isprimary > r.isprimary
|| (l.isprimary == r.isprimary && l.indexrelid < r.indexrelid);
});
}
QVariant ColumnTableModel::headerData(int section, Qt::Orientation orientation, int role) const
{
QVariant v;
if (orientation == Qt::Horizontal) {
if (role == Qt::DisplayRole) {
QString c;
if (section >= colCount) {
const auto &tbl_idx = m_indexes[section - colCount];
if (tbl_idx.isprimary)
c = "PK";
else if (tbl_idx.isunique)
c = "UIdx";
else
c = "Idx";
}
else {
switch (section) {
case NameCol:
c = tr("Name");
break;
case TypeCol:
c = tr("Type");
break;
case NullCol:
c = tr("Not null");
break;
case DefaultCol:
c = tr("Default");
break;
case CollationCol:
c = tr("Collation");
break;
}
}
v = c;
}
}
return v;
}
int ColumnTableModel::rowCount(const QModelIndex &/*parent*/) const
{
return m_columns.size();
}
int ColumnTableModel::columnCount(const QModelIndex &/*parent*/) const
{
return colCount + m_indexes.size();
}
Oid ColumnTableModel::getType(int /*column*/) const
{
Oid oid = Pgsql::VARCHAROID;
// switch (column) {
// case TypeCol:
// case NameCol:
// case NullCol:
// case DefaultCol:
// case CollationCol:
// oid = VARCHAROID;
// break;
// c = tr("Collation");
// break;
// }
return oid;
}
QVariant ColumnTableModel::getData(const QModelIndex &index) const
{
QVariant v;
const int row = index.row();
const auto &t = m_columns[row];
const int col = index.column();
if (col >= colCount) {
const auto &tbl_idx = m_indexes[col - colCount];
int i = 1;
for (auto attr : tbl_idx.key) {
if (attr == t.num) {
v = i;
break;
}
++i;
}
}
else {
QString s;
switch (col) {
case NameCol:
s = t.name;
break;
case TypeCol:
s = getTypeDisplayString(*m_catalog, t.typid, t.typmod);
break;
case NullCol:
s = QString::fromStdU16String(t.notnull ? u"\u2713" : u"");
break;
case DefaultCol:
s = t.defaultValue;
break;
case CollationCol:
s = ""; //t.collation;
break;
}
v = s;
}
return v;
}
QVariant ColumnTableModel::data(const QModelIndex &index, int role) const
{
if (role == Qt::ForegroundRole && index.column() == TypeCol) {
QVariant v;
const auto &t = m_columns[index.row()];
auto c = m_catalog->types()->getByKey(t.typid);
switch (c.category) {
case TypCategory::Boolean:
v = QBrush(Qt::darkGreen);
break;
case TypCategory::Numeric:
v = QBrush(Qt::darkBlue);
break;
case TypCategory::DateTime:
case TypCategory::Timespan:
v = QBrush(Qt::darkMagenta);
break;
case TypCategory::String:
v = QBrush(Qt::darkYellow);
break;
case TypCategory::Array:
case TypCategory::Composite:
case TypCategory::Enum:
case TypCategory::Geometric:
case TypCategory::NetworkAddress:
case TypCategory::Pseudo:
case TypCategory::Range:
case TypCategory::UserDefined:
case TypCategory::BitString:
case TypCategory::Unknown:
default:
v = QBrush(Qt::black);
}
return v;
}
return BaseTableModel::data(index, role);
}