Tuesday, 17 April 2018


AWSS3 Transfer Utility Complete Functioning (using Swift iOS)

This demo app requires you to register on AWS and get the Bucket-region, Bucket-name from there to use in your app for further steps.

Features :- 
  1. Single Video/Image upload (With functionality of Pause, Resume, Cancel)
  2. Multiple Videos/Images upload (With each has functionality of Upload, Pause, Resume, Cancel)
  3. See the list of running uploads in-progress.
  4. Mutlipart Video/Image upload.
  5. Get the list of uploaded Videos/Images.
  6. Easily Delete the already uploaded Videos/Images from your bucket

Let's Start With actual codes


1. We require pod file changes such as

pod 'AWSS3'
pod 'AWSMobileClient'


2. Some mandatory changes in info.plist file






3. awsconfiguration.json file that is downloaded from AWS while you created your bucket. Put this file in the same tree directory where your info.plist is present. The below screenshot shows the demo content within it.




4. Some important changes in Appdelegate.swift file.

Here the first method "handleEventsForBackgroundURLSession" will manage  background upload tasks.
Second method will help us to get default AWSServiceManager set up with our Region and PoolId configuration keys.


import AWSS3
import AWSMobileClient

func application(_ application: UIApplication, handleEventsForBackgroundURLSession identifier: String, completionHandler: @escaping () -> Void) {

  AWSS3TransferUtility.interceptApplication(application,         handleEventsForBackgroundURLSession: identifier, completionHandler: completionHandler)
}

func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
   let credentialsProvider = AWSCognitoCredentialsProvider(regionType:    AWSRegionType.APNorthEast2, identityPoolId: "Your-PoolId-In-String-Format")

   let configuration = AWSServiceConfiguration(region: AWSRegionType.APNorthEast2, credentialsProvider: credentialsProvider)
AWSServiceManager.default().defaultServiceConfiguration = configuration

   return AWSMobileClient.sharedInstance().interceptApplication(application, didFinishLaunchingWithOptions: launchOptions)
}



5. Create singleton class with any name (I given UploadManager.swift), It will manage all your upload tasks, handling pause/resume/cancel of each task simultaneously, multiple in-Progress uploads, provides list of current running tasks, handling delete of the uploads from your AWS bucket. We will have enum for type of assest to be uploaded and many more.

enum MediaContentType: String {
   case Video = "movie/mov"
   case Image = "image/png"
}



enum UploadStatus: String {
   case Pause = "Pause"
   case Resume = "Resume"
   case Cancelled = "Cancelled"
   case InProgress = "InProgress"
   case Failed = "Failed"
   case Success = "Success"
}

6. The above class will handle all the status of each running task via single instance variable of Transfer Utility

lazyvar transferUtility: AWSS3TransferUtility = {
   return AWSS3TransferUtility.default()
}()

The above transferUtility give update to the UIViewController/collectionViewController/TableViewController via NotificationCenter. 
You just have to create anonymous callbacks for 3 important callbacks which we got from above transferUtility. These are as follows
  • continuationTaskBlock - It will be fired only once when your upload starts and the uploading task gets TransferId from AWSS3 sdk. This TransferId will be used by your controller to distinguish the uploads which are Initiated by that controller. If you want to save instance of that task for further manipluation then you can put in variable like (var uploadTask: AWSS3TransferUtilityUploadTask). In this closure you will fire a ContinuationNotification.
  • progressBlock - It will be fired multiple times while you video/image is getting uploaded. This block will give  you the progess of upload between 0.0 - 1.0 range. 1.0 will denote that your upload completed successfully. In this closure you will fire a ProgressNotification.
  • completionBlock - It will be fired when your upload completes successfully or with error. In this closure you will fire a CompletionNotification.

7. Custom Model will be useful for developer perspective when he want to show/manage multiple uploads in CollectionView/TableView at a time. 



class UploadModel{
  var tranferId: String = ""
  var progress: Double = 0.0
  var status: String = ""
  var failed: Bool = false
  var completed: Bool = false
  var inProgess: Bool = false
  var cancelled: Bool = false
  var paused: Bool = false
  init(){
   }
}

You can keep shared dictionary with upload file URL as key and above model as Value for distinguishing each upload in your whole app.
e.g. var dict: [String: UploadModel] = ["video1.mov": UploadModel(), "video2.mov": UploadModel(), "image1.png": UploadModel()]
As per the dictionary you can update your views or collectionviewcells/ tableviewcells.

On each notification from progressBlock, continuationBlock, completionBlock you can easily update above dict and as per that dict values your view gets updated.

By using this approach you can easily manage many number of uploads at a time.


8. Key Name (Asset name is important) 

For uploading any asset you have to pass key name for that upload and that key name will be assigned to that asset on your AWS cloud bucket. You can keep that key names in array for future purpose such as delete or download from cloud.


9. Delete Asset 

 For deleting the uploaded asset from AWS bucket you have to only give the key name     which you had set when you started a upload for that asset.

For complete source code you can see the gitHub repo



Sunday, 15 April 2018

Star Rating Control With Effortless Dragging Feature Using Swift (iOS)





An Smooth Draggable Star Rating Control

I have seen many apps those who are not having any rating view inside that. Some are having the feature but not so smooth as per the user's perspective. That's why I have created an easy to use pod for draggable rating view with good user experience.

Some fantastic features:

- Easy smooth color change dragging can be seen.

- Any color support with the multiple stars. You can give low opacity to high opacity color to each star for looking awesome color change.

- Using this control in Storyboard or within XIB is very easy and developer can   easily see the changes applied to the control such as star selected color and Rate points in the Interface builder.

- Easy to use within any UIViewController or UIView.

- Developer can change the fill color of Star as per his requirement very easily.

- Easy and strong support of IBDesignable and IBInspectable (You can see the changes very easily in Interface builder).

- Easy and strong support of IBDesignable and IBInspectable (You can see the changes very easily in Interface builder).

- The Rate Points can be easily set in Interface builder and as per that the star will be filled.

- The fill color can be easily changed via Inteface builder or at run time.

- Can easily change colors.

- Gives exact Rate points in float(e.g. 1.2, 2.3, 4.9 etc) as per the your drag position.

- Default two buttons are there such as "Rate Now", "Cancel".

- Supports Multiple buttons (requires an array of string to be passed for button names).

- Easy button click delegates are provided via protocols.

Usage Guide:

You want to add pod 'StarRatingDraggable', '~> 1.0' similar to the following to your podfile:

target 'MyApp' do
    pod 'StarRatingDraggable', '~> 1.0'
end

Then run a pod install inside your terminal or from CocoaPods.app.



Without any Images used :) 

Cocoapod url -  https://cocoapods.org/pods/StarRatingDraggable

For source code please visit my GitHub Url

Below are the screenshots and gif is attached for demonstration purpose.
  1. 
    
    
    
    
    
     
    
    
    
    
    
    
    
    
    
    
    
    
    
    
    
    
    
    
      
    
    
    
      
    
    
    
    
    
    Thank you so much.
    
    

Saturday, 24 March 2018

Extract .zip directly to external hard drive in MacOS

Easily extract .zip file directly to External HDD / USB / External Storage instead of default SSD or HDD.


If you are having two storage in your Mac machine in which the default is having small storage space and other one is with large space then you obviously want to store files, large projects on big volume and your working softwares and compilers on default volume.
Below is the example demonstrated (storage for example purpose only).

  1. SSD (120 GB) - 
     2. HDD (External 500 GB) -  Archive.zip    ( <--- it's the zip to be extracted, and we want it to be extracted on this location only where the zip is present)

But when you click it to extract then it extracts to the default SSD storage at the location ~/Downloads/ with extracted folder named as "Archive".  (This is the actual problem we are facing when extracting the .zip file whose actual size is 100GB and we are having small storage of default SSD)

At this point we want to extract the .zip file to the external storage only.

Open the Terminal app from Spotlight search or from Applications -> Utilities -> Terminal and navigate to your folder where the .zip file is stored with "cd ~/locationOf/Acrchive.zip" and press Enter.

And extract the ZIP file with the OSX command line tool 

unzip /ExtrenalHDD/Folder/Archive.zip -d /Volumes/ExtrenalHDD/FolderName

In the above command after typing /Volumes press double Tab and you can see the list of Volumes present such as SSD, HDD, USB etc. The the second path  /Volumes/ExtrenalHDD/FolderName is the location where you want to extract the zip.

Thanks You





Sunday, 11 March 2018

List Of Trending Software Development Blogs

In the today's passion for technology every school or college student or any software professional who wants to learn software coding, searches online for extremely good blogs for practice.
Here are the list of top blogs which could be better for all those who want to learn Software development briefly.


The top 20 Software development blogs are listed below


1. Dzone
One of the best software development blogs is Dzone. Web, where you will find all necessary information about agile software development. Tutorials, guidelines, tools and software insights for beginners and experts. Hundreds of publications, over 1M members. Top topics: Agile, Big data, Cloud, Data base, Devops, Integraton, IOT, Java, Mobile, Performance, Security and many more.


A computer science portal for geeks. It contains well written, well thought and well explained computer science and programming articles.


Place for in-depth development tutorials and new technology trends. Here you will find latest information about Back-end, Web front-end, Mobile, agile project management, etc.


This blog is about software development & software architecture. Here you will find useful information about: Agile, Backend, IOS, Android, DDD, TDD, CI, SOLID, Unit testing, microservices, docker, natural language processing, Reactive, Javascript, PHP, Scala, Nodejs, Angularjs and many many more.

This blog has tutorials for iOS and Android developers. Tips and best practices for swift and mac lovers. Unit testing, Unity, C#, Json and many more.

Awesome blog for Agile lovers. It has some practical tips and approaches for agile software development; testing, integration, etc. Here you may find announcements, journal entries, status reports, news, trends, tricks and tips and many more.

Best place to find examples of clean code. Also, you will see DevOps tools and best software development practices.

Scotch is a web development blog discussing all programming topics. Most popular ones are: Javascript, Angular 2, Node.JS, Docker, PHP, etc.

This blog you will love if you have a good sense of humor as it’s posts often include funny asides on the human aspects of coding. Also you will find articles discussing recent advances in the tech world.

As you could guess from the name, here you will find all useful information about Docker. Case studies, tutorials, examples, updates, news and many more. Everything you need to be convinced using docker, but using it right.

Here you may actually learn Java online. You will find Android development tutorials, Java tutorials for beginners, Java books, Scala, Kotlin, Groovy and JRuby news, code examples and many more.

Useful blog with articles about Java, .NET, PHP, Javascript, C++ and many more.

Here it is a bit easy to guess again. This blog is about JavaScript, about React. All necessary tips and advices you may get there to be sure your Javascript project is going in the right direction.

In this blog engineers of Twitter share their case studies, their tips, their findings and pitfalls. This blog is based on real examples, real projects. Here you may really learn from one of the best engineer teams in the world and know which tools they use and which methodology they follow.

This blog is about Scrum; best practices and tools. Here you will find success stories, tutorials, examples, statistics and other useful articles to improve team’s productivity and efficiency of the project.

Again quite easy to guess that this blog is about Scala. Scala updates, Scala best practices, Scala tips and examples.


17. Devhumor
Yes, this one is related to software humor. Memes, pictures, jokes, code and other stuff from real life that make you laugh.

Offers daily posts of user-submitted examples of bad code and software design. Good place to find examples and explanation of curious perversions in Information Technology. Basically, it is “how not to” guide for developing software. They recount tales of disastrous development, from project management gone spectacularly bad to inexplicable coding choices.

Blog with interesting articles about Java, Performance Solutions, agile, software architecture, continuous delivery, cloud and many more.

Engineering blog for Node.js and JavaScript lovers. TDD, callback hell, clean coding and other buzz and important topics are discussed here.

  • Also make profile on Stackoverflow.com and search daily for any type of stuff related to software development, Networking, Hardware related questions.



All the Best for the future.


Tuesday, 24 May 2016

Left aligned UICollectionView cells with dynamic cell width in Xamarin.ios

Since this is my first blog post, if you find any spelling mistake then please forgive me.
As a Mobile App developer, I faced many issues in designing. Since in App developement using Xamarin.ios in .Net environment, i found many problems regarding some design features of  UICollectionView, UITableView.
So I want to share a some simple code and tricks to design a good looking Left Aligned UICollectionView with Dynamic cell width. Here you can assign dynamic height also. But most of the Mobile App developer requires UICollectionView with dynamic cell width.
So here is the full code.
The whole code is written in C# and it will be more helpful for the Xamarin.ios developers.


1.First create a UICollectionView and add it in View where you want it to be displayed.

UICollectionView collectionView;


2.Then create a UICollectionViewFlowLayout with any name. This FlowLayout will assign a frame to each of the cell that are created in UICollectionView.

UICollectionViewFlowLayout CollectionFlowLayout;
CollectionFlowLayout = new LeftAlignedCollectionViewFlowLayout();

if you are confused then let me explain why i had instantiated the flowlayout with custom name, because i had my whole code  and method declaration in my custom flowlayout class named LeftAlignedCollectionViewFlowLayout.

3. Then instantiate a collectionView with some frame and pass it our custom flowLayout named CollectionFlowLayout 

4. Write the class declaration and whole overridden methods in the LeftAlignedCollectionViewFlowLayout. The code is below.

class LeftAlignedCollectionViewFlowLayout : UICollectionViewFlowLayout
        {
            nfloat maxCellSpacing = 10;

            public LeftAlignedCollectionViewFlowLayout()
            {
            }

            public override UICollectionViewLayoutAttributes[] LayoutAttributesForElementsInRect(CGRect rect)
            {

               var arr = base.LayoutAttributesForElementsInRect(rect);
                for (int i = 1; i < arr.Count(); ++i)
                {
                    UICollectionViewLayoutAttributes currentLayoutAttributes = arr[i];
                    UICollectionViewLayoutAttributes prevLayoutAttributes = arr[i - 1];
                    nint maximumSpacing = 10;
                    nfloat origin =  prevLayoutAttributes.Frame.GetMaxX();
                    if(origin + maximumSpacing+ currentLayoutAttributes.Frame.Size.Width<CollectionView.ContentSize.Width)
                    {
                        CGRect frame = currentLayoutAttributes.Frame;
                        frame.X = origin + maximumSpacing;
                        currentLayoutAttributes.Frame = frame;
                    }
                }
                return arr;
            }

            public override UICollectionViewLayoutAttributes LayoutAttributesForItem(NSIndexPath indexPath)
            {
                var currentItemAttributes = base.LayoutAttributesForItem(indexPath);


                var collectionViewFlowLayout = CollectionView.CollectionViewLayout as UICollectionViewFlowLayout;

                if (collectionViewFlowLayout != null)
                {
                    var sectionInset = collectionViewFlowLayout.SectionInset;
                    if (indexPath.Item == 0)
                    { // first item of section
                        var frame = currentItemAttributes.Frame;
                        frame.X = sectionInset.Left; // first item of the section should always be left aligned
                        currentItemAttributes.Frame = frame;
                        return currentItemAttributes;
                    }

                    var previousIndexPath = NSIndexPath.FromItemSection(indexPath.Item - 1, indexPath.Section);
                    var previousFrame = base.LayoutAttributesForItem(previousIndexPath).Frame;

                    previousFrame.X = base.LayoutAttributesForItem(previousIndexPath).Frame.Left;
                    if (previousFrame.X != base.LayoutAttributesForItem(previousIndexPath).Frame.Left)
                    {
                        var n = base.LayoutAttributesForItem(previousIndexPath).Frame.Left;
                        previousFrame.X = n;
                        maxCellSpacing = 0;
                    }
                    var previousFrameRightPoint = (previousFrame.X) + (previousFrame.Size.Width) + maxCellSpacing;

                    var currentFrame = currentItemAttributes.Frame;
                    var width = 0.0;

                    var collectionViewWidth = CollectionView == null ? 0 : CollectionView.Frame.Size.Width;
                    width = collectionViewWidth;
                    var strecthedCurrentFrame = new CGRect(0, currentFrame.Y, width, currentFrame.Size.Height);

                    if (CGRect.Intersect(previousFrame, strecthedCurrentFrame) == CGRect.Empty)
                    { // if current item is the first item on the line
                        // the approach here is to take the current frame, left align it to the edge of the view
                        // then stretch it the width of the collection view, if it intersects with the previous frame then that means it
                        // is on the same line, otherwise it is on it's own new line
                        var frame = currentItemAttributes.Frame;
                        frame.X = sectionInset.Left; // first item on the line should always be left aligned
                        currentItemAttributes.Frame = frame;
                        return currentItemAttributes;
                    }

                    var frame2 = currentItemAttributes.Frame;
                    frame2.X = previousFrameRightPoint;
                    currentItemAttributes.Frame = frame2;
                }
                return currentItemAttributes;
            }

        }

5.Create and assign a data source to the our previously insaniated collectionView.

UIcollectionDInterestSource collectionDataSource;
collectionView.Source = collectionDataSource = new UIcollectionDInterestSource(this, collectionView, lstString);

Here 'this' parameter in the datasource is the instance of the class that holds our UICollectionView.
2nd parameter is the collectionView, and 3rd parameter is the actual data that is to be displayed in the cells of collection View.

My lstString is as follows.
List<string> lstString = new List<string> { "A Thing", "Another", "BTopic gsrg Thing", "A Thing", "Another", "BTopic Thing", "AB", "Interest BTopic", "My Interest", "Other Toipc here", "Some Topic", "A Thing", "Another", "BTopic", "Interest", "My Interest", "Other Toipc here", "Some Topic", "My Interest", "Other Toipc here", "Some Topic", "Vivek Gupta", "My Other Friend" };

The list contains string element with dynamic number of text.

Then register a UICollectionView class for our custom UICollectionView cells.

6. Now create a custom UICollectionViewDelegateFlowLayout that will assign a dynamic width to our cell as per the string of text.

collectionView.Delegate = new CollectionViewFlowDelegate(lstString, CollectionFlowLayout);

and the whole code for UICollectionViewDelegateFlowLayout is below:


class CollectionViewFlowDelegate : UICollectionViewDelegateFlowLayout
        {
            List<string> lstStr;
            public CollectionViewFlowDelegate(List<string> lstString, UICollectionViewFlowLayout CollectionFlowLayout)
            {
                lstStr = lstString;

            }
            public override CGSize GetSizeForItem(UICollectionView collectionView, UICollectionViewLayout layout, NSIndexPath indexPath)
            {
                CGSize size = new NSString(lstStr.ElementAt(indexPath.Row).ToString()).GetSizeUsingAttributes(new UIStringAttributes(NSDictionary.FromObjectAndKey(AppFonts.TitleFontSemiBold(15), UIStringAttributeKey.Font)));
                size.Width += 20;
                size.Height += 20;
                collectionView.SystemLayoutSizeFittingSize(size, 1.0f, 1.0f);

                return size;
            }


        }

7: The datasource class :

 public class UIcollectionDInterestSource : UICollectionViewSource
        {           
            MyProfileController controller;
            List<string> lstStr;

            public UIcollectionDInterestSource(MyProfileController controller, UICollectionView collectionView, List<string> lstStr)
            {
                this.controller = controller;
                this.lstStr = lstStr;
            }

          

            public override nint NumberOfSections(UICollectionView collectionView)
            {
                return 1;

            }

            public override nint GetItemsCount(UICollectionView collectionView, nint section)
            {
                return lstStr.Count;
            }

            public override UICollectionViewCell GetCell(UICollectionView collectionView, NSIndexPath indexPath)
            {
                var cell = (MyInterestCollectionViewCell)collectionView.DequeueReusableCell(MyInterestCollectionViewCell.CellId, indexPath);

                cell.UpdateCell(lstStr.ElementAt(indexPath.Row));
                cell.ContentView.AddGestureRecognizer(new UILongPressGestureRecognizer(LongPress));
                cell.ContentView.AddGestureRecognizer(new UITapGestureRecognizer(TapGesture));
                cell.ContentView.Layer.BorderColor = UIColor.Clear.FromHexString(AppTheme.AttendeeNetworkColor, 1.0f).CGColor;
                cell.ContentView.Layer.BorderWidth = 2.0f;
                cell.ContentView.Layer.CornerRadius = 4.0f;
                Console.WriteLine(cell.Frame);
                return cell;


            }

           
            public override void ItemHighlighted(UICollectionView collectionView, NSIndexPath indexPath)
            {
                var cell = collectionView.CellForItem(indexPath);
            }

            public override void ItemUnhighlighted(UICollectionView collectionView, NSIndexPath indexPath)
            {
                var cell = collectionView.CellForItem(indexPath);
            }

            public override bool ShouldHighlightItem(UICollectionView collectionView, NSIndexPath indexPath)
            {
                return true;
            }

            public override bool ShouldSelectItem(UICollectionView collectionView, NSIndexPath indexPath)
            {

                return true;
            }

            // for edit menu
            public override bool ShouldShowMenu(UICollectionView collectionView, NSIndexPath indexPath)
            {
                return false;
            }

            public override bool CanPerformAction(UICollectionView collectionView, Selector action, NSIndexPath indexPath, NSObject sender)
            {
                if (action == new Selector("custom"))
                    return true;
                else
                    return false;
            }

            public override void PerformAction(UICollectionView collectionView, Selector action, NSIndexPath indexPath, NSObject sender)
            {
                System.Diagnostics.Debug.WriteLine("code to perform action");
            }



        }
8. The output is as follows displayed in the image.