синтаксический анализатор разметки, такой как форматировщик stackoverflow в Objective-C - PullRequest
3 голосов
/ 22 августа 2010

Я нахожусь в процессе создания редактора разметки в Objective C. Мне требуется следующая функциональность:

  • Распознать разграничение блока, например, **block**
  • Удалите начальный и конечный «теги», например «Следующий текст **bold**» становится «Следующий текст жирным шрифтом»
  • Определить начальную и конечную позиции размеченного текста в новом контексте: «Следующий текст выделен жирным шрифтом»

Edit: Поскольку я могу расширить синтаксис в будущем (в настоящий момент он будет очень ограничен), важно, чтобы синтаксический анализ выполнялся сверху вниз, чтобы начальная и конечная позиции текста всегда соответствовали результирующему тексту. По этой причине регулярное выражение может быть не лучшим решением.

Каков наилучший способ сделать это?

Ответы [ 2 ]

0 голосов
/ 23 августа 2010

MarkDown Sharp, процессор уценки, используемый на веб-сайтах StackExchange, имеет открытый исходный код . Взгляните на файл , возможно, вы сможете увидеть, как они это делают или перенести его на target-c.

Возможно, еще лучше, взгляните на этот вопрос: "Какая простейшая реализация Markdown для приложения Какао?"

Он ссылается на приложение с открытым исходным кодом под названием MarkdownLive , которое использует реализацию Markdown для C, называемую discount, а также предоставляет для нее оболочку target-c.

0 голосов
/ 23 августа 2010

В итоге мы остановились на подходе регулярных выражений с использованием RegexKitLite

Код ниже не полностью протестирован, но работает в случае, указанном St3fan.

- (NSArray *) scanContent:(NSMutableString **)content {
    NSMutableArray *tokens = [[NSMutableArray alloc] init];

    NSArray *captureRegex = [[NSArray alloc] initWithObjects:
                             @"\\[\\[(.*?)\\]\\]",@"\\*\\*(.*?)\\*\\*", nil];

    NSArray *tokenID = [[NSArray alloc] initWithObjects:
                        @"Italic",@"Bold", nil];

    int index = 0;

    for (NSString*capture in captureRegex) {

        NSRange captureRange;
        NSRange stringRange;
        stringRange.location = 0;
        stringRange.length = [*content length];

        do {
            captureRange = [*content rangeOfRegex:capture inRange:stringRange];
            if ( captureRange.location != NSNotFound ) {

                NSMutableDictionary *dictionary = [[NSMutableDictionary alloc] init];
                [dictionary setObject:[tokenID objectAtIndex:index] forKey:@"Token"];

                [dictionary setObject:[NSNumber numberWithInt:captureRange.location]
                               forKey:@"Start"];
                [dictionary setObject:[NSNumber numberWithInt:captureRange.length]
                               forKey:@"Length"];

                [tokens addObject:dictionary];

                for (NSMutableDictionary *dict in tokens) {
                    NSNumber *nRange = [dict objectForKey:@"Start"];
                    int start = [nRange intValue];

                    if (start > captureRange.location) {
                        nRange = [NSNumber numberWithInt:start - 4]; // Removing 4 characters 
                        [dict setObject:nRange forKey:@"Start"];
                    }

                    if (start == captureRange.location) {
                        NSString *data = [*content stringByMatching:capture options:RKLMultiline inRange:captureRange capture:1 error:NULL];                
                        NSLog(@"data: %@",data);
                        [*content replaceOccurrencesOfRegex:capture withString:data range:captureRange];
                        NSLog(@"Replaced Content: %@",*content);
                    }
                }

                stringRange.location = captureRange.location + captureRange.length -4;
                stringRange.length = [*content length] - stringRange.location;
            }
        }
        while ( captureRange.location != NSNotFound );

        index++;
    }
    return tokens;
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...