WM_LBUTTONDBLCLK netratat

Intrebari legate de programarea cu biblioteci precum MFC, ATL, WTL si GDI+.
Post Reply
0ptr
Membru
Membru
Posts: 71
Joined: 01 Feb 2011, 23:27
Judet: Ilfov

WM_LBUTTONDBLCLK netratat

Post by 0ptr » 07 Jun 2012, 12:55

Am o aplicatie construita cu wizard-ul din VS2010 de tipul MDI cu project style Visual Studio (usor de generat din cateva click-uri).
In stanga am un tree generat de wizard ca demo intr-o clasa de CClassView : public CDockablePane.

Incerc sa tratez mesaje de mouse pe item-urile tree-ului cu handler-ele aferente genrate de Class Wizard (WM_LBUTTONDBLCLK) dar e noapte... Mesajele de right/left click up/down nu sunt prinse desi in zona de message maps am: ON_WM_LBUTTONDBLCLK() , ON_WM_LBUTTONDOWN(), ON_WM_RBUTTONDOWN(), ON_WM_RBUTTONUP().
Am dat o geana cu Spy++ si iata cam ce am prins:
mouse_messages.png
mouse_messages.png (15.98 KiB) Viewed 4775 times
Aveti idee cum as putea prinde aceste mesaje in aplicatia mea?



User avatar
Silviu Ardelean
Senior
Senior
Posts: 1175
Joined: 12 Jul 2007, 09:22
Judet: Timiş
Location: Timisoara
Contact:

Re: WM_LBUTTONDBLCLK netratat

Post by Silviu Ardelean » 07 Jun 2012, 13:22

O varianta de-a prinde mesajele ar fi sa metoda PreTranslateMessage().

Code: Select all

BOOL CClassView::PreTranslateMessage(MSG* pMsg)
{
	switch (pMsg->message)
    {
		case WM_LBUTTONDBLCLK:
			OnLButtonDblClk( MK_LBUTTON, pMsg->pt);
        break;

        default:
        break;
    }

	return CDockablePane::PreTranslateMessage(pMsg);
}

User avatar
Ovidiu Cucu
Fondator
Fondator
Posts: 3776
Joined: 11 Jul 2007, 16:10
Judet: Iaşi
Location: Iasi
Contact:

Re: WM_LBUTTONDBLCLK netratat

Post by Ovidiu Cucu » 07 Jun 2012, 14:47

Am o mica observatie. In general e bine sa eviti sa chemi handlere de mesaje de pe unde te taie capul.
Sa zicem ca aici rezolvam problema si stergem/comentam apelul la handlerul din clasa de baza...

Code: Select all

void CClassView::OnLButtonDblClk(UINT nFlags, CPoint point)
{
   // CDockablePane::OnLButtonDblClk(nFlags, point); // <- DELETE THIS
   // blah-blah...
}
...si evitam astfel ceva care nu trebuie facut, intr-o aplicatie babana s-ar putea sa ajungi sa-ti prinzi urechile prin handlere.
Asa ca, lasa handlerele asa cum sunt apelate de la mama lor framework si, daca vrei sa face ceva mai special fa-o intr-o functie privata.
Exemplu:

Code: Select all

BOOL CClassView::PreTranslateMessage(MSG* pMsg)
{
   switch(pMsg->message)
   {
   case WM_LBUTTONDBLCLK:
      _DoSomethingCool(pMsg->pt);
      break;
      // ...
   }
   return CDockablePane::PreTranslateMessage(pMsg);
}

User avatar
Marius Bancila
Fondator
Fondator
Posts: 2344
Joined: 11 Jul 2007, 11:45
Judet: Timiş
Location: Timisoara
Contact:

Re: WM_LBUTTONDBLCLK netratat

Post by Marius Bancila » 07 Jun 2012, 15:49

O "rule of thumb" (cum ii zice la asta in Romana?) e ca handlerele sunt metoda apelate de framework, si nu trebuie sa le apelezi in mod explicit. Daca ai ceva functionalitate intr-un handler ce trebuie sa se executa si din alt context, atunci fa putin refactoring, extrage acea functionalitate intr-o functie separata si apeleaz-o de unde e nevoie.
Marius Bancila
Fondator Codexpert, Microsoft MVP VC++
Site personal | Blog

0ptr
Membru
Membru
Posts: 71
Joined: 01 Feb 2011, 23:27
Judet: Ilfov

Re: WM_LBUTTONDBLCLK netratat

Post by 0ptr » 07 Jun 2012, 15:55

1st Multumesc! :)
Problema ce-am sesizat-o eu si am expus-o mai sus pare a fi un bug. Practic cu ON_WM_LBUTTONDBLCLK() in zona de messages map nu se intampla nimic si am zis sa nu fac o ciobaneala de genu' celei prezentate de Ovidiu initial (primul sample).
De aceea ma gandeam la fel diverse idei, de genul mesajelor reflectate.

User avatar
Ovidiu Cucu
Fondator
Fondator
Posts: 3776
Joined: 11 Jul 2007, 16:10
Judet: Iaşi
Location: Iasi
Contact:

Re: WM_LBUTTONDBLCLK netratat

Post by Ovidiu Cucu » 07 Jun 2012, 16:02

Marius Bancila wrote:... Daca ai ceva functionalitate intr-un handler ce trebuie sa se executa si din alt context, atunci fa putin refactoring, extrage acea functionalitate intr-o functie separata si apeleaz-o de unde e nevoie.
[ off-topic ]
Aha, deci asta inseamna vestitul "refactoring" cu care se bat unii in piept. Nu stiam ca fac asta de-o viata... :D

User avatar
Marius Bancila
Fondator
Fondator
Posts: 2344
Joined: 11 Jul 2007, 11:45
Judet: Timiş
Location: Timisoara
Contact:

Re: WM_LBUTTONDBLCLK netratat

Post by Marius Bancila » 08 Jun 2012, 00:32

Da, asta e "extract method" (http://www.refactoring.com/catalog/extractMethod.html). Inca putin si o sa-ti dai seama ca folosesti si design patterns de o viata si acuma afli si tu... :D
Marius Bancila
Fondator Codexpert, Microsoft MVP VC++
Site personal | Blog

User avatar
Ovidiu Cucu
Fondator
Fondator
Posts: 3776
Joined: 11 Jul 2007, 16:10
Judet: Iaşi
Location: Iasi
Contact:

Re: WM_LBUTTONDBLCLK netratat

Post by Ovidiu Cucu » 08 Jun 2012, 07:49

Marius Bancila wrote:...
Inca putin si o sa-ti dai seama ca folosesti si design patterns de o viata si acuma afli si tu... :D
Da, mai ales KISS Pattern.
Daca toti s-ar face architecti, ar disparea programatorii iar programele ar deveni... forme fără fond. :D

User avatar
Ovidiu Cucu
Fondator
Fondator
Posts: 3776
Joined: 11 Jul 2007, 16:10
Judet: Iaşi
Location: Iasi
Contact:

Re: WM_LBUTTONDBLCLK netratat

Post by Ovidiu Cucu » 08 Jun 2012, 09:42

[ Later edit, also off-topic]
Intr-o buna zi, un mare Architect cobora din Inalturi sa vada ce mai fac creaturile mici si negre, puse sa-i desavarseasca Opera.
Vazu una care tocmai se pregatea sa dea cu tastatura-n monitor.
"What's up?" intreba El cu indreptatita mirare.
"F*** this ******* architecture!" i se raspunse in furniceasca vulgara, imposibil de tradus.
Atunci, The Architect ofta, o batu compatimitor pe umar si-i zise cu blandete: "Don't be upset! I was a developer too".
NOTA:
Aceasta este o dramatizare dupa o intamplare reala. Din motive lesne de inteles, numele unor locuri si personaje au fost schimbate. :)

User avatar
Ovidiu Cucu
Fondator
Fondator
Posts: 3776
Joined: 11 Jul 2007, 16:10
Judet: Iaşi
Location: Iasi
Contact:

Re: WM_LBUTTONDBLCLK netratat

Post by Ovidiu Cucu » 11 Jun 2012, 07:50

Revenind on topic.
In fond si la urma urmei nici n-ai nevoie sa "prinzi" WM_LBUTTONDBLCLK.
Un control precum treeview-ul trimite notificarea NM_DBLCLK la parinte. Mapeaz-o pe aia si lasa-l in pace pe PreTranslateMessage.

0ptr
Membru
Membru
Posts: 71
Joined: 01 Feb 2011, 23:27
Judet: Ilfov

Re: WM_LBUTTONDBLCLK netratat

Post by 0ptr » 11 Jun 2012, 11:29

Ovidiu Cucu wrote: In fond si la urma urmei nici n-ai nevoie sa "prinzi" WM_LBUTTONDBLCLK.
Un control precum treeview-ul trimite notificarea NM_DBLCLK la parinte. Mapeaz-o pe aia si lasa-l in pace pe PreTranslateMessage.
Da. Din fericire wizard-ul a generat o clasa CViewTree ce suprascria CTreeCtrl si acolo pot avea notificarea NM_DBLCLK.
Faza e ca, data fiind arhitectura aplicatiei, mi-e mai util sa prind WM_LBUTTONDBLCLK pe PreTranslateMessage() din CMainFrame... deci e ok si asa.
Many Thanks! :)

Post Reply