286 lines
10 KiB
C#
286 lines
10 KiB
C#
using UnityEngine;
|
||
using UnityEngine.Networking;
|
||
using System.Collections;
|
||
using System.Collections.Generic;
|
||
using System.IO;
|
||
using System;
|
||
using TMPro;
|
||
using UnityEngine.UI;
|
||
|
||
// Класс для десериализации данных от сервера
|
||
[Serializable]
|
||
public class LevelEntry
|
||
{
|
||
public string id; // Guid с сервера придет как строка
|
||
public string name;
|
||
public string hash;
|
||
public string uploadDate;
|
||
public string authorName;
|
||
}
|
||
|
||
//public class accountData
|
||
// {
|
||
// public Guid id;
|
||
// public int CompleteLevels;
|
||
// public int CompleteCenter;
|
||
// public int CompleteRight;
|
||
// public int CompleteLeft;
|
||
// public List<int> CollectAchievements;
|
||
// public List<int> HaveSword;
|
||
// public List<int> HaveHead;
|
||
// public List<int> HaveSkins;
|
||
// public List<int> EntityKilled;
|
||
// public List<int> OtherStat;
|
||
// public List<int> HaveOther;
|
||
// }
|
||
[System.Serializable]
|
||
public class account
|
||
{
|
||
public Guid id;
|
||
public string name ;
|
||
public int level ;
|
||
public List<string> levels ;
|
||
public int CompletedLevels ;
|
||
public int HaveSkins ;//20
|
||
public int HaveMoneys ;
|
||
public string password ;
|
||
public DateTime CreateDate ;
|
||
public int HaveMetall ;
|
||
public bool disabled ;
|
||
public int status ;
|
||
}
|
||
|
||
// Обертка для JSON-массива (Unity не умеет парсить чистые массивы через JsonUtility)
|
||
[Serializable]
|
||
public class LevelListWrapper
|
||
{
|
||
public List<LevelEntry> levels;
|
||
}
|
||
|
||
public class ServerClient : MonoBehaviour
|
||
{
|
||
public GameObject Canv;
|
||
public List<Button> starts;
|
||
public GameObject LevelOpener;
|
||
public List<GameObject> Openers;
|
||
public RectTransform LevelList;
|
||
public List<Button.ButtonClickedEvent> Open;
|
||
public List<Button> AuthorAcc;
|
||
public List<Button> Delete;
|
||
|
||
public Image AuthIcon;
|
||
public TMP_Text AuthName;
|
||
public TMP_Text AuthLevelsCount;
|
||
// public TransferScript TS;
|
||
|
||
void Start()
|
||
{GetPublicLevels((levels) => {
|
||
// Внутри этих скобок переменная 'data' — это и есть твой «просто лист»
|
||
List<LevelEntry> myLocalList = levels;
|
||
Debug.Log("Получили список из " + myLocalList.Count + " элементов");
|
||
for(int i = 0; i < myLocalList.Count; i++)
|
||
{
|
||
print($"{levels[i].name}, {levels[i].hash}, {levels[i].id}");
|
||
}
|
||
|
||
for (int i = 0; i < myLocalList.Count; i++)
|
||
{
|
||
|
||
int num = i;
|
||
Openers.Add(Instantiate(LevelOpener, LevelOpener.transform.parent));
|
||
Openers[i].GetComponent<RectTransform>().position -= new Vector3(0, i * LevelOpener.GetComponent<RectTransform>().rect.height* Canv.transform.localScale.y*1.1f, 0);
|
||
Openers[i].GetComponentsInChildren<TMP_Text>()[0].text = levels[i].name;
|
||
Openers[i].GetComponentsInChildren<TMP_Text>()[1].text = levels[i].authorName;
|
||
starts.Add(Openers[i].GetComponentInChildren<Button>());
|
||
print(starts.IndexOf(starts[i]));
|
||
Open.Add(new Button.ButtonClickedEvent { });
|
||
Open[i].AddListener(() => DownloadLevel(levels[num].id));
|
||
print(i);
|
||
starts[i].onClick.AddListener(() => DownloadLevel(levels[num].id));
|
||
AuthorAcc.Add(Openers[i].GetComponentsInChildren<Button>()[1]);
|
||
AuthorAcc[i].onClick.AddListener(() => GetAuthor(levels[num].authorName));
|
||
//Delete.Add(Openers[i].GetComponentsInChildren<Button>()[2]);
|
||
//Delete[i].onClick.AddListener(() => Dellvl(levels[num].id));
|
||
//upload.Add(Openers[i].transform.GetChild(1).GetComponent<Button>());
|
||
//uplo.Add(new Button.ButtonClickedEvent { });
|
||
//uplo[i].AddListener(() => Upl(num));
|
||
//upload[i].onClick.AddListener(() => Upl(num));
|
||
|
||
}
|
||
LevelList.sizeDelta = new Vector2(0, myLocalList.Count * LevelOpener.GetComponent<RectTransform>().sizeDelta.y*1.1f);});
|
||
}
|
||
private string baseUrl = "http://mc1.live-on.pro:64096/api/levels/";
|
||
void PlayOpen(string ID)
|
||
{
|
||
Buttons bb = new Buttons();
|
||
print(ID);
|
||
TransferScript TS = GameObject.Find("Tobj").GetComponent<TransferScript>();
|
||
DontDestroyOnLoad(TS);
|
||
TS.string1 = Application.persistentDataPath + "/" +ID;
|
||
bb.OpenScene("ImportLevel");
|
||
}
|
||
|
||
|
||
|
||
// --- 1. ЗАГРУЗКА (Твой существующий код, немного подправленный) ---
|
||
public void SendLevelToServer(string filePath, string levelName, string fileHash, string existingId = null)
|
||
{
|
||
StartCoroutine(UploadRoutine(filePath, levelName, fileHash, existingId));
|
||
}
|
||
|
||
private IEnumerator UploadRoutine(string filePath, string levelName, string fileHash, string existingId)
|
||
{
|
||
if (!File.Exists(filePath)) yield break;
|
||
|
||
byte[] fileData = File.ReadAllBytes(filePath);
|
||
WWWForm form = new WWWForm();
|
||
form.AddBinaryData("file", fileData, Path.GetFileName(filePath), "application/octet-stream");
|
||
form.AddField("name", levelName);
|
||
form.AddField("hash", fileHash);
|
||
|
||
// Если мы обновляем старый уровень, передаем его ID
|
||
if (!string.IsNullOrEmpty(existingId))
|
||
form.AddField("existingId", existingId);
|
||
|
||
using (UnityWebRequest www = UnityWebRequest.Post(baseUrl + "upload", form))
|
||
{
|
||
yield return www.SendWebRequest();
|
||
if (www.result == UnityWebRequest.Result.Success)
|
||
Debug.Log("Уровень успешно на сервере: " + www.downloadHandler.text);
|
||
}
|
||
}
|
||
|
||
// --- 2. ПОЛУЧЕНИЕ СПИСКА (Для Игрока Б) ---
|
||
public void GetPublicLevels(Action<List<LevelEntry>> callback)
|
||
{
|
||
StartCoroutine(GetLevelsRoutine(callback));
|
||
}
|
||
|
||
private IEnumerator GetLevelsRoutine(Action<List<LevelEntry>> callback)
|
||
{
|
||
using (UnityWebRequest www = UnityWebRequest.Get(baseUrl + "list"))
|
||
{
|
||
yield return www.SendWebRequest();
|
||
|
||
if (www.result == UnityWebRequest.Result.Success)
|
||
{
|
||
// Магия: превращаем [{},{}] в {"levels":[{},{}]} чтобы Unity понял
|
||
string rawJson = www.downloadHandler.text;
|
||
string processedJson = "{\"levels\":" + rawJson + "}";
|
||
|
||
LevelListWrapper wrapper = JsonUtility.FromJson<LevelListWrapper>(processedJson);
|
||
callback?.Invoke(wrapper.levels);
|
||
}
|
||
else
|
||
{
|
||
Debug.LogError("Не удалось получить список: " + www.error);
|
||
}
|
||
}
|
||
}
|
||
|
||
// --- 3. СКАЧИВАНИЕ ФАЙЛА (Для Игрока Б) ---
|
||
public void DownloadLevel(string levelId)
|
||
{
|
||
StartCoroutine(DownloadRoutine(levelId));
|
||
}
|
||
|
||
private IEnumerator DownloadRoutine(string levelId)
|
||
{
|
||
string url = baseUrl + "download/" + levelId;
|
||
// Путь, куда сохраняем на телефоне/ПК
|
||
string savePath = Path.Combine(Application.persistentDataPath, levelId + ".lpjl");
|
||
|
||
using (UnityWebRequest www = UnityWebRequest.Get(url))
|
||
{
|
||
yield return www.SendWebRequest();
|
||
|
||
if (www.result == UnityWebRequest.Result.Success)
|
||
{
|
||
// Записываем байты в файл
|
||
File.WriteAllBytes(savePath, www.downloadHandler.data);
|
||
Debug.Log($"Уровень скачан и сохранен в: {savePath}");
|
||
ServerClient SC = new ServerClient();
|
||
SC.PlayOpen(levelId);
|
||
// ТУТ ВЫЗЫВАЙ СВОЙ ИМПОРТ УРОВНЯ В ИГРУ
|
||
}
|
||
else
|
||
{
|
||
Debug.LogError("Ошибка при скачивании: " + www.error);
|
||
}
|
||
}
|
||
}
|
||
|
||
public void Dellvl(string levelId)
|
||
{
|
||
StartCoroutine(DeleteLevel(levelId));
|
||
}
|
||
|
||
private IEnumerator DeleteLevel(string levelId)
|
||
{
|
||
string url = baseUrl + "delete/" + levelId;
|
||
// Путь, куда сохраняем на телефоне/ПК
|
||
|
||
using (UnityWebRequest www = UnityWebRequest.Delete(url))
|
||
{
|
||
yield return www.SendWebRequest();
|
||
|
||
if (www.result == UnityWebRequest.Result.Success)
|
||
{
|
||
Debug.Log("Level deleted, id:" + levelId);
|
||
}
|
||
else
|
||
{
|
||
Debug.LogError("Ошибка при удалении: " + www.error);
|
||
}
|
||
}
|
||
}
|
||
|
||
public void SendAccountData(string filePath, string levelName, string fileHash, string existingId = null)
|
||
{
|
||
//accountData AD = new accountData;
|
||
//AD.id =
|
||
StartCoroutine(UploadRoutine(filePath, levelName, fileHash, existingId));
|
||
}
|
||
|
||
public IEnumerator UploadData(string filePath, string levelName, string fileHash, string existingId)
|
||
{
|
||
if (!File.Exists(filePath)) yield break;
|
||
|
||
byte[] fileData = File.ReadAllBytes(filePath);
|
||
WWWForm form = new WWWForm();
|
||
form.AddBinaryData("file", fileData, Path.GetFileName(filePath), "application/octet-stream");
|
||
form.AddField("name", levelName);
|
||
form.AddField("hash", fileHash);
|
||
|
||
// Если мы обновляем старый уровень, передаем его ID
|
||
if (!string.IsNullOrEmpty(existingId))
|
||
form.AddField("existingId", existingId);
|
||
|
||
using (UnityWebRequest www = UnityWebRequest.Post(baseUrl + "upload", form))
|
||
{
|
||
yield return www.SendWebRequest();
|
||
if (www.result == UnityWebRequest.Result.Success)
|
||
Debug.Log("Уровень успешно на сервере: " + www.downloadHandler.text);
|
||
}
|
||
}
|
||
public void GetAuthor(string name)
|
||
{
|
||
StartCoroutine(GetA(name));
|
||
}
|
||
|
||
public IEnumerator GetA(string name)
|
||
{
|
||
string basetUrl = "http://mc1.live-on.pro:64096/api/accounts/GetA/";
|
||
using(UnityWebRequest www = UnityWebRequest.Get(basetUrl + name))
|
||
{
|
||
yield return www.SendWebRequest();
|
||
|
||
string json = www.downloadHandler.text;
|
||
print(json);
|
||
account acc = JsonUtility.FromJson<account>(json);
|
||
AuthName.text = acc.name;
|
||
Debug.Log(acc.levels);
|
||
AuthLevelsCount.text = (acc.levels.Count).ToString();
|
||
}
|
||
}
|
||
}
|