dcsimg
Results 1 to 22 of 22

Thread: Display dpi scaling problem

  1. #1

    Thread Starter
    Fanatic Member
    Join Date
    Apr 2015
    Location
    Finland
    Posts
    657

    Display dpi scaling problem

    Any idea, how to remedy situation, when user has dpi scaling set to other than 100% ?

    On some workstations, textboxes shift from their original place to right- and downwards, depending of display scaling value set.

    Tested this on several different boxes/OS versions and it seems, that W7 boxes are more prone to shifting of controls than, W10 boxes.
    Attached Images Attached Images  

  2. #2
    Hyperactive Member
    Join Date
    Feb 2019
    Posts
    382

    Re: Display dpi scaling problem


  3. #3
    Frenzied Member
    Join Date
    Feb 2017
    Posts
    1,727

    Re: Display dpi scaling problem

    Quote Originally Posted by Tech99 View Post
    Any idea, how to remedy situation, when user has dpi scaling set to other than 100% ?

    On some workstations, textboxes shift from their original place to right- and downwards, depending of display scaling value set.

    Tested this on several different boxes/OS versions and it seems, that W7 boxes are more prone to shifting of controls than, W10 boxes.
    For this to happen you must have a manifest file for the exe declaring the program as DPI aware or an special setting in the compatibility tab of the properties of the exe in the end user machine.

    Also, your form's ScaleMode must be set to vbPixels.

    Solution: Set the form's ScaleMode to vbTwips or don't declare it as DPI aware in the manifest.

    They are not the same thing, if you remove the DPI aware section from the manifest, the program will be a bit blurred when the scale is not 100%.

  4. #4

    Thread Starter
    Fanatic Member
    Join Date
    Apr 2015
    Location
    Finland
    Posts
    657

    Re: Display dpi scaling problem

    Hi Eduardo,

    Form scalemode is twips, usercontrol also has twips, but picturebox inside usercontrol scalemode is pixels. Application is manifested as dpi aware and no compatibility settings defined on .exe shortcut.

    W10 machines tested are all ok, problem is group of W7 machines, most are ok though.

    Thanks for the link, and thanks to La volpe also - extensive article - indeed more work to be in dpi aware, have to read and see what can be done.

  5. #5
    PowerPoster
    Join Date
    Feb 2006
    Posts
    20,323

    Re: Display dpi scaling problem

    Improving the high-DPI experience in GDI based Desktop Apps goes into changes in recent versions of Windows 10 that help address DPI Scaling issues for VB6 programs. Most of the "meat" for developers is near the end.

    To sum up

    High DPI displays are a hit but computer users are being blocked from getting the value out of all that extra pixels for older apps. It turns out that changing the scale of the display is a pretty big breaking change for older applications. To help, the GDI team at Microsoft has come up with a feature that lets some of these apps compensate for this change with minimum changes–GDI Scaling.
    Windows 7 SP1 drops off extended support in 6 months. Windows 8 and 8.1 are unsupported already. Windows 8.1 Fire Two ("Update 1") is only on a tiny minority of devices. There is no good reason for you to try to support those dead and dying OSs anyway.


    You can try to go whole hog and fully support DPI Awareness but it can be a ton of effort. The Win10 1703 GDI Scaling appcompat option doesn't handle every scenario but for most common applications it can do it all and others only need minor tweaks like using compatible bitmaps and metafile vector graphics instead of DIBs.

    An option to consider.

  6. #6
    Frenzied Member
    Join Date
    Feb 2017
    Posts
    1,727

    Re: Display dpi scaling problem

    Quote Originally Posted by Tech99 View Post
    but picturebox inside usercontrol scalemode is pixels
    That must be causing the problem then.

  7. #7
    VB-aholic & Lovin' It LaVolpe's Avatar
    Join Date
    Oct 2007
    Location
    Beside Waldo
    Posts
    18,234

    Re: Display dpi scaling problem

    Quote Originally Posted by Eduardo- View Post
    That must be causing the problem then.
    Likely. Always save the form and all of its controls in twips scalemode. If pixels or another scalemode is needed at runtime, change the scalemode in form load, i.e., Picutre1.ScaleMode = vbPixels.
    Insomnia is just a byproduct of, "It can't be done"

    Classics Enthusiast? Here's my 1969 Mustang Mach I Fastback. Her sister '67 Coupe has been adopted

    Newbie? Novice? Bored? Spend a few minutes browsing the FAQ section of the forum.
    Read the HitchHiker's Guide to Getting Help on the Forums.
    Here is the list of TAGs you can use to format your posts
    Here are VB6 Help Files online


    {Alpha Image Control} {Memory Leak FAQ} {Unicode Open/Save Dialog} {Resource Image Viewer/Extractor}
    {VB and DPI Tutorial} {Manifest Creator} {UserControl Button Template} {stdPicture Render Usage}

  8. #8
    PowerPoster
    Join Date
    Jun 2013
    Posts
    4,322

    Re: Display dpi scaling problem

    That must be causing the problem then.
    Quote Originally Posted by LaVolpe View Post
    Likely.
    I'd think "unlikely" - because:
    When Windows does DPI-related adjustment as the OP described them -
    these often happen (when the "cheap, blurry scaling of the whole Form-ClientArea" is not in place),
    based on the hWnds of Controls by the Win-DPI-Scaling-mechanism which tries "to correct things"...

    So, on a system with 200% scaling-factor:
    - the Form will be resized to twice its original size (to be precise, so that its client-area will end up with twice the size)
    - all PicBox-Controls on that Form will be resized to twice their original size (and their TopLeft -ClientRect-Coord will be shifted factor 2 as well)
    - same goes for hWnd'ed Controls which have that PicBox as their parent-container

    What *doesn't happen* (in a reliable manner at least) is, an automatic resizing/rescaling of a PicBox StdPicture-content.
    At least I cannot see how the "sizing of StdPic-Content" on a VB.PicBox.Picture.Property is related to its current Scalemode.

    If I set a PicBox-Picture-Property (e.g. via LoadPicture) to an ImageBitmap which is 24x24 Pixels,
    then its rendered size does not change, no matter if I previously have set the PicBox-Scalemode to vbPixels or vbTwips.

    A VB.PictureBox has no directly built-in way, to "scale current StdPicture-content along with its outer size"
    (as e.g. the VB.Image-Control supports it).

    IMO that's the reason why the original ScreenShot of the OP is "like it is":
    the hWnd-based Controls were all "resized and TopLeft-shifted" (according to the new DPI-scale) -
    but the size of the PicBox StdPicture content (the underlying Bitmap with its Pixels) remained constant.

    So, what the OP will have to ensure is (IMO) - to "scale the contained Image, when the container-size changes".
    (in that case the PictureBox, when it is "autoresized" hWnd-wise by the external DPI-scaler - a Resize-Event should happen, where one could ensure such a content-scaling).

    Olaf
    Last edited by Schmidt; Jun 5th, 2019 at 08:30 PM.

  9. #9
    Frenzied Member
    Join Date
    Feb 2017
    Posts
    1,727

    Re: Display dpi scaling problem

    The problem of the OP wasn't the size of images but the position and size of textboxes.
    It is true that VB automatically convert sizes and positions even if the ScaleMode of the container is in Pixels, but that only applies to the design time values.

    If by code the program positions and/or sizes controls based in Pixels coordinates, that is when the problems occurs.
    The solution, again, is to work in Twips.

    Or... to convert the Pixels to the current DPI setting:
    NewValue = OrigValue / Screen.TwipsPerPixelX/Y * 15
    But only if there is a real reason to work in Pixels.
    Last edited by Eduardo-; Jun 6th, 2019 at 03:29 AM.

  10. #10
    PowerPoster
    Join Date
    Jun 2013
    Posts
    4,322

    Re: Display dpi scaling problem

    Quote Originally Posted by Eduardo- View Post
    The problem of the OP wasn't the size of images but the position and size of textboxes.
    Of course - the problem of the OP happens, because the position and size of PictureBoxes and TextBoxes was changed by Windows.
    (and Windows does not care, nor does it know about vbTwips).

    And the solution for the OP is simply, to scale the *unchanged and unscaled Bitmap-content* (within the affected and externally resized PicBox) -
    according to the new dimensions of that PicBox-container.

    Olaf

  11. #11
    Frenzied Member
    Join Date
    Feb 2017
    Posts
    1,727

    Re: Display dpi scaling problem

    Quote Originally Posted by Schmidt View Post
    Of course - the problem of the OP happens, because the position and size of PictureBoxes and TextBoxes was changed by Windows.
    No. It is not changed by Windows.
    VB is the one that does the scaling automatically from the design time DPI to the run-time DPI.

    If the measures are in Twips, all right, now with the new PDI setting one twip is bigger ("bigger" meaning having more pixels) and the scaling is "natural", since Twips is an unit based in virtual size (similar to real world sizes) like the ones based in inches or centimeters and should not be affected by DPI settings.

    If the measures are in pixels, it is in fact affected by DPI settings, because in higher DPI settings there are more pixels per inch and then the pixels get smaller.
    And if the pixels are smaller and measures in pixels are the same, the objects in the screen get smaller to the eye (that's is what happen also with images).

    VB, not respecting the measures in pixels that you set at design time, helps you by changing the measures and size of the controls, changing their sizes and positions in pixels to adapt to the new DPI setting.
    That means that if you designed a textbox of 100 pixels at 96 DPI, it will become 125 pixels at 120 DPI.
    But that automatic re-scaling only applies to what you set at design time.

    The problem comes when in the code there is a repositioning of the controls (that is something very normal to do). If the code moves the textbox to:
    Texbox.Move 500, 300, 100, 45
    That size and position gets "fixed" in pixels in whatever DPI it is running, and VB does not help you in that case.

    That's why it is advisable to work in Twips, because Twips are always adjusted automatically to the current DPI setting.
    Instead of Twips, it can also be Centimeters, Millimeters, Inches, Himetric or Points. I say Twips because it is the VB default and because in the containers that don't have ScaleMode their scales are fixed in Twips.
    In fact, vbPixels is the only ScaleMode setting that has the problem.

    Quote Originally Posted by Schmidt View Post
    (and Windows does not care, nor does it know about vbTwips).
    That's correct.

    Quote Originally Posted by Schmidt View Post
    And the solution for the OP is simply, to scale the *unchanged and unscaled Bitmap-content* (within the affected and externally resized PicBox) -
    according to the new dimensions of that PicBox-container.

    Olaf
    Images are a different issue.
    The images are not scaled by VB. It is understable: bitmap images and icons are pixel based. You need to do the scaling yourself.

    That are basically the two main issues about being DPI aware.

  12. #12
    PowerPoster
    Join Date
    Jun 2013
    Posts
    4,322

    Re: Display dpi scaling problem

    Quote Originally Posted by Eduardo- View Post
    No. It is not changed by Windows.
    VB is the one that does the scaling...
    No.
    Seems there's still a fundamental misunderstanding on your end - how all that modern DPI-awareness stuff works,
    because if VB6 (the VB6-runtime) would do the scaling, then the vbRuntime would be fully DPI-aware -
    and then would (have to) tell the system about it explicitely (in an appropriate manifest).

    But as we all know, VB6 is definitely not DPI-aware (as the term is understood these days) - since it was developed at a time, where manifests were not even invented.

    So (again) - it remains entirely to the system (the Win-OS), to ensure a kind of "Auto-DPI-awareness" on Applications,
    which didn't tell the system via manifest, that they are fully capable, to handle that stuff properly via "internal means".

    So, when you tell the system, that your App "is fully DPI-aware" (in your manifest), you tell it to do nothing (scaling-wise from the outside) on your App-hWnds.
    In all other cases, the system will "try something" - and "how much - and what it tries"...:
    - depends on the OS
    - and what you've told it in your manifest via the different attributes in the XML-node
    - or if you had a manifest included in your App at all

    So, as said - it is the Windows-OS which will attempt to scale your TopLevel-Forms, and their Child-Control-hWnds,
    in case you haven't flagged your App as "fully DPI-aware" via manifest.

    And as you already admitted - the System does not know anything about "vbTwips" -
    the Window-manager of the OS works (as you know from the Win32-API-Declares) entirely pixel-based.

    And so it does not matter at all, whether you have vbTwips or vbPixels set as the Form-Scalemode -
    a PictureBox-Child-hWnd on that Form will be resized (scaled) in always the same way by the system,
    when your App does not include a manifest with "full dpi-awareness".

    Please make this test yourself:
    - create a Form in a simple project, set the Form-Scalemode to Pixels and adjust its Client-Area to 200x200 Pixels.
    - then place a Picture1 on it, where you switch off the Borders - and then size this PixBox to 100x100 Pixels in the designer.

    Compile that Project to TestPixels.exe
    Now change that Forms Scalemode back to vbTwips again - and compile to TestTwips.exe.

    Now change your Screen-Res to e.g. 150% (144dpi) - and start the two executables.

    Here is, what you'll find when you start TestPixels.exe:


    And here is the result for TestTwips.exe:


    The results are apparently identical (since the Form, as well as the PixBox were scaled by the system... q.e.d.)...

    HTH

    Olaf

  13. #13
    Frenzied Member
    Join Date
    Feb 2017
    Posts
    1,727

    Re: Display dpi scaling problem

    Quote Originally Posted by Schmidt View Post
    if VB6 (the VB6-runtime) would do the scaling, then the vbRuntime would be fully DPI-aware -
    The VB6 runtime, in fact is fully DPI aware as long as you work in Twips.

    The are still some few things that demand some work on the developer side, mainly the scaling of images.

    Quote Originally Posted by Schmidt View Post
    and then would (have to) tell the system about it explicitly (in an appropriate manifest).
    Of course, all this "discussion" assumes that you are manifesting the exe as DPI aware.
    And that is the case of the OP in this thread.

    Quote Originally Posted by Schmidt View Post
    But as we all know, VB6 is definitely not DPI-aware (as the term is understood these days) - since it was developed at a time, where manifests were not even invented.
    I see you are very confused.
    These days DPI changes and adapting to different DPI settings are the same as they were before, in 1998.
    I could say that VB6 was quite advanced in that regard. The developers cared about to provide some automatic DPI adapting support.

    The issue of manifesting programs is another issue.
    I'll explain:
    Even when some developers cared about adapting their programs to different DPI settings (as VB6 developer did), most programmers did not take the time and the work to do such barely necessary thing at the time. Because almost everybody used 96 DPI (called 100% today).
    And many other didn't even know what DPI setting was and what it meant and how it affected the applications (I was in that group).

    When LCD monitors became to offer higher and higher DPI, MS realized that there was a big problem incoming, since most of the programs didn't adapt well to higher DPI settings.
    They decide to take action from their side to try to remedy this problem, since it was unlikely that millions of developers overnight would all adapt their programs.

    But their solution had a drawback, it produces blurry screens.
    So, they didn't want to condemn all the programs to be blurry, since some, and hopefully an increasing number over time will do the homework and make their programs DPI aware.

    Then there is when the DPI aware manifest comes into play.

    Quote Originally Posted by Schmidt View Post
    So (again) - it remains entirely to the system (the Win-OS), to ensure a kind of "Auto-DPI-awareness" on Applications,
    which didn't tell the system via manifest, that they are fully capable, to handle that stuff properly via "internal means".

    So, when you tell the system, that your App "is fully DPI-aware" (in your manifest), you tell it to do nothing (scaling-wise from the outside) on your App-hWnds.
    In all other cases, the system will "try something" - and "how much - and what it tries"...:
    - depends on the OS
    - and what you've told it in your manifest via the different attributes in the XML-node
    - or if you had a manifest included in your App at all

    So, as said - it is the Windows-OS which will attempt to scale your TopLevel-Forms, and their Child-Control-hWnds,
    in case you haven't flagged your App as "fully DPI-aware" via manifest.

    And as you already admitted - the System does not know anything about "vbTwips" -
    the Window-manager of the OS works (as you know from the Win32-API-Declares) entirely pixel-based.

    And so it does not matter at all, whether you have vbTwips or vbPixels set as the Form-Scalemode -
    a PictureBox-Child-hWnd on that Form will be resized (scaled) in always the same way by the system,
    when your App does not include a manifest with "full dpi-awareness".
    You are talking about the same: the blurry images that Windows produces.
    That's not the adaptation I was talking about.
    I see that you don't get the point of what I explained before.

    I'll try again:

    VB6 works in Twips. Read an *.frm file and you'll see that VB6 stores the dimensions and sizes in Twips, not Pixels.

    Twips, unlike Pixels is an unit of measurement that is DPI agnostics.
    Twips are converted to pixels only at the end, when it already know in what DPI setting is is running.
    That is what makes VB6 to adapt automatically to different DPI settings.

    I hope that this time you think about it and get the point of what I explained.
    Last edited by Eduardo-; Jun 6th, 2019 at 10:08 AM.

  14. #14
    PowerPoster
    Join Date
    Feb 2006
    Posts
    20,323

    Re: Display dpi scaling problem

    Working in Twips would resolve many of the High DPI issues except when Twips/Pixel is not a whole number, such as 200% DPI (7.5 Twips/Pixel). LaVolpe's writeup covered that as well as some issues specific to UserControl metrics.

    There is a similar problem with text sizes in Points and font scaling in general.

  15. #15
    Frenzied Member
    Join Date
    Feb 2017
    Posts
    1,727

    Re: Display dpi scaling problem

    Quote Originally Posted by dilettante View Post
    Working in Twips would resolve many of the High DPI issues except when Twips/Pixel is not a whole number, such as 200% DPI (7.5 Twips/Pixel). LaVolpe's writeup covered that as well as some issues specific to UserControl metrics.

    There is a similar problem with text sizes in Points and font scaling in general.
    I suggest to forget about the TwipsPerPixel issue. That renders the current version of VB6 almost unusable.
    Yes, you can find workarounds, but that renders your code like not being a normal language any more. Better use C or Assembler if you will have to go to that level of programming for a simple hello world program (or any other program that has a GUI).

  16. #16
    Frenzied Member
    Join Date
    Feb 2017
    Posts
    1,727

    Re: Display dpi scaling problem

    You dilettante that are the master of the manifest files, is there a way to make a manifest that declares that the program is DPI aware for some DPI settings but not for other settings?

    It will be DPI aware if 1440/DPI is integer, but if it is not, then it is not DPI aware and the OS should handle the scaling in that case.

    That would be a solution to the problem of the TwipsPerPixel rounding.

  17. #17
    PowerPoster
    Join Date
    Feb 2006
    Posts
    20,323

    Re: Display dpi scaling problem

    No, there isn't any provision for that. Even if there was it would mean blurriness or mutilation at some DPI settings but not others.

    That's why I suggest using GDI Scaling for most programs. Program's which can't be handled with that (and maybe a few image tweaks) means doing a lot more work as you describe. That's just how it is.

    The issues aren't isolated to VB, you see them to a greater or lesser degree no matter what you use.

  18. #18
    VB-aholic & Lovin' It LaVolpe's Avatar
    Join Date
    Oct 2007
    Location
    Beside Waldo
    Posts
    18,234

    Re: Display dpi scaling problem

    Quote Originally Posted by Eduardo- View Post
    You dilettante that are the master of the manifest files, is there a way to make a manifest that declares that the program is DPI aware for some DPI settings but not for other settings?
    Technically, it could be possible but don't know if it's worth the effort and requires a registry modification.

    On modern O/S, Windows will not honor external manifests. Well, a registry setting overrides that, at least until Windows decides to never use them again (if that happens). So, you can probably see where I'm going. If external manifests are honored, you could possibly start the application, detect the DPI, then unload & restart using a different manifest as desired.

    Again, even if it is possible, I think it is also possible that Windows caching of manifests may interfere with such a strategy.

    Edited: Eduardo, regarding VB being DPI aware... On XP/Vista/Win7, there was an XP-Style DPI scaling option that can be set system-wide (no manifest needed). That setting disabled virtualization (Vista/Win7). Been awhile since I used those systems, but if I recall, VB's built-in DPI awareness messed up some projects. A solution used by many was to force their application into virtualization so they didn't have to mess with DPI.
    Last edited by LaVolpe; Jun 7th, 2019 at 11:59 PM.
    Insomnia is just a byproduct of, "It can't be done"

    Classics Enthusiast? Here's my 1969 Mustang Mach I Fastback. Her sister '67 Coupe has been adopted

    Newbie? Novice? Bored? Spend a few minutes browsing the FAQ section of the forum.
    Read the HitchHiker's Guide to Getting Help on the Forums.
    Here is the list of TAGs you can use to format your posts
    Here are VB6 Help Files online


    {Alpha Image Control} {Memory Leak FAQ} {Unicode Open/Save Dialog} {Resource Image Viewer/Extractor}
    {VB and DPI Tutorial} {Manifest Creator} {UserControl Button Template} {stdPicture Render Usage}

  19. #19
    PowerPoster
    Join Date
    Feb 2006
    Posts
    20,323

    Re: Display dpi scaling problem

    The only reliable thing I can think of is to take your application A.EXE and provide an A1.EXE and A2.EXE with different manifests. Then write a launcher program to take the place of A.EXE and install that as the "real" application. It might look at its environment and decide whether to launch A1 or A2.

  20. #20
    Frenzied Member
    Join Date
    Feb 2017
    Posts
    1,727

    Re: Display dpi scaling problem

    Quote Originally Posted by dilettante View Post
    The only reliable thing I can think of is to take your application A.EXE and provide an A1.EXE and A2.EXE with different manifests. Then write a launcher program to take the place of A.EXE and install that as the "real" application. It might look at its environment and decide whether to launch A1 or A2.
    Exactly.
    I could not come to the forums the last days, but that was my idea.
    For now I still stay in my decision of not supporting not integers TwipsPerPixels, because anyway I think there is probable nobody that tried to use my programs in non integers TwipsPerPixels settings (currently it would be mainly 200% -192 DPI).
    But... but... when this issue come to be an actual problem in practice in the future, I think I'll do that: one exe will be the launcher, it will check the DPI/TPP and if TPP is integer it would launch an exe manifested as DPI aware, and if it is not integer, then it would launch an exe manifested to use GDI scaling.
    The Scaling that Windows performs is blurry at 120%, but I think it must be much better at 200%, probably not blurry at all since it is and integer multiple.

  21. #21
    Frenzied Member wqweto's Avatar
    Join Date
    May 2011
    Posts
    1,477

    Re: Display dpi scaling problem

    Technically you only need 2 executables for a hack like this. The main app is manifested and if DPI is non-integer it acts as the laucher by silently re-spawning a non-manifested clone.

    cheers,
    </wqw>

  22. #22
    Frenzied Member
    Join Date
    Feb 2017
    Posts
    1,727

    Re: Display dpi scaling problem

    Quote Originally Posted by wqweto View Post
    Technically you only need 2 executables for a hack like this. The main app is manifested and if DPI is non-integer it acts as the laucher by silently re-spawning a non-manifested clone.

    cheers,
    </wqw>
    Yes, exactly.

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  



Featured


Click Here to Expand Forum to Full Width