Вимкнення вертикальної прокрутки в UIScrollView


84

У IB є можливість зняти прапорець вертикальної прокрутки в режимі прокрутки, але, схоже, це не працює.

Як можна встановити для прокручування перегляд лише горизонтально, а не вертикально в коді, а не IB?


Відповіді:


121

Спробуйте встановити висоту contentSize на висоту scrollView. Тоді вертикальну прокрутку слід відключити, тому що не було б чого прокручувати вертикально.

scrollView.contentSize = CGSizeMake(scrollView.contentSize.width,scrollView.frame.size.height);

Ви просто заощадили мені багато часу, налагоджуючи цю дивну проблему. Дякую!
— jpm

2
@fabb, як можна знати, коли кадр змінюється?
— Сем

137

з iOS7:

по-перше: ширина розміру вмісту повинна дорівнювати ширині перегляду прокрутки

друге: у вашому initWithNibName:

self.automaticallyAdjustsScrollViewInsets = NO;

Це воно.


Чудове рішення. Працював як оберіг. Чи вплине це на розмір решти переглядів у моєму ViewController? (Кнопки, мітки ..) Я маю на увазі, що "self" - це UIViewController у моєму випадку
— voghDev

@voghDev ні, це не впливає на підпрогляди у вашому прокручуваному перегляді.
— Мірко Бруннер

Amazing додав це до методу viewdidload на моїх контролерах перегляду, які мали проблеми.
— StackRunner

якщо ви використовуєте navigationController, а ваш прокручуваний перегляд стоїть за назвою навігаційної панелі, як це використовується при методі viewDidLoad Це вирішує.
— EFE

1
Ви можете досягти того ж у налаштуваннях розкадрування безпосередньо без будь-якого рядка коду. Просто виберіть контролер перегляду прокрутки та зніміть прапорець "Налаштувати вставки прокрутки перегляду" в інспекторі атрибутів.
— Morpheus78,

49

так, відповідь pt2ph8 правильна,

але якщо з якихось дивних причин розмір вашого вмісту повинен бути вищим, ніж UIScrollView, ви можете відключити вертикальну прокрутку, реалізуючи метод протоколу UIScrollView

 -(void)scrollViewDidScroll:(UIScrollView *)aScrollView;

просто додайте це у свій UIViewController

float oldY; // here or better in .h interface

- (void)scrollViewDidScroll:(UIScrollView *)aScrollView
{
    [aScrollView setContentOffset: CGPointMake(aScrollView.contentOffset.x, oldY)];
    // or if you are sure you wanna it always on top:
    // [aScrollView setContentOffset: CGPointMake(aScrollView.contentOffset.x, 0)];
}

це просто метод, що викликається, коли користувач прокручує ваш UIScrollView, і, роблячи це, ви змушуєте вміст його мати завжди однаковий .y


6
Боже! Будь ласка, НЕ оголошуйте змінну oldY у файлі .m, як float oldY;посилання на наведений код. Це символ змінної в стилі C для кожної програми, змінна ПОВИННА бути оголошена як член екземпляра класу контролера.
— Ітачі

21

Включіть наступний метод

-(void)viewDidLayoutSubviews{
    self.automaticallyAdjustsScrollViewInsets = NO;
}

та встановіть ширину розміру вмісту подання прокрутки, рівну ширині подання прокрутки.


1
Це також можна зробити в Storyboard, вибравши контролер перегляду та знявши прапорець там
— justColbs

1
Мені це не подобається, оскільки це встановлює його для всіх видів прокрутки ... Бажаю, щоб ви могли бути конкретним одним видом прокрутки на діаграмі без створення нового класу ScrollView тощо
— visc

20

Вам потрібно передати 0 за розміром вмісту, щоб відключити, у якому напрямку ви хочете.

Щоб вимкнути вертикальну прокрутку

scrollView.contentSize = CGSizeMake(scrollView.contentSize.width,0);

Щоб вимкнути горизонтальну прокрутку

scrollView.contentSize = CGSizeMake(0,scrollView.contentSize.height);

1
Це встановить для contentSize подання значення 0 на заданій осі. ContentSize має на увазі розмір вмісту, тому ми хочемо перейти у висоту екрана, щоб вимкнути вертикальну прокрутку поза цим кадром. рішення, позначене як правильне, є правильним.
— система

Це добре в мене вийшло. встановлення висоти як contentSize по висоті все ще змусило мене вертикальну прокрутку.
— KoreanXcodeWorker

1
У мене це не спрацювало. Також пробував self.automaticallyAdjustsScrollViewInsets
— StackRunner

Це воно! Налаштування висоти режиму прокрутки для мене не спрацювало, але це зробило
— Echizzle

18

Я оновив розмір вмісту, щоб вимкнути вертикальну прокрутку, і можливість прокрутки все ще залишалася. Потім я зрозумів, що мені потрібно також відключити вертикальний відмов, щоб повністю відключити прокрутку.

Можливо, теж є люди з цією проблемою.


Ти врятував мене. Мій розмір вмісту та рамки були однаковими, і я не міг за все своє життя зрозуміти, що сталося. Спасибі купу !!
— юф

2
Ваша відповідь - чому я люблю stackoverflow! :-) Святий дим ... це збило мене з розуму! Ти правий. Це ефект відскоку. Я хочу ефект відскоку, але не тоді, коли немає необхідності прокручувати, тому я буду прагнути вимкнути / повторно ввімкнути цей ефект зараз у коді, залежно від того, чи потрібно прокручувати.
— Ерік ван дер Нойт,

2
Гаразд, дуже легко ввімкнути / вимкнути відскаки на UIScrollView під час виконання. У моєму випадку мені важлива лише висота вмісту прокрутки, і це зробило трюк: self.scrollView.bounces = (BOOL) (self.scrollView.contentSize.height> self.scrollView.frame.size.height);
— Ерік ван дер Нойт,

12
- (void)scrollViewDidScroll:(UIScrollView *)aScrollView
{
    [aScrollView setContentOffset: CGPointMake(aScrollView.contentOffset.x,0)];

}

ви, мабуть, підтвердили UIScrollViewDelegate

aScrollView.delegate = self;

4

Просто встановіть y, щоб він завжди був зверху. Потрібно відповідати UIScrollViewDelegate

func scrollViewDidScroll(scrollView: UIScrollView) {
        scrollView.contentOffset.y = 0.0
}

Це збереже ефект уповільнення / прискорення прокрутки.


4

У iOS 11, будь ласка, не забудьте додати наступне, якщо ви зацікавлені у створенні прокрутки, яка чіпляється до меж екрана, а не до безпечної зони.

if (@available(iOS 11.0, *)) {
    [self.scrollView setContentInsetAdjustmentBehavior:UIScrollViewContentInsetAdjustmentNever];
}

1
після всього. спасибі тисячу разів, сер! ти врятував мій день
— ha100

0

З iOS11 можна використовувати наступну властивість

let frameLayoutGuide: UILayoutGuide

Якщо ви встановите обмеження для frameLayoutGuide.topAnchor і frameLayoutGuide.bottomAnchor для тих самих прив'язок деякого підвиду вашого scrollView тоді вертикальна прокрутка буде вимкнена, а висота scrollView буде дорівнює висоті її подання.


0

Найбільш очевидне рішення - заборонити зміни координат y у вашому підкласі.

override var contentOffset: CGPoint {
  get {
    return super.contentOffset
  }
  set {
    super.contentOffset = CGPoint(x: newValue.x, y: 0)
  }
}

Це єдине підходяще рішення в ситуаціях, коли:

  1. Вам заборонено або просто не хочете використовувати делегат.
  2. Висота вмісту перевищує висоту контейнера

0

Багато відповідей включають встановлення значення contentOffset0. У мене був випадок, коли я хотів, щоб вид всередині scrollView був центрований. Це зробило роботу для мене:

public func scrollViewDidScroll(_ scrollView: UIScrollView) {
    scrollView.contentOffset.y = -scrollView.contentInset.top
}
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.