即使我在主线程中更新它,UIButton标题文本也不会更新

时间:2013-11-14 09:07:38

标签: ios objective-c uibutton ios7 xcode5

我正在尝试更改我在用户点击时以编程方式创建的UIButton的标题。所以,这是我创建UIButton

的代码
myButton = [[UIButton alloc] initWithFrame:CGRectMake(0, 0, parentView.frame.size.width, parentView.frame.size.height)];
[myButton setBackgroundColor:[UIColor blackColor]];
[myButton setAlpha:0.7];
[myButton setTitle:@"Hello" forState:UIControlStateNormal];
[myButton addTarget:self action:@selector(userClicked:) forControlEvents:UIControlEventTouchUpInside];

[parentView addSubview:myButton];

而且,在我的userClicked:方法中,我这样做:

-(void) userClicked:(UIButton*)button
{
    NSLog(@"USER CLICKED!!!");
    if ([NSThread isMainThread])
    {
        NSLog(@"is main thread");
    }

    [button setTitle:@"Bye" forState:UIControlStateHighlighted];
    [button setTitle:@"Bye" forState:UIControlStateNormal];
    [button setTitle:@"Bye" forState:UIControlStateSelected];

    [self someLengthyComputation];
}

奇怪的是我可以看到打印的日志消息:

USER CLICKED!!! 
isMainThread

但是,按钮的标题不会改变!我做错了什么?

编辑:设置几种状态的标题也不起作用。

EDIT2:如果我在Xcode的调试器窗口中打印按钮的描述,它会显示正确的标题!

Printing description of button->_titleView:
<UIButtonLabel: 0xa4c9310; frame = (95 216; 130 22); text = 'Bye'; clipsToBounds = YES; opaque = NO; userInteractionEnabled = NO; layer = <CALayer: 0xa44f080>>

24 个答案:

答案 0 :(得分:47)

这对我来说更新标题文本(iOS 7.1,Xcode 5.1):

button.enabled = FALSE;
[button setTitle:@"Test" forState:UIControlStateNormal];
button.enabled = TRUE;

答案 1 :(得分:24)

我遇到了同样的问题,我发现在其他任何地方我都在设置attributesTitle。因此,对标题的任何更新都不会影响属性标题。

我的解决方案:

[button setAttributedTitle:@"" forState:UIControlStateNormal];

而不是

[button setTitle:@"" forState:UIControlStateNormal];

答案 2 :(得分:20)

目前,我参加的最短工作是打电话:

[button setNeedsLayout];

更新标题后。

这似乎发生在iOS 7.1中。 在Xcode 5.1.1 SDK 7.1中编译时,所有在以前的iOS版本中正常运行的按钮(或者可能只是使用以前的SDK编译)突然停止了这样做。

看起来像Apple的错误。

答案 3 :(得分:10)

我在使用故事板时遇到了类似的问题。使用上面的答案,我不得不使用

[mybutton setTitle:@"SomeText" forState:UIControlStateNormal];
[button setNeedsLayout];
[button layoutIfNeeded];

我必须确保按钮类型是&#39; Custom&#39;不是&#39;系统&#39;在属性检查器中。

答案 4 :(得分:7)

请查看这可能对您有所帮助......单击按钮时检查条件是否为buttonToggled ...如下所示,当您有像changeButtonText这样的函数时

-(IBAction)changeButtonText:(id)sender {
    if (!buttonToggled) {
        [sender setTitle:@"Initial Text" forState:UIControlStateNormal];
        buttonToggled = YES;
    } else {
        [sender setTitle:@"Alternative Text" forState:UIControlStateNormal];
        buttonToggled = NO;
    }
}

答案 5 :(得分:6)

您的代码中存在以下几个问题:

您正在为按钮指定回调:

@selector(userClicked:)

但你的代码是另一种方法:

-(void)userTapOnTapToRefreshView:(UIButton*)button

要解决此问题,您需要实现以下内容:

-(void)userClicked:(id)sender
{
    [(UIButton*)sender setTitle:@"Bye" forState:UIControlStateNormal];
}

此部分代码对我来说也没有意义:

[parentView myButton];

尝试将其更改为:

[parentView addSubview:myButton];

希望它会有所帮助:)

答案 6 :(得分:5)

在iOS 7中,UIButton的标题在禁用时不会更新。这似乎是iOS 7上的一个错误。

作为解决方法,更新正常和禁用标题。它有效!

[button setTitle:title forState:UIControlStateNormal];
[button setTitle:title forState:UIControlStateDisabled];

答案 7 :(得分:4)

这有点晚了,有点与Walter Schurter的回应有关:

我有一个类似的问题,我的按钮文本设置正确,直到我更新到7.1。然后我发现由于我的按钮被禁用,我必须设置禁用状态的标题颜色和标题文本以显示文本。然后一切都像魅力一样!

答案 8 :(得分:4)

在我的情况下,我尝试了一切,但没有任何工作。 然后我只是从故事板中将按钮类型从系统更改为自定义。繁荣!一切都开始正常。

答案 9 :(得分:3)

将按钮类型更改为“自定义”,而不是“系统”,它将按预期工作:)

答案 10 :(得分:3)

试试这个:

[button setTitle:@"Bye" forState:UIControlStateHighlighted];

或:

[button setTitle:@"Bye" forState:UIControlStateSelected];

你也可以修改你的虚函数:

-(void) userClicked
{
    NSLog(@"USER CLICKED!!!");
    if ([NSThread isMainThread])
    {
        NSLog(@"is main thread");
    }

    [myButton setTitle:@"Bye" forState:UIControlStateNormal];
}

答案 11 :(得分:2)

可能是按钮布局刷新问题..... 尝试使用...

[button setNeedsLayout];
[button layoutIfNeeded];

它会强制按钮更新布局。

答案 12 :(得分:2)

对于 Swift 3 ,只需使用以下内容:

button.setTitle("My title", for: .normal)

或属性文字

button.setAttributedTitle(<AttributedString>, for: .normal)

答案 13 :(得分:2)

这可能是微不足道的,但如果你设置了一个填充整个按钮框的按钮图像(而不是背景图像),这将使标题向右移动,从而使其不可见。 如果是这样,请尝试将按钮图像更改为背景图像。

答案 14 :(得分:2)

好吧,关于UIButton的启用状态,Apple已经改变了7.1中的某些内容,如果UIButton处于禁用状态,则不允许您更改标题,这就是全部。

感谢Apple,我已经失去了10分钟。调试一个工作正常的应用程序。

今天早上刚刚发现,昨天更新了XCode到5.1.1和iOS到7.1

答案 15 :(得分:1)

根据Apple开发者指南,您不应将按钮标题标签文本或颜色直接设置为属性(例如,执行此操作:myButton.titleLabel.text =@" ; SomeText&#34;或myButton.titleLabel.textColor = [UIColor blackColor])。

相反,您可以使用UIButton setter功能设置它们,如下所示:

    [myButton setTitleColor:[UIColor blackColor] forState:UIControlStateNormal];

......或者像这样:

    [myButton setTitle:@"SomeText" forState:UIControlStateNormal];.

请参阅the Apple guide

答案 16 :(得分:1)

无需使用:

[button setNeedsLayout];
[button layoutIfNeeded];

相反,首先将类型设置为DEFAULT为 CUSTOM

如果您申请setAttributedTitle,请使用:

[button setAttributedTitle:[NSAttributedString new] forState:UIControlStateNormal];

否则无需改变任何东西。

如果文本的颜色没有改变,那么应用相同的东西并设置标题颜色:

[button setTitleColor:[any_color] forState:UIControlStateNormal];

答案 17 :(得分:1)

尝试多种解决方案后的结论是使用setAttributedTitle而不是setTitle。

为AttributedString制作标题字符串:

NSMutableAttributedString *attString = [[NSMutableAttributedString alloc] initWithString:@" new Test "];

[button setAttributedTitle:attString forState:UIControlStateNormal];

顺便说一下,这个问题偶尔不会发生在正常情况下但突然发生的主要原因如下:

  1. 如果您更改UIButton的启用状态并尝试更改标题。

  2. 如果您使用属性值,然后想要使用setTitle更改它,那么在这种情况下,属性值优于标题。

  3. 如果您导航到另一个视图控制器,然后返回以更新按钮标题。

答案 18 :(得分:1)

最后,我已经弄明白了。有两个问题:

1)button未处于州UIControlStateNormal

2)在设置标题[self someLengthyComputation]之后,我正在调用一个执行长计算的方法。

我通过以下方式解决了问题:

1)为按钮的所有状态设置标题。

2)在另一个线程中执行大计算,而不是主线程。

我现在的工作代码是:

-(void) userClicked:(UIButton*)button
{
    NSLog(@"USER CLICKED!!!");
    if ([NSThread isMainThread])
    {
        NSLog(@"is main thread");
    }

    [button setTitle:@"Bye" forState:UIControlStateHighlighted];
    [button setTitle:@"Bye" forState:UIControlStateNormal];
    [button setTitle:@"Bye" forState:UIControlStateSelected];
    dispatch_async(dispatch_get_global_queue( DISPATCH_QUEUE_PRIORITY_LOW, 0), ^{
        [self someLengthyComputation];
    });
}

非常感谢所有回复/评论过的人!

答案 19 :(得分:0)

尝试在视图/视图控制器的界面或实现部分中将按钮声明为属性

@property(nonatomic,strong) UIButton* myButton;

然后创建它

self.myButton = [[UIButton alloc] initWithFrame:CGRectMake(0, 0, parentView.frame.size.width, parentView.frame.size.height)];
[_myButton setBackgroundColor:[UIColor blackColor]];
...

它应该工作。不要问我为什么真的 - 我只是认为它是关于ARC /现代内存管理的。

修改

如果您在实现中保留对按钮的引用,它也应该有效。

@implementation myViewController
{
    UIButton* myButton;
}

-(void)createButton
{
    myButton = [[UIButton alloc] initWithFrame:CGRectMake(0, 0, parentView.frame.size.width, parentView.frame.size.height)];
    [myButton setBackgroundColor:[UIColor blackColor]];
    ...
}

...

答案 20 :(得分:0)

我怀疑'button'是否作为参数传入myButton.Anyway,如果myButton是一个成员var,你可以只[myButton setTitle:@“Bye”forState:UIControlStateNormal];

答案 21 :(得分:0)

以上都没有为我的情况工作(我在UIPopoverController上显示的视图上有一个按钮),我不得不在setTitle之前删除SuperSuperview,然后再回到addSubview - 希望这可以帮助有类似问题的人

答案 22 :(得分:0)

代替 yourButton.titleLabel?.text =“ T”

使用此 yourButton.setTitle(“ TITLE”,代表:.normal)

答案 23 :(得分:-2)

在UIButton上设置文本之前,请务必执行addSubview。