- Home /
3D textmesh not being drawn properly in a 2D game
Ok, so I've been having a couple of issues with 3D text in my 2D game. Mainly it boils down to setting the depth of the 3D text to be behind other objects instead of drawing over the top. I've changed the shader to match the one that I've seen linked around on the unity forums and it sort of works and sort of doesnt. When I created a test scene with just one cube and some 3d text it worked perfectly with the text being hidden behind the cube, however in my actual game scene (when I apply the same font & text material) it doesn't work the same way.
The only reason I can see this happening is because I'm using sprites in my main game and was using a cube in my test scene. Maybe there's an issue with the sorting depth interfering with how things are drawn? I am very stuck on this issue and I'd love any help.
I also read somewhere that non-sprite objects were sent to the default sorting layer, so this might be what's causing the issue? But I still wouldn't know how to fix it if this were the case.
Here are some pictures to illustrate the issue: This one is working exactly as it should (this is the text scene). The text is behind the object since it is further away from the camera.
However, in the actual game scene the text for the behind clipboard is being rendered on top of the above clipboard, even though it's set up almost the exact same as in the test scene.
Thanks for any light you're able to shed on this one :).
Answer by Xorglord · Dec 13, 2013 at 09:21 AM
Ok I've got an answer, finally! The problem was because of all non-sprite components defaulting to be in the "default" sorting layer. I though it wasn't possible to edit the sorting layer or layer order of non-sprite elements since there are no sorting options in their renderers, but apparently those options are accessible via code and are just not available in the Inspector.
More info here http://forum.unity3d.com/threads/211822-Using-non-Sprites-with-the-new-sorting-layers
Anyway, by using
GetComponent().sortingLayerID = blah;
and .sortingOrder = blah;
I was able to set the rendering depth of the text. Thanks for the advice though Young :).
I'll do you one better. This guy wrote an editor component that allows you to set it in the inspector on any renderer. Wooo!
https://github.com/nickgravelyn/UnityToolbag/tree/master/Sorting%20Layer%20Exposed
Thanks for posting and answering the question. Highly appreciated.
You can attach this script to such objects so you can edit these parameters right in the Editor, though they won't have effect until the game is run.
using UnityEngine;
using System.Collections;
public class SortingLayerExposer : $$anonymous$$onoBehaviour
{
public string SortingLayerName = "Default";
public int SortingOrder = 0;
void Awake ()
{
gameObject.GetComponent<$$anonymous$$eshRenderer> ().sortingLayerName = SortingLayerName;
gameObject.GetComponent<$$anonymous$$eshRenderer> ().sortingOrder = SortingOrder;
}
}
Goddamit - I wanted to report you for being awesome... however, that is not possible :( I have ins$$anonymous$$d rewarded you with an upvote and this comment. You are awesome!
To get it shown in-Editor (pre-Play time), here's an updated version of @$$anonymous$$arzoa's code (also mentioned above by @Jinxology)
using UnityEngine;
/// <summary>
/// Place on a 3D object to modify its visibility relative to Sprite 'sorting
/// layers'.
/// </summary>
[ExecuteInEdit$$anonymous$$ode]
public sealed class SortingLayerExposer : $$anonymous$$onoBehaviour {
[SerializeField]
private string SortingLayerName = "Default";
[SerializeField]
private int SortingOrder = 0;
public void OnValidate() {
apply();
}
public void OnEnable() {
apply();
}
private void apply() {
var meshRenderer = gameObject.GetComponent<$$anonymous$$eshRenderer>();
meshRenderer.sortingLayerName = SortingLayerName;
meshRenderer.sortingOrder = SortingOrder;
}
}
This works like a charm, thanks for providing me a solution.
This had been causing me such a headache for the opposite reason (I wanted to display text above sprites in different layers) thank you for sharing that information!
Answer by kernjiro · Jul 20, 2014 at 09:09 PM
Alright, I had this problem too and the only solutions i could find were SUPER complicated. Here, just attach this simple script to any game object with a mesh renderer.(C#)
using UnityEngine; using System.Collections;
public class RendererSorter : MonoBehaviour {
void Start () {
this.gameObject.GetComponent<MeshRenderer>().sortingLayerName = "Foreground";
//or whatever your layer name is
this.gameObject.GetComponent<MeshRenderer>().sortingOrder = 50;
//or whatever order you want it in the layer
}
}
Answer by Free286 · Jun 08, 2016 at 03:55 PM
It is a useful pattern to write code that only runs in the editor, Unity internally serializes many fields such as the sorting layer and order, which we can take advantage of by creating editor only scripts. This is especially important on mobile platforms, where performance is critical.
[ExecuteInEditMode]
[RequireComponent(typeof(TextMesh))]
public class CONTENT_Text : MonoBehaviour
{
public string sortingLayerName = "Default";
public int orderInLayer = 0;
#if UNITY_EDITOR
public void Update ()
{
gameObject.GetComponent<MeshRenderer>().sortingLayerName = sortingLayerName;
gameObject.GetComponent<MeshRenderer>().sortingOrder = orderInLayer;
}
#endif
}
Answer by YoungDeveloper · Dec 13, 2013 at 01:31 AM
When you render anything gui related (text, rect, etc), you can use GUI.depth to set render priority, for example GUI.depth=0; is on top of everything.
http://docs.unity3d.com/Documentation/ScriptReference/GUI-depth.html
Does the GUI Depth work in relation to the depth of the other objects in the scene which aren't GUI? I tried looking at the reference you linked but it wasn't that informative. I assume since the sprites aren't really gui, their spriterenderer doesn't have a GUI.depth property? What would I set the 3D text's gui depth to be so it renders in front of some sprites and behind others?
For what exactly are you using sprites in the view ?
Im a little confused by your question. The game is in 2D, so all of the objects are basically sprites apart from the dynamically created stuff (like text). Everything is a sprite apart from the text at this point.
EDIT: I might have misunderstood what you meant by view, i'm not sure. You mean just like, the view in the game?
Yea, i mean game view, overally i never had any experience with sprites, so i can't tell much about it's render priority with gui text. I'm not sure why are you using sprites for drawing those notepads. You could use gui for all this and there would be no broblems. The only idea what comes to my $$anonymous$$d for now is drawing transparent gui box in the shape of the front notepad, so by that you could hide background text, but that might be inefficient from optimization perspective.
Yeah I feel like it might be a bit inefficient, plus I'd have to draw one for each item like a clipboard that I had (there would be multiple). I guess it's my best option for now though. I've never really used GUI, but wouldn't it be a bit dodgy to render every sprite in a 2D game with GUI? I feel like it should be reserved for actual GUI elements haha.
Answer by GreyEyedBeast · Feb 17, 2014 at 12:49 AM
setting my default layer to render on top seems to have fixed my issues
Your answer
Follow this Question
Related Questions
If Statements with PlayerPrefs 1 Answer
Display Emojis using its HTML code in a text 1 Answer
Is it possible to make textMeshProGui text to toggle with the unity editor gizmo's button? 0 Answers
TextMeshPro smallcaps option is converting "i" to "İ" not "I", why ? 1 Answer
Mesh with Transparent material makes TextMesh in front of it invisible 3 Answers