timpone
timpone

Reputation: 19969

showing a UITextField that is a local variable vs a property in a custom view

I am mocking up a quick demo of a project but am having a problem with a UITextField.

The behavior that we want is that when a user clicks on a button, there should be a custom view that appears with a UITextField and a UIButton in a custom view that overlays the main view.

I have a custom view called Searchview and the following in the Searchview.m. The problem is that when the textField is a property, it doesn't show but when it is a local variable, it does show. Can anybody help me with what is going on so that the UITextField shows? Is how I am doing this even the right idea (custom UIView or custom UIControl or a modal controller)? Finally, would setNeedsDisplay be appropriate here?

thx in advance

@interface Searchview()
  @property (nonatomic, weak) UITextField *textField;
@end


- (void)drawRect:(CGRect)rect
{
  // this doesn't work
  self.textField = [[UITextField alloc] initWithFrame:CGRectMake(0.0f, 0.0f, 120.0f, 25.0f)];
  self.textField.returnKeyType = UIReturnKeyDone;
  self.textField.placeholder = @"Writer";
  self.textField.borderStyle=UITextBorderStyleBezel;
  [self.textField addTarget:self
                    action:@selector(textFieldDone:) 
          forControlEvents:UIControlEventEditingDidEndOnExit];     
  [self addSubview: self.textField];

/* this works
  UITextField *textField = [[UITextField alloc] initWithFrame:CGRectMake(10.0f, 10.0f, 120, 25)];
  textField.returnKeyType = UIReturnKeyDone;
  textField.placeholder = @"Writer";
  textField.borderStyle=UITextBorderStyleBezel;
  [textField addTarget:self
                    action:@selector(textFieldDone:) 
          forControlEvents:UIControlEventEditingDidEndOnExit];    

  [self addSubview: textField];
*/

  UIButton *mButton=[UIButton buttonWithType:UIButtonTypeRoundedRect];
  mButton.frame=CGRectMake(200.0f,10.0f,100.0f,37.0f);
  [mButton setTitle:@"search" forState:UIControlStateNormal];
  [mButton addTarget:self action:@selector(showSearchController:) forControlEvents:UIControlEventTouchUpInside];
  [self addSubview:mButton];
  [self setNeedsDisplay];

}

As a property - not showing: as a property:

As a local variable - showing: local variable

Upvotes: 0

Views: 128

Answers (2)

tc.
tc.

Reputation: 33592

It's pretty simple when you think about it. ARC (approximately) converts the following code:

self.weakProp = [[Foo alloc] init];

to the equivalent of the following "manually reference-counted" code:

Foo * temp = [[Foo alloc] init];
self.weakProp = temp;
[temp release];

Nothing is retaining it, so it is released.

I can only think of two reasons to have assign/weak IBOutlets:

  • For an outlet in a VC, so it doesn't retain a subview when its view is set to nil (e.g. on a memory warning). This is less relevant in iOS 6.0 since views are not automatically released on a memory warning (so if you do it, you can release them all explicitly).
  • For a view where the outlet points to a superview (and would cause a retain cycle). This is quite rare.

In general, I prefer strong IBOutlets: They might keep objects alive for a little longer than necessary, but they are safer than assign and more efficient than weak. Just watch out for retain cycles!

Upvotes: 0

Guo Luchuan
Guo Luchuan

Reputation: 4731

@property (nonatomic, strong) UITextField *textField;

change the weak to strong and change the self.textFiled to _textField to have a try

And make sure your textField property not be released

Upvotes: 1

Related Questions