Форум программистов, компьютерный форум CyberForum.ru

Программирование iOS/iPhone

Войти
Регистрация
Восстановить пароль
 
Рейтинг: Рейтинг темы: голосов - 13, средняя оценка - 5.00
arsgram
0 / 0 / 0
Регистрация: 07.07.2013
Сообщений: 14
#1

Модальный ViewController - Программирование iOS/iPhone

05.02.2014, 08:59. Просмотров 1630. Ответов 14
Метки нет (Все метки)

Здравствуйте!
На выходных начал щупать разработку под iOS, до этого макось даже не видел.
Вокруг столько всего непонятного, аж глаза разбегаются.

Столкнулся с проблемой.
Есть UITabViewController и внутри него 4 UIViewController'а, у каждого контроллера переопределён свой класс, а у некоторых есть ещё и потомки вью-контроллеры.
Суть в том, что каждое некое действие(переключение между табами, нажатие кнопок в навигации) нужно проверять некий параметр, пусть будет NSString *ID и, если он nil, то вызывать модально(!) ViewController(внутри с WebView). Первое, что бросается в глаза - это deprecated present/dismissModalViewController.
Не знаю как было раньше, но сейчас вызов таким образом контроллера не блокирует основной цикл событий.
Например, пишу:
C
1
2
3
4
5
6
7
8
// Где-то в классе объекта iWannaBeModal
-(NSString *)doEpicStuff
{
     int blowTheUniverse = 42/0;
     return @"Done!";
}
// ~
if(!ID){ NSString *result = [iWannaBeModal doEpicStuff]; }
Смотрю дебаггером, iWannaBeModal вызывается в отдельном потоке, а цикл событий идёт дальше. Получается, что у меня result всегда nil.

Т.к. в iWannaBeModal живёт ещё и UIWebView, то хотелось бы дождаться завершения webViewDidFinishLoad и только потом вернуть значение. В принципе, если модально вызвать iWannaBeModal, то можно внутри класса в методе webViewDidFinishLoad присвоить нужное значение переменной, а потом его забрать. Как-нибудь так:
C
1
2
[iWannaBeModal becomeModal]; // Тут цикл событий останавливается пока не пропадёт модальный виджет
NSString *result = iWannaBeModal.result;
В итоге всё упирается в то, как вызвать iWannaBeModal модально. И необходимо ли для этого создавать контроллер в IB? Сейчас его нет. Создавал, думал через аутлеты привязать, но почему-то не смог их создать и забил.

Надеюсь на вашу помощь, товарищи.
После регистрации реклама в сообщениях будет скрыта и будут доступны все возможности форума.
mobidevelop
182 / 182 / 3
Регистрация: 10.01.2013
Сообщений: 596
05.02.2014, 10:44     Модальный ViewController #2
Цитата Сообщение от arsgram Посмотреть сообщение
42/0
Там exception просто валится Хоть на что-нибудь другое разделите
arsgram
0 / 0 / 0
Регистрация: 07.07.2013
Сообщений: 14
05.02.2014, 10:59  [ТС]     Модальный ViewController #3
Цитата Сообщение от mobidevelop Посмотреть сообщение
Там exception просто валится Хоть на что-нибудь другое разделите
Не валится там исключение, это просто как пример какой-либо операции
zulkis
681 / 608 / 38
Регистрация: 13.01.2011
Сообщений: 1,724
05.02.2014, 12:15     Модальный ViewController #4
mobidevelop, 42/0 - "Division by 0 is undefined."

arsgram, дело не в аутлетах. Просто возьмите и прочитайте, что такое аутлеты.
Для показа view "модально", у UIViewController есть метод:
Objective-C
1
- (void)presentViewController:(UIViewController *)viewControllerToPresent animated: (BOOL)flag completion:(void (^)(void))completion NS_AVAILABLE_IOS(5_0);
Цитата Сообщение от arsgram Посмотреть сообщение
И необходимо ли для этого создавать контроллер в IB?
Не обязательно в IB, но для того, чтобы у одного UIViewController-а вызвать вышеупомянутый метод, нужно в него передать другой UIViewController.
arsgram
0 / 0 / 0
Регистрация: 07.07.2013
Сообщений: 14
12.02.2014, 12:55  [ТС]     Модальный ViewController #5
zulkis, спасибо за наводку.
Всё равно не работает всё так, как я хочу.
У меня есть UITabBarController, просто на storyboard, класс я не переопределял.
У него есть UIViewController, чей класс я переопределил. Пусть будет vc1.
Есть ещё один контроллер, на которой UIWebView. Пусть он называется vc2.
Пишу:
C
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
// B vc1
-(void)viewDidLoad
{
[super viewDidLoad];
vc2 *pew = [[vc2 alloc] init];
[self presentViewController: pew animated: YES completion: nil];
}
 
//B vc2
//...
@property (nonatomic, retain) UIWebView *webView;
//...
-(void)viewDidLoad
{
[super viewDidLoad];
if(!self.webView)
{
self.webView = [[UIWebView alloc] initWithFrame: self.view.bounds];
[self.view addSubView:self.webView];
self.webView.delegate = self;
}
}
При загрузке ничего не появляется, а в аутпуте пишет:
"Attempt to present <vc2> on <UITabBarController> whose view is not in the window hierarchy!"
Не понимаю, причём тут UITabBarController? Ведь vc1, поверх которого я пытаюсь вывести vc2, - это же UIViewController.

И ещё один эпический вопрос. Например, vc2 сделал то, что от него требовалось и теперь надо его убрать + выполнить некую функцию в vc1. Как это сделать?
В Qt очень удобный механизм сигналов/слотов для такого есть, а как корректно сделать это здесь - не понимаю.
zulkis
681 / 608 / 38
Регистрация: 13.01.2011
Сообщений: 1,724
12.02.2014, 13:15     Модальный ViewController #6
Цитата Сообщение от arsgram Посмотреть сообщение
При загрузке ничего не появляется, а в аутпуте пишет:
"Attempt to present <vc2> on <UITabBarController> whose view is not in the window hierarchy!"
Не понимаю, причём тут UITabBarController? Ведь vc1, поверх которого я пытаюсь вывести vc2, - это же UIViewController.
Дело в том, что вызов -viewDidLoad происходит до того, как стэк отображений ваших UIViewController-ов добавится на UIWindow
Пробуйте -viewDidAppear.

Цитата Сообщение от arsgram Посмотреть сообщение
И ещё один эпический вопрос. Например, vc2 сделал то, что от него требовалось и теперь надо его убрать + выполнить некую функцию в vc1. Как это сделать?
В Qt очень удобный механизм сигналов/слотов для такого есть, а как корректно сделать это здесь - не понимаю.
3 варианта:
1. Блоки (предпочтительный для конкретного отдельного действия);
2. Делегирования с реализацией/поддержкой протокола;
3. Передача через свойства target\selector и непосредственный вызов selector у target в момент совершения действия.
arsgram
0 / 0 / 0
Регистрация: 07.07.2013
Сообщений: 14
12.02.2014, 17:35  [ТС]     Модальный ViewController #7
zulkis, спасибо, помогло, но в таком случае не появляется webVIew в vc2.
И. как я понял, viewDidAppear вызывается каждый раз, когда появляется view, в том числе и когда переключаются представления в таббаре. Каким образом тогда будет корректно сделать? В viewDidLoad инициализировать vc2, а в viewDidAppear делаеть его present?

И блоки - хм. Читал про них, но как в конкретно этом случае их использовать - не пойму.
Можно какой-нибудь простой пример?
arsgram
0 / 0 / 0
Регистрация: 07.07.2013
Сообщений: 14
13.02.2014, 20:30  [ТС]     Модальный ViewController #8
И ещё вопрос, не в тему, но не хочется новую создавать. // а надо
Есть UIImageView, у него стоит режим Aspect to Fit, т.е. если картинка в нём высокая, то её высота устанавливается высоте представления, а ширина подтягивается с сохранением пропорций картинки.
Если картинка широкая, но низкая, то ширина дотягивается до ширины представления и картинка центрируется по высоте.
UIImageView находится в UITableViewCell. Мне нужно, чтоб при широкой картинке пустогом еста вверху и внизу не было.
Получается, мне надо менять размер UiImageView и самоё ячейки?
Долго искал на эту тему инфу - не нашел. Смотрел методы доступные, документацию - тоже не нашел.
Может, кто-нибудь подскажет?
Да данный момент такой код, но он не работает:
C
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *CellIdentifier = @"Cell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier forIndexPath:indexPath];
 
UIImageView *thumb = (UIImageView*)[cell viewWithTag:1];
UIImage *image = [UIImage imageWithData:[NSData dataWithContentsOfURL:[NSURL URLWithString:self.feed[self.feedKeys[indexPath.row]][@"i"]]]];
thumb.image = image;
CGRect rect = CGRectZero;
rect.origin = CGPointMake(0.0,0.0);
rect.size.height = image.size.height;
rect.size.width = thumb.frame.size.width;
 
[thumb sizeToFit];
[cell sizeToFit];
 
return cell;
}
zulkis
681 / 608 / 38
Регистрация: 13.01.2011
Сообщений: 1,724
13.02.2014, 21:23     Модальный ViewController #9
arsgram, пользуйтесь свойством contentMode для UIView.
arsgram
0 / 0 / 0
Регистрация: 07.07.2013
Сообщений: 14
13.02.2014, 21:53  [ТС]     Модальный ViewController #10
zulkis, оно не работает так, как я описал. Корректно отображаются только картинки с высота>ширина, а если ширина>высоты, то появляются пустоты.
zulkis
681 / 608 / 38
Регистрация: 13.01.2011
Сообщений: 1,724
14.02.2014, 07:21     Модальный ViewController #11
arsgram,
UIViewContentModeScaleAspectFill
The option to scale the content to fill the size of the view. Some portion of the content may be clipped to fill the view’s bounds.
Серьезно?
arsgram
0 / 0 / 0
Регистрация: 07.07.2013
Сообщений: 14
14.02.2014, 18:17  [ТС]     Модальный ViewController #12
zulkis, да. Если задать UIImageView 150x150, например, а картинка будет 200х200, то по 50 пикселей отрежет и поставит картинку туда.
Если режим ставить UIViewContentModeScaleAspectFit, то будет всё как я до этого написал.
Мне нужен, посути, режим UIViewContentModeScaleAspectFit, но при этом чтоб если ширина>высоты, то изменялся размер UIImageView, чтоб избежать пустот сверху и внизу.

Добавлено через 16 минут
Заморочка в том, что на форме ещё элементы присутствуют, и при UIViewContentModeScaleAspectFill, если у картинки высота сильно больше ширины, то она будет вылезать за границы UIImageView вниз и перекрывать другие элементы.
zulkis
681 / 608 / 38
Регистрация: 13.01.2011
Сообщений: 1,724
14.02.2014, 18:36     Модальный ViewController #13
Цитата Сообщение от arsgram Посмотреть сообщение
Заморочка в том, что на форме ещё элементы присутствуют, и при UIViewContentModeScaleAspectFill, если у картинки высота сильно больше ширины, то она будет вылезать за границы UIImageView вниз и перекрывать другие элементы.
Процитирую свою цитату:
Цитата Сообщение от zulkis Посмотреть сообщение
Some portion of the content may be clipped to fill the view’s bounds.
Включите clipsToBounds, если выключена.
arsgram
0 / 0 / 0
Регистрация: 07.07.2013
Сообщений: 14
14.02.2014, 20:47  [ТС]     Модальный ViewController #14
zulkis, но мне-то нужно чтоб представление картинки по вертикали соответствовало размерам картинке на нём, при этом отодвигая или подтягивая к себе элементы соседние. Поулчается, что размеры строчек в таблице должны разного размера получаться тогда.
MoreAnswers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
15.02.2014, 07:42     Модальный ViewController
Еще ссылки по теме:

Как обратиться к методу в ViewController.m из AppDelegate.m? Objective-C
Как удалить ViewController из UITabBarController Objective-C
Запуск нового ViewController из кода Swift
Objective-C MVC storyboard+ViewController
Загрузка ViewController из xib в storyboard Objective-C

Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
zulkis
681 / 608 / 38
Регистрация: 13.01.2011
Сообщений: 1,724
15.02.2014, 07:42     Модальный ViewController #15
arsgram, Значит переопределяйте -layoutSubviews контейнера и от размера своей картинки уже исходите.
Двигайте/уменьшайте/увеличивайте.
Yandex
Объявления
15.02.2014, 07:42     Модальный ViewController
Ответ Создать тему
Опции темы

Текущее время: 06:22. Часовой пояс GMT +3.
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2017, vBulletin Solutions, Inc.
Рейтинг@Mail.ru