Why, Unity? Like… it’s a dictionary!! It’s literally a json! I’d understand if I was asking something vastly complicated and you were like “nah, dude, too hard”. But it’s a dictionary! Why can’t you just loop over keys and shove them into a string???
If you want to use dictionarys take a look at json.net.
Unity did optimize the JsonUtility for speed and does not support all possible features.
Since version 2020.3 Unity already includes the “Json .NET” (v12) as a package found in the package manager.
Note that the “Json .Net for Unity” asset on the store is outdated and runs on v8 or something. Still works, according to reviews, but it is quite interesting that Unity now includes the latest Github project as a semi-official package.
After import just use
string json = JsonConvert.SerializeObject(object);
instead of the “old”
string json = JsonUtility.ToJson(object);
It serializes Dictionaries properly.
Here you find the official docs:
I can’t find this in the package manager or any info on the package when googling
Package info and installation instructions here^
thank you!
Good info but this still doesn’t explain why Unity doesn’t just add this basic functionality to the built-in utility? Is there no native equivalent of a Dictionary on some platforms?
The simple answer is that JsonUtility uses the same serialization mechanism as the rest of Unity (the same one used for serializing asset files, scene files, Instantiate, etc) and that serialization mechanism does not support dictionaries.
The longer answer is that serializing Dictionaries would add a lot of complexity to an otherwise very simple and performant framework which is optimized for speed. Unity’s serializer is fast, and since the workarounds for a serialized Dictionary are pretty simple, it’s not worth sacrificing performance for it.
what is the workaround? I’m developing a library (asset) and don’t want to pull an extra Newtonsoft.Json dependency for this small task, because that will force all my users to pull the same dependency as well.
That’s not a big deal as long as you are Unity2020 or onwards: AFAIK it becomes automagically added at that point.
Problems with Unity “tiny lite” built-in JSON:
In general I highly suggest staying away from Unity’s JSON “tiny lite” package. It’s really not very capable at all and will silently fail on very common data structures, such as bare arrays, tuples, Dictionaries and Hashes and ALL properties.
Instead grab Newtonsoft JSON .NET from the Unity Package Manager (Window → Package Manager).
If you want to avoid the Package Mangler’s UI, just add this to your Packages/manifest.json file:
"com.unity.nuget.newtonsoft-json": "3.0.2",
The former asset store package is now deprecated, as you can see here:
https://assetstore.unity.com/packages/tools/input-management/json-net-for-unity-11347
Also, always be sure to leverage sites like:
https://jsonlint.com
https://json2csharp.com
https://csharptojson.com/
Off-topic, but…
You might want to update your copy-paste drafts. This site appears to be dead since June (domain for sale).
.
Thanks a lot! Looks like there’s another one here:
I shall update my notes accordingly. I really appreciate the heads-up.
also you can use this instead of Dictionary
[Serializable]
public class SerializableDictionary<K, V> : Dictionary<K, V>, ISerializationCallbackReceiver
{
[SerializeField]
private List<K> m_Keys = new List<K>();
[SerializeField]
private List<V> m_Values = new List<V>();
public void OnBeforeSerialize()
{
m_Keys.Clear();
m_Values.Clear();
using Enumerator enumerator = GetEnumerator();
while (enumerator.MoveNext())
{
KeyValuePair<K, V> current = enumerator.Current;
m_Keys.Add(current.Key);
m_Values.Add(current.Value);
}
}
public void OnAfterDeserialize()
{
Clear();
for (int i = 0; i < m_Keys.Count; i++)
{
Add(m_Keys[i], m_Values[i]);
}
m_Keys.Clear();
m_Values.Clear();
}
}