SlideShare ist ein Scribd-Unternehmen logo
1 von 63
Downloaden Sie, um offline zu lesen
Hi-Performance Table
Views with QuartzCore
    and CoreText
  Beginners guide to an advanced concept




              Mugunth Kumar
  Steinlogic Consulting and Training Pte Ltd
About me
About me
    •   Author of the iOS 5, iOS 6 Programming:
        Pushing the Limits book - Reached the top
        100 books in Amazon’s Computer and
        Technology books list

    •   Trainer - Conducts training on iOS
        programming at iOSTraining.sg.

    •   Developer

    •   MKNetworkKit (1200+ watchers)

    •   MKStoreKit (700+ watchers)

    •   Several other “minor” projects with 200+
        watchers

    •   Clients include startups in Singapore like
        Squiryl, Found and MNC’s including
        Microsoft Redmond, Oracle and such.
Why?



•   What makes apps pleasant to use?

    •   Fast scrolling

    •   Why?
Why?
Why?


•   iPhone is a direct manipulation device
Why?


•   iPhone is a direct manipulation device

•   iPhone screen is closer to your eye than your HDTV or your
    computer monitor
Why?


•   iPhone is a direct manipulation device

•   iPhone screen is closer to your eye than your HDTV or your
    computer monitor



•   60 frames per second = 16.66ms per frame
Why?


•   iPhone is a direct manipulation device

•   iPhone screen is closer to your eye than your HDTV or your
    computer monitor



•   60 frames per second = 16.66ms per frame

•   Anything less, you will get a headache
Agenda
Agenda

•   Why?
Agenda

•   Why?

•   Three different methods
Agenda

•   Why?

•   Three different methods

•   Pros and Cons
Agenda

•   Why?

•   Three different methods

•   Pros and Cons

•   QuartzCore/CoreText introduction
Agenda

•   Why?

•   Three different methods

•   Pros and Cons

•   QuartzCore/CoreText introduction

•   A simple table view cell example
Agenda

•   Why?

•   Three different methods

•   Pros and Cons

•   QuartzCore/CoreText introduction

•   A simple table view cell example

•   What else can you build? - Facebook style news feed
Compositing Table View Cells



•   UITableViewCell

    •   Subviews (UILabel, UIImageView)
Pros/Cons
Pros/Cons


•   Advantages

    •   Programmatically easy

    •   Fast for compositing images

    •   Built in cells are rendered differently
Pros/Cons


•   Advantages

    •   Programmatically easy

    •   Fast for compositing images

    •   Built in cells are rendered differently

•   Drawbacks

    •   Slow for text based tables
Direct Drawing



•   UITableViewCell drawRect

    •   NSString -drawInRect, drawAtPoint

    •   UIImage -drawInRect, drawAtPoint
Pros/Cons
Pros/Cons


•   Advantages

    •   Fast

    •   Really fast!
Pros/Cons


•   Advantages

    •   Fast

    •   Really fast!

•   Drawbacks

    •   Difficult (Annoyingly complex to build complex layouts)

    •   CGContextDrawImage is really slow compared to using
        UIImageView
Hybrid




•   A mix of drawRect + UIImageViews
Cons
Cons

•   Still cannot render shadows around images views
Cons

•     Still cannot render shadows around images views


    self.view.layer.masksToBounds = NO;
    self.view.layer.shadowColor = [UIColor blackColor].CGColor;
    self.view.layer.shadowOffset = CGSizeMake(0.0f, -1.0f);
    self.view.layer.shadowOpacity = 0.5f;
    self.view.layer.shadowRadius = 1.0f;
Cons

    •     Still cannot render shadows around images views


        self.view.layer.masksToBounds = NO;
        self.view.layer.shadowColor = [UIColor blackColor].CGColor;
        self.view.layer.shadowOffset = CGSizeMake(0.0f, -1.0f);
        self.view.layer.shadowOpacity = 0.5f;
        self.view.layer.shadowRadius = 1.0f;




•       The above code is dog slow.

•       Good for views, very bad for table view cells or collection view
        cells
Is there a better way?



•   QuartzCore.framework



•   CoreText.framework
Pros/Cons
Pros/Cons


•   Advantages

    •   Fast

    •   Can render text and image within our 16ms deadline

    •   Rendering highly customized text is hard
Pros/Cons


•   Advantages

    •   Fast

    •   Can render text and image within our 16ms deadline

    •   Rendering highly customized text is hard




               This is BOLD and this is in italics.
QuartzCore



•   CALayer

•   CATextLayer

•   CAGradientLayer

•   CAShapeLayer
CoreText


•   NSAttributedString

•   NSMutableAttributedString



•   UIBezierPath
Composition


@interface SCTCoreTextCell

@property   (strong,   nonatomic)   CATextLayer *nameTextLayer;
@property   (strong,   nonatomic)   CATextLayer *timeTextLayer;
@property   (strong,   nonatomic)   CALayer *avatarImageLayer;
@property   (strong,   nonatomic)   CALayer *avatarImageShadowLayer;
@property   (strong,   nonatomic)   CATextLayer *descriptionTextLayer;

@end
CALayer - Images

  self.backgroundLayer = [CALayer layer];
  self.backgroundLayer.frame = CGRectMake(0, 0, 320, 150);
  self.backgroundLayer.contentsScale = [[UIScreen mainScreen] scale];
  self.backgroundLayer.actions = [NSDictionary actionsDictionary];
  self.backgroundLayer.contents = (id) backgroundImage.CGImage;

  self.backgroundLayer.contentsCenter = CGRectMake(1.0/
backgroundImage.size.width, 8.0/backgroundImage.size.height,
                                                   1.0/
backgroundImage.size.width,1.0/backgroundImage.size.height);
  self.backgroundLayer.contentsGravity = kCAGravityResize;

  [self.contentView.layer addSublayer:self.backgroundLayer];
CATextLayer - Text


self.nameTextLayer = [CATextLayer layer];

self.nameTextLayer.frame = CGRectMake(65, 3, 240, 21);
self.nameTextLayer.alignmentMode = kCAAlignmentLeft;
self.nameTextLayer.wrapped = YES;
self.nameTextLayer.contentsScale = [[UIScreen mainScreen] scale];

self.nameTextLayer.actions = [NSDictionary actionsDictionary];

[self.contentView.layer addSublayer:self.nameTextLayer];
Composition

+(NSDictionary*) actionsDictionary {

    return @{
      @"onOrderIn" : [NSNull null],
      @"onOrderOut" : [NSNull null],
      @"sublayers" : [NSNull null],
      @"contents" : [NSNull null],
      @"position" : [NSNull null],
      @"bounds" : [NSNull null],
      @"onLayout" : [NSNull null],
      @"hidden" : [NSNull null],
      };
    });
}
Contents
Contents


•   CALayer

    •   Mostly Images

    •   Rendering a graphics context in background
Contents


•   CALayer

    •   Mostly Images

    •   Rendering a graphics context in background
Contents


•   CALayer

    •   Mostly Images

    •   Rendering a graphics context in background



•   CAGradientLayer

    •   Adding gradient backgrounds
Contents
Contents


•   CAShapeLayer

    •   Mostly Paths

    •   Use UIBezierPath to create a path
Contents


•   CAShapeLayer

    •   Mostly Paths

    •   Use UIBezierPath to create a path
Contents


•   CAShapeLayer

    •   Mostly Paths

    •   Use UIBezierPath to create a path



•   CATextLayer (Most useful + complicated)

    •   Text (NSAttributedString)
NSAttributedString



•   The basic building block for complex text rendering



•   NSAttributedString = NSString + Attributes Dictionary
Demo 1 - Simple Bold
Composition
-(void) setText {

  CTFontRef ctBoldFont = CTFontCreateWithName((__bridge CFStringRef)[UIFont
boldSystemFontOfSize:17].fontName, [UIFont boldSystemFontOfSize:17].pointSize, NULL);
  NSDictionary *boldAttributes = [NSDictionary dictionaryWithObjectsAndKeys:
                              (__bridge id)ctBoldFont,
                              (id)kCTFontAttributeName,
                              [UIColor blackColor].CGColor,
(id)kCTForegroundColorAttributeName, nil];
  CFRelease(ctBoldFont);

  CTFontRef ctNormalFont = CTFontCreateWithName((__bridge CFStringRef)[UIFont
systemFontOfSize:16].fontName, [UIFont systemFontOfSize:16].pointSize, NULL);
  NSDictionary *normalAttributes = [NSDictionary dictionaryWithObjectsAndKeys:
                              (__bridge id)ctNormalFont,
                              (id)kCTFontAttributeName,
                              [UIColor blackColor].CGColor,
(id)kCTForegroundColorAttributeName, nil];
  CFRelease(ctNormalFont);

  NSMutableAttributedString *string = [[NSMutableAttributedString alloc]
initWithString:@"iOS Dev Scout is a AWESOME iOS group!" attributes:normalAttributes];
  [string addAttributes:boldAttributes range:NSMakeRange(19, 7)];
  self.textLayer.string = string;
}
Composition



  CTFontRef ctNormalFont = CTFontCreateWithName((__bridge CFStringRef)[UIFont
systemFontOfSize:16].fontName, [UIFont systemFontOfSize:16].pointSize, NULL);
  NSDictionary *normalAttributes = [NSDictionary dictionaryWithObjectsAndKeys:
                              (__bridge id)ctNormalFont,
                              (id)kCTFontAttributeName,
                              [UIColor blackColor].CGColor,
(id)kCTForegroundColorAttributeName, nil];
  CFRelease(ctNormalFont);
Composition



  CTFontRef ctBoldFont = CTFontCreateWithName((__bridge CFStringRef)[UIFont
boldSystemFontOfSize:17].fontName, [UIFont boldSystemFontOfSize:17].pointSize, NULL);
  NSDictionary *boldAttributes = [NSDictionary dictionaryWithObjectsAndKeys:
                              (__bridge id)ctBoldFont,
                              (id)kCTFontAttributeName,
                              [UIColor blackColor].CGColor,
(id)kCTForegroundColorAttributeName, nil];
  CFRelease(ctBoldFont);
Composition



  NSMutableAttributedString *string = [[NSMutableAttributedString alloc]
initWithString:@"iOS Dev Scout is a AWESOME iOS group!" attributes:normalAttributes];
  [string addAttributes:boldAttributes range:NSMakeRange(19, 7)];
  self.textLayer.string = string;
What did we use?




•   kCTForegroundColorAttributeName

•   kCTFontAttributeName
What else available?


•   kCTCharacterShapeAttributeName

•   kCTKernAttributeName

•   kCTLigatureAttributeName

•   kCTParagraphStyleAttributeName

•   kCTStrokeWidthAttributeName

•   kCTStrokeColorAttributeName
What else available?

•   kCTSuperscriptAttributeName

•   kCTUnderlineColorAttributeName

•   kCTUnderlineStyleAttributeName

•   kCTVerticalFormsAttributeName

•   kCTGlyphInfoAttributeName

•   kCTRunDelegateAttributeName



•   NSLinkAttributeName (only on Mac)
What else available?

•   And that is just text.



•   Lot more for image rendering



•   Even lot more for animation



•   NSLinkAttributeName not available on iOS. You should look
    at OHAttributedLabel or play around with UIButtons
Demo 2 - Facebook
Performance tips
Performance tips


•   Use dispatch_once for almost any “constants”

    •   UIFont, UIBezierPath, UIColor etc.,
Performance tips


•   Use dispatch_once for almost any “constants”

    •   UIFont, UIBezierPath, UIColor etc.,
Performance tips


•   Use dispatch_once for almost any “constants”

    •   UIFont, UIBezierPath, UIColor etc.,



•   Use strptime* methods instead of NSDateFormatter

    •   No support for locale, but crazy fast
Thanks
       @mugunthkumar
    mugunth@steinlogic.com

         iostraining.sg



    Available for consulting
            services

     iOS App Development
          API Design
          Mobile UX

Weitere ähnliche Inhalte

Was ist angesagt?

MFF UK - Advanced iOS Topics
MFF UK - Advanced iOS TopicsMFF UK - Advanced iOS Topics
MFF UK - Advanced iOS Topics
Petr Dvorak
 
FI MUNI 2012 - iOS Basics
FI MUNI 2012 - iOS BasicsFI MUNI 2012 - iOS Basics
FI MUNI 2012 - iOS Basics
Petr Dvorak
 
Intro To JavaScript Unit Testing - Ran Mizrahi
Intro To JavaScript Unit Testing - Ran MizrahiIntro To JavaScript Unit Testing - Ran Mizrahi
Intro To JavaScript Unit Testing - Ran Mizrahi
Ran Mizrahi
 
Intro to JavaScript Testing
Intro to JavaScript TestingIntro to JavaScript Testing
Intro to JavaScript Testing
Ran Mizrahi
 

Was ist angesagt? (20)

Performance Optimization and JavaScript Best Practices
Performance Optimization and JavaScript Best PracticesPerformance Optimization and JavaScript Best Practices
Performance Optimization and JavaScript Best Practices
 
MFF UK - Advanced iOS Topics
MFF UK - Advanced iOS TopicsMFF UK - Advanced iOS Topics
MFF UK - Advanced iOS Topics
 
Javascript and Jquery Best practices
Javascript and Jquery Best practicesJavascript and Jquery Best practices
Javascript and Jquery Best practices
 
From Ruby to Scala
From Ruby to ScalaFrom Ruby to Scala
From Ruby to Scala
 
What's a macro?: Learning by Examples / Scalaのマクロに実用例から触れてみよう!
What's a macro?: Learning by Examples / Scalaのマクロに実用例から触れてみよう!What's a macro?: Learning by Examples / Scalaのマクロに実用例から触れてみよう!
What's a macro?: Learning by Examples / Scalaのマクロに実用例から触れてみよう!
 
Solid And Sustainable Development in Scala
Solid And Sustainable Development in ScalaSolid And Sustainable Development in Scala
Solid And Sustainable Development in Scala
 
Node.js vs Play Framework (with Japanese subtitles)
Node.js vs Play Framework (with Japanese subtitles)Node.js vs Play Framework (with Japanese subtitles)
Node.js vs Play Framework (with Japanese subtitles)
 
JavaFX 2 and Scala - Like Milk and Cookies (33rd Degrees)
JavaFX 2 and Scala - Like Milk and Cookies (33rd Degrees)JavaFX 2 and Scala - Like Milk and Cookies (33rd Degrees)
JavaFX 2 and Scala - Like Milk and Cookies (33rd Degrees)
 
FI MUNI 2012 - iOS Basics
FI MUNI 2012 - iOS BasicsFI MUNI 2012 - iOS Basics
FI MUNI 2012 - iOS Basics
 
Introduction to node.js by Ran Mizrahi @ Reversim Summit
Introduction to node.js by Ran Mizrahi @ Reversim SummitIntroduction to node.js by Ran Mizrahi @ Reversim Summit
Introduction to node.js by Ran Mizrahi @ Reversim Summit
 
Intro To JavaScript Unit Testing - Ran Mizrahi
Intro To JavaScript Unit Testing - Ran MizrahiIntro To JavaScript Unit Testing - Ran Mizrahi
Intro To JavaScript Unit Testing - Ran Mizrahi
 
Intro to JavaScript Testing
Intro to JavaScript TestingIntro to JavaScript Testing
Intro to JavaScript Testing
 
Practical JRuby
Practical JRubyPractical JRuby
Practical JRuby
 
Creating Dynamic Charts With JFreeChart
Creating Dynamic Charts With JFreeChartCreating Dynamic Charts With JFreeChart
Creating Dynamic Charts With JFreeChart
 
How and Where in GLORP
How and Where in GLORPHow and Where in GLORP
How and Where in GLORP
 
jQuery Objects
jQuery ObjectsjQuery Objects
jQuery Objects
 
[2015/2016] Require JS and Handlebars JS
[2015/2016] Require JS and Handlebars JS[2015/2016] Require JS and Handlebars JS
[2015/2016] Require JS and Handlebars JS
 
Building a real life application in node js
Building a real life application in node jsBuilding a real life application in node js
Building a real life application in node js
 
SenchaCon 2016: How to Auto Generate a Back-end in Minutes - Per Minborg, Emi...
SenchaCon 2016: How to Auto Generate a Back-end in Minutes - Per Minborg, Emi...SenchaCon 2016: How to Auto Generate a Back-end in Minutes - Per Minborg, Emi...
SenchaCon 2016: How to Auto Generate a Back-end in Minutes - Per Minborg, Emi...
 
Simpler Core Data with RubyMotion
Simpler Core Data with RubyMotionSimpler Core Data with RubyMotion
Simpler Core Data with RubyMotion
 

Andere mochten auch (6)

Text Layout With Core Text
Text Layout With Core TextText Layout With Core Text
Text Layout With Core Text
 
はじめて Phantom と遭遇して、闇雲に闘いを挑んでみた話 #kbkz_tech
はじめて Phantom と遭遇して、闇雲に闘いを挑んでみた話 #kbkz_techはじめて Phantom と遭遇して、闇雲に闘いを挑んでみた話 #kbkz_tech
はじめて Phantom と遭遇して、闇雲に闘いを挑んでみた話 #kbkz_tech
 
RxSwift x Realm
RxSwift x RealmRxSwift x Realm
RxSwift x Realm
 
アメブロの大規模システム刷新と それを支えるSpring
アメブロの大規模システム刷新と それを支えるSpringアメブロの大規模システム刷新と それを支えるSpring
アメブロの大規模システム刷新と それを支えるSpring
 
Type-safe Web APIs with Protocol Buffers in Swift at iOSCon
Type-safe Web APIs with Protocol Buffers in Swift at iOSConType-safe Web APIs with Protocol Buffers in Swift at iOSCon
Type-safe Web APIs with Protocol Buffers in Swift at iOSCon
 
絶対落ちないアプリの作り方
絶対落ちないアプリの作り方絶対落ちないアプリの作り方
絶対落ちないアプリの作り方
 

Ähnlich wie Hi performance table views with QuartzCore and CoreText

Cocoa Heads Tricity - Design Patterns
Cocoa Heads Tricity - Design PatternsCocoa Heads Tricity - Design Patterns
Cocoa Heads Tricity - Design Patterns
Maciej Burda
 
iOS Development: What's New
iOS Development: What's NewiOS Development: What's New
iOS Development: What's New
NascentDigital
 
Mongo db washington dc 2014
Mongo db washington dc 2014Mongo db washington dc 2014
Mongo db washington dc 2014
ikanow
 

Ähnlich wie Hi performance table views with QuartzCore and CoreText (20)

Implementing CATiledLayer
Implementing CATiledLayerImplementing CATiledLayer
Implementing CATiledLayer
 
CATiled Layer - Melbourne Cocoheads February 2012
CATiled Layer - Melbourne Cocoheads February 2012CATiled Layer - Melbourne Cocoheads February 2012
CATiled Layer - Melbourne Cocoheads February 2012
 
Awesome html with ujs, jQuery and coffeescript
Awesome html with ujs, jQuery and coffeescriptAwesome html with ujs, jQuery and coffeescript
Awesome html with ujs, jQuery and coffeescript
 
Cocoa Heads Tricity - Design Patterns
Cocoa Heads Tricity - Design PatternsCocoa Heads Tricity - Design Patterns
Cocoa Heads Tricity - Design Patterns
 
David Bilík: Anko – modern way to build your layouts?
David Bilík: Anko – modern way to build your layouts?David Bilík: Anko – modern way to build your layouts?
David Bilík: Anko – modern way to build your layouts?
 
Core animation
Core animationCore animation
Core animation
 
Medium TechTalk — iOS
Medium TechTalk — iOSMedium TechTalk — iOS
Medium TechTalk — iOS
 
Solid and Sustainable Development in Scala
Solid and Sustainable Development in ScalaSolid and Sustainable Development in Scala
Solid and Sustainable Development in Scala
 
React Native: Introduction
React Native: IntroductionReact Native: Introduction
React Native: Introduction
 
iOS Development: What's New
iOS Development: What's NewiOS Development: What's New
iOS Development: What's New
 
Programming iOS in C#
Programming iOS in C#Programming iOS in C#
Programming iOS in C#
 
Declarative UI on iOS without SwiftUI (中文)
Declarative UI on iOS without SwiftUI (中文)Declarative UI on iOS without SwiftUI (中文)
Declarative UI on iOS without SwiftUI (中文)
 
Mongo db washington dc 2014
Mongo db washington dc 2014Mongo db washington dc 2014
Mongo db washington dc 2014
 
Masterin Large Scale Java Script Applications
Masterin Large Scale Java Script ApplicationsMasterin Large Scale Java Script Applications
Masterin Large Scale Java Script Applications
 
SquiDB: a SQLite layer for Android - Jonathan Koren, Yahoo!
SquiDB: a SQLite layer for Android - Jonathan Koren, Yahoo!SquiDB: a SQLite layer for Android - Jonathan Koren, Yahoo!
SquiDB: a SQLite layer for Android - Jonathan Koren, Yahoo!
 
Titanium Alloy Tutorial
Titanium Alloy TutorialTitanium Alloy Tutorial
Titanium Alloy Tutorial
 
Build Mobile Application with React-Native
Build Mobile Application with React-NativeBuild Mobile Application with React-Native
Build Mobile Application with React-Native
 
Core Animation
Core AnimationCore Animation
Core Animation
 
CBDW2014 - MockBox, get ready to mock your socks off!
CBDW2014 - MockBox, get ready to mock your socks off!CBDW2014 - MockBox, get ready to mock your socks off!
CBDW2014 - MockBox, get ready to mock your socks off!
 
Getting started with titanium
Getting started with titaniumGetting started with titanium
Getting started with titanium
 

Mehr von Mugunth Kumar (6)

Using CoreML to Push the Limits of your App
Using CoreML to Push the Limits of your AppUsing CoreML to Push the Limits of your App
Using CoreML to Push the Limits of your App
 
The new Apple TV and the tvOS
The new Apple TV and the tvOSThe new Apple TV and the tvOS
The new Apple TV and the tvOS
 
App store economics
App store economicsApp store economics
App store economics
 
Designing your API Server for mobile apps
Designing your API Server for mobile appsDesigning your API Server for mobile apps
Designing your API Server for mobile apps
 
My experience as a indie consultant
My experience as a indie consultant My experience as a indie consultant
My experience as a indie consultant
 
In App Purchases
In  App  PurchasesIn  App  Purchases
In App Purchases
 

Kürzlich hochgeladen

Kürzlich hochgeladen (20)

Apidays New York 2024 - Accelerating FinTech Innovation by Vasa Krishnan, Fin...
Apidays New York 2024 - Accelerating FinTech Innovation by Vasa Krishnan, Fin...Apidays New York 2024 - Accelerating FinTech Innovation by Vasa Krishnan, Fin...
Apidays New York 2024 - Accelerating FinTech Innovation by Vasa Krishnan, Fin...
 
Apidays New York 2024 - The Good, the Bad and the Governed by David O'Neill, ...
Apidays New York 2024 - The Good, the Bad and the Governed by David O'Neill, ...Apidays New York 2024 - The Good, the Bad and the Governed by David O'Neill, ...
Apidays New York 2024 - The Good, the Bad and the Governed by David O'Neill, ...
 
Powerful Google developer tools for immediate impact! (2023-24 C)
Powerful Google developer tools for immediate impact! (2023-24 C)Powerful Google developer tools for immediate impact! (2023-24 C)
Powerful Google developer tools for immediate impact! (2023-24 C)
 
Apidays Singapore 2024 - Modernizing Securities Finance by Madhu Subbu
Apidays Singapore 2024 - Modernizing Securities Finance by Madhu SubbuApidays Singapore 2024 - Modernizing Securities Finance by Madhu Subbu
Apidays Singapore 2024 - Modernizing Securities Finance by Madhu Subbu
 
TrustArc Webinar - Unlock the Power of AI-Driven Data Discovery
TrustArc Webinar - Unlock the Power of AI-Driven Data DiscoveryTrustArc Webinar - Unlock the Power of AI-Driven Data Discovery
TrustArc Webinar - Unlock the Power of AI-Driven Data Discovery
 
Repurposing LNG terminals for Hydrogen Ammonia: Feasibility and Cost Saving
Repurposing LNG terminals for Hydrogen Ammonia: Feasibility and Cost SavingRepurposing LNG terminals for Hydrogen Ammonia: Feasibility and Cost Saving
Repurposing LNG terminals for Hydrogen Ammonia: Feasibility and Cost Saving
 
Boost Fertility New Invention Ups Success Rates.pdf
Boost Fertility New Invention Ups Success Rates.pdfBoost Fertility New Invention Ups Success Rates.pdf
Boost Fertility New Invention Ups Success Rates.pdf
 
Data Cloud, More than a CDP by Matt Robison
Data Cloud, More than a CDP by Matt RobisonData Cloud, More than a CDP by Matt Robison
Data Cloud, More than a CDP by Matt Robison
 
Automating Google Workspace (GWS) & more with Apps Script
Automating Google Workspace (GWS) & more with Apps ScriptAutomating Google Workspace (GWS) & more with Apps Script
Automating Google Workspace (GWS) & more with Apps Script
 
FWD Group - Insurer Innovation Award 2024
FWD Group - Insurer Innovation Award 2024FWD Group - Insurer Innovation Award 2024
FWD Group - Insurer Innovation Award 2024
 
Connector Corner: Accelerate revenue generation using UiPath API-centric busi...
Connector Corner: Accelerate revenue generation using UiPath API-centric busi...Connector Corner: Accelerate revenue generation using UiPath API-centric busi...
Connector Corner: Accelerate revenue generation using UiPath API-centric busi...
 
Strategies for Unlocking Knowledge Management in Microsoft 365 in the Copilot...
Strategies for Unlocking Knowledge Management in Microsoft 365 in the Copilot...Strategies for Unlocking Knowledge Management in Microsoft 365 in the Copilot...
Strategies for Unlocking Knowledge Management in Microsoft 365 in the Copilot...
 
ProductAnonymous-April2024-WinProductDiscovery-MelissaKlemke
ProductAnonymous-April2024-WinProductDiscovery-MelissaKlemkeProductAnonymous-April2024-WinProductDiscovery-MelissaKlemke
ProductAnonymous-April2024-WinProductDiscovery-MelissaKlemke
 
Navi Mumbai Call Girls 🥰 8617370543 Service Offer VIP Hot Model
Navi Mumbai Call Girls 🥰 8617370543 Service Offer VIP Hot ModelNavi Mumbai Call Girls 🥰 8617370543 Service Offer VIP Hot Model
Navi Mumbai Call Girls 🥰 8617370543 Service Offer VIP Hot Model
 
Polkadot JAM Slides - Token2049 - By Dr. Gavin Wood
Polkadot JAM Slides - Token2049 - By Dr. Gavin WoodPolkadot JAM Slides - Token2049 - By Dr. Gavin Wood
Polkadot JAM Slides - Token2049 - By Dr. Gavin Wood
 
EMPOWERMENT TECHNOLOGY GRADE 11 QUARTER 2 REVIEWER
EMPOWERMENT TECHNOLOGY GRADE 11 QUARTER 2 REVIEWEREMPOWERMENT TECHNOLOGY GRADE 11 QUARTER 2 REVIEWER
EMPOWERMENT TECHNOLOGY GRADE 11 QUARTER 2 REVIEWER
 
Apidays New York 2024 - The value of a flexible API Management solution for O...
Apidays New York 2024 - The value of a flexible API Management solution for O...Apidays New York 2024 - The value of a flexible API Management solution for O...
Apidays New York 2024 - The value of a flexible API Management solution for O...
 
Web Form Automation for Bonterra Impact Management (fka Social Solutions Apri...
Web Form Automation for Bonterra Impact Management (fka Social Solutions Apri...Web Form Automation for Bonterra Impact Management (fka Social Solutions Apri...
Web Form Automation for Bonterra Impact Management (fka Social Solutions Apri...
 
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
 
MS Copilot expands with MS Graph connectors
MS Copilot expands with MS Graph connectorsMS Copilot expands with MS Graph connectors
MS Copilot expands with MS Graph connectors
 

Hi performance table views with QuartzCore and CoreText

  • 1. Hi-Performance Table Views with QuartzCore and CoreText Beginners guide to an advanced concept Mugunth Kumar Steinlogic Consulting and Training Pte Ltd
  • 3. About me • Author of the iOS 5, iOS 6 Programming: Pushing the Limits book - Reached the top 100 books in Amazon’s Computer and Technology books list • Trainer - Conducts training on iOS programming at iOSTraining.sg. • Developer • MKNetworkKit (1200+ watchers) • MKStoreKit (700+ watchers) • Several other “minor” projects with 200+ watchers • Clients include startups in Singapore like Squiryl, Found and MNC’s including Microsoft Redmond, Oracle and such.
  • 4. Why? • What makes apps pleasant to use? • Fast scrolling • Why?
  • 6. Why? • iPhone is a direct manipulation device
  • 7. Why? • iPhone is a direct manipulation device • iPhone screen is closer to your eye than your HDTV or your computer monitor
  • 8. Why? • iPhone is a direct manipulation device • iPhone screen is closer to your eye than your HDTV or your computer monitor • 60 frames per second = 16.66ms per frame
  • 9. Why? • iPhone is a direct manipulation device • iPhone screen is closer to your eye than your HDTV or your computer monitor • 60 frames per second = 16.66ms per frame • Anything less, you will get a headache
  • 11. Agenda • Why?
  • 12. Agenda • Why? • Three different methods
  • 13. Agenda • Why? • Three different methods • Pros and Cons
  • 14. Agenda • Why? • Three different methods • Pros and Cons • QuartzCore/CoreText introduction
  • 15. Agenda • Why? • Three different methods • Pros and Cons • QuartzCore/CoreText introduction • A simple table view cell example
  • 16. Agenda • Why? • Three different methods • Pros and Cons • QuartzCore/CoreText introduction • A simple table view cell example • What else can you build? - Facebook style news feed
  • 17. Compositing Table View Cells • UITableViewCell • Subviews (UILabel, UIImageView)
  • 19. Pros/Cons • Advantages • Programmatically easy • Fast for compositing images • Built in cells are rendered differently
  • 20. Pros/Cons • Advantages • Programmatically easy • Fast for compositing images • Built in cells are rendered differently • Drawbacks • Slow for text based tables
  • 21. Direct Drawing • UITableViewCell drawRect • NSString -drawInRect, drawAtPoint • UIImage -drawInRect, drawAtPoint
  • 23. Pros/Cons • Advantages • Fast • Really fast!
  • 24. Pros/Cons • Advantages • Fast • Really fast! • Drawbacks • Difficult (Annoyingly complex to build complex layouts) • CGContextDrawImage is really slow compared to using UIImageView
  • 25. Hybrid • A mix of drawRect + UIImageViews
  • 26. Cons
  • 27. Cons • Still cannot render shadows around images views
  • 28. Cons • Still cannot render shadows around images views self.view.layer.masksToBounds = NO; self.view.layer.shadowColor = [UIColor blackColor].CGColor; self.view.layer.shadowOffset = CGSizeMake(0.0f, -1.0f); self.view.layer.shadowOpacity = 0.5f; self.view.layer.shadowRadius = 1.0f;
  • 29. Cons • Still cannot render shadows around images views self.view.layer.masksToBounds = NO; self.view.layer.shadowColor = [UIColor blackColor].CGColor; self.view.layer.shadowOffset = CGSizeMake(0.0f, -1.0f); self.view.layer.shadowOpacity = 0.5f; self.view.layer.shadowRadius = 1.0f; • The above code is dog slow. • Good for views, very bad for table view cells or collection view cells
  • 30. Is there a better way? • QuartzCore.framework • CoreText.framework
  • 32. Pros/Cons • Advantages • Fast • Can render text and image within our 16ms deadline • Rendering highly customized text is hard
  • 33. Pros/Cons • Advantages • Fast • Can render text and image within our 16ms deadline • Rendering highly customized text is hard This is BOLD and this is in italics.
  • 34. QuartzCore • CALayer • CATextLayer • CAGradientLayer • CAShapeLayer
  • 35. CoreText • NSAttributedString • NSMutableAttributedString • UIBezierPath
  • 36. Composition @interface SCTCoreTextCell @property (strong, nonatomic) CATextLayer *nameTextLayer; @property (strong, nonatomic) CATextLayer *timeTextLayer; @property (strong, nonatomic) CALayer *avatarImageLayer; @property (strong, nonatomic) CALayer *avatarImageShadowLayer; @property (strong, nonatomic) CATextLayer *descriptionTextLayer; @end
  • 37. CALayer - Images self.backgroundLayer = [CALayer layer]; self.backgroundLayer.frame = CGRectMake(0, 0, 320, 150); self.backgroundLayer.contentsScale = [[UIScreen mainScreen] scale]; self.backgroundLayer.actions = [NSDictionary actionsDictionary]; self.backgroundLayer.contents = (id) backgroundImage.CGImage; self.backgroundLayer.contentsCenter = CGRectMake(1.0/ backgroundImage.size.width, 8.0/backgroundImage.size.height, 1.0/ backgroundImage.size.width,1.0/backgroundImage.size.height); self.backgroundLayer.contentsGravity = kCAGravityResize; [self.contentView.layer addSublayer:self.backgroundLayer];
  • 38. CATextLayer - Text self.nameTextLayer = [CATextLayer layer]; self.nameTextLayer.frame = CGRectMake(65, 3, 240, 21); self.nameTextLayer.alignmentMode = kCAAlignmentLeft; self.nameTextLayer.wrapped = YES; self.nameTextLayer.contentsScale = [[UIScreen mainScreen] scale]; self.nameTextLayer.actions = [NSDictionary actionsDictionary]; [self.contentView.layer addSublayer:self.nameTextLayer];
  • 39. Composition +(NSDictionary*) actionsDictionary { return @{ @"onOrderIn" : [NSNull null], @"onOrderOut" : [NSNull null], @"sublayers" : [NSNull null], @"contents" : [NSNull null], @"position" : [NSNull null], @"bounds" : [NSNull null], @"onLayout" : [NSNull null], @"hidden" : [NSNull null], }; }); }
  • 41. Contents • CALayer • Mostly Images • Rendering a graphics context in background
  • 42. Contents • CALayer • Mostly Images • Rendering a graphics context in background
  • 43. Contents • CALayer • Mostly Images • Rendering a graphics context in background • CAGradientLayer • Adding gradient backgrounds
  • 45. Contents • CAShapeLayer • Mostly Paths • Use UIBezierPath to create a path
  • 46. Contents • CAShapeLayer • Mostly Paths • Use UIBezierPath to create a path
  • 47. Contents • CAShapeLayer • Mostly Paths • Use UIBezierPath to create a path • CATextLayer (Most useful + complicated) • Text (NSAttributedString)
  • 48. NSAttributedString • The basic building block for complex text rendering • NSAttributedString = NSString + Attributes Dictionary
  • 49. Demo 1 - Simple Bold
  • 50. Composition -(void) setText { CTFontRef ctBoldFont = CTFontCreateWithName((__bridge CFStringRef)[UIFont boldSystemFontOfSize:17].fontName, [UIFont boldSystemFontOfSize:17].pointSize, NULL); NSDictionary *boldAttributes = [NSDictionary dictionaryWithObjectsAndKeys: (__bridge id)ctBoldFont, (id)kCTFontAttributeName, [UIColor blackColor].CGColor, (id)kCTForegroundColorAttributeName, nil]; CFRelease(ctBoldFont); CTFontRef ctNormalFont = CTFontCreateWithName((__bridge CFStringRef)[UIFont systemFontOfSize:16].fontName, [UIFont systemFontOfSize:16].pointSize, NULL); NSDictionary *normalAttributes = [NSDictionary dictionaryWithObjectsAndKeys: (__bridge id)ctNormalFont, (id)kCTFontAttributeName, [UIColor blackColor].CGColor, (id)kCTForegroundColorAttributeName, nil]; CFRelease(ctNormalFont); NSMutableAttributedString *string = [[NSMutableAttributedString alloc] initWithString:@"iOS Dev Scout is a AWESOME iOS group!" attributes:normalAttributes]; [string addAttributes:boldAttributes range:NSMakeRange(19, 7)]; self.textLayer.string = string; }
  • 51. Composition CTFontRef ctNormalFont = CTFontCreateWithName((__bridge CFStringRef)[UIFont systemFontOfSize:16].fontName, [UIFont systemFontOfSize:16].pointSize, NULL); NSDictionary *normalAttributes = [NSDictionary dictionaryWithObjectsAndKeys: (__bridge id)ctNormalFont, (id)kCTFontAttributeName, [UIColor blackColor].CGColor, (id)kCTForegroundColorAttributeName, nil]; CFRelease(ctNormalFont);
  • 52. Composition CTFontRef ctBoldFont = CTFontCreateWithName((__bridge CFStringRef)[UIFont boldSystemFontOfSize:17].fontName, [UIFont boldSystemFontOfSize:17].pointSize, NULL); NSDictionary *boldAttributes = [NSDictionary dictionaryWithObjectsAndKeys: (__bridge id)ctBoldFont, (id)kCTFontAttributeName, [UIColor blackColor].CGColor, (id)kCTForegroundColorAttributeName, nil]; CFRelease(ctBoldFont);
  • 53. Composition NSMutableAttributedString *string = [[NSMutableAttributedString alloc] initWithString:@"iOS Dev Scout is a AWESOME iOS group!" attributes:normalAttributes]; [string addAttributes:boldAttributes range:NSMakeRange(19, 7)]; self.textLayer.string = string;
  • 54. What did we use? • kCTForegroundColorAttributeName • kCTFontAttributeName
  • 55. What else available? • kCTCharacterShapeAttributeName • kCTKernAttributeName • kCTLigatureAttributeName • kCTParagraphStyleAttributeName • kCTStrokeWidthAttributeName • kCTStrokeColorAttributeName
  • 56. What else available? • kCTSuperscriptAttributeName • kCTUnderlineColorAttributeName • kCTUnderlineStyleAttributeName • kCTVerticalFormsAttributeName • kCTGlyphInfoAttributeName • kCTRunDelegateAttributeName • NSLinkAttributeName (only on Mac)
  • 57. What else available? • And that is just text. • Lot more for image rendering • Even lot more for animation • NSLinkAttributeName not available on iOS. You should look at OHAttributedLabel or play around with UIButtons
  • 58. Demo 2 - Facebook
  • 60. Performance tips • Use dispatch_once for almost any “constants” • UIFont, UIBezierPath, UIColor etc.,
  • 61. Performance tips • Use dispatch_once for almost any “constants” • UIFont, UIBezierPath, UIColor etc.,
  • 62. Performance tips • Use dispatch_once for almost any “constants” • UIFont, UIBezierPath, UIColor etc., • Use strptime* methods instead of NSDateFormatter • No support for locale, but crazy fast
  • 63. Thanks @mugunthkumar mugunth@steinlogic.com iostraining.sg Available for consulting services iOS App Development API Design Mobile UX