My Pointer Noodge application displays an animated image surrounding the mouse 
pointer using a layer-hosting multi-screen view: 
<http://pfiddlesoft.com/pfiddles>. I am having difficulty upgrading it to 
handle a mix of retina and non-retina displays. All help appreciated.

The specific problem is that the image surrounding the pointer appears highly 
pixellated when the pointer moves onto a HiDPI screen. I can see that the 
correct @2x image has been loaded into the layer's contents, and it appears at 
the correct size on the HiDPI screen, but it is pixellated.

My implementation creates a borderless transparent overlay window more or less 
on the model of Apple's FunkyOverlayWindow sample code. The overlay window 
encompasses all attached screens (which I suspect is the problem; see below). 
The overlay window's content view is a layer-hosting view. The animated image 
is implemented using CALayer, which handles all the drawing.

The image surrounding the pointer is an NSImage object containing two image 
representations, created as a TIFF file by Xcode from a normal and a @2x PNG 
image file. I have examined the combined TIFF image file in the built 
application, and it looks correct when opened in Preview. In fact, I can drag 
the Preview window onto the HiDPI screen and it looks correct -- no pixellation 
appears in the HiDPI image representation.

The documentation says that an NSImage-based layer will automatically choose 
the image representation with the correct scale in most situations, but, not 
surprisingly, this is apparently not one of those situations.

In an attempt to force the CALayer object to draw the correct image 
representation, I have written a simple routine using NSTrackingArea to detect 
when the pointer enters a new screen. My implementation of the -[NSResponder 
mouseEntered:] method is called every time the pointer enters a new screen, and 
an NSLog() call shows the screen's backingScaleFactor as 2.0 or 1.0 depending 
on whether it is a retina display screen or not. Another NSLog() call shows 
that the image contains the two image representations, as expected. I then try 
a variety of techniques to display the correct representation, but I always see 
a pixellated image. The simplest technique detects the backingScaleFactor of 
the newly-entered screen, creates a copy of the NSImage object, removes the 
representation with the wrong scale, and sets the layer's contents to the 
resulting NSImage object. An NSLog() call confirms that the layer's contents 
are the single image representation with the correct scale. But it is drawn 
pixellated. Setting the contentsScale of the overlay window's contentView to 
the backingScaleFactor of the screen does not help. Doing the same thing by 
setting the view to be the layer's delegate and triggering the -displayLayer: 
delegate method by sending the -setNeedsDisplay message to the layer when the 
pointer enters a new screen has the same problem.

My best guess is that the problem results from the fact that the overlay window 
spans all attached screens. An NSLog() call confirms that the window's 
backingScaleFactor is always 1.0 (because it is initially created on a 
non-retina display in my testing). There is no NSWindow method to 
-setBackingScaleFactor, so there appears to be nothing I can do about this. 
Reading the documentation about CALayer and HiDPI screens very, very carefully, 
I notice that it always assumes that the layer-hosting view is in a window that 
is being dragged across screen boundaries. Am I correct in guessing that a 
fixed multi-screen window simply isn't capable of displaying HiDPI images if 
the window started out with a backingScaleFactor of 1.0?

If that's correct, I guess I'll have to abandon my multi-screen overlay window 
and implement a multi-overlay-window solution, which is going to be a ton of 
work. Unless somebody can suggest a different approach using a multi-screen 
overlay window.

-- 

Bill Cheeseman - b...@cheeseman.name

_______________________________________________

Cocoa-dev mailing list (Cocoa-dev@lists.apple.com)

Please do not post admin requests or moderator comments to the list.
Contact the moderators at cocoa-dev-admins(at)lists.apple.com

Help/Unsubscribe/Update your Subscription:
https://lists.apple.com/mailman/options/cocoa-dev/archive%40mail-archive.com

This email sent to arch...@mail-archive.com

Reply via email to