All streams
Search
Write a publication
Pull to refresh
0
0

iOS developer

Send message
Слишком радужный обзор, а по факту IOS интерфейс все такой же не нативный — видно, что они используют отличный рендер, потому что все привычные элементы (UIScrollView и производные — таблица, коллекция, UITextField) работают по-другому, c другими анимациями и таймингами, ну а как пробрасывать родные железячные фичи — это отдельный минус.
зачастую бывает, что некоторые аутсорсинг компании пытаются зарелизиться от лица большой компании и еще по индивидуальной подписке, никто же не знает о ваших договоренностях и требуется документация от подтверждении сотрудничества.
Недавно, одно из моих приложений получило реджект спустя год после релиза на минорном обновлении из-за использования некоторых хаков (спасибо аутсорсу, но я с ним уже давно и не работают)
так чувство, что просто никто не читает ни Human Interface Guidelines, ни App Store Review Guidelines. А ведь все пункты там прописаны и регламентированы, если им следовать — ревью пролетает за 1 — 3 дня без проблем и лишних вопросов, и не пытаться встроить фоновую геолокацию, дабы отправлять background запросы с целью слежки за пользователем (чем почему-то любят заниматься многие менеджеры).
А в чем сложность возникла то?
Кейс для создания сертификатов описан 1000 и 1 один раз на любых языках разной степени подробности
такое чувство — что про полиморфизм до Swift ни разу не слышали
не, писать анимацию через Таймер, когда есть UIView.animate — это фантастика)
а не проще ли было например переопределить UIControlEvents методы?
делается все тоже самое, только в 30 строк и на родных средствах анимирования без костылей
а что будет — если экранов станет больше 10 хотя бы, и если будут использоваться разные сценарии — длинный кейс авторизации, кейс редактирования, кейс оплаты?

RootController распухнет до тысяч строк, а еще и синглтон — как менять реализацию на лету например?

И по итогу каждый VC знает, куда ему шагать дальше, а если необходимо в N-ое количество VC заменить вызываемый экран (корзину -> на оплату)?

подход неплох, но и проблем не мало
Давным — давно, в конце еще 80-ых многие писали, что наследование — это мощный инструмент и очень классный, если использовать с умом, но в большинстве случаев — полиморфизм решает все проблемы.
Но почему — то спустя 40 лет решили одну из составляющих ООП вынести в отдельную концепцию и сделать ее модной — популярной и на конференциях с умным видом вещать цитаты из далеких времен, но преподнося как нечто инновационное.
Как бы все сводилось к тому, что плохой дизайн архитектуры может иметь право на существование при хорошем дизайне кода, но скрывать плохой дизайн кода (читай размазывать не лучшие решения в разные слои) очень быстро приводит к деградации любой архитектуры.
логику работы можно описать в слое Controller, который знает о фасадах с бизнес логикой, и возвращает новое состояние во View слой (в данном случае выступает XXXViewController), output protocol того, что будет рисовать View.

Мне нравится из концепции REDUX возвращать один метод func update(_ state: MyState) и через switch - case обновлять весь UI под новые данные.
По идее — у тебя ViewController будет выполнять функцию View слоя, и только он делает import UIKit.
Cервисы должны быть чистыми функциями первого порядка — не могут хранить никаких данных.
Для данных у тебя есть отдельный слой Model, модели могут быть пассивными — это старый вариант, и активными — этот путь как раз и описывается в MVC по гайдлайну Apple. Один из хороших примеров M слоя — это CoreData, просто закрой ее за сервис, возвращающий Plain Object.
но сложные VC можно так же поделить на множество маленьких простых VC (с помощью чайдов), сложные сервисы сложить и закрыть простыми фасадами, анимацию вынести в классы Animator, реализации протоколов в отдельные extension .swift файлы, за навигацию будет отвечать класс Координатор, и получится ViewController толщиной до 300 строк со всеми отступами по код стайл.

ИМХО, Вайпер интересно смотрелся в мире Objc с обязательным .h/.m разделением, но в Swift можно делать и проще и удобнее и лаконичнее.
По поводу «протоколы легко ломает бизнес логику и приводит к взаимоисключающим состояниям» элементарный пример — на экране показывается AlertView или любое модальное окно с какой-либо информацией как callback одного из сервисов, а другой сервис уже хочет дернуть навигацию для перехода в следующий экран. В любом однонаправленном принципе разработки — это будет просто новый State модуля, а двунаправленной архитектуре придется разруливать.

Буду очень признателен (и не я один), если продемонстрируете свой пример использования Роутера, так как удачный и функциональный способ будет очень полезен для сообщества.

Некоторые принципы Redux так же очень клево ложаться на IOS и UIKit, при этом позволяют обойти многие проблемы роутинга и разделения отвественности, а так же удобно расширяемые по мере роста приложения.
Раскрою подробнее свою мысль.
Когда говорят про VIPER, то почти первым же предложением добавляют — тестируемость и модульность. Но странным образом, когда берутся за реализацию, то unit тесты сразу отпадают, их просто не хотят писать ни по TDD, ни по BDD техникам. Где то была обширная статейка про статистику количество багов на проект, и процент Crash Free от смены богомерского MVC на правильный VIPER не дал перфоманса, даже малейшего.

Следующим пунктом — это модульность и независимость классов друг от друга. Идея, которая должна порадить массу маленьких самодостаточных фреймворков, наподобие компонентов, которые можно использовать между проектами и соблюдая Code Style и UI Style, оказалась утопической и нереализуемой в продакшене.

И чисто из технических подходов — это двунаправленная связь через протоколы легко ломает бизнес логику и приводит к взаимоисключающим состояниям, Presenter раздувается до невообразимых размеров (Massive View Controller перекочевал в слой Presenter ?), а Router вообще плохо ложится на UIKit.

Описывать проблемы использования VIPER в контексте IOS можно бесконечно…

Другими словами — VIPER это один из видов MV(X) архитектуры, но с более дробленном контроллером.
опять же и опять же — на небольших приложениях любая архитектура себя отлично проявляет, но в крупных enterprise проектах ломается об многие процессы разработки…
очень надеюсь, что привлечение англоязычных коллег снова вернет Хабр на путь интересных и «глубоких» статей о неординарных проблемах и недокументированных фичах, а не свалится в еще более рекламные попсовые статьи.
не было цели спорить, но просто хотел узнать примеры и мотивы — где это хорошо работает) иногда для реализации какой либо фичи приходится делать страшные «костыли», но в тот момент и с тем багажом знаний — они были наиболее эффективны.
Встречался такой же сценарий за созависимость соседний ячеек от текущего размера и состояния, но тогда было удачное решение — производить некоторый расчет размеров внутри ViewModel, кэшировать эти размеры и отдавать в Collection View, и зачастую это зависит даже не от насыщенности UI эффектами, а бизнес логики работы общего контрола.
но это легко поломать, добавив Accessibility изменяемый размер шрифта. И простое изменение дизайна — отступы прибавить / убавить, добавить множитель для констрейнтов или приоритеты, а если там будет коллекция с интересным лайаутом… ИМХО, такое решение хорошо для построения ленты с предрасчетом высоты ячейки какой — либо ленты, ячейки которой надо уметь сворачивать / разворачивать и сохранять их стейт, но расчет самого АЛ никто не отменял.
как вы рассчитываете ячейки? вы уже в базе храните параметры ячеек, что то вроде UserInfoCellModel, которая включает width, height, UserModel (другая модель, которая отобразиться) и height рассчитывается при создании модели?
по большей части, это имеет смысл при довольно объемном лайауте с обновлением ячеек или tableView.beginUpdates() / tableView.endUpdates(), в 99% случаем будет оверхед
2

Information

Rating
Does not participate
Location
Россия
Date of birth
Registered
Activity