public void Write(BinaryOutputStream s)
 {
     properties.WriteToStream(s);
     if (layout == null)
     {
         s.WriteBool(false);
         return;
     }
     s.WriteBool(true);
     s.WriteObject(layout);
 }
        public void WriteToStream(BinaryOutputStream s, bool is_short_version = false)
        {
            if (!is_short_version)
            {
                s.WriteBool(true);
            }

            List<KeyValuePair<string, int>> name_list = new List<KeyValuePair<string, int>>();
            List<Action> write_desc = new List<Action>();
            List<Action> write_values = new List<Action>();
            foreach (PropertyInfo pi in this.GetType().GetTypeInfo().GetProperties())
            {
                string name = pi.Name;
                int type = GetTypeId(pi.PropertyType.GetTypeInfo());
                int raw_type = type;
                var atts = pi.GetCustomAttributes(typeof(ExplicitTypeAttribute));
                if (atts.Count() == 1)
                {
                    type = ((ExplicitTypeAttribute) atts.First()).value;
                }

                name_list.Add(new KeyValuePair<string, int>(name, name_list.Count));
                write_desc.Add(() =>
                {
                    s.WriteString(name);
                    s.WriteInt32(type);
                });
                write_values.Add(() =>
                {
                    type_handlers[raw_type].WriteField(this, pi, s);
                });
            }
            name_list.Sort((a, b) => a.Key.CompareTo(b.Key));

            s.WriteInt32(name_list.Count);
            foreach (var n in name_list)
            {
                write_desc[n.Value]();
            }
            foreach (var n in name_list)
            {
                write_values[n.Value]();
            }
        }