How can I center QCheckBox in QTableView?
-
@JonB, yeees, I understood this and I was using
Qt::TextAlignmentRole
and returningQt::AlignCenter
, but for some reason it's not aligned :(
wrote on 12 Nov 2021, 13:57 last edited byThis post is deleted! -
@CuriousPan
I do not know about the behaviour of the delegate. But if you want to know to know whether it is being "triggered" and recognises the role in question put in aqDebug()
statement (in the delegate) to find out.wrote on 12 Nov 2021, 13:58 last edited by@JonB, yes, it's defenitely triggered.
-
@JonB, yes, it's defenitely triggered.
wrote on 12 Nov 2021, 14:04 last edited by@CuriousPan
Find all your occurrences ofQStyle::alignedRect(opt.direction, index.data(Qt::TextAlignmentRole).value<Qt::Alignment>(), rect.size(), opt.rect)
and
qDebug() << index.data(Qt::TextAlignmentRole).value<Qt::Alignment>()
. -
@CuriousPan
Find all your occurrences ofQStyle::alignedRect(opt.direction, index.data(Qt::TextAlignmentRole).value<Qt::Alignment>(), rect.size(), opt.rect)
and
qDebug() << index.data(Qt::TextAlignmentRole).value<Qt::Alignment>()
.wrote on 12 Nov 2021, 14:07 last edited by@JonB, it always retruns
QFlags<Qt::AlignmentFlag>() 1
which isQt::DecorationRole
, right? -
@JonB, it always retruns
QFlags<Qt::AlignmentFlag>() 1
which isQt::DecorationRole
, right?@CuriousPan said in How can I center QCheckBox in QTableView?:
it always retruns QFlagsQt::AlignmentFlag() 1 which is Qt::DecorationRole, right
the
Qt::AlignmentFlag
flags/enum doesnt containQt::DecorationRole
, so no
https://doc.qt.io/qt-5/qt.html#AlignmentFlag-enum -
@CuriousPan said in How can I center QCheckBox in QTableView?:
it always retruns QFlagsQt::AlignmentFlag() 1 which is Qt::DecorationRole, right
the
Qt::AlignmentFlag
flags/enum doesnt containQt::DecorationRole
, so no
https://doc.qt.io/qt-5/qt.html#AlignmentFlag-enumwrote on 12 Nov 2021, 14:15 last edited by@raven-worx, oh, I see. You're right. Anyway, why is that so?
-
@CuriousPan said in How can I center QCheckBox in QTableView?:
it always retruns QFlagsQt::AlignmentFlag() 1 which is Qt::DecorationRole, right
the
Qt::AlignmentFlag
flags/enum doesnt containQt::DecorationRole
, so no
https://doc.qt.io/qt-5/qt.html#AlignmentFlag-enumwrote on 12 Nov 2021, 14:20 last edited by@raven-worx, wait! I confused you and me. This '1' is my custom printout. So what you suggested printing just gives following output:
QFlags<Qt::AlignmentFlag>()
-
@raven-worx, wait! I confused you and me. This '1' is my custom printout. So what you suggested printing just gives following output:
QFlags<Qt::AlignmentFlag>()
wrote on 12 Nov 2021, 14:26 last edited by JonB 11 Dec 2021, 14:26@CuriousPan
Qt::AlignLeft 0x0001 Aligns with the left edge.
So this value
1
is left alignment, just as per your picture, and no kind of centering specified, which would have value4
. -
@CuriousPan
Qt::AlignLeft 0x0001 Aligns with the left edge.
So this value
1
is left alignment, just as per your picture, and no kind of centering specified, which would have value4
.wrote on 12 Nov 2021, 14:28 last edited by@JonB, yeah, it is, but as I said, no numbers are printed.
-
@JonB, it always retruns
QFlags<Qt::AlignmentFlag>() 1
which isQt::DecorationRole
, right?wrote on 12 Nov 2021, 14:29 last edited by JonB 11 Dec 2021, 14:30@CuriousPan said in How can I center QCheckBox in QTableView?:
@JonB, it always retruns QFlagsQt::AlignmentFlag() 1 which is Qt::DecorationRole, right?
That's what you wrote. See that
1
? Can you please concentrate on one thing at a time. -
@CuriousPan said in How can I center QCheckBox in QTableView?:
@JonB, it always retruns QFlagsQt::AlignmentFlag() 1 which is Qt::DecorationRole, right?
That's what you wrote. See that
1
? Can you please concentrate on one thing at a time.wrote on 12 Nov 2021, 14:30 last edited by@JonB, yep, I can. I'm really sorry for confusing you. No
1
is printed, it's just my mistake. -
@JonB, yep, I can. I'm really sorry for confusing you. No
1
is printed, it's just my mistake.wrote on 12 Nov 2021, 14:34 last edited by@CuriousPan
So that would be the value for left-align. Either you are not setting or returning the desired "center" flag on your item for theQt::TextAlignmentRole
--- you have to do that if you want it centered, that's what the code does --- or you are not looking at the right item/index. -
@CuriousPan
So that would be the value for left-align. Either you are not setting or returning the desired "center" flag on your item for theQt::TextAlignmentRole
--- you have to do that if you want it centered, that's what the code does --- or you are not looking at the right item/index.wrote on 12 Nov 2021, 14:41 last edited by CuriousPan 11 Dec 2021, 14:42@JonB, I guess you're right, but, as I showed on this screenshot:
I'm using the correct role and column is defenitely correct (checked usingqDebug()
). -
@JonB, I guess you're right, but, as I showed on this screenshot:
I'm using the correct role and column is defenitely correct (checked usingqDebug()
).wrote on 12 Nov 2021, 14:46 last edited by JonB 11 Dec 2021, 14:46- Print out
index.column()
in the delegate. - Print out
RecurrentColumn
. - Put a
qDebug()
just abovereturn Qt::AlignCenter
in your "screenshot" to make sure it's being hit. - Please don't paste code as screenshots, paste it as code. Show where you have that code and what is above the extract you show.
- Print out
-
- Print out
index.column()
in the delegate. - Print out
RecurrentColumn
. - Put a
qDebug()
just abovereturn Qt::AlignCenter
in your "screenshot" to make sure it's being hit. - Please don't paste code as screenshots, paste it as code. Show where you have that code and what is above the extract you show.
wrote on 12 Nov 2021, 15:01 last edited by CuriousPan 11 Dec 2021, 15:05index.column()
in the delegate has the proper number.4
in my case as long as it is 4th (starting from 0) column in the table view.- What do you mean by printing
RecurrentColumn
?
//checking other roles } else if (index.isValid() && role == Qt::TextAlignmentRole) { switch (index.column()) { case RecurrentColumn: qDebug() << "Hit"; return Qt::AlignCenter; case TotalColumn: return {Qt::AlignRight | Qt::AlignVCenter}; case PlnTotalColumn: return {Qt::AlignRight | Qt::AlignVCenter}; return Qt::AlignCenter; } } // "Hit" is getting printed.
- Okay, will try to value your time and effort :)
- Print out
-
index.column()
in the delegate has the proper number.4
in my case as long as it is 4th (starting from 0) column in the table view.- What do you mean by printing
RecurrentColumn
?
//checking other roles } else if (index.isValid() && role == Qt::TextAlignmentRole) { switch (index.column()) { case RecurrentColumn: qDebug() << "Hit"; return Qt::AlignCenter; case TotalColumn: return {Qt::AlignRight | Qt::AlignVCenter}; case PlnTotalColumn: return {Qt::AlignRight | Qt::AlignVCenter}; return Qt::AlignCenter; } } // "Hit" is getting printed.
- Okay, will try to value your time and effort :)
wrote on 12 Nov 2021, 15:50 last edited by CuriousPan 11 Dec 2021, 15:51@CuriousPan I have fixed the issue.
I used pretty dirty, but working trick: setQt::AlignedCenter
right in the delegate:void CenteredCheckBoxDelegate::paint(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const { QStyleOptionViewItem opt = option; const QWidget *widget = option.widget; initStyleOption(&opt, index); QStyle *style = opt.widget ? opt.widget->style() : QApplication::style(); style->drawPrimitive(QStyle::PE_PanelItemViewItem, &opt, painter, widget); if (opt.features & QStyleOptionViewItem::HasCheckIndicator) { switch (opt.checkState) { case Qt::Unchecked: opt.state |= QStyle::State_Off; break; case Qt::PartiallyChecked: opt.state |= QStyle::State_NoChange; break; case Qt::Checked: opt.state |= QStyle::State_On; break; } auto rect = style->subElementRect(QStyle::SE_ItemViewItemCheckIndicator, &opt, widget); opt.rect = QStyle::alignedRect(opt.direction, Qt::AlignCenter/*index.data(Qt::TextAlignmentRole).value<Qt::Alignment>()*/, rect.size(), opt.rect); opt.state = opt.state & ~QStyle::State_HasFocus; style->drawPrimitive(QStyle::PE_IndicatorItemViewItemCheck, &opt, painter, widget); } else if (!opt.icon.isNull()) { // draw the icon QRect iconRect = style->subElementRect(QStyle::SE_ItemViewItemDecoration, &opt, widget); iconRect = QStyle::alignedRect(opt.direction, Qt::AlignCenter/*index.data(Qt::TextAlignmentRole).value<Qt::Alignment>()*/, iconRect.size(), opt.rect); QIcon::Mode mode = QIcon::Normal; if (!(opt.state & QStyle::State_Enabled)) mode = QIcon::Disabled; else if (opt.state & QStyle::State_Selected) mode = QIcon::Selected; QIcon::State state = opt.state & QStyle::State_Open ? QIcon::On : QIcon::Off; opt.icon.paint(painter, iconRect, opt.decorationAlignment, mode, state); } else { QStyledItemDelegate::paint(painter, option, index); } } bool CenteredCheckBoxDelegate::editorEvent(QEvent *event, QAbstractItemModel *model, const QStyleOptionViewItem &option, const QModelIndex &index) { Q_ASSERT(event); Q_ASSERT(model); // make sure that the item is checkable Qt::ItemFlags flags = model->flags(index); if (!(flags & Qt::ItemIsUserCheckable) || !(option.state & QStyle::State_Enabled) || !(flags & Qt::ItemIsEnabled)) return false; // make sure that we have a check state QVariant value = index.data(Qt::CheckStateRole); if (!value.isValid()) return false; const QWidget *widget = option.widget; QStyle *style = option.widget ? widget->style() : QApplication::style(); // make sure that we have the right event type if ((event->type() == QEvent::MouseButtonRelease) || (event->type() == QEvent::MouseButtonDblClick) || (event->type() == QEvent::MouseButtonPress)) { QStyleOptionViewItem viewOpt(option); initStyleOption(&viewOpt, index); QRect checkRect = style->subElementRect(QStyle::SE_ItemViewItemCheckIndicator, &viewOpt, widget); checkRect = QStyle::alignedRect(viewOpt.direction, Qt::AlignCenter/*index.data(Qt::TextAlignmentRole).value<Qt::Alignment>()*/, checkRect.size(), viewOpt.rect); QMouseEvent *me = static_cast<QMouseEvent *>(event); if (me->button() != Qt::LeftButton || !checkRect.contains(me->pos())) return false; if ((event->type() == QEvent::MouseButtonPress) || (event->type() == QEvent::MouseButtonDblClick)) return true; } else if (event->type() == QEvent::KeyPress) { if (static_cast<QKeyEvent *>(event)->key() != Qt::Key_Space && static_cast<QKeyEvent *>(event)->key() != Qt::Key_Select) return false; } else { return false; } Qt::CheckState state = static_cast<Qt::CheckState>(value.toInt()); if (flags & Qt::ItemIsUserTristate) state = ((Qt::CheckState)((state + 1) % 3)); else state = (state == Qt::Checked) ? Qt::Unchecked : Qt::Checked; return model->setData(index, state, Qt::CheckStateRole); }
Thanks everyone who took part in the discussion.
19/25