https://github.com/Starkrimson/Oh.Swift

💡Extension

Bundle

Bundle.oh.displayName
Bundle.oh.marketingVersion
Bundle.oh.buildVersion

CGFloat

let size = CGSize(width: .oh.screenWidth, height: .oh.screenHeight)

String

title = "demo".oh.localized()
title = "demo".oh.localized("foo", "bar")

title = .oh.appName

UIApplication

UIApplication.oh.openSettings()

UICollectionView

// Register and dequeue UICollectionViewCell
collectionView.oh.register(UICollectionViewCell.self)
let cell = collectionView.oh.dequeue(UICollectionViewCell.self, for: indexPath)

// Register and dequeue UICollectionReusableView
collectionView.oh.register(UICollectionReusableView.self, for: "kind")
let reusableView = collectionView.oh.dequeue(UICollectionReusableView.self, of: "kind", for: indexPath)

UIColor

view.backgroundColor = .oh.hex(0xFFFFFF)
view.backgroundColor = .oh.random

UIScreen

UIScreen.oh.width
UIScreen.oh.height

UIScreen.oh.portraitWidth
UIScreen.oh.landscapeWidth

UITableView

// Register and dequeue UITableViewCell
tableView.oh.register(UITableViewCell.self)
let cell = tableView.oh.dequeue(UITableViewCell.self)

💡Property Wrapper

UserDefaultsWrapper

import OhSwift

@UserDefaultsWrapper("oh.swift.toggle", defaultValue: true)
var toggle: Bool!

// UserDefaults.standard.bool(forKey: "oh.swift.toggle")
"toggle \\(toggle!)"

// UserDefaults.standard.set(false, forKey: "oh.swift.toggle")
// UserDefaults.standard.synchronize()
toggle = false

CodableDefaultWrapper

struct Model: Codable {
    @Default<String> var text: String
    @Default<Int> var integer: Int
    @Default<Double> var decimal: Double
		@Default.True var flag: Bool
}

// ...

let jsonString = """
                 {
                    "text1": "hello world!",
                    "integer": 99,
                    "decimal": 66
                 }
                 """
do {
    let model = try JSONDecoder().decode(Model.self, from: jsonString.data(using: .utf8)!)
		print(model) // text = "", integer = 99, decimal = 66.0, flag = true
} catch {
    print(error.localizedDescription)
}

💡Modifier

UIView

let testView = UIView.oh.new { make in
    make.background(color: .white)
        .border(width: 10)
        .corner(radius: 20)
    if #available(iOS 11.0, *) {
        make.corner(radius: 20, corners: [.topLeft, .bottomRight])
    }
    make.rawValue.frame = .init(x: 50, y: 650, width: 100, height: 100)
}

UIButton

UIButton(frame: .init(x: 310, y: 650, width: 100, height: 100))
    .oh.modifier
    .superView(view)
    .title("Button")
    .titleColor(.oh.random)
    .font(ofSize: 20, weight: .semibold)
    .action(for: .touchDown) {
        print("...")
    }

💡RxSwift Extension

/// disposeBag
button.rx.tap
    .subscribe()
    .disposed(by: rx.disposeBag)

/// 简化 items(cellIdentifier:,cellType:)
/// 可配合 tableView.oh.register(UITableViewCell.self) 使用
Observable.just(dataSource.map { $0.items }.flatMap { $0 } )
    .bind(to: tableView.rx.items(cell: UITableViewCell.self)) { (row, element, cell) in
        cell.textLabel?.text = element
    }
    .disposed(by: rx.disposeBag)

/// 在原 modelSelected 基础上返回 IndexPath
tableView.rx.modelSelectedAtIndexPath(String.self)
    .subscribe(onNext: { (element, indexPath) in
        print("\\(element) \\(indexPath)")
    })
    .disposed(by: rx.disposeBag)