NSCoder Availability - objective-c

trying to use the initwithcoder init method in my custom NSControl Class.
It works just fine and does what I need it to do. However and this leads me to asking this question on this here forum -> in the class reference of NCControl when you scroll down to initWithCoder and click on it it states SDKs
macOS 10.10+ which leads me to believe that it would not work and do what I need it to do on versions prior to that... Unless Apple's documentation once again is wrong...
BTW - from Apple's own reference (Online as well as offline) apparently the NSCoder Class is also suffering from this SDKs macOS 10.10+
https://developer.apple.com/reference/foundation/nscoder
The strange thing is that in the documentation describing how a NIB is loaded and which init methods it calls on various objects, it describes initWithCoder as being the designated initializer but that documentation is from before 10.10.
Thanks to anyone who can set my mind at ease ;-)

Yes it will not work before defined version. I think you are checking versions of Swift, if you select objective-c you should see version 10.0+ which i think should work fine for your need. If you change the language, you can put your mind to ease :)
I am assuming if you would like to support things that far back you are going to use objective-c over swift.
Check the below image for NSCoder documentation after you select objective-c on right hand side.

Related

Playgrounds for Objective-C

Is it at all possible to have Xcode create a .playground file for Objective-C instead of Swift? Are there any available Xcode plugins that allow that?
You can quickly test code snippets using a test case in a new project. Just create a new project and go to the Navigator in the left pane and hit the Test Navigator button. Then follow this guide
The setup code will look a little different than a swift playground, but it still allows you to prototype and play around.
There is a very good library developed by Krzysztof Zabłocki in Github entitled KZPlayground that support both code in Playgrounds for Objective-C and Swift and a lot of cool features.
I hope this can help you.
If the only purpose is to test out Objective-C snippets, i would really recommend you an OS X command line Tool project.
There are enough moving parts in a playground, and all of those would have to be reimplemented for Objective-C. Reliable playgrounds also depend on definite initialization which Objective-C does not have.
For instance consider:
var d: NSData // this is not initialized, so I can't use it
vs.
NSData *d; // this is also not initialized, but now I can use it
If I am the person storing the description of your NSData for the sidebar, now I know that I am not supposed to do
describe(d)
in the Swift case, but for the Objective-C case, I don't have equal knowledge and I run the risk of saying
[d description]; // even though d is a random pointer now.. oops, I just crashed!
In short, I don't think any such thing exists, and making one work would also involve some trickery

Is it OK to implement a protocol that's unavailable in my deployed OS version?

Say I'm writing an app to run on iOS7 and iOS6. I've a class that implements a protocol - a protocol only available in iOS7 (in this case, NSLayoutManagerDelegate).
Everything seems to work on iOS6 - my code that instantiates the class implementing the protocol is skipped on iOS6 - so it appears I'm good to go.
I was a little surprised not to see an error during app load though; apparently the loader is OK with me implementing a protocol that doesn't exist. Luckily for me!
Is there any Apple documentation that discusses this scenario? Is it safe? Any gotchas I should watch for?
No problem with that, a bit like implementing a method that is only called by the system for some version upwards.
At worst you can say that you have generated some code that takes up space somewhere (the "disk" if you can call it that on iOS and probably also the RAM) without being used on the older version(s), but that is minimal.
This all requires that the code is compiled with an SDK that includes the protocol in question - if conformance to the protocol is declared by using the <ProtocolName> construct and including the corresponding header. But that is kind of a given, since it won't compile otherwise.

Understanding how predefined methods work

I am a novice in Objective-C and I am trying to understand how pre-defined methods work. I went through the documentation of XCode and the *.h files where the method is defined. However I am eager to read the *.m file or any other document that can help me understand how the method works.
For instance - isEqualToString:(NSString *) checks if two strings (of the type NSString) are equal or not. I am not satisfied with this description. I am eager to see how the method works internally or what is the algorithm it follows. Where can I find this information?
Thank you for your help.
isEqualToString:(NSString *) is a method defined in the NSString class. Apple provides you with the framework, but they do not provide the implementation of those methods. Therefore, you can't see the source behind the standard framework's libraries.
Edit: you can create a binary and use this app to check the assembly code: http://itunes.apple.com/us/app/hopper-disassembler/id422856039?mt=12
Unfortunately, a lot of the implementation (.m) files for Apple's frameworks aren't provided publicly. You have a couple alternatives:
As Matthias suggested in a comment, use the debugger and inspect the assembler code generated for that method.
Browse through the repositories for the GNUstep project, which has some equivalents to Apple classes.

Override a method in a single object instance

Am not sure how to put this, and I couldn't find the answer because of my inability to find the words to express what am looking for. (!)
In Java, I used to do something like this (I don't remember):
JPanel myButton = new JPanel("Press me"){
public void add(JComponent component){
//override add method
}
};
But, i couldn't find how to do this in Objective-C .. What I found in my search was categories and weird ^{} symbols ...
So, how can I override method(s) in a newly created object?
(For example, override -(BOOL)isEqual; in a newly created NSString* ?)
Am sorry if the question is a bit vague..
EDIT:
Obviously, without subclassing :)
EDIT:
Might as well post my problem in case someone has a better idea:
I have a few CCTransitions in COCOS2D, and I want to be notified when the transition ends .. The thing is, as soon as the transition ends, the -(void)finish; method is invoked (which is part of the CCTransition class structure)
I would really want to avoid subclassing the CCTransition class, and override the finish method to do my logic when the transition ends :)
EDIT:
-(void)onEnterTransitionDidFinish; ... I can't believe something as awesome as that existed and I haven't came across it while searching......
Which means, instead of subclassing CCTransition, override this method in my CCNode subclass :D!
It's still not going to be very clean, but assuming you're willing to concentrate the ugliness, you could do something like (untested):
Method methodToReplace =
[targetClass instanceMethodSignatureForSelector:#selector(methodToReplace)];
IMP implementationToSet =
[someProxyClass instanceMethodForSelector:#selector(implementationYouWant)];
method_setImplementation(methodToReplace, implementationToSet);
Relevant reference documentation is the Objective-C Runtime Reference and, optionally, the NSObject Class Reference (because it makes a few things slightly neater, though e.g. you could use class_getInstanceMethod from the runtime rather than instanceMethodSigntureForSelector:).
Note that you'll have no way to call the original implementation if you use exactly that recipe. method_setImplementation returns the old implementation, it's generally wise to add that to the class under a brand new selector and call that instead.
For reference, I've had a legitimate reason to do this sort of thing only exactly once: when we implemented printing support in an iOS application with which needed to be compatible with both OS 3.2 and 4.0. You need to subclass a particular class, but the class isn't available in 3.2. So you sort of have to subclass at runtime (though the conceptually neater way would be to use a normal subclass, put that into a framework and weak link, but Apple's iOS SDK terms allow static libraries only, so...).
Following Daniel's suggestion, you can implement a method in an NSObject category of the form
[anObject overrideMethod:#selector(foo:)
byBlock:^(id self,id super,id originalArg){
...
}];
What you need to do is to
objc_allocateClassPair against self's own class, to create a new temporary class
Turn a block into a function pointer, using e.g. this or this
method_setImplementation to set the new implementation to the temporary class
use object_setClass to self to set the class to the new temporary class
I haven't figured out how to provide super to the block :p
It's believed this is basically how the KVO is done by Apple, see e.g. this discussion.
Read Runtime reference.
What you have there in Java is an anonymous subclass. This is not possible in Objective-C (well, it sort of is but you would have to do some pretty involved contortions with the Obj-C runtime library).
But Objective-C as of iOS 4 or OS X 10.6 has "blocks", which is what the ^{} syntax is for. This is Objective-C's notion of a closure. This isn't going to help you directly if the APIs that you're calling don't support block callbacks, but you may be able to create wrapper classes that use blocks instead of subclassed methods to handle callbacks.
There are many resources for learning about blocks in Objective-C.

Confused about Xibs and programmatically

i a newbie for iphone development. I got some questions here.
I know IB is a convinience tool for UI desgin and you also can do most things programmatically. I am just wondering, when should I create an interface controll without IB and why so. I am trying to form a good habit for this. Thank you very much. A friend told me that when efficiency should be considered for the application, then i should create interface controller programmatically, any other cases?
I am studying Learn Objective c on Mac now. It says that "Apple suggests you avoid using autorelease on your own code". So, does it mean I cannot use "autorelease" or just i should avoid using it. For example, can i use following code in my own code for iphone development?
#Interface Test {
A* a;
}
#Implementation {
a = [[[A alloc]init]autorelease];
}
Thank you for your time to read this. I am looking forward to answers :D.
Sometimes creating custom controls will require you to build them programmatically.
No, it's not that you can not use autorealease, it's just that using it adds to the burden of memory management. But in some cases you probably don't have an option, such as when you have a method that returns a temporary object. Using retain/release method to manually control object lifespan is the recommended way of doing things in iPhone development. Please see Autorelease pool for more details.
See Matt Gallagher's blog post for a discussion of efficiency. Simply put, one method is probably no more efficient than the other. This depends on your specific application, of course. Generally speaking, do what is most comfortable in designing your user interface. Make optimizations as needed.
1) If you are doing basic views that interface building has the widgets ready to go for, then use interface builder, it will make your life easier. Plus if you are just starting out it will let you get some sample code out the door faster. I'm not a huge fan of interface builder, but if you have to maintain code, you'll come across it so good thing to get familiar with it.
2) I don't think that autorelease is a bad thing. If you are writing single threaded code there is not as much to worry about. However, the thing that can come back to bite you is that you don't actually know when things will be released. So if you have programmed poorly, and try to reference an object that you have autoreleased later in code then you may get inconsistent behavior. I autorelease, but I also am very good about retain/release in other parts of my code that is passed these objects.