A small, flexible framework for expressing NSAttributedString values structurally.
label.attributedText = [
"This is a string with ",
UIColor.blueColor().foregroundAttribute([
"blue ",
100.kernAttribute(
"kerned"
),
" text"
].join()),
" and ",
UIColor.redColor().foregroundAttribute([
NSAttributedString(string: "red", attributes: ["Custom": "Value"]),
" text"
].join()),
"."
].join().attributedStringAttributed defines the AttributedStringConvertible protocol, which allows clients to create an NSAttributedString value with the attributedString property. String and NSAttributedString are extended to conform to this protocol.
The most important values in Attributed are attribute functions, which take an AttributedStringConvertible value as a parameter, and return a second AttributedStringConvertible value, with additional attributes applied. A basic attribute function can be created with the attribute(name:value:) function:
let attributeFunction = attribute(name: "Foo", value: "Bar")
let attributedString = attributeFunction("Baz").attributedStringMultiple attributes can also be set at once:
let attributeFunction = attributes(values: [
"Foo": "Bar",
"Bar": "Foo"
])
let attributedString = attributeFunction("Baz").attributedStringThe AttributeFunction typealias is provided to define this function type.
The core of Attributed's functionality is in the extensions added to support the standard attributes.
NSColor and UIColor are extended with these attribute functions:
foregroundAttribute, which maps toNSForegroundColorAttributeName.backgroundAttribute, which maps toNSBackgroundColorAttributeName.underlineAttribute, which maps toNSUnderlineColorAttributeName.strikethroughAttribute, which maps toNSStrikethroughColorAttributeName.
These additional framework types are extended with attribute functions:
NSCursor, on OS X only:attributes, which maps toNSCursorAttributeName.NSFont/UIFont:attribute, which maps toNSFontAttributeName.NSTextAttachment:attribute, which maps toNSAttachmentAttributeName.NSParagraphStyle:attribute, which maps toNSParagraphStyleAttributeName.NSShadow:attribute, which maps toNSShadowAttributeName.NSURL:attribute, which maps toNSLinkAttributeName.NSUnderlineStyle:attribute, which maps toNSUnderlineStyleAttributeName; andstrikethroughAttribute, which maps toNSStrikethroughStyleAttributeName.String, on OS X only:toolTipAttribute, which maps toNSToolTipAttributeName.
Attributes with numeric values use the NSNumberConvertible protocol. The framework provides implementations for these types:
NSNumberIntUIntInt8UInt8Int16UInt16Int32UInt32Int64UInt64FloatDoubleCGFloat
Types that conform to NSNumberConvertible are extended with these functions:
baselineOffsetAttribute, which maps toNSBaselineOffsetAttributeName.expansionAttribute, which maps toNSExpansionAttributeName.kernAttribute, which maps toNSKernAttributeName.
To enforce valid values for the ligature attribute, the Ligature type is declared as an enumeration, with the cases:
NoneDefaultAll(this case is only available on OS X)
The Ligature enumeration is extended with the attribute function, which maps to NSLigatureAttributeName.
Attributed extends SequenceType with join() functions, which make flattening sequences of AttributedStringConvertible and AttributeFunction values possible.
let attributedString = [
UIColor.redColor().foregroundAttribute("Red"),
UIColor.greenColor().foregroundAttribute("Green")
].join().attributedStringlet attributes = [
UIColor.redColor().foregroundAttribute,
UIColor.greenColor().backgroundAttribute
].join()
let attributedString = attributes("Complementary").attributedStringIf you are writing an extension that composes with Attributed, it's best to work in terms of these two types. Here's an extension that applies Photoshop tracking values, which require knowledge of both the current font and the tracking value, and thus cannot be implemented as an AttributeFunction-compatible extension of either type:
extension UIFont
{
public func photoshopTrackingAttributes(tracking: CGFloat) -> AttributeFunction
{
return [attribute, (pointSize * tracking / 1000).kernAttribute].join()
}
}This is better than a function taking the tracking value and an attributed string convertible as two arguments and returning an AttributedStringConvertible because it can be composed with other attribute functions:
let attributes = [
UIColor.redColor().foregroundAttribute,
font.photoshopTrackingAttributes(500)
].join()
let attributedString = attributes("Tracked Red").attributedStringOuter attributed values do not override inner values, so this code works as expected:
UIColor.greenColor().foregroundAttribute([
"There is some ",
UIColor.blueColor().foregroundAttribute(
"blue text "
),
"embedded in this green text."
].join())Add:
github "natestedman/Attributed"
To your Cartfile.