Форум программистов, компьютерный форум, киберфорум
Unity, Unity3D
Войти
Регистрация
Восстановить пароль
Карта форума Темы раздела Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.56/25: Рейтинг темы: голосов - 25, средняя оценка - 4.56
-9 / 1 / 0
Регистрация: 02.05.2018
Сообщений: 79
1

Аналог корутины без параллельного выполнения

24.06.2020, 12:07. Показов 4516. Ответов 8

Author24 — интернет-сервис помощи студентам
Здравствуйте, у меня появилась проблема. Необходимо сделать так, чтобы объект(мы говорим о 2d) передвинулся из точки A в точку B, причём лучше всего это сделать с помощью функции(просто в update засунуть не вариант) или корутины, но необходимо, чтобы во время движения этого объекта, т. е. после запуска корутины, компилятор ждал того момента, когды объект дойдёт до точки B и только тогда продолжал считывать команды.
Да, можно было бы просто взять кучу булевых переменных, кучу вложенных друг в друга корутин и т. д., или, например, засунуть всё это в Update, но когда таких функций становиться больше, то код становиться не читаемым и не редактируемым.
Поясню. пусть есть например корутина doF();, которая выполняется 10 секунд, есть просто функция, которая зависит от результата работы doF(), назовём её doS(); Если запустить doF(), а за ней doS(), то результат будет неверным, т. к. во время запуска doS() результат doF() ещё не был получен, а когда таких функций становиться больше, то работать с ними совсем невозможно.
Облазин все возможные форумы, перечитал документацию - ничего нету, может быть вы на своём опыте что-то, что мне подойдёт встречали?
0
Лучшие ответы (1)
Programming
Эксперт
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
24.06.2020, 12:07
Ответы с готовыми решениями:

Интерактивный музей, задержка действий на время выполнения анимации и Корутины в Unity
Доброго времени суток! Я новичок. Делаю проект интерактивного музея, там есть театральная сцена...

Завершение выполнения корутины
Добрый день, пишу клиентское приложение, для общения с несколькими устройствами. Взяв пример из...

Написать аналог Selenium WebDriver для выполнения действий на сайте
Итак, хочу написать прогу на VB.NET, которая будет автоматически выполнять рутинные действия на...

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

8
3353 / 1769 / 1025
Регистрация: 26.10.2018
Сообщений: 5,198
24.06.2020, 12:34 2
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
using UnityEngine;
using System.Collections;
 
class Test : MonoBehaviour
{
    public Transform a, b;
 
    void Start()
    {
        StartCoroutine(c_Move());
    }
 
    IEnumerator c_Move()
    {
        print("Start!");
 
        while (a.position != b.position)
        {
            a.position = Vector3.MoveTowards(a.position, b.position, 50.0f * Time.deltaTime);
 
            yield return null;
        }
 
        // После того как "a" попал в точку "b"
 
        print("Finish!");
    }
}
0
-9 / 1 / 0
Регистрация: 02.05.2018
Сообщений: 79
24.06.2020, 14:01  [ТС] 3
Я это пробовал, но, как я и написал в вопросе, это весьма сложно использовать, т. к., если запустить другую функцию или корутину после этой, которая зависит от того, что объект уже прибыл, то она сработает некорректно, т.к. вторая функция не будет ждать завершения корутины

Добавлено через 1 минуту
Я про то, что это будет выполнять параллельно, как бы в другом потоке(хоть это и не так), а мне нужно, чтобы всё всё выполнялось последовательно, как обычный код
0
3353 / 1769 / 1025
Регистрация: 26.10.2018
Сообщений: 5,198
24.06.2020, 14:14 4
Цитата Сообщение от MaxiD Посмотреть сообщение
т.к. вторая функция не будет ждать завершения корутины
Запускай ее в этой же корутине, после while, либо сделай 3 корутину, которая будет выполнять первые 2 последовательно.
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
using UnityEngine;
using System.Collections;
 
class Test : MonoBehaviour
{
    void Start()
    {
        StartCoroutine(c_Mediator());
    }
 
    IEnumerator c_Mediator()
    {
        print($"Start: {Time.time}");
        yield return c_Other1();
        yield return c_Other2();
        print($"Finish: {Time.time}");
    }
 
    IEnumerator c_Other1()
    {
        print($"c_Other1: {Time.time}");
        yield return new WaitForSeconds(1.0f);
    }
 
    IEnumerator c_Other2()
    {
        print($"c_Other2: {Time.time}");
        yield return new WaitForSeconds(1.0f);
    }
}
Вот, еще это глянь, может будет удобней с этим работать https://habr.com/ru/post/342660/
0
-9 / 1 / 0
Регистрация: 02.05.2018
Сообщений: 79
24.06.2020, 14:58  [ТС] 5
Я и это делал, и, да, это работает, когда у тебя 3-4 функции, но, когда у тебя большой проект, много функций, в том числе и рекурсивных, но использовать это невозможно. Я спрашивал вас про то, как сделать некий аналог корутины, которые будет работать не параллельно(т.е. не в многопоточном режиме). Или я хотел бы знать, можно ли каким-либо образом использовать yield return null; вне корутины, в интернете я этого не нашёл.
0
3353 / 1769 / 1025
Регистрация: 26.10.2018
Сообщений: 5,198
24.06.2020, 15:34 6
Лучший ответ Сообщение было отмечено MaxiD как решение

Решение

Ссылку выше смотрел? Вот еще такое есть https://github.com/Cysharp/UniTask
Думаю тебе стоит смотреть в сторону асинхронного программирования, там как раз есть всякие плюшки для задержек и ожиданий.

Добавлено через 27 минут
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
using UnityEngine;
using System.Threading.Tasks;
 
class Test : MonoBehaviour
{
    public Transform a, b, c;
 
    void Start()
    {
        test();
    }
 
    async void test()
    {
        await Move(a, b, 100.0f); // Ждем пока А доедет до Б со скоростью 100
        await Task.Delay(2000);   // Ждем 2 секунды, после того как доехали до Б
        await Move(a, c, 300.0f); // Теперь едем к С со скорость 300
    }
 
    async Task Move(Transform t1, Transform t2, float speedMove)
    {
        while (t1.position != t2.position) // Если не достигли цели
        {
            t1.position = Vector3.MoveTowards(t1.position, t2.position, speedMove * Time.deltaTime);
 
            await Task.Yield(); // Пропускаем кадр
        }
    }
}
1
-9 / 1 / 0
Регистрация: 02.05.2018
Сообщений: 79
24.06.2020, 16:27  [ТС] 7
Спасибо, я именно это и искал
0
3353 / 1769 / 1025
Регистрация: 26.10.2018
Сообщений: 5,198
24.06.2020, 17:47 8
Ты особо не радуйся))
У этого всего есть малюсенькое НО.
При запуске метода, если остановить режим воспроизведения в редакторе, то выполнение метода все равно продолжится
Довольно неудобно будет ловить объекты в режиме редактирования по всей карте, когда они должны быть остановлены.
К тому же, их свойства будут сохранены редактором. Это выглядит вот так:
https://youtu.be/8etKudhxnGo

Добавлено через 43 минуты
Так что лучше все же корутины, тем более выглядят они почти также, только значение из них не вытянешь без костылей:
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
using UnityEngine;
using System.Collections;
 
class Test : MonoBehaviour
{
    public Transform a, b, c;
 
    void Start()
    {
        StartCoroutine(test());
    }
 
    IEnumerator test()
    {
        yield return Move(a, b, 100.0f);       // Ждем пока А доедет до Б со скоростью 100
        yield return new WaitForSeconds(2.0f); // Ждем 2 секунды, после того как доехали до Б
        yield return Move(a, c, 300.0f);       // Теперь едем к С со скорость 300
    }
 
    IEnumerator Move(Transform t1, Transform t2, float speedMove)
    {
        while (t1.position != t2.position) // Если не достигли цели
        {
            t1.position = Vector3.MoveTowards(t1.position, t2.position, speedMove * Time.deltaTime);
 
            yield return null; // Пропускаем кадр
        }
    }
}
0
-9 / 1 / 0
Регистрация: 02.05.2018
Сообщений: 79
24.06.2020, 19:05  [ТС] 9
Да не, мне всё подходит, у мне все объекты создаются в игре, в редакторе до запуска ничего нету
0
24.06.2020, 19:05
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
24.06.2020, 19:05
Помогаю со студенческими работами здесь

Корутины
Есть у меня такой код для движения и анимации персонажа: using System.Collections; using...

Корутины и потоки
В общем, моя программа состоит из 3-х функций (корутин), каждая функция не зависит от другой....

Про корутины
Доброго времени! public void Start() { StartCoroutine(CoroutineOdin()); ...

Пролагивают корутины в Unity
Я делаю игру где надо считать счёт и пройденое расстояние для этого я использую корутины. Игра...

Анимация в unity и корутины
Добрый день. Мне нужно что бы по нажатию кнопки у меня менялись декорации на сцене. У меня есть...

Про корутины 2 часть
Приветствую! public void Start() { StartCoroutine(Time()); } public...


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

Или воспользуйтесь поиском по форуму:
9
Ответ Создать тему
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2024, CyberForum.ru