NSTextView выбрать конкретную строку - PullRequest
0 голосов
/ 17 января 2019

Я нахожусь на Xcode 10, Objective-C, macOS, а не на iOS.

Можно ли программно выбрать строку в NSTextView, если указан номер строки? Не изменяя какие-либо атрибуты содержимого, просто выберите его, как пользователь сделал бы это, трижды щелкнув.

Я знаю, как получить выделенный текст по диапазону, но на этот раз мне нужно выделить текст программно.

Я нашел selectLine:(id), но, похоже, это точка вставки. Указатель в правильном направлении был бы великолепен и очень ценен.

1 Ответ

0 голосов
/ 18 января 2019

Документация Apple здесь https://developer.apple.com/library/archive/documentation/Cocoa/Conceptual/TextLayout/Tasks/CountLines.html должна быть полезна для того, что вы пытаетесь сделать.

В своем примере подсчета строк обернутого текста они используют метод NSLayoutManager lineFragmentRectForGlyphAtIndex:effectiveRange https://developer.apple.com/documentation/appkit/nslayoutmanager/1403140-linefragmentrectforglyphatindex, чтобы найти эффективный диапазон строки, а затем увеличивают индекс подсчета до конца этого диапазона (т.е. начиная с следующая строка). С некоторыми незначительными изменениями вы можете использовать его, чтобы найти диапазон линии, которую вы хотите выделить, а затем использовать NSTextView setSelectedRange:, чтобы выбрать ее.

Вот это изменение, где я думаю, что это, вероятно, сработает для того, чего вы пытаетесь достичь:

- (void)selectLineNumber:(NSUInteger)lineNumberToSelect {
    NSLayoutManager *layoutManager = [self.testTextView layoutManager];
    NSUInteger numberOfLines = 0;
    NSUInteger numberOfGlyphs = [layoutManager numberOfGlyphs];
    NSRange lineRange;
    for (NSUInteger indexOfGlyph = 0; indexOfGlyph < numberOfGlyphs; numberOfLines++) {
        [layoutManager lineFragmentRectForGlyphAtIndex:indexOfGlyph effectiveRange:&lineRange];
        // check if we've found our line number
        if (numberOfLines == lineNumberToSelect) {
            [[NSOperationQueue mainQueue] addOperationWithBlock:^{
                [self.testTextView setSelectedRange:lineRange];
            }];
            break;
        }
        indexOfGlyph = NSMaxRange(lineRange);
    }
}

Тогда вы можете назвать это как-то так:

[self selectLineNumber:3];

Имейте в виду, что мы начинаем с индекса 0. Если вы передаете lineNumberToSelect, который больше, чем numberOfLines, он должен быть просто неактивным, и выбор должен оставаться там, где он есть.

...