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

C++Builder Discussion :

Placer un Label au-dessus du curseur de texte dans un Memo [Non suivi]


Sujet :

C++Builder

  1. #1
    Membre régulier Avatar de benj63
    Homme Profil pro
    Responsable de service informatique
    Inscrit en
    Mai 2002
    Messages
    207
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Puy de Dôme (Auvergne)

    Informations professionnelles :
    Activité : Responsable de service informatique
    Secteur : Conseil

    Informations forums :
    Inscription : Mai 2002
    Messages : 207
    Points : 99
    Points
    99
    Par défaut Placer un Label au-dessus du curseur de texte dans un Memo
    Bonjour,

    Je souhaiterais afficher au-dessus du texte en train d'être saisi dans un TMemo, une bulle d'aide. Mon problème est que je souhaiterais que cette bulle soit toujours au-dessus du curseur de texte, et pas n'importe où sur ma Form. Y'a-t'il un moyen de connaitre la position exacte du curseur de texte, en pixels à partir du haut et de la gauche du Memo ?

    Car je pourrais bien utiliser SelStart et SelLength pour connaître la position du curseur, mais mon problème est que cela ne correspond pas à un nombre de pixels, mais à un nombre de lettres...

    En vous remerciant !

  2. #2
    Membre du Club
    Profil pro
    Inscrit en
    Août 2004
    Messages
    94
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Août 2004
    Messages : 94
    Points : 53
    Points
    53
    Par défaut
    bjr
    il y a la propriété CaretPos de TMemo qui renvoit un TPoint indiquant la position du signe insertion dans la zone client et Application->ActivateHint(TPoint CursorPos) permétant de positionner l'info bulle à la position CursorPos soit le code suivant dans l'événement OnChange de Memo1 :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    void __fastcall TForm1::Memo1Change(TObject *Sender)
    {
      Application->ActivateHint(Memo1->CaretPos);
    }
    coordialement

  3. #3
    Membre averti
    Avatar de Neo41
    Inscrit en
    Janvier 2003
    Messages
    241
    Détails du profil
    Informations forums :
    Inscription : Janvier 2003
    Messages : 241
    Points : 403
    Points
    403
    Par défaut
    Bonjour,

    j'ai essayé la méthode de sony351 sous tous les angles mais j'ai pas le Hint qui s'affiche à côté du curseur. Est tu sûr de ton code? Si ca marche chez toi, tu pourrais nous poster le code stp?

    Merci

  4. #4
    Membre régulier Avatar de benj63
    Homme Profil pro
    Responsable de service informatique
    Inscrit en
    Mai 2002
    Messages
    207
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Puy de Dôme (Auvergne)

    Informations professionnelles :
    Activité : Responsable de service informatique
    Secteur : Conseil

    Informations forums :
    Inscription : Mai 2002
    Messages : 207
    Points : 99
    Points
    99
    Par défaut
    Merci sony351, mais comme le dit Neo41, le hint ne semble pas s'afficher correctement... J'ai bien mis la propriété Memo1->ShowHint à true, et j'ai placé ton code lors de l'événement Memo1->Memo1KeyUp, mais il ne s'affiche que si je déplace le curseur de la souris dans la zone de texte de Memo1 : il suit le curseur de la souris, mais pas le curseur de texte au fûr et à mesure qu'on le tape. Je vais essayer de regarder si on peut aller plus loin avec Memo1->CaretPos.

  5. #5
    Membre régulier Avatar de benj63
    Homme Profil pro
    Responsable de service informatique
    Inscrit en
    Mai 2002
    Messages
    207
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Puy de Dôme (Auvergne)

    Informations professionnelles :
    Activité : Responsable de service informatique
    Secteur : Conseil

    Informations forums :
    Inscription : Mai 2002
    Messages : 207
    Points : 99
    Points
    99
    Par défaut
    Bon, ça marche !!!

    D'abord, pour que le Label s'affiche au dessus du Memo :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    Label1->Parent = Memo1;
    Puis pour que le Label s'affiche au dessus de la position actuelle du curseur de texte :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    Label1->Top = Memo1->CaretPos.y-10;
    Label1->Left = Memo1->CaretPos.x;
    Merci sony351 !!


    Il me reste par contre un détail à régler, le Label s'affiche bien au dessus du Memo, mais pas au dessus de ma Form. Par exemple, si je suis en train d'écrire sur la 1ère ligne du Memo, le Label qui s'affiche au dessus, est moitié sur le Memo, moitié en dessous de la Form. Comment faire ?... :

  6. #6
    Membre régulier Avatar de benj63
    Homme Profil pro
    Responsable de service informatique
    Inscrit en
    Mai 2002
    Messages
    207
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Puy de Dôme (Auvergne)

    Informations professionnelles :
    Activité : Responsable de service informatique
    Secteur : Conseil

    Informations forums :
    Inscription : Mai 2002
    Messages : 207
    Points : 99
    Points
    99
    Par défaut
    En fait ça ne marche pas super bien...

    Memo1->CaretPos->y renvoie la ligne, et non la position en pixels... ce qui fait que si mon Memo fait 4 lignes de haut, mais que mon curseur est à la 10ème ligne de texte, ma bulle d'aide n'est pas du tout au bon endroit, elle est bcp trop basse !! J'espère que je me suis fait comprendre...

    Je cherche toujours une solution...

  7. #7
    Membre averti
    Avatar de Neo41
    Inscrit en
    Janvier 2003
    Messages
    241
    Détails du profil
    Informations forums :
    Inscription : Janvier 2003
    Messages : 241
    Points : 403
    Points
    403
    Par défaut
    Tu pourrais poster le code tout entier stp? chez moi ca affiche le Label largement an dessus que le texte, et en plus ca ne descend pas bien sur ENTER.

  8. #8
    Membre régulier Avatar de benj63
    Homme Profil pro
    Responsable de service informatique
    Inscrit en
    Mai 2002
    Messages
    207
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Puy de Dôme (Auvergne)

    Informations professionnelles :
    Activité : Responsable de service informatique
    Secteur : Conseil

    Informations forums :
    Inscription : Mai 2002
    Messages : 207
    Points : 99
    Points
    99
    Par défaut
    Pour l'instant, c'est comme ça, mais ça ne fonctionne pas parfaitement (cf mon précédent post) :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    void __fastcall TForm1::Memo1KeyUp(TObject *Sender, WORD &Key,
          TShiftState Shift)
    {
     
    // (... code qui donne le texte à afficher...)
     
    Label1->Caption = texte;
    if(Memo1->CaretPos.y>1)
       Label1->Top = fabs(Memo1->CaretPos.y*Memo1->Font->Height);
    else
       Label1->Top = Memo1->CaretPos.y+15;
    Label1->Left = Memo1->CaretPos.x;
    Label1->Visible = true;
    }
    attention, c'est sur l'évenemement OnKeyUp du Memo1 (pas OnChange) !!

  9. #9
    Membre chevronné

    Profil pro
    Inscrit en
    Juin 2002
    Messages
    1 390
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2002
    Messages : 1 390
    Points : 1 777
    Points
    1 777
    Par défaut
    Salut !

    Une idée franchement stupide : et pourquoi ne pas utiliser une form (fsStayOnTop) !
    Stupide parce que ça semble consommer pas mal de resources ! Mais si l'effet en vaut la peine !
    Remarques... c'est comme ça que je fais mes boites à outils surgissantes
    au lieu de les avoir sur une toolbar... mais ça c'est une autre histoire !

    A plus et bon réveillon !

  10. #10
    Membre averti
    Avatar de Neo41
    Inscrit en
    Janvier 2003
    Messages
    241
    Détails du profil
    Informations forums :
    Inscription : Janvier 2003
    Messages : 241
    Points : 403
    Points
    403
    Par défaut
    Citation Envoyé par henderson
    Salut !

    Une idée franchement stupide : et pourquoi ne pas utiliser une form (fsStayOnTop) !
    Stupide parce que ça semble consommer pas mal de resources ! Mais si l'effet en vaut la peine !
    Remarques... c'est comme ça que je fais mes boites à outils surgissantes
    au lieu de les avoir sur une toolbar... mais ça c'est une autre histoire !

    A plus et bon réveillon !
    ???

  11. #11
    Membre régulier Avatar de Poilou
    Homme Profil pro
    Inscrit en
    Janvier 2004
    Messages
    59
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Maine et Loire (Pays de la Loire)

    Informations forums :
    Inscription : Janvier 2004
    Messages : 59
    Points : 70
    Points
    70
    Par défaut
    Bonjour,

    Et en utilisant le canvas de la form ? Ca ne marcherait pas ?

    Sinon tu peux, peut etre, t'en servir pour calculer la taille de ton texte en pixel avec la méthode TCanvas::TextWidth

    C'est juste une idée comme ça...

  12. #12
    Membre chevronné

    Profil pro
    Inscrit en
    Juin 2002
    Messages
    1 390
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2002
    Messages : 1 390
    Points : 1 777
    Points
    1 777
    Par défaut
    Salut !

    Une fsStayOnTop se dessine au dessus de la form qui contient le memo.
    En faisant en sorte que cette fsStayOnTop n'ait pas de barre de titre etc...
    on peut facilement lui donner une apparence de bulle info.

    Ici le problème est que le memo est parent du label. Ce dernier se dessinera donc toujours dans la zone client du memo sans pouvoir déborder... Il est donc rogné s'il dépasse d'un bord ou l'autre du memo !

    A plus !

  13. #13
    Membre chevronné

    Profil pro
    Inscrit en
    Juin 2002
    Messages
    1 390
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2002
    Messages : 1 390
    Points : 1 777
    Points
    1 777
    Par défaut
    Salut !

    Voici comment on peut mettre en oeuvre un hint tel qu'on l'envisage ici, et ce
    avec une form.

    Form1 contient le TMemo
    Form2 est une fiche dont :
    - on a vidé tous les BorderIcons,
    - BorderStyle sur bsNone
    - FormStyle sur fsStayOnTop
    - on ajoute une propriété Info du type AnsiString dans sa class, en public
    - Width à 135
    - Height à 52

    Voici ce qu'il y a à faire dans Form1 :

    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
    void __fastcall TForm1::Memo1KeyUp(TObject *Sender, WORD &Key,
          TShiftState Shift)
    {
    Form2->Info = "Bulle"; //s'il y a quelque chose à montrer... c'est ici
    Form2->FixPosition();
    Form2->Show();
    Memo1->SetFocus();
    }
    //--
    void __fastcall TForm1::FormMouseMove(TObject *Sender, TShiftState Shift,
          int X, int Y)
    {
    if(Form2->Visible)
        {
        Form2->Hide();
        }
    }
    //--
    void __fastcall TForm1::Memo1Click(TObject *Sender)
    {
    Form2->Info = "Clic sur Memo"; //s'il y a quelque chose à montrer... c'est ici
    Form2->FixPosition();
    if(Form2->Visible == false)
        {
        Form2->Show();
        Memo1->SetFocus();
        }
    else
        {
        Form2->Repaint();
        }
    }
    Voici ce qu'il y a à faire dans Form2 (le fameux hint) :

    Dans sa class on trouve :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    public:
    AnsiString Info;
    void __fastcall FixPosition(); //méthode perso pour fixer sa position
    Dans le .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
    __fastcall TForm2::TForm2(TComponent* Owner)
        : TForm(Owner)
    {
    Info = "Bulle";
    }
    //--
    void __fastcall TForm2::FixPosition()
    {
    TMemo *M = Form1->Memo1;
    AnsiString S = M->Lines->Strings[M->CaretPos.y].SubString(0,M->CaretPos.x);
    int y = Form1->Top + M->Top;
    int h = -M->Font->Height + 2;
    //Normalement il faudra récupérer l'indice de la ligne du haut
    int topindex = 0; //voir dans la FAQ... le sujet a déjà été abordé ...
    SetBounds(Form1->Left + M->Left + Canvas->TextWidth(S),
    	  //calculer la position écran : index ligne - index ligne du haut
              y + ((M->CaretPos.y - topindex) * h) - 8,
              Width,
              Height);
    }
    //--
    void __fastcall TForm2::FormPaint(TObject *Sender)
    {
    Canvas->Pen->Color = clBlack;
    Canvas->Pen->Style = psSolid;
    Canvas->Pen->Mode = pmCopy;
    Canvas->Brush->Color = Color; // clInfoBk
    Canvas->Brush->Style = bsSolid;
    Canvas->Rectangle(0, 0, Width, Height);
    Canvas->Brush->Style = bsClear;
    int y = (Height - Canvas->TextHeight(Info)) / 2;
    Canvas->TextOut(2, y, Info);
    }
    Chez moi ça fonctionne !

    A plus !

  14. #14
    Membre régulier Avatar de benj63
    Homme Profil pro
    Responsable de service informatique
    Inscrit en
    Mai 2002
    Messages
    207
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Puy de Dôme (Auvergne)

    Informations professionnelles :
    Activité : Responsable de service informatique
    Secteur : Conseil

    Informations forums :
    Inscription : Mai 2002
    Messages : 207
    Points : 99
    Points
    99
    Par défaut
    Merci beaucoup pour cette astuce très détaillée, c'est très sympa à toi... mes meilleurs voeux pour 2005 !

    Cependant, je rencontre toujours un problème, lorsque je descends dans les lignes du TMemo : par exemple, si le TMemo fait 5 lignes de hauteur, et que j'écris 15 lignes de texte, l'info bulle apparaît trop bas ! J'espère que je me suis bien expliqué

  15. #15
    Membre chevronné

    Profil pro
    Inscrit en
    Juin 2002
    Messages
    1 390
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2002
    Messages : 1 390
    Points : 1 777
    Points
    1 777
    Par défaut
    Salut !

    J'ai retrouvé le truc !

    An application sends an EM_GETFIRSTVISIBLELINE message to determine the uppermost visible line in an edit control.

    EM_GETFIRSTVISIBLELINE
    wParam = 0; // not used; must be zero
    lParam = 0; // not used; must be zero
    Si tu reprends ce que j'ai montré, alors dans la méthode FixPosition de Form2 :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    int Topline = SendMessage(Form1->Memo1->Handle, EM_GETFIRSTVISIBLELINE, 0,0);
    SetBounds(Form1->Left + M->Left + Canvas->TextWidth(S),
              y + ((M->CaretPos.y - Topline) * h) - 8,
              Width,
              Height);
    A plus !

Discussions similaires

  1. Déplacer curseur de texte dans liste
    Par blackmario dans le forum Général JavaScript
    Réponses: 0
    Dernier message: 02/05/2012, 10h43
  2. repositionner curseur de text dans un Textfield
    Par yanker_man dans le forum Java ME
    Réponses: 3
    Dernier message: 09/11/2010, 17h47
  3. Placer un DIV au-dessus d'un TR
    Par Erakis dans le forum Général JavaScript
    Réponses: 5
    Dernier message: 23/07/2006, 18h11
  4. [débutant]Placer une image par dessus une autre
    Par sempire dans le forum Balisage (X)HTML et validation W3C
    Réponses: 2
    Dernier message: 21/11/2005, 18h42

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