Metin özelliği ayarlandıktan sonra UITextView stili sıfırlanıyor


146

Ben var UITextView *_masterTextve çağrı yöntemi setTextözelliği yazı tipi sonra sıfırlanıyor. Sdk 7'yi değiştirdikten sonra oluyor. _MasterText IBOutlet, global ve özellikler storyboard'da ayarlandı. Sadece ben mi yoksa bu genel SDK hatası mı?

@interface myViewController : UIViewController
{
  IBOutlet UITextView *_masterText;
}

@implementation myViewController

-(void)viewWillAppear:(BOOL)animated
{
    [_masterText setText:@"New text"];
}

Yanıtlar:


450

Saatlerce bununla oturup böceği buldum. "Seçilebilir" özelliği = HAYIR ise, setText kullanıldığında yazı tipi ve yazı tipi rengini sıfırlar.

Öyleyse Seçilebilir'i AÇIN ve hata ortadan kalkar.



8
Vay canına, ne saçma bir böcek. Görüş için teşekkürler!
Micah

3
Çok çok teşekkür ederim !
Magurizio

6
6.4'te hala bu sorun var
RndmTsk

4
Bu, iOS 10'da düzeltilmiş gibi görünüyor, eğer hala iOS 9 veya altını hedefliyorsanız, geçici çözümü yapmanız gerekecektir.
user1184205

11

Aynı sorunla karşılaştım (Xcode 6.1'de) ve John Cogan'ın cevabı benim için işe yararken, UITextView sınıfını bir kategori ile genişletmenin özel projem için daha iyi bir çözüm olduğunu gördüm.

arayüz

@interface UITextView (XcodeSetTextFormattingBugWorkaround)
    - (void)setSafeText:(NSString *)textValue;
@end

uygulama

@implementation UITextView (XcodeSetTextFormattingBugWorkaround)
- (void)setSafeText:(NSString *)textValue
{
    BOOL selectable = [self isSelectable];
    [self setSelectable:YES];
    [self setText:textValue];
    [self setSelectable:selectable];
}
@end

1
Ve hızlı bir şekilde:extension UITextView { func setSafeText(text: String){ let originalSelectable = selectable selectable = true self.text = text selectable = originalSelectable } }
küçük

8

Metin görünümünüzün "salt okunur" olmasını istiyorsanız, Düzenlenebilir ve Seçilebilir'i işaretleyebilir ve Kullanıcı Etkileşimi Etkin'in işaretini kaldırabilirsiniz, bununla UITextView istediğim gibi davranıyordu

görüntü açıklamasını buraya girin

görüntü açıklamasını buraya girin


3
Bu, yüzeyde uygulanabilir bir çözüm gibi görünüyor, ancak sonuçta bir UITextView için iyi bir seçenek değil. Normalde bir UITextView seçersiniz çünkü kaydırılabilir bir metin alanına ihtiyacınız vardır. Kullanıcı Etkileşimini devre dışı bırakmak, kaydırma görünümünü de devre dışı bırakır. Benim için bir UITextView kullanma seçimi, o alana sığabilecek olandan daha fazla metin tutmam ve kaydırabilmem gereken bir alana sahip olmamdı.
jhelzer

6

Bu sorunu kendim yaptım ve yukarıdaki cevap yardımcı oldu, ancak ViewController koduma aşağıdaki gibi bir sarmalayıcı ekledim ve sadece uiview örneğini ve metni değiştirdim ve sarmalayıcı işlevi Seçilebilir değeri açar, metni değiştirir ve ardından tekrar kapatır. Uitextview'un varsayılan olarak her zaman kapalı olması gerektiğinde kullanışlıdır.

/*
    We set the text views Selectable value to YES temporarily, change text and turn it off again.
    This is a known bug that if the selectable value = NO the view loses its formatting.
 */
-(void)changeTextOfUiTextViewAndKeepFormatting:(UITextView*)viewToUpdate withText:(NSString*)textValue
{
    if(![viewToUpdate isSelectable]){
        [viewToUpdate setSelectable:YES];
        [viewToUpdate setText:textValue];
        [viewToUpdate setSelectable:NO];
    }else{
        [viewToUpdate setText:textValue];
        [viewToUpdate setSelectable:NO];
    }
}

1
UITextView'ı alt sınıflara
ayırmak

2

DÜZENLE :

İOS 7'de UITextView için yazı tipini ayarlamak, önce metni ayarlarsanız ve ardından yazı tipini ayarlarsanız benim için çalışır:

@property (nonatomic, weak) IBOutlet UITextView *masterText;

@implementation myViewController

-(void)viewWillAppear:(BOOL)animated
{
    [super viewWillAppear:animated];

    _myTextView.text = @"My Text";

    _myTextView.font = [UIFont fontWithName:@"Helvetica.ttf" size:16]; // Set Font

}

Bir XIB dosyasında, UITextView'unuza bir metin eklerseniz ve yazı tipini veya rengini değiştirirseniz işe yarayacaktır.


hmm .. Mülk kullanıyorum ama değişiklik yok.
Błażej

unuttum [super viewWillAppear: animated];
Jordan Montel

Bunu unuttum, ancak bu etkilemedi :(
Błażej

XCode'unuzu temizleyin ve yeniden başlatın çünkü "_myTextView.font ..." satırı olmadan yazı tipini XIB dosyasından değiştirsem bile
Jordan Montel

Temizleyin, yeniden başlatın ve etkisi yok. Proje> iOS Dağıtım Hedefi 7.0, Temel SDK 7.0'da aynı ayarları hedefleyin.
Błażej

2

İşte bu problem için sıklıkla kullandığım hızlı bir alt sınıf çözümü.

class WorkaroundTextView: UITextView {
    override var text: String! {
        get {
            return super.text
        }
        set {
            let originalSelectableValue = self.selectable
            self.selectable = true
            super.text = newValue
            self.selectable = originalSelectableValue
        }
    }
}

2

Bu sorun Xcode 8'de yeniden ortaya çıktı. Bunu şu şekilde düzelttim:

Uzantı şu şekilde değiştirildi:

extension UITextView{
    func setTextAvoidXcodeIssue(newText : String, selectable: Bool){
        isSelectable = true
        text = newText
        isSelectable = selectable
    }
}

ve Arayüz Oluşturucu'daki Seçilebilir seçeneğini işaretlediniz.

Bu 'seçilebilir' parametreye sahip olmak çok zarif değil ama işe yarayacak.


1

İOS 8.3'te, "seçilebilir" i setText'ten önce EVET'e ve sonra HAYIR'a ayarlamanın geçici çözümü benim için düzeltmedi.

Bu işe yaramadan önce film şeridinde de "seçilebilir" seçeneğini EVET olarak ayarlamam gerektiğini fark ettim.


Günümü kurtardınız, bunun CocoaTouch'daki bir başka saçma hata olduğuna inanıyorum
Chris

1

Bu benim için çalıştı:

let font = textView.font
textView.attributedText = attributedString
textView.font  = font

0

Nitelikli metinle benim için, yazı tipini kendi alanında ayarlamak yerine özellikler sözlüğünde ayarlamam gerekiyordu.


0

Bu sorunu yaşıyorum. @Ken Steele'in cevabının hızlı dostu bir çözümü. UITextView'ı genişletiyorum ve hesaplanmış bir özellik ekliyorum.

extension UITextView {
    // For older Swift version output should be NSString!
    public var safeText:String!
        {
        set {
            let selectable = self.selectable;
            self.selectable = true;
            self.text = newValue;
            self.selectable = selectable;
        }
        get {
            return self.text;
        }
    }
}

Umarım yardımcı olur.


0

3 yıl oldu ve hata Xcode'un (7.3) en son kararlı sürümünde hala var. Açıkçası apple, geliştiricilere iki seçenek bırakarak yakında bunu düzeltmeyecek: seçilebilir bırakmak ve UserInteractionEnabled'ı false veya Method swizzling olarak ayarlamak.

TextView'unuzda bir düğme varsa, eski yeterli olmayacaktır.

Hızlı bir şekilde kod değişikliği gerektirmeyen çözüm:

import UIKit

extension UITextView {
    @nonobjc var text: String! {
        get {
            return performSelector(Selector("text")).takeUnretainedValue() as? String ?? ""
        } set {
            let originalSelectableValue = selectable
            selectable = true
            performSelector(Selector("setText:"), withObject: newValue)
            selectable = originalSelectableValue
        }
    }
}

Amaç-C:

#import <objc/runtime.h>
#import <UIKit/UIKit.h>

@implementation UITextView (SetTextFix)

+ (void)load {
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        Class class = [self class];

        SEL originalSelector = @selector(setText:);
        SEL swizzledSelector = @selector(xxx_setText:);

        Method originalMethod = class_getInstanceMethod(class, originalSelector);
        Method swizzledMethod = class_getInstanceMethod(class, swizzledSelector);

        BOOL didAddMethod =
        class_addMethod(class,
                    originalSelector,
                    method_getImplementation(swizzledMethod),
                    method_getTypeEncoding(swizzledMethod));

        if (didAddMethod) {
            class_replaceMethod(class,
                            swizzledSelector,
                            method_getImplementation(originalMethod),
                            method_getTypeEncoding(originalMethod));
        } else {
            method_exchangeImplementations(originalMethod, swizzledMethod);
       }
   });
}

- (void)xxx_setText:(NSString *)text {
    BOOL originalSelectableValue = self.selectable;
    self.selectable = YES;
    [self xxx_setText:text];
    self.selectable = originalSelectableValue;
}

@end

0

Bu sayıda tartışılan geçici çözümü kullanarak, UITextView'e yapılan bu uzantı bir setTextInCurrentStyle()işlev sağlar. Alessandro Ranaldi'nin çözümüne dayalıdır ancak mevcut isSelectable değerinin işleve aktarılmasını gerektirmez.

extension UITextView{
    func setTextInCurrentStyle(_ newText: String) {
        let selectablePreviously = self.isSelectable
        isSelectable = true
        text = newText
        isSelectable = selectablePreviously
    }
}
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.