Grinchman
23rd June 2011, 03:44
Hello.
I bumped into a problem of adding an item QCheckBox into QComboBox. What I`ve found is the code for creating ItemDelegate for QComboBox, but it makes all of items in QComboBox as QCheckBox. My task is to add just one check box into the list of common combobox`s items...
Here is a code I found:
class CheckBoxList: public QComboBox
{
Q_OBJECT;
public:
CheckBoxList(QWidget *widget = 0);
virtual ~CheckBoxList();
virtual void paintEvent(QPaintEvent *);
void SetDisplayText(QString text);
QString GetDisplayText() const;
private:
QString m_DisplayText;
};
class CheckBoxListDelegate : public QItemDelegate
{
public:
CheckBoxListDelegate(QObject *parent)
: QItemDelegate(parent)
{
;
}
void paint(QPainter *painter, const QStyleOptionViewItem &option,
const QModelIndex &index) const
{
//Get item data
bool value = index.data(Qt::UserRole).toBool();
QString text = index.data(Qt::DisplayRole).toString();
// fill style options with item data
const QStyle *style = QApplication::style();
QStyleOptionButton opt;
opt.state |= value ? QStyle::State_On : QStyle::State_Off;
opt.state |= QStyle::State_Enabled;
opt.text = text;
opt.rect = option.rect;
// draw item data as CheckBox
style->drawControl(QStyle::CE_CheckBox,&opt,painter);
}
QWidget *createEditor(QWidget *parent,
const QStyleOptionViewItem & option ,
const QModelIndex & index ) const
{
// create check box as our editor
QCheckBox *editor = new QCheckBox(parent);
return editor;
}
void setEditorData(QWidget *editor,
const QModelIndex &index) const
{
//set editor data
QCheckBox *myEditor = static_cast<QCheckBox*>(editor);
myEditor->setText(index.data(Qt::DisplayRole).toString());
myEditor->setChecked(index.data(Qt::UserRole).toBool());
}
void setModelData(QWidget *editor, QAbstractItemModel *model,
const QModelIndex &index) const
{
//get the value from the editor (CheckBox)
QCheckBox *myEditor = static_cast<QCheckBox*>(editor);
bool value = myEditor->isChecked();
//set model data
QMap<int,QVariant> data;
data.insert(Qt::DisplayRole,myEditor->text());
data.insert(Qt::UserRole,value);
model->setItemData(index,data);
}
};
CheckBoxList::CheckBoxList(QWidget *widget )
:QComboBox(widget),m_DisplayText("")
{
// set delegate items view
view()->setItemDelegate(new CheckBoxListDelegate(this));
// Enable editing on items view
view()->setEditTriggers(QAbstractItemView::CurrentChanged) ;
}
CheckBoxList::~CheckBoxList()
{
;
}
void CheckBoxList::paintEvent(QPaintEvent *)
{
QStylePainter painter(this);
painter.setPen(palette().color(QPalette::Text));
// draw the combobox frame, focusrect and selected etc.
QStyleOptionComboBox opt;
initStyleOption(&opt);
// if no display text been set , use "..." as default
if(m_DisplayText.isNull())
opt.currentText = "...";
else
opt.currentText = m_DisplayText;
painter.drawComplexControl(QStyle::CC_ComboBox, opt);
// draw the icon and text
painter.drawControl(QStyle::CE_ComboBoxLabel, opt);
}
void CheckBoxList::SetDisplayText(QString text)
{
m_DisplayText = text;
}
QString CheckBoxList::GetDisplayText() const
{
return m_DisplayText;
}
Is anyone have thoughts how to improve this code to get possibility for adding into QComboBox 2 types of items: QCheckBox and common QComboBox items?
Or there is some other ways to achieve such behaviour?
I bumped into a problem of adding an item QCheckBox into QComboBox. What I`ve found is the code for creating ItemDelegate for QComboBox, but it makes all of items in QComboBox as QCheckBox. My task is to add just one check box into the list of common combobox`s items...
Here is a code I found:
class CheckBoxList: public QComboBox
{
Q_OBJECT;
public:
CheckBoxList(QWidget *widget = 0);
virtual ~CheckBoxList();
virtual void paintEvent(QPaintEvent *);
void SetDisplayText(QString text);
QString GetDisplayText() const;
private:
QString m_DisplayText;
};
class CheckBoxListDelegate : public QItemDelegate
{
public:
CheckBoxListDelegate(QObject *parent)
: QItemDelegate(parent)
{
;
}
void paint(QPainter *painter, const QStyleOptionViewItem &option,
const QModelIndex &index) const
{
//Get item data
bool value = index.data(Qt::UserRole).toBool();
QString text = index.data(Qt::DisplayRole).toString();
// fill style options with item data
const QStyle *style = QApplication::style();
QStyleOptionButton opt;
opt.state |= value ? QStyle::State_On : QStyle::State_Off;
opt.state |= QStyle::State_Enabled;
opt.text = text;
opt.rect = option.rect;
// draw item data as CheckBox
style->drawControl(QStyle::CE_CheckBox,&opt,painter);
}
QWidget *createEditor(QWidget *parent,
const QStyleOptionViewItem & option ,
const QModelIndex & index ) const
{
// create check box as our editor
QCheckBox *editor = new QCheckBox(parent);
return editor;
}
void setEditorData(QWidget *editor,
const QModelIndex &index) const
{
//set editor data
QCheckBox *myEditor = static_cast<QCheckBox*>(editor);
myEditor->setText(index.data(Qt::DisplayRole).toString());
myEditor->setChecked(index.data(Qt::UserRole).toBool());
}
void setModelData(QWidget *editor, QAbstractItemModel *model,
const QModelIndex &index) const
{
//get the value from the editor (CheckBox)
QCheckBox *myEditor = static_cast<QCheckBox*>(editor);
bool value = myEditor->isChecked();
//set model data
QMap<int,QVariant> data;
data.insert(Qt::DisplayRole,myEditor->text());
data.insert(Qt::UserRole,value);
model->setItemData(index,data);
}
};
CheckBoxList::CheckBoxList(QWidget *widget )
:QComboBox(widget),m_DisplayText("")
{
// set delegate items view
view()->setItemDelegate(new CheckBoxListDelegate(this));
// Enable editing on items view
view()->setEditTriggers(QAbstractItemView::CurrentChanged) ;
}
CheckBoxList::~CheckBoxList()
{
;
}
void CheckBoxList::paintEvent(QPaintEvent *)
{
QStylePainter painter(this);
painter.setPen(palette().color(QPalette::Text));
// draw the combobox frame, focusrect and selected etc.
QStyleOptionComboBox opt;
initStyleOption(&opt);
// if no display text been set , use "..." as default
if(m_DisplayText.isNull())
opt.currentText = "...";
else
opt.currentText = m_DisplayText;
painter.drawComplexControl(QStyle::CC_ComboBox, opt);
// draw the icon and text
painter.drawControl(QStyle::CE_ComboBoxLabel, opt);
}
void CheckBoxList::SetDisplayText(QString text)
{
m_DisplayText = text;
}
QString CheckBoxList::GetDisplayText() const
{
return m_DisplayText;
}
Is anyone have thoughts how to improve this code to get possibility for adding into QComboBox 2 types of items: QCheckBox and common QComboBox items?
Or there is some other ways to achieve such behaviour?