fack
This commit is contained in:
231
Assets/Inventory/Scripts/ItemBuilderTool.cs
Normal file
231
Assets/Inventory/Scripts/ItemBuilderTool.cs
Normal file
@@ -0,0 +1,231 @@
|
||||
using UnityEngine;
|
||||
using UnityEngine.UI;
|
||||
using UnityEditor;
|
||||
using TMPro;
|
||||
|
||||
public class ItemBuilderTool : EditorWindow
|
||||
{
|
||||
// Основные данные
|
||||
private string itemName = "NewItem";
|
||||
private string itemId = "";
|
||||
private string description = "";
|
||||
private ItemType itemType = ItemType.Material;
|
||||
|
||||
// Визуал
|
||||
private GameObject modelPrefab;
|
||||
private Sprite icon;
|
||||
private Color previewColor = Color.gray;
|
||||
|
||||
// Свойства
|
||||
private int maxStack = 64;
|
||||
private int value = 1;
|
||||
private float weight = 1f;
|
||||
private bool isDroppable = true;
|
||||
private bool isStackable = true;
|
||||
|
||||
// Префаб
|
||||
private GameObject worldItemPrefab;
|
||||
|
||||
[MenuItem("Tools/Item Builder")]
|
||||
public static void ShowWindow()
|
||||
{
|
||||
GetWindow<ItemBuilderTool>("Конструктор Предметов");
|
||||
}
|
||||
|
||||
void OnGUI()
|
||||
{
|
||||
GUILayout.Label("Создание предмета", EditorStyles.boldLabel);
|
||||
|
||||
// Основные данные
|
||||
GUILayout.Label("Основное", EditorStyles.miniBoldLabel);
|
||||
itemName = EditorGUILayout.TextField("Название", itemName);
|
||||
itemId = EditorGUILayout.TextField("ID", itemId);
|
||||
description = EditorGUILayout.TextField("Описание", description);
|
||||
itemType = (ItemType)EditorGUILayout.EnumPopup("Тип предмета", itemType);
|
||||
|
||||
GUILayout.Space(10);
|
||||
|
||||
// Визуал
|
||||
GUILayout.Label("Визуал", EditorStyles.miniBoldLabel);
|
||||
modelPrefab = (GameObject)EditorGUILayout.ObjectField("3D модель", modelPrefab, typeof(GameObject), false);
|
||||
icon = (Sprite)EditorGUILayout.ObjectField("Иконка", icon, typeof(Sprite), false);
|
||||
|
||||
if (icon == null)
|
||||
{
|
||||
previewColor = EditorGUILayout.ColorField("Цвет иконки", previewColor);
|
||||
}
|
||||
|
||||
GUILayout.Space(10);
|
||||
|
||||
// Свойства
|
||||
GUILayout.Label("Свойства", EditorStyles.miniBoldLabel);
|
||||
maxStack = EditorGUILayout.IntField("Макс. стек", maxStack);
|
||||
value = EditorGUILayout.IntField("Цена", value);
|
||||
weight = EditorGUILayout.FloatField("Вес", weight);
|
||||
isDroppable = EditorGUILayout.Toggle("Можно выбросить", isDroppable);
|
||||
isStackable = EditorGUILayout.Toggle("Стек", isStackable);
|
||||
|
||||
GUILayout.Space(10);
|
||||
|
||||
// Префаб
|
||||
GUILayout.Label("Префаб предмета в мире", EditorStyles.miniBoldLabel);
|
||||
worldItemPrefab = (GameObject)EditorGUILayout.ObjectField("WorldItem Prefab", worldItemPrefab, typeof(GameObject), false);
|
||||
|
||||
GUILayout.Space(20);
|
||||
|
||||
// Кнопки
|
||||
GUI.color = Color.green;
|
||||
if (GUILayout.Button("Создать ItemData"))
|
||||
{
|
||||
CreateItemData();
|
||||
}
|
||||
|
||||
GUI.color = Color.cyan;
|
||||
if (GUILayout.Button("Создать WorldItem в сцене"))
|
||||
{
|
||||
CreateWorldItem();
|
||||
}
|
||||
|
||||
GUI.color = Color.yellow;
|
||||
if (GUILayout.Button("Создать префаб"))
|
||||
{
|
||||
CreateItemPrefab();
|
||||
}
|
||||
|
||||
GUI.color = Color.white;
|
||||
|
||||
GUILayout.Space(10);
|
||||
EditorGUILayout.HelpBox(
|
||||
"1. Заполните данные предмета\n" +
|
||||
"2. Назначьте модель и иконку\n" +
|
||||
"3. Создайте ItemData или префаб",
|
||||
MessageType.Info);
|
||||
}
|
||||
|
||||
void CreateItemData()
|
||||
{
|
||||
if (string.IsNullOrEmpty(itemName))
|
||||
{
|
||||
EditorUtility.DisplayDialog("Ошибка", "Введите название предмета", "OK");
|
||||
return;
|
||||
}
|
||||
|
||||
var item = ScriptableObject.CreateInstance<ItemData>();
|
||||
|
||||
item.id = string.IsNullOrEmpty(itemId) ? GUID.Generate().ToString() : itemId;
|
||||
item.itemName = itemName;
|
||||
item.description = description;
|
||||
item.type = itemType;
|
||||
item.modelPrefab = modelPrefab;
|
||||
item.icon = icon != null ? icon : CreatePlaceholderIcon();
|
||||
item.maxStack = maxStack;
|
||||
item.value = value;
|
||||
item.weight = weight;
|
||||
item.isDroppable = isDroppable;
|
||||
item.isStackable = isStackable;
|
||||
|
||||
// Сохраняем
|
||||
string path = $"Assets/Inventory/Items/{itemName}.asset";
|
||||
string folder = System.IO.Path.GetDirectoryName(path);
|
||||
if (!System.IO.Directory.Exists(folder))
|
||||
{
|
||||
System.IO.Directory.CreateDirectory(folder);
|
||||
}
|
||||
|
||||
AssetDatabase.CreateAsset(item, path);
|
||||
AssetDatabase.SaveAssets();
|
||||
|
||||
Selection.activeObject = item;
|
||||
Debug.Log($"[ItemBuilder] Создан: {itemName}");
|
||||
}
|
||||
|
||||
void CreateWorldItem()
|
||||
{
|
||||
if (modelPrefab == null)
|
||||
{
|
||||
// Создаём простой визуал
|
||||
var itemGO = new GameObject(itemName);
|
||||
var visual = GameObject.CreatePrimitive(PrimitiveType.Cube);
|
||||
visual.name = "Visual";
|
||||
visual.transform.SetParent(itemGO.transform);
|
||||
visual.transform.localPosition = Vector3.zero;
|
||||
visual.transform.localScale = Vector3.one * 0.3f;
|
||||
DestroyImmediate(visual.GetComponent<Collider>());
|
||||
|
||||
var worldItem = itemGO.AddComponent<WorldItem>();
|
||||
var col = itemGO.AddComponent<SphereCollider>();
|
||||
col.radius = 0.5f;
|
||||
col.isTrigger = true;
|
||||
|
||||
itemGO.transform.position = Vector3.zero;
|
||||
Selection.activeGameObject = itemGO;
|
||||
}
|
||||
else
|
||||
{
|
||||
var itemGO = Instantiate(modelPrefab);
|
||||
itemGO.name = itemName;
|
||||
itemGO.AddComponent<WorldItem>();
|
||||
itemGO.transform.position = Vector3.zero;
|
||||
Selection.activeGameObject = itemGO;
|
||||
}
|
||||
|
||||
Debug.Log($"[ItemBuilder] Создан WorldItem: {itemName}");
|
||||
}
|
||||
|
||||
void CreateItemPrefab()
|
||||
{
|
||||
string path = EditorUtility.SaveFilePanelInProject(
|
||||
"Сохранить префаб",
|
||||
itemName,
|
||||
"prefab",
|
||||
"Выберите место");
|
||||
|
||||
if (string.IsNullOrEmpty(path)) return;
|
||||
|
||||
GameObject prefab;
|
||||
if (modelPrefab != null)
|
||||
{
|
||||
prefab = Instantiate(modelPrefab);
|
||||
prefab.name = itemName;
|
||||
}
|
||||
else
|
||||
{
|
||||
prefab = new GameObject(itemName);
|
||||
var visual = GameObject.CreatePrimitive(PrimitiveType.Cube);
|
||||
visual.name = "Visual";
|
||||
visual.transform.SetParent(prefab.transform);
|
||||
visual.transform.localPosition = Vector3.zero;
|
||||
visual.transform.localScale = Vector3.one * 0.3f;
|
||||
DestroyImmediate(visual.GetComponent<Collider>());
|
||||
}
|
||||
|
||||
prefab.AddComponent<WorldItem>();
|
||||
|
||||
var col = prefab.GetComponent<Collider>();
|
||||
if (col == null)
|
||||
{
|
||||
var sphere = prefab.AddComponent<SphereCollider>();
|
||||
sphere.radius = 0.5f;
|
||||
sphere.isTrigger = true;
|
||||
}
|
||||
|
||||
GameObject savedPrefab = PrefabUtility.SaveAsPrefabAsset(prefab, path);
|
||||
DestroyImmediate(prefab);
|
||||
|
||||
Selection.activeObject = savedPrefab;
|
||||
Debug.Log($"[ItemBuilder] Префаб сохранён: {path}");
|
||||
}
|
||||
|
||||
Sprite CreatePlaceholderIcon()
|
||||
{
|
||||
var tex = new Texture2D(64, 64);
|
||||
var colors = new Color[64 * 64];
|
||||
for (int i = 0; i < colors.Length; i++)
|
||||
{
|
||||
colors[i] = previewColor;
|
||||
}
|
||||
tex.SetPixels(colors);
|
||||
tex.Apply();
|
||||
return Sprite.Create(tex, new Rect(0, 0, 64, 64), new Vector2(0.5f, 0.5f));
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user