#import "House.h"
@interface House()
@property (nonatomic, readwrite) int numberOfBedrooms;
@end
@implementation House
-(instancetype)initWithAddress:(NSString*)address {
self = [super init];
if(self){
_address = [address copy];
_numberOfBedrooms = 2;
_hasHotTub = false;
}
return self;
}
@end
Month: September 2017
House Object Diagram
House
*address
int numberOfBedrooms
bool hasHotTub
-> address
#import <Foundation/Foundation.h> @interface House : NSObject @property (nonatomic) NSString *address @property (nonatomic) int numberOfBetrooms; @property (nonatomic) BOOL hasHotTub; @end
#import <Foundation/Foundation.h>
#import "House.h"
#import <Foundation/Foundation.h>
#import "House.h"
int main(int argc, const char * argv[]){
@autoreleasepool {
House *myHouse = [[House alloc] init];
}
return 0;
}
Dynamic Method Resolution
#import <Foundation/Foundation.h>
#import "Puppy.h"
#import "Dealer.h"
#import "Drum.h"
int main(int argc, const char * argv[]){
@autoreleasepool {
Puppy *spot = [[Puppy alloc] init];
Drum *drum = [[Drum alloc] init];
Dealer *cardDealer = [[Dealer alloc] init];
NSArray *array = @[spot, drum, cardDealer];
NSUInteger index = arc4random_uniform(3);
id item = [array objectAtIndex:index];
[item play];
}
return 0;
}
NSMutableArray *attendance = [NSMutableArray arrayWithArray: @[@”Diego”]];
[attendance addObject:@”Rahul”]
NSArray *invited = @[@”Diego”, @”Rahul”, @”Elana”]
Differences:Handling Nil
Objective-C: Any object can be nil
Swift: Optionals can be nil
#import <Foundation/Foundation.h>
#import "Messengaer.h"
#import "Package.h"
int main(int argc, const char * argv[]){
@autoreleasepool {
Messenger +spike = [[Messenger alloc] init];
Package *importantDocuments = [spike pickUpPackage];
NSLog(@"package contents: %@", importantDocuments.contents);
}
return 0;
}
Objective-C and Swift approaches to mutability differ
– how mutability is achieved for a given type
– the probability of an unintended mutation propagating through a program
#import <Foundation/Foundation.h>
#import "Messengaer.h"
#import "Package.h"
int main(int argc, const char * argv[]){
@autoreleasepool {
NSArray *kayakingGear = [NSMutableArray arrayWithArray:@[@"halmet",@"paddle",@"boat",
@"lifejacket"]];
[kayakingGear addObject:@"booties"];
NSLog(@"%@", kayakingGear);
}
return 0;
}
Design pattern
Protocols Enable Shared Functionality Across Classes
pets, dogs, birds, flight, bats, insects
UITextFieldDelegateProtocol in Swift
func textField(textField: UITextField,
shouldChangeCharactersInRange range:NSRange,
replacementString string: String) -> Bool {
var newText = textField.text! as NSString
newText =
newText.stringByReplacingCharactersInRange(range,
withString: string)
return newText.length <= 5
}
UITextFieldDelegateProtocol in Objective-C
-(BOOL)textField:(UITextField *)textField
shouldChangeCharactersInRange:(NSRange)range
replacementString:(NSString *)string{
NSString *nexText = textField.text;
newText = [newText
stringByReplacingCharactersInRange:range
withString:string];
return (newText.length <=5);
}
Objective-C
Objective-C: Any object can be nil, dynamic typing
Swift: Optionals can be nil, limited mutability
iOS Frameworks Design-Patterns: static typing
// Swift
override func viewWillAppear(animated: Bool){
super.viewWillAppear(animated)
displayResult()
}
// Objective-C
- (void)viewWillAppear:(BOOL) animated {
[super viewWillAppear:animated];
[self displayResult];
}
AppDelegate Methods
func application(application: UIApplication, didFinishLaunchingWithOptions
launchOptions: [NSObject: AnyObject]?) -> Bool {
return true
}
func applicationWillResignActive(application: UIApplication){
}
func applicationDidEnterBackground(application: UIApplication){
}
func applicationWillEnterForeground(application: UIApplication){
}
-(BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:
(NSDictionary *)launchOptions {
return YES;
}
- (void)applicationWillResignActive:(UIApplication *)application{
}
- (void)applicationDidEnterBackground:(UIApplication *)application {
}
- (void)applicationWillEnterForeground:(UIApplication *)application {
}
AdMob Console
Register an Account
https://www.google.co.jp/admob/
Loading and showing interstitial AD
Interstitial Ad – AdListener
loadAd -> onAdLoaded -> show, isLoaded
public class InterstitialActivity extends Activity {
private Button mShowButton;
private InterstitialAd mInterstitial;
@Override
public void onCreate(Bundle savedInstanceState){
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_interstitial);
mShowButton = (Button) findViewById(R.id.showButton);
mShowButton.setEnabled(false);
}
public void loadInterstitial(View unusedView){
mShowButton.setEnabled(false);
mShowButton.setText("Loading Interstitial");
mInterstitial = new InterstitialAd(this);
mInterstitial.setAdUnitId("ca-app-pub-xxxx/xxxx");
mInterstitial.astAdListener(new ToastAdListener(this){
@Override
public void onAdLoaded(){
super.onAdLoaded();
mShowButton.setText("Show Interstitial");
mShowButton.setEnabled(true);
}
@Override
public void onAdFailedToLoad(int errorCode){
super.onAdFailedToLoad(errorCode);
mShowButton.setText(getErrorReason());
}
});
AdRequest.on = new AdRequest.Builder().build();
mInterstitial.loadAd(ar);
}
public void showInterstitial(view unusedView){
if (mInterstitial.isLoaded()){
mInterstitial.show();
}
mShowButton.setText("Interstitial Not Ready");
mShowButton.setEnabled(false);
}
}
loadInterstitial
-Create InterstitialAd
-Set AdUnit Id
-Create Listener – onAdLoaded – show, onAdFailedToLoad – error
-Create AdRequest & LiadAd
Implementing an interstitial AD
InterstitialActivity
callback: loadInterstitial
Disable button
Set text to “Loading Interstitial”
Property: mShowButton
callback: showInterstitial (empty)
set to disable in onCreate
interstitial_ad_unit_id
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:id="@+id/linearLayout" android:orientation="vertical" android:layout_width="fill_parent" android:layout_height="fill_parent"> <Button android:id="@+id/loadButton" android:layout_width="fill_parent" android:layout_height="wrap_content" android:text="Load Interstitial" android:onClick="loadInterstitial"/> <Button android:id="@+id/showButton" android:layout_width="fill_parent" android:layout_height="wrap_content" android:text="Interstitial Not Ready" android:onClick="showInterstitial" /> </LinearLayout>
public class InterstitialActivity extends Activity {
private Button mShowButton;
@Override
public void onCreate(Bundle savedInstanceState){
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_interstitial);
mShowButton = (Button) findViewById(R.id.showButton);
mShowButton.setEnabled(false);
}
public void loadInterstitial(View unusedView){
mShowButton.setEnabled(false);
mShowButton.setText("Loading Interstitial");
}
public void showInterstitial(view unusedView){
}
}
Adding AdListener
import ...
public class ToastAdListener extends AdListener {
private Context mContext;
private String mErrorReason;
public ToastAdListener(Context context) { this.mContext = context; }
@Override
public void onAdLoaded(){
Toast.makeText(mContext,
"onAdLoaded()",
Toast.LENGTH_SHORT).show();
}
@Override
public void onAdOpened(){
Toast.makeText(mContext,
"onAdOpened()",
Toast.LENGTH_SHORT).show();
}
}