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

wxWidgets Discussion :

Chaînage de wxEvtHandler et wxPaintEvent


Sujet :

wxWidgets

  1. #1
    Rédacteur
    Avatar de 3DArchi
    Profil pro
    Inscrit en
    Juin 2008
    Messages
    7 634
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2008
    Messages : 7 634
    Points : 13 017
    Points
    13 017
    Par défaut Chaînage de wxEvtHandler et wxPaintEvent
    Bonjour,
    J'ai une classe CMonControle qui dérive de wxControl.
    J'ai une classe CMonItemRender qui dérive de wxEvtHandler.
    CMonControle contient un ou des membres de type CMonItemRender.
    Lorsque j'initialise un membre de type CMonItemRender, je fais PushEventHandler pour brancher le CMonItemRender dans la chaîne des EvtHandler.
    Tout marche très bien sauf pour l'évènement wxPaintEvent.
    Là, le déroulement est le suivant :
    Appel de CMonItemRender::OnPaint,
    Puis Appel de CMonControle::OnPaint.
    Sauf que visuellement, je n'ai que le rendu de CMonItemRender::OnPaint. Celui de CMonControle::OnPaint semble ne pas s'afficher.
    Pourtant que ce soit par trace ou en mettant des breakpoints, je passe bien dans CMonControle::OnPaint. En rentrant dans les fonctions wxWindows tout semble bien se passer.
    Donc, j'aimerais savoir si d'autres ont déjà eu le problème ?
    Je suis sous Windows et le problème se pose aussi bien avec une version de wxWidget pour Visual Express qu'avec une version pour gcc. Est-ce que le problème se pose sur d'autres plateformes ?
    Voici un code source minimal qui le reproduit :
    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
    89
    90
    91
    92
    93
    94
    95
    96
    97
    98
    99
    100
    101
    102
    103
    104
    105
    106
    107
    108
    109
    110
    111
    112
    113
    114
    115
    116
     
    #include "wx/wx.h"
     
    class MyApp : public wxApp
    {
    public:
        virtual bool OnInit();
    };
     
    class MyFrame : public wxFrame
    {
    public:
        MyFrame(const wxString& title);
     
    private:
        DECLARE_EVENT_TABLE()
    };
     
    class CMonItemRender : public wxEvtHandler
    {
    public:
       virtual ~CMonItemRender()
       {
          if(mp_container){
             mp_container->RemoveEventHandler(this);
          }
       }
       CMonItemRender(wxWindow *  container_,wxPoint const & top_left_, wxSize const & size_)
          :mp_container(container_),m_top_left(top_left_),m_size(size_)
       {
          mp_container->PushEventHandler(this);
       }
       void OnPaint(wxPaintEvent&evt_)
       {
          wxPaintDC dc(mp_container);
          dc.SetBrush(*wxBLUE_BRUSH);
          dc.SetPen(wxPen(*wxBLUE));
          dc.DrawRectangle(m_top_left.x,m_top_left.y,m_size.x,m_size.y);
          evt_.Skip();
       }
    private:
       wxWindow *mp_container;
       wxPoint m_top_left;
       wxSize m_size;
     
       DECLARE_EVENT_TABLE()
    };
    BEGIN_EVENT_TABLE(CMonItemRender,wxEvtHandler)
       EVT_PAINT(CMonItemRender::OnPaint)
    END_EVENT_TABLE()
     
    class CMonControle :public wxControl
    {
    public:
       static const wxChar CMonControleNameStr[];
       CMonControle():m_renderer(this,wxPoint(5,5),wxSize(20,20)){}
       CMonControle(wxWindow *parent,
          wxWindowID id,
          const wxPoint& pos = wxDefaultPosition,
          const wxSize& size = wxDefaultSize, long style = 0,
          const wxValidator& validator = wxDefaultValidator,
          const wxString& name = CMonControleNameStr)
          :m_renderer(this,wxPoint(5,5),wxSize(20,20))
       {
          Create(parent, id, pos, size, style, validator, name);
       }
    private:
       void OnPaint(wxPaintEvent&)
       {
          wxPaintDC dc(this);
          wxSize ma_taille = GetClientSize();
          dc.SetBrush(*wxGREEN_BRUSH);
          dc.SetPen(*wxGREEN_PEN);
          dc.DrawRectangle(0,0,ma_taille.x,ma_taille.y);
       }
       void OnSize(wxSizeEvent&)
       {
          Refresh();
       }
     
    private:
       CMonItemRender m_renderer;
     
       DECLARE_DYNAMIC_CLASS(CMonControle)
       DECLARE_EVENT_TABLE()
    };
    IMPLEMENT_DYNAMIC_CLASS(CMonControle,wxControl);
     
    BEGIN_EVENT_TABLE(CMonControle,wxControl)
       EVT_PAINT(CMonControle::OnPaint)
       EVT_SIZE(CMonControle::OnSize)
    END_EVENT_TABLE()
    const wxChar CMonControle::CMonControleNameStr[]="monControle";
     
     
    IMPLEMENT_APP(MyApp)
     
    // 'Main program' equivalent: the program execution "starts" here
    bool MyApp::OnInit()
    {
        if ( !wxApp::OnInit() )
            return false;
     
        MyFrame *frame = new MyFrame(_T("Minimal wxWidgets App"));
        frame->Show(true);
        new CMonControle(frame,wxID_ANY,wxPoint(10,10),wxSize(100,100));
     
        return true;
    }
     
    BEGIN_EVENT_TABLE(MyFrame, wxFrame)
    END_EVENT_TABLE()
     
    MyFrame::MyFrame(const wxString& title)
           : wxFrame(NULL, wxID_ANY, title)
    {}

  2. #2
    Rédacteur
    Avatar de 3DArchi
    Profil pro
    Inscrit en
    Juin 2008
    Messages
    7 634
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2008
    Messages : 7 634
    Points : 13 017
    Points
    13 017
    Par défaut
    J'ai trouvé un contournement : lors de l'affichage de CMonItemRender je demande un refresh sur les zones dont il n'a pas la charge. Là ça semble marcher. Mais je ne suis pas sûr que ce soit la solution adéquate. Des avis ?

    Voici la version de CMonItemRender::OnPaint modifiée qui marche :
    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
     
    class CMonItemRender : public wxEvtHandler
    {
    //
    //... tout pareil qu'avant
    //
       void OnPaint(wxPaintEvent&evt_)
       {
          wxPaintDC dc(mp_container);
          wxRect clip_rgn;
          dc.GetClippingBox(&clip_rgn.x,&clip_rgn.y,&clip_rgn.width,&clip_rgn.height);
          if(clip_rgn==wxRect(0,0,0,0)){
             clip_rgn = wxRect(wxPoint(0,0),mp_container->GetClientSize());
          }
          if(clip_rgn.Contains(wxRect(m_top_left,m_size))){
             wxRect rect_left(
                clip_rgn.x,
                clip_rgn.y,
                m_top_left.x-clip_rgn.x,
                clip_rgn.height
             );
     
             wxRect rect_right(
                m_top_left.x+m_size.x,
                clip_rgn.y,
                clip_rgn.x + clip_rgn.width-(m_top_left.x+m_size.x),
                clip_rgn.height
             );
             wxRect rect_top(
                m_top_left.x,
                clip_rgn.y,
                m_size.x,
                m_top_left.y-clip_rgn.y
             );
             wxRect rect_bottom(
                m_top_left.x,
                m_top_left.y+m_size.y,
                m_size.x,
                clip_rgn.y + clip_rgn.height-(m_top_left.y+m_size.y)
             );
             if(rect_left.height&&rect_left.width)
             {
                mp_container->RefreshRect(rect_left,false);
             }
             if(rect_right.height&&rect_right.width)
             {
                mp_container->RefreshRect(rect_right,false);
             }
             if(rect_top.height&&rect_top.width)
             {
                mp_container->RefreshRect(rect_top,false);
             }
             if(rect_bottom.height&&rect_bottom.width)
             {
                mp_container->RefreshRect(rect_bottom,false);
             }
             dc.SetBrush(*wxBLUE_BRUSH);
             dc.SetPen(wxPen(*wxBLUE));
             dc.DrawRectangle(m_top_left.x,m_top_left.y,m_size.x,m_size.y);
          }
     
          evt_.Skip();
       }
    //
    //... tout pareil qu'avant
    //
     
    };

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

Discussions similaires

  1. Moteur d'inférence et chaînage arrière
    Par titi_lion dans le forum Prolog
    Réponses: 4
    Dernier message: 04/05/2011, 15h29
  2. Liste chaînage dynamique
    Par punisher999 dans le forum Général Java
    Réponses: 2
    Dernier message: 25/03/2010, 01h30
  3. Chaînage de LDAP et sécurité
    Par CinePhil dans le forum Sécurité
    Réponses: 0
    Dernier message: 09/01/2009, 11h24
  4. [debutant] BEGIN_EVENT_TABLE ou wxEvtHandler::Connect ?
    Par Biosox dans le forum wxWidgets
    Réponses: 3
    Dernier message: 31/10/2006, 15h51
  5. Chaînage
    Par kameleo10 dans le forum Oracle
    Réponses: 1
    Dernier message: 03/12/2005, 13h57

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