Система достижений мобильной игры: архитектура, синхронизация, retention
Мы сталкивались с ситуацией, когда система достижений была «слеплена на коленке»: прогресс хранился локально, после переустановки игры достижения пропадали, а игроки писали негативные отзывы. Правильно спроектированная система достижений — это не просто список «убей 100 врагов». Она управляет retention: игрок возвращается, потому что хочет закрыть ачивку, которая требует 7 дней подряд входить в игру или убить конкретного босса. Достижения дают долгосрочные цели пользователям, прошедшим основной контент. По нашим данным, внедрение продуманной системы Streak-достижений повышает дневную активность на 20–30%. Наша команда имеет 5+ лет опыта в разработке мобильных игр и реализовала более 30 систем достижений для игр разных жанров.
Почему достижения важны для retention?
Достижения создают микроцели, которые превращают короткие сессии в привычку. Например, ачивка «Входи в игру 7 дней подряд» мотивирует игрока возвращаться ежедневно. Без таких механик игрок быстро теряет интерес после прохождения основного сюжета. Исследования показывают, что игры с системами достижений имеют на 40% более высокий 30-дневный retention (по данным GameAnalytics report).
Какие типы достижений мы используем?
| Тип | Описание | Пример | Влияние на retention |
|---|---|---|---|
| OneTime | Однократное выполнение | Убить первого босса | Низкое |
| Counter | Прогрессивное накопление | Убить 100 врагов | Среднее |
| Streak | Серия подряд | Входить 7 дней подряд | Высокое |
| Cumulative | Накопительное за всё время | Набрать 10000 очков | Среднее |
Streak-достижения особенно эффективны — они формируют привычку ежедневного захода. Для их реализации требуется аккуратная обработка временных зон с использованием UTC.
Архитектура: локальная vs серверная
Для большинства мобильных игр архитектура выглядит так:
| Компонент | Рекомендация | Причина |
|---|---|---|
| Прогресс достижений | Клиент + серверная синхронизация (Google Play Games / Game Center / PlayFab) | Защита от потери данных, античит |
| Выдача наград | Только сервер (или Platform SDK с верификацией) | Предотвращение взлома |
| Отображение | Клиент | Минимальная задержка для пользователя |
Хранить прогресс только локально рискованно: переустановка = потеря ачивок = негативный опыт. PlayFab Player Data или Google Play Games Snapshots решают это. Серверная синхронизация лучше локального хранения в 3–5 раз по надёжности и retention.
Модель данных
[Serializable]
public class Achievement
{
public string id;
public string titleKey; // локализация
public string descriptionKey;
public AchievementType type; // Counter, OneTime, Streak
public int targetValue;
public List<Reward> rewards;
public bool isSecret; // скрытые до выполнения
public string[] requiredAchievements; // цепочки зависимостей
}
public enum AchievementType
{
OneTime, // выполнено или нет
Counter, // прогресс 0..targetValue
Streak, // N дней подряд
Cumulative // накопительно за всё время
}
[Serializable]
public class AchievementProgress
{
public string achievementId;
public int currentValue;
public bool isUnlocked;
public DateTime? unlockedAt;
public bool rewardClaimed;
}
AchievementsManager
public class AchievementsManager : MonoBehaviour
{
public static AchievementsManager Instance { get; private set; }
private Dictionary<string, AchievementProgress> _progress;
private AchievementDatabase _database;
// Вызывается из игровой логики
public void TrackEvent(string eventType, int value = 1, Dictionary<string, object> context = null)
{
foreach (var achievement in _database.GetAchievementsByEvent(eventType))
{
var progress = GetOrCreate(achievement.id);
if (progress.isUnlocked) continue;
switch (achievement.type)
{
case AchievementType.Counter:
case AchievementType.Cumulative:
progress.currentValue += value;
break;
case AchievementType.OneTime:
progress.currentValue = 1;
break;
}
if (progress.currentValue >= achievement.targetValue)
Unlock(achievement, progress);
}
SaveProgress();
}
private void Unlock(Achievement achievement, AchievementProgress progress)
{
progress.isUnlocked = true;
progress.unlockedAt = DateTime.UtcNow;
// Уведомление игрока
AchievementPopupUI.Instance.Show(achievement);
// Аналитика
GameAnalytics.NewDesignEvent($"Achievement:Unlocked:{achievement.id}");
// Синхронизация с платформой
SyncWithPlatform(achievement);
}
}
Метод TrackEvent — единственная точка входа из геймплея. Это значит, что добавление нового достижения не требует изменений в боевой логике, системе квестов или магазине — только новая запись в AchievementDatabase.
Как проектировать Streak-достижения?
Серия входов подряд — один из лучших retention-инструментов. Требует аккуратной обработки дат:
public void RecordDailyLogin()
{
var lastLogin = PlayerPrefs.GetString("last_login_date", "");
var today = DateTime.UtcNow.Date.ToString("yyyy-MM-dd");
var yesterday = DateTime.UtcNow.Date.AddDays(-1).ToString("yyyy-MM-dd");
if (lastLogin == today) return; // уже засчитано сегодня
int streak = PlayerPrefs.GetInt("login_streak", 0);
streak = (lastLogin == yesterday) ? streak + 1 : 1; // сброс если пропустил день
PlayerPrefs.SetString("last_login_date", today);
PlayerPrefs.SetInt("login_streak", streak);
TrackEvent("daily_login_streak", streak);
}
Важно использовать UTC, а не локальное время — иначе игрок в UTC+12 может получить двойной бонус при смене дня.
Система наград и их баланс
Каждое достижение может выдавать один или несколько типов наград: внутриигровая валюта, предметы, косметика, скины. Важно настроить баланс — награда должна быть ценной, но не нарушать экономику игры. Мы используем серверную верификацию, чтобы предотвратить повторное получение наград через взлом клиента. Свяжитесь с нами для консультации по вашему проекту.
Интеграция с платформенными достижениями
Google Play Games и Game Center имеют собственные ачивки, которые видны в платформенном интерфейсе:
// Google Play Games (Play Games Services v2)
PlayGamesPlatform.Instance.UnlockAchievement("CgkI6ISmlocOEAIQAQ");
// Game Center (iOS)
GKAchievement achievement = new GKAchievement("first_boss_killed");
achievement.percentComplete = 100;
GKAchievement.Report(new[] { achievement }, (error) => { });
Синхронизируем только те достижения, которые имеют смысл на платформе. Не нужно дублировать все 100 внутриигровых ачивок в Game Center — только ключевые milestone.
Процесс работы
- Аналитика и прототипирование — определяем цели (retention, монетизация), выбираем типы достижений.
- Проектирование базы данных — создаём модель
Achievement, настраиваем связи и зависимости. - Реализация ядра —
AchievementsManager,TrackEvent, сохранение прогресса. - Интеграция с платформами — подключаем Google Play Games, Game Center, настраиваем синхронизацию.
- UI и визуализация — список достижений, прогресс-бары, popup при разблокировке.
- Система наград — выдача валюты, предметов, косметики с серверной верификацией.
- Аналитика и балансировка — настраиваем события, тестируем сложность, корректируем.
- Деплой и мониторинг — интеграция с App Store Connect и Google Play Console.
Что входит в работу
- Проектирование схемы достижений и системы событий
- Реализация
AchievementsManagerс типами Counter/OneTime/Streak - Синхронизация прогресса с PlayFab / Google Play Games / Game Center
- UI: список достижений, прогресс-бары, popup при разблокировке
- Система наград: валюта, предметы, косметика
- Аналитика разблокировок для балансировки сложности
- Локализация заголовков и описаний
Сроки
Базовая система без платформенной интеграции: 4–6 дней. Полная система с синхронизацией, UI и наградами: 1,5–2,5 недели. Закажите проектирование системы достижений под вашу игру — мы подберём оптимальную архитектуру с учётом жанра и целевой аудитории. Получите консультацию по интеграции с платформами.







