UIScrollView Прокручиваемый размер содержимого Неоднозначность

У меня есть проблемы с AutoLayout в Interface Builder (Xcode 5 / iOS 7). Это очень просто и очень важно, поэтому я думаю, что каждый должен знать, как это работает. Если это ошибка в Xcode, это очень важно!

Итак, всякий раз, когда у меня есть иерархия представлений, такая как я сталкиваюсь с проблемами:

UIViewController

UIView

UIScrollView

UILabel (или любой другой сопоставимый элемент UIKit)

UIScrollView имеет жесткие ограничения, например, 50 пикселей со всех сторон (без проблем). Затем я добавляю ограничение по верхнему пространству в UILabel (без проблем) (и я даже могу выровнять высоту / ширину метки, ничего не меняет, но должен быть ненужным из-за собственного размера Label)

Проблема возникает, когда я добавляю трейлинг-ограничение в UILabel:

Например, Trailing Space для: Superview Equals: 25

Теперь возникают два предупреждения – и я не понимаю, почему:

A) Масштабируемость прокручиваемого содержимого (просмотр прокрутки имеет неоднозначную прокручиваемую высоту / ширину содержимого)

B) Неверные представления (Ожидаемая метка: x = -67 Фактическое значение: x = 207

Я сделал этот минимальный пример в новом новом проекте, который вы можете скачать, и я прикрепил скриншот. Как вы можете видеть, Interface Builder ожидает, что ярлык будет находиться за пределами границы UIScrollView (оранжевый пунктирный прямоугольник). Обновление рамки Label с помощью инструмента Resolve Issues Tool перемещает его прямо там.

Обратите внимание: если вы замените UIScrollView на UIView, поведение будет таким, как ожидалось (рамка Label верна и соответствует ограничению). Так что, похоже, проблема с UIScrollView или я упускаю что-то важное.

Когда я запускаю приложение, не обновляя рамку Label, как было предложено IB, он позиционируется просто отлично, где он должен быть, и UIScrollView прокручивается. Если я обновляю фрейм, ярлык скрыт из виду, а UIScrollView не будет прокручиваться.

Помоги мне Оби-Ван Кеноби! Почему неоднозначный макет? Почему неправильный вид ???

Вы можете скачать образец проекта здесь и попробовать, если вы можете выяснить, что происходит: https://github.com/Wirsing84/AutoLayoutProblem

Иллюстрация проблемы в интерфейсе Builder

22 Solutions collect form web for “UIScrollView Прокручиваемый размер содержимого Неоднозначность”

Поэтому я просто разобрался в этом:

  1. Добавьте в UIScrollView UIView (мы можем назвать это contentView );

  2. В этом contentView установите верхнее, нижнее, левое и правое поля на 0 (конечно, из scrollView который является superView ); Установите также выравнивание по горизонтали и по вертикали ;

Закончено .

Теперь вы можете добавить все свои представления в этот contentView , а contentSize scrollView будет автоматически изменяться в соответствии с contentView .

Обновить:

Некоторое частное дело освещено этим видео, опубликованным @Sergio в комментариях ниже.

Эта ошибка заняла некоторое время для отслеживания, изначально я попытался укрепить размер ScrollView, но в сообщении об ошибке четко сказано «размер содержимого». Я убедился, что все, что я приколол с вершины ScrollView, также было закреплено на дне. Таким образом ScrollView может вычислять свою высоту содержимого, определяя высоту всех объектов и ограничений. Это разрешило неоднозначную высоту контента, ширина очень похожа … Первоначально у меня было большинство вещей X, сосредоточенных в ScrollView, но мне пришлось также привязывать объекты к стороне ScrollView. Мне это не нравится, потому что iPhone6 ​​может иметь более широкий экран, но он удалит ошибку «неоднозначной ширины содержимого».

Это ответ для моего ответа на вопрос UIScrollView + Centered View + Ambigous Scrollable Content Size + много размеров iPhone .

Но он полностью покрывает ваше дело!

Итак, вот начальное состояние для простейшего случая:

  1. scrollView с 0 ограничениями для всех ребер
  2. Кнопка центрирована по горизонтали и по вертикали с фиксированными ограничениями ширины и высоты
  3. И, конечно же, раздражающие предупреждения имеют Has ambiguous scrollable content width и имеют Has ambiguous scrollable content height .

1

Все, что нам нужно сделать, это:

  • Добавьте еще 2 дополнительных ограничения, например «0» для трейлинга и / или нижнего пространства для нашего представления (см. Пример на скриншоте ниже).

Важно: вам нужно добавить ограничивающие и / или нижние ограничения. Не «ведущий и топ» – это не работает!

2

Вы можете проверить это в моем примере проекта , демонстрируя, как исправить эту проблему.

PS

Согласно логике – это действие должно вызывать «конфликтующие ограничения». Но нет!

Я не знаю, почему это работает и как Xcode обнаруживает, какое ограничение более приоритетно (потому что я не задал приоритет для этих ограничений). Я буду благодарен, если кто-нибудь объяснит, почему он работает в комментариях ниже.

У меня была та же проблема и после поиска документации и не найти приемлемого решения. Вам необходимо создать UIView в качестве подзадачи UIScrollView, как описано ниже:

  • UIViewController
  • UIView 'Main View'
    • UIScrollView
      • UIView 'Container View'
        • [Ваше содержание]

Второй шаг – сделать ограничения UIScrollView. Я сделал это с верхними, нижними, ведущими и конечными ограничениями для своего супервизора.

Затем я добавил ограничения для контейнера UIScrollView и вот где проблема начинается. Когда вы устанавливаете те же ограничения (верхний, нижний, верхний и конечный), Storyboard выдает предупреждающее сообщение:

«Имеет неоднозначную ширину прокручиваемого содержимого» и «Имеет неоднозначную прокручиваемую высоту содержимого»,

Продолжите с теми же ограничениями выше, и просто добавьте ограничения к « Равная высота » и « Равная ширина » в свой вид контейнера по отношению к главному виду, а не к вашему UIScrollView. Другими словами, ограничения Container View привязаны к супервизору UIScrollView.

После этого у вас не будет предупреждений в вашей раскадровке, и вы можете продолжить добавлять ограничения для своих подзонов.

Я надеюсь, что это помогает кому-то.

Я, наконец, понял это, надеюсь, это легче понять.

Вам обязательно нужно добавить базовый UIView в scrollview как «контент-представление», как они упомянули, и сделать его того же размера, что и прокрутка, и на этом представлении содержимого установить эти 6 параметров.

введите описание изображения здесь

Как вы можете видеть, вам нужны 6 полных параметров! Что … при нормальных обстоятельствах вы дублируете 2 ограничения, но это способ избежать этой ошибки в раскадровке.

Я знаю, что могу опоздать, но следующее решение решает такие проблемы без дополнительного кода , просто используя раскадровки:

Для просмотра содержимого вам нужно установить ограничения для ведущих / конечных / верхних / нижних пробелов для scrollview, и это не изменит рамки представления контента , например: введите описание изображения здесь

Конечно, вам нужно создать дополнительные ограничения для просмотра контента, чтобы прокрутка могла знать размер содержимого. Например, установите фиксированную высоту и центр x.

Надеюсь это поможет.

Посмотрите на это очень быстро и на точечный учебник о том, как заставить просмотр прокрутки работать и полностью прокручиваться с автоматической компоновкой. Теперь единственное, что все еще оставляет меня озадаченным, – это то, почему размер содержимого прокрутки всегда больше, чем необходимо ..

http://samwize.com/2014/03/14/how-to-use-uiscrollview-with-autolayout/

См. Ниже: просмотр содержимого в вертикальном и горизонтальном централизованном виде. вы получили ошибку двусмысленности, всегда убедитесь, что два добавленных в scrollview из вашего представления содержимого: 1) .button space to container.2), переходящее пространство в ограничение, выделенное на снимке экрана,

эти средства ограничения в прокрутке – это сколько вы можете прокручивать после высоты или ширины вашего контента.

введите описание изображения здесь

это может помочь вам.

Ответ @Matteo Gobbi является идеальным, но в моем случае прокрутка не может прокручиваться, я удаляю « align center Y » и добавляю « height> = 1 », scrollview станет прокручиваемым

Для меня добавление contentView действительно не срабатывало, как было предложено. Более того, он создает накладные расходы из-за добавленного представления (хотя я не считаю это большой проблемой). Для меня лучше всего было отключить проверку двусмысленности для моего scrollView . Все складывается красиво, поэтому я думаю, что это нормально в простых случаях, таких как мои. Но имейте в виду, что если другие ограничения для вашего scrollView ломаются, Interface-Builder больше не будет предупреждать вас об этом.

введите описание изображения здесь

Используя contentView (UView) в качестве контейнера внутри UIScrollView, придерживайтесь краев (верхний, нижний, конечный, ведущий) супервизора (UIScrollView), а contentView должен иметь равную ширину и высоту для просмотра. Это ограничения. И вызов метода:

 -(void)viewDidLayoutSubviews { [super viewDidLayoutSubviews]; self.scrollView.contentSize = self.contentView.frame.size; } 

Решенные проблемы для меня.

Люди, которые борются с uiscrollview, а не прокруткой, просто ограничивают нижнее ограничение нижестоящего содержимого вашим нижним макетом последнего представления (которое находится внутри вашего содержимого). Не забудьте удалить ограничение центра Y.

Остальные все ограничения такие же, как указано выше. Scrollview беспокоится только о том, чтобы получить максимальную высоту из своего представления содержимого, и мы устанавливаем его как нижнее ограничение последнего вида, что означает, что scrollview автоматически изменит его смещение содержимого.

В моем случае последнее представление было UILable без свойства lines = 0 (которое автоматически регулирует его высоту в зависимости от его содержимого), чтобы оно динамически увеличивало высоту uilable и, в конечном итоге, нашу область прокручивания увеличивалась из-за того, что нижний макет uilable выравнивается с нижней частью нашего контента, который заставляет scrollview увеличивать смещение содержимого.

То, что я сделал, это создать отдельный контент, как показано здесь.

Представление контента является свободной формой и может иметь все подзаголовки, добавленные к нему со своими ограничениями по отношению к contentView.

UIScrollView добавляется в основной контроллер представления.

Программно я добавляю contentView, который связан через IBOutlet с классом и устанавливает contentView UIScrollView.

UIScrollView с ContentView через интерфейс Builder

Я получал ту же ошибку. Я сделал следующее

  1. Просмотр (SuperView)
  2. ScrollView 0,0,6600,600
  3. UIView внутри ScrollView: 0,0,600,600
  4. UIView содержит изображение, метку

Теперь добавьте ведущий / конечный / верхний / нижний для scrollView (2), затем UIView (3).

Выберите «Вид» (1) и «Вид» (3), заданный одинаково по высоте и весу.

Я сделал видео, которое поможет:

https://www.youtube.com/watch?v=s-CPN3xZS1A

[проверено в XCode 7.2 и для iOS 9.2]

То, что подавляло ошибки и предупреждения Storyboard для меня, заключалось в определении внутреннего размера прокрутки и просмотра содержимого (в моем случае, стека) для Placeholder . Этот параметр можно найти в инспекторе размера в раскадровке. И в нем говорится: настройка размера внутреннего содержимого времени разработки влияет только на представление при редактировании в Interface Builder. У представления не будет такого внутреннего размера содержимого во время выполнения.

Итак, я думаю, мы не ошибаемся, установив это.

Примечание. В раскадровке я привязал все края scrollview к супервизу и всем краям stackview к scrollview. В моем коде я установил translatesAutoresizingMaskIntoConstraints как false как для scrollview, так и для stackview. И я не упомянул о размере контента. Когда стековый просмотр растет динамически, ограничения, установленные в раскадровке, гарантируют, что стек прокручивается.

Предупреждение раскадровки сводило меня с ума, и я не хотел центрировать вещи горизонтально или вертикально, чтобы подавить предупреждение.

Если кто-то получает поведение, когда вы замечаете полосу прокрутки на правом свитке, но контент не перемещается, этот факт, вероятно, стоит рассмотреть:

Вы также можете использовать ограничения между содержимым и объектами прокрутки за пределами прокрутки, чтобы обеспечить фиксированную позицию для содержимого вида прокрутки, заставляя это содержимое отображаться в виде прокрутки.

Это из документации Apple. Например, если вы случайно привязали свой верхний ярлык / Button / Img / View к виду вне области прокрутки (может быть, заголовок или что-то еще выше scrollView?) Вместо contentView, вы бы заморозили весь контентный просмотр на месте.

Как упоминалось в предыдущих ответах, вы должны добавить пользовательский вид внутри прокрутки:

Пользовательский вид - это ContentView, помеченный на изображении

Добавьте все ваши подпрограммы в представление содержимого. В какой-то момент вы увидите, что просмотр содержимого прокрутки имеет предупреждение неоднозначного размера содержимого, вы должны выбрать представление контента и нажать кнопку «Разрешить авто макет» (в нижнем правом углу макета IB) и выбрать «Добавить отсутствующий ограничения ".

введите описание изображения здесь

Теперь, когда вы запускаете проект, в режиме прокрутки будет автоматически обновляться его размер содержимого, без дополнительного кода.

Вам просто нужно убедиться, что существует способ сделать непрерывную линию ограничений сверху вниз в scrollview. [-XXX]

В моем случае – прокрутка по горизонтали прокрутки – мне также нужно было добавлять ограничения ширины и высоты для каждого дочернего элемента прокрутки, хотя техническая заметка Apple не говорит об этом.

Установите для ViewController (тот, который имеет UIScrollView) размер Freeform в инспекторе размеров в Interface Builder, и все должно работать.

Настройка свободной формы в инспекторе размеров в Interface Builder для содержащего UIViewcontroller

Самый простой способ использования автозапуска:

  1. Добавьте UIScrollView и запишите его 0,0,0,0 для просмотра (или желаемого размера)
  2. Добавьте UIView в ScrollView, прикрепите его 0,0,0,0 ко всем 4 сторонам и центрируйте его по горизонтали и по вертикали.
  3. В инспекторе размеров измените значение «bottom» и «align center Y» на значение 250.
  4. Добавьте все представления, которые вам нужны в этом представлении. Не забудьте установить нижнее ограничение на нижний вид.

все подсмотры внутри scrollview должны иметь ограничения, затрагивающие все края прокрутки, как объясняется в документации, высота и ширина прокрутки автоматически вычисляются с помощью мер в подзонах, это означает, что вам нужно иметь Трейлинг и ведущие ограничения для ширины и верхних и нижних ограничений для высоты.

Я думаю, что это 10-секундная работа. Я заметил это в XCode 7.3 и сделал видео на нем. Проверить здесь:

https://www.youtube.com/watch?v=yETZKqdaPiI

Все, что вам нужно сделать, добавить subview в UIScrollView с одинаковой шириной и высотой. Затем выберите ViewController и нажмите Reset to suggested constraint . Пожалуйста, проверьте видео для четкого понимания.

благодаря

Interesting Posts

UIView.animate – Swift 3 – завершение

UIDynamicAnimator Встряска с пружинным эффектом

Передача nil в archivedDataWithRootObject возвращает странные NSData

AVCaptureVideoPreviewLayer (предварительный просмотр камеры) зависает / застревает после перемещения на задний план и обратно

iOS – поддерживает ли AVFoundation 3D-штрих-коды?

Отображать изображение из пути в imageView в ios

Системный шрифт «Hiragino Sans» – это шоу с подрезанным поджатием и спусками

Два проекта с одинаковой базой кода

Кадр AVCaptureVideoPreviewLayer в Swift

Swift – итерация по символам в строке вызывает утечку памяти

Как преобразовать HTML в Markdown в iOS / OS X? Любой способ использовать pandoc в приложении?

Сложная сортировка для запроса выборки ядра

Анимация новой вставки данных в основной сюжет (iOS)

Правильный способ преобразования CGColors между цветами

Градиент треугольника с базовой графикой

PhoneC: Разработка iOS проста с помощью XCode, Swift3, UITableView, cocatouch, давайте создадим приложения для iPhone, iPad и Macbook.