Для того чтобы правильно разделить движение и ввод, полезно использовать принципы проектирования программного обеспечения, такие как разделение ответственности (Separation of Concerns) и инверсия зависимостей (Dependency Inversion).
Вот один из возможных способов организации кода:
1. `InputController` занимается только обработкой пользовательского ввода и не должен знать, что делается с этой информацией. Его задача — определить, какие действия хочет совершить пользователь, и сгенерировать соответствующие сигналы или команды.
2. `Person` (игровой персонаж) содержит методы для перемещения и другой логики поведения, но не знает о существовании `InputController`.
3. Создайте промежуточный слой (например, `PlayerController`, `GameplayController` или даже `EventSystem`), который будет получать команды от `InputController` и вызывать соответствующие методы в `Person`.
Пример кода на C# с использованием Unity3D (псевдокод):
```csharp
// Класс, который обрабатывает ввод пользователя
public class InputController : MonoBehaviour
{
public event Action<Vector2> OnMoveInput;
void Update()
{
Vector2 moveInput = new Vector2(Input.GetAxis("Horizontal"), Input.GetAxis("Vertical"));
if (moveInput != Vector2.zero)
{
OnMoveInput?.Invoke(moveInput); // Вызываем событие с текущим вектором движения
}
}
}
// Класс игрока
public class Person
{
// Метод для обработки движения
public void Move(Vector2 direction)
{
// Здесь ваш код для движения, например, изменение положения transform
transform.Translate(direction * speed * Time.deltaTime);
}
}
// Класс контроллера персонажа, который связывает InputController и Person
public class PlayerController : MonoBehaviour
{
private InputController inputController;
private Person person;
void Awake()
{
inputController = GetComponent<InputController>();
person = GetComponent<Person>();
inputController.OnMoveInput += HandleMoveInput; // Подписываемся на событие
}
// Обработчик события ввода движения
private void HandleMoveInput(Vector2 input)
{
person.Move(input); // Передаем ввод в метод Move класса Person
}
void OnDestroy()
{
inputController.OnMoveInput -= HandleMoveInput; // Отписываемся от события при уничтожении объекта
}
}
```
Такая структура позволяет вам легко изменять способ получения ввода (например, для других платформ или устройств ввода), не затрагивая класс `Person`. Кроме того, `Person` не зависит от конкретных реализаций ввода данных, что делает этот класс более модульным и удобным для тестирования.
Когда вы связываете всё вместе в Unity, вы просто добавляете эти компоненты (скрипты) на один игровой объект (GameObject), который представляет игрока. Компонент `PlayerController` служит связующим звеном между вводом пользователя и логикой движения персонажа.