2016-03-25 1 views
0

J'ai passé la moitié de la journée à essayer de résoudre le problème de personnalisation du comportement de QListWidget: lorsque vous utilisez le bouton gauche de la souris et déplace le curseur, le contenu de ListWidget défile est déplacé vers un autre élément qui apparaît sous le curseur de la souris. Je suis d'accord avec le défilement, mais je veux éviter de sélectionner tous les éléments qui en découlent, car cela provoque un fonctionnement rapide dans mon programme. Enfin, j'aimerais que le contenu de la liste défile lorsque vous appuyez sur la souris et que vous vous déplaciez, mais sélectionnez uniquement les éléments en cliquant directement dessus. Drag-n-drop est désactivé pour cette liste (qui est le comportement par défaut) et il devrait être; J'ai essayé de le désactiver explicitement: aucun changement.Désactiver la sélection automatique des éléments dans QListWidget sur click + glisser

J'ai lu tous les documents disponibles sur les classes liées à Qt comme QListWidget, QListWidgetItem, QListView, vous l'appelez! Je ai essayé de donner un sens au code source pour ces widgets; déterré StackOverflow et Google ... mais malheureusement aucun résultat :(

est ici tout le code correspondant pour mon QListWidget: sélection simple, rien d'extraordinaire:

QListWidget* categoryListWidget; 
... 
categoryListWidget = new QListWidget(); 
categoryListWidget->move(offsetX, offsetY); 
categoryListWidget->setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff); 
categoryListWidget->setSelectionMode(QAbstractItemView::SingleSelection); 
categoryListWidget->setFocusPolicy(Qt::NoFocus); 
categoryListWidget->setStyleSheet(listQSS); 
... 
categoryListWidget->clear(); 
new QListWidgetItem(tr("1 - Sample Category 1"), categoryListWidget); 
new QListWidgetItem(tr("2 - Sample Category 2"), categoryListWidget); 
new QListWidgetItem(tr("3 - Sample Category 3 with a very long name"), categoryListWidget); 
new QListWidgetItem(tr("4 - Sample Category 4"), categoryListWidget); 

C++/Qt 5.5, si c'est en quelque sorte pertinent, à la fois . Win et Mac partagent le même comportement

+0

Avez-vous essayé d'utiliser la fonction eventFilter pour filtrer l'événement qui cause des problèmes? – user3147395

+0

De quel événement parlez-vous? Il y a la souris Press, mouseMove et mouseRelease, combinaison classique. Je m'abstiendrais d'écrire ma propre version personnalisée de ListWidget s'il y avait un moyen simple de garantir son comportement (ce que je n'ai pas réussi à trouver). Avant celui-ci j'ai fait 4 autres personnalisations dans le même ListWidget, chacun d'entre eux prenait 2h chacun pour parcourir docs, samples, etc. et résultait en une ligne de code: mettre ce drapeau ou changer ce paramètre. J'espère vraiment trouver quelque chose de similaire. –

+0

Désolé, je ne connais pas de drapeau qui implémentera ce comportement, mais je n'ai pas beaucoup d'expérience avec ListWidgets, donc il y a peut-être un drapeau que je ne connais pas. – user3147395

Répondre

1

au nom de celui qui trébuche sur la même question, voici ma solution: sous-classe QListWidget et faire la classe enfant ignorer les événements mouseMove lorsque LeftButton est pressé

tête.

class QtListWidget: public QListWidget 
{ // QListWidget clone that suppresses item selection on mouse click+drag 
private: 
    bool mousePressed; 
public: 
    QtListWidget():QListWidget(), mousePressed(false) {} 
protected: 
    virtual void mousePressEvent(QMouseEvent *event); 
    virtual void mouseMoveEvent(QMouseEvent *event); 
    virtual void mouseReleaseEvent(QMouseEvent *event); 
}; 

Source:

////////////////////////////////////////////////////////////////////////// 
void QtListWidget::mousePressEvent(QMouseEvent *event){ 
// qDebug() << "QtListWidget::mousePressEvent"; 
    if(event->button() == Qt::LeftButton) 
     mousePressed = true; 
    QListWidget::mousePressEvent(event); 
} 

void QtListWidget::mouseMoveEvent(QMouseEvent *event){ 
// qDebug() << "QtListWidget::mouseMoveEvent"; 
    if(!mousePressed) // disable click+drag 
     QListWidget::mouseMoveEvent(event); 
} 

void QtListWidget::mouseReleaseEvent(QMouseEvent *event){ 
// qDebug() << "QtListWidget::mouseReleaseEvent"; 
    if(event->button() == Qt::LeftButton) 
     mousePressed = false; 
    QListWidget::mouseReleaseEvent(event); 
} 
////////////////////////////////////////////////////////////////////////// 

L'utilisation est trivial, pour autant liste Widgets que vous avez besoin:

QtListWidget* categoryListWidget; 
// all original code above would still work as expected 
... 

voulez bien fait? alors faites-le vous-même! :)

0

Votre solution a tué le défilement pour moi. J'utilise QListView. Voici une autre façon:

Dans le constructeur du parent du QListView:

ui->listView->setSelectionMode(QAbstractItemView::NoSelection); 
connect(ui->listView, SIGNAL(clicked(QModelIndex)), this, SLOT(on_listview_clicked(QModelIndex))); 

Dans la fente connectée:

on_listview_clicked(const QModelIndex &index) 
{ 
    if (index.isValid()) 
    { 
     ui->listView->selectionModel->select(index, QItemSelectionModel::Toggle | QItemSelectionModel::Rows); 

    } 
} 

Ainsi, il sélectionne uniquement sur un clic.