IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Discussion :

QCheckBox dans QTableView

  1. #1
    Membre confirmé
    Profil pro
    Inscrit en
    Octobre 2009
    Messages
    65
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2009
    Messages : 65
    Par défaut QCheckBox dans QTableView
    Bonjour à tous,

    Comme dit dans le titre, je cherche à insérer dans une tableview existante un checkbox dans le but de pouvoir faire une sélection multiple.

    Pour le moment, j'ai une class delegate qui permet de récupérer la valeur et l'index

    Par exemple ma fonction me permet cela :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
     
    if(field_name == "decision"){
                int decision = valeur_champ.toInt();
                if(decision == 0){//SI la valeur de ce champs == 0 alors on affiche Attente
                    return "Attente";
                }else if(decision == 1){//SI la valeur de ce champs == 1 alors on affiche Accordé
     
                    return "Accordé";
                }
            }
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    if (field_name == "action")
     {
      //ici doit se retrouver le return avec le check box        
     }
    Ci dessous la fonction me permettant de mettre à jour lma table

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
     
    void Creer_liste_phoning::rafraichir_table(){
     
        QAbstractItemModel* astm = ui->table_liste->model();
        model_personnalise* stm = dynamic_cast<model_personnalise*>(astm);
     
        stm->setTable("liste_prospect");//On donne le nom de la table
     
        stm->select();
     
     
    }
    Avez vous une idée da la façon de faire :
    1 créer pour chaque ligne et que pour la colonne "action" (field_name == "action") un checkbox
    2 récupérer sous forme de tableau ou autre les id sélectionné
    3 créer une boucle pour faire une action sur ces id

    Voilou rien de plus :-°

    Merci par avance à tous

  2. #2
    Membre Expert

    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Mai 2009
    Messages
    1 009
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 37
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Mai 2009
    Messages : 1 009
    Par défaut
    Tu n'as pas besoin de faire un dynamic_cast, qobject_cast suffit vu que ce sont des QObject.

    1) Réimplémenter flags() de ton modèle pour rajouter le flag Qt::ItemIsUserCheckable pour la colonne que tu veux (test sur index.column() par exemple).

    2) Je crois qu'il te faut parcourir les cases de ton tableau (ou de ta colonne pour optimiser), en appelant data(index, Qt::CheckStateRole). Le QVariant renvoyé contiendra le CheckState.

    3) A l'étape précédente tu auras construit ta QModelIndexList, qu'il te suffira de parcourir...

  3. #3
    Membre confirmé
    Profil pro
    Inscrit en
    Octobre 2009
    Messages
    65
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2009
    Messages : 65
    Par défaut
    Salut et merci pour la réponse,
    N'aurais tu pas un petit exemple car j'avoue bloquer un peu la .....

    Merci d'avance pour ta compréhension

  4. #4
    Membre Expert

    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Mai 2009
    Messages
    1 009
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 37
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Mai 2009
    Messages : 1 009
    Par défaut
    Si tu as une question plus précise, je peux t'aider, sinon je pense que c'est assez clair et qu'il faut te documenter. A part peut-être le lien avec tes questions. Déjà tu dois être clair sur le fonctionnement du modèle/vue Qt. J'ai vu que tu as fait ton propre modèle alors j'ai pensé que ce point était bon.

    1) Il ne faut pas "créer des checkbox", mais rendre les données checkable grâce au flag.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    #define COLONNE_ID 3
     
    Qt::ItemFlags model_personnalise::flags ( const QModelIndex& index ) const
    {
        if ( !index.isValid() ) {
            return 0;
        }
     
        Qt::ItemFlags l_Flags ( Qt::ItemIsEnabled | Qt::ItemIsSelectable );
     
        if ( index.column() == COLONNE_ID ) {
            l_Flags |= Qt::ItemIsUserCheckable;
        }
     
        return l_Flags;
    }
    2) Quelle que soit l'information demandée, c'est data(index, RoleDeLinfo) qui te la donnera. CheckStateRole est déjà un rôle implémenté par défaut dans Qt donc tu peux t'en servir tel quel. Ça ressemblera à ça :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    QModelIndexList l_IdList;
    for ( int i = 0; i < rowCount(); i++ )
    {
        QModelIndex l_Index = index ( i, COLONNE_ID, QModelIndex() );
        if ( l_Index.isValid() && static_cast<Qt::CheckState> ( l_Index.data ( Qt::CheckStateRole ).toInt() ) == Qt::Checked )
            l_IdList.append ( l_Index );
    }
    3) Pas de difficulté.
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    foreach ( const QModelIndex& l_Index, l_IdList )
    {
        QString l_sID = l_Index.data();
        // gérer l'ID
    }

  5. #5
    Membre confirmé
    Profil pro
    Inscrit en
    Octobre 2009
    Messages
    65
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2009
    Messages : 65
    Par défaut
    Salut,

    Merci, je vais regarder ça ce soir.
    Par contre, à quoi correspond COLONNE_ID

    Dans mon cas, à la place de :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    if ( index.column() == COLONNE_ID ) {
            l_Flags |= Qt::ItemIsUserCheckable;
        }
    je doit mettre
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    if (field_name == "action") {
            l_Flags |= Qt::ItemIsUserCheckable;
        }
    Est ce bien cela ?

  6. #6
    Membre Expert

    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Mai 2009
    Messages
    1 009
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 37
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Mai 2009
    Messages : 1 009
    Par défaut
    Oui, mais là le problème c'est de récupérer field_name car tout ce que tu as c'est l'objet index. Tu peux chercher dans le HeaderView horizontal, à l'index index.column().
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    if ( headerData ( index.column(), Qt::Horizontal ) == QLatin1String ( "action" ) )
    devrait le faire...

  7. #7
    Membre confirmé
    Profil pro
    Inscrit en
    Octobre 2009
    Messages
    65
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2009
    Messages : 65
    Par défaut
    Salut,
    Je l'ai déjà récupéré le field_name, le code que j'ai posté au début est fonctionnel.
    J’essaie tout ça ce soir pour voir si je m'en sort

  8. #8
    Membre confirmé
    Profil pro
    Inscrit en
    Octobre 2009
    Messages
    65
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2009
    Messages : 65
    Par défaut
    Salut,

    Je te remercie pour ton explication mais j'ai tout de même du mal à tout comprendre et à m'en sortir.

    Je vais te montrer à l'identique mon processus :

    Création d'une class model_personnalise.
    Cette class me permet d'afficher par exemple une date au lieu du timestamp, oui au lieu de 1 etc....
    Voici le code de cette class : .cpp
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    #include "model_personnalise.h"
    #include <QSqlRecord>
    #include <QDateTime>
    #include <QPixmap>
    #include <QDebug>
    #include "Sql.h"
     
    model_personnalise::model_personnalise(QObject *parent) :
        QSqlTableModel(parent)
    {
     
        liste_champs_date_ << "date_insert" << "last_connexion" << "date_accord" << "periode_du" << "periode_au" << "date_tache" << "debut" << "fin" << "date_recyclage" << "date" << "date_reponse" << "date_regle" << "Début" << "Fin" << "date_paiement" << "date_creation" << "date_debut" << "date_fin" << "date_enregistre" << "date_echeance";
        liste_champs_duree_ << "duree_prevue" << "duree_fait" << "heure_fait" << "deja_heure_fait" << "restant_heure" << "duree_presence" << "duree" << "Duree" << "Durée" << "duree_total" << "nombre_heure";
        liste_champs_cout_ << "tarif_ss_theme" << "Débit" << "Débittva"<< "Débitttc"  << "Crédit"<< "Crédittva"<< "Créditttc" << "total_non_facture" << "regle" << "Débit" << "Bénéfice" << "montant_accorde" << "montant_client" <<"montant_demande"<< "Deja_facture" << "montant_tva"<< "montant_ttc"<< "montant_restant" <<"montant_ligne_ttc"<<"montant_ligne_tva"<< "montant_facture" << "montant_ligne" << "montant_stagiaire" << "restant" << "total_facture" << "montant_regle" << "tarif" << "tarif_opca" << "montant" << "montant_enregistre" << "Déja facturé" << "deja_regle" << "Total" << "montant_total" << "deja_facture" << "total_deja_regle";
        liste_champs_marge_ << "Marge";
    }
     
     
    QVariant model_personnalise::data ( const QModelIndex & index, int role) const{
        if(role == Qt::DisplayRole){
            QString field_name = record().fieldName(index.column());
            QVariant valeur_champ = QSqlTableModel::data(index, role);
            if(liste_champs_date_.contains(field_name)){
                if(valeur_champ != "//" && valeur_champ != "0"){
                    return nouvelle_date(valeur_champ.toInt());
                }else{
                    return "--/--/----";
                }
            }
     
            if(liste_champs_marge_.contains(field_name)){
                QString montant = arrondi_affichage(valeur_champ.toFloat());
                return QString("%1 %").arg(montant);
            }
     
            if(liste_champs_cout_.contains(field_name)){
                QString montant = arrondi_affichage(valeur_champ.toDouble());
                QString signe = QChar(0x20AC);
                return QString("%1 %2").arg(montant).arg(signe);
            }
            if(liste_champs_duree_.contains(field_name)){
                QString montant = arrondi_affichage(valeur_champ.toFloat());
                return QString("%1 H").arg(montant);
            }
     
            if(field_name == "etat"){
                int pour_qui = valeur_champ.toInt();
                if(pour_qui == 0){
                    return "Active";
                }else if(pour_qui == 1){
     
                    return "Annulée";
                }
            }
     
            if(field_name == "nature_deduction"){
                int nature = valeur_champ.toInt();
                if(nature == 0){
                    return "Règlement";
                }else if(nature == 1){
                    return "Acompte";
                }else if(nature == 2){
                    return "Avoir";
                }
            }
     
            if(field_name == "action"){
                int action = valeur_champ.toInt();
                if(action == 0){
                    return "A faire";
                }else if(action == 1){
                    return "Répond pas";
                }
            }
     
          if (field_name == "action")  
         {  
            //ici doit se retrouver le return avec le check box          
         } 
     
        }
        return QSqlTableModel::data(index, role);
    }
     
    QString model_personnalise::nouvelle_date(int valeur)const{
        QDateTime date = QDateTime::fromTime_t(valeur);
        return date.toString("dd/MM/yyyy");
    }
    Et .h
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    #ifndef MODEL_PERSONNALISE_H
    #define MODEL_PERSONNALISE_H
     
    #include <QSqlTableModel>
    #include <QSet>
    #include <QPushButton>
    #include <QModelIndex>
     
    class model_personnalise : public QSqlTableModel
    {
        Q_OBJECT
    public:
        explicit model_personnalise(QObject *parent = 0);
        virtual QVariant data ( const QModelIndex & index, int role = Qt::DisplayRole ) const ;
     
    private:
        QString nouvelle_date(int valeur) const;
        QSet<QString> liste_champs_date_;
        QSet<QString> liste_champs_cout_;
        QSet<QString> liste_champs_duree_;
        QSet<QString> liste_champs_marge_;
    signals:
     
    public slots:
     
    };
     
    #endif // MODEL_PERSONNALISE_H
    Maintenant le constructeur de la fenêtre qui affiche ma table (class Creer_liste) :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    model_personnalise* stm = new model_personnalise;
        ui->table_liste->setModel(stm);
        ui->table_liste->setEditTriggers(QAbstractItemView::NoEditTriggers);//empeche d'accéer au element du tableau
        ui->table_liste->horizontalHeader()->setStretchLastSection(true);
    Et pour afficher le tableau :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    void Creer_liste::rafraichir_table(){
     
        QAbstractItemModel* astm = ui->table_liste->model();
        model_personnalise* stm = dynamic_cast<model_personnalise*>(astm);
     
        stm->setTable("liste_prospect");//On donne le nom de la table
     
        stm->select();
    }
    Voila grossomodo mon code, j'espère que tu pourras m'aider à résoudre mon problème

  9. #9
    Membre Expert

    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Mai 2009
    Messages
    1 009
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 37
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Mai 2009
    Messages : 1 009
    Par défaut
    Il ne te reste pratiquement plus que du copier/coller, même si évidemment faut que tu comprennes ce que tu fais...

    Dans data, tu n'as rien d'autre à faire que ce que tu as déjà fait. Donc ton if incomplet n'a rien à faire : tu as rempli les données (DisplayRole) et le CheckStateRole est géré déjà par défaut (return QSqlTableModel::data(index, role);). Donc dans un premier temps ce qu'il manque comme je l'ai expliqué c'est la réimplémentation de flags() pour rendre cette colonne checkable, c'est là que tu dois mettre ce if.

    (Je ne connais pas du tout QSqlTableModel, mon explication était valable pour tout QAbstractItemModel, donc effectivement au même titre que record().fieldName(index.column()) que tu as utilisé, il y a peut-être d'autres méthodes bien pratiques par rapport à mes exemples).

Discussions similaires

  1. Réponses: 2
    Dernier message: 23/05/2014, 08h41
  2. Réponses: 6
    Dernier message: 21/04/2010, 14h27
  3. Affichage d'une table dans QTableView et QSqlTableModel
    Par boumacmilan dans le forum Bases de données
    Réponses: 1
    Dernier message: 13/04/2010, 10h48
  4. Navigation dans QTableView
    Par dj.motte dans le forum Qt
    Réponses: 4
    Dernier message: 09/03/2009, 15h29

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo