/// <summary> /// Special version of <see cref="ICloneOperation.HandleObject"/> for cases where the target object graph alreay /// exists and it is undesireable for a source value of null to overwrite a non-null target value. /// </summary> /// <typeparam name="T"></typeparam> /// <param name="operation"></param> /// <param name="source"></param> /// <param name="target"></param> /// <param name="dontNullifyExternal"></param> /// <returns></returns> public static void HandleObject <T>(this ICloneOperation operation, T source, ref T target, bool dontNullifyExternal) where T : class { if (object.ReferenceEquals(source, null) && dontNullifyExternal && !operation.IsTarget(target)) { return; } operation.HandleObject(source, ref target); }
public override void CreateTargetObjectLate(Delegate source, ref Delegate target, ICloneOperation operation) { Delegate[] sourceInvokeList = (source != null) ? source.GetInvocationList() : null; Delegate[] targetInvokeList = (target != null) ? target.GetInvocationList() : null; RawList <Delegate> mergedInvokeList = new RawList <Delegate>( ((sourceInvokeList != null) ? sourceInvokeList.Length : 0) + ((targetInvokeList != null) ? targetInvokeList.Length : 0)); // Iterate over our sources invocation list and copy entries are part of the target object graph if (sourceInvokeList != null) { for (int i = 0; i < sourceInvokeList.Length; i++) { if (sourceInvokeList[i].Target == null) { continue; } object invokeTargetObject = null; if (operation.GetTarget(sourceInvokeList[i].Target, ref invokeTargetObject)) { MethodInfo method = sourceInvokeList[i].GetMethodInfo(); Delegate targetSubDelegate = method.CreateDelegate(sourceInvokeList[i].GetType(), invokeTargetObject); mergedInvokeList.Add(targetSubDelegate); } } } // Iterate over our targets invocation list and keep entries that are NOT part of the target object graph if (targetInvokeList != null) { for (int i = 0; i < targetInvokeList.Length; i++) { if (targetInvokeList[i].Target == null) { continue; } if (!operation.IsTarget(targetInvokeList[i].Target)) { MethodInfo method = targetInvokeList[i].GetMethodInfo(); Delegate targetSubDelegate = method.CreateDelegate(targetInvokeList[i].GetType(), targetInvokeList[i].Target); mergedInvokeList.Add(targetSubDelegate); } } } // Create a new delegate instance Delegate[] mergedInvokeArray = mergedInvokeList.Data; if (mergedInvokeArray.Length != mergedInvokeList.Count) { Array.Resize(ref mergedInvokeArray, mergedInvokeList.Count); } target = Delegate.Combine(mergedInvokeArray); }