The fonts built into iOS cover a lot of ground, but sooner or later a brand needs its own typeface. Adding a custom font to an iPhone or iPad app takes five steps. Most problems come from skipping one of them — usually using the file name instead of the PostScript name.
1. Check the licence
Desktop font licences often don’t cover embedding in apps. Confirm that your licence includes app or “mobile application” embedding, or use an open-licence font (for example SIL Open Font License) that permits bundling.
2. Add the font files to Xcode
Drag the .ttf or .otf files into your project. In the dialog, tick Copy items if needed and make sure your app target is checked under Add to targets. Afterwards, confirm each file appears under Build Phases › Copy Bundle Resources.
3. Register the fonts in Info.plist
Add the key Fonts provided by application (raw key UIAppFonts) as an array, with one entry per file name including its extension.
<key>UIAppFonts</key>
<array>
<string>Inter-Regular.ttf</string>
<string>Inter-Bold.ttf</string>
</array>4. Find the PostScript name
The name you pass to iOS is the font’s internal PostScript name, which is often different from both the file name and the family name. The quickest way to find it is to print every installed font once at launch. The same snippet lists every built-in font on whatever iOS version you are running, which is handy for checking the availability shown on this site.
for family in UIFont.familyNames.sorted() {
print(family)
for name in UIFont.fontNames(forFamilyName: family) {
print(" \(name)")
}
}On a Mac you can also open the font in Font Book and choose Show Font Info to see its PostScript name.
5. Use the font with Dynamic Type
Fixed point sizes ignore the user’s text size setting. Scale custom fonts relative to a system text style instead.
// SwiftUI
Text("Welcome")
.font(.custom("Inter-Bold", size: 28, relativeTo: .title))
// UIKit
let base = UIFont(name: "Inter-Regular", size: 17) ?? .systemFont(ofSize: 17)
label.font = UIFontMetrics(forTextStyle: .body).scaledFont(for: base)
label.adjustsFontForContentSizeCategory = trueTroubleshooting checklist
- Font returns nil: print the font list above and copy the PostScript name exactly — names are case-sensitive.
- Font missing on device but works in Simulator: the file isn’t in Copy Bundle Resources for the device target.
- Bold or italic falls back to regular: each style is a separate file and needs its own Info.plist entry.
- Text clipped at large sizes: allow labels to wrap (
numberOfLines = 0) and test with the largest accessibility sizes.
If a built-in typeface is good enough, skip all of this: every family in the iOS font list is already on the device. Popular choices include Avenir Next, Futura and Georgia.
Frequently asked questions
Why does UIFont(name:size:) return nil?
Almost always because the name is wrong (it must be the PostScript name, not the file name), the font isn’t listed under UIAppFonts in Info.plist, or the file isn’t included in the app target’s Copy Bundle Resources phase.
Do I need to add built-in iOS fonts to Info.plist?
No. Fonts that ship with iOS, such as Avenir Next or Georgia, are available to every app. Only fonts you bundle yourself need to be registered.
Which font formats does iOS support?
iOS supports TrueType (.ttf) and OpenType (.otf) fonts, including font collections (.ttc). Web-only formats such as WOFF and WOFF2 are not supported for app bundling.