• Stars
    star
    1,250
  • Rank 37,587 (Top 0.8 %)
  • Language
    Swift
  • License
    MIT License
  • Created over 9 years ago
  • Updated about 3 years ago

Reviews

There are no reviews yet. Be the first to send feedback to the community and the maintainers!

Repository Details

Simple static table views for iOS in Swift.

Static Logo

Version Status Swift Version Carthage compatible

Simple static table views for iOS in Swift. Static's goal is to separate model data from presentation. Rows and Sections are your “view models” for your cells. You simply specify a cell class to use and that handles all of the presentation. See the usage section below for details.

Version Compatibility

Swift Version Static Version
5.0+ 4.0.2
4.2+ 3.0.1
3.2+ 2.1
3.0.1 2.0.1
3.0 2.0
2.3 1.2
2.2 1.1
2.0 - 2.1 1.0

Installation

Carthage

Carthage is the recommended way to install Static. Add the following to your Cartfile:

github "venmo/Static"

CocoaPods

CocoaPods is a dependency manager for Cocoa projects. To install Static with CocoaPods:

Make sure CocoaPods is installed (Static requires version 0.37 or greater).

Update your Podfile to include the following:

use_frameworks!
pod 'Static', git: 'https://github.com/venmo/Static'

Run pod install.

Manual

For manual installation, it's recommended to add the project as a subproject to your project or workspace and adding the appropriate framework as a target dependency.

Usage

An example app is included demonstrating Static's functionality.

Getting Started

To use Static, you need to define Rows and Sections to describe your data. Here's a simple example:

import Static

Section(rows: [
    Row(text: "Hello")
])

You can configure Sections and Rows for anything you want. Here's another example:

Section(header: "Money", rows: [
    Row(text: "Balance", detailText: "$12.00", accessory: .disclosureIndicator, selection: {
        // Show statement
    }),
    Row(text: "Transfer to Bank…", cellClass: ButtonCell.self, selection: {
        [unowned self] in
        let viewController = ViewController()
        self.presentViewController(viewController, animated: true, completion: nil)
    })
], footer: "Transfers usually arrive within 1-3 business days.")

Since this is Swift, we can provide instance methods instead of inline blocks for selections. This makes things really nice. You don't have to switch on index paths in a tableView:didSelectRowAtIndexPath: any more!

Customizing Appearance

The Row never has access to the cell. This is by design. The Row shouldn't care about its appearance other than specifying what will handle it. In practice, this has been really nice. Our cells have one responsibility.

There are several custom cells provided:

  • Value1Cell — This is the default cell. It's a plain UITableViewCell with the .Value1 style.
  • Value2Cell — Plain UITableViewCell with the .Value2 style.
  • SubtitleCell — Plain UITableViewCell with the .Subtitle style.
  • ButtonCell — Plain UITableViewCell with the .Default style. The textLabel's textColor is set to the cell's tintColor.

All of these conform to Cell. The gist of the protocol is one method:

func configure(row row: Row)

This gets called by DataSource (which we'll look at more in a minute) to set the row on the cell. There is a default implementation provided by the protocol that simply sets the Row's text on the cell's textLabel, etc. If you need to do custom things, this is a great place to hook in.

Row also has a context property. You can put whatever you want in here that the cell needs to know. You should try to use this as sparingly as possible.

Custom Row Accessories

Row has an accessory property that is an Accessory enum. This has cases for all of UITableViewCellAccessoryType. Here's a row with a checkmark:

Row(text: "Buy milk", accessory: .checkmark)

Easy enough. Some of the system accessory types are selectable (like that little i button with a circle around it). You can make those and handle the selection like this:

Row(text: "Sam Soffes", accessory: .detailButton({
  // Show info about this contact
}))

Again, you could use whatever function here. Instance methods are great for this.

There is an additional case called .view that takes a custom view. Here's a Row with a custom accessory view:

Row(text: "My Profile", accessory: .view(someEditButton))

Custom Section Header & Footer Views

Section has properties for header and footer. These take a Section.Extremity. This is an enum with Title and View cases. Extremity is StringLiteralConvertible you can simply specify strings if you want titles like we did the Getting Started section.

For a custom view, you can simply specify the View case:

Section(header: .view(yourView))

The height returned to the table view will be the view's bounds.height so be sure it's already sized properly.

Working with the Data Source

To hook up your Sections and Rows to a table view, simply initialize a DataSource:

let dataSource = DataSource()
dataSource.sections = [
    Section(rows: [
        Row(text: "Hello")
    ])
]

Now assign your table view:

dataSource.tableView = tableView

Easy as that! If you modify your data source later, it will automatically update the table view for you. It is important that you don't change the table view's dataSource or delegate. The DataSource needs to be those so it can handle events correctly. The purpose of Static is to abstract all of that away from you.

Wrapping Up

There is a provided TableViewController that sets up a DataSource for you. Here's a short example:

class SomeViewController: TableViewController {
    override func viewDidLoad() {
        super.viewDidLoad()
        dataSource.sections = [
            Section(rows: [
                Row(text: "Hi")
            ]),
            // ...
        ]
    }
}

Enjoy.

More Repositories

1

synx

A command-line tool that reorganizes your Xcode project folder to match your Xcode groups
Ruby
6,082
star
2

VENTouchLock

A Touch ID and Passcode framework used in the Venmo app.
Objective-C
965
star
3

business-rules

Python DSL for setting up business intelligence rules that can be configured without code
Python
891
star
4

VENTokenField

Easy-to-use token field that is used in the Venmo app.
Objective-C
793
star
5

VENCalculatorInputView

Calculator keyboard used in the Venmo iOS app
Objective-C
763
star
6

DVR

Network testing for Swift
Swift
651
star
7

tooltip-view

Dead simple Android Tooltip Views
Java
486
star
8

DryDock-iOS

DEPRECATED: An open-source internal installer app
433
star
9

VENSeparatorView

Jagged border separators on UIViews used in the Venmo app.
Objective-C
379
star
10

VENVersionTracker

Objective-C
300
star
11

business-rules-ui

A JavaScript library for building out the logic and UI for business rules.
JavaScript
197
star
12

VENPromotionsManager

iOS Library to perform location & time-based promotions.
Objective-C
197
star
13

cursor-utils

A library that encapsulates the repeatable actions of Android Cursors.
Java
195
star
14

venmo-ios-sdk

Make and accept payments in your iOS app via Venmo
Objective-C
176
star
15

react-html-document

A foundational React component useful for rendering full html documents on the server.
JavaScript
155
star
16

VENExperimentsManager

An Objective-C library enabling easy implementation of feature experiments on iOS allowing users to opt in and out of experiments at will.
Objective-C
76
star
17

slouch

A lightweight Python framework for building cli-inspired Slack bots.
Python
71
star
18

xcode_server

Xcode Bot client
Ruby
58
star
19

android-pin

An easy drop-in PIN controller for Android
Java
42
star
20

app-switch-android

Java
35
star
21

VENCore

Core Objective-C client library for the Venmo API
Objective-C
27
star
22

QuizTrain

Swift Framework for TestRail's API
Swift
19
star
23

feature_ramp

Toggling and ramping features via a lightweight Redis backend.
Python
18
star
24

btnamespace

A Python library to isolate state on the Braintree sandbox during testing.
Python
17
star
25

flaskeleton

Python
13
star
26

swaggergenerator

Create swagger / OpenAPI schemas from example interactions.
Python
11
star
27

tornado-stub-client

A stub library for making requests with tornado's AsyncHTTPClient
Python
9
star
28

venmo.github.io

Old Venmo Engineering Blog
CSS
8
star
29

nose-detecthttp

A nose plugin that can detect tests making external http calls.
Python
7
star
30

puppet-consulr

Dynamic puppet manifests using consul
Ruby
5
star
31

puppet-sentry

Puppet module for managing the Sentry realtime event logging and aggregation platform
Ruby
4
star
32

python3-avro

Copies the python3 client implementation from our fork of apache's avro project.
Python
4
star
33

nose-seed-faker

A nose plugin that seeds the faker package
Python
4
star
34

QuizTrainExample

Example of how to use QuizTrain with Unit Tests and UI Tests on iOS
Swift
3
star
35

single-click-highlightable

HOC for React that allows users to highlight text on elements without triggering the onClick handler
JavaScript
3
star
36

puppet-hound

Puppet hound module
Puppet
2
star
37

nose-timeout

Nose plugin for aborting long running tests
Python
1
star
38

foundations-interview

This is a test repository used in Foundations team interview process
JavaScript
1
star