[squeak-dev] [long] Squeak and High-DPI
Das.Linux at gmx.de
Mon May 2 19:04:55 UTC 2016
[this is a longish post, you might want to use this toc]
- [DEFAULT DPI]
- [WINDOWS DPI]
- [OSX CARBON DPI]
- [OSX COCOA DPI]
- [SUGGESTIONS] <<<< PLEASE COMMENT
- [OSX COCOA PATCH]
- [VM/IMAGE INTERFACE]
For some time now, OSX and also Windows support screens of different pixel per inch (DPI, :P).
The approaches are slightly different; but both support a fallback mode where the pixel content of non-aware applications is automatically scaled to look like on "default dpi"[See DEFAULT DPI]. Effectively, we end up with pixel doubling.
One way or another, this means Squeak looks somewhat pixelated on new hardware.
These are some thoughts of mine on how to address this.
[DPI] Actually "dots-per-inch" but freely used in multiple senses by different people. For displays it used to mean "how many pixels are there approximately in an inch?", but for a long time now, The [DEFAULT DPI] that OSes report usually was fixed/defaulted (Win: 96, OS X: 72), _regardless_ of the actual screen's dpi.
[DEFAULT DPI] On OS X, the system reports default DPI as 72 dpi and Retina typically as 144 dpi, _although_ the "actual" dpi is different. For example, My MacBook Pro 15" is reported as 144dpi, but https://www.sven.de/dpi/ calculates that I have 220.53 pixel to the inch. That's why Apple is moving away from DPI and just talking about a "scale factor", and the abstract "point" principle, moving away from actual pixels for "user content". On Windows, the default dpi is 96 dpi, but Windows always made it a little easier to change that.
Squeak also has a default dpi, namely 96.0 dpi.
Windows supports different levels of DPI awareness, available depending on OS Version.
Long story short, with calling a special function or (As we did/do/can do) setting a key in the executables ".manifest" file to "true" or "true/PM", Windows treats our Application as DPI-Aware.
Currently the effect of enabling this for our VMs means:
- Looks ok on non-High-DPI screens
- Looks tiny on High-DPI screens
- Moving the VM between High-DPI and non-High-DPI screens changes the outer frame size of the application, the pixel size reported _to_ the VM remains the same.
[OSX CARBON DPI]
DPI-awareness and High-DPI are not possible with the QuickDraw-API the Carbon VM used to use.
[OSX COCOA DPI]
OS X now has a Device-in-pixel mode and a Userspace-in-"point" mode. When opted-in via Info.plist file, on AppKit-Level, one can convert between those with +[NSScreen backingScaleFactor], -convertRectToBacking:, -convertRectFromBacking and similar. On Quartz2D/CoreGraphics-Level, CGContextGetUserSpaceToDeviceSpaceTransform(), CGContextConvertRectToDeviceSpace(), and CGContextConvertRectToUserSpace() can be used. Both approaches are slightly different. OpenGL needs an additional Opt-in.
In contrast (currently) to Windows, when moving between high- and non-high-DPI, the outer frame size of the application stays the same but the pixels of the backing store change.
Up until now, the Cocoa branch is not DPI-aware.
[OSX COCOA PATCH]
Attached is a patch that makes the VM High-DPI ready. PLEASE COMMENT.
- Add Info.plist entry to state whether we want High DPI (NSHighResolutionCapable)
THIS IS DISABLED BY DEFAULT (as with the Windows VM's manifest)
- All Views:
-add -sqScreenSize for the Pixel-dimensions to report to Squeak (and use for calculation in Squeak coordinates)
-add -sqMousePosition: to convert Mouse coordinates from the View's system (maybe high-dpi) to Squeak coordinates
- OpenGL view:
- Opt-in for High resolution (-setWantsBestResolutionOpenGLSurface:) (overridden by Info.plist's entry)
- Make texture size/tracking rects based on -sqScreenSize
- Quartz2D/CoreGraphics view:
- Work around deprecation of [[NSGraphicsContext currentContext] graphicsPort] in OS X 10.10
- Draw image in -sqScreenSize size, and position correctly in the View's coordinate system
- (remove some duplication from OpenGL view)
- iPhone SqueakUIView:
- use Fallbacks for -sqScreenSize/-sqMousePosition:, no High-DPI yet.
Note: this patch is against the Cog/platform/ios directory, Interpreter needs similar treating.
With the current Windows VM and the Cocoa VM (+patch as above), users can Opt-in for High-DPI.
However, the Image does not know that its high pixel count is on a small display (hello Etoys!). I _want_ the image to know and to be able to react.
I think that the image should treat DPI changes similar screen size changes. Here are my ideas:
- The VM exposes screen size as prim 106, screen depth as 'primitiveScreenDepth'
* We should expose 'primitivePixelPerInch' with a fallback of '^ 96.0'.
* 96.0 dpi shall be the [DEFAULT DPI] of Squeak.
> For OS X that would mean, on non-high-dpi it shall report 96.0 dpi (not 72 dpi), on high-dpi it shall report 192.0 dpi (not 144)
> Windows already has 96.0 dpi as [DEFAULT DPI], it shall reuse that and adhere to 
- The image regularly checks the display size (DisplayScreen class>>checkForNewScreenSize).
* We should do the same for DPI (Morphic main loop etc.)
- There's already a client of DPI changes, TextStyles.
* The image shall store changed dpi settings to TextStyles>>pixelsPerInch:
- Projects can react to display size changes via #displaySizeChanged, But only fonts can react to DPI changes via #pixelsPerInchChanged
* We shall make project able to react to dpi changes, maybe via #pixelsPerInchChanged
- The standard tools are currently pixel-oriented and use hard-coded pixel values
* I am unsure.
* We could introduce conventions to act dpi-dependent (integers: pixels with autoscaling (pixels / default dpi * actual dpi or so), floats or scaled: dpi-based, via TextStyle class>>pointsToPixels:).
* We could introduce actual units and say "this tool is 3 cm wide" and calculate pixels via #pointsToPixels:.
* We could eliminate hard-coded values and base tools on font sizes. I tried that with the FontImporterTool (for example: FontImporterTool>>#buttonHeight, #filenameHeight. This may be hard and not very traceable, tho.
- We could move the dpi api from TextStyle to somewhere more general.
I know there are some rough edges here and there; I'd like to hear your suggestions.
Let's make Squeak look nice and sharp :)
PS: Thanks to Marcel for some valuable suggestions and help to get Quartz transformations right.
-------------- next part --------------
A non-text attachment was scrubbed...
Size: 19320 bytes
Desc: not available
Url : http://lists.squeakfoundation.org/pipermail/squeak-dev/attachments/20160502/d4ad2a40/osx-highdpi-0001.obj
More information about the Squeak-dev