Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

UIGestureRecognizer causing "EXC_BAD_ACCESS" error

Using the GestureRecognizer attached to a view triggers my app to crash with EXC_BAD_ACCESS error. Here's the classes involved

BoardViewController - Displaying a board (as background) set as rootViewController in the AppDelegate. It instantiates multiple objects of the "TaskViewcontroller".

//BoardViewController.h
@interface BoardViewController : UIViewController {
    NSMutableArray* allTaskViews; //for storing taskViews to avoid having them autoreleased
}

 

//BoardViewController.m - Rootviewcontroller, instantiating TaskViews    
- (void)viewDidLoad
{
    [super viewDidLoad];
    TaskViewController* taskA = [[TaskViewController alloc]init];
    [allTaskViews addObject:taskA];
    [[self view]addSubview:[taskA view]];
}

TaskViewController - An indivual box displayed on the board. It should be draggable. Therefore I attached UIPanGestureRecoginzer to its view

- (void)viewDidLoad
{
    [super viewDidLoad];

    UIPanGestureRecognizer* panRecognizer = [[UIPanGestureRecognizer alloc]initWithTarget:self action:@selector(handlePan:)];
    [[self view] addGestureRecognizer:panRecognizer];
}

- (void)handlePan:(UIPanGestureRecognizer *)recognizer {
    NSLog(@"PAN!");
}

The .xib file is a simple view.

enter image description here

All programming with the gesture recognizer I'd prefer to do in code. Any idea how to fix the error causing the app crash?

like image 551
Bernd Avatar asked Feb 20 '23 13:02

Bernd


1 Answers

The method handlePan is on your view controller, not on your view. You should set the target to self:

UIPanGestureRecognizer* panRecognizer = [[UIPanGestureRecognizer alloc]initWithTarget:self action:@selector(handlePan:)];

EDIT (in response to the edit of the question) As omz has correctly noted, your TaskViewController gets released upon BoardViewController's viewDidLoad: exit. There are two ways of dealing with it:

  • Fold the handlePan method into the parent view controller, along with the code of viewDidLoad:, or
  • Make an instance variable for TaskViewController *taskA, rather than making it a local variable.
like image 168
Sergey Kalinichenko Avatar answered Mar 02 '23 16:03

Sergey Kalinichenko