chunk 1: core gameplay scripts scenes runtime assets

This commit is contained in:
2026-04-06 11:02:34 +03:00
parent fa0388bc79
commit 0d11a097d8
703 changed files with 2292651 additions and 0 deletions

View File

@@ -0,0 +1,298 @@
using UnityEngine;
using UnityEngine.Networking;
using System.Threading.Tasks;
using System;
public class CoinWalletSystem : MonoBehaviour
{
private static CoinWalletSystem _instance;
public static CoinWalletSystem Instance
{
get
{
if (_instance == null)
{
_instance = FindAnyObjectByType<CoinWalletSystem>();
if (_instance != null)
{
#if UNITY_EDITOR
if (Application.isPlaying)
{
DontDestroyOnLoad(_instance.gameObject);
}
#else
DontDestroyOnLoad(_instance.gameObject);
#endif
}
}
return _instance;
}
}
private int walletCoins = 0;
private bool isInitialized = false;
private string baseUrl = "http://127.0.0.1:8001/api";
private CoinWalletUIManager uiManager;
private void Awake()
{
if (_instance == null)
{
_instance = this;
DontDestroyOnLoad(gameObject);
}
else if (_instance != this)
{
Destroy(gameObject);
}
}
private async void Start()
{
uiManager = FindAnyObjectByType<CoinWalletUIManager>();
if (!isInitialized)
{
Debug.Log("Starting wallet initialization...");
await InitializeWallet();
}
}
public async Task<bool> InitializeWallet()
{
try
{
bool success = await FetchWalletBalance();
return success;
}
catch (Exception e)
{
Debug.LogError($"Failed to initialize wallet: {e.Message}");
return false;
}
}
public bool IsInitialized()
{
return isInitialized;
}
private async Task<bool> FetchWalletBalance()
{
try
{
string url = $"{baseUrl}/wallet/?format=json"; // Use JSON format explicitly
Debug.Log($"Sending GET request to: {url}");
using (UnityWebRequest request = UnityWebRequest.Get(url))
{
string token = PlayerPrefs.GetString("AuthToken");
if (string.IsNullOrEmpty(token))
{
Debug.LogError("No auth token found in PlayerPrefs");
return false;
}
// Set Authorization and Accept headers
request.SetRequestHeader("Authorization", $"Token {token}");
request.SetRequestHeader("Accept", "application/json"); // Explicitly request JSON
Debug.Log($"Authorization header set: Token {token}");
var operation = request.SendWebRequest();
while (!operation.isDone)
await Task.Yield();
Debug.Log($"Request completed with status: {request.result}");
if (request.result == UnityWebRequest.Result.Success)
{
Debug.Log($"Response received: {request.downloadHandler.text}");
JsonData walletData = JsonUtility.FromJson<JsonData>(request.downloadHandler.text);
if (walletData != null)
{
walletCoins = walletData.balance;
Debug.Log($"Wallet balance updated: {walletCoins}");
return true;
}
else
{
Debug.LogError("Failed to parse JSON response. Response text is empty or invalid.");
return false;
}
}
else
{
Debug.LogError($"Request failed with status: {request.responseCode}, error: {request.error}");
return false;
}
}
}
catch (Exception e)
{
Debug.LogError($"Exception in FetchWalletBalance: {e.Message}");
return false;
}
}
public async Task AddCoins(int amount)
{
#if UNITY_EDITOR
// In development mode, simulate the API call
try
{
Debug.Log($"Development mode: Simulating adding {amount} coins");
await Task.Delay(500);
walletCoins += amount;
UpdateWalletUI();
Debug.Log($"Development mode: Successfully added {amount} coins. New balance: {walletCoins}");
return;
}
catch (Exception e)
{
Debug.LogError($"Development mode: Error adding coins: {e.Message}");
throw;
}
#else
try
{
// Create JSON payload instead of form data
string jsonPayload = JsonUtility.ToJson(new WalletUpdateRequest
{
amount = amount,
operation = "add"
});
using (UnityWebRequest request = new UnityWebRequest($"{baseUrl}/wallet/update/", "POST"))
{
byte[] bodyRaw = System.Text.Encoding.UTF8.GetBytes(jsonPayload);
request.uploadHandler = new UploadHandlerRaw(bodyRaw);
request.downloadHandler = new DownloadHandlerBuffer();
string token = PlayerPrefs.GetString("AuthToken");
if (string.IsNullOrEmpty(token))
{
Debug.LogError("No auth token found in PlayerPrefs");
throw new Exception("Authentication token not found");
}
// Set proper headers
request.SetRequestHeader("Authorization", $"Token {token}");
request.SetRequestHeader("Content-Type", "application/json");
request.SetRequestHeader("Accept", "application/json");
Debug.Log($"Sending request with payload: {jsonPayload}");
var operation = request.SendWebRequest();
while (!operation.isDone)
await Task.Yield();
if (request.result == UnityWebRequest.Result.Success)
{
Debug.Log($"Successfully added {amount} coins. Response: {request.downloadHandler.text}");
await FetchWalletBalance();
UpdateWalletUI();
}
else
{
string errorMessage = $"Failed to add coins. Status: {request.responseCode}, Error: {request.error}, Response: {request.downloadHandler.text}";
Debug.LogError(errorMessage);
throw new Exception(errorMessage);
}
}
}
catch (Exception e)
{
Debug.LogError($"Error adding coins: {e.Message}");
throw;
}
#endif
}
private void UpdateWalletUI()
{
try
{
if (uiManager == null)
{
uiManager = FindAnyObjectByType<CoinWalletUIManager>();
}
if (uiManager != null)
{
Debug.Log($"Updating UI with walletCoins: {walletCoins}");
uiManager.UpdateAllWallets(walletCoins);
}
else
{
Debug.LogWarning("CoinWalletUIManager not found, creating new instance");
var go = new GameObject("CoinWalletUIManager");
uiManager = go.AddComponent<CoinWalletUIManager>();
uiManager.UpdateAllWallets(walletCoins);
}
}
catch (Exception e)
{
Debug.LogError($"Error updating wallet UI: {e.Message}");
}
}
public int GetCurrentBalance()
{
return walletCoins;
}
public async Task ResetCoins()
{
try
{
WWWForm form = new WWWForm();
form.AddField("amount", 0);
form.AddField("operation", "reset");
using (UnityWebRequest request = UnityWebRequest.Post($"{baseUrl}/wallet/update/", form))
{
string token = PlayerPrefs.GetString("AuthToken");
request.SetRequestHeader("Authorization", $"Token {token}");
var operation = request.SendWebRequest();
while (!operation.isDone)
await Task.Yield();
if (request.result == UnityWebRequest.Result.Success)
{
walletCoins = 0;
UpdateWalletUI();
Debug.Log("Wallet reset successful");
}
else
{
Debug.LogError($"Failed to reset wallet: {request.error}");
}
}
}
catch (Exception e)
{
Debug.LogError($"Error resetting wallet: {e.Message}");
}
}
public async Task RefreshWallet()
{
await FetchWalletBalance();
UpdateWalletUI();
}
[Serializable]
private class JsonData
{
public int balance;
}
// Add this class to match your server's expected request format
[Serializable]
private class WalletUpdateRequest
{
public int amount;
public string operation;
}
}

View File

@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 954d672ae8dec97458b4fe7103351395

View File

@@ -0,0 +1,118 @@
using UnityEngine;
using TMPro;
using System.Threading.Tasks;
public class CoinWalletUIManager : MonoBehaviour
{
[SerializeField] private TextMeshProUGUI[] walletTexts;
// Performance: prevent repeated initialization and refresh spam
private bool hasInitialized = false;
private bool isRefreshing = false;
private float lastRefreshTime = 0f;
private const float REFRESH_COOLDOWN = 5f; // Minimum seconds between refreshes
private void Awake()
{
// IMPORTANT: Only use explicitly assigned walletTexts from Inspector
// Do NOT use GetComponentsInChildren as it will grab ALL text components!
if (walletTexts == null || walletTexts.Length == 0)
{
#if UNITY_EDITOR
Debug.LogWarning("[CoinWalletUIManager] No walletTexts assigned in Inspector. Please assign the coin balance TextMeshProUGUI references manually.");
#endif
// Don't fallback to GetComponentsInChildren - that corrupts other UI text!
}
}
private async void Start()
{
// Skip if no wallet texts are assigned
if (walletTexts == null || walletTexts.Length == 0)
{
#if UNITY_EDITOR
Debug.LogWarning("[CoinWalletUIManager] Skipping wallet initialization - no walletTexts assigned.");
#endif
return;
}
await InitializeWalletAsync();
}
private async Task InitializeWalletAsync()
{
if (hasInitialized) return;
int maxAttempts = 5; // Reduced from 10
int currentAttempt = 0;
float delayBetweenAttempts = 0.5f;
while (currentAttempt < maxAttempts)
{
if (CoinWalletSystem.Instance != null && CoinWalletSystem.Instance.IsInitialized())
{
UpdateAllWallets(CoinWalletSystem.Instance.GetCurrentBalance());
hasInitialized = true;
return;
}
#if UNITY_EDITOR
Debug.Log($"[CoinWalletUIManager] Waiting for wallet system... Attempt {currentAttempt + 1}/{maxAttempts}");
#endif
await Task.Delay((int)(delayBetweenAttempts * 1000));
currentAttempt++;
}
#if UNITY_EDITOR
Debug.LogWarning("[CoinWalletUIManager] CoinWalletSystem initialization timed out");
#endif
}
public void UpdateAllWallets(int amount)
{
if (walletTexts == null) return;
foreach (var walletText in walletTexts)
{
if (walletText != null)
{
walletText.text = amount.ToString();
}
}
}
public async void RefreshWalletUI()
{
// Skip if no wallet texts or if already refreshing
if (walletTexts == null || walletTexts.Length == 0) return;
if (isRefreshing) return;
// Cooldown to prevent refresh spam
if (Time.time - lastRefreshTime < REFRESH_COOLDOWN) return;
isRefreshing = true;
lastRefreshTime = Time.time;
#if UNITY_EDITOR
Debug.Log("[CoinWalletUIManager] Refreshing wallet UI...");
#endif
if (CoinWalletSystem.Instance != null)
{
await CoinWalletSystem.Instance.InitializeWallet();
UpdateAllWallets(CoinWalletSystem.Instance.GetCurrentBalance());
}
isRefreshing = false;
}
private void OnEnable()
{
// Only refresh if already initialized and cooldown passed
// This prevents spam when toggling between screens
if (hasInitialized && Time.time - lastRefreshTime >= REFRESH_COOLDOWN)
{
RefreshWalletUI();
}
}
}

View File

@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: a8a69b68660124a40af1d7b8dea156ce