Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/319.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/wpf/14.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 在WPF中撤消/重做集合_C#_Wpf_Datagrid_Undo Redo - Fatal编程技术网

C# 在WPF中撤消/重做集合

C# 在WPF中撤消/重做集合,c#,wpf,datagrid,undo-redo,C#,Wpf,Datagrid,Undo Redo,我有一个简单的WPF屏幕,带有DataGrid和一些用于剪切、复制、粘贴和删除行的按钮: 我想为所有操作(如剪切/复制/粘贴/添加/删除等)实现Undo/Redo功能。我愿意使用另一个收集控件,而不是DataGrid,如果它们比其他控件有一些好处的话。我在stackoverflow.com上浏览了一些关于同一主题的其他问题,但没有发现它们有用。您应该实现 使用此模式,每个操作都有一个反操作(重做/撤消)。您可以在堆栈中保存应用的和撤消的命令。这将允许您撤消和重做所有命令。WPF在这方面非常好,

我有一个简单的WPF屏幕,带有
DataGrid
和一些用于剪切、复制、粘贴和删除行的按钮:

我想为所有操作(如剪切/复制/粘贴/添加/删除等)实现
Undo/Redo
功能。我愿意使用另一个收集控件,而不是
DataGrid
,如果它们比其他控件有一些好处的话。我在stackoverflow.com上浏览了一些关于同一主题的其他问题,但没有发现它们有用。

您应该实现


使用此模式,每个操作都有一个反操作(重做/撤消)。您可以在堆栈中保存应用的和撤消的命令。这将允许您撤消和重做所有命令。WPF在这方面非常好,因为您可以直接将命令绑定到元素,而不是普通事件。

我认为这个功能最容易使用特殊框架实现,它们通常不是大型的和免费的。有许多框架允许您实现
Undo/Redo
功能。就我个人而言,我喜欢他,他是我用过的最简单、最舒服的人之一。整个工作重点在于:

每个操作都封装了对域模型的更改。准备动作的过程与执行动作是明确分开的。一个动作的执行可能会在准备好并安排好之后的一个更晚的阶段。任何操作都实现了
IAction
,本质上提供了两种方法:一种用于实际操作,另一种用于撤销操作

最重要的是创建一个AbstractAction接口类并将其保存在正确的位置。您必须使用
ActionManager
来保留将来要撤消的操作:

private void SomeActionLogic()
{
    MyAction action = new MyAction(parameter);
    actionManager.RecordAction(action);
}
然后在某处使用
Undo/Redo

actionManager.Undo();
...
actionManager.Redo();
<> P>你需要考虑如何使用<代码>抽象动作> /代码>类中的集合吗?可能这会耗费大量的人力资源,因为每次触发
Undo/Redo
时都需要处理集合

使用的简单示例,摘自:


@我的回答对你有帮助?
class Program
{
    static void Main(string[] args)
    {
        Console.WriteLine("Original color");

        SetConsoleColor(ConsoleColor.Green);
        Console.WriteLine("New color");

        actionManager.Undo();
        Console.WriteLine("Old color again");

        using (Transaction.Create(actionManager))
        {
            SetConsoleColor(ConsoleColor.Red); // you never see Red
            Console.WriteLine("Still didn't change to Red because of lazy evaluation");
            SetConsoleColor(ConsoleColor.Blue);
        }

        Console.WriteLine("Changed two colors at once");

        actionManager.Undo();
        Console.WriteLine("Back to original");

        actionManager.Redo();
        Console.WriteLine("Blue again");
        Console.ReadKey();
    }

    static void SetConsoleColor(ConsoleColor color)
    {
        SetConsoleColorAction action = new SetConsoleColorAction(color);
        actionManager.RecordAction(action);
    }

    static ActionManager actionManager = new ActionManager();
}

class SetConsoleColorAction : AbstractAction
{
    public SetConsoleColorAction(ConsoleColor newColor)
    {
        color = newColor;
    }

    ConsoleColor color;
    ConsoleColor oldColor;

    protected override void ExecuteCore()
    {
        oldColor = Console.ForegroundColor;
        Console.ForegroundColor = color;
    }

    protected override void UnExecuteCore()
    {
        Console.ForegroundColor = oldColor;
    }
}