[win32] - getting child controls from it's parent

i'm trying doing a class for getting the child parent controls:
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
class ChildControls
{
private:
    vector<HWND> childcontrols;
    UINT childcontrolsindex;
    HWND windowparent;

public:
    ChildControls(const HWND parent)
    {
        windowparent=parent;
        //EnumChildWindows(parent, EnumChildProc, 0);
    }

    UINT childcontrolscount()
    {
        return childcontrolsindex;
    }

    HWND GetHWND(UINT index)
    {
        EnumChildWindows( windowparent,
                              [this]( HWND hwnd, LPARAM lParam )
                              {
                                    this->childcontrols.push_back(hwnd);
                                    this->childcontrolsindex = this->childcontrols.size(); // TODO:
                                    return TRUE;
                              },
                              0);


        if(index>=childcontrolsindex)
            index=childcontrolsindex-1;
        return childcontrols[index];
    }
}ChildControls;

but i'm getting several errors with EnumChildWindows() function and when i close the class. can anyone tell me what i'm doing wrong?
but i'm getting several errors with EnumChildWindows() function and when i close the class.
What are this errors and what does it mean "close the class"?
The first problem is on the first and the last line. You cannot create instance of class ChildControls called ChildControls. What you are doing is equivalent to
ChildControls ChildControls; Also, you fail create instance of the class because contructor requires a paramater ( ChildControls(const HWND parent) )

Second, the callback function cannot be part of the class.

Try this
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
BOOL CALLBACK EnumChildProc( HWND hwnd, LPARAM lParam );
class ChildControls
{
private:
    vector<HWND> childcontrols;
    UINT childcontrolsindex;
    HWND windowparent;
    friend BOOL EnumChildProc( HWND hwnd, LPARAM lParam );
public:
    ChildControls(const HWND parent)
    {
        windowparent=parent;
        //EnumChildWindows(parent, EnumChildProc, 0);
    }

    UINT childcontrolscount()
    {
        return childcontrolsindex;
    }

    HWND GetHWND(UINT index)
    {
        EnumChildWindows( windowparent,EnumChildProc,(LPARAM)this);


        if(index>=childcontrolsindex)
            index=childcontrolsindex-1;
        return childcontrols[index];
    }
};

BOOL EnumChildProc( HWND hwnd, LPARAM lParam )
{
    ChildControls *cc=(ChildControls *)lParam;
    
    cc->childcontrols.push_back(hwnd);
    cc->childcontrolsindex = cc->childcontrols.size(); // TODO:
    return TRUE;    
}

// ..somewhere in main
ChildControls cc(some_windows_handle)
Last edited on
thanks for all.
but i continue confuse why i can't do these line(when i close the class)?

}ChildControls;
what i need is avoiding instances of the class ;)
You can
}childControls(window_handle); but I doubt you'll have an open window handle by the time you create a class. You can do something like

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
class ChildControls
{
// ...
public:
    ChildControls()
    {
        windowparent=0;
    }
    ChildControls(const HWND parent)
    {
// ...

  void SetHWND(const HWND parent)
  {
     windowparent=parent;
  }
// ...
}childControls;

// in main

childControls.setHWND(window_handle);
// do stuff 
thanks for all.
need ask 1 thing: without the EnumChildProc() function, can i get the control(not child control) with index 0(normaly it's the 1st form created)?
i'm trying:
1
2
3
4
5
6
7
8
9
10
11
12
HWND WindowMain=NULL;

BOOL GetWindowMain( HWND hwnd, LPARAM lParam )
{
    WindowMain=hwnd;
    return false;
}

void GetMainWindow()
{
    EnumWindows(GetWindowMain,(LPARAM)0);
}

but i get 1 error on last argument :(
what i'm doing wrong?
(i only need find the 1st handle)
Last edited on
The callback function definition must be
BOOL CALLBACK GetWindowMain( HWND hwnd, LPARAM lParam )
thanks for correct me.
but i continue with errors:
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
BOOL CALLBACK EnumOnceProc( HWND hwnd, LPARAM lParam );
class WMain
{
private:
    HWND windowparent=NULL;
    friend BOOL EnumOnceProc( HWND hwnd, LPARAM lParam );
public:

    WMain()
    {
        EnumWindows( EnumOnceProc,(LPARAM)this);
    }

    operator HWND()
    {
        return windowparent;
    }

}WindowMain;

BOOL CALLBACK EnumOnceProc( HWND hwnd, LPARAM lParam )
{
    WMain *cc=(WMain*)lParam;
    cc->windowparent=hwnd;
    return false;
}


heres how i use it:
1
2
if (WindowMain==hwnd)
                        MessageBox(NULL,"they match", "hi",MB_OK);

the hwnd is from window main procedure.
why that message isn't activated?
the EnumWindows() is for the application? or for the Operate System?
I am not sure what you want to do. Do you want to check whether the first window handle returned by EnumWindows is a handle of your application? If so, then it might not always be true, because the topmost window can be taskbar or some hidden window ( http://stackoverflow.com/questions/295996/is-the-order-in-which-handles-are-returned-by-enumwindows-meaningful?answertab=votes#tab-top )
Null just see these function:
1
2
3
4
5
6
7
8
BOOL EnumChildProc( HWND hwnd, LPARAM lParam )
{
    ChildControls *cc=(ChildControls *)lParam;
    
    cc->childcontrols.push_back(hwnd);
    cc->childcontrolsindex = cc->childcontrols.size(); // TODO:
    return TRUE;    
}

you told me for pass the 'this' for EnumWindows() function. and then i can use that way for catch the pointer.
i did the same thing for windows procedure, but don't works :(
when i create the control(CreateWindowEx()) i send the 'this' on last parameter and in window procedure i do:
form *inst = (form*)lParam;
but by some reason i only get NULL... why?
The pointer is passed to your window procedure only once to WM_CREATE message. You must handle the WM_CREATE message, and save the pointer.
1
2
3
4
5
6
7
8
9
// in window procedure
        case WM_CREATE:
         {
          CREATESTRUCT *cs=(CREATESTRUCT*)lParam;
          form *inst=(form*)cs->lpCreateParams; // this value is equal to the last parameter of CreateWindoiwEx

          SetWindowLongPtr(hwnd,GWL_USERDATA,(LONG_PTR)inst); // save it for later use
          return 0;
         }

To get the pointer again, use GetwindowLongPtr:
1
2
// somewhere in window porocedure, when you need it
form *inst=(form*)GetWindowLongPtr(hwnd,GWL_USERDATA);


WM_CREATE: http://msdn.microsoft.com/en-us/library/windows/desktop/ms632619(v=vs.85).aspx
CREATESTRUCT: http://msdn.microsoft.com/en-us/library/windows/desktop/ms632603(v=vs.85).aspx
SetWindowLongPtr: http://msdn.microsoft.com/en-us/library/windows/desktop/ms644898(v=vs.85).aspx
i'm sorry NULL :(
but by some reason, that code don't works :(
it's because i use Code Blocks IDE with GNU compiler?
Can you post full code?
heres the entire code: http://codepad.org/SrOIpP6t
(sorry... the class is to big for put here :( )
by some reason i can't get the form instance pointer :(
I quickly looked to your code and I saw that you mixed some class and window procedure variables. Your wm_ncreate should be
1
2
3
4
5
6
7
8
9
            case WM_NCCREATE:
            {
                CREATESTRUCT *p = (CREATESTRUCT *)lParam;
                inst = (form *)p->lpCreateParams;
                SetWindowLongPtr(HandleWindow, GWLP_USERDATA, (LONG_PTR)inst); // notice HandleWindow
                inst->hwnd =  HandleWindow;
                if (inst==NULL)
                     inst = (form *)GetWindowLongPtr( HandleWindow, GWLP_USERDATA);
            }
after execute the form isn't showed and then i get these ouptup message:
"Process terminated with status -1073741819 (0 minutes, 9 seconds)"
i don't know what means :(
Topic archived. No new replies allowed.