Reputation: 1832
I was wondering how to pass objects as parameters in objective C. As you can see, in my code, Obj1 * myObj1 is out of scope for the btnIncrementObj1 method. How do I put it in scope? I'm thinking that there is a way to make instances of a class as static.
As you can see, I only want myObj1 to be instantiated on a button press, not when a view is loaded.
Is there a way to make Obj1 static, or give it a global scope?
- (IBAction)btnCreateObj1:(UIButton *)sender
{
Obj1 * myObj1 = [[Obj1 alloc] init];
int intVal = [self.textField.text intValue];
[myObj1 increment:intVal];
[myObj1 restring:@"orig string 1"];
NSString * newLabel = [self.labelObject1.text stringByAppendingFormat:@"value:%d string:%@",myObj1.value,myObj1.someString];
self.labelObject1.text = newLabel;
}
- (IBAction)btnIncrementObj1:(UIButton *)sender
{
//-I want to increment myObj1.value by [self.textField.text intValue]
}
Upvotes: 1
Views: 825
Reputation: 2864
Your .h file should import the object you want to keep and create a member of the object in that class. It would look something like this.
#import "Obj1.h";
@interface MyViewController : UIViewController{
Obj1 * myObj1;
}
I wouldn't init a class variable in a IBAction method, but you can do it. In the button that creates you can keep the same code. But in your other method, just check if the myObj1 is created.
- (IBAction)btnIncrementObj1:(UIButton *)sender
{
if(myObj1){
//Handle the increment.
}else{
//Handle what to do if you haven't clicked the other button before this one.
}
}
And for good memory managment you should release the object in dealloc
-(void) dealloc{
if(myObj1){
[myObj1 release];
}
[super dealloc];
}
Upvotes: 0
Reputation: 86651
OK, here's my answer. This expands on the one given by Lanc.
Firstly, you need to decide what the scope of myObj1 should be. Do you want one per instance of the class or only one for the whole application. If it's per instance of the class, make an instance variable and have a property that creates it on demand. e.g.
@interface MyViewController : UIViewController
@property (nonatomic, readonly, retain) Obj1* myObj1;
// other stuff
@end
@implementation MyViewController
{
@private
Obj1* myObj1;
}
-(Obj1*) myObj1
{
@synchronized(self) // if you know you are single threaded you can omit the @synchronized block
{
if (myObj1 == nil)
{
myObj1 = [[Obj1 alloc] init];
}
}
return myObj1;
}
- (IBAction)btnCreateObj1:(UIButton *)sender
{
[[self myObj1] increment:intVal];
[[self myObj1] restring:@"orig string 1"];
NSString * newLabel = [self.labelObject1.text stringByAppendingFormat:@"value:%d string:%@",myObj1.value,myObj1.someString];
self.labelObject1.text = newLabel;
}
- (IBAction)btnIncrementObj1:(UIButton *)sender
{
[[self myObj1] increment: [self.textField.text intValue]];
}
If you need a singleton (i.e. only one object per program), you can use a static variable as per wizH's answer but I prefer using a method to access it. So the following will work:
@interface MyViewController : UIViewController
@property (nonatomic, readonly, retain) Obj1* myObj1;
// other stuff
@end
@implementation MyViewController
-(Obj1*) myObj1
{
static Obj1* myObj1 = nil; // instance var moved to be a static variable
@synchronized([MyViewController class) // if you know you are single threaded you can omit the @synchronized block
{
if (myObj1 == nil)
{
myObj1 = [[Obj1 alloc] init];
}
}
return myObj1;
}
- (IBAction)btnCreateObj1:(UIButton *)sender
{
[[self myObj1] increment:intVal];
[[self myObj1] restring:@"orig string 1"];
NSString * newLabel = [self.labelObject1.text stringByAppendingFormat:@"value:%d string:%@",myObj1.value,myObj1.someString];
self.labelObject1.text = newLabel;
}
- (IBAction)btnIncrementObj1:(UIButton *)sender
{
[[self myObj1] increment: [self.textField.text intValue]];
}
Notice how the only thing that has changed is the way the API for the class is satisfied. No code that uses the API has to change.
Upvotes: 1
Reputation: 488
You should create your object right after the
@implementation
Here you can create it as a static object:
static Obj1* _myObj1 = nil;
From here on you can access it from other classes like this:
[Obj1 myObj1].property
Upvotes: 0
Reputation: 17478
If you want to access a variable throughout the class, then make it as a class member.
Upvotes: 1