[MFC ] [Resolu] clique sur CLIstCtrl

clique sur CLIstCtrl [MFC ] [Resolu] - C++ - Programmation

Marsh Posté le 11-04-2003 à 11:52:46    

Pour savoir sur quelle ligne de ma CListCtrl je viens de cliquer, je prend la methode OnClick
puis

Code :
  1. CListCtrl * plist = (CListCtrl *) GetDlgItem(IDC_LIST1);
  2. POSITION pos = plist->GetFirstSelectedItemPosition();
  3. if (pos == NULL)
  4. AfxMessageBox(CString("clique mais pas ds la bonne colonne" ));
  5. else
  6. {
  7.  while (pos)
  8.  {
  9.   nItem = plist->GetNextSelectedItem(pos);
  10. //et ici j'ai la ligne


mais ceci ne fonctionne que si je clique sur la colonne qui a l'index 0 dans ma liste.
Comment faire pour prendre la ligne peut importe dans quelle colonne je clique?


Message édité par polo021 le 11-04-2003 à 16:16:13
Reply

Marsh Posté le 11-04-2003 à 11:52:46   

Reply

Marsh Posté le 11-04-2003 à 12:04:42    

Faut passer par les methodes HitTest et le mieu a mettre ds un OnMousDown (sur le left button) car tu recup le CPoint avec les coordonnees de la souris au moment du click et tu as plsu qu'a faire
 

Code :
  1. .....::OnLButtonDown(UINT nFlags, CPoint point) {
  2.     int iItem = plistctrl->HitTest(point);
  3.    
  4.     if (iItem == -1) >> pas un item
  5.     else >> iItem = index item selectione
  6. }


 
Edit: attention a verifier quand mm que le curseur de la souris se trouve ds CtrlList avant quand mm.


Message édité par VisualC++ le 11-04-2003 à 12:05:36
Reply

Marsh Posté le 11-04-2003 à 12:10:51    

merci pour ta reponse mais bon, c'est encore et toujours pour Pocket PC donc ecran tactile sur l'engin avec un stylet et j'ai du mal a visualiser le clique gauche [:spamafote]. Enfin je suppose mais je vais voir si il n'y a pas un truc prevu pour ca.
 
Sinon y a pas un autre moyen?

Reply

Marsh Posté le 11-04-2003 à 12:12:09    

Ben tu recuperera quand mm un mousedown (donc tu t en fou du droit ou gauche)
 
Et non tt les methode pour tester un clique ds un clistview tourne autour du HitTest
Edit : enfin a ma connaissance


Message édité par VisualC++ le 11-04-2003 à 12:12:35
Reply

Marsh Posté le 11-04-2003 à 12:36:59    

j'ai pas tout compris ce ke tu voulais...
 
tu clik sur une ligne ou une colonne ? (et tu veux savoir koi exactement) (précise aussi si c'est une listview a multi-selection)
 
si c'est les lignes ke tu veux savoir, y a ca ki devrait marcher :
 

Code :
  1. int i = -1;
  2. while ((i = SendMessage(hWndLV, LVM_GETNEXTITEM, i, MAKELPARAM(LVNI_ALL | LVNI_SELECTED, 0))) != -1)
  3. {
  4. // ton traitement
  5. }


 
en gros (si ca marche, je l'ai repris d'un vieux code), i indique tous les index des lignes seléctionnées.

Reply

Marsh Posté le 11-04-2003 à 12:39:18    

polo021 a écrit :

merci pour ta reponse mais bon, c'est encore et toujours pour Pocket PC donc ecran tactile sur l'engin avec un stylet et j'ai du mal a visualiser le clique gauche [:spamafote]. Enfin je suppose mais je vais voir si il n'y a pas un truc prevu pour ca.
 
Sinon y a pas un autre moyen?


 
Oui : la bonne méthode est de choisir les options de créations de la CListCtrl : il y a un flag qui permet de choisir que la selection se fasse sur toute la ligne. Par contre, je m'en rappelle plus sur le moment. Faudrait que j'aille voir dans mes projets.


---------------
"Dieu a exploité tous nos complexes d'infériorité, en commençant par notre incapacité de croire à notre propre divinité." - Emil Michel Cioran
Reply

Marsh Posté le 11-04-2003 à 12:41:32    

Tetragrammaton IHVH a écrit :


 
Oui : la bonne méthode est de choisir les options de créations de la CListCtrl : il y a un flag qui permet de choisir que la selection se fasse sur toute la ligne. Par contre, je m'en rappelle plus sur le moment. Faudrait que j'aille voir dans mes projets.


 
LVS_EX_FULLROWSELECT

Reply

Marsh Posté le 11-04-2003 à 12:45:41    

Sauf que cette methode requiere des DLL version 4.7 (jsais plus lesquels donc depend de la platefrome sur laqeulle ca tournera, car les ExtendedInfo ne sont pas dispo sur les controls suivant les versions.

Reply

Marsh Posté le 11-04-2003 à 12:48:26    

VisualC++ a écrit :

Sauf que cette methode requiere des DLL version 4.7 (jsais plus lesquels donc depend de la platefrome sur laqeulle ca tournera, car les ExtendedInfo ne sont pas dispo sur les controls suivant les versions.


 
exact...
 
LVS_EX_FULLROWSELECT  
Version 4.70. When an item is selected, the item and all its subitems are highlighted. This style is available only in conjunction with the LVS_REPORT style.  
 
Version DLL Distribution Platform  
4.70 All Microsoft® Internet Explorer 3.x.  
 
ca devrait qd meme marcher sur pocketPC...

Reply

Marsh Posté le 11-04-2003 à 12:50:04    

Jsais pas jamais fait sur pocket :lol:
Par contre j ai un doute sur le IE 3.0, car sur le 5.0 de base y a des pb avec les Extended

Reply

Marsh Posté le 11-04-2003 à 12:50:04   

Reply

Marsh Posté le 11-04-2003 à 12:50:42    

Konar a écrit :


 
LVS_EX_FULLROWSELECT


 
Merci  :jap:


---------------
"Dieu a exploité tous nos complexes d'infériorité, en commençant par notre incapacité de croire à notre propre divinité." - Emil Michel Cioran
Reply

Marsh Posté le 11-04-2003 à 12:54:52    

VisualC++ a écrit :

Jsais pas jamais fait sur pocket :lol:
Par contre j ai un doute sur le IE 3.0, car sur le 5.0 de base y a des pb avec les Extended


 
ca doit dependre des styles, par exemple y en a 1 ki demande direct XP, me souviens plus lequel, mais la plupart des extended demandent IE 5.0 c vrai.
(faut aussi savoir si c'est la vérité, faudra demander aux gens ki codent sur pocketPC si ca marche a l'arrivée...)
 
http://msdn.microsoft.com/library/ [...] styles.asp
http://msdn.microsoft.com/library/ [...] rsions.asp

Reply

Marsh Posté le 11-04-2003 à 13:49:02    

merci les gens
j'essayerai ca et je vous dis quoi

Reply

Marsh Posté le 11-04-2003 à 14:29:43    

Konar a écrit :

j'ai pas tout compris ce ke tu voulais...


ben en fait :
x 10000
y 20000
z 30000
 pour selectionner la deuxieme ligne, ca ne fonctionne que si on clique sur "y" car c'est la colonne qui a l'index 0. et j;'aurais voulu pouvoir selectionner la deuxieme ligne en cliquant soit sur y soit sur 20000
 
Je viens d'essayer avec ta methode mais je n'y arrive pas et pour le LVS_EX_FULLROWSELECT je trouve pas non plus.

Reply

Marsh Posté le 11-04-2003 à 14:36:44    

Code :
  1. SendMessage(hWndListView, LVM_SETEXTENDEDLISTVIEWSTYLE, NULL, LVS_EX_FULLROWSELECT);


 
et il faut aussi ke ta listview soit créée avec le style LVS_REPORT.
 
ca serait quand meme chelou si ca marchait pas...

Reply

Marsh Posté le 11-04-2003 à 14:45:48    

Konar a écrit :

Code :
  1. SendMessage(hWndListView, LVM_SETEXTENDEDLISTVIEWSTYLE, NULL, LVS_EX_FULLROWSELECT);


 
et il faut aussi ke ta listview soit créée avec le style LVS_REPORT.
 
ca serait quand meme chelou si ca marchait pas...


 
C'est pas une listview c'est une listctrl, je sais pas si c'est la meme chose ou pas, je suppose que oui.
 
pour le LVS_report c'est bien comme ca qu'elle est.
 
hWndListView => c'est quoi ca?
 

Reply

Marsh Posté le 11-04-2003 à 14:49:18    

Code :
  1. GetDlgItem(IDC_TALISTE)->GetSafeHwnd()


Message édité par VisualC++ le 11-04-2003 à 14:49:36
Reply

Marsh Posté le 11-04-2003 à 14:51:54    

polo021 a écrit :


 
C'est pas une listview c'est une listctrl, je sais pas si c'est la meme chose ou pas, je suppose que oui.
 
pour le LVS_report c'est bien comme ca qu'elle est.
 
hWndListView => c'est quoi ca?
 
 


 
C'est quasiment pareil. Seule l'encapsulation change (l'un est un contrôle, l'autre une vue pour SDI)


---------------
"Dieu a exploité tous nos complexes d'infériorité, en commençant par notre incapacité de croire à notre propre divinité." - Emil Michel Cioran
Reply

Marsh Posté le 11-04-2003 à 15:08:36    

int i = -1;  
while ((i = SendMessage(hWndLV, LVM_GETNEXTITEM, i, MAKELPARAM(LVNI_ALL | LVNI_SELECTED, 0))) != -1)  
{  
// ton traitement  
}  
 
ca fonctionne pas, quand j'affiche i :
- si j'ai clique dans la premiere colonne, ca me donne bien le numero de la ligne
- si j'ai clique dans la deuxieme colonne, ca me retourne -1 donc c'est pas bon ou alors j'ai pas su le faire fonctionne.
 
Mais bon c'est pas bien grave on va pas s'eterniser sur un ptit probleme comme ca. merci quand meme pour votre aide.

Reply

Marsh Posté le 11-04-2003 à 15:16:58    

Mais tu as fait ds ton init lors des contructions

Code :
  1. pList = (CTaListeCtrl*) GetDlgItem(IDC_TALISTE);
  2. pList->SendMessage(LVM_SETEXTENDEDLISTVIEWSTYLE, LVS_EX_FULLROWSELECT, 1);


 
:??:

Reply

Marsh Posté le 11-04-2003 à 15:18:35    

c'est normal ke ca marche pas, cette reponse c'est juste pour trouver les index des éléments sélectionnés (j'avais pas encore vraiment compris ce ke tu voulais a cet instant).
 
si le truc du LVS_EX_FULLROWSELECT marche pas, y a peu de chance pour ke ca fonctionne un jour, a part faire une methode débile a la bourrin (genre chopper les coordonnées de la souris, calculer a la main si t'as cliqué sur telle ligne telle colonne puis sélectionner la bonne ligne encore a la main en envoyant le bon msg, mais faut serieusement eviter ce genre de choses, en plus t'y passera bien 20h...)

Reply

Marsh Posté le 11-04-2003 à 15:19:19    

Euh la methode de detection souris ca prend 2 min :p

Reply

Marsh Posté le 11-04-2003 à 15:21:58    

VisualC++ a écrit :

Euh la methode de detection souris ca prend 2 min :p


 
non 20h pour moi c'etait une bonne appreciation   :whistle:

Reply

Marsh Posté le 11-04-2003 à 15:24:14    

VisualC++ a écrit :

Mais tu as fait ds ton init lors des contructions

Code :
  1. pList = (CTaListeCtrl*) GetDlgItem(IDC_TALISTE);
  2. pList->SendMessage(LVM_SETEXTENDEDLISTVIEWSTYLE, LVS_EX_FULLROWSELECT, 1);


 
:??:


 
ca ne force en rien la selection de la ligne par clique dans n'importe quelle colonne, je viens d'essayer [:spamafote]

Reply

Marsh Posté le 11-04-2003 à 15:35:40    

polo021 a écrit :


 
ca ne force en rien la selection de la ligne par clique dans n'importe quelle colonne, je viens d'essayer [:spamafote]


 
chelou...
essayes ces autres styles, comme ils sont visuels, si ca marche pas ca se verra de suite :
 
LVS_EX_GRIDLINES (rajoute des grilles ds ta listview, du plus bel effet)
LVS_EX_HEADERDRAGDROP (permet de bouger les colonnes)
 
si aucun des 2 ne marche, bah oublie ca.

Reply

Marsh Posté le 11-04-2003 à 15:36:38    

VisualC++ a écrit :

Euh la methode de detection souris ca prend 2 min :p


 
 :heink:

Reply

Marsh Posté le 11-04-2003 à 15:40:43    

Tiens, à propos de CListCtrl, il va falloir prochainement que je me replonge dedans pour faire des tris avec les colonnes. Qqn a déjà expérimenté ça ?
 
Y a un callback, non ?


---------------
"Dieu a exploité tous nos complexes d'infériorité, en commençant par notre incapacité de croire à notre propre divinité." - Emil Michel Cioran
Reply

Marsh Posté le 11-04-2003 à 15:44:01    

Polo021 > euh j ai marque une connerie en plus , c est pas 1 mais le mm const qu il faut

Code :
  1. (CtaListeView*)GetDlgItem(IDC_TaLiset)->SendMessage(LVM_SETEXTENDEDLISTVIEWSTYLE, LVS_EX_FULLROWSELECT, LVS_EX_FULLROWSELECT);


 
 
Tetra > oui y a callback

Reply

Marsh Posté le 11-04-2003 à 15:46:16    

CListCtrl * plist = (CListCtrl *) GetDlgItem(IDC_LIST1);
 
 plist->SendMessage(LVM_SETEXTENDEDLISTVIEWSTYLE,LVS_EX_GRIDLINES , 1);
 
oui, le rajouteage de grille dans la liste fonctionne (quand je clique dessus)
 
Mais pour le fullrowselect je comprends pas. [:spamafote]

Reply

Marsh Posté le 11-04-2003 à 15:47:55    

polo021 a écrit :

 
Mais pour le fullrowselect je comprends pas. [:spamafote]


 
Bon je vais voir dans un de mes projets, parce qu'il y a visiblement un stress, là.


---------------
"Dieu a exploité tous nos complexes d'infériorité, en commençant par notre incapacité de croire à notre propre divinité." - Emil Michel Cioran
Reply

Marsh Posté le 11-04-2003 à 15:47:57    


 
 
Ben ca prend 2 min a faire la detection a la souris, y a les fonction HitTest et CWnd::GetWindowRect / CRect::PtInRect qui facilite la vie.

Reply

Marsh Posté le 11-04-2003 à 15:47:59    

CListCtrl * plist = (CListCtrl *) GetDlgItem(IDC_LIST1);
 
 plist->SendMessage(LVM_SETEXTENDEDLISTVIEWSTYLE,LVS_EX_GRIDLINES , 1);
 
oui, le rajouteage de grille dans la liste fonctionne (quand je clique dessus)
 
Mais pour le fullrowselect je comprends pas. [:spamafote]

Reply

Marsh Posté le 11-04-2003 à 15:50:08    

Fait comme marque audessus, le (... , 1) marche pas
 
Edit:
Le gridline marche avec (...., 1) car

Code :
  1. #define LVS_EX_GRIDLINES        0x00000001


;)


Message édité par VisualC++ le 11-04-2003 à 15:51:28
Reply

Marsh Posté le 11-04-2003 à 15:50:31    

Tetragrammaton IHVH a écrit :

Tiens, à propos de CListCtrl, il va falloir prochainement que je me replonge dedans pour faire des tris avec les colonnes. Qqn a déjà expérimenté ça ?
 
Y a un callback, non ?

la fonction de comparaison

Code :
  1. int CALLBACK CDlgClasse1::MyCompareProc(LPARAM lParam1, LPARAM lParam2, LPARAM lParamSort)
  2. {
  3. CListCtrl* pListCtrl = (CListCtrl*) lParamSort;
  4. CString    strItem1 = pListCtrl->GetItemText(lParam1, 0);
  5. CString    strItem2 = pListCtrl->GetItemText(lParam2, 0);
  6. int comp = strItem1.CompareNoCase(strItem2);
  7. return comp;
  8. }


Code :
  1. void CDlgclasse1::m_fnvSetItemData()
  2. {
  3. CListCtrl * plist = (CListCtrl *) GetDlgItem(IDC_LIST1);
  4. int iNum = plist->GetItemCount();
  5.     for (int i=0; i<iNum; i++)
  6.      plist->SetItemData(i, i);
  7. }


l'appel

Code :
  1. m_fnvSetItemData();
  2. plist->SortItems(MyCompareProc, (LPARAM) plist);

Reply

Marsh Posté le 11-04-2003 à 15:55:10    

VisualC++ a écrit :

Polo021 > euh j ai marque une connerie en plus , c est pas 1 mais le mm const qu il faut

Code :
  1. (CtaListeView*)GetDlgItem(IDC_TaLiset)->SendMessage(LVM_SETEXTENDEDLISTVIEWSTYLE, LVS_EX_FULLROWSELECT, LVS_EX_FULLROWSELECT);


 
 
Tetra > oui y a callback


 [:trey azagthoth]  
youpi ca fonctionne   [:tozwarrior]  :jap:

Reply

Marsh Posté le 11-04-2003 à 15:57:28    

Bon, voila le code que j'utilise pour créer une CListCtrl
 

Code :
  1. view2D->Create( WS_CHILD | LVS_REPORT | LVS_NOSORTHEADER | WS_TABSTOP | WS_VSCROLL, rRect, this, ID_LISTCTRL );
  2. view2D->SetExtendedStyle( LVS_EX_FULLROWSELECT | WS_EX_CLIENTEDGE | WS_EX_RIGHTSCROLLBAR); 
  3. view2D->SetImageList(view2DImages,LVSIL_SMALL);


 
C'est bien LVS_EX_FULLROWSELECT. Les autres options n'ont pas d'influence sur ça.


---------------
"Dieu a exploité tous nos complexes d'infériorité, en commençant par notre incapacité de croire à notre propre divinité." - Emil Michel Cioran
Reply

Marsh Posté le 11-04-2003 à 15:58:38    

polo021 a écrit :


 [:trey azagthoth]  
youpi ca fonctionne   [:tozwarrior]  :jap:  


 
OK Cool.  
 
Et merci pour le code des tris  :jap:


---------------
"Dieu a exploité tous nos complexes d'infériorité, en commençant par notre incapacité de croire à notre propre divinité." - Emil Michel Cioran
Reply

Marsh Posté le 11-04-2003 à 16:31:51    

polo021 a écrit :


 [:trey azagthoth]  
youpi ca fonctionne   [:tozwarrior]  :jap:  


 
dommage, j'aurais bien kiffé voir la solution "2 min" de Visual C++
 
tiens ca me rappelle un code ke je corrigeais (sous win), dedans y avais un gars qu'avait codé une fct pour copier un fichier d'un emplacement a un autre, a base de open/read avec un buffer de 1 Mo, et le fichier de sortie etait multiple de 1 Mo qqsoit le fichier d'entrée. c'etait bo.

Reply

Marsh Posté le 11-04-2003 à 16:37:17    

Te mettrais un code quand je rentre np

Reply

Marsh Posté le 11-04-2003 à 17:52:49    

La version ds une dialog avec recuperation du Click (reflect event de la liste)
 

Code :
  1. void CTestProjetDlg::OnClickList1(NMHDR* pNMHDR, LRESULT* pResult)
  2. {
  3. CListView* pList = (CListView*) GetDlgItem(IDC_LIST1);
  4. NM_LISTVIEW* pNMListView = (NM_LISTVIEW*)pNMHDR;
  5. int index, column;
  6. if( ( index = m_fniHitTestEx( CPoint(pNMListView->ptAction), &column )) != -1 ) {
  7.  TRACE("Line %d / Sub Item %d selected\n", index, column);
  8. }
  9. *pResult = 0;
  10. }
  11. int CTestProjetDlg::m_fniHitTestEx(CPoint &point, int *col) const
  12. {
  13. CListView* pList = (CListView*) GetDlgItem(IDC_LIST1);
  14. int colnum = 0;
  15. int row = pList->GetListCtrl().HitTest( point, NULL );
  16. if( col ) *col = 0;
  17. if( (::GetWindowLong(pList->GetSafeHwnd(), GWL_STYLE) & LVS_TYPEMASK) != LVS_REPORT )
  18.   return row;
  19. row = pList->GetListCtrl().GetTopIndex();
  20. int bottom = row + pList->GetListCtrl().GetCountPerPage();
  21. if( bottom > pList->GetListCtrl().GetItemCount() )
  22.   bottom = pList->GetListCtrl().GetItemCount();
  23. CHeaderCtrl* pHeader = (CHeaderCtrl*)pList->GetDlgItem(0);
  24. int nColumnCount = pHeader->GetItemCount();
  25. for( ;row <=bottom;row++) {
  26.  CRect rect;
  27.  pList->GetListCtrl().GetItemRect( row, &rect, LVIR_BOUNDS );
  28.  if( rect.PtInRect(point) ) {
  29.   for( colnum = 0; colnum < nColumnCount; colnum++ ) {
  30.    int colwidth = pList->GetListCtrl().GetColumnWidth(colnum);
  31.    if( point.x >= rect.left && point.x <= (rect.left + colwidth ) ) {
  32.      if( col ) *col = colnum;
  33.      return row;
  34.    }
  35.    rect.left += colwidth;
  36.   }
  37.  }
  38. }
  39. return -1;
  40. }


 
Ca a pas besoin de l'extended style. Par contre bon 5 min le temsp de trouver une fonction HitTestEx qq part ds mes sources.
 
Edit: par contre si on utilise un CListCtrl a nous, on doit pourvoir utilsier les infos contenues ds le NMHDR* qui est passe sur le click, mais bon jsais pas si info remontee qqsoit la version des DLL utilisees.


Message édité par VisualC++ le 11-04-2003 à 17:55:00
Reply

Marsh Posté le    

Reply

Sujets relatifs:

Leave a Replay

Make sure you enter the(*)required information where indicate.HTML code is not allowed