Foro de elhacker.net

Programación => Programación C/C++ => Mensaje iniciado por: CBFD en 9 Junio 2016, 10:56 am



Título: invalid use of member ' ' in static member function
Publicado por: CBFD en 9 Junio 2016, 10:56 am
Hola a todos:

En primer lugar soy muy novato con C++ y estoy haciendo una clase para crear ventanas hijas y en ellas escribir textos, la clase es la siguiente:

Código
  1. #include <windows.h>
  2. #include <string>
  3.  
  4. using namespace std;
  5.  
  6. #if !defined(ClaseTSay)
  7. #define ClaseTSay
  8.  
  9. #if _MSC_VER > 1000
  10. #pragma once
  11. #endif // _MSC_VER > 1000
  12.  
  13. class TSay
  14. {
  15. private:
  16. static LRESULT CALLBACK  WinProc(HWND vHij, UINT uMsg, WPARAM wParam, LPARAM lParam)
  17. {
  18. switch (uMsg)
  19. {
  20. case WM_PAINT :
  21. {
  22. HDC dc  = GetDC(vHij);
  23. PAINTSTRUCT ps;
  24. RECT rc;
  25. HRGN bgRgn;
  26. HBRUSH hBrush;
  27. HGDIOBJ old;
  28.  
  29.   int x_posX = (int)posX;
  30. int x_posY = (int)posY;
  31. int x_tamX = (int)tamX;
  32. int x_tamY = (int)tamY;
  33.  
  34. dc = BeginPaint (vHij, &ps);
  35. SetRect (&rc, 0, 0, x_tamX, x_tamY);
  36. bgRgn = CreateRectRgnIndirect(&rc);
  37. hBrush = CreateSolidBrush(fond);
  38. FrameRgn(dc, bgRgn, hBrush,2,2);
  39. SetBkMode    (dc, fond);
  40. SetTextColor (dc, escr);
  41. old = SelectObject(dc, letr);
  42.  
  43. switch (m_alin)
  44. {
  45. case 0:
  46. DrawText(dc, pint, lstrlen(pint), &rc, DT_LEFT | DT_VCENTER );
  47. break;
  48. case 1:
  49. DrawText(dc, pint, lstrlen(pint), &rc, DT_CENTER | DT_VCENTER );
  50. break;
  51. case 2:
  52. DrawText(dc, pint, lstrlen(pint), &rc, DT_RIGHT | DT_VCENTER );
  53. break;
  54. }
  55.  
  56.  
  57. SelectObject(dc, old);
  58. ReleaseDC(vHij, dc);
  59. DeleteObject(old);
  60. DeleteObject(bgRgn);
  61. DeleteObject(hBrush);
  62.    EndPaint (vHij, &ps);
  63.    break;
  64. }
  65. default :
  66. return DefWindowProc(vHij, uMsg, wParam, lParam);
  67. }
  68. return 0;
  69. }
  70. protected:
  71. HWND     vHij;
  72. WNDPROC   oldW;
  73. double      posX;
  74. double      posY;
  75. const char* pint;
  76. HWND        vent;
  77. HFONT       letr;
  78. COLORREF    escr;
  79. COLORREF    fond;
  80. double      tamX;
  81. double      tamY;
  82. int         bord;
  83. int         alin;
  84. const TCHAR *cVen;
  85. public:
  86. TSay()
  87. {
  88. vHij = NULL;
  89. oldW = NULL;
  90. posX = 0;
  91. posY = 0;
  92. pint = NULL;
  93. vent = NULL;
  94. letr = NULL;
  95. escr = 00;
  96. fond = 0;
  97. tamX = 0;
  98. tamY = 0;
  99. bord = 0;
  100. alin = 0;
  101. cVen = NULL;
  102. }
  103.  
  104. ~TSay()
  105. {
  106. }
  107.  
  108. HWND Crear( double posX, double posY, const char* pint, HWND vent, HFONT letr, COLORREF escr, COLORREF fond, double tamX, double tamY, int bord, int alin, const TCHAR *cVen)
  109. {
  110. DWORD hPen;
  111. if (bord == 1)
  112. {
  113. hPen = WS_BORDER | WS_CHILD| WS_VISIBLE;
  114. }
  115. else
  116. {
  117. hPen = WS_CHILD| WS_VISIBLE;
  118. }
  119.  
  120. WNDCLASSEX WndClass;
  121.  
  122. WndClass.cbSize = sizeof(WNDCLASSEX);
  123. WndClass.style = 0;
  124. WndClass.lpfnWndProc = WinProc;
  125. WndClass.cbClsExtra = 0;
  126. WndClass.cbWndExtra = 0;
  127. WndClass.hInstance = GetModuleHandle(NULL);
  128. WndClass.hIcon = NULL;
  129. WndClass.hIconSm = NULL;
  130. WndClass.hCursor = LoadCursor(0, IDC_ARROW);
  131. WndClass.hbrBackground = (HBRUSH)CreateSolidBrush(fond);
  132. WndClass.lpszMenuName = 0;
  133. WndClass.lpszClassName = cVen;
  134.  
  135. RegisterClassEx(&WndClass);
  136.  
  137.   int x_posX = (int)posX;
  138. int x_posY = (int)posY;
  139. int x_tamX = (int)tamX;
  140. int x_tamY = (int)tamY;
  141.  
  142. vHij = CreateWindowEx(
  143. 0,
  144. cVen,
  145. "TSay",
  146. hPen,
  147.    x_posY,
  148.    x_posX,
  149.    x_tamX,
  150.    x_tamY,
  151. vent,
  152.    NULL,
  153. GetModuleHandle(NULL),
  154.    NULL);
  155.  
  156. if(vHij)
  157. {
  158. ShowWindow(vHij, 5);
  159.    UpdateWindow(vHij);
  160. }
  161. return vHij;
  162. }
  163. };
  164. #endif // !defined(ClaseTSay)
  165.  
:

Mi problema es que en las líneas 73, 74, 75, 77, 78, 79, 80 y 81 me da el error de "invalid use of member ' ' in static member function" y en las líneas entre la 29 y la 52 que las usan en WM_PAINT me pone "from this location".

Me podéis orientar para poder solucionar este problema.

Un saludo y gracias.

Carlos



Título: Re: invalid use of member ' ' in static member function
Publicado por: ivancea96 en 9 Junio 2016, 15:55 pm
Veamos. En un static, no estás trabajando con ningún objeto, por tanto, no hay miembros con los que trabajar (salvo otros miembros static.

Para acceder a los miembros de ese objeto TSay, tendrás primero que obtener ese objeto. CreateWindowEx tiene un parámetro, el último, que es el LPARAM que recibirá la función en el mensaje WM_CREATE. Puedes pasarle por ahí un puntero al objeto, por ejemplo.

Aunque claro, así solo sabrás ese dato la primera vez. Para conocer el objeto de TSay en cada llamada, algo que puedes hacer es almacenarlo en otro miembro static, y utilizar ese miembro las próximas llamadas al callback.

Por ejemplo, yo haría un map<LONG, TSay*>, donde el LONG sería el identificador de la ventana, que obtienes con la función GetWindowLong (https://msdn.microsoft.com/es-es/library/windows/desktop/ms633584(v=vs.85).aspx).

Ciertamente esta parte tiene algo más de enjundia, pero bueno. Una vez hecho, hecho queda xD


Título: Re: invalid use of member ' ' in static member function
Publicado por: CBFD en 22 Junio 2016, 12:59 pm
Hola de nuevo:

Ya he conseguido mucho y casi tengo todo hecho pero me falta todavía una cosa que no se porque pasa.

El código es ahora así:

Código
  1. #if !defined(TSAY)
  2.    #define TSAY
  3.  
  4.   #include <windows.h>
  5.  
  6.    WNDCLASS   wc;
  7.    HWND       vHij;
  8.  
  9. const char* pint;
  10. HFONT       letr;
  11.    COLORREF    escr;
  12.    double      tamX;
  13. double      tamY;
  14. int         alin;
  15.  
  16.    class TSay
  17.    {
  18.    protected:
  19.        static LRESULT CALLBACK WinProc(HWND vHij, UINT msg, WPARAM wParam, LPARAM lParam)
  20.        {
  21.            switch(msg)
  22.            {
  23.                case WM_DESTROY:
  24.                    PostQuitMessage(0);
  25.                    break;
  26.                default:
  27.                    return DefWindowProc(vHij, msg, wParam, lParam);
  28.            }
  29.            return 0;
  30.        }
  31.    public:
  32.        TSay()
  33.        {
  34.        }
  35.        ~TSay()
  36.        {
  37.        }
  38.        HWND Crear(HINSTANCE hIns,double posX, double posY, const char* pint, HWND vent, HFONT letr, COLORREF escr, COLORREF fond, double tamX, double tamY, int bord, int alin, const char *cVen)
  39.        {
  40. WNDCLASSEX WndClass;
  41.  
  42. WndClass.cbSize = sizeof(WNDCLASSEX);
  43. WndClass.style = 0;
  44. WndClass.lpfnWndProc = WinProc;
  45. WndClass.cbClsExtra = 0;
  46. WndClass.cbWndExtra = 0;
  47. WndClass.hInstance = hIns;
  48. WndClass.hIcon = NULL;
  49. WndClass.hIconSm = NULL;
  50. WndClass.hCursor = LoadCursor(0, IDC_ARROW);
  51. WndClass.hbrBackground = (HBRUSH)CreateSolidBrush(fond);
  52. WndClass.lpszMenuName = 0;
  53. WndClass.lpszClassName = cVen;
  54.  
  55. RegisterClassEx(&WndClass);
  56.  
  57. DWORD hPen;
  58. if (bord == 1)
  59. {
  60. hPen = WS_BORDER | WS_CHILD| WS_VISIBLE;
  61. }
  62. else
  63. {
  64. hPen = WS_CHILD| WS_VISIBLE;
  65. }
  66.  
  67.   int x_posX = (int)posX;
  68. int x_posY = (int)posY;
  69. int x_tamX = (int)tamX;
  70. int x_tamY = (int)tamY;
  71.  
  72. vHij = CreateWindow(
  73. cVen,
  74. "TSay",
  75. hPen,
  76.    x_posY,
  77.    x_posX,
  78.    x_tamX,
  79.    x_tamY,
  80. vent,
  81.    NULL,
  82.    hIns,
  83.    NULL);
  84.  
  85. ShowWindow(vHij, 5);
  86. RedrawWindow(vHij,NULL,NULL,RDW_INVALIDATE | RDW_INTERNALPAINT);
  87.  
  88. HDC dc  = GetDC(vHij);
  89. PAINTSTRUCT ps;
  90. RECT rc;
  91. HRGN bgRgn;
  92. HBRUSH hBrush;
  93. HGDIOBJ old;
  94.  
  95. dc = BeginPaint (vHij, &ps);
  96. SetRect (&rc, 0, 0, x_tamX, x_tamY);
  97. bgRgn = CreateRectRgnIndirect(&rc);
  98. hBrush = CreateSolidBrush(fond);
  99. FrameRgn(dc, bgRgn, hBrush,2,2);
  100. SetBkMode    (dc, TRANSPARENT);
  101. SetTextColor (dc, escr);
  102. old = SelectObject(dc, letr);
  103.  
  104. switch (alin)
  105. {
  106. case 0:
  107. DrawText(dc, pint, lstrlen(pint), &rc, DT_LEFT | DT_VCENTER );
  108. break;
  109. case 1:
  110. DrawText(dc, pint, lstrlen(pint), &rc, DT_CENTER | DT_VCENTER );
  111. break;
  112. case 2:
  113. DrawText(dc, pint, lstrlen(pint), &rc, DT_RIGHT | DT_VCENTER );
  114. break;
  115. }
  116.  
  117.  
  118. SelectObject(dc, old);
  119. ReleaseDC(vHij, dc);
  120. DeleteObject(old);
  121. DeleteObject(bgRgn);
  122. DeleteObject(hBrush);
  123.    EndPaint (vHij, &ps);
  124.  
  125. RedrawWindow(vHij,NULL,NULL,RDW_INVALIDATE | RDW_INTERNALPAINT);
  126.  
  127. return vHij;
  128. }
  129. };
  130. #endif // TSAY

Y crea las ventanas corectamente pero no me incorpora los textos que quiero esto lo debería hacer con las líneas de la 88 a 123. pero no lo pone. Estoy haciendo todo tipo de pruebas con eclipse y haciendo el debug cuando paro entre impresiones si me las pone pero luego cuando finaliza la función y refresca la ventana donde van desaparecen y quedan las ventanas sin textos.

la función que llama a esta clase es :

Código
  1. void Pantalla()
  2. {
  3.   TSay   oSay  = TSay  ();
  4.   oPan4     = oSay.Crear(hInstance,  10*TamPan, 30*TamPan, wtex000, oDlgwVen, oFont, escri1, fondo2,1020*TamPan, 77*TamPan, 0, 0, "oPan4");
  5.   oPan401   = oSay.Crear(hInstance,  25*TamPan,340*TamPan, wtex001, oPan4   , oFon3, escri3, fondo1, 630*TamPan, 30*TamPan, 1, 1, "oPan401");
  6.   oMenPan   = oSay.Crear(hInstance,  95*TamPan, 30*TamPan, wtex000, oDlgwVen, oFont, escri3, fondo1, 245*TamPan,555*TamPan, 0, 0, "oMenPan");
  7.   oMenPan01 = oSay.Crear(hInstance,  22*TamPan, 30*TamPan, wtex002, oMenPan , oFont, escri1, fondo1, 200*TamPan, 28*TamPan, 0, 0, "oMenPan01");
  8.   oMenPan02 = oSay.Crear(hInstance,  52*TamPan, 30*TamPan, wtex003, oMenPan , oFont, escri1, fondo1, 200*TamPan, 28*TamPan, 0, 0, "oMenPan02");
  9.   oMenPan03 = oSay.Crear(hInstance,  82*TamPan, 30*TamPan, wtex004, oMenPan , oFont, escri1, fondo1, 200*TamPan, 28*TamPan, 0, 0, "oMenPan03");
  10.   oMenPan04 = oSay.Crear(hInstance, 112*TamPan, 30*TamPan, wtex008, oMenPan , oFont, escri1, fondo1, 200*TamPan, 28*TamPan, 0, 0, "oMenPan04");
  11.   oMenPan05 = oSay.Crear(hInstance, 142*TamPan, 30*TamPan, wtex009, oMenPan , oFont, escri1, fondo1, 200*TamPan, 28*TamPan, 0, 0, "oMenPan05");
  12.   oMenPan06 = oSay.Crear(hInstance, 172*TamPan, 30*TamPan, wtex010, oMenPan , oFont, escri1, fondo1, 200*TamPan, 28*TamPan, 0, 0, "oMenPan06");
  13.   oMenPan07 = oSay.Crear(hInstance, 202*TamPan, 30*TamPan, wtex011, oMenPan , oFont, escri1, fondo1, 200*TamPan, 28*TamPan, 0, 0, "oMenPan07");
  14.   oMenPan08 = oSay.Crear(hInstance, 232*TamPan, 30*TamPan, wtex012, oMenPan , oFont, escri1, fondo1, 200*TamPan, 28*TamPan, 0, 0, "oMenPan08");
  15.   oMenPan09 = oSay.Crear(hInstance, 262*TamPan, 30*TamPan, wtex013, oMenPan , oFont, escri1, fondo1, 200*TamPan, 28*TamPan, 0, 0, "oMenPan09");
  16.   oPant     = oSay.Crear(hInstance,  95*TamPan,300*TamPan, wtex001, oDlgwVen, oFont, escri1, fondo2, 750*TamPan,555*TamPan, 1, 0, "oPant");
  17.   oPan2     = oSay.Crear(hInstance, 117*TamPan, 30*TamPan, wtex001, oDlgwVen, oFont, escri1, fondo2, 280*TamPan, 25*TamPan, 0, 0, "oPan2");
  18.  
  19.    RedrawWindow(oDlgwVen,NULL,NULL,RDW_INVALIDATE | RDW_INTERNALPAINT);
  20. }

Alguna ayuda por favor.

Un saludo, gracias.

Carlos


Título: Re: invalid use of member ' ' in static member function
Publicado por: CBFD en 22 Junio 2016, 13:11 pm
Os dejo las imágenes de cuando estoy haceindo el debug :

(http://www.colthop.es/img01.jpg)

y cuando termina la función y refresca la pantalla:

(http://www.colthop.es/img02.jpg)

Un saludo.

Carlos.