public static bool Merge (ToolStrip sourceToolStrip, ToolStrip targetToolStrip)
		{
			// Check for exceptions
			if (sourceToolStrip == null)
				throw new ArgumentNullException ("sourceToolStrip");
				
			if (targetToolStrip == null)
				throw new ArgumentNullException ("targetName");
				
			if (targetToolStrip == sourceToolStrip)
				throw new ArgumentException ("Source and target ToolStrip must be different.");
			
			// If the toolstrips don't allow merging, don't merge them
			if (!sourceToolStrip.AllowMerge || !targetToolStrip.AllowMerge)
				return false;
			
			// We currently can't support merging multiple times
			if (sourceToolStrip.IsCurrentlyMerged || targetToolStrip.IsCurrentlyMerged)
				return false;
				
			// What I wouldn't give to be able to modify a collection
			// while enumerating through it...

			List<ToolStripItem> items_to_move = new List<ToolStripItem> ();
			
			// Create a list of every ToolStripItem we plan on moving
			foreach (ToolStripItem tsi in sourceToolStrip.Items) {
				switch (tsi.MergeAction) {
					case MergeAction.Append:
					default:
						items_to_move.Add (tsi);
						break;
					case MergeAction.Insert:
						if (tsi.MergeIndex >= 0)
							items_to_move.Add (tsi);
						break;
					case MergeAction.Replace:
					case MergeAction.Remove:
					case MergeAction.MatchOnly:
						foreach (ToolStripItem target_tsi in targetToolStrip.Items)
							if (tsi.Text == target_tsi.Text) {
								items_to_move.Add (tsi);
								break;
							}
						break;
				}
			}

			// If there was nothing valid to merge, return false
			if (items_to_move.Count == 0)
				return false;
				
			// Set some state so we can unmerge later
			sourceToolStrip.BeginMerge ();
			targetToolStrip.BeginMerge ();			

			sourceToolStrip.SuspendLayout ();
			targetToolStrip.SuspendLayout ();
	
			while (items_to_move.Count > 0) {
				ToolStripItem tsi = items_to_move[0];
				items_to_move.Remove (tsi);
				
				switch (tsi.MergeAction) {
					case MergeAction.Append:
					default:
						// Just changing the parent will append it to the target
						// and remove it from the source
						ToolStrip.SetItemParent (tsi, targetToolStrip);
						
						break;
					case MergeAction.Insert:
						// Do the same work as Append, except Insert it into the
						// location specified by the MergeIndex
						RemoveItemFromParentToolStrip (tsi);

						if (tsi.MergeIndex == -1)
							continue;
						else if (tsi.MergeIndex >= CountRealToolStripItems (targetToolStrip))
							targetToolStrip.Items.AddNoOwnerOrLayout (tsi);						
						else
							targetToolStrip.Items.InsertNoOwnerOrLayout (AdjustItemMergeIndex (targetToolStrip, tsi), tsi);

						tsi.Parent = targetToolStrip;
						
						break;
					case MergeAction.Replace:
						// Find a target ToolStripItem with the same Text, remove it
						// and replace it with the source one
						foreach (ToolStripItem target_tsi in targetToolStrip.Items)
							if (tsi.Text == target_tsi.Text) {
								RemoveItemFromParentToolStrip (tsi);

								// Insert where the old one is, then remove the old one
								targetToolStrip.Items.InsertNoOwnerOrLayout (targetToolStrip.Items.IndexOf (target_tsi), tsi);
								targetToolStrip.Items.RemoveNoOwnerOrLayout (target_tsi);

								// Store the replaced one so we can get it back in unmerge
								targetToolStrip.HiddenMergedItems.Add (target_tsi);
								break;
							}

						break;
					case MergeAction.Remove:
						// Find a target ToolStripItem with the same Text, and remove
						// it from the target, nothing else
						foreach (ToolStripItem target_tsi in targetToolStrip.Items)
							if (tsi.Text == target_tsi.Text) {
								targetToolStrip.Items.RemoveNoOwnerOrLayout (target_tsi);
								
								// Store the removed one so we can get it back in unmerge
								targetToolStrip.HiddenMergedItems.Add (target_tsi);
								break;
							}

						break;
					case MergeAction.MatchOnly:
						// Ugh, find the target ToolStripItem with the same Text, and take
						// all the subitems from the source one, and append it to the target one
						foreach (ToolStripItem target_tsi in targetToolStrip.Items)
							if (tsi.Text == target_tsi.Text) {
								if (target_tsi is ToolStripMenuItem && tsi is ToolStripMenuItem) {
									ToolStripMenuItem source = (ToolStripMenuItem)tsi;
									ToolStripMenuItem target = (ToolStripMenuItem)target_tsi;
									
									ToolStripManager.Merge (source.DropDown, target.DropDown);
								}
								
								break;
							}
						
						break;
				}
			}
			
			sourceToolStrip.ResumeLayout ();
			targetToolStrip.ResumeLayout ();
			
			// Store who we merged with, so we can unmerge when only given the target toolstrip
			sourceToolStrip.CurrentlyMergedWith = targetToolStrip;
			targetToolStrip.CurrentlyMergedWith = sourceToolStrip;
			
			return true;
		}
Esempio n. 2
0
        public static bool Merge(ToolStrip sourceToolStrip, ToolStrip targetToolStrip)
        {
            // Check for exceptions
            if (sourceToolStrip == null)
            {
                throw new ArgumentNullException("sourceToolStrip");
            }

            if (targetToolStrip == null)
            {
                throw new ArgumentNullException("targetName");
            }

            if (targetToolStrip == sourceToolStrip)
            {
                throw new ArgumentException("Source and target ToolStrip must be different.");
            }

            // If the toolstrips don't allow merging, don't merge them
            if (!sourceToolStrip.AllowMerge || !targetToolStrip.AllowMerge)
            {
                return(false);
            }

            // We currently can't support merging multiple times
            if (sourceToolStrip.IsCurrentlyMerged || targetToolStrip.IsCurrentlyMerged)
            {
                return(false);
            }

            // What I wouldn't give to be able to modify a collection
            // while enumerating through it...

            List <ToolStripItem> items_to_move = new List <ToolStripItem> ();

            // Create a list of every ToolStripItem we plan on moving
            foreach (ToolStripItem tsi in sourceToolStrip.Items)
            {
                switch (tsi.MergeAction)
                {
                case MergeAction.Append:
                default:
                    items_to_move.Add(tsi);
                    break;

                case MergeAction.Insert:
                    if (tsi.MergeIndex >= 0)
                    {
                        items_to_move.Add(tsi);
                    }
                    break;

                case MergeAction.Replace:
                case MergeAction.Remove:
                case MergeAction.MatchOnly:
                    foreach (ToolStripItem target_tsi in targetToolStrip.Items)
                    {
                        if (tsi.Text == target_tsi.Text)
                        {
                            items_to_move.Add(tsi);
                            break;
                        }
                    }
                    break;
                }
            }

            // If there was nothing valid to merge, return false
            if (items_to_move.Count == 0)
            {
                return(false);
            }

            // Set some state so we can unmerge later
            sourceToolStrip.BeginMerge();
            targetToolStrip.BeginMerge();

            sourceToolStrip.SuspendLayout();
            targetToolStrip.SuspendLayout();

            while (items_to_move.Count > 0)
            {
                ToolStripItem tsi = items_to_move[0];
                items_to_move.Remove(tsi);

                switch (tsi.MergeAction)
                {
                case MergeAction.Append:
                default:
                    // Just changing the parent will append it to the target
                    // and remove it from the source
                    ToolStrip.SetItemParent(tsi, targetToolStrip);

                    break;

                case MergeAction.Insert:
                    // Do the same work as Append, except Insert it into the
                    // location specified by the MergeIndex
                    RemoveItemFromParentToolStrip(tsi);

                    if (tsi.MergeIndex == -1)
                    {
                        continue;
                    }
                    else if (tsi.MergeIndex >= CountRealToolStripItems(targetToolStrip))
                    {
                        targetToolStrip.Items.AddNoOwnerOrLayout(tsi);
                    }
                    else
                    {
                        targetToolStrip.Items.InsertNoOwnerOrLayout(AdjustItemMergeIndex(targetToolStrip, tsi), tsi);
                    }

                    tsi.Parent = targetToolStrip;

                    break;

                case MergeAction.Replace:
                    // Find a target ToolStripItem with the same Text, remove it
                    // and replace it with the source one
                    foreach (ToolStripItem target_tsi in targetToolStrip.Items)
                    {
                        if (tsi.Text == target_tsi.Text)
                        {
                            RemoveItemFromParentToolStrip(tsi);

                            // Insert where the old one is, then remove the old one
                            targetToolStrip.Items.InsertNoOwnerOrLayout(targetToolStrip.Items.IndexOf(target_tsi), tsi);
                            targetToolStrip.Items.RemoveNoOwnerOrLayout(target_tsi);

                            // Store the replaced one so we can get it back in unmerge
                            targetToolStrip.HiddenMergedItems.Add(target_tsi);
                            break;
                        }
                    }

                    break;

                case MergeAction.Remove:
                    // Find a target ToolStripItem with the same Text, and remove
                    // it from the target, nothing else
                    foreach (ToolStripItem target_tsi in targetToolStrip.Items)
                    {
                        if (tsi.Text == target_tsi.Text)
                        {
                            targetToolStrip.Items.RemoveNoOwnerOrLayout(target_tsi);

                            // Store the removed one so we can get it back in unmerge
                            targetToolStrip.HiddenMergedItems.Add(target_tsi);
                            break;
                        }
                    }

                    break;

                case MergeAction.MatchOnly:
                    // Ugh, find the target ToolStripItem with the same Text, and take
                    // all the subitems from the source one, and append it to the target one
                    foreach (ToolStripItem target_tsi in targetToolStrip.Items)
                    {
                        if (tsi.Text == target_tsi.Text)
                        {
                            if (target_tsi is ToolStripMenuItem && tsi is ToolStripMenuItem)
                            {
                                ToolStripMenuItem source = (ToolStripMenuItem)tsi;
                                ToolStripMenuItem target = (ToolStripMenuItem)target_tsi;

                                ToolStripManager.Merge(source.DropDown, target.DropDown);
                            }

                            break;
                        }
                    }

                    break;
                }
            }

            sourceToolStrip.ResumeLayout();
            targetToolStrip.ResumeLayout();

            // Store who we merged with, so we can unmerge when only given the target toolstrip
            sourceToolStrip.CurrentlyMergedWith = targetToolStrip;
            targetToolStrip.CurrentlyMergedWith = sourceToolStrip;

            return(true);
        }