sp: какво е това, мащабируеми пиксели за текст в Android

Автор: IT Sectr Публикувано: 2026-02-25 Време за четене: 9 мин

sp — Scale-independent Pixels, единица за измерване на текст в Android, която взема предвид настройките за размер на шрифта на устройството. За разлика от dp, sp се мащабира заедно с размера на системния шрифт, осигурявайки достъпност на интерфейсите. Статията обяснява разликата между sp и dp, показва настройката на textSize в XML и Kotlin, както и разкрива най-добрите практики за работа с типография в Android.

Основни точки

  • sp — единица за текст, мащабируема според системните настройки на шрифта на потребителя
  • dp — единица за размери на елементи, не реагира на промяна на размера на шрифта
  • Разлика между sp и dp: sp = dp × scaleFactor, където scaleFactor зависи от настройките на шрифта
  • textSize в XML се задава чрез sp: android:textSize="16sp"
  • Material Design препоръчва типографска стъпка от 12sp до 34sp за заглавия

Какво е sp в Android?

sp (scale-independent pixel) — единица за измерване на размер на шрифта в Android, която автоматично се мащабира според системните настройки на потребителя. Когато собственикът на устройството увеличи размера на шрифта в настройките, всички елементи със стойности в sp пропорционално нарастват. Това осигурява достъпност на интерфейса за хора с лошо зрение.

Основно съотношение: 1 sp = 1 dp при стандартен мащаб на шрифта 1.0 (normal). Ако потребителят зададе шрифт Large (1.15×), 16 sp се превръща в 18.4 физически пиксела. При размер на шрифта Small (0.85×) същите 16 sp ще станат 13.6 px. Механизмът за мащабиране се управлява чрез Settings.System.FONT_SCALE на ниво Android Framework.

Според Google Material Design Guidelines, текстът трябва да се задава изключително в sp. Изключение — фиксирани етикети в компоненти, където размерът е критичен за оформлението (например текст вътре в бутони с фиксирана височина). В такива случаи се препоръчва използването на dp с ръчен контрол на достъпността.

sp vs dp: ключови разлики

Разликата между sp и dp — една от най-честите теми на въпроси на интервюта за Android разработчици и в реални code review. И двете единици са свързани с density-independent pixel (160 dpi = 1 dp = 1 px на mdpi екран), но се държат различно при промяна на размера на системния шрифт.

Характеристикаspdp
ПредназначениеРазмер на текстРазмери на елементи, разстояния, ширина, височина
Мащабиране с шрифтДа (scale factor)Не
Мащабиране с плътностДаДа
API за настройкаandroid:textSizeandroid:layout_width, layout_height, padding, margin
Material Design Tokentypescalespacing, sizing

На практика грешка — използване на dp за текст. Ако текстът е зададен в dp, той не се мащабира при увеличаване на шрифта, което прави интерфейса недостъпен за потребители с лошо зрение. Обратната грешка — използване на sp за височина на бутон или разстояния: при увеличаване на шрифта бутонът може да се „надуе", разваляйки оформлението.

Как работи мащабирането на sp

Мащабирането на sp е имплементирано на ниво Android Framework в класа TypedValue. Формула за преизчисляване: sp = dp × scaledDensity, където scaledDensity е коефициент на мащаб, който взема предвид както плътността на екрана, така и настройката на шрифта на потребителя.

kotlin
// Програмно получаване на scaledDensity в Kotlin
val scaledDensity = with(context.resources) {
    displayMetrics.scaledDensity
}

// Конвертиране на sp в px
fun spToPx(sp: Float, context: Context): Float {
    return TypedValue.applyDimension(
        TypedValue.COMPLEX_UNIT_SP,
        sp,
        context.resources.displayMetrics
    )
}

// Конвертиране на px в sp
fun pxToSp(px: Float, context: Context): Float {
    return px / context.resources.displayMetrics.scaledDensity
}

Методът TypedValue.applyDimension — единственият правилен начин за конвертиране на sp в пиксели по време на изпълнение. Директното умножение по scaledDensity е по-малко надеждно, защото не обработва гранични случаи (нулеви стойности, препълване). scaledDensity се променя при промяна на настройките на шрифта чрез Settings > Display > Font size.

Коефициенти на мащабиране

Android предоставя пет предварително зададени нива на мащаб на шрифта: Small (0.85×), Default (1.0×), Large (1.15×), Largest (1.3×) и допълнително ниво Very Large (>1.3×) в Android 14+. Производителите на устройства (Samsung, Xiaomi) добавят собствени нива — до 2.0×. Минималният размер на текст в sp никога не гарантира фиксиран брой пиксели.

Използване на sp в XML

В XML sp се използва изключително в атрибута android:textSize. Всички останали размери — width, height, padding, margin, elevation — се задават в dp. Правилото е просто: ако елемент показва текст — размерът му в sp, ако елемент определя геометрия — размерът в dp.

Основен пример за textSize в XML

xml
<!-- Оформление на TextView с textSize в sp -->
<TextView
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:text="@string/hello"
    android:textSize="16sp"
    android:padding="12dp"
    android:lineSpacingExtra="4dp" />

<!-- Използване на dimens ресурси -->
<TextView
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:textSize="@dimen/text_body_large" />

Препоръчва се изнасяне на размерите на текста във файла dimens.xml. Това опростява поддръжката на типографията, позволява презаписване на размери за различни конфигурации на екрана и осигурява еднородност в цялото приложение.

dimens.xml с типографски токени

xml
<!-- res/values/dimens.xml -->
<resources>
    <!-- Material Design Type Scale -->
    <dimen name="text_display_large">34sp</dimen>
    <dimen name="text_display_medium">28sp</dimen>
    <dimen name="text_headline_large">24sp</dimen>
    <dimen name="text_headline_medium">20sp</dimen>
    <dimen name="text_title_large">18sp</dimen>
    <dimen name="text_body_large">16sp</dimen>
    <dimen name="text_body_medium">14sp</dimen>
    <dimen name="text_label_large">14sp</dimen>
    <dimen name="text_label_small">11sp</dimen>
</resources>

Material Design Type Scale включва 13 нива на размери — от 11sp за малки етикети до 57sp за големи дисплейни заглавия. Android проектите обикновено използват 8–10 нива. Всички стойности трябва да са кратни на 1sp — дробните стойности (15.5sp) влошават рендирането поради субпикселно позициониране.

Настройка на типография чрез Kotlin

В модерната Android разработка текстът рядко се задава директно чрез textSize в sp. Вместо това се използва системата MaterialTheme.typography, където всеки стил е предварително дефиниран и включва размер, тегло, междуредие и letter-spacing.

kotlin
// Персонализирана типография чрез Typography API
val AppTypography = Typography(
    displayLarge = TextStyle(
        fontWeight = FontWeight.Normal,
        fontSize = 34.sp,
        lineHeight = 40.sp,
        letterSpacing = 0.sp
    ),
    headlineLarge = TextStyle(
        fontWeight = FontWeight.SemiBold,
        fontSize = 24.sp,
        lineHeight = 32.sp
    ),
    titleLarge = TextStyle(
        fontWeight = FontWeight.Medium,
        fontSize = 18.sp,
        lineHeight = 24.sp
    ),
    bodyLarge = TextStyle(
        fontWeight = FontWeight.Normal,
        fontSize = 16.sp,
        lineHeight = 24.sp,
        letterSpacing = 0.5.sp
    ),
    labelSmall = TextStyle(
        fontWeight = FontWeight.Medium,
        fontSize = 11.sp,
        lineHeight = 16.sp,
        letterSpacing = 0.5.sp
    )
)

Функцията за разширение .sp в Jetpack Compose автоматично се превежда на scale-independent pixels. При промяна на размера на системния шрифт, Compose преизчислява fontSize, lineHeight и spacing според новия scaledDensity. TextUnit (класът, представляващ sp) гарантира, че текстът се мащабира, а разстоянията — не.

sp в Jetpack Compose

В Jetpack Compose sp е представен от типа TextUnit, който не може случайно да се използва за размери на елементи. Компилаторът на Kotlin дава грешка, ако TextUnit бъде предаден там, където се очаква Dp. Това елиминира цял клас грешки, свързани с неправилно мащабиране.

kotlin
// TextUnit в Compose — безопасна работа със sp
@Composable
fun ArticleCard(title: String, description: String) {
    Card(modifier = Modifier
        .fillMaxWidth()
        .padding(16.dp)
    ) {
        Text(
            text = title,
            style = MaterialTheme.typography.titleLarge
        )
        Spacer(modifier = Modifier.height(8.dp))
        Text(
            text = description,
            style = MaterialTheme.typography.bodyMedium
        )
    }
}

// Изрично задаване на fontSize в sp
Text(
    text = "Персонализиран размер",
    fontSize = 20.sp,
    fontWeight = FontWeight.Bold,
    color = MaterialTheme.colorScheme.primary
)

В Compose няма пряк еквивалент на XML атрибута android:textSize — размерът на текста се задава чрез TextStyle.fontSize. Системата MaterialTheme.typography предоставя предварително дефинирани стилове, които съответстват на Material Design Type Scale. Ако е необходим персонализиран размер, се използва литералът 20.sp — езикът гарантира, че това е TextUnit, а не Dp.

Най-добри практики за работа с sp

Правилното използване на sp — основата на достъпно Android приложение. По-долу са събрани правила, базирани на препоръките на Google Material Design и Android Developers Guide.

  • Винаги използвайте sp за текст — никога не задавайте textSize в dp или px, в противен случай потребителите с увеличен шрифт няма да могат да четат интерфейса
  • Използвайте dp за контейнери — височината на бутоните, разстоянията и ширината на картите трябва да са в dp, в противен случай при голям шрифт елементите могат да се припокриват
  • Изнасяйте размерите в dimens.xml — централизираното съхранение на типографски токени опростява рефакторирането и поддръжката на тъмна тема
  • Не използвайте sp по-малък от 12sp — текст с по-малък размер става нечетлив на устройства с висок PPI и при стандартен шрифт
  • Тествайте при максимален мащаб на шрифта — включете в настройките на устройството най-големия шрифт и проверете дали интерфейсът не се разбива

Основното правило за достъпност: потребителят трябва да има възможност да увеличи шрифта без загуба на функционалност. Ако приложението работи правилно при мащаб на шрифта 1.3×, то ще премине основните тестове за достъпност. Google Play може да отхвърли приложението, ако textSize е зададен в dp и интерфейсът не се мащабира.

Често задавани въпроси

Каква е разликата между sp и dp?

sp (scale-independent pixel) се мащабира при промяна на размера на системния шрифт, а dp — не. sp се използва само за текст, dp — за всички останали размери на елементи. Коефициент на преобразуване: sp = dp × FONT_SCALE.

Може ли sp да се използва за разстояния?

Не. Разстоянията, височината на бутоните, ширината на картите трябва да се задават в dp. Използването на sp за разстояния води до неестествен растеж на елементите при увеличаване на шрифта и те могат да излязат извън границите на екрана.

Как да проверя дали приложението работи правилно с sp?

Отворете Settings > Display > Font size и задайте максималната стойност (Largest). Стартирайте приложението и проверете дали целият текст е четим, елементите не се припокриват и бутоните не излизат извън границите на екрана. За автоматизация използвайте Espresso с UiAutomator.

Какъв е минималният допустим размер на текст в sp?

Material Design препоръчва минимален размер 11sp за labelSmall. За основен текст — от 14sp (bodyMedium) до 16sp (bodyLarge). Размери по-малки от 11sp не се препоръчват, тъй като стават нечетливи на устройства с висока плътност на пикселите.

Какво ще се случи, ако задам textSize в dp?

Текстът ще се показва в фиксиран размер независимо от системните настройки на шрифта. Потребителите с увеличен шрифт няма да могат да четат удобно такъв текст. Това нарушава изискванията за достъпност WCAG и може да бъде причина за отхвърляне на приложението в Google Play.

Обобщение

  • sp — единица за измерване на шрифт в Android, мащабируема според настройките на потребителя чрез FONT_SCALE
  • dp — единица за размери на елементи, не реагира на промяна на размера на шрифта
  • textSize в XML се задава чрез android:textSize="16sp", всички останали размери — в dp
  • MaterialTheme.typography в Jetpack Compose използва TextUnit (.sp) за безопасност на типовете
  • dimens.xml — централизирано съхранение на типографски токени за еднородност
  • Минимален размер на текст — 11sp, препоръчителен за body — 14–16sp
  • Тестване при максимален мащаб на шрифта — задължителен етап от проверката на достъпността

Ще разработим мобилно приложение под ключ

IT Sectr създава iOS и Android приложения за стартъпи и бизнеси от 2017 г. Ще ви консултираме и ще предложим най-доброто решение.

Обсъдете проекта

Прочетете също