Jak obliczyć szerokość UILabel na podstawie długości tekstu?

142

Chcę wyświetlić obraz obok UILabel, jednak UILabel ma zmienną długość tekstu, więc nie wiem, gdzie umieścić obraz. Jak mogę to osiągnąć?

Sheehan Alam
źródło

Odpowiedzi:

191
CGSize expectedLabelSize = [yourString sizeWithFont:yourLabel.font 
                        constrainedToSize:maximumLabelSize 
                        lineBreakMode:yourLabel.lineBreakMode]; 

Do czego służy - [NSString sizeWithFont: forWidth: lineBreakMode:]?

to pytanie może mieć twoją odpowiedź, zadziałało dla mnie.


W 2014 r. Redagowałem w tej nowej wersji, na podstawie bardzo przydatnego komentarza Norberta poniżej! To wszystko. Twoje zdrowie

// yourLabel is your UILabel.

float widthIs = 
 [self.yourLabel.text
  boundingRectWithSize:self.yourLabel.frame.size                                           
  options:NSStringDrawingUsesLineFragmentOrigin
  attributes:@{ NSFontAttributeName:self.yourLabel.font }
  context:nil]
   .size.width;

NSLog(@"the width of yourLabel is %f", widthIs);
Aaron Saunders
źródło
41
Tylko uwaga: to jest przestarzałe od iOS7. Preferowany sposób to teraz:[yourString boundingRectWithSize:maximumLabelSize options:NSStringDrawingUsesLineFragmentOrigin attributes:@{ NSFontAttributeName:yourLabel.font } context:nil];
Norbert
17
Możesz również użyć właściwości IntrinsicContentSize. Nie przepadam za Objective-c, ale powinno wyglądać mniej więcej tak: self.yourLabel.intrinsicContentSize To da ci rozmiar zawartości etykiety, więc możesz po prostu uzyskać stamtąd szerokość.
Boris
1
Po prostu yourLabel.intrinsicContentSize.widthdziała świetnie, sprawdź odpowiedź poniżej.
denis_lor
155

yourLabel.intrinsicContentSize.widthdla Objective-C / Swift

Jakub Truhlář
źródło
u mnie nie działa to nie oblicza wysokości etykiety na podstawie ich tekstu
Chandni
1
Działa idealnie dla mnie, również z niestandardową czcionką!
fl034
1
doskonała odpowiedź na uzyskanie szerokości dynamicznej etykiety
Chetan
52

Szybko

 yourLabel.intrinsicContentSize().width 
Arshad
źródło
3
Ta odpowiedź jest ważna tylko dla poglądu, który został przedstawiony
rommex
33

Wybrana odpowiedź jest prawidłowa dla iOS 6 i starszych.

W iOS 7 sizeWithFont:constrainedToSize:lineBreakMode:został wycofany . Teraz zaleca się użycie boundingRectWithSize:options:attributes:context:.

CGRect expectedLabelSize = [yourString boundingRectWithSize:sizeOfRect
                                                    options:<NSStringDrawingOptions>
                                                 attributes:@{
                                                    NSFontAttributeName: yourString.font
                                                    AnyOtherAttributes: valuesForAttributes
                                                 }
                                                    context:(NSStringDrawingContext *)];

Zwróć uwagę, że zwracana wartość to CGRectnie CGSize. Mamy nadzieję, że będzie to pomocne dla osób używających go w iOS 7.

Chetan Shenoy
źródło
12

W iOS8 sizeWithFont został wycofany, zapoznaj się z

CGSize yourLabelSize = [yourLabel.text sizeWithAttributes:@{NSFontAttributeName : [UIFont fontWithName:yourLabel.font size:yourLabel.fontSize]}];

Możesz dodać wszystkie atrybuty, które chcesz, w sizeWithAttributes. Inne atrybuty, które możesz ustawić:

- NSForegroundColorAttributeName
- NSParagraphStyleAttributeName
- NSBackgroundColorAttributeName
- NSShadowAttributeName

i tak dalej. Ale prawdopodobnie nie będziesz potrzebować innych

jarora
źródło
10

Swift 4 Odpowiedz, kto używa ograniczenia

label.text = "Hello World"

var rect: CGRect = label.frame //get frame of label
rect.size = (label.text?.size(attributes: [NSFontAttributeName: UIFont(name: label.font.fontName , size: label.font.pointSize)!]))! //Calculate as per label font
labelWidth.constant = rect.width // set width to Constraint outlet

Swift 5 Odpowiedz, kto używa ograniczenia

label.text = "Hello World"

var rect: CGRect = label.frame //get frame of label
rect.size = (label.text?.size(withAttributes: [NSAttributedString.Key.font: UIFont(name: label.font.fontName , size: label.font.pointSize)!]))! //Calculate as per label font
labelWidth.constant = rect.width // set width to Constraint outlet
iOS Lifee
źródło
1
Wspaniały! Wygodne do obliczania szerokości UIButton na podstawie tekstu, gdzie intrinsicContentSize.width nie zawsze działa poprawnie.
nomnom
8
CGRect rect = label.frame;
rect.size = [label.text sizeWithAttributes:@{NSFontAttributeName : [UIFont fontWithName:label.font.fontName size:label.font.pointSize]}];
label.frame = rect;
Honey Lakhani
źródło
2
To nie daje odpowiedzi na pytanie. Aby skrytykować lub poprosić autora o wyjaśnienie, zostaw komentarz pod jego postem - zawsze możesz komentować własne posty, a gdy zdobędziesz wystarczającą reputację , będziesz mógł komentować każdy post .
The Humble Rat
ta odpowiedź mówi, jak dostosować rozmiar etykiety do tekstu. jaki jest w tym problem?
Honey Lakhani
2

Oto coś, co wymyśliłem po zastosowaniu kilku zasad do innych postów SO, w tym link Aarona:

    AnnotationPin *myAnnotation = (AnnotationPin *)annotation;

    self = [super initWithAnnotation:myAnnotation reuseIdentifier:reuseIdentifier];
    self.backgroundColor = [UIColor greenColor];
    self.frame = CGRectMake(0,0,30,30);
    imageView = [[UIImageView alloc] initWithImage:myAnnotation.THEIMAGE];
    imageView.frame = CGRectMake(3,3,20,20);
    imageView.layer.masksToBounds = NO;
    [self addSubview:imageView];
    [imageView release];

    CGSize titleSize = [myAnnotation.THETEXT sizeWithFont:[UIFont systemFontOfSize:12]];
    CGRect newFrame = self.frame;
    newFrame.size.height = titleSize.height + 12;
    newFrame.size.width = titleSize.width + 32;
    self.frame = newFrame;
    self.layer.borderColor = [UIColor colorWithRed:0 green:.3 blue:0 alpha:1.0f].CGColor;
    self.layer.borderWidth = 3.0;

    UILabel *infoLabel = [[UILabel alloc] initWithFrame:CGRectMake(26,5,newFrame.size.width-32,newFrame.size.height-12)];
    infoLabel.text = myAnnotation.title;
    infoLabel.backgroundColor = [UIColor clearColor];
    infoLabel.textColor = [UIColor blackColor];
    infoLabel.textAlignment = UITextAlignmentCenter;
    infoLabel.font = [UIFont systemFontOfSize:12];

    [self addSubview:infoLabel];
    [infoLabel release];

W tym przykładzie dodaję niestandardową pinezkę do klasy MKAnnotation, która zmienia rozmiar UILabel zgodnie z rozmiarem tekstu. Dodaje również obraz po lewej stronie widoku, dzięki czemu część kodu zarządza odpowiednimi odstępami w celu obsługi obrazu i dopełnienia.

Kluczem jest użycie, CGSize titleSize = [myAnnotation.THETEXT sizeWithFont:[UIFont systemFontOfSize:12]];a następnie ponowne zdefiniowanie wymiarów widoku. Możesz zastosować tę logikę do dowolnego widoku.

Chociaż odpowiedź Aarona działa dla niektórych, nie zadziałała dla mnie. Jest to znacznie bardziej szczegółowe wyjaśnienie, które powinieneś wypróbować bezpośrednio przed przejściem w inne miejsce, jeśli chcesz mieć bardziej dynamiczny widok z obrazem i zmiennym UILabel. Wykonałem już dla ciebie całą pracę !!

Whyoz
źródło