{"id":13663217,"url":"https://github.com/arimger/Unity-Editor-Toolbox","last_synced_at":"2025-04-25T13:32:21.387Z","repository":{"id":37549740,"uuid":"201811024","full_name":"arimger/Unity-Editor-Toolbox","owner":"arimger","description":"Tools, custom attributes, drawers, hierarchy overlay, and other extensions for the Unity Editor.","archived":false,"fork":false,"pushed_at":"2025-04-22T15:56:29.000Z","size":6049,"stargazers_count":1813,"open_issues_count":15,"forks_count":131,"subscribers_count":25,"default_branch":"master","last_synced_at":"2025-04-22T16:51:55.232Z","etag":null,"topics":["attributes","inspector","unity","unity-asset","unity-editor","unity3d","unity3d-editor"],"latest_commit_sha":null,"homepage":"","language":"C#","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/arimger.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE.md","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null}},"created_at":"2019-08-11T20:18:59.000Z","updated_at":"2025-04-22T10:00:53.000Z","dependencies_parsed_at":"2024-01-11T20:42:59.035Z","dependency_job_id":"16dde465-7bf8-4854-9daf-3e123621f1f2","html_url":"https://github.com/arimger/Unity-Editor-Toolbox","commit_stats":{"total_commits":675,"total_committers":8,"mean_commits":84.375,"dds":0.07407407407407407,"last_synced_commit":"625cdcf68f695ee8572b1b8eb49a70d5f93adb07"},"previous_names":[],"tags_count":30,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/arimger%2FUnity-Editor-Toolbox","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/arimger%2FUnity-Editor-Toolbox/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/arimger%2FUnity-Editor-Toolbox/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/arimger%2FUnity-Editor-Toolbox/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/arimger","download_url":"https://codeload.github.com/arimger/Unity-Editor-Toolbox/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":250825062,"owners_count":21493390,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["attributes","inspector","unity","unity-asset","unity-editor","unity3d","unity3d-editor"],"created_at":"2024-08-02T05:02:21.508Z","updated_at":"2025-04-25T13:32:16.344Z","avatar_url":"https://github.com/arimger.png","language":"C#","readme":"# Unity Editor Toolbox\n\n## Introduction\n\nImprove usability and clarity of key features in Unity Editor for better workflow!\n\nThis Toolbox not only extends functionalities, it does so with the user in mind.\nWritten to be as flexible and optimized as possible. Now you and other programming professionals will be able to create a readable and useful component editor simply by using attributes. You’ll get fast and clear access to data from GameObjects placed in the Scene. Lastly, you’ll gain more control over the Project window. Go ahead, customize those folder icons.\n\nIt's worth to mention that prepared drawers are based on the custom, layout-based system. Additionally, I’m leaving you some useful scripts, classes, and functions that facilitate Editor extensions development.\n\nLearn all the details about the main features below.\n\n## System Requirements\nUnity 2018.x or newer\n\n## Dependencies\n\n[EditorCoroutines](https://docs.unity3d.com/Packages/com.unity.editorcoroutines@0.0/api/Unity.EditorCoroutines.Editor.html)\n\n## Installation\n\n- Install Editor Toolbox package:\n\t- 1 way: Find Unity Package Manager (Window/Package Manager) and add package using this git URL:\n\t```\n\thttps://github.com/arimger/Unity-Editor-Toolbox.git#upm\n\t```\n\t- 2 way: Copy and paste `Assets/Editor Toolbox` directory into your project (Assets/...) + add dependencies\n\t- 3 way: Install via [OpenUPM registry](https://openupm.com):\n\t```\n\topenupm add com.browar.editor-toolbox\n\t```\n- Open Edit/Project Settings/Editor Toolbox window\n- If settings file is not found, press the \"Refresh\" button or create a new one\n- Manage settings in your way\n\t- Enable/disable Hierarchy overlay, choose allowed information\n\t- Enable/disable Project icons or/and assign own directories\n\t- Enable/disable Toolbox drawers or/and assign custom drawers\n\t- Enable/disable Toolbox Scene View and assign hotkeys\n\t\n---\n\u003e [!IMPORTANT]  \n\u003e This package is fully IMGUI-based, which means it may conflict with pure UI Toolkit features in your project. Additionally, Toolbox overwrites the 'base' custom Editor for all `UnityEngine.Objects`, it's a common solution but means that you can't combine other Inspector extensions/plugins.\n\n## Table Of Contents\n\n- [Attributes \u0026 Drawers](#drawers)\n\t- [Regular Drawers](#regulardrawers)\n\t- [Toolbox Drawers](#toolboxdrawers)\n\t\t- [Toolbox Decorator Attributes](#toolboxdecorator)\n\t\t- [Toolbox Condition Attributes](#toolboxcondition)\n\t\t- [Toolbox Property (Self/List) Attributes](#toolboxproperty)\n\t\t- [Toolbox Special Attributes](#toolboxspecial)\n\t\t- [Toolbox Archetype Attributes](#toolboxarchetype)\n\t\t- [SerializeReference (ReferencePicker)](#toolboxreference)\n\t\t- [Toolbox Custom Editors](#toolboxeditors)\n\t- [Material Drawers](#materialdrawers)\n- [Serialized Types](#serialized-types)\n- [Editor Extensions](#editor-extensions)\n\t- [Hierarchy](#hierarchy)\n\t- [Project](#project)\n\t- [Toolbar](#toolbar)\n\t- [SceneView](#sceneview)\n\t- [Utilities](#utilities)\n\n## Settings\n\nThe most important file, allows the user to manage all available features. Can be accessed from the Project Settings window (Edit/Project Settings.../Editor Toolbox) or directly inside the Project window. Make sure to have one valid settings file per project.\n\nAvailable features are divided into four groups:\n- Hierarchy\n- Project\n- Inspector\n- SceneView\n\nEach module is described in its respective section.\n\nIf you want to keep your custom settings between UET versions, create your own settings file:\n```\nCreate/Editor Toolbox/Settings\n```\n\n---\n\u003e [!IMPORTANT]  \n\u003e If you are getting warnings related to the current settings state, it most likely means that some features are not present in your Unity version. I suggest creating your own settings file and adjusting potential issues. Generally, it's always better to use a custom settings file rather than the default one. I'm planning to replace the ScriptableObject-based solution in the future, so it won't be a problem anymore.\n\n## Attributes \u0026 Drawers \u003ca name=\"drawers\"\u003e\u003c/a\u003e\n\n### Regular Drawers \u003ca name=\"regulardrawers\"\u003e\u003c/a\u003e\n\nDrawers based on built-in classes **PropertyDrawer/DecoratorDrawer** and associated **PropertyAttribute**.\nRegular drawers have priority over Toolbox drawers and they cannot be mixed.\n\n#### TagSelectorAttribute\n\nSupported types: **string**.\n\n```csharp\n[TagSelector]\npublic string var1;\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/tagselector.png)\n\n#### ProgressBarAttribute\n\nSupported types: **int**, **float**, **double**.\n\n```csharp\n[ProgressBar(\"Name\", minValue: 0.0f, maxValue: 100.0f, HexColor = \"#EB7D34\", IsInteractable = true)]\npublic float var1 = 80.0f;\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/progressbar1.png)\\\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/progressbar2.png)\n\n#### MinMaxSliderAttribute\n\nSupported types: **Vector2, Vector2Int**.\n\n```csharp\n[MinMaxSlider(0.5f, 71.7f)]\npublic Vector2 var1;\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/minmaxslider.png)\n\n#### AssetPreviewAttribute\n\nSupported types: UnityEngine.**Object**.\n\n```csharp\n[AssetPreview]\npublic GameObject var1;\n```\n\n```csharp\n[AssetPreview(useLabel: false)]\npublic Component var2;\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/assetpreview.png)\n\n#### SuffixAttribute\n\nSupported types: **all**.\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/suffix.png)\n\n\n#### EnumTogglesAttribute\n\nSupported types: **Enums**.\n\n```csharp\n[System.Flags]\npublic enum FlagExample\n{\n\tNothing = 0,\n\tFlag1 = 1,\n\tFlag2 = 2,\n\tFlag3 = 4,\n\tFlag4 = 8,\n\tFlag5 = 16,\n\tFlag6 = 32,\n\tFlag7 = 64,\n\tFlag8 = 128,\n\tFlag9 = 256,\n\tEverything = ~0\n}\n\n[EnumToggles]\npublic FlagExample enumFlag = FlagExample.Flag1 | FlagExample.Flag2 | FlagExample.Flag6;\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/enumtoggles.png)\n\n#### NotNullAttribute\n\nSupported types: UnityEngine.**Object**.\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/notnull1.png)\\\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/notnull2.png)\n\n\n#### DirectoryAttribute\n\nSupported types: **string**.\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/directory1.png)\\\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/directory2.png)\n\n#### SceneNameAttribute\n\nSupported types: **string**.\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/scenename1.png)\\\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/scenename2.png)\n\n#### PresetAttribute\n\nSupported types: **all**.\n\nRemark: can be used only within classes, structs are not supported.\n```csharp\nprivate readonly int[] presetValues = new[] { 1, 2, 3, 4, 5 };\n\n[Preset(nameof(presetValues))]\npublic int presetTarget;\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/preset.png)\n\n```csharp\nprivate readonly int[] presetValues = new[] { 1, 2, 3, 4, 5 };\nprivate readonly string[] optionLabels = new[] { \"a\", \"b\", \"c\", \"d\", \"e\" };\n\n[Preset(nameof(presetValues), nameof(optionLabels))]\npublic int presetTarget;\n```\n\n#### SearchableEnumAttribute\n\nSupported types: **Enums**.\n\n```csharp\n[SearchableEnum]\npublic KeyCode enumSearch;\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/enumsearch.png)\n\n#### ClampAttribute\n\nSupported types: **int, float, double**.\n\n```csharp\n[Clamp(minValue = 1.5f, maxValue = 11.3f)]\npublic double var1;\n```\n\n#### PasswordAttribute\n\nSupported types: **string**.\n\n```csharp\n[Password]\npublic string password;\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/password.png)\n\n#### LeftToggleAttribute\n\nSupported types: **bool**.\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/lefttoggle.png)\n\n#### FormattedNumberAttribute\n\nSupported types: **int, float, double**.\n\n```csharp\n[FormattedNumber]\npublic int bigNumber;\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/formattednumber.png)\n\n#### LayerAttribute\n\nSupported types: **int**.\n\n```csharp\n[Layer]\npublic int layer;\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/layer.png)\n\n#### ChildObjectOnlyAttribute\n\nSupported types: **GameObject, Component**.\n\n#### SceneObjectOnlyAttribute\n\nSupported types: **GameObject, Component**.\n\n#### PrefabObjectOnlyAttribute\n\nSupported types: **GameObject, Component**.\n\n#### NotPrefabObjectOnlyAttribute\n\nSupported types: **GameObject, Component**.\n\n---\n\n### Toolbox Drawers \u003ca name=\"toolboxdrawers\"\u003e\u003c/a\u003e\n\nDrawers are based on classes inherited from the **ToolboxDrawer** class and associated **ToolboxAttribute**. With this powerful custom system you are able to create really flexible drawers. You can use them without limitations (they work with sub-classes and as array children). Every ToolboxDrawer is layout-based. For proper work they need at least one settings file located in your project. You can find predefined one here - `Editor Toolbox/EditorSettings.asset`.\n\nExamples **'How to'** create custom ToolboxDrawers you can find [HERE](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Assets/Editor%20Toolbox/HOWTO.md).\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/inspector.png)\n\n#### Toolbox Decorator Attributes \u003ca name=\"toolboxdecorator\"\u003e\u003c/a\u003e\n\nDisplay/create something before and after property in the desired order (using Order property).   \nIn fact **ToolboxDecoratorDrawers** are like extended version of built-in **DecoratorDrawers**. \nUnfortunately, standard decorators won't always work with ToolboxDrawers so try to use this replacement instead.\n\nEach **ToolboxDecoratorAttribute** has two basic properties **Order** (indicates the drawing order) and **ApplyCondition** (determines if decorator will be disabled/hidden along with associated property).\n\n```csharp\n[BeginGroup(\"Group1\", Style = GroupStyle.Round)]\npublic int var1;\n[EndGroup]\npublic int var2;\n```\n```csharp\n//NOTE: you can use [SpaceArea] to adjust positions between layout elements\n[BeginHorizontal(LabelWidth = 50.0f)]\npublic int var1;\n[EndHorizontal]\npublic int var2;\n```\n```csharp\n[BeginHorizontalGroup(Label = \"Horizontal Group\", ControlFieldWidth = true, ElementsInLayout = 2)]\npublic GameObject gameObject;\n[SpaceArea]\n[EndHorizontalGroup]\n[ReorderableList]\npublic int[] ints;\n```\n```csharp\n[BeginIndent]\npublic int var1;\n[EndIndent]\npublic int var2;\n```\n```csharp\n[IndentArea(4)]\npublic int var1;\n```\n```csharp\n[SpaceArea(spaceBefore = 10.0f, spaceAfter = 5.0f, Order = 1)]\npublic int var1;\n```\n```csharp\n[Label(\"My Custom Header\", skinStyle: SkinStyle.Box, Alignment = TextAnchor.MiddleCenter)]\npublic int var1;\n```\n```csharp\n[Highlight(0, 1, 0)]\npublic int var1;\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/decorators.png)\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/horizontal.png)\n\n```csharp\n[EditorButton(nameof(MyMethod), \"\u003cb\u003eMy\u003c/b\u003e Custom Label\", activityType: ButtonActivityType.OnPlayMode, ValidateMethodName = nameof(ValidationMethod))]\npublic int var1;\n\nprivate void MyMethod()\n{\n\tDebug.Log(\"MyMethod is invoked\");\n}\n\nprivate bool ValidationMethod()\n{\n\treturn var1 == 0;\n}\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/button.png)\n\n```csharp\n[Help(\"Help information\", UnityMessageType.Warning, Order = -1)]\npublic int var1;\n```\n```csharp\n[DynamicHelp(nameof(Message), UnityMessageType.Error)]\npublic int var2;\n\npublic string Message =\u003e \"Dynamic Message\";\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/helpbox.png)\n\n```csharp\n[ImageArea(\"https://img.itch.zone/aW1nLzE5Mjc3NzUucG5n/original/Viawjm.png\", 150.0f)]\npublic int var1;\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/imagearea.png)\n\n```csharp\n[LabelWidth(220.0f)]\npublic int veryVeryVeryVeryVeryLongName;\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/labelwidth.png)\n\n\n#### Toolbox Condition Attributes \u003ca name=\"toolboxcondition\"\u003e\u003c/a\u003e\n\nEnable/disable or show/hide properties using custom conditions. You can use them together with any other type of drawer.\nEvery ToolboxConditionDrawer supports boolean, int, string, UnityEngine.Object and enum types and works even with array/list properties.\nYou are able to pass values from fields, properties, and methods.\n\n```csharp\npublic string StringValue =\u003e \"Sho\";\n[ShowIf(nameof(StringValue), \"show\")]\npublic int var1;\n```\n```csharp\npublic GameObject objectValue;\n[HideIf(nameof(objectValue), false)]\npublic int var2;\n```\n\n```csharp\npublic KeyCode enumValue = KeyCode.A;\n[EnableIf(nameof(enumValue), KeyCode.A)]\npublic int var1;\n```\n```csharp\n[DisableIf(nameof(GetFloatValue), 2.0f, Comparison = UnityComparisonMethod.GreaterEqual)]\npublic int var2;\n\npublic float GetFloatValue()\n{\n\treturn 1.6f;\n}\n```\n```csharp\n[DisableInPlayMode]\npublic int var1;\n```\n```csharp\n[DisableInEditMode]\npublic int var1;\n```\n```csharp\npublic int var1;\n[ShowDisabledIf(nameof(var1), 3, Comparison = UnityComparisonMethod.LessEqual)]\npublic int var2;\n```\n```csharp\npublic int var1;\n[HideDisabledIf(nameof(var1), 3, Comparison = UnityComparisonMethod.GreaterEqual)]\npublic int var2;\n```\n```csharp\npublic bool boolValue = true;\n[ShowWarningIf(nameof(boolValue), false, \"Message\", DisableField = true)]\npublic int var1;\n```\n\n```csharp\n[Disable, ReorderableList]\npublic int[] vars1 = new [] { 1, 2, 3, 4 };\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/disabled.png)\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/enableif1.png)\\\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/enableif2.png)\n\n#### Toolbox Property Attributes \u003ca name=\"toolboxproperty\"\u003e\u003c/a\u003e\n\n##### InLineEditorAttribute\n\nThis attribute gives a great possibility to extend all reference-related (UnityEngine.Object) fields. \nUsing it you are able to 'inline' Editors for: components, ScriptableObjects, Materials, Renderers, MeshFilters, Textures, AudioClips, etc.\n\n```csharp\n[InLineEditor(DisableEditor = false)]\npublic Transform var1;\n```\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/inlined3.png)\n```csharp\n[InLineEditor]\npublic AudioClip var1;\n```\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/inlined2.png)\n```csharp\n[InLineEditor(true, true)]\npublic Material var1;\n```\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/inlined1.png)\n\n```csharp\n[InLineEditor(HideScript = false)]\npublic MyCustomType var1;\n```\n\n##### Reorderable List\n\nCustom implementation of standard ReorderableList (UnityEditorInternal). Usable as an attribute in serialized fields or a single object in custom Editors.\n\n```csharp\nvar list = new ReorderableList(SerializedProperty property, string elementLabel, bool draggable, bool hasHeader, bool fixedSize);\n```\n```csharp\n[ReorderableList, InLineEditor]\npublic Canvas[] vars1;\n```\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/list4.png)\n```csharp\n[ReorderableList(ListStyle.Lined, \"Item\", Foldable = false)]\npublic List\u003cint\u003e linedStyleList;\n```\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/list1.png)\n```csharp\n[ReorderableList(ListStyle.Round)]\npublic List\u003cstring\u003e standardStyleList;\n```\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/list2.png)\n```csharp\n[ReorderableList(ListStyle.Boxed, fixedSize: true)]\npublic GameObject[] boxedStyleList = new GameObject[4];\n```\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/list3.png)\n\n\n```csharp\n[ReorderableListExposed(OverrideNewElementMethodName = nameof(GetValue))]\npublic int[] list;\n\nprivate int GetValue()\n{\n\treturn list.Length + Random.Range(0, 4);\n}\n```\n\n##### ScrollableItemsAttribute\n\nIt's a perfect solution to inspect large arrays/lists and optimize displaying them within the Inspector window.\n\n```csharp\n[ScrollableItems(defaultMinIndex: 0, defaultMaxIndex: 5)]\npublic GameObject[] largeArray = new GameObject[19];\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/scrollableitems.png)\n\n##### Other ToolboxProperty attributes\n\n**IgnoreParent** allows you to hide the parent's label, foldout arrow and remove the standard indentation for nested fields.\n\n```csharp\npublic Quaternion quaternion;\n[IgnoreParent]\npublic Quaternion q;\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/ignoreparent.png)\n\n```csharp\n[DynamicMinMaxSlider(nameof(minValue), nameof(MaxValue))]\npublic Vector2 vec2;\n\npublic float minValue;\npublic float MaxValue =\u003e 15.0f;\n```\n\n#### Toolbox Special Attributes \u003ca name=\"toolboxspecial\"\u003e\u003c/a\u003e\n\nAttributes handled internally by the ToolboxEditor. You can combine them with any other attributes.\n\n##### NewLabelAttribute\n\n```csharp\n[NewLabel(\"Custom Label\")]\npublic float var1 = 25.4f;\n```\n\n##### HideLabelAttribute\n\n```csharp\n[HideLabel]\npublic float var1;\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/hidelabel.png)\n\n##### LabelByChildAttribute\n\n```csharp\n[System.Serializable]\npublic class SampleClass1\n{\n\tpublic Material var1;\n\tpublic KeyCode var2;\n\tpublic SampleClass2 var3;\n}\n\n[System.Serializable]\npublic class SampleClass2\n{\n\tpublic int var1;\n\tpublic string var2;\n}\n\n[LabelByChild(\"var2\")]\npublic SampleClass1[] vars1;\n[LabelByChild(\"var3.var2\")]\npublic SampleClass1 var1;\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/labelbychild1.png)\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/labelbychild2.png)\n\n#### Toolbox Archetype Attributes \u003ca name=\"toolboxarchetype\"\u003e\u003c/a\u003e\n\nUsing this attribute you are able to implement custom patterns of frequently grouped **ToolboxAttributes**.\n\n\n```csharp\n[AttributeUsage(AttributeTargets.Field, AllowMultiple = true)]\npublic class TitleAttribute : ToolboxArchetypeAttribute\n{\n\tpublic TitleAttribute(string label)\n\t{\n\t\tLabel = label;\n\t}\n\n\n\tpublic override ToolboxAttribute[] Process()\n\t{\n\t\treturn new ToolboxAttribute[]\n\t\t{\n\t\t\tnew LabelAttribute(Label),\n\t\t\tnew LineAttribute(padding: 0)\n\t\t\t{\n\t\t\t\tApplyIndent = true\n\t\t\t}\n\t\t};\n\t}\n\n\n\tpublic string Label { get; private set; }\n}\n```\n\n```csharp\n[Title(\"Header\")]\npublic int var1;\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/title.png)\n\n#### SerializeReference (ReferencePicker) \u003ca name=\"toolboxreference\"\u003e\u003c/a\u003e\n\nYou can draw properties marked with the **[SerializeReference]** attribute with an additional type picker that allows you to manipulate what managed type will be serialized.\nDepending on the picked type we have different object creation strategies:\n- `Activator.CreateInstance(targetType)` (default constructor will be called and all readonly members will be initialized)\n\t- Target type has default constructor\n\t- Target type is a value type\n- `FormatterServices.GetUninitializedObject(targetType)` (object will be uninitialized)\n\t- Target type has one or more constructors with arguments\n\t- `ForceUninitializedInstance` property is set to true\n\t\nTo prevent issues after renaming types use `UnityEngine.Scripting.APIUpdating.MovedFromAttribute`.\n\n```csharp\n[SerializeReference, ReferencePicker(TypeGrouping = TypeGrouping.ByFlatName)]\npublic ISampleInterface var1;\n[SerializeReference, ReferencePicker(ForceUninitializedInstance = true)]\npublic ISampleInterface var1;\n[SerializeReference, ReferencePicker(ParentType = typeof(ClassWithInterface2)]\npublic ClassWithInterfaceBase var2;\n\npublic interface ISampleInterface { }\n\n[Serializable]\npublic struct Struct : ISampleInterface\n{\n\tpublic bool var1;\n\tpublic bool var2;\n}\n\npublic abstract class ClassWithInterfaceBase : ISampleInterface { }\n\n[Serializable]\npublic class ClassWithInterface1 : ClassWithInterfaceBase\n{\n\tpublic GameObject go;\n}\n\n[Serializable]\npublic class ClassWithInterface2 : ClassWithInterfaceBase\n{\n\t[LeftToggle]\n\tpublic bool var1;\n}\n\n[Serializable]\npublic class ClassWithInterface3 : ClassWithInterfaceBase\n{\n\tpublic int var1;\n}\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/referencepicker.png)\n\n##### SerializeReference generics support\n\nUnity 2023.x introduced support for serializing generic references.\nIn this case you can serialize generic types or use generics as a base class for your references.\n**ReferencePicker** will automatically create all available generic types if the generic definition satisfies the constraints.\n\n```csharp\n#if UNITY_2023_2_OR_NEWER\n[SerializeReference, ReferencePicker(TypeGrouping = TypeGrouping.None)]\npublic IGenericInterface\u003cstring\u003e genericString;\n[SerializeReference, ReferencePicker(TypeGrouping = TypeGrouping.None)]\npublic IGenericInterface\u003cint\u003e genericInt;\n[SerializeReference, ReferencePicker(TypeGrouping = TypeGrouping.None)]\npublic IGenericInterface\u003cbool\u003e genericBool;\n\npublic interface IGenericInterface\u003cTValue\u003e\n{\n\tTValue Value { get; }\n}\n\npublic class GenericInterfaceImplementation\u003cTValue\u003e : IGenericInterface\u003cTValue\u003e\n{\n\t[SerializeField]\n\tprivate TValue value;\n\n\tpublic TValue Value =\u003e value;\n}\n#endif\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/serializereferencegenerics.png)\n\n##### SerializeReference context menu operations\n\nYou can use few custom context menu operations for the **[SerializeReference]** fields:\n- **Copy Serialize Reference**: creates a deep copy of the linked reference\n- **Paste Serialize Reference**: allows to paste preserved copy to a field\n- **Duplicate Serialize Reference**: allows to duplicate the linked reference (works only on collection elements)\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/serializereferenceoperations.png)\n\n#### Custom Editors \u003ca name=\"toolboxeditors\"\u003e\u003c/a\u003e\n\nIf you want to create a custom **UnityEditor.Editor** for your components and still use Toolbox-related features be sure to inherit from the **Toolbox.Editor.ToolboxEditor** class.\nMore details (e.g. how to customize properties drawing) you can find in the [HOWTO](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Assets/Editor%20Toolbox/HOWTO.md) document.\n\n```csharp\nusing UnityEditor;\nusing UnityEngine;\n#if UNITY_2019_1_OR_NEWER\nusing UnityEditor.UIElements;\nusing UnityEngine.UIElements;\n#endif\nusing Toolbox.Editor;\n\n[CustomEditor(typeof(SampleBehaviour))]\npublic class SampleEditor : ToolboxEditor\n{\n\tprivate void OnEnable()\n\t{ }\n\n\tprivate void OnDisable()\n\t{ }\n\n\tpublic override void DrawCustomInspector()\n\t{\n\t\tbase.DrawCustomInspector();\n\t\t\n\t\t//for custom properties:\n\t\t// - ToolboxEditorGui.DrawToolboxProperty(serializedObject.FindProperty(\"myProperty\"));\n\t}\n}\n```\n\n##### Custom Editor Implementations\n- **Toolbox.Editor.ToolboxEditor**: default class, override it if you want to implement a custom Editor for your components and ScriptableObjects\n- **Toolbox.Editor.ToolboxScriptedImporterEditor**: override it if you want to implement a custom Editor for your custom importers\n\n### Material Drawers \u003ca name=\"materialdrawers\"\u003e\u003c/a\u003e\n\n```\n[CompactTexture]\n_MainTex (\"Texture\", 2D) = \"white\" {}\n[Vector2]\n_Vector1 (\"Vector2\", Vector) = (0.0, 0.0, 0.0)\n[Vector3]\n_Vector2 (\"Vector3\", Vector) = (0.0, 0.0, 0.0)\n[MinMaxSlider(20.0, 165.0)]\n_Vector3 (\"MinMax Vector\", Vector) = (50.0, 55.0, 0.0)\n[Indent(3)]\n_Float1 (\"Float1\", Float) = 0.0\n[Help(Custom Help Box , 1)]\n_Float2 (\"Float2\", Float) = 0.0\n_Float3 (\"Float3\", Float) = 0.0\n[Title(Custom Title, 4)]\n_Float (\"Float\", Float) = 0.5\n[Toggle][Space]\n_ToggleProperty (\"Toggle\", Int) = 0\n[ShowIfToggle(_ToggleProperty)]\n_ShowIfExample (\"Texture\", 2D) = \"White\" {}\n[HideIfToggle(_ToggleProperty)]\n_HideIfExample (\"Range\", Range(0, 1)) = 0.75\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/customshader.png)\n\n## Serialized Types\n\n#### SerializedType\n\nAllows to serialize Types and pick them through a dedicated picker.\n\n```csharp\n[TypeConstraint(typeof(Collider), AllowAbstract = false, AllowObsolete = false, TypeSettings = TypeSettings.Class, TypeGrouping = TypeGrouping.None)]\npublic SerializedType serializedType;\n\npublic void Usage()\n{\n\tSystem.Type type = serializedType.Type;\n}\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/serializedtype.png)\n\n#### SerializedScene\n\nAllows to serialize SceneAssets and use them in Runtime.\n\n```csharp\npublic SerializedScene serializedScene;\n\npublic void Usage()\n{\n\tUnityEngine.SceneManagement.SceneManager.LoadScene(serializedScene.BuildIndex);\n}\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/serializedscene.png)\n\n```csharp\n[SceneDetails]\npublic SerializedScene serializedScene;\n```\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/scenedetails.png)\n\nKeep in mind that SerializedScene stores Scene's index, name and path. These properties are updated each time scenes collection in the Build Settings is updated or any SceneAsset is created/removed/reimported. \nUnfortunately, you need to handle associated objects reserialization by yourself, otherwise e.g. updated indexes won't be saved. I prepared for you a static event `SceneSerializationUtility.OnCacheRefreshed` that can be used to validate SerializedScenes in your project. \nYou can link SerializedScene in a ScriptableObject and trigger reserialization (`EditorUtility.SetDirty()`) if needed, it's really convinient approach.\n\n#### SerializedDictionary\u003cTK, TV\u003e\n\nAllows to serialize and use Dictionaries. The presented class implements the IDictionary interface, so it can be easily used like the standard version.\n\nRequires at least Unity 2020.1.x because of generic serialization and has to be assigned in the Settings file.\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/dictionary3.png)\n\n```csharp\n#if UNITY_2020_1_OR_NEWER\npublic SerializedDictionary\u003cint, GameObject\u003e serializedDictionary;\n\npublic void Usage()\n{\n\tserializedDictionary.Add(3, new GameObject(\"TestObject\"));\n\tserializedDictionary.ContainsKey(2);\n\t//etc. like standard System.Collections.Generic.Dictionary\u003c\u003e\n\tSystem.Collections.Generic.Dictionary\u003cint, GameObject\u003e dictionary = serializedDictionary;\n}\n#endif\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/dictionary1.png)\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/dictionary2.png)\n\n#### SerializedDateTime\n\nAllows to serialize DateTime.\n\n```csharp\npublic SerializedDateTime serializedDateTime;\n\npublic void Usage()\n{\n\tSystem.DateTime dateTime = serializedDateTime;\n}\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/serializeddate.png)\n\n#### SerializedDirectory\n\nAllows to serialize folders in form of assets and retrieve direct paths in runtime.\n\n```csharp\npublic SerializedDirectory serializeDirectory;\n\npublic void Usage()\n{\n\tstring path = serializeDirectory.DirectoryPath;\n}\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/serializeddirectory.png)\n\n## Editor Extensions\n\n### Hierarchy \u003ca name=\"hierarchy\"\u003e\u003c/a\u003e\n\nEnable and customize the presented hierarchy overlay in the **ToolboxEditorSettings**. Basically it provides more data about particular GameObjects directly within the Hierarchy window. Additionally, you can create special 'Header' objects using the '#h' prefix or Create menu: **GameObject/Editor Toolbox/Hierarchy Header** (by default created object will have **EditorOnly** tag).\n\nEach row can contain:\n- Scripts information\n- Layer\n- Tag\n- Toggle to enable/disable GameObject\n- Icon\n- Tree Lines\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/hierarchy.png)\n\n### Project \u003ca name=\"project\"\u003e\u003c/a\u003e\n\nSet custom folder icons in the **ToolboxEditorSettings**.\n\nProperties that can be edited include:\n- XY position and scale of the large icon\n- XY position and scale of the small icon\n- Path to directory or name (depends on picked item type)\n- Optional tooltip\n- Large icon\n- Small icon\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/project1.png)\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/project2.png)\n\n### Toolbar \u003ca name=\"toolbar\"\u003e\u003c/a\u003e\n\n\u003e Editor Toolbox/Editor/ToolboxEditorToolbar.cs\n\nCheck **Examples** for more details.\n\n\u003e Examples/Editor/SampleToolbar.cs\n\n```csharp\nusing Toolbox.Editor;\n\n[UnityEditor.InitializeOnLoad]\npublic static class MyEditorUtility\n{\n\tstatic MyEditorUtility()\n\t{\n\t\tToolboxEditorToolbar.OnToolbarGui += OnToolbarGui;\n\t}\n\t\n\tprivate static void OnToolbarGui()\n\t{\n\t\tGUILayout.FlexibleSpace();\n\t\tif (GUILayout.Button(\"1\", Style.commandLeftStyle))\n\t\t{\n\t\t\tDebug.Log(\"1\");\n\t\t}\n\t\tif (GUILayout.Button(\"2\", Style.commandMidStyle))\n\t\t{\n\t\t\tDebug.Log(\"2\");\n\t\t}\n\t\tif (GUILayout.Button(\"3\", Style.commandMidStyle))\n\t\t{\n\t\t\tDebug.Log(\"3\");\n\t\t}\n\t\tif (GUILayout.Button(\"4\", Style.commandMidStyle))\n\t\t{\n\t\t\tDebug.Log(\"4\");\n\t\t}\n\t\tif (GUILayout.Button(\"5\", Style.commandRightStyle))\n\t\t{\n\t\t\tDebug.Log(\"5\");\n\t\t}\n\t}\n}\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/toolbar.png)\n\n### SceneView \u003ca name=\"sceneview\"\u003e\u003c/a\u003e\n\nSelect a specific object that is under the cursor (default key: tab).\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/sceneview.png)\n\n### Utilities \u003ca name=\"utilities\"\u003e\u003c/a\u003e\n\nIn this section you will find various extensions that don't fit into a specific category.\n\n#### Context Menu operations\n\nCopy and paste all components from/to particular GameObject.\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/utils.png)\n\n#### Wizards\n\nIf you want to create custom wizards and still utilize Toolbox-related features then feel free to use the **ToolboxWizard** class.\nWorks in similar way to Unity's ScriptableWizard.\n\n\u003e Editor Toolbox/Editor/Wizards/ToolboxWizard.cs\n\n##### ScriptableObject Creation Wizard\n\nCreate multiple ScriptableObjects at once.\nWizard will allow only ScritpableObjects marked with **[Toolbox.Attributes.CreateInWizard]** or **[UnityEngine.CreateAssetMenu]** attributes.\n\n```\nAssets/Create/Editor Toolbox/ScriptableObject Creation Wizard\n```\n\n![inspector](https://github.com/arimger/Unity-Editor-Toolbox/blob/develop/Docs/createso.png)","funding_links":[],"categories":["GamePlay","C\\#","Open Source Repositories","C#","Open Source Packages"],"sub_categories":["HUD","Editor"],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Farimger%2FUnity-Editor-Toolbox","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Farimger%2FUnity-Editor-Toolbox","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Farimger%2FUnity-Editor-Toolbox/lists"}