Skip to content

Instantly share code, notes, and snippets.

@spiney199
Last active January 20, 2025 19:38
Show Gist options
  • Save spiney199/8826eaafdfc215f16c0460d2125071df to your computer and use it in GitHub Desktop.
Save spiney199/8826eaafdfc215f16c0460d2125071df to your computer and use it in GitHub Desktop.
Unity - Snapping created GameObjects
if UNITY_EDITOR
namespace LBG.EditorUtils.Editor
{
using UnityEngine;
using UnityEditor;
using UnityEditor.Toolbars;
using UnityEngine.UIElements;
[EditorToolbarElement(SnapOnCreateToolbarToggle.id, typeof(SceneView))]
internal sealed class SnapOnCreateToolbarToggle : EditorToolbarToggle
{
public const string id = "Snapping/SnapOnCreate";
public SnapOnCreateToolbarToggle() : base()
{
text = "Snap On Create";
tooltip = "Toggles whether game objects are always automatically snapped to the grid on creation.";
icon = (Texture2D)EditorGUIUtility.Load("d_SceneViewSnap");
bool snapOnCreate = SnapSettings.instance.SnapOnCreate;
this.SetValueWithoutNotify(snapOnCreate);
this.RegisterValueChangedCallback<bool>(HandleToggleEvent);
}
private void HandleToggleEvent(ChangeEvent<bool> e)
{
SnapSettings.instance.SnapOnCreate = e.newValue;
}
}
}
#endif
#if UNITY_EDITOR
namespace LBG.EditorUtils.Editor
{
using UnityEditor;
using UnityEditor.Overlays;
[Overlay(typeof(SceneView), "Snapping Tools")]
internal sealed class SnappingToolbar : ToolbarOverlay
{
public SnappingToolbar() : base(SnapOnCreateToolbarToggle.id) { }
}
}
#endif
#if UNITY_EDITOR
namespace LBG.EditorUtils.Editor
{
using UnityEngine;
using UnityEditor;
[InitializeOnLoad]
internal static class SnappingTracker
{
static SnappingTracker()
{
ObjectChangeEvents.changesPublished += HandleCreatedGameObjects;
}
private static void HandleCreatedGameObjects(ref ObjectChangeEventStream stream)
{
int length = stream.length;
for (int i = 0; i < length; i++)
{
var eventType = stream.GetEventType(i);
if (eventType == ObjectChangeKind.CreateGameObjectHierarchy)
{
stream.GetCreateGameObjectHierarchyEvent(i, out var createdGameObjectsEvent);
int instanceID = createdGameObjectsEvent.instanceId;
if (AssetDatabase.Contains(instanceID) == true) // don't want to snap assets
{
return;
}
var createdGameObject = EditorUtility.InstanceIDToObject(instanceID) as GameObject;
var snaps = new Transform[] { createdGameObject.transform };
Handles.SnapToGrid(snaps);
}
}
}
}
}
#endif
#if UNITY_EDITOR
namespace LBG.EditorUtils.Editor
{
using System.Collections;
using System.Collections.Generic;
using UnityEditor;
using UnityEngine;
[FilePath("Library/LBGSnapSettings.asset", FilePathAttribute.Location.ProjectFolder)]
public sealed class SnapSettings : ScriptableSingleton<SnapSettings>
{
#region Inspector Fields
[SerializeField]
private bool _snapOnCreate;
#endregion
#region Properties
public bool SnapOnCreate
{
get => _snapOnCreate;
set => _snapOnCreate = value;
}
#endregion
private void OnDisable()
{
this.Save(true);
}
}
}
#endif
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment