|
// Licensed to the .NET Foundation under one or more agreements.
// The .NET Foundation licenses this file to you under the MIT license.
// See the LICENSE file in the project root for more information.
//
// Description: Undo wrapper for any edit on or through a TextRange or
// TextContainer.
//
using System;
using System.Windows;
using MS.Internal;
using MS.Internal.Documents;
namespace System.Windows.Documents
{
// Undo wrapper for any edit on or through a TextRange or TextContainer.
internal class ChangeBlockUndoRecord
{
//------------------------------------------------------
//
// Constructors
//
//------------------------------------------------------
#region Constructors
// Constructor, called when a change block is opening.
internal ChangeBlockUndoRecord(ITextContainer textContainer, string actionDescription)
{
if (textContainer.UndoManager != null)
{
_undoManager = textContainer.UndoManager;
if (_undoManager.IsEnabled)
{
// Don't bother opening an undo unit if the owning control is
// still being initialized (ie, programmatic load by parser).
if (textContainer.TextView != null)
{
// Don't bother opening a new undo unit if we're already nested
// inside another.
if (_undoManager.OpenedUnit == null)
{
if (textContainer.TextSelection != null)
{
_parentUndoUnit = new TextParentUndoUnit(textContainer.TextSelection);
}
else
{
_parentUndoUnit = new ParentUndoUnit(actionDescription);
}
_undoManager.Open(_parentUndoUnit);
}
}
else
{
// If the owning control isn't initialized (parser is still running),
// don't add anything to the undo record. Instead, clear it.
_undoManager.Clear();
}
}
}
}
#endregion Constructors
//------------------------------------------------------
//
// Internal Methods
//
//------------------------------------------------------
#region Internal Methods
// Called when a change block is closing.
internal void OnEndChange()
{
// Commit our undo unit.
if (_parentUndoUnit != null)
{
IParentUndoUnit openedUnit;
if (_parentUndoUnit.Container is UndoManager)
{
openedUnit = ((UndoManager)_parentUndoUnit.Container).OpenedUnit;
}
else
{
openedUnit = ((IParentUndoUnit)_parentUndoUnit.Container).OpenedUnit;
}
// UIElementPropertyUndoUnit can clear the undo stack if a change is made to a databound property
if (openedUnit == _parentUndoUnit)
{
if (_parentUndoUnit is TextParentUndoUnit)
{
((TextParentUndoUnit)_parentUndoUnit).RecordRedoSelectionState();
}
Invariant.Assert(_undoManager != null);
_undoManager.Close(_parentUndoUnit, (_parentUndoUnit.LastUnit != null) ? UndoCloseAction.Commit : UndoCloseAction.Discard);
}
}
}
#endregion Internal Methods
//------------------------------------------------------
//
// Private Fields
//
//------------------------------------------------------
#region Private Fields
private readonly UndoManager _undoManager;
private readonly IParentUndoUnit _parentUndoUnit;
#endregion Private Fields
}
}
|