Obtain a reference to a graphics object under CF

  • Thread starter Thread starter me
  • Start date Start date
M

me

Hello,

I'm stuck again ....:
I'm building an app using .NET Framework 1.1 and .NET-CF 1.0-SP2. In
the form there exist a PictureBox containing a JPG image. I want to
draw a rectangle at the location where the MouseDown event occurs.
Outside the PicBox, this is not a problem; inside the PicBox, it gives
me a "NotSupportedException"!
Doing the same in a 'normal' .NET Framework app: runs OK; so it must
be something of the CF (?).
Tried to search the web, MSDN, installed OpenNETCF ..., with no result
up to this point.
Please help.

Thank you!
Saya
 
Hi Sergey,
Thanks for replying. Here is the situation:

public void OnMyMouseDown( object source, MouseEventArgs mouseEv)
{
The following is OK, a rectangle in parent window:
Graphics gfx = this.CreateGraphics;

The following is NOT OK, 'NotSupportedException':
Graphics gfx = pbx.CreateGraphics; // pbx=PictureBox gfx ref.
...
}
In my context 'Graphics' only have a definition for 'FromImage' .... .
The MSDN FAQ gives as reason: "Only the Control and Form classes
support Control.CreateGraphics()." Well, a PictureBox is a control...
or am I thinking wrongly here.

But ..., I'm a bit further now, thanks to your suggestions:
The funny thing is: in both manners, with the OnPaint method or using
'this.CreateGraphics' (instead of 'pbx.CreateGraphics'), I'm able to
draw the rect's, but *outside* the actual PictureBox! Debugging shows
that 'OnMyMouseDown' produces *local* coordinates, with its own
top-left-corner as 0,0! This is then mapped to the parent ... hence
drawing outside the picturebox ... .
I've to repair this - if you've a suggestion, please do ;-))

Thank you for reading!
Saya

======================================================
 
One thing led to another: it's now possible to draw the rect's.
Unfortunately, adding the picturebox coord's offset causes the
rectangular being drawn *behind* the picturebox....! resulting in
invisible rect's.
How can I bring this up front? Please advise.

Thank you, Saya

-----------------------------------------------------------------------------------------
 
The reason why you can invoke parent's CreateGraphics is because you
indeed call Form.CreateGraphics (see FAQ: "Only the Control and Form
classes support Control.CreateGraphics()."). The PictureBox is not a
Control but its derived class.

In you case it would be better to create custom Control and implement
simple double buffering:- all drawing comes through offscreen Bitmap
that in one's part displays in OnPaint event. If you need complete
example for that see this:
http://www.sergeybogdanov.com/samples/SaveImage.zip

It demonstrates how to capture the user signature and save it as a
monochrome bitmap.
 
Sergey,
Some questions:
1. Regarding your first paragraph below: why is it then that
IntelliSense in particular, and VS .NET2003 in general, is giving me
the possibility to choose 'CreateGraphics' when I select the
PictureBox as the base?
Also: when I tried this scheme in a classic Windows Application, all
works well - meaning, I can draw visible rect's within the PictureBox
area. This sounds to me as if it's a CF limitation? Although ... MSDN
says that CreateGraphics is also supported for CF; and here I'm back
again at your pointing of '...only Control, and not a derived object
....' (but, IntelliSense does .... etc). It puzzles me!

2. When trying to build your SaveImage example I'm confronted with:
"Type/namespace 'Win32Window' not found". Do I need more stuff?

Thank you,
greetz Saya
 
See below.
Some questions:
1. Regarding your first paragraph below: why is it then that
IntelliSense in particular, and VS .NET2003 in general, is giving me
the possibility to choose 'CreateGraphics' when I select the
PictureBox as the base?
Also: when I tried this scheme in a classic Windows Application, all
works well - meaning, I can draw visible rect's within the PictureBox
area. This sounds to me as if it's a CF limitation? Although ... MSDN
says that CreateGraphics is also supported for CF; and here I'm back
again at your pointing of '...only Control, and not a derived object
...' (but, IntelliSense does .... etc). It puzzles me!

Just assumption:- it can be explained, because most of the controls in
..NET CF are wrappers for native controls and it's not so easy to inject
into its drawing process. Whereas Control and Form are managed controls.
The controls like DataGrid, PictureBox - are managed and instead of
CreateGraphics you have to use their Graphics object provided by Paint
event.

By the way, CreateGraphics is not the only example of the Unsupported
methods that are visible in IntelliSense. For example,
Activator.CreateInstance, Attribute.GetCustomAttributes also are visible
in IntelliSense but throws the same exception in some cases. Most of
that limitations you will realize only through trial-and-error method.
2. When trying to build your SaveImage example I'm confronted with:
"Type/namespace 'Win32Window' not found". Do I need more stuff?
You have to install OpenNETCF SDF:
http://www.opennetcf.org/PermaLink.aspx?guid=3a013afd-791e-45ef-802a-4c1dbe1cfef9
 
Sergey,
Just for the record (and fun): after 'furious' trial + errors +
juggling through the MSDN jungle, I've found a workaround in this
matter!
What I did is: create the method on 'ParentChanged' event; in this
method do the DrawRectangle, Refresh the picbox.
The ParentChanged event itself is raised by OnMyMouseDown (overridden
OnMouseDown).
The result is ... amazing: I now have rectangles within my
PictureBox area, and its all under CF!

Thank you for reading!
 
Back
Top