1

Ray Wenderlich のシンプルな雑誌のチュートリアルにあるパーサーを自分のプロジェクトに取り入れようとしました。彼のパーサー コードは次のとおり です。コア テキストを使用したシンプルな雑誌アプリの作成方法

メイン コントローラーはテキスト文字列をパーサーに渡します。パーサーはそれを分析し、属性を追加してから、viewDidLoad で次のコードを使用して、属性付きの文字列を返します。

 - (void)viewDidLoad
{
    [super viewDidLoad];

    NSString *path = [[NSBundle mainBundle] pathForResource:@"zombies" ofType:@"txt"];
    NSString* text = [NSString stringWithContentsOfFile:path encoding:NSUTF8StringEncoding error:NULL];
MarkupParser* p = [[[MarkupParser alloc] init] autorelease];
NSAttributedString* attString = [p attrStringFromMarkup: text];
[(CTView *)[self view] setAttString:attString withImages: p.images];
[(CTView *)[self view] buildFrames];
}

私はIos6を使用しているので、パーサーから返された属性付きの文字列は、CoreTextをいじる代わりに、UITextViewに簡単に追加できると考えています。これを念頭に置いて、上記のコードを次のように変更しました。

    - (void)viewDidLoad
{
    [super viewDidLoad];

    NSString *path = [[NSBundle mainBundle] pathForResource:@"zombies" ofType:@"txt"];
    NSString* text = [NSString stringWithContentsOfFile:path encoding:NSUTF8StringEncoding error:NULL];
    MarkupParser* p = [[[MarkupParser alloc] init] autorelease];
    NSAttributedString* attString = [p attrStringFromMarkup: text];

    UITextView *view = [[UITextView alloc] initWithFrame:CGRectMake(0, 0, self.view.bounds.size.width, self.view.bounds.size.height)];

    view.attributedText = attString;
    [self.view addSubview:view];
}

ただし、これにより、view.attributedText を attString に設定する行で「不明なセレクターがインスタンスに送信されました」というエラーが生成されます。パーサーから返された属性付きの文字列が原因であると確信していますが、その理由を一生理解することはできません! そこに何かアイデアはありますか?


実行時のコンソールのスクリーンショットを次に示します。

ここに画像の説明を入力

ここに画像の説明を入力


次の画像は、問題を引き起こしているattStringという名前のAttributedStringの詳細のスクリーンショットです

ここに画像の説明を入力

最後に、コードの次のセクションは、パーサーが属性を設定する場所であり、上記のデバッガーに示されている pointSize エラーを引き起こす可能性があります。

 CTFontRef fontRef = CTFontCreateWithName((CFStringRef)CFBridgingRetain(self.font),
                                             24.0f, NULL);

 //apply the current text style
 NSDictionary* attrs = [NSDictionary dictionaryWithObjectsAndKeys:
                       (id)self.color.CGColor, kCTForegroundColorAttributeName,
                       (id)CFBridgingRelease(fontRef), kCTFontAttributeName,
                       (id)self.strokeColor.CGColor, (NSString *) kCTStrokeColorAttributeName,
                       (id)[NSNumber numberWithFloat: self.strokeWidth], (NSString *)kCTStrokeWidthAttributeName,
                       nil];

 [aString appendAttributedString:[[NSAttributedString alloc] initWithString:[parts objectAtIndex:0] attributes:attrs] ];

上記の「ブリッジング」コマンドは Xcode によって自動的に追加されました。ARC と関係があることは知っていますが、実際には理解していないため、これらが問題を引き起こしているかどうかはわかりません。

4

2 に答える 2

2

3日後、ソートされました!!

私の解決策 (@Adam Eberbach がパーサーを教えてくれたことに感謝します!) は、Ray Wenderlich が使用するパーサー コードを大幅に見直したものです。基本的に問題は、私が彼の例から CoreText コーディングを持ち上げて、UITextView 属性付き文字列でそれらの属性を使用しようとしたことでした。そのため、UITextView は渡されたものを理解していませんでした。

彼のパーサーを CG 属性ではなく基本的な NS 属性に置き換えることで (その結果、彼のコードの大部分が変更されました!)、UITextView は渡されたものを理解することができました。私は彼が作成したのと同じ正規表現を保持することができました。これは神からの贈り物です。

元の投稿の最後のコード スニペットの代わりのコードは次のとおりです。

    for (NSTextCheckingResult* b in chunks) {
    NSArray* parts = [[markup substringWithRange:b.range]
                      componentsSeparatedByString:@"<"]; //1

    NSMutableAttributedString *temp = [[NSMutableAttributedString alloc] initWithString:[parts objectAtIndex:0]];
    [temp addAttribute:NSFontAttributeName value:[UIFont fontWithName:self.font size:20] range:NSMakeRange(0, [temp length])];
    [temp addAttribute:NSForegroundColorAttributeName value:self.color range:NSMakeRange(0, [temp length])];

    [aString appendAttributedString:temp];

これには、レイがオリジナルで持っていたストロークの色と幅の属性が含まれていないことに注意してください。これらは UITextView ではサポートされておらず、CoreText だけでサポートされているためです。ただし、別の正規表現と別の add:Attribute を単純に追加するだけで、他の属性を同じ方法で設定できるようになりました。

全体として、フォーマットを変更したいテキストにいくつかのタグを追加するだけで、長い .txt ファイルを属性付きテキストに変換する非常に簡単な方法が得られました。レイとアランに感謝!

于 2013-06-18T14:42:12.447 に答える
2

iOS6 より前の環境で実行している必要があるように思えます。iOS6 SDK を使用している場合でも、iOS5 シミュレーターで実行している可能性があります。あなたは間違いなく持っていますUITextView、それがiOS6だったらsetAttributedText:大丈夫でしょう。iOS6 より前にUITextViewはプロパティがなかったattributedTextため、設定しようとすると「不明なセレクターがインスタンスに送信されました」という結果になりました。

そうでない場合は、コンソールの出力を確認してください。おそらく、未知のセレクターが何であるかを示しています...

于 2013-06-17T23:26:25.970 に答える