Паттерн Состояние (State Machine)

Поділитися
Вставка
  • Опубліковано 28 вер 2024
  • Перезалив старого урока в новом улучшенном качестве.
    В этом уроке мы поговорим о поведенческом паттерне Состояние или как его еще называют State Machine (Конечный автомат). Я постараюсь простым языком объяснить вам его построение и архитектуру. Паттерн Состояние подходит для создания различных поведений или состояний игрока или противника и помогает избежать многочисленных конструкций типа If else или использование многоуровневой switch машины.

КОМЕНТАРІ • 123

  • @unityk555
    @unityk555  2 роки тому +13

    Ребят, если будете использовать этот паттерн для смены анимаций, не забудьте перед каждым CrossFade писать строчку anim.StopPlayback() чтобы останавливать аниматор

    • @HizusHiz
      @HizusHiz Рік тому

      Некорректная реализация паттерна. Это видно сразу по двум моментам:
      1. Полотенце из if в методе Player.Update(). Основная причина для перехода на паттерн Состояние - это избавиться от таких вот if или switch.
      2. Бесполезный класс StateMachine, в котором есть только свойство CurrentState (кстати, правильнее сделать private set, раз есть специальный метод ChangeState()) для хранения текущего состояние и метод ChangeState() для установки состояния. Метод StateMachine.Initialize() это вырожденная вариация метода ChangeState() - можно обойтись без него.
      Обычно классы типа StateMachine вводятся там, где есть конечный автомат - изначально известны правила переходов. То есть известны все состояния и когда из какого состояния можно перейти, а когда нет. Или подгружается из вне - из каких либо настроек. При этом состояния не знают друг о друге. Например, в видео можно было задать в StateMachine правила перехода из Idle -> Jump, Idle -> Run, Run -> Jump, но не задавать переход Jump -> Run (Нельзя в прыжке бегать)
      Другой вариант - обойтись без StateMachine, но в этом случае состояниям "разрешено" знать друг о друге. То есть состояния сами решают: в какие состояния они могут перевести контекст (Player), а в какие нет. Кстати, для примера из видео этот вариант предпочтительнее, на мой взгляд.

    • @unityk555
      @unityk555  Рік тому +2

      @@HizusHiz в таком случае, вы можете поискать уроки на другом канале с корректной на ваш взгляд реализацией

    • @Veyron104
      @Veyron104 Рік тому

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

    • @thebiggestdick69
      @thebiggestdick69 Рік тому +1

      @@HizusHiz подскажи где можно посмотреть правильную реализацию?

  • @DevRadium
    @DevRadium 10 місяців тому +2

    Имеет смысл создать пул состояний и проинициализировать их 1 раз а не плодить задачи для сборщика мусора.
    А в остальном все супер.

  • @Koyotis
    @Koyotis Рік тому

    Отличное объяснение. Спасибо!

  • @shlembert
    @shlembert 2 роки тому +2

    Александр! С Днем защитника Отечества! Отличная работа! Новичкам будет очень пользительно!
    Хочу лишь обратить внимание на правила нейминга. Не сокращайте пожалуйста имена полей. Тем более, что IDE все напишет за Вас по первому вводимому символу.
    Спасибо!

    • @unityk555
      @unityk555  2 роки тому +1

      Спасибо Мартин, взаимно с праздником! Учту Ваши пожелания в будущих уроках.

  • @okitkin
    @okitkin 4 місяці тому

    ДОбрый день , спасибо вам большое за видео! Подскажите плиз как можно использовать Input.GetAxis в state скрипте ? Я заметил у вас класс CInput я так по нимаю это перегрузка метода Input?

    • @unityk555
      @unityk555  4 місяці тому

      Не подскажу, я уже давно не в юнити. Но насколько я помню это не перегрузка. У нас на работе esc подобное програмиирование было типа системы и компоненты . И все скрипты компоненты начинались с С. Пример SUnitsBeh система, а компонент CUnitBeh.

  • @grenadier4702
    @grenadier4702 Рік тому +1

    Я так понимаю, в данном примере из любого состояния можно перейти в любое. Было бы хорошо еще рассмотреть обратное

  • @ДмитрийАнтипанов-п8т
    @ДмитрийАнтипанов-п8т 4 місяці тому

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

    • @unityk555
      @unityk555  4 місяці тому

      Я уже не в юнити давно, не подскажу, но когда работал очень удобно все было. Надо покрутить для себя, понять кк лучше. Может модернизировать как-то

  • @andrey_aka_skif
    @andrey_aka_skif 2 роки тому +1

    Можно пару вопросов-придирок?
    1. Наверно, правильнее было сделать CurrentState { get; private set; }, чтобы кто-нибудь случайно не решил переключить состояние через это свойство?
    2. Зачем нужен метод Initialize() для класса StateMachine? Можно ведь передать начальное состояние прямо в конструктор.
    3. Насколько хорошая идея обращаться к аниматору через Player? Это вроде как нарушение Закона Деметры. Да мы и не должны знать ничего о внутреннем устройстве плеера. Может перемещение у нас реализуется через DOTwins, а прыжки через Rigidbody. Пример конечно искусственный, но суть Вы поняли. В крайнем случае, можно передать сам аниматор (как у Вас в примере реальной игры и сделано). А если уж совсем городить абстракции ради абстракций, то нужно иметь дело и не с аниматором вовсе, а с некоторым контрактом. В идеале, с интерфейсом IAnimator, который реализует Player =)))))))
    4. Как Вы относитесь к холиварной теме про Update() и 10 000 монобихевиаров? =)))

    • @unityk555
      @unityk555  2 роки тому

      1. Можно сделать приват Вы правы
      2. Для урока так было наглядней, когда я изучал этот паттерн в примерах было так же, но Вы можете сделать как Вам удобней.
      3. Это зависит уже от Вашей архитектуры и как вы выстраиваете связи в своем проекте. У меня аниматор обычно лежит в скрипте игрока, мне так удобней.
      4. Я думаю чем меньше Update тем лучше, на практике использую твины, rx update или подписки на изменения переменных. Старюсь минимизировать лишние вызовы.

    • @andrey_aka_skif
      @andrey_aka_skif 2 роки тому

      @@unityk555 спасибо за ответ! Третий вопрос в его текущем виде был скорее шуткой юмора. А вот четвертый вопрос отсылает к статье "10000 Update() calls" из блога Юнити. В ней, как мне кажется, всё доведено до абсурда, ибо предлагается совсем отказаться от использования Update() метода везде, кроме одного единственного объекта в сцене. В остальных объектах предлагается использовать метод UpdateMe() (как в ваших стейтах) и вызывать его с помощью сервиса. Что Вы об этом думаете?

    • @unityk555
      @unityk555  2 роки тому +1

      @@andrey_aka_skif да я про такой подход слышал и он не лишен смысла. Насколько я знаю каждый Update нагружает систему и вроде если будет только один Update то это будет хорошо для оптимизации. Я видел как ребята так делали, опять же могу ошибаться но мне кажется что в unirx тоже реализован такой подход. Вобщем такая практика есть. В серьезных компаниях на собеседованиях мне задавали такой вопрос значит такой подход имеет место быть. Как я понял нужно сиремиться минимизировать количество update. Но я думаю что не стоит доходить до абсурда и все зависит от сложности и объема проекта, нужна ли ему такая оптимизация.

    • @boykopb
      @boykopb 2 роки тому

      @@andrey_aka_skif вот аналогичная ситуация рассмотрена ua-cam.com/video/JcqU2zHBwFY/v-deo.html . Тоже интересно узнать мнение по этому поводу. С одной стороны удобно, что все в одном месте и есть понимание, сколько объектов используют Апдейт. С другой - это какой-то изврат)

    • @andrey_aka_skif
      @andrey_aka_skif 2 роки тому +1

      @@boykopb вот и я мучаю блогеров таким вопросом. Ибо без опыта реального проекта ничего не понятно. С одной стороны, идея контроля хорошая. С другой стороны, жуткий архитектурный оверхед при не очень понятных результатах. В упомянутой статье выигрыш по времени чуть не на порядок. В видео по ссылке городили дикий огород, а в результате пшик.

  • @gavr2811
    @gavr2811 Рік тому

    А насколько это хороший способ с точки зрения нагрузки? Мне rider сигнализирует, что дорогих методов в твоём коде много

  • @tttrrrrt1229
    @tttrrrrt1229 2 роки тому

    А у Вас не было раньше урока про состояния? По моему я смотрел какой-то другой, похожий, когда делал стейт машину.

    • @unityk555
      @unityk555  2 роки тому

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

    • @tttrrrrt1229
      @tttrrrrt1229 2 роки тому

      @@unityk555 Понял. Иногда просто находишь полезный видос , а когда возвращаешься к нему, чтобы освежить знания, его и след простыл. Ваш тот ролик мне сильно помог разобраться. Спасибо за контент!

    • @unityk555
      @unityk555  2 роки тому

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

  • @gameviewer5693
    @gameviewer5693 2 роки тому

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

    • @unityk555
      @unityk555  2 роки тому +1

      Я делал включение второго стейта сразу в конце логики включения первого стейта в Enter. Играть с этим паттерном можно по разному, дайте волю полету Вашей инженерной мысли. Например у игрока есть состояние получения урона после которого он должен вернуться либо в состояние покоя, либо в состояние боевой стойки, Мы включаем состояние получения урона, и после отыгрыша этого состояния прямо в последней строчке метода Enter включаем ChangeState следующего состояния

    • @gameviewer5693
      @gameviewer5693 2 роки тому

      @@unityk555 спасибо, примерно так и думал, но хотел уточнить на счёт передачи стейтмашины стейтам насколько это правильно

    • @unityk555
      @unityk555  2 роки тому +1

      @@gameviewer5693 можно не передаать контроль стейтам, а запустить событие в конце первого стейта и через событие включить второй стейт например, думаю так получше будет.

    • @andrey_aka_skif
      @andrey_aka_skif 2 роки тому +2

      @@gameviewer5693 я не разработчик, поэтому моё мнение можно сразу делить на два. Однако, моё мнение таково, что данный пример плохой. Более того, в этом примере вообще нет машины состояний. Вы задали вполне резонный вопрос про переключение состояний. Посмотрим на код на 10:31. Что будет, если выяснится, что прыгать мы можем только из состояния бега? Придется прямо в Player городить какой-то switch, от которого мы хотели избавиться. Потому что в таком виде это вариант стратегии. Александр в прошлый раз говорил, что машиной состояний такую реализацию делает наличие методов Enter() и Exit(). Но если открыть, например, Рефакторинг-Гуру, то там написано:
      Состояние можно рассматривать как надстройку над Стратегией. Оба паттерна используют композицию, чтобы менять поведение основного объекта, делегируя работу вложенным объектам-помощникам. Однако в Стратегии эти объекты не знают друг о друге и никак не связаны. В Состоянии сами конкретные состояния могут переключать контекст.

    • @unityk555
      @unityk555  2 роки тому

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

  • @Mr_TroubleMaker
    @Mr_TroubleMaker 2 роки тому

    привет, обновлённая версия лучше намного, чётко, лаконично, понятно) Про сервис-локатор нет задумок рассказать???

    • @unityk555
      @unityk555  2 роки тому

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

    • @Mr_TroubleMaker
      @Mr_TroubleMaker 2 роки тому

      @@unityk555 ну допустим прототипы когда делаешь и не нужно выстраивать крутую архитектуру, проще всего запилить сервис локатор какой-нибудь. Это вот мне такой совет дал бывалый разработчик. Чтобы избавиться от FindObjectOfType на старте например, когда в реалтайме допустим объект заспаунился и ему нужно найти единственный объект на сцене.

    • @unityk555
      @unityk555  2 роки тому +1

      @@Mr_TroubleMaker раз это все-таки паттерн то поставлю в планы.

  • @proKaps
    @proKaps Рік тому

    Храни тебя господь. Посмотрю все уроки и тимлидом стану и джуном не побывав!

  • @dzheraz_6953
    @dzheraz_6953 2 роки тому

    Я думаю имеет смысл добавить еще что этот паттерн имеет множество способов реализаций. Самое простое это комбинация enum и swith, по своей сути это тоже машина состояний и иногда этого хватает сполна, например для ui элементов. Более сложные реализации имеют более сложную, но гибкую логику включая еще один термин из этого паттерна "переход", которые могут иметь условия, а сами состояния могут быть подмашинами состояний(в контексте предложенной здесь концепцит можно просто внутри состояний держать машины состояний) , посути как это реализовано в машине состояний аниматора

  • @ziggykingdev7642
    @ziggykingdev7642 2 роки тому +12

    Спасибо. То что нужно! Смотрел про паттерны на других каналах, понял только тут. Хотелось бы больше уроков по уменьшению связности кода. Про интерфейсы, события. Все на примерах кода в юнити. Эта информация для новичка очень важная.

    • @unityk555
      @unityk555  2 роки тому +4

      Да и такие уроки будут, спасибо

  • @profftols
    @profftols Місяць тому

    Как же удобно и доходчиво объяснил с примерами и кодом (не сложным)

  • @eugenestepanets8069
    @eugenestepanets8069 6 місяців тому

    я правильно понимаю, что это хорошо для (например) класса Player. Если нужно писать класс для врага, то их огромное количество видов. у каждого свои параметры. это ладно, у каждого свои наборы состояний. а в идеале хотелось бы написать один набор скриптов на любого. и настраивать из окна инспектора через [SerializeField]. Полагаю, тут архитектура посложнее будет.

    • @unityk555
      @unityk555  6 місяців тому

      Можно и для врагов писать. Сейчас уже не подскажу, но раньше писал и для врагов тоже

  • @ilgiz2616
    @ilgiz2616 2 роки тому +1

    Интересный паттерн. Подача материала хорошая. Но у меня только один вопрос зачем так сложно uniRx + state machine, ECS ведь лучше )) Интересно Ваше мнение )

    • @unityk555
      @unityk555  2 роки тому

      Спасибо. У нас используется ECS подобная система в связке с UniRx. Плюс к этому я еще паттернами балуюсь.

  • @aleksandrgaziev4470
    @aleksandrgaziev4470 9 місяців тому

    Добрый день. Под скажите а как использовать паттерн? Я имею ввиду ведь скрипты не унаследованы от монобехевиор. Каким образом назначить.

    • @unityk555
      @unityk555  9 місяців тому

      Один монобех должен быть в этой системе, уже не пом где точно, но в уроке это должно где-то быть

    • @aleksandrgaziev4470
      @aleksandrgaziev4470 9 місяців тому

      @@unityk555 да нашел в другом уроке. Спасибо тема классная.

  • @cnfnbcn3227
    @cnfnbcn3227 Рік тому

    9:12 Он не становится "юнитёвским". Он остаётся обычным методом, который мы лишь для удобства называем Update(), но технически это не метод из API Unity.

  • @antonpashkevich5061
    @antonpashkevich5061 2 роки тому

    Спасибо, вроде бы годно) А то просто все показывают на примерах Debug , а как использовать в проекте полноценно в юнити нету...

  • @PaulGeraskin
    @PaulGeraskin 2 роки тому

    Очень круто, спасибо. Теперь я знаю больше про стейт машину. Один вопрос: при изменении состояния создается новый объект. Будет ли это сказываться на мусоре? Например 30 неписей постоянно меняют свои состояния...

    • @unityk555
      @unityk555  2 роки тому +1

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

  • @ВасилийМигулин-т1й

    Данный паттерн лучше всего реализовывать через интерфейс

  • @Veles017
    @Veles017 11 місяців тому

    Отличный урок! Спасибо большое!

  • @proKaps
    @proKaps Рік тому

    А если убрать метод Initialize в классе StateMachine и заменить его просто на конструктор? Насколько это корректно? Или метод Initialize обязателен в данном паттерне и это более практично?

    • @unityk555
      @unityk555  Рік тому +1

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

  • @PavelRodygin-h9i
    @PavelRodygin-h9i 2 роки тому

    Пасиб за урок, смотрится легко, щас реализовывать буду)

  • @ephitariathegame2brainstud996
    @ephitariathegame2brainstud996 2 роки тому

    Спасибо. очень полезное видео. Вот вопрос такой, теоретический, есть ли смысл использовать данный паттерн в разработке UI?

    • @unityk555
      @unityk555  2 роки тому +1

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

  • @fedmunty4051
    @fedmunty4051 2 роки тому

    Этот функционал же вроде уже реализован в StateMachineBehavior в самом юнити.

    • @unityk555
      @unityk555  2 роки тому

      Насколько я знаю он реализован в анимациях, в любом случае паттерн есть паттерн и знать о том как его развернуть самому будет не лишним.

  • @denis.leonovich
    @denis.leonovich 2 роки тому

    В видео показана странная реализация паттерна стратегия, от состояния тут только названия классов 😑

    • @unityk555
      @unityk555  2 роки тому

      Посмотрите видео по Стратегии, вдруг там странная реализация паттерна Состояние))

  • @JackieBaileys
    @JackieBaileys Рік тому

    Топ💪

  • @unityalexdev
    @unityalexdev Рік тому

    Красавчик,спасибо

  • @gendgee
    @gendgee Рік тому

    красавчик 😊😊😊

  • @Shashlichnuy
    @Shashlichnuy 11 місяців тому

    Офигенно объяснил. Жаль что, есть люди, которые напишут что метод плох, потому что сами кодят по другому

    • @unityk555
      @unityk555  11 місяців тому +1

      Ну, я дал основу, с которой можно уже работать и улучшать. А дальше можно ее модернизировать. В свое время неделю потратил чтобы въехать в этот патерн. Спасибо за комментарий))

    • @fentan6806
      @fentan6806 7 місяців тому

      Да, потому что мы кодим нормально.

  • @Eduard0213-x7p
    @Eduard0213-x7p 2 роки тому

    Spasib ogromnoe !

  • @ДмитрийБарсуков-ъ8р

    Спасибо, очень познавательно 👍

  • @sergeyhovhannisyan5506
    @sergeyhovhannisyan5506 2 роки тому

    👍

  • @koganboss4874
    @koganboss4874 2 роки тому

    Вопрос не по теме, но это единственное, что сейчас интересует... Как у тебя в райдере все так красиво подсвечивается? Все ключевые слова своими цветами... Я подписался на райдер год назад, но так и не разобрался, он скрипты открывает, все работает как надо, подсказки высвечивает, но весь текст одним цветом, подсветки нету.... Что я не так делаю? Помоги плиз. Лайкос влепил=) Ответишь еще и подпишусь=)))

    • @unityk555
      @unityk555  2 роки тому

      А у тебя в юнити в preferences - external tools стоит райдер? Обычно райдер не подсвечивает синтаксис когда он либо не прогрузил скрипты либо он не понимает синтаксис юнити по каким-то причинам. Погляди тут qna.habr.com/q/954825

    • @koganboss4874
      @koganboss4874 2 роки тому

      @@unityk555 Да, external tools стоит, но вот галочки Editor Attaching нету вообще...

    • @koganboss4874
      @koganboss4874 2 роки тому +1

      @@unityk555 Ооо, разобрался кажись. Оказывается в самом райдере, в настройках надо выставить цветовую схему, выбрав из списка Unity. Лол, че раньше не додумался? Подписон оформил=)

    • @unityk555
      @unityk555  2 роки тому

      @@koganboss4874 это была моя вторая задумка на случай если первая не сработает поглядеть цветовые схемы. Надеюсь теперь все будет подсвечиваться, благодарю за подписку.

  • @АндрейПинчук-х7б
    @АндрейПинчук-х7б 2 роки тому

    Спасибо большое за урок!

  • @ПавелЮ-р5э
    @ПавелЮ-р5э 2 роки тому

    ОО классно , видео прям живее стало ))

    • @unityk555
      @unityk555  2 роки тому

      Спасибо, я старался)

  • @Tumanop
    @Tumanop 2 роки тому

    Разве UniRX еще не мёртв ? поддержка ведется чиста на энтузиазме разраба без каких то денежных влияний со стороны площадки, да и апдейты выходят рандомно и очень часто получается что какая то новенькая версия юнити тихо плачет в сторонке обделённая вниманием

    • @unityk555
      @unityk555  2 роки тому

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

    • @Tumanop
      @Tumanop 2 роки тому

      @@unityk555 А если не секрет на какой версии Unity вы делаете свои проекты ?

    • @unityk555
      @unityk555  2 роки тому

      Последняя была 2020.3.18

    • @Tumanop
      @Tumanop 2 роки тому

      Ох, я думал 19 версия, попробую изучит unitRX тогда )

    • @unityk555
      @unityk555  2 роки тому +1

      @@Tumanop у меня на канале есть вводные уроки по rx можете начать с них если хотите

  • @dmitrynezamay454
    @dmitrynezamay454 2 роки тому

    12:56 - а разве корректно делать, что аниматор игрока публичный?

    • @unityk555
      @unityk555  2 роки тому

      Можете сделать его приватным. Это просто пример реализации.

    • @ueekand6626
      @ueekand6626 2 роки тому

      @@unityk555 В таком случае, если сделать поля приватными или protected, конструктор не дает обратиться к ним.
      Наследование двух скриптов (State и скрипт игрока) тоже не могу осуществить, IDE запрещает
      Придётся в каждом скрипте состояния указывать компоненты по новой?
      (Заранее извиняюсь, если это глупое непонимание с моей стороны.)
      В голову приходит только решение - для скрипта State указывать наследование от скрипта игрока, а в последующих скриптах состояний указывать наследование от State. Но тогда придется для каждого нуждающегося объекта создавать свою собственную Машину Состояний. Насколько это правильно?

    • @unityk555
      @unityk555  2 роки тому

      @@ueekand6626 урок записывал уже давненько, сейчас не вспомню нюансов, попробуйте поискать в гугле, варианты прокидывания аргументов. Можно попробовать через скрипт игрока. Лично я обычно делал стейт машину для игрока, а если объектов было много то выбирал паттерн Стратегия. Со стейт машиной нужно пробовать различные варианты, в этом уроке я показал основу, но модифицировать скрипт тут уже надо эксперемментировать

    • @ueekand6626
      @ueekand6626 2 роки тому

      @@unityk555 Хорошо, спасибо за ответ и наставление!)

  • @pulsar1934
    @pulsar1934 2 роки тому

    Не совсем понятно зачем наследнику после переопределения метода базового класса вызывать метод базового класса в переопределённом методе.
    Это касается абстрактного класса State и его наследников состояние бега и покоя. В абстрактном классе по логике ничего же не будет реализовываться это же просто как переключатель, или я чего-то не понимаю...

    • @unityk555
      @unityk555  2 роки тому

      Не очень Вас понял если честно.

    • @pulsar1934
      @pulsar1934 2 роки тому +1

      @@unityk555 таймлан 6-50 base.Exit() base.Enter() вызов метода из базового класса от которого мы наследуемся и после переопределяем его виртуальные методы. Логика будет в методе override. Virtual пуст, какая там будет логика, зачем его вызывать в override ? А если в абстрактном классе методы virtual не будут содержать логики и в теле метода пусто, тогда логичнее использовать абстрактный метод вместо виртуального.

    • @unityk555
      @unityk555  2 роки тому

      @@pulsar1934 Вы правы, попробуйте без них. Я просто использовал горячие клавиши для переопределения методов и захватил base.Exit() и base.Enter(). Они не мешают работе паттерна, вы можете их удалить если хотите

    • @pulsar1934
      @pulsar1934 2 роки тому

      @@unityk555 отлично, а то я думал, что я не совсем разобрался в теме. Спасибо!)

    • @PavelRodygin-h9i
      @PavelRodygin-h9i 2 роки тому

      мелочь же

  • @arin081
    @arin081 2 роки тому

    У меня методы Enter и Exit выполняются постоянно.
    void FixedUpdate()
    {
    _stateSwicher.currentState.FixedUpdate();

    if (joystick.onPointerDown)
    {
    _stateSwicher.SetState(new MoveState(this));
    }
    else
    {
    _stateSwicher.SetState(new IdleState(this));
    }

    }
    Как или я что то не так делаю?

    • @unityk555
      @unityk555  2 роки тому

      Вы в апдейте состояния переключаете. Как минимум else у вас отрабатывает все время когда джойстик не нажат. Лучше использовать подписки на ваш джойстик, либо переключать стейты вне update, либо не больше чем один раз за раз. Можете проставить логи и сами увидите какие методы сколько раз срабатывают.