Search code examples
xcodecocoanssegmentedcontrol

Muddy text when dragging NSSegmentedControl


I have an NSSegmentedControl within a draggable view (This is a much simplified test case to demonstrate the problem).

When first created everything looks ok as in this image:

Initial View

The view with the light green background is draggable. If I drag it slightly, the text in the lower NSSegmentedControl becomes "muddy", as in this image:

Control with muddy text

Also, while the view is being dragged, the text in the NSSegmentedControl flickers.

All views and controls are created in a nib, and there is no unusual code. The wantsLayer property of the view is set to YES, so that a border and background color can be displayed. This is just to make it easier to see the issue, but the problem occurs even if wantsLayer is set to NO.

The problem occurs only when the view is dragged. Dragging the main application window does not cause this effect.

This is on MacOS High Sierra 10.13.6, XCode 10.1

This is driving me crazy, so any help appreciated!

Edit: Here is the dragging code:

//
//  DraggableView.h
//

#import <Cocoa/Cocoa.h>

@interface DraggableView : NSView

@property(assign,nonatomic) NSPoint dragStart;
@property(assign,nonatomic) NSPoint startOrigin;

@end



//
//  DraggableView.m
//

#import "DraggableView.h"

@implementation DraggableView

// mouseDown - start dragging

- (void) mouseDown:(NSEvent *)theEvent {

    _dragStart = [[self superview] convertPoint:[theEvent locationInWindow] fromView:nil];
    _startOrigin = [self frame].origin;
}

// mouseDragged - move the view

- (void) mouseDragged:(NSEvent *)theEvent {

    CGPoint currentDrag = [[self superview] convertPoint:[theEvent locationInWindow] fromView:nil];

    CGPoint newOrigin = self.startOrigin;
    newOrigin.x += (currentDrag.x - _dragStart.x);
    newOrigin.y += (currentDrag.y - _dragStart.y);

    [self setFrameOrigin:newOrigin];
}

@end

All other code is standard Cocoa boilerplate for a document-based application.

The nib file defines the draggable view as an instance of the DraggableView class.


Solution

  • I resolved this by changing my drag code as follows:

    // mouseDragged - move the view
    
    - (void) mouseDragged:(NSEvent *)theEvent {
    
        CGPoint newOrigin = self.startOrigin;
        newOrigin.x += theEvent.deltaX;
        newOrigin.y -= theEvent.deltaY;
    
        [self setFrameOrigin:newOrigin];
    
        _startOrigin = newOrigin;
    }
    

    The underlying cause of this problem was that the draggable view origin had non-integer coordinates. Thanks to Matt for pointing me in the right direction.