2009-01-12 25 views
12

我对NSView有疑问:当父窗口不是窗口时,有没有办法获得相对于最内层NSView的坐标?

想象一下自定义视图,其中mouseDown,mouseDrag和mouseUp方法被重写,因此用户可以在屏幕上拖动一个点(NSRect)。要拖动它,我需要相对于当前视图的鼠标坐标。当视图的父窗口是窗口时,这不是问题,但当视图位于另一个视图内时,如何获取它们?

@implementation MyView 

- (id)initWithFrame:(NSRect)frame { 
    self = [super initWithFrame:frame]; 
    if (self) { 
     pointXPosition = 200.0f; 
     pointYPosition = 200.0f; 

     locked = NO; 
    } 
    return self; 
} 

- (void) drawRect:(NSRect)rect { 

    NSRect point = NSMakeRect(pointXPosition, pointYPosition, 6.0f, 6.0f); 
    [[NSColor redColor] set]; 
    NSRectFill(point); 

} 

- (void)mouseDown:(NSEvent *)theEvent { 
    NSPoint mousePos = [theEvent locationInWindow]; 
    NSRect frame = [super frame]; 
    CGFloat deltaX = mousePos.x - frame.origin.x - pointXPosition; 
    CGFloat deltaY = mousePos.y - frame.origin.y - pointYPosition; 
    if(sqrtf(deltaX * deltaX + deltaY * deltaY) < 100.0f) 
     locked = YES; 
} 

- (void)mouseUp:(NSEvent *)theEvent { 
    locked = NO; 
} 

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

    if(locked) { 
     NSPoint mousePos = [theEvent locationInWindow]; 

     NSRect frame = [super frame]; 

     CGFloat oldXPos = pointXPosition; 
     CGFloat oldYPos = pointYPosition; 

     pointXPosition = mousePos.x - frame.origin.x; 
     pointYPosition = mousePos.y - frame.origin.y; 

     CGFloat rectToDisplayXMin = MIN(oldXPos, pointXPosition); 
     CGFloat rectToDisplayYMin = MIN(oldYPos, pointYPosition); 

     CGFloat rectWidthToDisplay = MAX(oldXPos, pointXPosition) - rectToDisplayXMin; 
     CGFloat rectHeigthToDisplay = MAX(oldYPos, pointYPosition) - rectToDisplayYMin; 

     NSRect dirtyRect = NSMakeRect(rectToDisplayXMin, 
             rectToDisplayYMin, 
             rectWidthToDisplay + 6.0f, 
             rectHeigthToDisplay + 6.0f); 

     [self setNeedsDisplayInRect:dirtyRect]; 
    } 
} 

回答

23

您不需要手动转换到本地坐标系。您可以通过将convertPoint:fromView:消息发送到您的视图来将该点转换为本地坐标系。发送nil作为fromView的参数将从视图的父窗口(无论哪里)转换该点。您还可以发送任何其他视图以获得从该空间转换的坐标:

// convert from the window's coordinate system to the local coordinate system 
NSPoint clickPoint = [self convertPoint:[theEvent locationInWindow] fromView:nil]; 

// convert from some other view's cooridinate system 
NSPoint otherPoint = [self convertPoint:somePoint fromView:someSuperview]; 
相关问题