Skip to main content

Guia completa de la localització d’aplicacions iOS

Des de Localizable.strings fins a les metadades de l’App Store: localitzi l’aplicació iOS amb Xcode, SwiftUI, Fastlane i traducció automatitzada amb IA.

1

Activar la localització a Xcode

Obri la configuració del projecte de Xcode, vagi a Info > Localizations i afegeixi els idiomes que vulgui admetre. Xcode crea automàticament directoris .lproj per a cada idioma.

Xcode Project Settings
// In Xcode:
// 1. Select your project in the navigator
// 2. Go to Info tab > Localizations
// 3. Click + to add languages (e.g., German, Japanese)
// 4. Select which files to localize
//
// Xcode creates .lproj directories automatically:
// en.lproj/Localizable.strings
// de.lproj/Localizable.strings
// ja.lproj/Localizable.strings
La localització base separa la interfície de les seves cadenes. Quan afegeix un idioma, Xcode ofereix crear versions localitzades dels storyboards, els XIB i els fitxers de cadenes.
2

Crear Localizable.strings

El fitxer de localització estàndard d’iOS utilitza parelles de clau i valor separades per signes igual, amb un punt i coma al final de cada línia. Col·loqui’l a la carpeta Base.lproj per a l’idioma d’origen.

Base.lproj/Localizable.strings
// Base.lproj/Localizable.strings

"welcome_title" = "Welcome to MyApp";
"login_button" = "Sign In";
"settings_label" = "Settings";
"greeting" = "Hello, %@!";    // %@ = string placeholder
"item_count" = "%d items";     // %d = integer placeholder
Si falten punts i coma, es produeixen errors silenciosos: el fitxer es carrega sense errors, però les traduccions són buides. Asseguri’s també que el fitxer s’hagi afegit a la fase de compilació Copy Bundle Resources del target; altrament, no s’inclourà al paquet de l’aplicació.
Common .strings Mistakes
// ❌ Common mistakes in .strings files:

// Missing semicolon — file loads but translations are empty
"welcome_title" = "Welcome"

// Unescaped quotes — causes parse error
"message" = "Click "here" to continue";

// ✅ Correct versions:
"welcome_title" = "Welcome";
"message" = "Click \"here\" to continue";
3

Migrar als catàlegs de cadenes (Xcode 15+)

Els catàlegs de cadenes (.xcstrings) són el substitut modern d’Apple per als fitxers .strings. Ofereixen un editor visual a Xcode, extracció automàtica de cadenes de les vistes de SwiftUI i compatibilitat integrada amb els plurals.

Localizable.xcstrings
// Xcode 15+ String Catalog (Localizable.xcstrings)
// Xcode automatically extracts strings from your code
// and manages translations in a visual editor.

// In SwiftUI, strings are automatically localizable:
Text("Welcome to MyApp")
Text("Hello, \(userName)!")

// Mark strings explicitly:
let title = String(localized: "welcome_title")
Els catàlegs de cadenes emmagatzemen TOTS els idiomes en un únic fitxer JSON .xcstrings. En equips, això provoca conflictes de fusió freqüents a Git quan diverses persones afegeixen cadenes. En projectes grans, valori utilitzar un catàleg per mòdul.
4

Utilitzar cadenes localitzades a SwiftUI i UIKit

La vista Text de SwiftUI localitza automàticament els literals de cadena. UIKit utilitza NSLocalizedString. A partir d’iOS 16, l’API moderna String(localized:comment:) ofereix una sintaxi més neta amb compatibilitat integrada al compilador.

ContentView.swift
import SwiftUI

struct ContentView: View {
    let userName: String

    var body: some View {
        VStack {
            // ✅ SwiftUI auto-localizes string literals
            Text("welcome_title")

            // ⚠️ This does NOT localize (String interpolation)
            // Text("Hello, \(userName)")

            // ✅ Use String(localized:) for dynamic strings
            Text(String(localized: "greeting \(userName)"))

            // ✅ UIKit style (works everywhere)
            let title = NSLocalizedString(
                "settings_label",
                comment: "Settings screen title"
            )

            // ✅ Modern API (iOS 16+)
            let modern = String(
                localized: "welcome_title",
                comment: "Main screen title"
            )
        }
    }
}
Text("Hello \(name)") no es localitza i falla silenciosament quan name és una variable String simple. La interpolació de cadenes de SwiftUI crea un LocalizedStringKey, però només determinats tipus (Int, Double, etc.) s’interpolen correctament. Per a variables String, utilitzi String(localized:) per crear primer la cadena localitzada.
5

Gestionar els plurals

iOS utilitza fitxers .stringsdict per a les regles de plural i admet totes les categories de plural CLDR: zero, one, two, few, many, other. Els catàlegs de cadenes gestionen els plurals mitjançant un editor visual de Xcode, molt més senzill que escriure manualment l’XML de stringsdict.

Localizable.stringsdict
<!-- Localizable.stringsdict -->
<?xml version="1.0" encoding="UTF-8"?>
<plist version="1.0">
<dict>
    <key>items_count</key>
    <dict>
        <key>NSStringLocalizedFormatKey</key>
        <string>%#@count@</string>
        <key>count</key>
        <dict>
            <key>NSStringFormatSpecTypeKey</key>
            <string>NSStringPluralRuleType</string>
            <key>NSStringFormatValueTypeKey</key>
            <string>d</string>
            <key>zero</key>
            <string>No items</string>
            <key>one</key>
            <string>%d item</string>
            <key>other</key>
            <string>%d items</string>
        </dict>
    </dict>
</dict>
</plist>

// Usage in Swift:
String(format: NSLocalizedString("items_count", comment: ""),
       itemCount)
Idiomes com l’àrab tenen 6 formes de plural, el rus en té 3 i el japonès, 1. Defineixi sempre totes les categories CLDR que necessitin els idiomes de destinació. Els catàlegs de cadenes ho faciliten amb l’editor visual de plurals.
6

Localitzar les metadades de l’App Store amb Fastlane

Utilitzi l’eina deliver de Fastlane per mantenir les metadades de l’App Store —el nom de l’aplicació, el subtítol, la descripció, les paraules clau i les notes de la versió— sota control de versions al repositori com a fitxers de text sense format organitzats per configuració regional.

Terminal
# Install Fastlane
$ gem install fastlane

# Initialize deliver for App Store metadata
$ fastlane deliver init

# Directory structure created:
# fastlane/metadata/
# ├── en-US/
# │   ├── name.txt            # App name (30 chars)
# │   ├── subtitle.txt        # Subtitle (30 chars)
# │   ├── description.txt     # Full description
# │   ├── keywords.txt        # Search keywords (100 chars)
# │   ├── release_notes.txt   # What's New
# │   └── promotional_text.txt
# ├── de-DE/
# │   └── ...
# └── ja/
#     └── ...

# Push metadata to App Store Connect:
$ fastlane deliver
Localització creuada: l’App Store dels EUA indexa paraules clau tant en anglès com en castellà. Localitzar les metadades al castellà permet captar cerques d’usuaris hispans dels EUA sense orientar-se a un mercat diferent.
7

Provar la localització

Provi el contingut localitzat sense canviar l’idioma del dispositiu. Utilitzi les substitucions d’esquema de Xcode per executar l’aplicació en qualsevol idioma, les previsualitzacions de SwiftUI amb l’entorn de configuració regional i XCUITest amb arguments d’inici per a les proves automatitzades.

Testing Localization
// 1. Xcode Scheme Override:
// Edit Scheme > Run > Options > App Language > Choose language

// 2. SwiftUI Preview with locale:
struct ContentView_Previews: PreviewProvider {
    static var previews: some View {
        ContentView()
            .environment(\.locale, Locale(identifier: "de"))

        ContentView()
            .environment(\.locale, Locale(identifier: "ja"))

        ContentView()
            .environment(\.locale, Locale(identifier: "ar"))
    }
}

// 3. XCUITest with language override:
let app = XCUIApplication()
app.launchArguments += ["-AppleLanguages", "(de)"]
app.launchArguments += ["-AppleLocale", "de_DE"]
app.launch()
Faci proves amb l’alemany (les cadenes s’allarguen aproximadament un 30% respecte de l’anglès) i el japonès (s’escurcen aproximadament un 50%) per detectar aviat problemes de disposició. Utilitzi la pseudolocalització de Xcode per sotmetre les disposicions a proves intensives sense traduccions reals.

Automatitzar la qualitat de les traduccions

Detecti les claus que falten, els marcadors de posició malmesos i els problemes de plural abans de publicar-los amb i18n-validate. Provi la interfície amb pseudotraduccions mitjançant i18n-pseudo abans que arribin les traduccions reals.
8

Automatitzar les traduccions

Tradueixi amb IA els fitxers .strings, .xcstrings i de metadades de Fastlane. Automatitzi la traducció tant de les cadenes de l’aplicació com de les metadades de l’App Store per oferir una presència completament localitzada.

Terminal
# Translate .strings files
> Translate Base.lproj/Localizable.strings
  to Japanese, German, and Spanish

# Translate App Store metadata too
> Translate fastlane/metadata/en-US/
  to de-DE, ja, es-MX

✓ 6 files translated in 3.2s
Una presència localitzada a l’App Store augmenta les baixades més d’un 30% als mercats no anglòfons. Tradueixi les metadades juntament amb les cadenes de l’aplicació: és la localització amb més retorn de la inversió que pot fer.
+

Extra: alternativa intel·ligent de configuració regional amb LocaleChain

De manera predeterminada, iOS recorre a l’idioma de desenvolupament quan la configuració regional exacta de l’usuari no està disponible. Un usuari de pt-BR amb traduccions només per a pt-PT veu l’anglès en lloc del portuguès. LocaleChain ho resol amb cadenes d’alternatives configurables.

LocaleChain és un paquet Swift de codi obert. Veure’l a GitHub

Package Dependencies
// Swift Package Manager
// File > Add Package Dependencies >
// https://github.com/i18n-agent/ios-localechain.git
MyApp.swift
import LocaleChain

// In your App init or AppDelegate:
LocaleChain.configure()  // Activates all default chains

// pt-BR user with only pt-PT translations?
// → Shows Portuguese instead of falling back to English

// Custom overrides for your specific locales:
LocaleChain.configure(
    overrides: ["es-MX": ["es-419", "es"]]
)

Errors habituals

Errors de sintaxi als fitxers .strings

Els punts i coma que falten, les cometes sense escapar o una codificació incorrecta provoquen errors silenciosos. El fitxer es carrega, però les traduccions apareixen buides. Validi sempre els fitxers .strings abans de fer commit.

La interpolació de text de SwiftUI no es localitza

Text("Hello \(stringVar)") no es localitza com s’esperava. Utilitzi String(localized:) per a les cadenes calculades o asseguri’s que les variables interpolades tinguin el tipus correcte per a LocalizedStringKey.StringInterpolation.

Els ginys i les extensions mostren claus sense processar

Les extensions d’aplicació tenen paquets separats. Asseguri’s que els fitxers .strings o .xcstrings s’hagin afegit a la fase Copy Bundle Resources del target de l’extensió, no només al target de l’aplicació principal.

Les traduccions que falten mostren claus en producció

Quan una clau no té traducció per a l’idioma de l’usuari, iOS mostra la clau mateixa. Utilitzi una estratègia d’idioma de reserva i provi totes les configuracions regionals admeses abans de publicar l’aplicació.

Estructura de fitxers recomanada

Project Structure
MyApp/
├── MyApp.xcodeproj
├── MyApp/
│   ├── Base.lproj/
│   │   ├── Localizable.strings       # Source strings
│   │   └── Localizable.stringsdict   # Plural rules
│   ├── en.lproj/
│   │   └── Localizable.strings
│   ├── de.lproj/
│   │   └── Localizable.strings
│   ├── ja.lproj/
│   │   └── Localizable.strings
│   ├── Localizable.xcstrings          # OR String Catalog
│   └── Info.plist
├── MyAppTests/
├── fastlane/
│   ├── Fastfile
│   └── metadata/
│       ├── en-US/
│       │   ├── name.txt
│       │   ├── description.txt
│       │   └── keywords.txt
│       ├── de-DE/
│       └── ja/
└── Package.swift

Provar i18n Agent ara

Arrossegar aquí el fitxer de traducció

JSON, YAML, PO, XML, CSV, Markdown, Properties

o fer clic per explorar

Idiomes de destinació

No cal registrePressupost instantani

Alternativa de configuració regional amb ios-localechain

Quan falta una clau de traducció en una configuració regional com de-AT, iOS salta directament a l’idioma de desenvolupament en lloc de comprovar primer la configuració regional pare de.

Terminal
// Swift Package Manager
// https://github.com/i18n-agent/ios-localechain
Configuration
import LocaleChain

LocaleChain.configure(overrides: [
    "de": ["en-GB", "en"],
    "pt-BR": ["pt", "en"],
    "zh-Hant-HK": ["zh-Hant", "zh", "en"],
])

Consulti la nostra guia de reserva de configuració regional per veure la llista completa de frameworks compatibles i les 75 cadenes integrades. Learn more →

Preguntes més freqüents sobre la localització d’iOS