Seite 1 von 1

Probleme mit dem eigenen QItemDelegate

Verfasst: 6. März 2009 10:01
von bar0n
Hallo alle zusammen,

ich habe für eine TableView ein eigenes Model geschrieben und eine eigenes Delegate. Nun hab ich zwei Fragen zur paint methode:

Code: Alles auswählen

void DataDelegate::paint(QPainter *painter, const QStyleOptionViewItem &option
                                  , const QModelIndex &index) const
{
  // show a check box for visibility column
  if(index.column() == m_VisibilityColumnIndex)
  {
    //Get item data
    bool visibility = index.data(Qt::UserRole).toBool();
    painter->save();
    // draw item data as CheckBox
    if (option.state & QStyle::State_Selected)
      painter->fillRect(option.rect, option.palette.highlight());

    const QStyle *style = QApplication::style();
    QStyleOptionButton opt;
    opt.state |= visibility ? QStyle::State_On : QStyle::State_Off;
    opt.state |= QStyle::State_Enabled;
    opt.rect = option.rect;

    // draw item data as CheckBox
    style->drawControl(QStyle::CE_CheckBox,&opt,painter);
    painter->restore();
  }
  // for everything else paint the usual way
  else
  {
    QItemDelegate::paint(painter, option, index);
  }
}
Ok also: Ich zeichne eine CheckBox für einen Bool-Wert. Nun die Fragen:
1. Wie kann ich das Ding am elegantesten zentrieren?
2. Mit

Code: Alles auswählen

if (option.state & QStyle::State_Selected)
painter->fillRect(option.rect, option.palette.highlight());
frage ich ab ob die Zeile selektiert ist und wenn ja, dann highlighte ich den Hintergrund. Jetzt gibt es aber noch eine Unschönheit: Wenn die Zeile ausgewählt is, die Tabelle aber nicht den Fokus hat, dann erhält die Zeile standardmäßig dunkelgraue Unterlegung, ist also im Zustand "selektiert, aber nicht fokussiert". WIe kann ich das richtig zeichnen? Im Moment ist der Rest der Zeile nämlich dunkelgrau und meine eine Checkbox-Tabellenzelle dunkelblau (highlighted) und das sieht scheisse aus.

Zur 3. und letzten Frage: Ich muss natürlich den Editor, den ich dann zeichne auch zentrieren. Das muss irgendwie gehen in der updateEditorGeometry()-Methode:

Code: Alles auswählen

void DataDelegate::updateEditorGeometry( QWidget * editor, const QStyleOptionViewItem option, const QModelIndex & index ) const
{
  editor->setGeometry(opt.rect);
}
Hab aber keine Ahnung wie ich das machen soll.
Bin kein Qt-Newbie, aber im manuellen Zeichnen von Widgets hab ich keine Erfahrung.Danke für jede Antwort!

Verfasst: 6. März 2009 10:16
von MiKla
zu 1) ich habe das so gemacht:

Code: Alles auswählen

     QStyleOptionViewItemV2 opt = QItemDelegate::setOptions(index, option);
     QStyleOptionButton opt1;

            opt1.state |= index.data().toBool() ? QStyle::State_On : QStyle::State_Off;
            const QStyle *style = QApplication::style();
            const int indicatorWidth = style->pixelMetric(QStyle::PM_IndicatorWidth, &opt);
            const int indicatorHeight = style->pixelMetric(QStyle::PM_IndicatorHeight, &opt);
            opt1.rect = QRect(opt.rect.x()+ opt.rect.width()/2-indicatorWidth/2,
                              opt.rect.y()+ opt.rect.height()/2-indicatorHeight/2,
                              indicatorWidth, indicatorHeight);
            style->drawPrimitive(QStyle::PE_IndicatorCheckBox, &opt1, painter); 
siehe auch: http://www.qtforum.de/forum/viewtopic.p ... t=checkbox

Michael

Verfasst: 6. März 2009 10:36
von bar0n
Ja das hatte ich auch gefunden. Das is nelösung, wollte mal wissen, ob jmd noch ne einfachere lösung kennt. Wenn ich das so mache hab ich aber das Problem 3., dass der editor nicht mittig erscheint. D.h. Doppelklicken in die Zelle erscheint links die Editier-Checkbox und mittig die gezeichnete. Danke trotzdem erstmal.[/b]

Verfasst: 6. März 2009 12:09
von MiKla
Die Lösung habe ich mir aus dem Qt Quellcode raus kopiert. Sollte also nicht sooo schlecht sein :wink:
Ich habe bei mir den Editor für die CheckBox deaktiviert und das Handling über das clicked Signal gemacht:

Code: Alles auswählen

...
QWidget *MyDelegate::createEditor(QWidget *parent,
    const QStyleOptionViewItem &option ,
    const QModelIndex & index ) const
{
    switch(index.column())
    {
        case 0:
        {
			return 0;//checkBox;
...

...
void QScope::tableViewClicked(const QModelIndex &index){
	if (index.isValid()){
		if (index.column()== 0)
			model->setData(index, !index.data().toBool());
	}
}
...
Michael