Skip to content

Instantly share code, notes, and snippets.

@Ardaurum
Last active May 9, 2021 18:20
Show Gist options
  • Star 2 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save Ardaurum/9a9bcbfaf331adaef095956c4a8167b4 to your computer and use it in GitHub Desktop.
Save Ardaurum/9a9bcbfaf331adaef095956c4a8167b4 to your computer and use it in GitHub Desktop.
`EditorObjectHighlight.cs` is the core that stores objects to highlight and renders them. There's also an `EditorObjectHighlight.shader` which is a transparent one color shader and can be easily extended. The `HighlightOnHover.cs` is an example usage of `EditorObjectHighlight`.
using System.Collections.Generic;
using UnityEngine;
namespace Ard.Tools
{
[InitializeOnLoad]
public static class EditorObjectHighlight
{
private static readonly List<HighlightObject> _highlights;
static EditorObjectHighlight()
{
_highlights = new List<HighlightObject>();
}
public static void DrawHighlight(object id, Mesh mesh, Color color, Matrix4x4 localToWorld, bool updateIfExists = true)
{
var highlight = _highlights.Find(h => h.Id == id);
if (highlight != null)
{
if (updateIfExists)
{
highlight.Mesh = mesh;
highlight.Material.color = color;
highlight.LocalToWorld = localToWorld;
}
return;
}
var highlightMaterial = new Material(Shader.Find("Hidden/EditorObjectHighlight")) {color = color};
_highlights.Add(new HighlightObject(mesh, highlightMaterial, localToWorld));
if (_highlights.Count == 1)
{
Camera.onPostRender += RenderHighlights;
}
}
private static void RenderHighlights(Camera cam)
{
for (var i = 0; i < _highlights.Count; i++)
{
HighlightObject highlight = _highlights[i];
_highlights[i].Material.SetPass(0);
Graphics.DrawMeshNow(highlight.Mesh, highlight.LocalToWorld);
Object.DestroyImmediate(_highlights[i].Material);
}
_highlights.Clear();
Camera.onPostRender -= RenderHighlights;
}
private class HighlightObject
{
public readonly object Id;
public Mesh Mesh;
public readonly Material Material;
public Matrix4x4 LocalToWorld;
public HighlightObject(object id, Mesh mesh, Material material, Matrix4x4 localToWorld)
{
Id = id;
Mesh = mesh;
Material = material;
LocalToWorld = localToWorld;
}
}
}
}
Shader "Hidden/EditorObjectHighlight"
{
Properties
{
}
SubShader
{
Tags { "RenderType"="Transparent" }
LOD 100
Blend SrcAlpha OneMinusSrcAlpha
Cull Off
Pass
{
CGPROGRAM
#pragma vertex vert
#pragma fragment frag
#include "UnityCG.cginc"
struct appdata
{
float4 vertex : POSITION;
float2 uv : TEXCOORD0;
};
struct v2f
{
float2 uv : TEXCOORD0;
float4 vertex : SV_POSITION;
};
sampler2D _MainTex;
float4 _MainTex_ST;
float4 _Color;
v2f vert (appdata v)
{
v2f o;
o.vertex = UnityObjectToClipPos(v.vertex);
o.uv = TRANSFORM_TEX(v.uv, _MainTex);
return o;
}
fixed4 frag (v2f i) : SV_Target
{
fixed4 col = tex2D(_MainTex, i.uv);
if (col.a < 0.1)
{
discard;
}
return _Color;
}
ENDCG
}
}
}
using UnityEditor;
using UnityEngine;
namespace Ard.Tools
{
[InitializeOnLoad]
public static class HighlightOnHover
{
static HighlightOnHover()
{
SceneView.duringSceneGui += Update;
}
private static void Update(SceneView sceneView)
{
if (Event.current == null)
{
return;
}
Ray ray = HandleUtility.GUIPointToWorldRay(Event.current.mousePosition);
if (Physics.Raycast(ray, out RaycastHit hit))
{
var meshFilter = hit.transform.GetComponent<MeshFilter>();
if (meshFilter == null)
{
return;
}
EditorObjectHighlight.DrawHighlight(meshFilter, meshFilter.sharedMesh, Color.green, hit.transform.localToWorldMatrix);
}
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment