Become a MacRumors Supporter for $50/year with no ads, ability to filter front page stories, and private forums.

Blakeasd

macrumors 6502a
Original poster
Dec 29, 2009
643
0
Hello,
I have been following along with this tutorial
and I need some help porting some code to OS X.
1. Is viewDidLoad: the equivalent to awakeFromNib: ?
2. How did the author create those shapes and how can I do this in OS X?

I am only having a problem with the viewDidLoad: stuff.
Thanks!
 
viewDidLoad: is part of UIViewController while awakeFromNib can be called on any object created from a nib. However viewDidLoad: can also be called if the view was created programatically. So awakeFromNib can probably be used in most cases on OS X.
 
How did the author create those shapes and how can I do this in OS X?

They're UIViews with the background color set to different values.

The Mac OS X equivalent (NSView) doesn't have a background color.

NSTextField does have a background colour. So you could drag Wrapping Labels onto your window instead and just delete the text in the title.
 
So for the viewdidLoad: iOS method I create a NSViewController and call
-(void)awakeFromNib: and in that awakeFromNib: method I can use the same iOS code that is in the viewDidLoad? Do I create a different NSView subclass for each of the colored squares and in their awakeFromNib: method I call addPhysicalBodyForView: ?
 
I know about the background color, but how exactly do I handle the views I create? I have no idea how to convert this code:
Code:
- (void)viewDidLoad
{
	[super viewDidLoad];
 
	[self createPhysicsWorld];
 
	for (UIView *oneView in self.view.subviews)
	{
		[self addPhysicalBodyForView:oneView];
	}
 
	tickTimer = [NSTimer scheduledTimerWithTimeInterval:1.0/60.0 target:self selector:@selector(tick:) userInfo:nil repeats:YES];
}
 
So for the viewdidLoad: iOS method I create a NSViewController and call
-(void)awakeFromNib: and in that awakeFromNib: method I can use the same iOS code that is in the viewDidLoad? Do I create a different NSView subclass for each of the colored squares and in their awakeFromNib: method I call addPhysicalBodyForView: ?

Just create them in Interface Builder. Porting iOS viewdidLoad: to awakeFromNib: is probably good enough for this tutorial. No need to create view controllers. This is a simple tutorial. Just do it in the app delegate.


I know about the background color, but how exactly do I handle the views I create? I have no idea how to convert this code:
Code:
- (void)viewDidLoad
{
	[super viewDidLoad];
 
	[self createPhysicsWorld];
 
	for (UIView *oneView in self.view.subviews)
	{
		[self addPhysicalBodyForView:oneView];
	}
 
	tickTimer = [NSTimer scheduledTimerWithTimeInterval:1.0/60.0 target:self selector:@selector(tick:) userInfo:nil repeats:YES];
}

Start by changing UIView to NSView.
 
Last edited:
Thanks, I think I got it working. Here is my new code:
Code:
-(void)awakeFromNib{


    [self createPhysicsWorld];
    NSView *contentView;
    contentView = [window contentView];
    for (NSView * oneView in [contentView subviews]){
    
    
        [self addPhysicalBodyForView:oneView];
    
    }
        
 
    
    
    
    }
I have one more question, I get an error with this line of code:
Code:
physicalView.tag = (int)body;
The author said that this line would "abuse so the tag property", so what does this line of code do and what can I use in place of it? This line compiles in iOS, but not in Mac OS X. I get the error, " Cast from pointer to small type 'int' loses information "
Thanks!
 
Code:
physicalView.tag = (int)body;

Firstly the author was ignorant in type-casting a pointer to an int. Type-cast it to an NSInteger.

Secondly, while NSView has tag, it doesn't have setTag:. NSControl though does have setTag:. All of NSTextField, NSBox and NSColorWell inherit from NSControl, so you should be okay. But you'll need to change addPhysicalBodyForView: to accept an NSControl* instead of an NSView*. You'll then need to guard the call to addPhysicalBodyForView: in awakeFromNib: so it only happens with subviews that are kinds of NSControl.
 
Okay, Thanks!
I did everything but this:
You'll then need to guard the call to addPhysicalBodyForView: in awakeFromNib: so it only happens with subviews that are kinds of NSControl.
I am not exactly sure what guarding a call is.
 
I'm still not quite sure what you mean.
Thanks

Code:
    for (NSView * oneView in [contentView subviews]){
    
        [COLOR=blue]if ([oneView isKindOf:@class(NSControl)]) {[/COLOR]
    
            [self addPhysicalBodyForView:[COLOR=blue](NSControl*)[/COLOR]oneView];

        [COLOR=blue]}[/COLOR]
    
    }
 
The code you provided didn't compile and gave the following error:
"Unexpected @ in program"
I changed the code to this:
Code:
   if ([oneView isKindOfClass:[NSControl class]]) {
            
            [self addPhysicalBodyForView:(NSControl*)oneView];
            
        }
Is the code I created correct?
 
The code you provided didn't compile and gave the following error:
"Unexpected @ in program"
I changed the code to this:
Code:
   if ([oneView isKindOfClass:[NSControl class]]) {
            
            [self addPhysicalBodyForView:(NSControl*)oneView];
            
        }
Is the code I created correct?

Sorry for getting the @class construct wrong. I am actually away from my beloved Mac. The code you posted looks correct.
 
Thanks for all your help! I can't wait to do some cool physics stuff.
:D
 
I actually do have another question,
I will be applying a CGAffineTransform to a view (same tutorial) and the author is using an iOS only property
Code:
CGAffineTransform transform = CGAffineTransformMakeRotation(- b->GetAngle());
oneView.transform = transform
. What is an equivalent way to do this in OS X?
 
Last edited:
I actually do have another question,
I will be applying a CGAffineTransform to a view (same tutorial) and the author is using an iOS only property
Code:
CGAffineTransform transform = CGAffineTransformMakeRotation(- b->GetAngle());
oneView.transform = transform
. What is an equivalent way to do this in OS X?

Look it up in the documentation: NSView Programming Guide.
 
I actually didn't find a method or property that is the equivalent to the iOS property.
 
I actually didn't find a method or property that is the equivalent to the iOS property.

To the best of my knowledge there isn't one. The guide you were directed to has a lot of detail on how to achieve a similar thing in OSX (hint it's not as simple as setting a property).
 
I can't find anything there about CGAffineTransforms on NSViews. :confused:

That's because there isn't such a thing. As it says you are better performing the rotation yourself on the co-ordinate system in drawRect:. If it's not a custom view you can use the obvious methods to set either bounds or frame rotations.
 
Here is my new code:
Code:
			CGAffineTransform transform = CGAffineTransformMakeRotation(- b->GetAngle());
            
            oneView.wantsLayer = YES;
            [oneView.layer setAffineTransform:transform];
Can anyone confirm the code I wrote works?
I tried to compile my project and I get no errors, but all the shapes don't fall to the bottom of the window like they should. Could someone PLEASE take a look at my project and find out why it isn't working?
Here is the link to my project: Project Link
 
Register on MacRumors! This sidebar will go away, and you'll see fewer ads.