Ответ
Приоритет ограничения (Constraint Priority) — это числовое значение (UILayoutPriority), которое определяет важность ограничения в системе Auto Layout. Оно используется для разрешения конфликтов, когда не все заданные ограничения могут быть выполнены одновременно.
- Диапазон: от 1 до 1000.
- Required (Обязательное): Приоритет 1000. Система должна выполнить это ограничение. Конфликт обязательных ограничений приводит к ошибке макета (break).
- Optional (Необязательное): Приоритет < 1000 (например, 750, 250). Система пытается выполнить ограничение, но может его нарушить в пользу более приоритетного.
Стандартные приоритеты:
.required= 1000.defaultHigh= 750 (Высокий, например, дляcontentHuggingPriority).defaultLow= 250 (Низкий, например, дляcontentCompressionResistancePriority)
Как работает: При конфликте Auto Layout создает систему уравнений. Приоритеты влияют на «жесткость» этих уравнений. Ограничения с более высоким приоритетом удовлетворяются в первую очередь.
Пример на Swift:
let view = UIView()
view.translatesAutoresizingMaskIntoConstraints = false
// 1. Ограничение ширины 200 (высокий приоритет)
let widthConstraint = view.widthAnchor.constraint(equalToConstant: 200)
widthConstraint.priority = .defaultHigh // 750
// 2. Ограничение ширины <= 300 (низкий приоритет)
let maxWidthConstraint = view.widthAnchor.constraint(lessThanOrEqualToConstant: 300)
maxWidthConstraint.priority = .defaultLow // 250
// 3. Ограничение «растянуть по ширине родителя» (обязательное)
let leadingConstraint = view.leadingAnchor.constraint(equalTo: superview.leadingAnchor)
let trailingConstraint = view.trailingAnchor.constraint(equalTo: superview.trailingAnchor)
// Приоритет по умолчанию .required (1000)
NSLayoutConstraint.activate([
widthConstraint, maxWidthConstraint, leadingConstraint, trailingConstraint
])
В этом сценарии:
- Обязательные ограничения
leadingиtrailingвыполнятся, пытаясь растянутьviewна всю ширину. - Это вступит в конфликт с
widthConstraint = 200. - Система сравнит приоритеты:
.required(1000) у растяжения против.defaultHigh(750) у фиксированной ширины. - Будет нарушено ограничение с приоритетом 750 (
widthConstraint), и ширина станет больше 200. - Ограничение
maxWidthConstraint(приоритет 250) также будет нарушено, если итоговая ширина превысит 300.
Ответ 18+ 🔞
Ну, слушай, вот есть у тебя эта ваша Auto Layout, да? Красивая такая, уравнения строит, всё по линеечкам расставляет. А потом — бац! — и получается, что твои вьюхи хотят одновременно быть и широкими, и узкими, и посередине, и по краям. Пиздец, в общем. И вот тут-то на сцену выходит приоритет ограничения — это типа такой рейтинг важности, цифра от 1 до 1000, которая решает, какое желание вьюхи выполнить в первую очередь, а какое можно, прости господи, послать нахуй.
Представь, что это как спор между «хочу пиццу» (приоритет 250) и «надо на работу» (приоритет 750). Работа поважнее, так что пиццу отменяем. Но если «дом горит» (приоритет 1000), то на работу тоже похуй — бежим тушить.
- Обязательное (Required): Это приоритет 1000. Это не просьба, это приказ. Если два таких приказа начинают драться насмерть (например, «будь шириной 200» и «растянись на весь экран»), система просто плюёт на всё и говорит: «Ребята, я не могу, тут пиздец» — и ломает макет. В консоли будет красненькое, всё грустно.
- Необязательное (Optional): Всё, что ниже 1000. Система попытается его выполнить, но если что-то более важное помешает — ну, извини, дружок. Есть стандартные значения:
.defaultHigh(750) и.defaultLow(250). Их часто используют для всякихcontentHuggingPriority(не дать растянуться) иcontentCompressionResistancePriority(не дать сжаться).
Как это работает, блядь? Auto Layout строит систему уравнений. Приоритет — это как «жесткость пружины» в этом уравнении. Чем выше приоритет, тем туже закручена пружина, и её сложнее растянуть или сжать. Система сначала удовлетворяет самые тугые пружины, а на остальные уже по остаточному принципу.
Смотри пример, сейчас будет магия:
let view = UIView()
view.translatesAutoresizingMaskIntoConstraints = false
// 1. Хочу быть шириной 200 пикселей. Приоритет высокий, но не обязательный.
let widthConstraint = view.widthAnchor.constraint(equalToConstant: 200)
widthConstraint.priority = .defaultHigh // 750
// 2. Но, блин, больше 300 пикселей — это уже перебор. Приоритет низкий.
let maxWidthConstraint = view.widthAnchor.constraint(lessThanOrEqualToConstant: 300)
maxWidthConstraint.priority = .defaultLow // 250
// 3. А ещё меня прибили к левому и правому краю родителя. Это железное правило!
let leadingConstraint = view.leadingAnchor.constraint(equalTo: superview.leadingAnchor)
let trailingConstraint = view.trailingAnchor.constraint(equalTo: superview.trailingAnchor)
// У этих парней приоритет по умолчанию .required (1000), они главные тут.
NSLayoutConstraint.activate([
widthConstraint, maxWidthConstraint, leadingConstraint, trailingConstraint
])
И что в итоге, ёпта?
- Железные ребята (
leadingиtrailing) с приоритетом 1000 говорят: «Растягивайся на всю ширину родителя!» - Первое желание (
width = 200) с приоритетом 750 орёт: «Нет, стой, будь узенькой!» - Система смотрит на цифры: 1000 против 750. И говорит первому желанию: «Извини, чувак, ты проиграл». Ограничение на 200 пикселей нарушается.
- Второе желание (
width <= 300) с приоритетом 250 вообще тихонько сидит в углу. Если родитель шире 300 пикселей, это ограничение тоже полетит в пизду, потому что приоритеты 1000 (растянуться) и 750 (быть 200) всё равно важнее, чем «не быть больше 300».
Вот и вся магия. Расставляй приоритеты с умом, а то вьюхи разбегутся кто куда, как тараканы от света.