Reputation: 3749
Whenever I tap "newButton" my app crashes. I am using automatic reference counting.
Edit: Just tried this in a different app and it works but does not work in my own.
Here is my code:
- (void)viewDidLoad
{
[super viewDidLoad];
UIView *fullView = [[UIView alloc] initWithFrame:CGRectMake(0, -20, 320, 480)];
fullView.backgroundColor = [UIColor blackColor];
[[self view] addSubview:fullView];
UIImage* blackButton =[[UIImage imageNamed:@"UIButtonBlack.png"]stretchableImageWithLeftCapWidth:10.0 topCapHeight:0.0];
// Create button
UIButton *newButton = [[UIButton alloc] initWithFrame:CGRectMake(100, 100, 100, 30)];
// Set button content alignment
newButton.contentVerticalAlignment = UIControlContentVerticalAlignmentCenter;
newButton.contentHorizontalAlignment = UIControlContentHorizontalAlignmentCenter;
// Set button title
[newButton setTitle:@"Do Something" forState:UIControlStateNormal & UIControlStateHighlighted & UIControlStateSelected];
// Set button title color
[newButton setTitleColor:[UIColor colorWithRed:255.0f/255.0 green:255.0f/255.0 blue:255.0f/255.0 alpha:1.0] forState:UIControlStateNormal & UIControlStateHighlighted & UIControlStateSelected];
// Add the background image
[newButton setBackgroundImage:blackButton forState:UIControlStateNormal];
// Add Events
[newButton addTarget:self action:@selector(showScanner:) forControlEvents:UIControlEventTouchUpInside];
// in case the parent view draws with a custom color or gradient, use a transparent color
[newButton setBackgroundColor:[UIColor clearColor]];
// Set titleShadowColor this way (apparently, titleLabel.shadowcolor does not work)
[newButton setTitleShadowColor:[UIColor colorWithRed:0.0f/255.0 green:0.0f/255.0 blue:0.0f/255.0 alpha:.75] forState:UIControlStateNormal & UIControlStateHighlighted & UIControlStateSelected];
// Set button titleLabel properties
newButton.titleLabel.font = [UIFont fontWithName:@"PTSans-Bold" size:13.0];
newButton.titleLabel.shadowOffset = CGSizeMake(1, 1);
[fullView addSubview:newButton];
}
- (void)showScanner:(id)sender
{
NSLog(@"Do something…");
}
Upvotes: 1
Views: 531
Reputation: 16458
You're not keeping a reference to your view controller. You either need to
Note that if you were to re-write this code with ARC turned off, you'd have a memory leak, instead of a crash.
The problem is that all references to the view controller from the view are weak references, meaning that they don't retain the controller*. So in your loading code ARC releases the view controller after you've made it and accessed its view, and it's gone.
Within your app you should keep track of all the view controllers, and access their views through them. Something like UINavigationController does this for you.
*This is because the view controller is considered to have ownership over the view, and if the view controller retained the view and the view retained the view controller, there'd be a retain loop, and neither of them would ever be released.
Upvotes: 0
Reputation: 52788
I believe UIControlState
's cannot be &
(or |
) together because according to the UIControl
Reference Docs:
a control can have more than one state at a time.
Try separating them out like this:
// Set button title
[newButton setTitle:@"Do Something" forState:UIControlStateNormal];
[newButton setTitle:@"Do Something" forState:UIControlStateHighlighted];
[newButton setTitle:@"Do Something" forState:UIControlStateSelected];
// Set button title color
[newButton setTitleColor:[UIColor colorWithRed:255.0f/255.0 green:255.0f/255.0 blue:255.0f/255.0 alpha:1.0] forState:UIControlStateNormal];
[newButton setTitleColor:[UIColor colorWithRed:255.0f/255.0 green:255.0f/255.0 blue:255.0f/255.0 alpha:1.0] forState:UIControlStateHighlighted];
[newButton setTitleColor:[UIColor colorWithRed:255.0f/255.0 green:255.0f/255.0 blue:255.0f/255.0 alpha:1.0] forState:UIControlStateSelected];
// Add the background image
[newButton setBackgroundImage:blackButton forState:UIControlStateNormal];
// Add Events
[newButton addTarget:self action:@selector(showScanner:) forControlEvents:UIControlEventTouchUpInside];
// in case the parent view draws with a custom color or gradient, use a transparent color
[newButton setBackgroundColor:[UIColor clearColor]];
// Set titleShadowColor this way (apparently, titleLabel.shadowcolor does not work)
[newButton setTitleShadowColor:[UIColor colorWithRed:0.0f/255.0 green:0.0f/255.0 blue:0.0f/255.0 alpha:.75] forState:UIControlStateNormal];
[newButton setTitleShadowColor:[UIColor colorWithRed:0.0f/255.0 green:0.0f/255.0 blue:0.0f/255.0 alpha:.75] forState:UIControlStateHighlighted];
[newButton setTitleShadowColor:[UIColor colorWithRed:0.0f/255.0 green:0.0f/255.0 blue:0.0f/255.0 alpha:.75] forState:UIControlStateSelected];
// Set button titleLabel properties
newButton.titleLabel.font = [UIFont fontWithName:@"PTSans-Bold" size:13.0];
newButton.titleLabel.shadowOffset = CGSizeMake(1, 1);
It may be crashing because button
should be newButton
.
Change this:
[button setTitleShadowColor:[UIColor colorWithRed:0.0f/255.0 green:0.0f/255.0 blue:0.0f/255.0 alpha:.75] forState:UIControlStateNormal & UIControlStateHighlighted & UIControlStateSelected];
To this:
[newButton setTitleShadowColor:[UIColor colorWithRed:0.0f/255.0 green:0.0f/255.0 blue:0.0f/255.0 alpha:.75] forState:UIControlStateNormal & UIControlStateHighlighted & UIControlStateSelected];
Upvotes: 3