views:

1318

answers:

2

I am attempting to create a Clipboard stack in C#. Clipboard data is stored in System.Windows.Forms.DataObject objects. I wanted to store each clipboard entry (IDataObject) directly in a Generic list. Due to the way Bitmaps (seem to be) stored I am thinking I need to perform a deep copy first before I add it to the list.

I attempted to use Binary serialization (see below) to create a deep copy but since System.Windows.Forms.DataObject is not marked as serializable the serialization step fails. Any ideas?

public IDataObject GetClipboardData()
{
    MemoryStream memoryStream = new MemoryStream();
    BinaryFormatter binaryFormatter = new BinaryFormatter();
    binaryFormatter.Serialize(memoryStream, Clipboard.GetDataObject());
    memoryStream.Position = 0;
    return (IDataObject) binaryFormatter.Deserialize(memoryStream);
}
+3  A: 

I wrote the code below for another question and maybe it could come in useful for you in this scenario:

    public static class GhettoSerializer
    {
            // you could make this a factory method if your type
            // has a constructor that appeals to you (i.e. default 
            // parameterless constructor)
            public static void Initialize<T>(T instance, IDictionary<string, object> values)
            {
                    var props = typeof(T).GetProperties();

                    // my approach does nothing to handle rare properties with array indexers
                    var matches = props.Join(
                            values,
                            pi => pi.Name,
                            kvp => kvp.Key,
                            (property, kvp) =>
                                    new {
                                            Set = new Action<object,object,object[]>(property.SetValue), 
                                            kvp.Value
                                    }
                    );

                    foreach (var match in matches)
                            match.Set(instance, match.Value, null);
            }
            public static IDictionary<string, object> Serialize<T>(T instance)
            {
                    var props = typeof(T).GetProperties();

                    var ret = new Dictionary<string, object>();

                    foreach (var property in props)
                    {
                            if (!property.CanWrite || !property.CanRead)
                                    continue;
                            ret.Add(property.Name, property.GetValue(instance, null));
                    }

                    return ret;
            }
    }

However I don't think this will be the final solution to your problem though it may give you a place to start.

cfeduke
Thanks for taking a shot at this (points for class naming convention as well). Unfortunately IDataObject contains no properties. Data is "extracted" using methods so the above code returns an empty Dictionary.
Sepia
Yes, it’s a bug in the code. Instead of `typeof(T).GetProperties()`, it should say `instance.GetType().GetProperties()`. In fact, I would argue it should actually use the fields rather than properties, but that’s a design choice.
Timwi
A: 

Look up the docks for Serializable and find the stuff about serialization helpers. You can wrap the bitmap in your own serialization code the integrates with the .net framework.

DrFloyd5