SwiftUI
SF Symbols
iOS Development
App Design
Swift Programming

How do I set the size of a SF Symbol in SwiftUI?

Interview Questions practice on Codemia

Over 8,000 real interview questions from top companies, searchable by company and role.

Browse interview questions

Introduction

SF Symbols are vector icons designed to align with Apple typography and platform conventions. In SwiftUI, symbol size is usually controlled through font-related modifiers, not only frame values. Choosing the right sizing method depends on whether the symbol behaves like text, a decorative image, or a scalable custom asset.

Text-Like Sizing with .font

Most SF Symbols should be sized using .font, because symbols are designed to inherit typographic metrics.

swift
1import SwiftUI
2
3struct FontSizedSymbolView: View {
4    var body: some View {
5        VStack(spacing: 16) {
6            Image(systemName: "heart.fill")
7                .font(.title)
8
9            Image(systemName: "heart.fill")
10                .font(.system(size: 32, weight: .semibold))
11
12            Label("Favorites", systemImage: "heart.fill")
13                .font(.headline)
14        }
15        .padding()
16    }
17}

Using .font keeps symbol proportions aligned with text and dynamic type behavior.

Fine-Tuning with .imageScale

If you already set a font but want subtle size variants, use .imageScale.

swift
1Image(systemName: "bell")
2    .font(.title2)
3    .imageScale(.small)
4
5Image(systemName: "bell")
6    .font(.title2)
7    .imageScale(.large)

imageScale is relative, so it works best for small adjustments, not major size changes.

Explicit Pixel-Like Control with resizable

For custom graphic-style usage, make the symbol resizable and apply a frame.

swift
1Image(systemName: "paperplane.fill")
2    .resizable()
3    .scaledToFit()
4    .frame(width: 48, height: 48)

This gives tight control, but it can detach the icon from text metrics. Use it when the symbol acts like standalone artwork.

Keep Visual Weight Consistent

Large symbols can look too thin or too heavy depending on rendering mode and weight. Match weight explicitly when needed.

swift
1Image(systemName: "person.crop.circle")
2    .font(.system(size: 40, weight: .regular))
3
4Image(systemName: "person.crop.circle")
5    .font(.system(size: 40, weight: .bold))

For multicolor symbols, pair size decisions with rendering mode checks.

swift
1Image(systemName: "sun.max.fill")
2    .symbolRenderingMode(.palette)
3    .foregroundStyle(.yellow, .orange)
4    .font(.system(size: 36))

Dynamic Type and Accessibility

If symbols convey meaning near text, use text-driven sizes that respond to dynamic type. Fixed pixel sizes may become visually inconsistent in accessibility categories.

swift
1struct AccessibleSymbolRow: View {
2    @ScaledMetric(relativeTo: .body) private var iconSize = 20
3
4    var body: some View {
5        HStack(spacing: 12) {
6            Image(systemName: "checkmark.seal.fill")
7                .font(.system(size: iconSize))
8
9            Text("Verified account")
10                .font(.body)
11        }
12    }
13}

@ScaledMetric helps custom values follow system text scaling.

Alignment and Baseline Details

Perceived size is affected by alignment. If a symbol looks too small next to text, baseline position may be the issue instead of actual point size.

swift
1HStack(alignment: .firstTextBaseline, spacing: 8) {
2    Image(systemName: "exclamationmark.triangle.fill")
3        .font(.body)
4        .baselineOffset(1)
5    Text("Action required")
6        .font(.body)
7}

Small baseline adjustments can make symbol and text feel visually balanced without changing global typography.

Common Sizing Patterns

Use these quick rules:

  • Navigation and toolbars: .font(.body) or .font(.headline).
  • Inline labels: inherit surrounding text style.
  • Hero or status icons: .font(.system(size: ...)) with explicit weight.
  • Decorative standalone icons: resizable plus frame.

Picking one consistent pattern per UI area makes your design more coherent.

Variants and Symbol Effects

Some symbols support variants such as circle, fill, or slash. Variant choice can change visual area and make icons appear larger or smaller at identical point sizes.

swift
1VStack(spacing: 10) {
2    Image(systemName: "heart")
3        .font(.title)
4
5    Image(systemName: "heart.fill")
6        .font(.title)
7
8    Image(systemName: "heart.circle.fill")
9        .font(.title)
10}

When comparing sizes across controls, ensure you compare the same visual style variant.

Common Pitfalls

  • Setting only .frame on non-resizable symbols. Fix by sizing with .font or adding resizable explicitly.
  • Overusing fixed pixel values in text-heavy screens. Fix by using typographic styles and dynamic scaling.
  • Ignoring symbol weight at larger sizes. Fix by setting .font(.system(size:weight:)) intentionally.
  • Mixing rendering modes without testing contrast. Fix by validating size and color combinations in light and dark appearances.
  • Using oversized icons in compact controls. Fix by matching control density and platform conventions.

Summary

  • Prefer .font for most SF Symbol sizing in SwiftUI.
  • Use .imageScale for relative tweaks.
  • Use resizable and frame for artwork-like layouts.
  • Align symbol weight and rendering mode with size choices.
  • Support accessibility using dynamic scaling-aware techniques.

Related reading
Free course
Beginner
7 lessons
2 hours
Tackling System Design Interview Problems

A short course that equips you with the skills to approach system design interviews methodically.

Start the free course
Basis Lab
No course covers this one yet

Basis Lab writes one for you from a sentence about what you want to be able to do, then teaches it and checks you understood. Your first course is free.

Build my course
Track what you have practised

A free account saves your progress, solutions and study plan across every problem on Codemia.

Interview Questions practice on Codemia

Over 8,000 real interview questions from top companies, searchable by company and role.

Browse interview questions