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 :

Tableau de boutons disparu

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    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 Tableau de boutons disparu
    Bonjour,

    Alors j'ai essayé de cibler le problème au maximum. Je "fabrique" des boutons à partir d'un fichier d'initialisation, dans ma classe MainWindow, sous la forme d'un tableau de taille indéfinie (à la déclaration) que j'instancie dans le constructeur.

    Voici le code épuré au maximum :

    mainwindow.h
    Code C++ : 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
    #ifndef MAINWINDOW_H
    #define MAINWINDOW_H
     
    #include <QMainWindow>
    #include <QSettings>
    #include <QXmlStreamReader>
    #include <QPushButton>
     
    class MainWindow : public QMainWindow
    {
        Q_OBJECT
     
        public:
            MainWindow();
     
        private:
            QSettings *settings;
     
            QWidget *centralWidget;
     
            QWidget *containerbtn;
            int NbTabsMax;
            QPushButton *btn;
     
        private slots:
            void initStyleSheet();
            void on_btnn_pressed();
    };
     
    #endif // MAINWINDOW_H

    mainwindow.cpp
    Code C++ : 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
    #include "mainwindow.h"
    #include <QDebug>
     
    MainWindow::MainWindow()
    {
     
        if (objectName().isEmpty())
            setObjectName(QString::fromUtf8("MainWindow"));
        setFixedSize(800, 480);
     
        settings = new QSettings("config.xml", QSettings::defaultFormat());
     
        /* BOUTONS */
        containerbtn = new QWidget(centralWidget);
        containerbtn->setObjectName(QString::fromUtf8("containerbtn"));
        containerbtn->setGeometry(QRect(700, 80, 100, 400));
        containerbtn->hide();
     
        NbTabsMax = settings->value("NbTabsMax").toInt();
        QPushButton btn[NbTabsMax];
        int x = 3;
        for(int i = 0; i < NbTabsMax; i++) {
            btn[i].setParent(containerbtn);
            btn[i].setObjectName(QString::fromUtf8(QString("btn" + QString::number(i)).toStdString().c_str()));
            btn[i].setGeometry(QRect(10, x, 81, 60));
            btn[i].setText(tr(settings->value("Tab" + QString::number(i) + "/Label","").toString().toStdString().c_str()));
            btn[i].setCheckable(true);
            x += 66;
        }
     
        // bouton créé juste pour cerner mieux le problème
        QPushButton *btnn = new QPushButton(containerbtn);
        btnn->setObjectName(QString::fromUtf8("btnn"));
        btnn->setGeometry(QRect(10, 10, 81, 60));
        btnn->setText(tr("test"));
        btnn->setCheckable(true);
     
        qDebug() << containerbtn->children();
     
        setCentralWidget(centralWidget);
     
        initStyleSheet();
        containerbtn->setStyleSheet("background-color: blue");
        containerbtn->show();
        btn[0].show();
        QMetaObject::connectSlotsByName(this);
    }
     
    void MainWindow::initStyleSheet()
    {
        qDebug() << containerbtn->children();
    }
     
    void MainWindow::on_btnn_pressed()
    {
        qDebug() << containerbtn->children();
    }

    Résultat :

    Citation Envoyé par Exécution
    (QPushButton(0x22f9e0, name = "btn0") , QPushButton(0x22f9f4, name = "btn1") , QPushButton(0x22fa08, name = "btn2") , QPushButton(0x22fa1c, name = "btn3") , QPushButton(0x22fa30, name = "btn4") , QPushButton(0x22fa44, name = "btn5") , QPushButton(0xb217bf0, name = "btnn") )
    (QPushButton(0x22f9e0, name = "btn0") , QPushButton(0x22f9f4, name = "btn1") , QPushButton(0x22fa08, name = "btn2") , QPushButton(0x22fa1c, name = "btn3") , QPushButton(0x22fa30, name = "btn4") , QPushButton(0x22fa44, name = "btn5") , QPushButton(0xb217bf0, name = "btnn") )
    Citation Envoyé par Appui sur btnn
    (QPushButton(0xb217bf0, name = "btnn") )
    Les boutons sont créés comme il faut (le problème ne vient pas de la méthode de configuration avec le XML, j'ai vérifié le contenu des attributs d'un bouton). Quelle que soit la fonction on_<object>_<signal_object>, j'ai le même résultat.



    --------------------------------------------------------------------



    Je rajoute, si ça peut aider, qu'en réalité je n'utilise pas des QPushButton mais une classe héritée (pour faire des boutons clignotants), qui comporte un QTimer en plus. Pour cela, j'ai redéfini la méthode setParent comme suit :
    Code C++ : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    void BlinkButton::setParent(QWidget *parent) {
        QPushButton::setParent(parent);
        blinking->setParent(parent);
    }
    A ce moment là, j'obtiens :
    Citation Envoyé par Exécution
    (BlinkButton(0x22f9d0, name = "btn0") , QTimer(0xb2172f0) , BlinkButton(0x22f9e8, name = "btn1") , QTimer(0xb2175b8) , BlinkButton(0x22fa00, name = "btn2") , QTimer(0xb2178a0) , BlinkButton(0x22fa18, name = "btn3") , QTimer(0xb217b88) , BlinkButton(0x22fa30, name = "btn4") , QTimer(0xb217e38) , BlinkButton(0x22fa48, name = "btn5") , QTimer(0xb218118) , BlinkButton(0xb2182f0, name = "btnn") , QTimer(0xb218a10) )
    (BlinkButton(0x22f9d0, name = "btn0") , QTimer(0xb2172f0) , BlinkButton(0x22f9e8, name = "btn1") , QTimer(0xb2175b8) , BlinkButton(0x22fa00, name = "btn2") , QTimer(0xb2178a0) , BlinkButton(0x22fa18, name = "btn3") , QTimer(0xb217b88) , BlinkButton(0x22fa30, name = "btn4") , QTimer(0xb217e38) , BlinkButton(0x22fa48, name = "btn5") , QTimer(0xb218118) , BlinkButton(0xb2182f0, name = "btnn") , QTimer(0xb218a10) )
    Citation Envoyé par Appui sur btnn
    (QTimer(0xb2172f0) , QTimer(0xb2175b8) , QTimer(0xb2178a0) , QTimer(0xb217b88) , QTimer(0xb217e38) , QTimer(0xb218118) , BlinkButton(0xb2182f0, name = "btnn") , QTimer(0xb218a10) )


    Une idée ?

  2. #2
    Rédacteur

    Inscrit en
    Novembre 2006
    Messages
    1 272
    Détails du profil
    Informations forums :
    Inscription : Novembre 2006
    Messages : 1 272
    Par défaut
    Il faut passer par des pointeurs. Tes boutons sont créés sur la pile et par conséquent c'est normal que tu ai un problème.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    QPushButton btn[NbTabsMax];
    A modifer par exmple en
    si tu veux toujours avoir un tableau dynamique de QPushButton.
    Vous voulez participer aux Tutoriels, FAQ ou Traductions et faire partie de l'équipe Qt de Developpez.
    N'hésitez pas à me contacter par MP.

  3. #3
    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
    D'accord, merci beaucoup, je testerai ça demain avant de mettre "résolu".

    Par contre pour être sûr :

    C'est un tableau de pointeurs de boutons ? Ou un pointeur de tableau de boutons ?
    (Autrement dit, je travaille comment avec ensuite ? *btn[0]-> ou **btn[0]. ? Oui oui je ferais bien de réviser le C... Je pensais Qt au-dessus de tout ça :p)

    Edit :

    Code C++ : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    BlinkButton **btn;
    btn = new BlinkButton*[NbTabsMax];
    for(int i = 0; i < NbTabsMax; i++) {
        btn[i] = new BlinkButton(containerbtn);
        btn[i]->setObjectName(QString::fromUtf8(QString("btn" + QString::number(i)).toStdString().c_str()));
        /*[...]*/
    }

    Résolu

  4. #4
    Inactif  


    Homme Profil pro
    Inscrit en
    Novembre 2008
    Messages
    5 288
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 49
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Secteur : Santé

    Informations forums :
    Inscription : Novembre 2008
    Messages : 5 288
    Par défaut
    Bonjour

    Par contre, tu devrais travailler avec un conteneur plutôt que des pointeurs nus :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    QVector< QPushButton* > buttons;
    buttons.resize(nb_buttons);
     
    foreach(QPushButton* button, buttons)
    {
        button = new BlinkButton(containerbtn);
        button->setObjectName("btn" + QString::number(i));
    }
    (pas besoin de conversion de string, setObjectName prend une QString)

    Et attention lors de la destruction de tes boutons : il faut bien penser à leurs donner un parent pour qu'ils soient détruits automatiquement, ou alors, il faut le faire soit même dans le destructeur de la classe (lors de la destruction de QVector, QVector détruit les pointeurs mais pas les objets pointés)

  5. #5
    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
    (J'avais oublié de remplacer mes BlinkButton par des QPushButton dans le code du post au-dessus)

    C'est vrai pour le setObjectName() que j'ai continué à partir d'une version générée par QtDesigner et il utilise fromUtf8 (qui prend un char*) systématiquement alors j'ai laissé. Du coup c'est lourd.

    Concernant ta remarque sur les pointeurs nus, déjà le code que tu mets ne connait pas "i" pour nommer les boutons. Et cet "i" me sert à boucler sur plusieurs tableaux en parallèle pour les associer... J'ai pas trop l'habitude d'utiliser les conteneurs, ça m'embête de charger des librairies pour des trucs que je sais faire "à l'ancienne". Logiquement ça alourdit le programme non ? Enfin merci du conseil, je vais regarder ça.

  6. #6
    Inactif  


    Homme Profil pro
    Inscrit en
    Novembre 2008
    Messages
    5 288
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 49
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Secteur : Santé

    Informations forums :
    Inscription : Novembre 2008
    Messages : 5 288
    Par défaut
    J'ai utilité foreach parce que dans ton code, tu n'utilisais pas l'indice (EDIT : en fait si, tu en avais besoin dans le nom de l'objet et le code que j'avais donné n'aurait pas fonctionné )mais si tu en as besoin, QVector propose l'opérateur []. Donc tu n'utilise exactement comme std::vector :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    QVector< QPushButton* > buttons;
    buttons.resize(nb_buttons);
     
    for (int i=0; i<buttons.size(); ++i)
    {
        buttons[i] = new QPushButton(containerbtn);
        buttons[i]->setObjectName("btn" + QString::number(i));
    // etc.
    }

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. [ActionListener] Evénement sur tableau de boutons
    Par frouge dans le forum Composants
    Réponses: 5
    Dernier message: 08/10/2011, 02h44
  2. Tableau de boutons
    Par hbzied dans le forum AWT/Swing
    Réponses: 1
    Dernier message: 26/04/2006, 14h14
  3. Disposition d'un tableau de boutons dans un JPanel
    Par Arnaud F. dans le forum AWT/Swing
    Réponses: 6
    Dernier message: 23/04/2006, 18h09
  4. [AWT]tableau de boutons
    Par pierrot106 dans le forum AWT/Swing
    Réponses: 3
    Dernier message: 06/12/2004, 17h59
  5. Gérer les events d'un tableau de boutons
    Par lord_kalipsy dans le forum wxWidgets
    Réponses: 7
    Dernier message: 20/10/2004, 10h13

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