NSTableView Cell中的几个超链接

时间:2013-10-05 12:45:19

标签: macos cocoa hyperlink nstableview nstextfieldcell

目前我有一个带有自定义NSTextFieldCell的NSTableView,它包含NSAttributedString,其中包含NSLinkAttribute的某些范围。我试图整合来自Apple的TableViewLinks example和Toomas Vather HyperlinkTextField的代码。

我实现了像这样的-trackMouse函数:

- (BOOL)trackMouse:(NSEvent *)theEvent inRect:(NSRect)cellFrame ofView:(NSView *)controlView untilMouseUp:(BOOL)flag {

BOOL result = YES;
NSUInteger hitTestResult = [self hitTestForEvent:theEvent inRect:cellFrame ofView:controlView];
if ((hitTestResult & NSCellHitContentArea) != 0) {
    result = [super trackMouse:theEvent inRect:cellFrame ofView:controlView untilMouseUp:flag];
    theEvent = [NSApp currentEvent];
    hitTestResult = [self hitTestForEvent:theEvent inRect:cellFrame ofView:controlView];
    if ((hitTestResult & NSCellHitContentArea) != 0) {
        NSAttributedString* attrValue = [self.objectValues objectForKey:@"theAttributedString"];
        NSMutableAttributedString* attributedStringWithLinks = [[NSMutableAttributedString alloc] initWithAttributedString:attrValue];

        //HOW TO GET A RIGHT INDEX?
        NSTableView* myTableView = (NSTableView *)[self controlView];
        NSPoint eventPoint = [myTableView convertPoint:[theEvent locationInWindow] fromView:nil];
        NSInteger myRow = [myTableView rowAtPoint:eventPoint];
        NSRect myBetterViewRect = [myTableView rectOfRow:myRow];


        __block NSTextView* myTextView = [[NSTextView alloc] initWithFrame:myBetterViewRect];
        [myTextView.textStorage setAttributedString:attributedStringWithLinks];

        NSPoint localPoint = [myTextView convertPoint:eventPoint fromView:myTableView];
        NSUInteger index = [myTextView.layoutManager characterIndexForPoint:localPoint inTextContainer:myTextView.textContainer fractionOfDistanceBetweenInsertionPoints:NULL];

        if (index != NSNotFound)
        {
            NSMutableArray* myHyperlinkInfos = [[NSMutableArray alloc] init];
            NSRange stringRange = NSMakeRange(0, [attrValue length]);
            [attrValue enumerateAttribute:NSLinkAttributeName inRange:stringRange options:0 usingBlock:^(id value, NSRange range, BOOL* stop)
             {
                 if (value)
                 {
                     NSUInteger rectCount = 0;
                     NSRectArray rectArray = [myTextView.layoutManager rectArrayForCharacterRange:range withinSelectedCharacterRange:range inTextContainer:myTextView.textContainer rectCount:&rectCount];
                     for (NSUInteger i = 0; i < rectCount; i++)
                     {
                         [myHyperlinkInfos addObject:@{kHyperlinkInfoCharacterRangeKey : [NSValue valueWithRange:range], kHyperlinkInfoURLKey : value, kHyperlinkInfoRectKey : [NSValue valueWithRect:rectArray[i]]}];
                     }
                 }
             }];

            for (NSDictionary* info in myHyperlinkInfos)
            {
                NSRange range = [[info objectForKey:kHyperlinkInfoCharacterRangeKey] rangeValue];
                if (NSLocationInRange(index, range))
                {
                    NSURL* url = [NSURL URLWithString:[info objectForKey:kHyperlinkInfoURLKey]];
                    [[NSWorkspace sharedWorkspace] openURL:url];
                }
            }
        }
    }
}
return result;}

单击单元格(nstextview)文本时的字符索引似乎不合适。因此,即使文本中有多个链接,通常也会打开最后一个链接。我的猜测是我没有得到点击单元格的修正。如果是这样,我怎么能得到正确的NSRect?

我很高兴任何建议,评论,代码片段或更简单的解决方案(即使这包括切换到基于视图的tableview)。

感谢。

0 个答案:

没有答案