forum.boolean.name

forum.boolean.name (http://forum.boolean.name/index.php)
-   Уроки (http://forum.boolean.name/forumdisplay.php?f=145)
-   -   Рисуем список текстур в редакторе (http://forum.boolean.name/showthread.php?t=17818)

WISHMASTER35 31.01.2013 20:00

Рисуем список текстур в редакторе
 
Вложений: 2
Написал интересный класс для рисования списка текстур. Список похож на тот, который используется в редактировании Terrain, но имеет еще возможность перетягивания элементов при помощи DragAndDrop.
Так же при помощи DragAndDrop можно перетянуть текстуру из ассетов и задать ее элементу списка. Хотя возможно было бы лучше, чтобы тексутра из ассетов вставлялась как новый элемент.

WISHMASTER35 31.01.2013 20:02

Ответ: Рисуем список текстур в редакторе
 
И основной класс. Кода конечно много, но как мог оптимизировал.
Тут, кстати, спойлера нету?
Код:

using UnityEditor;
using UnityEngine;
using System.Collections.Generic;

public class ImagesListViewer {

        private static Color SELECT_COLOR = new Color( 61/255f, 128/255f, 223/255f );
        private const string DRAG_AND_DROP = "drag block";
       
        public static int SelectionGrid(List<Texture> items, int index) {
                Rect rect = new Rect();
                int xCount, yCount;
                index = SelectionGrid(items, index, out rect, out xCount, out yCount);
                float width = rect.width / xCount;
                float height = rect.height / yCount;
               
               
                GUI.BeginGroup(rect);
                Vector2 mouse = Event.current.mousePosition;
                int posX = Mathf.FloorToInt(mouse.x/width);
                int posY = Mathf.FloorToInt(mouse.y/height);
                int realIndex = -1; // номер элемента под курсором
                if(posX >= 0 && posX < xCount && posY >= 0 && posY < yCount) realIndex = posY*xCount + posX;
               
                int dropX = Mathf.Clamp(posX, 0, xCount-1);
                int dropY = Mathf.Clamp(posY, 0, yCount-1);
                if(dropY == yCount-1 && items.Count%xCount != 0) dropX = Mathf.Clamp(dropX, 0, items.Count%xCount);
                int dropIndex = dropY*xCount + dropX; // ближайший элемент к курсору
               
                if(Event.current.type == EventType.MouseDrag && Event.current.button == 0 && realIndex == index && realIndex != -1) { //начинаем DragAndDrop
                        DragAndDrop.PrepareStartDrag();
                        DragAndDrop.objectReferences = new Object[0];
                        DragAndDrop.paths = new string[0];
                        DragAndDrop.SetGenericData(DRAG_AND_DROP, new Index(index));
                        DragAndDrop.StartDrag("DragAndDrop");
                        Event.current.Use();
                }
               
                if(Event.current.type == EventType.DragUpdated) { // проверяем можем ли принять DragAndDrop
                        Index data = (Index) DragAndDrop.GetGenericData(DRAG_AND_DROP);
                        if(data != null) {
                                DragAndDrop.visualMode = DragAndDropVisualMode.Link;
                                Event.current.Use();
                        }
                        if(DragAndDrop.objectReferences.Length == 1) {
                                if(DragAndDrop.objectReferences[0] is Texture) {
                                        DragAndDrop.visualMode = DragAndDropVisualMode.Link;
                                        Event.current.Use();
                                }
                        }
                }
                if(Event.current.type == EventType.DragPerform) { // DragAndDrop завершен
                        Index data = (Index) DragAndDrop.GetGenericData(DRAG_AND_DROP);
                        if(data != null) {
                                Texture moveItem = items[data.index];
                                items.RemoveAt(data.index);
                                if(dropIndex > data.index) dropIndex--;
                                dropIndex = Mathf.Clamp(dropIndex, 0, items.Count);
                                items.Insert(dropIndex, moveItem);
                                index = dropIndex;
                        }
                        if(DragAndDrop.objectReferences.Length == 1) {
                                if(DragAndDrop.objectReferences[0] is Texture) {
                                        if(realIndex != -1) items[realIndex] = (Texture) DragAndDrop.objectReferences[0];
                                }
                        }
                       
                        DragAndDrop.AcceptDrag();
                        Event.current.Use();
                }
                if(Event.current.type == EventType.Repaint && DragAndDrop.visualMode == DragAndDropVisualMode.Link) { // рисуем красную полоску
                        Vector2 pos = new Vector2(2+dropX*width, 2+dropY*height);
                        Rect lineRect = new Rect(pos.x-2, pos.y, 2, width-2);
                        FillRect(lineRect, Color.red);
                }
                GUI.EndGroup();
               
                return index;
        }
       
        private static int SelectionGrid(List<Texture> items, int index, out Rect rect, out int xCount, out int yCount) {
                xCount = Mathf.FloorToInt( Screen.width/66f ); // количество элементов по горизонтале
                yCount = Mathf.CeilToInt( (float)items.Count/xCount ); // количество элементов по вертикали
               
                rect = GUILayoutUtility.GetAspectRect((float)xCount/yCount); // выделить место для картинок и лейбов
                float labelHeight = GUI.skin.label.CalcHeight(GUIContent.none, 0); // высота текста
                GUILayout.Space(labelHeight*yCount);
                rect.height += labelHeight*yCount;
               
               
                float itemWidth = rect.width / xCount;
                float itemHeight = rect.height / yCount;
               
                for(int y=0, i=0; y<yCount; y++) {
                        for(int x=0; x<xCount && i<items.Count; x++, i++) {
                                Rect position = new Rect(rect.x+itemWidth*x, rect.y+itemHeight*y, itemWidth, itemHeight);
                                position.xMin += 2;
                                position.yMin += 2;
                               
                                bool selected = DrawItem(position, items[i], i == index, i);
                                if(selected) index = i;
                        }
                }
               
                return index;
        }
       
        private static bool DrawItem(Rect position, Texture texture, bool selected, int index) {
                Rect texturePosition = position;
                texturePosition.height = texturePosition.width;
                Rect labelPosition = position;
                labelPosition.yMin += texturePosition.height;
               
                if(selected) FillRect(labelPosition, SELECT_COLOR);
                if(texture) {
                        GUI.DrawTexture(texturePosition, texture);
                        GUI.Label(labelPosition, texture.name);
                } else {
                        FillRect(texturePosition, Color.gray);
                        GUI.Label(labelPosition, "Null");
                }
               
                if(Event.current.type == EventType.MouseDown && position.Contains(Event.current.mousePosition)) {
                        Event.current.Use();
                        return true;
                }
                return false;
        }
       
        private static void FillRect(Rect rect, Color color) {
                Color oldColor = GUI.color;
                GUI.color = color;
                GUI.DrawTexture(rect, EditorGUIUtility.whiteTexture);
                GUI.color = oldColor;
        }
       
        class Index {
                public int index;
                public Index(int index) {
                        this.index = index;
                }
        }
       
}


pax 31.01.2013 21:15

Ответ: Рисуем список текстур в редакторе
 
Спойлер есть - тэг оффтоп.

ARA 31.01.2013 23:15

Ответ: Рисуем список текстур в редакторе
 
А чем отличается от стандартного списка текстур?

WISHMASTER35 31.01.2013 23:20

Ответ: Рисуем список текстур в редакторе
 
ARENSHI, DragAndDrop. Впрочем какая разница, все равно эти стандартные средства недоступны.

pax 01.02.2013 10:42

Ответ: Рисуем список текстур в редакторе
 
Если заглянуть в класс http://docs.unity3d.com/Documentatio...etPreview.html то можно и модели например рисовать таким же образом.

а еще есть http://docs.unity3d.com/Documentatio...ewTexture.html

WISHMASTER35 01.02.2013 15:04

Ответ: Рисуем список текстур в редакторе
 
pax, да, когда-то давно рисовал список префабов при помощи этих функций. Только не у всех префабов есть привью. У системы частиц привью не создается.


Часовой пояс GMT +4, время: 20:04.

vBulletin® Version 3.6.5.
Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
Перевод: zCarot