- Home /
 
Assistance needed with serialization, inheritance and scriptableobject
So I've hit that roadblock of "I'm trying to serialize child classes but everything is being serialized as the parent class". I expected this, but despite the base class inheriting from ScriptableObject, I can't seem to store my instances in a .asset file, as they're showing up with a Type Mismatch error.
Here's an example: I have a generic ScriptableObjectDatabase class, which should be capable of storing whatever I pass it:
 public class ScriptableObjectDatabase<T> : ScriptableObject where T : class
 {
     [SerializeField] protected List<T> database = new List<T>();
     public static T GetDatabase<T>(string dbPath, string dbName) where T : ScriptableObject
     {
         var dbFullPath = @"Assets/" + dbPath + "/" + dbName;
         var db = AssetDatabase.LoadAssetAtPath(dbFullPath, typeof(T)) as T;
         if (db != null) return db;
         if (!AssetDatabase.IsValidFolder("Assets/" + dbPath))
             AssetDatabase.CreateFolder("Assets", dbPath);
         db = CreateInstance<T>();
         AssetDatabase.CreateAsset(db, dbFullPath);
         AssetDatabase.SaveAssets();
         AssetDatabase.Refresh();
         return db;
     }
 }
 
               Then different types of databases exist with different functionality, the one I'm working on now being the ItemDatabase which does very little. So I have an Item class, which is the base for other classes, such as Equipment etc.
 public class Item : ScriptableObject
 {
     //fields etc
 }
 public class Equipment : Item
 {
     //equipment specific fields
 }
 
               I then have an item editor window, which is responsible for managing the items in a .asset file.
 public class ItemEditor : EditorWindow
 {
     private ItemDatabase itemDatabase;
     
     private void OnEnable()
     {
         if (itemDatabase == null)
             itemDatabase = ItemDatabase.GetDatabase<ItemDatabase>(DATABASE_PATH, ITEM_DATABASE_NAME);
     }
     
     private void OnGUI()
     {
         if (GUILayout.Button("Add"))
         {
             ItemDatabase.Add(CreateInstance<Item>());
         }
     }
 }
 
               Then finally when I look at the database via the inspector, I see the following: 
 I'm assuming that the information inside the database is no longer saving as SetDirty(itemDatabase) isn't enough to trigger saving the scriptable object? I can edit things on the fly but writing them to disk isn't working out right now.
Any guidance on what I'm doing wrong would be greatly appreciated.
I am not totally sure about what I'm about to say, but I think the problem is working with T ins$$anonymous$$d of ScriptableObjectDatsBase. if T was a float then that's what you're using for your AssetDatabase, not the actual ScriptableObject as a whole.
furthermore, I'm pretty sure only concrete classes are capable of being serializable, but proof me wrong. the last time I tried genetics with that I needed to create subclasses for each type. 
Answer by Adam-Mechtley · Feb 07, 2017 at 08:08 AM
Is there a reason your generic type constraint on ScriptableObjectDatabase is simply class? It seems to me like it should be ScriptableObject. I wonder if that would make the difference.
Also, I'd suggest for readability that you rewrite the signature for GetItemDatabase as something like public static TDatabase GetItemDatabase<TDatabase> (string dbPath, string dbName) where TDatabase : ScriptableObjectDatabase<T> 
Your answer
 
             Follow this Question
Related Questions
Multiple Cars not working 1 Answer
Distribute terrain in zones 3 Answers
How do I access assets of an asset database .asset file via c# ? 1 Answer