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 :

VitualTreeView et IVTEditLink


Sujet :

C++Builder

  1. #1
    Membre confirm�
    Profil pro
    Inscrit en
    Janvier 2003
    Messages
    229
    D�tails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Janvier 2003
    Messages : 229
    Par d�faut VitualTreeView et IVTEditLink
    Bonjour,

    J'utilise un virtualtreeview et j'ai besoin d'�diter plusieurs colonnes.
    Une d'elle est une combobox, j'ai cr�� ma classe d�riv�e de IVTEditLink que j'appelle via l'�v�nement CreateEditor et �a fonctionne tr�s bien.
    Probl�me, ce mode d'�dition s'applique sur toutes les colonnes �ditables alors que je ne souhaite la combo que sur une seule. Sur les autres je voudrais laisser l'�dition de base.
    J'ai essay� dans CreateEditor ne faire appel � ma class que si je suis sur la colonne qui m�int�resse, mais du coup j'obtiens le message d'erreur suivant lorsque j'essaye d'�diter une autre colonne :
    Edit Link must not be nil

    Quelqu'un sait il comment faire pour obtenir 2 modes d'�dition diff�rents ?

    merci !
    Pascale38

  2. #2
    Expert �minent
    Avatar de ShaiLeTroll
    Homme Profil pro
    D�veloppeur C++\Delphi
    Inscrit en
    Juillet 2006
    Messages
    14 089
    D�tails du profil
    Informations personnelles :
    Sexe : Homme
    �ge : 44
    Localisation : France, Seine Saint Denis (�le de France)

    Informations professionnelles :
    Activit� : D�veloppeur C++\Delphi
    Secteur : High Tech - �diteur de logiciels

    Informations forums :
    Inscription : Juillet 2006
    Messages : 14 089
    Par d�faut
    Je ne connais pas VirtualTreeView, il semble que le OnCreateEditor fourni des param�tres, un Sender �videmment ainsi qu'un param�tre Column.

    Pourquoi ne pas cr�er un IVTEditLink par d�faut, il doit bien y avoir une classe par d�faut pour impl�menter cette interface ?
    Regarde dans le code source Delphi de DoCreateEditor, il doit y avoir un code genre :
    Code delphi : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
    7
    function TVirtualTreeView.DoCreateEditor(Column): IVTEditLink 
    begin
      if FOnCreateEditor then
        FOnCreateEditor(Self, Column, Result)
      else
        Result := LaClasseParDéfaut.Create();  
    end;



    Sinon, pour une simple ComboBox dans une colonne il n'y a rien de plus simple ?
    Tu n'aurais pas une propri�t� PickList comme on pourrait le voir dans la TDBGrid ?
    Aide via F1 - FAQ - Guide du d�veloppeur Delphi devant un probl�me - Pensez-y !
    Attention Troll M�chant !
    "Quand un homme a faim, mieux vaut lui apprendre � p�cher que de lui donner un poisson" Confucius
    Mieux vaut se taire et para�tre idiot, Que l'ouvrir et de le confirmer !
    L'ignorance n'excuse pas la m�diocrit� !

    L'exp�rience, c'est le nom que chacun donne � ses erreurs. (Oscar Wilde)
    Il faut avoir le courage de se tromper et d'apprendre de ses erreurs

  3. #3
    Membre confirm�
    Profil pro
    Inscrit en
    Janvier 2003
    Messages
    229
    D�tails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Janvier 2003
    Messages : 229
    Par d�faut
    Salut ShaiLeTroll,

    pas trouv� plus simple que le IVTEditLink malheureusement ! Tout ce que j'ai trouv� c'est de devoir cr�er la classe qui d�rive donc de IVTEditLink.
    Autant les checkBox sont pr�sentes nativement dans le composant, autant rien concernant les combo...

    J'ai cherch� du c�t� de la classe par d�faut bien s�r, mais je n'ai pas trouv�, d'o� le post...

    j'ai trouv� �a dans les sources
    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
    7
    8
    9
     
    function TCustomVirtualStringTree.DoCreateEditor(Node: PVirtualNode; Column: TColumnIndex): IVTEditLink;
     
    begin
      Result := inherited DoCreateEditor(Node, Column);
      // Enable generic label editing support if the application does not have own editors.
      if Result = nil then
        Result := TStringEditLink.Create;
    end;
    mais je ne sais pas trop comment m'en servir et en c++ en plus...???
    (je connais rien au delphi !!!)

    Il semblerait que la solution soit dans ma classe d�riv�e de g�rer les diff�rentes �ditions possibles selon ma colonne... pfff quel boulot juste pour une combo !

  4. #4
    Expert �minent
    Avatar de ShaiLeTroll
    Homme Profil pro
    D�veloppeur C++\Delphi
    Inscrit en
    Juillet 2006
    Messages
    14 089
    D�tails du profil
    Informations personnelles :
    Sexe : Homme
    �ge : 44
    Localisation : France, Seine Saint Denis (�le de France)

    Informations professionnelles :
    Activit� : D�veloppeur C++\Delphi
    Secteur : High Tech - �diteur de logiciels

    Informations forums :
    Inscription : Juillet 2006
    Messages : 14 089
    Par d�faut
    Eh bien mon LaClasseParD�faut correspond donc � TStringEditLink
    Le code devrait g�rer l'utilisation du NULL (nil) et fournir une instance par d�faut, tu as une �trange erreur !

    il te suffit de faire

    Tu as bien utiliser OnCreateEditor (via l'inspecteur d'objet) ? tu n'as pas fait un h�ritage de TVirtualTreeView et red�fini DoCreateEditor ?

    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
    7
    void TForm1::VirtualTreeView1CreateEditor(TObject* Sender, TColumnIndex Column, IVTEditLink* &EditLink)
    {
      if (Column == IndexDELaColonneAvecCombo)
        EditLink = new TComboLinkDePascale38();
      else
        EditLink = new TStringEditLink();
    }
    cherche dans le code un raise avec le message "Edit Link must not be nil"
    Soit c'est une Exception sp�cifique au TVirtualTreeView
    Soit c'est une Assertion (EAssertionFailed) avec la fonction Assert()

    Lorsque l'on fait du C++Builder, il est important de savoir lire du Delphi, surtout lorsque l'on utilise des composants externes avec des documentations souvent l�g�res !
    Aide via F1 - FAQ - Guide du d�veloppeur Delphi devant un probl�me - Pensez-y !
    Attention Troll M�chant !
    "Quand un homme a faim, mieux vaut lui apprendre � p�cher que de lui donner un poisson" Confucius
    Mieux vaut se taire et para�tre idiot, Que l'ouvrir et de le confirmer !
    L'ignorance n'excuse pas la m�diocrit� !

    L'exp�rience, c'est le nom que chacun donne � ses erreurs. (Oscar Wilde)
    Il faut avoir le courage de se tromper et d'apprendre de ses erreurs

  5. #5
    Membre confirm�
    Profil pro
    Inscrit en
    Janvier 2003
    Messages
    229
    D�tails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Janvier 2003
    Messages : 229
    Par d�faut
    on a donc :
    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
    7
    8
    9
     
    function TCustomVirtualStringTree.DoCreateEditor(Node: PVirtualNode; Column: TColumnIndex): IVTEditLink;
     
    begin
      Result := inherited DoCreateEditor(Node, Column);
      // Enable generic label editing support if the application does not have own editors.
      if Result = nil then
        Result := TStringEditLink.Create;
    end;
    et TCustomVirtualStringTree h�rite de TBaseVirtualTree :
    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
     
     TCustomVirtualStringTree = class(TBaseVirtualTree)
    et
    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
     
    function TBaseVirtualTree.DoCreateEditor(Node: PVirtualNode; Column: TColumnIndex): IVTEditLink;
     
    begin
      Result := nil;
      if Assigned(FOnCreateEditor) then
      begin
        FOnCreateEditor(Self, Node, Column, Result);
        if Result = nil then
          ShowError(SEditLinkIsNil, hcTFEditLinkIsNil);
      end;
    end;
    c'est de la que vient le message, et du coup il appara�t avant l'appel de
    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
     
    TStringEditLink.Create
    suis un peu perdue l�...

  6. #6
    Expert �minent
    Avatar de ShaiLeTroll
    Homme Profil pro
    D�veloppeur C++\Delphi
    Inscrit en
    Juillet 2006
    Messages
    14 089
    D�tails du profil
    Informations personnelles :
    Sexe : Homme
    �ge : 44
    Localisation : France, Seine Saint Denis (�le de France)

    Informations professionnelles :
    Activit� : D�veloppeur C++\Delphi
    Secteur : High Tech - �diteur de logiciels

    Informations forums :
    Inscription : Juillet 2006
    Messages : 14 089
    Par d�faut
    As-tu essay� mon exemple de code de 13h16, en cr�ant manuellement un TStringEditLink dont le Gestionnaire d'�v�menent OnCreateEditor

    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
    7
    void TForm1::VirtualStringTree1CreateEditor(TObject* Sender, PVirtualNode Node, TColumnIndex Column, IVTEditLink* &EditLink)
    {
      if (Column == IndexDELaColonneAvecCombo)
        EditLink = new TComboLinkDePascale38();
      else
        EditLink = new TStringEditLink();
    }
    Aide via F1 - FAQ - Guide du d�veloppeur Delphi devant un probl�me - Pensez-y !
    Attention Troll M�chant !
    "Quand un homme a faim, mieux vaut lui apprendre � p�cher que de lui donner un poisson" Confucius
    Mieux vaut se taire et para�tre idiot, Que l'ouvrir et de le confirmer !
    L'ignorance n'excuse pas la m�diocrit� !

    L'exp�rience, c'est le nom que chacun donne � ses erreurs. (Oscar Wilde)
    Il faut avoir le courage de se tromper et d'apprendre de ses erreurs

  7. #7
    Membre confirm�
    Profil pro
    Inscrit en
    Janvier 2003
    Messages
    229
    D�tails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Janvier 2003
    Messages : 229
    Par d�faut
    oui d�sol�e, me revoil� !!!
    alors j'ai test� �a (il faut passer par un QueryInterface) :

    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
     
    void __fastcall TLabelForm::VirtualStringTreeCreateEditor
    	(TBaseVirtualTree *Sender,
    	PVirtualNode Node, TColumnIndex Column, IVTEditLink *EditLink){
    	if (Column == IndexDELaColonneAvecCombo){
    		TMyEditLink *NewEditLink = new TMyEditLink(true);
    		NewEditLink->QueryInterface(__uuidof(IVTEditLink), (void**)EditLink);
    	}
    	else{
    		TStringEditLink *NewEditLink = new TStringEditLink();
    		NewEditLink->QueryInterface(__uuidof(IVTEditLink), (void**)EditLink);
    	}
    }
    et �a a l'air de bien fonctionner !!
    Je continue mes tests, et si je ne trouve pas de probl�me majeur je mettrai le post en r�solu !!

    encore une fois, merci � toi !!!
    Pascale38

  8. #8
    Expert �minent
    Avatar de ShaiLeTroll
    Homme Profil pro
    D�veloppeur C++\Delphi
    Inscrit en
    Juillet 2006
    Messages
    14 089
    D�tails du profil
    Informations personnelles :
    Sexe : Homme
    �ge : 44
    Localisation : France, Seine Saint Denis (�le de France)

    Informations professionnelles :
    Activit� : D�veloppeur C++\Delphi
    Secteur : High Tech - �diteur de logiciels

    Informations forums :
    Inscription : Juillet 2006
    Messages : 14 089
    Par d�faut
    Fait attention tout de m�me, l'utilisation d'interface implique probablement un compteur de r�f�rence et une lib�ration automatique par les DelphiInterface !

    TMyEditLink et TStringEditLink n'impl�mente pas IVTEditLink directement ?

    IVTEditLink est-ce un __interface ou un DelphiInterface ?

    v�rifie l'exactitude du prototype entre les diff�rentes possibilit�s

    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    IVTEditLink *EditLink
    IVTEditLink **EditLink
    IVTEditLink* &EditLink
    _di_IVTEditLink &EditLink
    la derni�re syntaxe �tant en r�alit� la plus proche de celle des interfaces Delphi !
    Aide via F1 - FAQ - Guide du d�veloppeur Delphi devant un probl�me - Pensez-y !
    Attention Troll M�chant !
    "Quand un homme a faim, mieux vaut lui apprendre � p�cher que de lui donner un poisson" Confucius
    Mieux vaut se taire et para�tre idiot, Que l'ouvrir et de le confirmer !
    L'ignorance n'excuse pas la m�diocrit� !

    L'exp�rience, c'est le nom que chacun donne � ses erreurs. (Oscar Wilde)
    Il faut avoir le courage de se tromper et d'apprendre de ses erreurs

  9. #9
    Membre confirm�
    Profil pro
    Inscrit en
    Janvier 2003
    Messages
    229
    D�tails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Janvier 2003
    Messages : 229
    Par d�faut
    En ce qui concerne IVTEditLink , je n'ai pas trouv� les sources en C++, mais voil� le bout de code delphi :
    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
     
      IVTEditLink = interface
        ['{2BE3EAFA-5ACB-45B4-9D9A-B58BCC496E17}']
        function BeginEdit: Boolean; stdcall;                  // Called when editing actually starts.
        function CancelEdit: Boolean; stdcall;                 // Called when editing has been cancelled by the tree.
        function EndEdit: Boolean; stdcall;                    // Called when editing has been finished by the tree.
        function PrepareEdit(Tree: TBaseVirtualTree; Node: PVirtualNode; Column: TColumnIndex): Boolean; stdcall;
                                                               // Called after creation to allow a setup.
        function GetBounds: TRect; stdcall;                    // Called to get the current size of the edit window
                                                               // (only important if the edit resizes itself).
        procedure ProcessMessage(var Message: TMessage); stdcall;
                                                               // Used to forward messages to the edit window(s)-
        procedure SetBounds(R: TRect); stdcall;                // Called to place the editor.
      end;
    quand au compteur de r�f�rence, c'est g�rer dans TMyEditLink dont voici le code (r�cup�r� sur internet)
    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
    117
    118
    119
    120
    121
    122
    123
    124
    125
    126
    127
    128
    129
    130
    131
    132
    133
    134
    135
    136
    137
     
    class TMyEditLink : public IVTEditLink
    {
    private:
    	TComboBox *FComboBox;
    	TBaseVirtualTree* FTree;
    	PVirtualNode FNode;
    	TColumnIndex FColumn;
    	TNodeLabel *FNodeData;
    	unsigned long m_RefCount;
     
    public:
    	/* general */
    	__fastcall TMyEditLink() : IVTEditLink()
    	{
    		// initialise
    		FComboBox = new TComboBox(HWND(NULL));
    		FComboBox->Style = csDropDownList;
    		FComboBox->Visible = false;
    		m_RefCount = 0;
    	}
     
    	__fastcall ~TMyEditLink()
    	{
    		// free memory
    		delete FComboBox;
    	}
     
    	/* IVTEditLink */
    	virtual bool __stdcall BeginEdit(void)
    	{
    		// show combo
    		FComboBox->Show();
    		FComboBox->SetFocus();
     
    		return true;
    	}
     
    	virtual bool __stdcall CancelEdit(void)
    	{
    		// hide combo
    		FComboBox->Hide();
    		FTree->SetFocus();
     
    		return true;
    	}
     
    	virtual bool __stdcall EndEdit(void)
    	{
    		// set new data
    		FNodeData->type = FComboBox->Text;
    		if (FNodeData->usage != NULL)
    		{
    			FNodeData->usage->type = FComboBox->Text;
    		}
     
    		// hide combo
    		FComboBox->Hide();
    		FTree->SetFocus();
     
    		return true;
    	}
     
    	virtual bool __stdcall PrepareEdit(TBaseVirtualTree* Tree,
    		PVirtualNode Node,
    		TColumnIndex Column)
    	{
    		// set ptrs
    		FTree = Tree;
    		FNode = Node;
    		FColumn = Column;
     
    		// get data for node
    		FNodeData = (TNodeLabel*)(FTree->GetNodeData(FNode));
     
    		// init combobox
    		FComboBox->Parent = FTree;
    		FComboBox->Items->CommaText = "Setting,Measure,Fault,State";
    		FComboBox->ItemIndex =
    			FComboBox->Items->IndexOf(FNodeData->type);
     
    		return true;
    	}
     
    	virtual TRect __stdcall GetBounds(void)
    	{
    		return FComboBox->BoundsRect;
    	}
     
    	virtual void __stdcall ProcessMessage(TMessage &Message)
    	{
    		FComboBox->WindowProc(Message);
    	}
     
    	virtual void __stdcall SetBounds(const TRect R)
    	{
    		FComboBox->BoundsRect =
    			FTree->GetDisplayRect(FNode, FColumn, false, true);
    	}
     
    	/* IUnkown */
    	virtual HRESULT __stdcall QueryInterface(const IID& iid, void** ppv)
    	{
    		if (iid == IID_IUnknown || iid == __uuidof(IVTEditLink))
    		{
    			*ppv = static_cast<IVTEditLink*>(this);
    		}
    		else
    		{
    			*ppv = 0;
    			return E_NOINTERFACE;
    		}
     
    		(reinterpret_cast<IUnknown*>(*ppv))->AddRef();
    		return S_OK;
    	}
     
    	virtual unsigned long __stdcall AddRef(void)
    	{
    		return static_cast<unsigned long>(InterlockedIncrement(
    			reinterpret_cast<long*>(&m_RefCount)));
    	}
     
    	virtual unsigned long __stdcall Release(void)
    	{
    		if (m_RefCount == 1)
    		{
    			delete this;
    			return 0;
    		}
    		else
    		{
                            return static_cast<unsigned long>(InterlockedDecrement(
    				reinterpret_cast<long*>(&m_RefCount)));
    		}
    	}
    };

+ R�pondre � la discussion
Cette discussion est r�solue.

Discussions similaires

  1. VirtualTreeView et IVTEditLink
    Par Pascale38 dans le forum Composants VCL
    R�ponses: 1
    Dernier message: 21/11/2011, 11h09

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