Wie zeige ich Absatzzaehler zu einem Text einer UITextView an, welche das attributedText Property verwendet?

Diese Seite verwendet Cookies. Durch die Nutzung unserer Seite erklären Sie sich damit einverstanden, dass wir Cookies setzen. Weitere Informationen

  • Wie zeige ich Absatzzaehler zu einem Text einer UITextView an, welche das attributedText Property verwendet?

    Hallo auch,

    ich hab dazu auch schon eine Anfrage auf Stackoverflow laufen.

    Es geht um Folgendes:
    Ich habe eine UITextView, welche via attributedText Property den Content mit jeder Menge Styling-Informationen darstellt. Die Darstellung selbst funktioniert korrekt. Nun moechte ich seitlich neben dieser Textview (ich verwende dazu aktuell eine zweite UITextView) Absatznummern darstellen. Das soll wie im Link oben beschrieben aussehen.

    Alle Absaetze im Text sind durch U+2029 voneinander getrennt. Normale Linebreaks durch U+2028. Ich habe auch zu jedem Absatz die entsprechenden NSRange Informationen. Meine Idee ist nun, anhand dieser Informationen "irgendwie" die Anzahl der belegten Zeilen eines jeden Absatzes zu ermitteln, um auf der Gegenseite die Absatznummer an der richtigen Stelle zu platzieren. Aber hier scheitert es schon. Ich finde keinen Weg fuer jeden Absatz die Anzahl der Zeilen zu bekommen.

    Vielleicht bin ich mit diesem Loesungsansatz aber auch vollkommen auf dem falschen Pfad...?
    Wie wuerdet Ihr das loesen? Irgendwelche Ideen?

    Danke
    phranck
  • Mac & i Test Abo
  • Die Größe eines Attributed-Strings kannst Du über boundingRectWithSize:options:context: berechnen. Die Anzahl der Zeilen ist damit einfach die Höhe des Absatzes durch die Höhe einer Zeile.

    Ich würde aber für die Absatznumerierung nicht mit einem Textview sondern mit einer eigenen Viewklasse arbeiten, die die Startpositionen (Höhen) der Absätze in einem Array bekommt und an diesen Positionen die entsprechenden Ziffern zeichnet. Wenn Du dem View zusätzlich noch einen Offset mitgibst, kannst Du damit auch gut das Scrolling des Textviews abfrühstücken.
    „Meine Komplikation hatte eine Komplikation.“
  • Hast du boundingRectWithSize:options:context: selbst auch schon benutzt? Im Prinzip funktioniert das ueber diesen Weg. Aber aus "irgendeinem Grund passt das zurueckgelieferte Rect nicht ganz, es ist dann genau um eine Zeile zu "kurz". Ich poste mal meinen Code:

    Quellcode

    1. NSAttributedString *currentText = self.textView.attributedText;
    2. __block NSUInteger rangeLength = 0;
    3. __block CGSize lastSuggestedSize = CGSizeZero;
    4. CGFloat lineHeight = self.currentText.lineHeight;
    5. [self.currentText.paragraphRanges enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) {
    6. NSRange paragraphRange = [obj rangeValue];
    7. rangeLength += paragraphRange.length;
    8. NSAttributedString *attrString = [currentText attributedSubstringFromRange:NSMakeRange(0, rangeLength)];
    9. CGSize targetSize = CGSizeMake(self.currentTextViewSize.width, CGFLOAT_MAX);
    10. CGRect boundingRect = [attrString boundingRectWithSize:targetSize options:NSStringDrawingUsesLineFragmentOrigin | NSStringDrawingUsesFontLeading context:nil];
    11. CNLogForRect(boundingRect);
    12. CGSize suggestedSize = boundingRect.size;
    13. marker = [UILabel new];
    14. marker.font = [UIFont fontWithName:@"HelveticaNeue" size:12.0];
    15. marker.textAlignment = NSTextAlignmentRight;
    16. marker.textColor = [UIColor grayColor];
    17. marker.text = [NSString stringWithFormat:@"%i", idx+1];
    18. marker.backgroundColor = [UIColor clearColor];
    19. CGFloat yPos = 0;
    20. CGFloat yOffset = (lineHeight - marker.font.lineHeight) / 2 + 2;
    21. yPos = (idx == 0 ? yOffset : lastSuggestedSize.height + lineHeight + yOffset);
    22. marker.frame = CGRectMake(0, yPos, _markerViewWidth - 6, lineHeight);
    23. [self.markerView addSubview:marker];
    24. lastSuggestedSize = suggestedSize;
    25. }];
    Alles anzeigen
  • So ganz verstehe ich Deine Rechnungen ehrlich gesagt nicht. Zeichne doch mal die Höhen des Bounding-Rects neben die Absätze, in dem Du einen entsprechend hohen View mit farbigen Hintergrund hinzufügst; dann siehst Du wahrscheinlich, wo es hakt. Könnte es vielleicht an Leerzeilen zwischen den Abätzen liegen?

    BTW: Die Block-Variante für die Iteration macht wenig Sinn; warum verwendest Du nicht einfach eine Fast-Enumeration?
    „Meine Komplikation hatte eine Komplikation.“