?
Solved

Capturing area behind a form to create a magnifying glass

Posted on 2003-03-11
22
Medium Priority
?
215 Views
Last Modified: 2010-05-01
Hi, my problem is this...

I am using the Wang image controls to create a simple image viewer. I have zoom function but i would like the user to be able to use a magnifying glass to enlarge the area directly under and around the mouse. To do this i was thinking of having a form which appears when the mouse is down, and fill the background with the images behind the magnifying form with stretchblt. I would like the form to follow the mouse and not just have a form stationary in the corner.

The actual problem is that i can only get stretchblt to 'grab' what is visible on the screen, which means that the background of the magnifiying form is infact, the form!

I hope that makes sense...
Any help would be appreciated, a better way to do this?

Thanks for your Help
0
Comment
Question by:zomby_dog
[X]
Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people just like you are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions
  • 12
  • 9
22 Comments
 
LVL 3

Expert Comment

by:DocM
ID: 8111149
You could Use the PaintPicture method instead of stretchblt.
0
 

Author Comment

by:zomby_dog
ID: 8111213
DocM:
I thought you could only use a form or picturebox as the source, or at least an object with the picture method? The imgedit control does not have this.

Or have i got that completely wrong?
0
 
LVL 5

Expert Comment

by:JohnMcCann
ID: 8111536
Ok where to start.

First off when you are using the Stretchbit API.  make sure you are giving the handle to the device context of the thing containing the picture.  Not a screen capture.

e.g. Frm.Picture.Handle

Have you managed to get the form to foolow the mouse?
0
Technology Partners: We Want Your Opinion!

We value your feedback.

Take our survey and automatically be enter to win anyone of the following:
Yeti Cooler, Amazon eGift Card, and Movie eGift Card!

 

Author Comment

by:zomby_dog
ID: 8111700
Yeh i think so: im using GetHDC(imgedit1) as the source and form2.hdc as the destination

I have got the form to move using the SetWindowPos and GetCursorPos in the mousemove event. I can't seem to just use x,y coordinates that are passed to the sub, for some reason they are a bit out. Anyway it makes it easier because if this form is a child of an MDI (which it is), then i don't have to worry about its parent.
0
 
LVL 5

Expert Comment

by:JohnMcCann
ID: 8111759
Try using imgedit1.Picture.Handle as the source
0
 

Author Comment

by:zomby_dog
ID: 8111807
As far as i can see the Kodak Imgedit control doesn't have a picture property. I have tried using a picture box instead, but if something is actually in front of the picture it will show that obstruction.
0
 
LVL 5

Expert Comment

by:JohnMcCann
ID: 8112347
Sorry.

This may be of more use

tmpDc = GetDC(ImgEdit1.hwnd)

With targetObj
   StretchBlt .hdc, 0, 0, .ScaleWidth, .ScaleHeight, _
               tmpDc, 0, 0, .ScaleWidth / 2, .ScaleHeight / 2, vbSrcCopy
   .Refresh
end with

To work properly targetObj must have AutoRedraw set to true.

targetObj  can be any obkect that supports hDc
0
 

Author Comment

by:zomby_dog
ID: 8117861
John: That does work... but it still shows any obstruction that is in front of the source object. So if form2 is in front of form1 (form1 being the source) then the background of form2 is form2.
0
 
LVL 5

Expert Comment

by:JohnMcCann
ID: 8119864
Ok, Try this

Private Declare Function LockWindowUpdate Lib "user32" (ByVal hwndLock As Long) As Long

LockWindowUpdate me.hWnd
me.Visible = False
'DoEvents 'If it doesn't work uncomment this line
tmpDc = GetDC(ImgEdit1.hwnd)

With targetObj
  StretchBlt .hdc, 0, 0, .ScaleWidth, .ScaleHeight, _
              tmpDc, 0, 0, .ScaleWidth / 2, .ScaleHeight / 2, vbSrcCopy
  .Refresh
end with
me.visible =true
LockWindowUpdate False

0
 
LVL 5

Expert Comment

by:JohnMcCann
ID: 8119886
Note,

form2.AutoRedraw must be set to true.
0
 
LVL 5

Expert Comment

by:JohnMcCann
ID: 8119898
When we have got this working, I can post you an example that will make your form round like a magnifiying glass.

Regards


John McCann
0
 

Author Comment

by:zomby_dog
ID: 8126620
Hi john cheers for your continued help. I have good and bad news:

Good news: it does work if the lockwindowupdate is commented out.

Bad news: Even with Doevents uncommented it stretchblt still sees for magnifier form in front on the form with imgedit1 on it.

I am starting to wonder if i am going about this the wrong way... another API instead of stretchblt maybe?
0
 
LVL 5

Expert Comment

by:JohnMcCann
ID: 8128128
When you say

Bad news: Even with Doevents uncommented it stretchblt still sees for magnifier form in front on the form with imgedit1 on it.

I assume by this you mean you magnifying glass is blank.  As the section it is enlarging is directly underneath.

If this is the case double check AutoRedraw on the form is set to true and refresh is being called at the end.

If you post me your code, I will quickly run it and see if I can resolve tis issue.
0
 

Author Comment

by:zomby_dog
ID: 8128186
Ok here is the code, sorry about the unreadability of that statement, late night.

This is in Form2 and imgedit1 is on form1
Form2 is set to autodraw

Private Sub Command1_Click()
LockWindowUpdate Me.hwnd
Me.Visible = False
DoEvents 'If it doesn't work uncomment this line
tmpdc = GetDC(Form1.ImgEdit1.hwnd)

With Me
 StretchBlt .hdc, 0, 0, .ScaleWidth, .ScaleHeight, _
             tmpdc, 0, 0, .ScaleWidth / 2, .ScaleHeight / 2, vbSrcCopy
 .Refresh
End With
Me.Visible = True
LockWindowUpdate False
End Sub

Private Sub Form_Load()
tmpdc = GetDC(Form1.ImgEdit1.hwnd)
End Sub

Private Sub Form_Unload(Cancel As Integer)
ReleaseDC Form1.ImgEdit1.hwnd, tmpdc
End Sub
0
 
LVL 5

Expert Comment

by:JohnMcCann
ID: 8128445
Ok ran the code no problem.

All I used was

Private Sub Command1_Click()
Dim tmpdc As Long

   LockWindowUpdate 0
   Me.Visible = False
   DoEvents 'If it doesn't work uncomment this line
   tmpdc = GetDC(Form1.ImgEdit1.hwnd)
   
   With Me
      StretchBlt .hdc, 0, 0, .ScaleWidth, .ScaleHeight, _
                  tmpdc, 0, 0, .ScaleWidth / 2, .ScaleHeight / 2, vbSrcCopy
      .Refresh
   End With
   Me.Visible = True
   LockWindowUpdate False
End Sub


Note From2 ScaleMode = vbPixels
AutoRedraw = True
0
 
LVL 5

Expert Comment

by:JohnMcCann
ID: 8128565
A tiny bit neater

Private Sub Command1_Click()
Dim tmpdc As Long
Dim hWndDesk As Long, hDCDesk As Long

   hWndDesk = GetDesktopWindow()
   hDCDesk = GetDC(hWndDesk)
   
   tmpdc = GetDC(Form1.ImgEdit1.hwnd)
   
   With Me
      .Visible = False
      DoEvents
      StretchBlt .hdc, 0, 0, .ScaleWidth, .ScaleHeight, _
                 tmpdc, 0, 0, .ScaleWidth / 2, .ScaleHeight / 2, vbSrcCopy
      .Refresh
      .Visible = True
   End With
   
   ReleaseDC hWndDesk, hDCDesk
End Sub

But still there will be some flicker.
0
 

Author Comment

by:zomby_dog
ID: 8135161
Hmmmm, yes it does work, there seems to be to much flicker... I wouldn't be ble to put this on the mouse move event. There must be a better way to do this...
0
 
LVL 5

Expert Comment

by:JohnMcCann
ID: 8135746
If you do not need thew Kodax Image edit control and used the picturebox instead.

Private Sub Command1_Click()
Dim tmpdc As Long

  tmpdc = Form1.Picture1.hDC
 
  With Me
     StretchBlt .hdc, 0, 0, .ScaleWidth, .ScaleHeight, _
                tmpdc, 0, 0, .ScaleWidth / 2, .ScaleHeight / 2, vbSrcCopy
     .Refresh
  End With
End Sub
0
 

Author Comment

by:zomby_dog
ID: 8136054
Unfortunalty i do need it.As it provides zooming, panning, zoom selection, advanced printing etc., etc.
0
 
LVL 5

Accepted Solution

by:
JohnMcCann earned 1000 total points
ID: 8136177
I have had a little look and I think you are going to have to use ImgEdit1.ClipboardCopy

As this appears to reduce the flicker.

I have not got this working properly yet, I'll leave it to you if you get stuck just ask.

How I would do it.

1) GetCursorPostion relative to ImgEdit1
2) Use cordinates above as parameters for ImgEdit1.ClipboardCopy
3) Paste the clipboard into a picture
4) Stretch the picture onto your form.
0
 

Author Comment

by:zomby_dog
ID: 8136969
Cheers for your help, i have used your final suggestion and it works well enough for my purposes. thanks for spending so much time helping me with this problem.
0
 
LVL 5

Expert Comment

by:JohnMcCann
ID: 8137048
It's ok.
0

Featured Post

What does it mean to be "Always On"?

Is your cloud always on? With an Always On cloud you won't have to worry about downtime for maintenance or software application code updates, ensuring that your bottom line isn't affected.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Introduction While answering a recent question about filtering a custom class collection, I realized that this could be accomplished with very little code by using the ScriptControl (SC) library.  This article will introduce you to the SC library a…
When trying to find the cause of a problem in VBA or VB6 it's often valuable to know what procedures were executed prior to the error. You can use the Call Stack for that but it is often inadequate because it may show procedures you aren't intereste…
Get people started with the process of using Access VBA to control Outlook using automation, Microsoft Access can control other applications. An example is the ability to programmatically talk to Microsoft Outlook. Using automation, an Access applic…
This lesson covers basic error handling code in Microsoft Excel using VBA. This is the first lesson in a 3-part series that uses code to loop through an Excel spreadsheet in VBA and then fix errors, taking advantage of error handling code. This l…
Suggested Courses

777 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question