FormView graphics-problem??

Hello!

In my FormView-App I used a PictureBox(Rectangle), where I wanna draw. I tried to realize
that in this way:

OnDraw:
CWnd *pWnd = GetDlgItem(IDC_PLACE);
CDC *hdc = pWnd->GetDC();
...... pWnd->ReleaseDC();

that works!!
In OnPaint(), i call OnDraw, and in the Doc i call UpdateAllViews when necassary!!

But there is one Problem on Resizing, the content disapears, but it goes in to the OnDraw
function, I checked that with a static int var in OnDraw, but i guess a other event is called and
this lets the PictureBox empty.

I guess it is the onSize event!! But how can I handle that?????

Same happens when i shove the application out of the screen only the drawin was inside the
screen is visible afer shoving the app back!!!

Thank you
ola
gonzalesblanco
gonzalesblancoAsked:
Who is Participating?
I wear a lot of hats...

"The solutions and answers provided on Experts Exchange have been extremely helpful to me over the last few years. I wear a lot of hats - Developer, Database Administrator, Help Desk, etc., so I know a lot of things but not a lot about one thing. Experts Exchange gives me answers from people who do know a lot about one thing, in a easy to use platform." -Todd S.

FrenchFriesCommented:
>>I guess it is the onSize event!! But how can I handle >>that?????


?? it's quite simple ? Go to ClassWizard (if  VC 6.0 )and handle WM_SIZE :-)
0
gonzalesblancoAuthor Commented:
He FrenchFries!

I tried that, but how?

Did it like this:

CWnd *pWnd = GetDlgItem(IDC_PLACE);
CDC *hdc = pWnd->GetDC();
OnDraw(hdc);

But that will make my prog crash, cause it will be called before the PictureBox(IDC_PLACE) is created!!!!!
So I don't know how to do that!!!

ciao
gonzalesblanco
0
FrenchFriesCommented:
Ola,

>>CWnd *pWnd = GetDlgItem(IDC_PLACE);
>>CDC *hdc = pWnd->GetDC();
>>OnDraw(hdc);

NOOOO !!! don't do that !
You don't need to call OnDraw if you have already got a CDC before .
Simply get a CDC with GetDC or construct a dc on the stack with
CClientDC dc(this) ( but it works only with CView )

Or

CDC *pDC=pWnd->GetDC();
// perform some drawing
pDC->Rectangle(...);
// important release the DC
pWnd->ReleaseDC(pDC);

Regards
0
Cloud Class® Course: CompTIA Healthcare IT Tech

This course will help prep you to earn the CompTIA Healthcare IT Technician certification showing that you have the knowledge and skills needed to succeed in installing, managing, and troubleshooting IT systems in medical and clinical settings.

gonzalesblancoAuthor Commented:
He,

can't really understand what you mean, cause i guess the system will crash that moment i write in the onSize, anything concerning the IDC_PLACE!!!! (PictureBox) cause the on size event is called before the wnd is initialized!!!

could you to me a favour, and write the lines you think i got to write in the OnSize down here? Thank you:

OnSize(....)

Ola, Gonzales
0
FrenchFriesCommented:
Dear Gonzalesblanco,

One thing that I don't understand is that you are talking about a "PictureBox" : is it an Active X ? Because there aren't any picture box controls with VC++ ( whereas Visual Basic has it ).
What I understand is that you need to repaint the client screen :
Here is a sample from MSDN , but if you want to repaint the screen , simply call Invalidate(TRUE ) or FALSE ..

void CMyView::OnSize(UINT nType, int cx, int cy)
{
   CView::OnSize(nType, cx, cy);

   m_MyPictureBox.MoveWindow (0, 0, cx, cy);
Invalidate(TRUE);
}

Regards.
0
northernchillCommented:
Why not just force a redraw of the view in OnSize(...)?

void MyView::OnSize(UINT nType,int cx, int cy)
{
  CView::OnSize(nType,cx,cy);
// this will go into OnPaint()
  Invalidate();
}

You should check the hWnd of the child window you retrieve to ensure it is a valid window.
pWnd = GetDlgItem(IDC_PLACE);
ASSERT(pWnd->m_hWnd != NULL) // don't do anything without a valid window

When you shove the window off the screen and then back, the picture window receives a message, instructing it to paint itself.  Since your drawing code is in the parent view, it won't be called in the appropriate order.

Do you need the window, or just the rectangular region?
0
northernchillCommented:
Sorry for the overlap of information. Missed the last post while typing.
0
gonzalesblancoAuthor Commented:
he,

i just thought about the possibility that every control gets his own WM_PAINT so it is possible that, the message of the form is doing right, but the WM_PAINT for the IDC_PLACE overwrites the forms one!!!

ad norhternchill:
tried your way, but the app is crashing at OnInitialUpdate, where should I check if the window is valid? In OnSize? No?

Ah, and I need the window. I got the problem i can only get the dc to the window at the onDraw, otherwise it will crash (when I to that in OnInitalUpdate or in the constructor!)

ad frenchfries:
i called the picture control picturebox!

ola
gonzales
0
gonzalesblancoAuthor Commented:
he,

i just thought about the possibility that every control gets his own WM_PAINT so it is possible that, the message of the form is doing right, but the WM_PAINT for the IDC_PLACE overwrites the forms one!!!

ad norhternchill:
tried your way, but the app is crashing at OnInitialUpdate, where should I check if the window is valid? In OnSize? No?

Ah, and I need the window. I got the problem i can only get the dc to the window at the onDraw, otherwise it will crash (when I to that in OnInitalUpdate or in the constructor!)

ad frenchfries:
i called the picture control picturebox!

ola
gonzales
0
gonzalesblancoAuthor Commented:
he,

i just thought about the possibility that every control gets his own WM_PAINT so it is possible that, the message of the form is doing right, but the WM_PAINT for the IDC_PLACE overwrites the forms one!!!

ad norhternchill:
tried your way, but the app is crashing at OnInitialUpdate, where should I check if the window is valid? In OnSize? No?

Ah, and I need the window. I got the problem i can only get the dc to the window at the onDraw, otherwise it will crash (when I to that in OnInitalUpdate or in the constructor!)

ad frenchfries:
i called the picture control picturebox!

ola
gonzales
0
gonzalesblancoAuthor Commented:
he,

i just thought about the possibility that every control gets his own WM_PAINT so it is possible that, the message of the form is doing right, but the WM_PAINT for the IDC_PLACE overwrites the forms one!!!

ad norhternchill:
tried your way, but the app is crashing at OnInitialUpdate, where should I check if the window is valid? In OnSize? No?

Ah, and I need the window. I got the problem i can only get the dc to the window at the onDraw, otherwise it will crash (when I to that in OnInitalUpdate or in the constructor!)

ad frenchfries:
i called the picture control picturebox!

ola
gonzales
0
northernchillCommented:
You should check after the picture is created.  If you are using a CView, then you are creating the picture window programmitcally.  Somewhere you should a picturebox.Create(...) call.

If you want to draw directly from the view, don't create a window, just draw in the rectangle you would have defined.

If you are using a FormView, then you probably created a resource template containing the picturebox.  In this case, retrieve the rectangle from OnIntialUpdate after the CFormView::OnInitialUpdate has completed.
0
gonzalesblancoAuthor Commented:
he,

i just thought about the possibility that every control gets his own WM_PAINT so it is possible that, the message of the form is doing right, but the WM_PAINT for the IDC_PLACE overwrites the forms one!!!

ad norhternchill:
tried your way, but the app is crashing at OnInitialUpdate, where should I check if the window is valid? In OnSize? No?

Ah, and I need the window. I got the problem i can only get the dc to the window at the onDraw, otherwise it will crash (when I to that in OnInitalUpdate or in the constructor!)

ad frenchfries:
i called the picture control picturebox!

ola
gonzales
0
northernchillCommented:
One other note, if you want to view the post as it is updated, click on the Reload this Question at the top left of the page.  Clicking on refresh after you have posted a comment adds your comment again to the thread.
0
gonzalesblancoAuthor Commented:
he,

i just thought about the possibility that every control gets his own WM_PAINT so it is possible that, the message of the form is doing right, but the WM_PAINT for the IDC_PLACE overwrites the forms one!!!

ad norhternchill:
tried your way, but the app is crashing at OnInitialUpdate, where should I check if the window is valid? In OnSize? No?

Ah, and I need the window. I got the problem i can only get the dc to the window at the onDraw, otherwise it will crash (when I to that in OnInitalUpdate or in the constructor!)

ad frenchfries:
i called the picture control picturebox!

ola
gonzales
0
northernchillCommented:
If you need the window, then do the drawing from the window, not the view.  
0
gonzalesblancoAuthor Commented:
Hello again!!

Won't work in that ways!!!
But I wanna try another one, but therefore i need to derrive a own class from CWnd, and then give the PictureControl over to that class!!

Never done that, thats my try:

OnInitialUpdate() //in formView

HWND hwnd;
hwnd = GetDlgItem* (IDC_PLACE);

CGraphicWnd wnd;
wnd.SubclassWindow(hwnd);

And now i wanna handle all paint events in the CWnd class!!
Won't work till now, any ideas???

Thanks for any of your opinions and advices (also the already given ones!)

ola
gonzalesblanco

0
northernchillCommented:
CGraphicWnd wnd should actually be a member variable, not a local variable to the OnInitialUpdate function so it won't go out of scope at the end of the function.

If CGraphicWnd is derived from CWnd, add a handler for the WM_PAINT message.  This will allow you to paint for the window.

You will need the view to provide all the data required to perform the drawing to the CGraphicWnd object.
0
gonzalesblancoAuthor Commented:
he northernchill!

I made it global, but when i call the subclass it crashes, when this happens:

m_graphic.SubclassWindow(GetDlgItem(IDC_PLACE)->m_hWnd);

wrong call?!?!?

thank you.

ola gonzalesblanco
0
gonzalesblancoAuthor Commented:
Ok, works that way!!!

m_graphic.SubclassWindow(GetDlgItem(IDC_PLACE)->m_hWnd);

but can I access the Doc from my own CWnd class???
How can i Initialize a pointer to the doc in CWnd??? Tried it but it's only crabb stuff coming out:-) typical me!!!

good night
gonzalesblanco
0
FrenchFriesCommented:
Dear Gonzales Blanco ,

I think that your problem "would" comes the fact that you need to create a DC in memory to constantly get access to the picture you have created.

>>but can I access the Doc from my own CWnd class???
Of course : AppWizard generates a CView method, GetDoc that returns a pointer to your app document class.
See OnDraw method where you get a CDocument pointer.

Regards;
0
FrenchFriesCommented:
Dear Gonzales Blanco ,

I think that your problem "would" comes the fact that you need to create a DC in memory to constantly get access to the picture you have created.

>>but can I access the Doc from my own CWnd class???
Of course : AppWizard generates a CView method, GetDoc that returns a pointer to your app document class.
See OnDraw method where you get a CDocument pointer.

Regards;
0
gonzalesblancoAuthor Commented:
He,

wish you a wonderful day first!

So, I`m nearly finished, but one there is still to do.

I need to access my doc from CWnd out. Have you any ideas
how i can construct a pointer to doc from my CWnd class out!!

can i to that calling a membervar of CWnd in the view, giving a pDoc pointer with her to the constructer of CWnd??

Thank you guys!

Ola
gonzalesblanco
0
northernchillCommented:
Add a member function and variable to your CWnd class
#include "MyDocument.h"
class CGraphicClass : public CWnd
{
protected:
   CMyDocument* m_pDoc;
}
SetDocument(CMyDocument* pDoc)
{
   m_pDoc = pDoc;
}

Call this after you create the instance of the CWnd object.  Now you will have access to the document.

Or you can add the above to a constructor, which would resemble the SetDocument(...) function.
0
gonzalesblancoAuthor Commented:
hello!

thank your have, done that already same way you suggested, works fine!

But now the problem just turned 180° cause now the window redraws at resize, and move, but when i call a self-defined member function in CWnd from the view after data in the view changed, which calls CWnd::OnPaint() nothing happens but it goes there i watched with the debugger!!!

got now idea whats that now:

code:

void CMyWnd::OnPaint()
{
CString temp;
CPaintDC dc(this); // device context for painting
temp.Format("OnPaint: %s", m_pDoc->m_strName);
dc.TextOut(0,0, temp);
}

void CMyWnd::test()
{
     OnPaint();
     testpaint();
}

in view:
m_wndGraphic.test();

thank you for all your patience with a bloddy novice!!

ciao
gonzales
0
northernchillCommented:
Instead of calling OnPaint() call Invalidate().  This will force a redraw of the control.
0

Experts Exchange Solution brought to you by

Your issues matter to us.

Facing a tech roadblock? Get the help and guidance you need from experienced professionals who care. Ask your question anytime, anywhere, with no hassle.

Start your 7-day free trial
gonzalesblancoAuthor Commented:
Okay works fine!!!
Invalidate, does a good job!

But how can i award you the points, will look that up!

Ciao and thanx,

next time will come I swear!! hahaha!

gonzales
0
gonzalesblancoAuthor Commented:
Sorry for do that so late!!!
0
It's more than this solution.Get answers and train to solve all your tech problems - anytime, anywhere.Try it for free Edge Out The Competitionfor your dream job with proven skills and certifications.Get started today Stand Outas the employee with proven skills.Start learning today for free Move Your Career Forwardwith certification training in the latest technologies.Start your trial today
System Programming

From novice to tech pro — start learning today.

Question has a verified solution.

Are you are experiencing a similar issue? Get a personalized answer when you ask a related question.

Have a better answer? Share it in a comment.