Skip to content

Instantly share code, notes, and snippets.

@Jxrgxn
Forked from codyrobb/CGRect+Additions.swift
Created February 5, 2016 10:41
Show Gist options
  • Save Jxrgxn/c6a001f4681d1cbb7ea6 to your computer and use it in GitHub Desktop.
Save Jxrgxn/c6a001f4681d1cbb7ea6 to your computer and use it in GitHub Desktop.
CGRect Alignment Extension
//
// CGGeometry+Additions.swift
// TokenField
//
// Created by Cody Robertson on 2/4/16.
// Copyright © 2016 Notion AI, Inc. All rights reserved.
//
import Foundation
import UIKit
public extension CGRect {
public enum Edge {
case Bottom
case Left
case Right
case Top
func toCGRectEdge() -> CGRectEdge {
switch self {
case .Bottom: return .MaxYEdge
case .Left: return .MinXEdge
case .Right: return .MaxXEdge
case .Top: return .MinYEdge
}
}
}
/**
This method creates a new CGRect by strecting the specified `edge` to align with the `toEdge`.
The result can end up with a negative width/height.
- Note: This method DOES mutate the size of the rect.
- SeeAlso: `algin(edge:toEdge:ofRect:withOffset:)`
*/
public func pin(edge: Edge, toEdge: Edge, ofRect rect: CGRect, withOffset offset: CGFloat = 0) -> CGRect {
switch (edge, toEdge) {
case (.Left, .Left):
return CGRect(x: rect.minX - offset, y: minY, width: width + (minX - rect.minX) + offset, height: height)
case (.Left, .Right):
return CGRect(x: rect.maxX + offset, y: minY, width: width + (minX - rect.maxX) - offset, height: height)
case (.Top, .Top):
return CGRect(x: minX, y: rect.minY - offset, width: width, height: height + (minY - rect.minY) + offset)
case (.Top, .Bottom):
return CGRect(x: minX, y: rect.maxY + offset, width: width, height: height + (minY - rect.maxY) - offset)
case (.Right, .Left):
return CGRect(x: rect.minX, y: minY, width: width - (maxX - rect.minX) + offset, height: height)
case (.Right, .Right):
return CGRect(x: minX, y: minY, width: width - (maxX - rect.maxX) - offset, height: height)
case (.Bottom, .Top):
return CGRect(x: minX, y: minY, width: width, height: height - (maxY - rect.minY) + offset)
case (.Bottom, .Bottom):
return CGRect(x: minX, y: minY, width: width, height: height - (maxY - rect.maxY) - offset)
default:
preconditionFailure("Cannot align to this combination of edges")
}
}
/**
This method creates a new CGRect by aligning the specified `edge` to the `toEdge`.
- SeeAlso: `pin(edge:toEdge:ofRect:withOffset:)`
*/
public func align(edge: Edge, toEdge: Edge, ofRect rect: CGRect, withOffset offset: CGFloat = 0) -> CGRect {
return CGRect(origin: alignOrigin(edge, toEdge: toEdge, ofRect: rect, withOffset: offset), size: size)
}
private func alignOrigin(edge: Edge, toEdge: Edge, ofRect rect: CGRect, withOffset offset: CGFloat) -> CGPoint {
switch (edge, toEdge) {
case (.Left, .Left):
return CGPoint(x: rect.minX + offset, y: minY)
case (.Left, .Right):
return CGPoint(x: rect.maxX + offset, y: minY)
case (.Top, .Top):
return CGPoint(x: minX, y: rect.minY + offset)
case (.Top, .Bottom):
return CGPoint(x: minX, y: rect.maxY + offset)
case (.Right, .Left):
return CGPoint(x: rect.minX - width - offset, y: minY)
case (.Right, .Right):
return CGPoint(x: rect.maxX - width - offset, y: minY)
case (.Bottom, .Top):
return CGPoint(x: minX, y: rect.minY - height - offset)
case (.Bottom, .Bottom):
return CGPoint(x: minX, y: rect.maxY - height - offset)
default:
preconditionFailure("Cannot align to this combination of edges")
}
}
}
extension CGRect {
public enum Direction {
case Up
case Down
case Left
case Right
}
public func move(direction: Direction, amount: CGFloat) -> CGRect {
switch direction {
case .Up: return CGRectMake(minX, minY - amount, width, height)
case .Down: return CGRectMake(minX, minY + amount, width, height)
case .Left: return CGRectMake(minX - amount, minY, width, height)
case .Right: return CGRectMake(minX + amount, minY, width, height)
}
}
public func expand(direction: Direction, amount: CGFloat) -> CGRect {
switch direction {
case .Up: return CGRectMake(minX, minY - amount, width, height + amount)
case .Down: return CGRectMake(minX, minY, width, height + amount)
case .Left: return CGRectMake(minX - amount, minY, width + amount, height)
case .Right: return CGRectMake(minX, minY, width + amount, height)
}
}
}
extension CGRect {
public enum Dimension {
case Height
case Width
}
public func setDimension(dimension: Dimension, toSize size: CGFloat) -> CGRect {
switch dimension {
case .Height: return CGRectMake(minX, minY, width, size)
case .Width: return CGRectMake(minX, minY, size, height)
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment