Добавление механизма достижений - как сделать дизайн - цель c - PullRequest
2 голосов
/ 25 января 2011

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

Я не уверен, как мне это реализовать, поэтому я дам вам знать, о каких вариантах я думал до сих пор:

  1. Написание класса AM (менеджер достижений), который будет иметь функцию addAchievment ().

    Внутри каждой функции в моем приложении, которая может предоставить достижение, я могу выделить объект Achievemnt и вызвать addAchievment () с этим объектом. Что мне не нравится в этом подходе, так это то, что вы сначала добавили много кода достижений во многие части приложения. (а также проверка не добавлять одно и то же достижение более одного раза).

Один из способов улучшить это - возможно, вызвать addAchievment () с определенным перечислением, а затем внутри реализации addAchievment () проверить каждое перечисление и выделить соответствующий объект достижения - однако функция с переключателем из 40 падежей не тоже не очень хорошо звучит.

2. Для каждого класса, который может сообщать о достижениях, я могу написать для каждого достижения функцию, которая возвращает значение, если это достижение должно быть предоставлено. Например, класс А может сообщать о 2 достижениях. Я могу написать 2 функции:

-(BOOL) shouldGrantA1
-(BOOL) shouldGrantA2

Когда я запускаю класс A, я вызываю менеджер достижений и добавляю эти две функции в массив функций, которые будет удерживать AM. Каждый раз, когда я хочу проверить, должен ли я предоставлять достижения, я просто вызываю AM CheckAchievements (), и он выполняет все функции и добавляет достижения где функция возвращает TRUE.

Проблема с этим подходом. Допустим, в классе A я достигаю места, где я изменяю значение, которое, как я знаю, может дать достижения. Я могу вызвать AM CheckAchievements (), но он будет проходить через все функции достижений, хотя, вероятно, в настоящее время будет достигнуто только достижение класса А. кажется немного над головой. Любой способ решить это?

Я бы с удовольствием предложил и другое предложение. Спасибо !!

1 Ответ

2 голосов
/ 25 января 2011

Я бы не стал добавлять какие-либо достижения, такие как код, в ваши существующие игровые классы. Никаких логических значений или чего-то еще, потому что это создает слишком тесную связь между вашими игровыми классами и вашей системой достижений. Лучше создать отдельный «AchievementManager», который управляет несколькими AchievementListener, они прослушивают состояние объектов, и когда соответствующее состояние меняет состояние, проверяется условие разблокировки. Я думаю, что эта идея лучше всего проиллюстрирована в коде.

Например, если у вас есть достижение «Игрок проходит 100 километров». PlayerWalksAchievementListener будет выглядеть следующим образом.

private AchievementManager manager;
private Player player.
private Vector2 previousPlayerPosition;
private float distanceWalked;
Update()
{
   float dist = Vector2.Distance(player.Position, previousPlayerPosition);
   if(dist > 0)
   {
      distanceWalked += dist;
      CheckUnlockCondition();
   }
}

CheckUnlockCondition()
{
    if(distanceWalked * conversionFactor > 100) { manager.UnlockAchivement(achievementID); } 
}
...