Friday, 26 February 2016

Working with blocks

Block is same as the c function.The basic idea of a block is to treat a small piece of code as if it were a value. The piece of code can then be passed as a parameter in messages or assigned to a variable.

^{NSLog(@"It is a block literal); }


The use of blocks often involves nothing more than including code in block literal form as parameters for methods (designed to take blocks) that are part of the iOS API.
A block is the only object that begins its life in stack, rather than heap memory.A very effective use of a block literal is to deal with a callback. 

Creating a block variable:

int  (^sum)(int, int) = ^(int a , int b){
 return a+b;
}

This  is a simple block definition . It takes two parameters  of type int and return one int parameter.
To call this block as:

int c = sum(3,5);
NSLog(@"sum is %d",c);

When a block is created, it will capture, or close around, the values of those variables that the code has referred to and that are in the same lexical scope of the block. Essentially, a snapshot is taken of these values. These values are preserved in the memory allocated for the block and cannot later be changed. It is said that these variables are "captured by value".
To change the this behavior(to use the latest values of the variable), we can declare these variable as 
__block storage specifier.

__block int z =5;

Block as method parameter: We can also use block as method parameter to use call back. For example:
 
-(void)validateString:(NSString *)str onCompletion:(void(^)(bool isValidate))completion{
          
 if(str.length ==0){
    completion(NO); //call block
}else{
    completion(YES);
}
}

Now call this method as 

[self validateString:@"iOS" onCompletion:^(bool isValidate){
    
if(isValidate){
 //str is valid, handle it
}else{
  // str is not valid, handle it here
}       
   
}];

That's it. Though the use of block seems some complex at first time but once we get used to, it is very easy to use block in our code. With the help of block we can make our code simple, readable and easy to maintain .

Friday, 19 February 2016

iOS app life cycle

We can categorized iOS life cycle mainly in two category:

1) The App launch cycle
2) View Controller life cycle

The launch cycle states different app states in which an iOS app can transit in its life . The different app states are as:

1) Not running
2) Inactive
3) Active
4) Background
5) Suspended

When an app goes from one states to another it is called app delegate methods. These methods provides a way  to take appropriate action  on app state changes. These methods are as:

application:didFinishLaunchingWithOption: called when app launches first time.

applicationDidBecomeActive: called after app enters in foreground.

applicationWillResignActive: called before an app enters in background.

applicationDidEnterBackground: called after app enters in background. In this state an app may be suspended at any time.

applicationWillEnterForeground:called when app changes state from background to foreground. But app is not yet active

applicationWillTerminated: This method is not called when an app is suspended or user terminated the app explicitly.


View Controller life cycle:

viewDidLoad: called only once  during initial load of the interface.

viewWillAppear:This method is called just  before views appears or renders on screen every time when you   navigate or switch between different views.

viewDidAppear: called when views completely.  Here we can handle UI or functionalities.

viewWillDisappear: called before view is removed or any animation is configured.

viewDidDisappear:called when view is removed.

Friday, 12 February 2016

Property Attributes in Objective C

Property attributes gives the functionality to define a way in which the property works. With attributes we can change the way property works. These property attributes can be categorized into three category.

1) Atomocity
       atomic and nonatomic
2)Access
       readonly and readwrite
3) Storage
      strong, weak , assign and copy


Atomic(default):
       An atomic property guaranteed that you will get a valid data when you try to read from it. It does not make any guarantees what the data might be but you will get the good data not just junk memory. This is used when multiple thread or processes pointing to same variable and reading and writing simultaneously.

Nonatomic:With it you lose the guarantee that you will get good data every time . When you try to access in the middle of the write, you could get back the garbage data.


ReadOnly: It makes the property read only that means no setter for it at all.

ReadWrite(default): It is the flip side of the readonly. Allows both read and write.

Strong(default): It means you have a reference to an object and you will keep the object alive. As you hold the reference to the object , the object will not  be deallocated and released back to the memory.

Weak: It gives the reference to the object so that  you can talk to the object but you can not keep it alive. If object's reference count goes to zero, the property becomes nil automatically.

Assign:It is used for primitives.

Copy:It works well with all kinds of mutable objects If you set a copy property, instead of just setting both references to the same object, what it actually does is makes a copy of the object you are setting and then sets the property to that copy.

Friday, 29 January 2016

Push notification

Push notifications:
There are two types of notifications in ios, local and remote notification. Remote notifications are also called push notification. Notifications enable an app that isn’t running in the foreground to let its users know it has information for them. The information could be a message, an impending calendar event, or new data on a remote server. When presented by the operating system, local and remote user notifications look and sound the same. They can display an alert message or they can badge the app icon. They can also play a sound when the alert or badge number is shown.
1) An app enables push notifications. The user has to confirm that he wishes to receive these notifications.
2) The app receives a “device token”. You can think of the device token as the address that push notifications will be sent to.
3) The app sends the device token to your server.
4) When something of interest to your app happens, the server sends a push notification to the Apple Push Notification Service, or APNS for short.
5) APNS sends the push notification to the user’s device.
6) When the user’s device receives the push notification, it shows an alert, plays a sound and/or updates the app’s icon. The user can launch the app from the alert. The app is given the contents of the push notification and can handle it as it sees fit. 
If you want to notify the users of your app about external events while the app is closed, you still need push notifications.
To enable push notification in an app you need some dependencies:
1)To enable push notifications in your app, it needs to be signed with a provisioning profile that is configured for push.
2)your server needs to sign its communications to APNS with an SSL certificate.
3)Each push app needs its own unique ID because push notifications are sent to a specific application. (You cannot use a wildcard ID.)
Register for remote notification in app delegate.m-(BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
 // Let the device know we want to receive push notifications

 [[UIApplication sharedApplication] registerForRemoteNotificationTypes:

(UIRemoteNotificationTypeBadge | UIRemoteNotificationTypeSound | UIRemoteNotificationTypeAlert)];

    return YES;
}

The new call to registerForRemoteNotificationTypes: tells the OS that this app wants to receive push notifications.
There is one more thing you need to add in order to be able to receive push notifications. Add the following to AppDelegate.m:
To obtain deviceToken:- 
(void)application:(UIApplication*)application didRegisterForRemoteNotificationsWithDeviceToken:(NSData*)deviceToken
{
 NSLog(@"My token is: %@", deviceToken);
}
- (void)application:(UIApplication*)application didFailToRegisterForRemoteNotificationsWithError:(NSError*)error
{
NSLog(@"Failed to get token, error: %@", error);
}
When your app registers for remote (push) notifications, it tries to obtain a “device token”. This is a 32-byte number that uniquely identifies your device. 
The didRegisterForRemoteNotificationsWithDeviceToken method is usually called right away after you’ve registered for push notifications. Usually, but not always. 

Receiving Push Messages in the App
So what happens when your iPhone receives a push notification? There are three possible situations:
The app is currently running in the foreground.
The app is closed, either the iPhone’s home screen is active or some other app is running.
The iPhone is locked.
The final modifications to our app all take place in AppDelegate.m, as the application delegate is the one who receives the push notifications. There are two places for this:
application:didFinishLaunchingWithOptions:. If your app wasn’t running when the notification came in, it is launched and the notification is passed as part of the launchOptions dictionary.
application:didReceiveRemoteNotification:. This method is invoked if your app is active when a notification comes in. On iOS 4.0 or later, if your app was suspended in the background it is woken up and this method is also called. You can use UIApplication’s applicationState property to find out whether your app was suspended or not.
Add Observer to register for events in order to call back when notification recieves :
[[NSNotificationCenter defaultCenter]  addObserver:menuVCDriver selector:@selector(showBookViewController:) name:@"bookingDetails" object:nil];
post the notification as app receives it :
[[NSNotificationCenter defaultCenter] postNotificationName:@"bookingDetails" object:self userInfo:dictBookingDetails];

For more information you can check this tutorial:

http://www.raywenderlich.com/32960/apple-push-notification-services-in-ios-6-tutorial-part-1

Friday, 15 January 2016

Searching the table view content

Hello... friends, I am here with a new blog. Today I am discussing how to search for specific content in a UITableView when it has a lot of data .

When we have a large number of data to display in UITableView, then looking for a particular  data is very tedious task. To overcome this problem we can enable a search functionality on the tableview. As I used this in one of my app.

UISearchBar provide a functionality to search the content we look for from the specific view (here it is table view).It is very simple to use UISearchBar in an app. Steps are as follows:

1) Add UISearchBar property in your view controller's interface file  and set its delegate

                     self.searchBar = [[UISearchBar alloc]init];
        self.searchBar.showsCancelButton = YES;
        self.searchBar.delegate = self;
        [self.searchBar becomeFirstResponder];

2)I am displaying the search bar in navigation bar as:
        self.navigationItem.titleView = self.searchBar;


3) Implement the delegate method of the  UISearchBar 

-(void)searchBarCancelButtonClicked:(UISearchBar *)searchBar{
    
    //hide the searchBar, and reload the tableview to show original data
    isSearching = NO;    
}
-(void)searchBarSearchButtonClicked:(UISearchBar *)searchBar{
    //start the search
    NSLog(@"search btn cliked");
    [searchBar resignFirstResponder];
    [self searhTableList];
    
}
-(BOOL)searchBarShouldBeginEditing:(UISearchBar *)searchBar{
    NSLog(@"search should begin editing");
    isSearching = YES;
    return YES;
}

Here when user type some text to search and tap the search button, we are searching the table list and then if any matches occur we add the specific row's data to a mutable array and we reload the table view to show the filtered result.

To store the filtered result, declare a mutable array in interface file , here it is filteredArrData,


-(void)searhTableList{
    NSString *searchString = self.searchBar.text;
   
    for (NSString *data in self.arr_tableData) {
         
        NSRange range = [data rangeOfString:searchString options:NSCaseInsensitiveSearch];
         
        NSComparisonResult result = [data compare:searchString options:(NSCaseInsensitiveSearch|NSDiacriticInsensitiveSearch) range:range];
        
        if (result == NSOrderedSame) {
            [self.filteredArrData addObject:data];
        }
    }

    if (self.filteredArrData.count == 0) {
         //show an alert, no results found
        
    }else{
         //reload the tableview
          
     }

That 's it. Here I am showing how to implement search on table's data.I am not showing how to use same table view to show the search result and original data(full data to show in table view). It's up to you  how to use it .
        




Friday, 8 January 2016

Enumeration in Objective C

Enum (enumerated type) is an user-defined type that is used in Objective-C to represent the data that can be stored in one of several predefined values (all of them are int).


Let’s imagine you have to implement a simple UIView that has three different visual modes: default (grey), green and red. Each mode is represented to user by three different pictures: my_mode_grey.pngmy_mode_green.png and my_mode_red.png. All of three final views would have some common behavior. 

To understand it , lets take an example:

1) First create an enum

enum myMode {
         
         myViewModeDefault,  //== 0(by default)
         myViewModeGreen,   //  == 1 (incremented by one from previous)
         myViewModeBlue    // ==2 

};


It means that every “mode” is simply described by the unique int value (unique inside current enum). Each next enum mode is incremented by 1 by default. You can also set the enum mode values by yourself (if you really need it):


enum myMode {
         
         myViewModeDefault = 5,  //== 5 (redefined)
         myViewModeGreen,   //  == 6 (incremented by one from previous)
         myViewModeBlue  = 9   // ==2 

};

2) Now lets create a class:

#import <UIKit/UIKit.h>
@interface MyViews:UIView{

    enum myMode mode ;

}
-(id)initWithMode:(enum myMode)amode;

@end


3) implement our custom initializer:

@implementation MyViews

-(id)initWithMode:(enum myMode)amode{
      
             self = [super init];
            
             if(self){
                   mode = amode;
             

       //to store different images

      NSString  *imageName;
    
         switch(amode){
             
       case myViewModeDefault:
                               imageName = @"tom.png"
                                break; 
       case myViewModeDefault:
                               imageName = @"jery.png"
                                break; 

     case myViewModeDefault:
                               imageName = @"draculla.png"
                                break; 

     default:
                  imageName = @"sorry.png"
                                break; 
}

      UIImageView *imageView = [UIImageView alloc]initWithImage:[UIImage imageNamed: imageName]];

     [self addSubview:imageView];
}

return self;

}

@end



Thats it, how easy it is.

Friday, 18 December 2015

UIDatePicker


Sometimes we need  of a date and time picker in our app to pick a date and time . Today I am going to  demonstrate how to use Apple's inbuilt UIDatePicker to pick the date and time. It is very simple.

To use UIDatePicker in an app , first of all create a UIDatePicker instance and set mode as what we want  to have in our picker, only date/time or both. As in my case I want to have both in my app . So i set the mode to  UIDatePickerModeDateAndTime .

//create an  instance of the NSDatePicker
UIDatePicker  *datePicker = [[UIDatePicker alloc] initWithFrame: CGRectZero];

//set mode
[datePicker setDatePickerMode:UIDatePickerModeDateAndTime];


Then add a selector to the date picker that will be called when user want to select the date and time from  datePicker .

//add target

[datePicker addTarget:self action:@selector(selectDateAndTime:) forControlEvents:UIControlEventValueChanged];

Thats all, we have configured the datePicker. Now add the datePicker to the control when we want to datePicker to be appeared.
As I want datePicker to be appeared when user tap on a textField, So i add the datePicker to texField's accessory view as:

//add datePicker as accessory view of the textField:
self.txt_Time.inputView = datePicker ;


Now implement the method that we have assigned as a selector to datePicker:

-(void)selectDateAndTime:(UIDatePicker*)picker{
    NSDateFormatter *dateFormatter  = [[NSDateFormatter alloc]init];
    [dateFormatter setDateFormat:@"hh:mm a dd-MM-yyyy "];
     NSString *formattedString = [dateFormatter stringFromDate:[datePicker date]];
     self.txt_time.text = formattedString;
}


That is it. How easy it is.