使用.Net Json序列化标签对象

时间:2015-08-10 06:07:57

标签: c# .net winforms serialization json.net

我正在尝试使用json.Net序列化一个对象,但我得到以下异常。

Newtonsoft.Json.JsonSerializationException: Error getting value from 'Parent' on 'System.Windows.Forms.Label+LabelAccessibleObject'. ---> System.Runtime.InteropServices.COMException: Interface not registered (Exception from HRESULT: 0x80040155)
   at Accessibility.IAccessible.get_accParent()
   at System.Windows.Forms.AccessibleObject.get_Parent()
   at System.Windows.Forms.Control.ControlAccessibleObject.get_Parent()
   at GetParent(Object )
   at Newtonsoft.Json.Serialization.DynamicValueProvider.GetValue(Object target)

以下是我用来序列化的代码:

  var settings = new JsonSerializerSettings();
  settings.TypeNameHandling = TypeNameHandling.Objects;
  Console.WriteLine(JsonConvert.SerializeObject(y), Formatting.Indented, settings);

奇怪的是我认为异常意味着我需要添加一个辅助功能参考,但添加它并没有修复任何问题。

还值得一提的是,y在这种情况下是一个Label对象。看起来串行器函数试图读取y的accessibility属性并失败。

编辑:仅供参考我在网站上推荐使用软件包管理器安装它,所以我怀疑它在64位运行32位或类似的东西。感谢。

1 个答案:

答案 0 :(得分:0)

WinForms对象非常复杂,我不会尝试序列化所有内容。这样做不能重新创建表单。一个问题是控件被添加到表单的顺序(也控制它们如何停靠)。

您需要创建DTO(仅包含相关属性的简单对象)并将其序列化。

public class LabelDTO
{
    public LabeLDTO(Label label)
    {
        Name = label.Name;
        Text = label.Text;
    }

    protected LabelDTO()
    {
    }

    public string Text { get; set; }
    public string Name { get; set; }
}

public class DtoFactory
{
    Dictionary<Type, Func<Control, object> _factories = new Dictionary<Type, Func<Control, object>();

    public DtoFactory()
    {
        _factories.Add(typeof(Label), ctrl => new LabelDTO(ctrl));
    }

    public object Create(Control control)
    {
        Func<Control, object> factoryMethod;
        return _factories.TryGetValue(control.GetType(), out factoryMethod)
            ? factoryMethod(control)
            : throw new NotSupportedException("Failed to find factory for " + control.GetType().FullName); 
    }
}


List<object> formData = new List<object>();
foreach (var control in Form.Controls) 
{
    var dto = DtoFactory.Create(control);
    formData.Add(dto);        
}

var json = JsonConvert.SerializeObject(formData);