Structures
The following structures are available globally.
-
AttributedText
allows you to apply strongly-typed attributes to strings (much like theAttributedString
type introduced in iOS 15). You can then access theattributedString
property to get an attributed string with those attributes applied.For example:
See morevar text = AttributedText(string: "Hello, world") // Apply a font to the entire range text.font = .systemFont(ofSize: 20) // Apply a color to part of the string let range = text.string.range(of: "world")! text[range].color = .blue // Render the attributed text let label = AttributedLabel(attributedText: text.attributedString)
Declaration
Swift
@dynamicMemberLookup public struct AttributedText
-
Declaration
Swift
public struct TextAttributeContainer
-
Declaration
Swift
public struct BlueprintViewRenderMetrics
-
The context passing to the
See morebackingViewDescription
of an Element.Declaration
Swift
public struct ViewDescriptionContext
-
Context object passed into
See moreupdateUIView
.Declaration
Swift
public struct UIViewElementContext
-
A two-way binding between a focusable element’s backing view and a
FocusState
-wrapped property.Generally you should not need to interact with this type directly. However, you can use focus bindings to add focus support to custom elements.
Adding Focus Bindings
On a
FocusState
, call thebinding(for:)
method to get a binding bound to an optional value, orbinding()
to get a binding bound to a boolean.To set up the 2-way binding, there are 2 steps:
Assign actions to the nested
FocusTrigger
, so that your backing view is updated when theFocusState
‘s value changes.Call the
onFocus
andonBlur
callbacks when your backing view gains or loses focus, so that the value of the boundFocusState
is updated.
Example
final class FocusableView: UIView { var focusBinding: FocusBinding? { didSet { oldValue?.trigger.focusAction = nil oldValue?.trigger.blurAction = nil guard let focusBinding = focusBinding else { return } focusBinding.trigger.focusAction = { [weak self] in self?.becomeFirstResponder() } focusBinding.trigger.blurAction = { [weak self] in self?.resignFirstResponder() } if isFirstResponder { focusBinding.onFocus() } else { focusBinding.onBlur() } } } @discardableResult override func becomeFirstResponder() -> Bool { let focused = super.becomeFirstResponder() if focused { focusBinding?.onFocus() } return focused } @discardableResult override func resignFirstResponder() -> Bool { let blurred = super.resignFirstResponder() if blurred { focusBinding?.onBlur() } return blurred } }
- Tag: FocusBinding
Declaration
Swift
public struct FocusBinding
-
A property wrapper type that can read and write a value that represents the placement of focus.
Use this property wrapper in conjunction with modifiers on elements that support focus, such as
TextField.focused(when:equals:)
andTextField.focused(when:)
, to describe when those elements should have focus. When focus enters the modified element, the wrapped value of this property updates to match a given value. Similarly, when focus leaves, the wrapped value of this property resets tonil
orfalse
. Setting this property’s value programmatically has the reverse effect, causing focus to move to the element associated with the updated value.In the following example of a simple login screen, when the user presses the Sign In button and one of the fields is still empty, focus moves to that field. Otherwise, the sign-in process proceeds.
struct LoginForm: ProxyElement { enum Field: Hashable { case username case password } var username: String var password: String var handleLogin: () -> Void @FocusState private var focusedField: Field? var elementRepresentation: Element { Column { column in column.add( child: TextField(text: "") .focused(when: $focusedField, equals: .username) ) column.add( child: TextField(text: "") .focused(when: $focusedField, equals: .password) ) column.add( child: Button( onTap: { if username.isEmpty { focusedField = .username } else if password.isEmpty { focusedField = .password } else { handleLogin() } }, wrapping: Label(text: "Sign In") ) ) } } }
To allow for cases where focus is completely absent from a view tree, the wrapped value must be either an optional or a Boolean. Set the focus binding to
false
ornil
as appropriate to remove focus from all bound fields. You can also use this to remove focus from aTextField
and thereby dismiss the keyboard.Auto-Focus
To auto-focus a field when it appears, set the value in an
onAppear
hook.struct Example: ProxyElement { @FocusState var isFocused: Bool var elementRepresentation: Element { TextField(text: "") .focused(when: $isFocused) .onAppear { isFocused = true } } }
Avoid Ambiguous Focus Bindings
A
TextField
can have only one focus binding, stored in itsfocusBinding
property. If you apply thefocused
modifier multiple times, the last one will overwrite the previous value.On the other hand, binding the same value to two views is ambiguous. In the following example, two separate fields bind focus to the
name
value:struct Content: ProxyElement { enum Field: Hashable { case name case fullName } @FocusState private var focusedField: Field? var elementRepresentation: Element { Column { column in column.add( child: TextField(text: "") .focused(when: $focusedField, equals: .name) ) column.add( child: TextField(text: "") .focused(when: $focusedField, equals: .name) // incorrect re-use of .name ) } } }
If the user moves focus to either field, the
See morefocusedField
binding updates toname
. However, if the app programmatically sets the value toname
, the last field bound will be chosen.Declaration
Swift
@propertyWrapper public struct FocusState<Value> where Value : Hashable
-
An alignment in both axes.
See moreDeclaration
Swift
public struct Alignment : Equatable
-
An alignment position along the horizontal axis.
See moreDeclaration
Swift
public struct HorizontalAlignment : Equatable, CustomStringConvertible
-
An alignment position along the vertical axis.
See moreDeclaration
Swift
public struct VerticalAlignment : Equatable, CustomStringConvertible
-
Represents an a proportional relationship between width and height.
See moreDeclaration
Swift
public struct AspectRatio
-
Generic result builder for converting blocks of
See moreChild...
into[Child]
.Declaration
Swift
@resultBuilder public struct Builder<Child>
-
Places a decoration element behind or in front of the given
wrapped
element, and positions it according to theposition
parameter.The size and position of the element is determined only by the
wrapped
element, thedecoration
element does not affect the layout at all.Example
The arrows represent the measured size of the element for layout purposes.
See more┌───────────────────┐ ┌──────┐ │ Decoration │ │ │ │ ┏━━━━━━━━━━━━━━━┓ │ ▲ │ ┣━━━━━━━━━━┓ ▲ │ ┃ ┃ │ │ └─┳────┘ ┃ │ │ ┃ Wrapped ┃ │ │ ┃ Wrapped ┃ │ │ ┃ ┃ │ │ ┃ ┃ │ │ ┗━━━━━━━━━━━━━━━┛ │ ▼ ┗━━━━━━━━━━━━━━━┛ ▼ └───────────────────┘ ◀───────────────▶ ◀───────────────▶
Declaration
Swift
public struct Decorate : ProxyElement
-
An element’s size and its alignment guides in its own coordinate space.
You can access the size of the element through the
width
andheight
properties. You can access alignment guide values by subscripting with the specific alignment.These dimensions are typically used when setting an alignment guide on a stack, with
StackElement.add(...)
.Example
// get the alignment guide value for `VerticalAlignment.center`, falling back to the default // value if no alignment guide has been set dimensions[VerticalAlignment.center] // get the alignment guide value for `HorizontalAlignment.trailing`, or `nil` if none has been // set. dimensions[explicit: .trailing]
See Also
See moreDeclaration
Swift
public struct ElementDimensions : Equatable
-
Element which lays out children horizontally, wrapping to another row when there is not enough space.
You may control the layout of each row within the flow layout, by providing a
LineAlignment
, which controls the horizontal alignment of content within a row when it is smaller than its container, and viaItemAlignment
, which controls the vertical alignment of shorter elements within a row.Flow(itemSpacing: 10, lineSpacing: 10) { OnboardingPill("Food / drink") OnboardingPill("Retail goods").flowChild(key: "aKey") OnboardingPill("Grocery / gourmet / alcohol") OnboardingPill("Beauty / wellness bookings") OnboardingPill("Healthcare services") OnboardingPill("Something else") }
Below is a diagram showing a simple example of a
Flow
layout.
See more┌─────────────────────────────────────┐ │ ┌─────────┐┌─────────┐┌────────────┐│ │ │ 1 ││ 2 ││ 3 ││ │ └─────────┘└─────────┘└────────────┘│ │ ┌───────┐┌─────┐┌───────────┐ │ │ │ 4 ││ 5 ││ 6 │ │ │ └───────┘└─────┘└───────────┘ │ └─────────────────────────────────────┘
Declaration
Swift
public struct Flow : Element
-
Contains information about the current layout being measured by GeometryReader
See moreDeclaration
Swift
public struct GeometryProxy
-
Like
Row
,GridRow
displays a list of items in a linear horizontal layout. UnlikeRow
,GridRow
provides convenience for describing columnar layout.Horizontally,
GridRow
children are stretched to fill the available space. Vertically, children are aligned according to theverticalAlignment
property.Children may be sized proportionally or absolutely. Proportionally-sized children are granted a proportion of the total layout space after absolutely-sized children and margins have been subtracted.
Example:
GridRow { row in row.verticalAlignment = .fill row.spacing = 8.0 row.add(width: .proportional(0.75), child: name) row.add(width: .proportional(0.25), child: number) row.add(width: .absolute(100), child: status) }
Expected layout:
See more┌────────────────────────────┬─┬────────┬─┬──────────────────┐ │ name │ │ number │ │ status │ │ (75%) │8│ (25%) │8│ (100 pts) │ │ │ │ │ │ │ ●──────────── 150 ───────────● ●── 50 ──● ●─────── 100 ──────● └────────────────────────────┴─┴────────┴─┴──────────────────┘ ●──────────────────────────── 316 ───────────────────────────●
Declaration
Swift
public struct GridRow : Element
-
Keyed
allows providing aHashable
value which is used during view updates to uniquely identify content during the diff process between the old and new element structure.This is useful if you have two elements of the same type at the same depth in the element hierarchy, and you’d like to differentiate between them, eg for appearance transition purposes.
Example
Keying the image returned, so that a transition occurs when changing between a placeholder image and an available photo.
See morefunc imageElement() -> Element { if let photo = self.photo { return Image(image: photo) .transition(.fade) .keyed("photo") } else { return Image(image: self.placeholder) .transition(.fade) .keyed("placeholder") } }
Declaration
Swift
public struct Keyed : Element
-
Contains layout-related metrics for an element.
See moreDeclaration
Swift
public struct LayoutAttributes
extension LayoutAttributes: Equatable
-
Configuration options for
caffeinated
.Generally these are only useful for experimenting with the performance profile of different element compositions, and you should stick with
See moredefault
.Declaration
Swift
public struct LayoutOptions : Equatable
-
A proxy that represents one child element of a layout.
This type acts as a proxy for a child element in a
Layout
. Layout protocol methods receive aLayoutSubelements
collection that contains exactly one proxy for each of the child elements managed by the layout.Use this proxy to get information about the associated element, like its size and traits. You should also use the proxy to tell its corresponding element where to appear by calling the proxy’s
place(at:anchor:size:)
method. Do this once for each subview from your implementation of the layout’splaceSubelements(in:subelements:environment:cache:)
method.Note
TheLayoutSubelement
API, and its documentation, are modeled after SwiftUI’s LayoutSubview, with major differences noted.Declaration
Swift
public struct LayoutSubelement
-
A parent element which allows arbitrary, custom layout and positioning of its children.
Instead of creating a custom
Element
with a customLayout
, you might use this element to create a customized layout in a more lightweight way.
See moreLayoutWriter { context, layout in layout.add(with: myFrame, child: myElement) layout.add(with: myOtherFrame, child: myOtherElement) layout.sizing = .unionOfChildren }
Declaration
Swift
public struct LayoutWriter : Element
-
A normalized point in an element’s coordinate space.
Use a unit point to represent a location in an element without having to know the element’s rendered size. The point stores a value in each dimension that indicates the fraction of the element’s size in that dimension — measured from the element’s origin — where the point appears. For example, you can create a unit point that represents the center of any element by using the value
0.5
for each dimension:let unitPoint = UnitPoint(x: 0.5, y: 0.5)
To project the unit point into the rendered element’s coordinate space, multiply each component of the unit point with the corresponding component of the element’s size:
let projectedPoint = CGPoint( x: unitPoint.x * size.width, y: unitPoint.y * size.height )
You can perform this calculation yourself if you happen to know an element’s size, but Blueprint typically does this for you to carry out operations that you request, like when you place a subelement in a custom layout.
You can create custom unit points with explicit values, like the example above, or you can use one of the built-in unit points, like
zero
,center
, ortopTrailing
. The built-in values correspond to the alignment positions of the similarly named, built-inAlignment
types.Note
A unit point with one or more components outside the range[0, 1]
projects to a point outside of the element.Declaration
Swift
public struct UnitPoint : Hashable
-
Defines the maximum size for a measurement.
Currently this constraint type can only handles layout where the primary (breaking) axis is horizontal (row in CSS-speak).
See moreDeclaration
Swift
public struct SizeConstraint : Hashable, CustomStringConvertible
-
UIView animation configuration values.
See moreDeclaration
Swift
public struct AnimationAttributes
-
Declaration
Swift
public struct URLHandlerEnvironmentKey : EnvironmentKey
-
Allows showing the system’s
UIMenuController
editing menu.You can show the menu upon tap or long press:
myElement.editingMenu(show: .onLongPress) { EditingMenuItem.copying("A String") EditingMenuItem(.select) { print("Selected!") } }
You can also show the menu as a result of another element’s
onTap
closure, using the trigger-based API:
See moreEditingMenu { menu in MyRow(text: "Hello, World") { menu.show() } } items: { EditingMenuItem.copying("A String") }
Declaration
Swift
public struct EditingMenu : Element
-
A single item in an editing menu.
See moreDeclaration
Swift
public struct EditingMenuItem