Passen Sie die Schriftgröße von UIButton an die Breite an


121

Ich habe folgenden Code:

UIButton *button = [UIButton buttonWithType:UIButtonTypeCustom];
button.frame = CGRectMake(0.0, 0.0, 25, 25);

[[button layer] setCornerRadius:5.0f];
[[button layer] setMasksToBounds:YES];
[[button layer] setBackgroundColor:[[UIColor redColor] CGColor]];
[button.titleLabel setFrame:CGRectMake(0,0, 25, 25)];

[button setTitle:[NSString stringWithFormat:@"%@", [[topics objectAtIndex:indexPath.row] unread]] forState:UIControlStateNormal];

Das Problem ist, dass wenn die Zeichenfolge im Text nicht lang ist, sie gut angezeigt wird (1-2 Ziffern). Wenn es jedoch ziemlich lang ist (3 ++ Ziffer), sehe ich nur einen roten Knopf ohne Text. Wie stelle ich das ein?

Das glaube ich nicht:

[button.titleLabel setAdjustsFontSizeToFitWidth:YES];

macht den Job, richtig?


Es sollte funktionieren, oder theLabel.adjustsFontSizeToFitWidth = YES.
Luke

Es funktioniert vontitleButton.setContentCompressionResistancePriority(.defaultLow, for: .horizontal)
onmyway133

Antworten:


290

Versuche dies:

button.titleLabel.numberOfLines = 1;
button.titleLabel.adjustsFontSizeToFitWidth = YES;
button.titleLabel.lineBreakMode = NSLineBreakByClipping; //<-- MAGIC LINE

Ich bin nicht sicher, warum dies den Trick macht, aber es tut :)


1
danke, während button.titleLabel.lineBreakMode = UILineBreakModeClip; <- MAGIC LINE wird jetzt abgeschrieben
yunas

8
@yunas Ersetzen Sie UILineBreakModeClip durch NSLineBreakByClipping
CodeReaper

1
Nvm, das hat es gerade numberOfLinesauf 0 geändert
Marty

33
button.titleLabel.adjustsFontSizeToFitWidth = YES;

sollte die Arbeit selbst erledigen, wenn Sie das automatische Layout verwenden und eine Einschränkung für die Breite der Schaltfläche festgelegt haben.

Die anderen Optionen (minimaler Skalierungsfaktor, Anzahl der Zeilen usw.) können weiterhin verwendet werden, um weitere Anpassungen an Ihre Anforderungen vorzunehmen, sind jedoch nicht erforderlich.


15

Die Antwort von EliBud funktioniert unter iOS 8 nicht. Ich habe eine Lösung gefunden, die unter iOS 8 funktioniert. Nachfolgend finden Sie einen schnellen Code:

let label = self.button?.titleLabel
label?.minimumScaleFactor = 0.01
label?.adjustsFontSizeToFitWidth = true
label?.font = UIFont.systemFontOfSize(100)

Sie können mit dem Label? .LineBreakMode spielen, da ich festgestellt habe, dass die Ergebnisse für verschiedene Unterbrechungsmodi variieren.


.adjustsFontSizeToFitWidth = true - Wie kann ich dasselbe mit einem NSTextField und einem Fenster mit veränderbarer Größe tun?
Leo Dabus

Das sieht für mich genauso aus, als würde man Xcode IB verwenden, um ein Etikett auszuwählen und es auf Autoshrink-Mindestschriftgröße auf 0,01
einzustellen

Es gibt keine AutoShrink-Option bei Verwendung von NSTextField
Leo Dabus

UITextField bietet eine Option zum automatischen Verkleinern von Text, NSTextField hingegen nicht. Ich denke, Sie müssen die Schriftart manuell an die Breite des Textfelds anpassen.
Alexander Belyavskiy

10

In letzter Zeit scheint dies für mich zu funktionieren

button.titleLabel!.numberOfLines = 1
button.titleLabel!.adjustsFontSizeToFitWidth = true
button.titleLabel!.lineBreakMode = NSLineBreakMode.ByClipping

10

iOS 10.3-Lösung basierend auf den anderen Antworten hier:

    button.titleLabel!.numberOfLines = 1
    button.titleLabel!.adjustsFontSizeToFitWidth = true
    button.titleLabel!.baselineAdjustment = .alignCenters

baselineAdjustmentNoch niemand erwähnt ; Ich brauchte es, weil die Tastenbeschriftung nach dem adjustsFontSizeToFitWidthWirksamwerden vertikal falsch ausgerichtet wird. Apples baselineAdjustmentDokumentation:

Wenn die adjustsFontSizeToFitWidthEigenschaft auf festgelegt ist true, steuert diese Eigenschaft das Verhalten der Textbasislinien in Situationen, in denen eine Anpassung der Schriftgröße erforderlich ist. Der Standardwert dieser Eigenschaft ist alignBaselines. Diese Eigenschaft ist nur wirksam, wenn die numberOfLinesEigenschaft auf festgelegt ist 1.


FWIW, ich konnte das Etikett nie perfekt ausrichten.


8

adjustsFontSizeToFitWidth funktionierte nicht für mich, bis ich in Interface Builder eine Breitenbeschränkung für meine Schaltfläche festgelegt habe.

Durch das Festlegen der Einschränkung wurde verhindert, dass die Schaltfläche größer wurde, und daher wurde nicht erkannt, dass der Text verkleinert werden musste.


8

Swift 4 Erweiterung

extension UIButton {
    @IBInspectable var adjustFontSizeToWidth: Bool {
        get {
            return self.titleLabel?.adjustsFontSizeToFitWidth
        }
        set {
            self.titleLabel?.numberOfLines = 1
            self.titleLabel?.adjustsFontSizeToFitWidth = newValue;
            self.titleLabel?.lineBreakMode = .byClipping;
            self.titleLabel?.baselineAdjustment = .alignCenters 
        }
    }
}

Geben Sie hier die Bildbeschreibung ein


Wofür benutzt du das Tag?
Zaporozhchenko Oleksandr

Für verfügbar sein, um den Getter zu machen
Nik Kov

Können Sie bitte genauer beschreiben, was Sie meinen?
Zaporozhchenko Oleksandr

Ich benutze ein Tag wie ein Flag, um zu definieren, ob die Anpassung aktiviert ist.
Nik Kov

Warum verwendest du nicht einfach self.titleLabel? .adjustsFontSizeToFitWidth? Wofür brauchst du etwas extra?
Zaporozhchenko Oleksandr

3

Xamarin.iOS-Lösung

var accountButton = new UIButton();
accountButton.SetTitle("Account", UIControlState.Normal);            
accountButton.TitleLabel.AdjustsFontSizeToFitWidth = true;
accountButton.TitleLabel.Lines = 1;
accountButton.TitleLabel.LineBreakMode = UILineBreakMode.Clip;
accountButton.TitleLabel.Font = accountButton.TitleLabel.Font.WithSize(35);

Am Ende habe ich die Schriftgröße festgelegt, um sicherzustellen, dass die Schrift "groß" ist, bevor das System die Größe anpasst.


3

basierend auf Nik Kovs Antwort:

import UIKit


    extension UIButton {
        @IBInspectable var adjustFontSizeToWidth: Bool {
            get {
                return titleLabel!.adjustsFontSizeToFitWidth
            }
            set {
                titleLabel!.adjustsFontSizeToFitWidth = newValue
                titleLabel!.lineBreakMode             = .byClipping
            }
        }
    }

Dies funktioniert, aber die Schriftgröße wird stark verringert, z. B. von 17 auf 12. Gibt es eine Möglichkeit, die Breite des Titeletiketts zu erhöhen, wenn die Zeichenfolge größer ist?
R. Mohan

@ R.Mohan sicher, aber das alles über feste Breite. Machen Sie einfach nicht festgelegte Einschränkungen, und es wird wachsen. Setzen Sie nicht beide führenden / nachlaufenden oder machen Sie eine von ihnen> =
Zaporozhchenko Oleksandr

0

Die folgende Lösung hat bei mir funktioniert:

button.titleLabel?.adjustsFontForContentSizeCategory = true

In der Entwicklerdokumentation wird diese Eigenschaft wie folgt erläutert:

Ein boolescher Wert, der angibt, ob das Objekt seine Schriftart automatisch aktualisiert, wenn sich die Inhaltsgrößenkategorie des Geräts ändert.


0

In iOS 13.1 mit Swift 5 musste ich contentEdgeInsetsauch die Polster anpassen.

extension UIButton {
    @IBInspectable var adjustFontSizeToWidth: Bool {
        get {
            return self.titleLabel?.adjustsFontSizeToFitWidth ?? false
        }
        set {
            self.titleLabel?.numberOfLines = 1
            self.titleLabel?.adjustsFontSizeToFitWidth = newValue;
            self.titleLabel?.lineBreakMode = .byClipping;
            self.titleLabel?.baselineAdjustment = .alignCenters
            self.contentEdgeInsets = UIEdgeInsets(top: 10, left: 10, bottom: 10, right: 10)
        }
    }
}
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.