Sample CodeiOS, iPadOS, Mac CatalystReviewed 2026-07-21View on Apple Developer

Changing the appearance of selected and highlighted cells

At a glance

Item Summary
Purpose Demonstrates separate visual feedback for the transient highlighted state and persistent selected state of collection-view cells.
App architecture A storyboard connects a collection view to one controller acting as data source/delegate; a custom cell owns reusable visual-state presentation.
Main patterns Framework-managed cell state, delegate callbacks, and reusable-cell encapsulation.
Project style Deliberately small UIKit sample: four Swift lifecycle/UI files and no domain/service layer.

Project structure

CollectionViewManagingVisualStates/
├── AppDelegate.swift
├── SceneDelegate.swift
├── ViewController.swift
├── CustomCollectionViewCell.swift
└── Base.lproj/
    ├── Main.storyboard
    └── LaunchScreen.storyboard

Structure observations

  • ViewController contains collection callbacks but no stored feature state.
  • CustomCollectionViewCell contains the visual implementation reused by all 25 cells.
  • The storyboard supplies collection layout, reuse registration, outlets, and delegate/data-source connections.

Overall architecture

Reference code

CollectionViewManagingVisualStates/ViewController.swift:34 — the collection delegate treats highlight and selection as different event streams and applies a different visual response to each.

func collectionView(
    _ collectionView: UICollectionView,
    didHighlightItemAt indexPath: IndexPath
) {
    if let cell = collectionView.cellForItem(at: indexPath) {
        cell.contentView.backgroundColor =
            #colorLiteral(red: 1, green: 0.4932718873,
                          blue: 0.4739984274, alpha: 1)
    }
}

func collectionView(
    _ collectionView: UICollectionView,
    didSelectItemAt indexPath: IndexPath
) {
    if let cell = collectionView.cellForItem(at: indexPath)
            as? CustomCollectionViewCell {
        cell.showIcon()
    }
}

Interpretation

UIKit owns the state machine and sends callbacks. The controller reacts to touch phases, while the cell owns how the persistent selected state looks. There is no app-level selection model because the sample’s subject is cell presentation.

Ownership and state

Ownership evidence

CollectionViewManagingVisualStates/CustomCollectionViewCell.swift:13 — each cell configures its two framework-defined background slots and retains the icon outlet used for selected-state detail.

static public let reuseID = "CustomCollectionViewCell"
@IBOutlet var iconView: UIImageView!

override func awakeFromNib() {
    super.awakeFromNib()

    let redView = UIView(frame: bounds)
    redView.backgroundColor =
        #colorLiteral(red: 1, green: 0, blue: 0, alpha: 1)
    backgroundView = redView

    let blueView = UIView(frame: bounds)
    blueView.backgroundColor =
        #colorLiteral(red: 0, green: 0, blue: 1, alpha: 1)
    selectedBackgroundView = blueView
}
Owner Object or state Relationship Mutation authority
Storyboard / collection view Cell registration, collection hierarchy, delegate/data-source wiring Constructs and reuses cells UIKit/storyboard lifecycle
ViewController No stored selection data Coordinates callbacks only Collection data-source/delegate methods
UICollectionView Highlighted and selected index-path state Framework-owned interaction state Touch/selection machinery
CustomCollectionViewCell Default/selected background views and icon outlet Owns reusable presentation objects awakeFromNib, showIcon, hideIcon
SceneDelegate Storyboard-created window reference Receives/stores scene window UIKit scene lifecycle

Class and protocol design

Type or protocol Responsibility Depends on or conforms to
ViewController Supply 25 cells and react to highlight/select transitions UICollectionViewDataSource, UICollectionViewDelegate
CustomCollectionViewCell Configure persistent background states and icon visibility UICollectionViewCell
SceneDelegate Hold the storyboard-created window UIWindowSceneDelegate
AppDelegate Configure scene sessions UIApplicationDelegate

There is no app-defined protocol or protocol-oriented domain layer. The only protocols are UIKit callback contracts, which is appropriate for this focused visual-state sample.

Access control

Symbol Access Verified effect Why it fits this design
All app classes implicit internal Types are visible only inside the app module. The sample exposes no reusable framework API.
CustomCollectionViewCell.reuseID Declared public static let The declaration is public, but effective external reach is limited by the internal cell class. Gives controller/storyboard code a named reuse identifier; internal would also suffice here.
iconView outlet implicit internal, strong App-module code could access it; the cell and view hierarchy retain the image view. Storyboard connection is simple, although only cell methods need it.
showIcon / hideIcon implicit internal The controller can request semantic visual changes without touching the outlet. Keeps call sites descriptive even without private properties.
Delegate/data-source methods implicit internal Available for UIKit protocol dispatch within the module. Required callback surface.
private / fileprivate / private(set) Not used No finer lexical boundary is enforced. The sample prioritizes brevity; production code could make iconView private where outlet tooling permits.

Reference code

CollectionViewManagingVisualStates/CustomCollectionViewCell.swift:28 — controller-facing methods express the visual intent while the cell performs the outlet mutation.

func showIcon() {
    iconView.alpha = 1.0
}

func hideIcon() {
    iconView.alpha = 0.0
}

Logic ownership and placement

Logic Owning type or file Placement rationale
Item count and cell dequeue ViewController data-source extension Requires collection-view context, not cell internals.
Highlight begin/end response ViewController delegate extension Maps UIKit touch callbacks to transient content feedback.
Selection begin/end response ViewController delegate extension Requests semantic icon changes for the selected cell.
Default/selected backgrounds CustomCollectionViewCell Reusable presentation belongs with the reusable view.
Icon visibility mutation CustomCollectionViewCell Hides outlet details from the controller call site.
Selection/highlight state machine UICollectionView / UICollectionViewCell UIKit already owns interaction and cell-state propagation.

Design patterns

Pattern Source evidence Purpose or tradeoff
Framework-managed visual state CollectionViewManagingVisualStates/CustomCollectionViewCell.swift:16 Uses backgroundView and selectedBackgroundView instead of an app state machine.
Delegate callbacks CollectionViewManagingVisualStates/ViewController.swift:32 Separates transient highlight and persistent selection responses.
Data source CollectionViewManagingVisualStates/ViewController.swift:19 Keeps cell creation/dequeue at the collection owner.
Reusable cell encapsulation CollectionViewManagingVisualStates/CustomCollectionViewCell.swift:11 Centralizes visual setup and icon changes across reused instances.

Naming conventions

  • CustomCollectionViewCell names the customized UIKit role; the generic ViewController reflects the sample’s intentionally tiny scope.
  • reuseID names framework identity, while iconView names the outlet by visual role.
  • showIcon and hideIcon use direct command verbs.
  • UIKit callback names distinguish didHighlight/didUnhighlight from didSelect/didDeselect.

Architecture takeaways

  • Let UICollectionView own selection and highlight state when no domain-level selection model is required.
  • Put reusable appearance in the cell and event interpretation in the collection delegate.
  • Treat highlight and selection as distinct lifetimes with distinct visuals.
  • Expose semantic cell commands rather than mutating its outlet from the controller.
  • This sample’s broad module-local visibility is concise, but production cells can narrow implementation properties.

Source map

Source file Relevant symbols
CollectionViewManagingVisualStates/ViewController.swift Data source and highlight/selection callbacks
CollectionViewManagingVisualStates/CustomCollectionViewCell.swift Background slots, reuse ID, icon presentation
CollectionViewManagingVisualStates/SceneDelegate.swift Storyboard window lifecycle
CollectionViewManagingVisualStates/AppDelegate.swift Scene configuration
CollectionViewManagingVisualStates/Base.lproj/Main.storyboard Collection wiring and cell registration