WWDC Quick Look đź’“ By SwiftGGTeam
Communicate your brand identity on iOS

Communicate your brand identity on iOS

Watch original video

Highlight

Under the Liquid Glass design system in iOS 26, Apple clearly divides app interfaces into a UI layer and a content layer: navigation controls should stay native, while all brand personality should be expressed through the content layer. Developers no longer need to choose between “feels like iOS” and “has a recognizable identity.”

Core Content

The Old Problem: Brand Expression and Native Experience Felt Like Enemies

Many developers have faced this dilemma: designers ask for the navigation bar to use the brand color and the TabBar to have a custom style, and then users open the app and need several seconds to find the back button. Cross-platform teams have it worse: when Web or Android designs are moved directly to iOS, users always feel that “something is off.” (00:14)

Apple’s position is clear: iPhone users expect apps on their phone to look like iOS. The point is not to limit creativity, but to reduce cognitive load. Users are not using your iOS, Android, and Web versions at the same time. They only care whether the app in their hand feels intuitive. (01:20)

The iOS 26 Answer: A Two-Layer Model

Liquid Glass introduces one core idea: treat the app as two layers.

  • UI layer: navigation bars, TabBars, and toolbars that help users find their way
  • Content layer: images, text, and data visualizations inside scroll views that make the app unique (02:36)

The content layer is the best place to express brand. The UI layer acts as the foundation that helps users quickly understand how to operate the app.

Gentler Streak is a fitness app full of brand illustrations and data charts at first glance. It has plenty of personality. But look closely at the navigation: the TabBar and top toolbar are all native components, without heavy customization. (03:21)

Slack customizes the top toolbar by placing a button with channel information in the center. But the button size, floating action placement, and popover behavior are all consistent with system components. (04:12)

Moonlitt is a moon-phase tracking app with no TabBar and an extremely minimal interface. Its moon-phase calendar is a custom component, but it uses a Liquid Glass background and concentric edges from system sheets that echo the hardware’s rounded corners. The app is unique, but it immediately feels native to iOS. (04:29)

Color: Move It from Navigation Bars into Content

Before iOS 26, many apps filled navigation bars and TabBars with brand colors. Those controls felt heavy and compressed the content area. (09:24)

The current recommendation is to move color into the content area, meaning inside the ScrollView. Liquid Glass controls float above content and dynamically pick up the brand color beneath them. Slack moved its solid top toolbar color into the content area so it disappears with scrolling and lets content fill the whole screen. (10:39)

Use color with restraint. It should communicate hierarchy, grouping, or interaction state, not cover the entire interface. Slack uses color only in important places: new-message badges, the compose button, and the selected TabBar state. (10:16)

Custom Fonts Must Support Dynamic Type

Crumbl uses its custom Crumbl Sans font in marketing and in large app headings. But when users set the system text size to the maximum, the app remains readable: text wraps instead of being truncated. (12:00)

Dynamic Type is an accessibility setting, but many people use it as an everyday preference. Apple’s system font has this capability built in. Custom fonts require developers to implement and test it themselves.

Gentler Streak uses only the system font, but mixes widths and SF Rounded variants to create rich hierarchy while preserving recognition. (13:53)

Icons: Both Custom Icons and SF Symbols Can Work

NYT Cooking uses its own icon style: sharper edges and mostly line-based forms. These icons appear in the TabBar, toolbar, and content layer. They are unified and simple, and they remain clear at small sizes. (14:26)

One detail matters: NYT Cooking uses three different “share” icons on iOS, Android, and Web. The style stays unified, but each platform follows the sharing pattern familiar to its users. (14:58)

Not every app needs custom icons. SF Symbols now contains more than 7,000 symbols, is built into Xcode, and supports dynamic scaling, accessibility, and localization. Designers no longer need to export icon libraries; developers can call symbols directly in code. (15:23)

Do Not Keep the Logo Permanently in the Navigation Bar

In the iOS context, users do not need to be reminded which app they are using. A logo consumes valuable screen space. NYT Cooking shows the logo only on the home page and fades it out on scroll. That restraint is elegant. (15:59)

Details

Make Custom Fonts Support Dynamic Type

Scenario: use a brand font while ensuring the layout does not break when users increase text size in system settings.

Text("This week's new flavor: Chocolate chip")
    .font(.custom("CrumblSans-Bold", size: 24, relativeTo: .title))
    .lineLimit(nil)
    .fixedSize(horizontal: false, vertical: true)

Key points:

  • relativeTo: .title binds the custom font to the system .title text style, so it scales proportionally when users adjust the system text size
  • lineLimit(nil) allows text to wrap when space is limited instead of being truncated
  • .fixedSize(horizontal: false, vertical: true) ensures SwiftUI correctly calculates the height of multiline text so enlarged text is not cut off

Pitfall: without relativeTo, the font size is fixed. When low-vision users enlarge text, it can overlap or overflow the screen.

Replace Custom Popovers with System Context Menus

Scenario: give up handwritten long-press menus and use a standard system component to get built-in morphing animation for free.

struct MoonPhaseView: View {
    var body: some View {
        Image("moon_full")
            .resizable()
            .frame(width: 100, height: 100)
            .contextMenu {
                Button {
                    // Handle settings logic
                } label: {
                    Label("Moon phase settings", systemImage: "gearshape")
                }

                Button(role: .destructive) {
                    // Handle deletion logic
                } label: {
                    Label("Remove observation", systemImage: "trash")
                }
            }
    }
}

Key points:

  • .contextMenu is a native SwiftUI modifier and does not require extra gesture recognition
  • The menu “grows” out of the tapped element with built-in system morphing animation
  • role: .destructive automatically shows the delete item in red, following system convention
  • Using Label with SF Symbols automatically aligns icons and text

Pitfall: if you use a custom Image instead of systemImage, mismatched size or baseline can make the morphing animation feel strange. Prefer SF Symbols, or make sure custom icons strictly follow 24x24 sizing with the correct baseline.

Use Zoom Transition to Connect Content

Scenario: when tapping a list item to enter a detail page, use a smooth transition animation to establish visual continuity.

struct RecipeListView: View {
    @Namespace private var animationNamespace

    var body: some View {
        NavigationStack {
            List(recipes) { recipe in
                NavigationLink(value: recipe) {
                    RecipeRow(recipe: recipe)
                        .matchedTransitionSource(id: recipe.id, in: animationNamespace)
                }
            }
            .navigationDestination(for: Recipe.self) { recipe in
                RecipeDetailView(recipe: recipe)
                    .navigationTransition(.zoom(sourceID: recipe.id, in: animationNamespace))
            }
        }
    }
}

Key points:

  • matchedTransitionSource marks the starting view for the transition
  • navigationTransition(.zoom(...)) defines the transition animation on the detail page
  • The list item the user tapped smoothly expands into the detail page, making the “where did this come from?” relationship clear
  • This transition is delightful and also improves interaction efficiency

Put Brand Color at the Top of Content So Liquid Glass Can Pick It Up

Scenario: move brand color from the navigation bar to the top of the ScrollView, letting floating glass controls naturally take on the brand tint.

struct ContentView: View {
    var body: some View {
        ScrollView {
            VStack(spacing: 0) {
                // Large brand-color area at the top, providing the base color for Liquid Glass
                Rectangle()
                    .fill(brandGradient)
                    .frame(height: 200)

                // Actual content
                LazyVStack {
                    ForEach(items) { item in
                        ItemRow(item: item)
                    }
                }
            }
        }
    }

    var brandGradient: LinearGradient {
        LinearGradient(
            colors: [Color.purple.opacity(0.8), Color.blue.opacity(0.6)],
            startPoint: .top,
            endPoint: .bottom
        )
    }
}

Key points:

  • Place a sufficiently tall colored region at the top so Liquid Glass controls can dynamically refract those colors while floating over it
  • Avoid colors that are too noisy or too low in contrast, or the glass effect can look dull
  • A large gradient in the content area creates more depth than a solid color block

Key Takeaways

  • Build a moon-phase tracking app with a full-screen gradient night-sky content background

    Follow Moonlitt’s approach: fill the content layer with a deep-blue-to-black gradient to simulate the night sky. A 3D moon-phase model floats in the center and changes dynamically with the user’s location. Navigation uses a minimal single-layer structure, without a TabBar. Liquid Glass controls naturally pick up the deep blue tone of the night sky, creating a unified and immersive interface. Entry point: use SwiftUI’s MeshGradient or LinearGradient for the background, and use SceneKit or RealityKit to render the 3D moon phase.

  • Build a recipe app that connects recipe lists and detail pages with Zoom Transition

    Following NYT Cooking, when users tap a dish image in the list, the image smoothly expands into the hero image on the detail page. Comments slide in from the bottom. When returning, the detail page shrinks back into its original position in the list. This makes the browse-to-read transition feel continuous. Entry point: SwiftUI’s matchedTransitionSource plus navigationTransition(.zoom).

  • Build a fitness data app where monthly data comes alive with spring animation

    Following Gentler Streak, as the monthly recap page scrolls, each data card enters with .spring(response: 0.4, dampingFraction: 0.7). Use different SF Symbols variants, such as figure.run and figure.swim, to distinguish workout types. Use the system font throughout, and create hierarchy through width and weight. Entry point: SwiftUI’s .scrollTransition or withAnimation(.spring).

  • Build a baking brand app where the custom font appears only in memorable moments

    Following Crumbl, design a brand font but use it only for large headings, such as weekly flavor names, and marketing popovers. Use San Francisco for body text, buttons, and navigation. This preserves brand memory while keeping readability and Dynamic Type support. Entry point: bind the font to a system text style with .custom("BrandFont", relativeTo: .largeTitle).

  • Build a Home Screen widget that reinforces brand memory with color

    Following Crumbl’s widget, if users find your data valuable, such as daily steps, to-do lists, or weather, provide a softly colored and recognizable Home Screen widget. The widget does not need complex interaction; appearing on the user’s Home Screen every day is already high-frequency brand exposure. Entry point: WidgetKit plus AppIntent, with colors and icons consistent with the app’s content layer.

  • Principles of great design — Apple’s hard safety line for design responsibility in the AI era, plus the interaction principles of Agency and Forgiveness
  • SwiftUI — New SwiftUI controls and animation APIs for implementing the transitions and interactions discussed in this session
  • UIKit modernization — UIKit modernization improvements for projects that need to mix UIKit and SwiftUI
  • Design principles — A deeper expansion of design principles that complements brand expression
  • AppKit modernization — Interface modernization on macOS when your brand needs to stay consistent across Apple platforms

Comments

GitHub Issues · utterances