22 #include <QMouseEvent>
25 #include <QAbstractItemView>
29 : QStandardItemModel( 0, 1, parent )
35 return QStandardItemModel::flags( index ) | Qt::ItemIsUserCheckable;
40 QVariant value = QStandardItemModel::data( index, role );
42 if ( index.isValid() && role == Qt::CheckStateRole && !value.isValid() )
44 value = Qt::Unchecked;
52 bool ok = QStandardItemModel::setData( index, value, role );
54 if ( ok && role == Qt::CheckStateRole )
59 emit dataChanged( index, index );
65 : QStyledItemDelegate( parent )
71 QStyleOptionViewItem &nonConstOpt =
const_cast<QStyleOptionViewItem &
>( option );
72 nonConstOpt.showDecorationSelected =
false;
73 QStyledItemDelegate::paint( painter, nonConstOpt, index );
80 , mSeparator( QStringLiteral(
", " ) )
85 QLineEdit *lineEdit =
new QLineEdit(
this );
86 lineEdit->setReadOnly(
true );
87 QPalette
pal = qApp->palette();
88 pal.setBrush( QPalette::Base,
pal.button() );
89 lineEdit->setPalette(
pal );
90 setLineEdit( lineEdit );
91 lineEdit->installEventFilter(
this );
92 lineEdit->setContextMenuPolicy( Qt::CustomContextMenu );
95 mContextMenu =
new QMenu(
this );
96 mSelectAllAction = mContextMenu->addAction( tr(
"Select All" ) );
97 mDeselectAllAction = mContextMenu->addAction( tr(
"Deselect All" ) );
101 view()->viewport()->installEventFilter(
this );
102 view()->setContextMenuPolicy( Qt::CustomContextMenu );
105 connect(
model(), &QStandardItemModel::rowsInserted,
this, [ = ](
const QModelIndex &,
int,
int ) { updateDisplayText(); } );
106 connect(
model(), &QStandardItemModel::rowsRemoved,
this, [ = ](
const QModelIndex &,
int,
int ) { updateDisplayText(); } );
107 connect(
model(), &QStandardItemModel::dataChanged,
this, [ = ](
const QModelIndex &,
const QModelIndex &,
const QVector< int > & ) { updateDisplayText(); } );
131 if ( mDefaultText != text )
140 QComboBox::addItem( text, userData );
148 if (
auto *lModel =
model() )
150 QModelIndex index = lModel->index( 0, modelColumn(), rootModelIndex() );
151 QModelIndexList indexes = lModel->match( index, Qt::CheckStateRole, Qt::Checked, -1, Qt::MatchExactly );
152 const auto constIndexes = indexes;
153 for (
const QModelIndex &index : constIndexes )
155 items += index.data().toString();
166 if (
auto *lModel =
model() )
168 QModelIndex index = lModel->index( 0, modelColumn(), rootModelIndex() );
169 QModelIndexList indexes = lModel->match( index, Qt::CheckStateRole, Qt::Checked, -1, Qt::MatchExactly );
170 const auto constIndexes = indexes;
171 for (
const QModelIndex &index : constIndexes )
173 data += index.data( Qt::UserRole ).toString();
182 return static_cast<Qt::CheckState
>( itemData( index, Qt::CheckStateRole ).toInt() );
187 setItemData( index, state, Qt::CheckStateRole );
192 QVariant value = itemData( index, Qt::CheckStateRole );
193 if ( value.isValid() )
195 Qt::CheckState state =
static_cast<Qt::CheckState
>( value.toInt() );
196 setItemData( index, ( state == Qt::Unchecked ? Qt::Checked : Qt::Unchecked ), Qt::CheckStateRole );
204 QComboBox::hidePopup();
213 mContextMenu->exec( QCursor::pos() );
218 blockSignals(
true );
219 for (
int i = 0; i < count(); i++ )
221 setItemData( i, Qt::Checked, Qt::CheckStateRole );
223 blockSignals(
false );
224 updateCheckedItems();
229 blockSignals(
true );
230 for (
int i = 0; i < count(); i++ )
232 setItemData( i, Qt::Unchecked, Qt::CheckStateRole );
234 blockSignals(
false );
235 updateCheckedItems();
240 if (
object == lineEdit() )
242 if ( event->type() == QEvent::MouseButtonPress &&
static_cast<QMouseEvent *
>( event )->button() == Qt::LeftButton &&
object == lineEdit() )
248 else if ( ( event->type() == QEvent::MouseButtonPress || event->type() == QEvent::MouseButtonRelease )
249 &&
object == view()->viewport() )
253 if ( event->type() == QEvent::MouseButtonRelease &&
static_cast<QMouseEvent *
>( event )->button() == Qt::RightButton )
258 if ( event->type() == QEvent::MouseButtonRelease )
260 QModelIndex index = view()->indexAt(
static_cast<QMouseEvent *
>( event )->pos() );
261 if ( index.isValid() )
264 QStandardItem *item = myModel->itemFromIndex( index );
265 item->checkState() == Qt::Checked ? item->setCheckState( Qt::Unchecked ) : item->setCheckState( Qt::Checked );
271 return QComboBox::eventFilter(
object, event );
276 const auto constItems = items;
277 for (
const QString &text : constItems )
279 const int index = findText( text );
282 updateCheckedItems();
287 QComboBox::resizeEvent( event );
291 void QgsCheckableComboBox::updateCheckedItems()
298 void QgsCheckableComboBox::updateDisplayText()
302 if ( items.isEmpty() )
308 text = items.join( mSeparator );
311 QRect rect = lineEdit()->rect();
312 QFontMetrics fontMetrics( font() );
313 text = fontMetrics.elidedText( text, Qt::ElideRight, rect.width() );